【问题标题】:Python KIVY: recursive DropDownPython KIVY:递归下拉
【发布时间】:2018-06-10 08:07:31
【问题描述】:

我想创建一个 DropDown,其中包含 3 个其他 DropDown,每个 DropDown 包含 3 个按钮。

我希望第一个DropDown再打开三个DropDown,当我们点击其中一个时,会出现三个按钮,而且无论如何当一个按钮出现时,它在下方没有显示错误。当您第二次单击下拉菜单时,它会隐藏其子小部件。

我正在使用这种方式来创建一个下拉列表:

.py:

from kivy.app import App
from kivy.uix.dropdown import DropDown
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.lang import Builder
from kivy.properties import StringProperty


class MyScreenManager(ScreenManager):
    button_text = StringProperty('Show possibilities')

    def __init__(self, **kwargs):
        super(MyScreenManager, self).__init__(**kwargs)
        self.dropdown = CustomDropDown(self)

    def open_drop_down(self, widget):            
        self.dropdown.open(widget)

class MyScreen(Screen):
    def __init__(self, **kwargs):
        super(MyScreen, self).__init__(**kwargs)

class CustomDropDown(DropDown):
    def __init__(self, screen_manager, **kwargs):
        super(CustomDropDown, self).__init__(**kwargs)
        self.sm = screen_manager

    def on_select(self, data):
        self.sm.button_text = data

Builder.load_file("debug.kv")

class MyAppli(App):
    def build(self):
        return MyScreenManager()

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

.kv:

<MyScreenManager>:

    MyScreen:

        AnchorLayout:
            anchor_x: 'center'
            anchor_y: 'top'

            Button:

                text: root.button_text
                size:(200,50)
                size_hint:(None,None)
                on_release: root.open_drop_down(self)

<CustomDropDown>:
    Button:
        text:"Item 1"
        size:(200,50)
        size_hint:(None,None)
        on_release: root.select("ONE")
    Button:
        text:"Item 2"
        size:(200,50)
        size_hint:(None,None)
        on_release: root.select(self.text)
    Button:
        text:"Item 3"
        size:(200,50)
        size_hint:(None,None)
        on_release: root.select("THREE")

【问题讨论】:

    标签: python kivy dropdown


    【解决方案1】:

    添加另一个自定义下拉类并添加一个按钮方法来打开/关闭第二个下拉列表。 open_drop2() 方法执行打开/关闭。将padding 添加到每个Button 以尝试显示级联。可以使用相同的方案完成额外的级联,即添加一个CustomDropDown3 类,该类由CustomDropDown2 中的按钮打开。请注意,kv 文件中的dismiss_on_select: False 是必需的,以确保正确更新is2Displayed 属性。

    .py:

    from kivy.app import App
    from kivy.properties import StringProperty
    from kivy.uix.dropdown import DropDown
    from kivy.uix.screenmanager import ScreenManager, Screen
    from kivy.lang import Builder
    
    
    class MyScreenManager(ScreenManager):
        button_text = StringProperty('Show possibilities')
    
        def __init__(self, **kwargs):
            super(MyScreenManager, self).__init__(**kwargs)
            self.dropdown = CustomDropDown1(self)
    
        def open_drop_down(self, widget):
            self.dropdown.open(widget)
    
    class MyScreen(Screen):
        def __init__(self, **kwargs):
            super(MyScreen, self).__init__(**kwargs)
    
    
    class CustomDropDown1(DropDown):
        def __init__(self, screen_manager, **kwargs):
            super(CustomDropDown1, self).__init__(**kwargs)
            self.sm = screen_manager
            self.dropdown2 = CustomDropDown2(self.sm)
            self.is2Displayed = False
    
        def on_select(self, data):
            self.sm.button_text = data
    
        def open_drop2(self):
            if not self.is2Displayed:
                self.dropdown2.open(self)
                self.is2Displayed = True
            else:
                self.dropdown2.dismiss()
                self.is2Displayed = False
    
    class CustomDropDown2(DropDown):
        def __init__(self, screen_manager, **kwargs):
            super(CustomDropDown2, self).__init__(**kwargs)
            self.sm = screen_manager
    
        def on_select(self, data):
            self.sm.button_text = data
    
    Builder.load_file("debug.kv")
    
    class MyAppli(App):
        def build(self):
            return MyScreenManager()
    
    if __name__ == '__main__':
        MyAppli().run()
    

    .kv:

    <MyScreenManager>:
        MyScreen:
            FloatLayout:
                Button:
                    text: root.button_text
                    size: (200, 50)
                    size_hint:(None,None)
                    pos_hint: {'center_x': 0.5, 'top': 1.0}
                    on_release: root.open_drop_down(self)
    
    <CustomDropDown1>:
        padding: [0,0,0,0]
        Button:
            text:"Item 1"
            size:(200,50)
            size_hint:(None,None)
            text_size: self.size
            valign: 'center'
            padding: (10,0)
            on_release: root.select(self.text)
        Button:
            text:"Item 2"
            size:(200,50)
            size_hint:(None,None)
            text_size: self.size
            valign: 'center'
            padding: (10,0)
            on_release: root.open_drop2()
        Button:
            text:"Item 3"
            size:(200,50)
            size_hint:(None,None)
            text_size: self.size
            valign: 'center'
            padding: (10,0)
            on_release: root.select(self.text)
    
    <CustomDropDown2>:
        dismiss_on_select: False
        Button:
            text:"Item 1,2"
            size:(200,50)
            size_hint:(None,None)
            text_size: self.size
            valign: 'center'
            padding: (50,0)
            on_release: root.select(self.text)
        Button:
            text:"Item 2,2"
            size:(200,50)
            size_hint:(None,None)
            text_size: self.size
            valign: 'center'
            padding: (50,0)
            on_release: root.select(self.text)
        Button:
            text:"Item 3,2"
            size:(200,50)
            size_hint:(None,None)
            text_size: self.size
            valign: 'center'
            padding: (50,0)
            on_release: root.select(self.text)
    

    【讨论】:

    • 非常感谢。当我运行您的代码并单击第 2 项时,第二个下拉列表出现在第 3 项下方。是否可以让第二个下拉菜单出现在其父项(第 2 项)下方并将第 3 项向下推?
    • 我认为使用 DropDown 是不可能的。 DropDown 是 GridLayout 的一个非常简单的子类,没有太多的装饰。如果你想做一些更有趣的事情,你可以不使用 DropDown,只需在 Python 代码中的主屏幕上添加/删除按钮。
    猜你喜欢
    • 2014-11-07
    • 1970-01-01
    • 1970-01-01
    • 2020-02-12
    • 1970-01-01
    • 2013-07-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多