我如何将小部件添加到 FloatLayout 内的 ScrollView 内的 StackLayout?
How would i add a widget to a StackLayout inside a ScrollView inside a FloatLayout?
对 kivy 还很陌生,只有 python 的高中学历,现在已经坚持了一个星期了。我想要一个可以在 StackLayout 中添加和删除按钮的系统,我该怎么做?
我可以添加和删除按钮,我现在只需要弄清楚如何将它们放置在正确的区域。
我知道这个问题有点乱***,我已经深入了解了这个问题,但我认为最好的学习方法是直接投入其中。
python代码:
# import kivy & functions/widgets.
import kivy
from kivy.app import App
from kivy.uix.button import Button
# import kivy layouts.
from kivy.uix.floatlayout import FloatLayout
# Specify version of kivy needed.
kivy.require("1.10.1")
# define buttons and widgets
testButton = Button(width=177, height=254, size_hint=(None, None), background_normal="pics/32864.jpg")
class Page(FloatLayout):
def __init__(self):
super().__init__()
def add_button(self):
Page.add_widget(self, widget=testButton)
class YuGiOhApp(App):
pass
YuGiOhApp().run()
我的 .kv 代码:
#:kivy 1.10.1
<TestButton@Button>:
width: 177
height: 254
size_hint: None, None
background_normal: "pics/32864.jpg"
FloatLayout:
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.60, "top": 1}
text: "Search"
on_press: root.add_button()
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.80, "top": 1}
text: "collection"
TextInput:
multiline: False
font_size: 48
size_hint: 0.60, 0.10
pos_hint: {"x": 0, "top": 1}
ScrollView:
size_hint: 0.60, 0.90
StackLayout:
orientation: "lr-tb"
pos_hint: {"x": 0, "top": 0.88}
size_hint: 1, None
height: self.minimum_height
padding: 5
spacing: 5
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
编辑 4:在按下标有 "search" 的按钮时尝试 运行 add_button() 函数时出现错误 "AttributeError: 'FloatLayout' object has no attribute 'add_button'"
您可以为您的 StackLayout
小部件指定一个独特的 id
。
StackLayout:
id: your_stacklayout_id
...
然后要访问您的 StackLayout
小部件,您可以在 root
小部件中使用它的 id
。
#: import Factory kivy.factory.Factory
FloatLayout:
...
Button:
text: "Add new Button"
on_press: root.ids["your_stacklayout_id"].add_widget(Factory.TestButton())
...
这是一个基本示例:
main.py
from kivy.app import App
from kivy.uix.boxlayout import *
from kivy.uix.button import *
class Main(BoxLayout):
pass
class TestApp(App):
def build(self):
return Main()
TestApp().run()
test.kv
#: import Factory kivy.factory.Factory
<MyButton@Button>:
text: "Added Button"
<Main>:
BoxLayout:
orientation: "vertical"
Button:
text: "Add New Button"
on_press: root.ids["my_boxlayout_id"].add_widget(Factory.MyButton())
BoxLayout:
id: my_boxlayout_id
orientation: "vertical"
您的代码存在一些问题。
首先,您的 kv
引用了 FloatLayout
,而您似乎真的想引用您的 Page
class。 (你引用了root.add_button()
,但是那个方法在Page
class中)。
其次,您的 testbutton
是 TestButton
的单个实例,因此您第二次单击 Search
按钮时,您会收到有关该按钮已经有parent。所以我在 python 代码中创建了一个 TestButton
class 并从 kv
.
中删除了 <TestButton@Button>
规则
这是我认为您想要的代码:
# import kivy & functions/widgets.
import kivy
from kivy.app import App
from kivy.lang import Builder
from kivy.uix.button import Button
# import kivy layouts.
from kivy.uix.floatlayout import FloatLayout
# Specify version of kivy needed.
kivy.require("1.10.1")
# define buttons and widgets
class TestButton(Button):
def __init__(self, **kwargs):
super(TestButton, self).__init__(**kwargs)
self.width = 177
self.height = 254
self.size_hint = (None, None)
self.background_normal = "pics/32864.jpg"
class Page(FloatLayout):
def __init__(self):
super().__init__()
def add_button(self):
self.ids.stack.add_widget(TestButton())
class YuGiOhApp(App):
def build(self):
return Page()
YuGiOhApp().run()
并在 kv
:
中为您的 StackLayout
添加一个 id
#:kivy 1.10.1
<Page>:
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.60, "top": 1}
text: "Search"
on_press: root.add_button()
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.80, "top": 1}
text: "collection"
TextInput:
multiline: False
font_size: 48
size_hint: 0.60, 0.10
pos_hint: {"x": 0, "top": 1}
ScrollView:
size_hint: 0.60, 0.90
StackLayout:
id: stack
orientation: "lr-tb"
pos_hint: {"x": 0, "top": 0.88}
size_hint: 1, None
height: self.minimum_height
padding: 5
spacing: 5
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
新的add_button()
方法引用新的stack
id访问StackLayout
,每次调用都会创建一个新的TestButton
对 kivy 还很陌生,只有 python 的高中学历,现在已经坚持了一个星期了。我想要一个可以在 StackLayout 中添加和删除按钮的系统,我该怎么做?
我可以添加和删除按钮,我现在只需要弄清楚如何将它们放置在正确的区域。
我知道这个问题有点乱***,我已经深入了解了这个问题,但我认为最好的学习方法是直接投入其中。
python代码:
# import kivy & functions/widgets.
import kivy
from kivy.app import App
from kivy.uix.button import Button
# import kivy layouts.
from kivy.uix.floatlayout import FloatLayout
# Specify version of kivy needed.
kivy.require("1.10.1")
# define buttons and widgets
testButton = Button(width=177, height=254, size_hint=(None, None), background_normal="pics/32864.jpg")
class Page(FloatLayout):
def __init__(self):
super().__init__()
def add_button(self):
Page.add_widget(self, widget=testButton)
class YuGiOhApp(App):
pass
YuGiOhApp().run()
我的 .kv 代码:
#:kivy 1.10.1
<TestButton@Button>:
width: 177
height: 254
size_hint: None, None
background_normal: "pics/32864.jpg"
FloatLayout:
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.60, "top": 1}
text: "Search"
on_press: root.add_button()
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.80, "top": 1}
text: "collection"
TextInput:
multiline: False
font_size: 48
size_hint: 0.60, 0.10
pos_hint: {"x": 0, "top": 1}
ScrollView:
size_hint: 0.60, 0.90
StackLayout:
orientation: "lr-tb"
pos_hint: {"x": 0, "top": 0.88}
size_hint: 1, None
height: self.minimum_height
padding: 5
spacing: 5
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
编辑 4:在按下标有 "search" 的按钮时尝试 运行 add_button() 函数时出现错误 "AttributeError: 'FloatLayout' object has no attribute 'add_button'"
您可以为您的 StackLayout
小部件指定一个独特的 id
。
StackLayout:
id: your_stacklayout_id
...
然后要访问您的 StackLayout
小部件,您可以在 root
小部件中使用它的 id
。
#: import Factory kivy.factory.Factory
FloatLayout:
...
Button:
text: "Add new Button"
on_press: root.ids["your_stacklayout_id"].add_widget(Factory.TestButton())
...
这是一个基本示例:
main.py
from kivy.app import App
from kivy.uix.boxlayout import *
from kivy.uix.button import *
class Main(BoxLayout):
pass
class TestApp(App):
def build(self):
return Main()
TestApp().run()
test.kv
#: import Factory kivy.factory.Factory
<MyButton@Button>:
text: "Added Button"
<Main>:
BoxLayout:
orientation: "vertical"
Button:
text: "Add New Button"
on_press: root.ids["my_boxlayout_id"].add_widget(Factory.MyButton())
BoxLayout:
id: my_boxlayout_id
orientation: "vertical"
您的代码存在一些问题。
首先,您的 kv
引用了 FloatLayout
,而您似乎真的想引用您的 Page
class。 (你引用了root.add_button()
,但是那个方法在Page
class中)。
其次,您的 testbutton
是 TestButton
的单个实例,因此您第二次单击 Search
按钮时,您会收到有关该按钮已经有parent。所以我在 python 代码中创建了一个 TestButton
class 并从 kv
.
<TestButton@Button>
规则
这是我认为您想要的代码:
# import kivy & functions/widgets.
import kivy
from kivy.app import App
from kivy.lang import Builder
from kivy.uix.button import Button
# import kivy layouts.
from kivy.uix.floatlayout import FloatLayout
# Specify version of kivy needed.
kivy.require("1.10.1")
# define buttons and widgets
class TestButton(Button):
def __init__(self, **kwargs):
super(TestButton, self).__init__(**kwargs)
self.width = 177
self.height = 254
self.size_hint = (None, None)
self.background_normal = "pics/32864.jpg"
class Page(FloatLayout):
def __init__(self):
super().__init__()
def add_button(self):
self.ids.stack.add_widget(TestButton())
class YuGiOhApp(App):
def build(self):
return Page()
YuGiOhApp().run()
并在 kv
:
StackLayout
添加一个 id
#:kivy 1.10.1
<Page>:
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.60, "top": 1}
text: "Search"
on_press: root.add_button()
Button:
size_hint: 0.20, 0.10
pos_hint: {"x": 0.80, "top": 1}
text: "collection"
TextInput:
multiline: False
font_size: 48
size_hint: 0.60, 0.10
pos_hint: {"x": 0, "top": 1}
ScrollView:
size_hint: 0.60, 0.90
StackLayout:
id: stack
orientation: "lr-tb"
pos_hint: {"x": 0, "top": 0.88}
size_hint: 1, None
height: self.minimum_height
padding: 5
spacing: 5
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
TestButton:
新的add_button()
方法引用新的stack
id访问StackLayout
,每次调用都会创建一个新的TestButton