【问题标题】:usage of DragBehavior in Kivy在 Kivy 中使用 DragBehavior
【发布时间】:2017-12-02 12:36:07
【问题描述】:

我是 python 和 kivy 的新手,正在与它们斗争。

我想用kivy实现拖放功能(当一个图像被拖到另一个图像并放在它上面时,做一些事情的功能。)。

我想做的是以下三件事;

  • 知道用户现在持有的元素的id。
  • 知道用户悬停的元素的 ID。
  • 知道当用户放下他所拥有的东西时指针下的元素的 ID。

我认为this 对处理它们很有用,所以我写下了下面的python 脚本和.kivy 文件。但是,它并没有按我的预期工作。

有很多问题我不知道如何解决;

  • print(self.id) 返回无。
  • 即使我只拖动 1 个元素,on_touch_up 也会打印 None 两次。
  • 一旦拖放图像,该图像将无法再拖动。

python 文件:

from kivy.app import App
from kivy.uix.image import Image
from kivy.uix.behaviors import DragBehavior
from kivy.properties import BooleanProperty
from kivy.properties import ObjectProperty
from kivy.factory import Factory
from kivy.core.window import Window


class HoverBehavior(object):
    """Hover behavior.
    :Events:
        `on_enter`
            Fired when mouse enter the bbox of the widget.
        `on_leave`
            Fired when the mouse exit the widget
    """

    hovered = BooleanProperty(False)
    border_point = ObjectProperty(None)
    '''Contains the last relevant point received by the Hoverable. This can
    be used in `on_enter` or `on_leave` in order to know where was dispatched the event.
    '''

    def __init__(self, **kwargs):
        self.register_event_type('on_enter')
        self.register_event_type('on_leave')
        Window.bind(mouse_pos=self.on_mouse_pos)
        super(HoverBehavior, self).__init__(**kwargs)

    def on_mouse_pos(self, *args):
        if not self.get_root_window():
            return  # do proceed if I'm not displayed <=> If have no parent
        pos = args[1]
        # Next line to_widget allow to compensate for relative layout
        inside = self.collide_point(*self.to_widget(*pos))
        if self.hovered == inside:
            # We have already done what was needed
            return
        self.border_point = pos
        self.hovered = inside
        if inside:
            self.dispatch('on_enter')
        else:
            self.dispatch('on_leave')

    def on_enter(self):
        pass

    def on_leave(self):
        pass


Factory.register('HoverBehavior', HoverBehavior)


class DraggableImage(DragBehavior, HoverBehavior, Image):
    def __init__(self, **args):
        super(DraggableImage, self).__init__(**args)
        self.source_file = ""
        self.is_on_hover = False

    def on_enter(self):
        self.source_file = self.source
        self.source = "green.png"
        self.is_on_hover = True
        print(self.id)

    def on_leave(self):
        self.source = self.source_file
        self.is_on_hover = False
        print(self.id)

    def on_touch_up(self, touch):
        if self.is_on_hover:
            print(self.id)


class TestApp(App):
    def build(self):
        pass


if __name__ == '__main__':
    TestApp().run()

test.kivy:

<DraggableImage>
    drag_rectangle: self.x, self.y, self.width, self.height
    drag_timeout: 10000000
    drag_distance: 0

BoxLayout:
    orientation: "horizontal"
    DraggableImage:
        id: "left_left"
        source: "red.png"
    DraggableImage:
        id: "left_right"
        source: "yellow.png"
    DraggableImage:
        id: "right_left"
        source: "red.png"
    DraggableImage:
        id: "right_right"
        source: "yellow.png"

【问题讨论】:

    标签: python python-3.x drag-and-drop kivy kivy-language


    【解决方案1】:

    创建一个名为StringProperty 的名称,例如name。不要使用id,因为在kv中使用了id。
    改变你的班级和kv:

    from kivy.properties import StringProperty
    
    class DraggableImage(DragBehavior, HoverBehavior, Image):
    
        name = StringProperty("")
    
        def __init__(self, **args):
            super(DraggableImage, self).__init__(**args)
            self.source_file = ""
            self.is_on_hover = False
    
        def on_enter(self):
            self.source_file = self.source
            self.source = "green.png"
            self.is_on_hover = True
            print(self.name)
    
        def on_leave(self):
            self.source = self.source_file
            self.is_on_hover = False
            print(self.name)
    
        def on_touch_up(self, touch):
            if self.is_on_hover:
                print(self.name)
    
    
    
    
    KV = """
    
    <DraggableImage>:
        drag_rectangle: self.x, self.y, self.width, self.height
        drag_timeout: 10000000
        drag_distance: 0
    
    BoxLayout:
        orientation: "horizontal"
        DraggableImage:
            name: "left_left"
            source: "red.png"
        DraggableImage:
            name: "left_right"
            source: "yellow.png"
        DraggableImage:
            name: "right_left"
            source: "red.png"
        DraggableImage:
            name: "right_right"
            source: "yellow.png"
    
    """
    

    【讨论】:

    • 非常感谢,对我帮助很大!
    猜你喜欢
    • 2019-06-04
    • 1970-01-01
    • 1970-01-01
    • 2014-05-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多