Переместить окно Kivy путем перетаскивания метки - Kivy, Python
Я хочу создать пользовательский заголовок окна Kivy. Я очень новичок в kivy, поэтому, пожалуйста, предоставьте некоторые объяснения, как работают события. Мне нужно просто переместить окно, "перемещая" метку.
Прежде всего я хочу знать, почему это вызывает любую функцию, когда я щелкаю или перетаскиваю ярлык. Это в KvLang:
#:import main main.window
CustBoxLayout:
<CustBoxLayout>:
orientation: 'vertical'
Label:
id: header
text: 'MyApp'
font_size: 24
padding_x: 16
color: self.theme_cls.primary_color
on_touch_down: main.click
on_touch_move: main.move
...
Любая функция не вызывается, когда я нажимаю или перетаскиваю метку. Однако если я изменю main.click
например print('touched!')
оно работает.
Итак, я создал свой собственный класс:
class HeadLabel(MaterialLabel):
def on_touch_down(self, touch):
window.click(touch)
def on_touch_move(self, touch):
window.drag(touch)
Это работает. Но теперь я не знаю, как получить положение экрана из MotionEvent
событие. Это мой фактический код окна:
class WindowApp(App):
theme_cls = ThemeManager()
def build(self):
self.theme_cls.theme_style = 'Light'
self.theme_cls.primary_palette = 'Purple'
return CustBoxLayout()
def click(self, touch):
self.touch_x, self.touch_y = touch.spos[0], touch.spos[1]
def drag(self, touch):
Window.top = self.touch_y + touch.spos[0]
Window.left = self.touch_x + touch.spos[1])
Любая помощь будет высоко оценена.
1 ответ
Определите класс для пользовательской метки и реализуйте методы on_touch_down и on_touch_move. Пожалуйста, обратитесь к примеру ниже для деталей.
Руководство по программированию "Управление вводом" Основы сенсорных событий
По умолчанию сенсорные события отправляются всем отображаемым в данный момент виджетам. Это означает, что виджеты получают событие касания, независимо от того, происходит оно в их физической области или нет.
Чтобы обеспечить максимальную гибкость, Kivy отправляет события всем виджетам и позволяет им решать, как на них реагировать. Если вы хотите отвечать только на сенсорные события внутри виджета, вы просто проверяете наличие столкновений.
пример
main.py
from kivy.app import App
from kivy.uix.boxlayout import BoxLayout
from kivy.uix.label import Label
from kivy.core.window import Window
from kivymd.theming import ThemeManager
class CustomLabel(Label):
def on_touch_down(self, touch):
print("\nCustomLabel.on_touch_down:")
if self.collide_point(*touch.pos):
print("\ttouch.pos =", touch.pos)
self.touch_x, self.touch_y = touch.spos[0], touch.spos[1]
return True
return super(CustomLabel, self).on_touch_down(touch)
def on_touch_move(self, touch):
print("\nCustomLabel.on_touch_move:")
if self.collide_point(*touch.pos):
print("\ttouch.pos =", touch.pos)
Window.top = self.touch_y + touch.spos[0]
Window.left = self.touch_x + touch.spos[1]
return True
return super(CustomLabel, self).on_touch_move(touch)
class CustBoxLayout(BoxLayout):
pass
class TestApp(App):
theme_cls = ThemeManager()
def build(self):
self.theme_cls.theme_style = 'Light'
self.theme_cls.primary_palette = 'Purple'
return CustBoxLayout()
if __name__ == "__main__":
TestApp().run()
test.kv
#:kivy 1.10.0
<CustomLabel>:
<CustBoxLayout>:
orientation: 'vertical'
CustomLabel:
id: header
text: 'MyApp'
font_size: 24
padding_x: 16
color: app.theme_cls.primary_color
Button:
text: 'Button Widget'
font_size: 24
padding_x: 16
color: app.theme_cls.primary_color