我在屏幕上添加了一个 FloatButton,但无法将任何 on_release 操作与其关联。我怀疑这个问题与我的 FloatButton 实际上继承自 FloatLayout 这一事实有关,因此它没有 on_release 属性? 这是我在 kv 文件中的 FloatButton 定义:
<FloatButton@FloatLayout>:
id: float_add_button # Giving id to button
size_hint: (None, None)
text: ''
btn_size: (70, 70)
size: (70, 70)
bg_color: (0.404, 0.227, 0.718, 1.0)
# pos_hint: {'x': .6}
Button:
text: float_add_button.text
markup: True
font_size: 40
size_hint: (None, None)
size: float_add_button.btn_size
pos_hint: {'x': .5, 'y': .8}
background_normal: ''
background_color: (0, 0, 0, 0)
canvas.before:
Color:
rgba: (0.404, 0.227, 0.718, 1.0)
Ellipse:
size: self.size
pos: self.pos
以及我在 on_release 上分配的 kv 文件
<MainWindow>:
name: 'main'
RelativeLayout:
orientation: 'lr-tb'
size_hint: 1, 1
padding: '20sp'
canvas.before:
Rectangle:
pos: self.pos
size: self.size
# A few buttons here
#
#
#
FloatButton:
id: addButton
text: '+'
markup: True
background_color: 1, 0, 1, 0
pos_hint: {"x":.5,"top":.5}
on_release:
print("[TEST] on_release works!")
但是,我收到以下错误:
Traceback (most recent call last):
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 734, in _apply_rule
raise AttributeError(key)
AttributeError: release
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "D:\Recipy_project\Recipy\main.py", line 1, in <module>
from Recipy.app import Recipy
File "D:\Recipy_project\Recipy\Recipy\app.py", line 21, in <module>
kv = Builder.load_file("Recipy/ui/layout.kv")
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 310, in load_file
return self.load_string(data, **kwargs)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 412, in load_string
self._apply_rule(
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 665, in _apply_rule
child.apply_class_lang_rules(
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\uix\widget.py", line 470, in apply_class_lang_rules
Builder.apply(
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 545, in apply
self._apply_rule(
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 741, in _apply_rule
raise BuilderException(
kivy.lang.builder.BuilderException: Parser: File "D:\Recipy_project\Recipy\Recipy\ui\layout.kv", line 590:
...
588: pos_hint: {"x":.5,"top":.5}
589: on_release:
>> 590: print("[TEST] on_release works!")
591: # root.manager.transition.direction = "left"
592: # app.root.current = 'add'
...
AttributeError: release
File "C:\Users\gitcanzo\AppData\Local\Packages\PythonSoftwareFoundation.Python.3.11_qbz5n2kfra8p0\LocalCache\local-packages\Python311\site-packages\kivy\lang\builder.py", line 734, in _apply_rule
raise AttributeError(key)
问题的原因正是你所说的,你的
FloatButton
类是从FloatLayout
派生的,而不是从Button
派生的,所以它没有on_release
事件。
一个选项是在您的
FloatButton
类中定义该自定义事件:
class FloatButton(FloatLayout):
def __init__(self, *args, **kwargs):
self.register_event_type('on_release')
super().__init__(*args, **kwargs)
def on_release(self, *args):
pass
并在按下内部按钮时调度它:
<FloatButton@FloatLayout>:
# ...
Button:
on_release: root.dispatch('on_release')
一个完整的可重现示例:
from kivy.app import App
from kivy.lang import Builder
from kivy.uix.floatlayout import FloatLayout
kv = '''
<FloatButton@FloatLayout>:
id: float_add_button # Giving id to button
size_hint: (None, None)
text: ''
btn_size: (70, 70)
size: (70, 70)
bg_color: (0.404, 0.227, 0.718, 1.0)
# pos_hint: {'x': .6}
Button:
on_release: root.dispatch('on_release')
text: float_add_button.text
markup: True
font_size: 40
size_hint: (None, None)
size: float_add_button.btn_size
pos_hint: {'x': .5, 'y': .8}
background_normal: ''
background_color: (0, 0, 0, 0)
canvas.before:
Color:
rgba: (0.404, 0.227, 0.718, 1.0)
Ellipse:
size: self.size
pos: self.pos
<MainWindow@RelativeLayout>:
name: 'main'
FloatButton:
id: addButton
text: '+'
markup: True
background_color: 1, 0, 1, 0
pos_hint: {"right":.5,"top":.5}
on_release:
print("[TEST] on_release works!")
MainWindow:
'''
class FloatButton(FloatLayout):
def __init__(self, *args, **kwargs):
self.register_event_type('on_release')
super().__init__(*args, **kwargs)
def on_release(self, *args):
pass
class MainWindow(App):
def build(self):
return Builder.load_string(kv)
if __name__ == '__main__':
MainWindow().run()