提问人:Leon Kardaš 提问时间:4/21/2021 更新时间:4/22/2021 访问量:95
Kivy - 我无法使用 id 更改 .source
Kivy - I can't change .source with an id
问:
我想在一个盒子里改变我的图片,我正在尝试在id的帮助下做到这一点。我尝试了很多解决方案,搜索了 3 个多小时,但我无法得到任何正确的东西,所以我将不胜感激。我对Kivy也很陌生。
我试着改变:
self.ids.rec.source = 'download.jpg'
to(正如 Python 所建议的那样 - Kivy:AttributeError:“super”对象在尝试获取 self.ids 时没有属性“__getattr__”)
self.parent.parent.ids
它没有用,只是将我的错误更改为:
AttributeError: 'NoneType' object has no attribute 'parent'
试图自己摆弄它,但除了将错误更改为另一个错误之外,也无能为力。
这是我的python文件:
from kivy.app import *
from kivy.uix.button import *
from kivy.graphics import *
from kivy.uix.widget import *
from kivy.uix.label import *
from kivy.uix.floatlayout import *
from kivy.uix.boxlayout import *
from kivy.uix.relativelayout import *
from kivy.properties import ListProperty, StringProperty,ObjectProperty
x = []
f = []
#---------------------------------------------------------------------------------
class Picture(FloatLayout):
def __init__(self, **kwargs):
super(Picture, self).__init__(**kwargs)
def change(self,**kwargs):
y = len(x)
if y % 2 == 0:
self.ids.rec.source = 'download.jpg'
tilesource = 'download.jpg'
print("aaaa")
else:
tilesource = 'images.jpg'
print("bbbbb")
#---------------------------------------------------------------------------------
class TileWidget(FloatLayout):
def __init__(self, **kwargs):
super(TileWidget, self).__init__(**kwargs)
self.pos = (0, 0)
self.size = (1,1)
d = Picture()
self.add_widget(d)
def swap(self):
x.append("0")
Picture().change()
#---------------------------------------------------------------------------------
class langApp(App):
def build(self):
return TileWidget()
#---------------------------------------------------------------------------------
if __name__ == '__main__':
langApp().run()
And this is my .kv file:
#:kivy 1.11.1
<TileWidget>:
FloatLayout:
pos: 0,0
size: root.width,root.height
Button:
text: 'Last'
pos_hint: {'x':.25,'y':.1}
size_hint: .1,.1
Button:
text: 'Stop'
pos_hint: {'x':.45,'y':.1}
size_hint: .1,.1
Button:
on_press: root.swap()
text: 'Next'
pos_hint: {'x':.65,'y':.1}
size_hint: .1,.1
<Picture>:
pos_hint: {'x':.25,'y':.4}
canvas:
Rectangle:
id: rec
size: self.size[0]*0.5,self.size[1]*0.5
pos: self.pos[0],self.pos[1]
source: "images.jpg"
这是我的完整错误日志:
Traceback (most recent call last):
File "kivy\properties.pyx", line 861, in kivy.properties.ObservableDict.__getattr__
KeyError: 'rec'
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "c:/Users/Leon/mobile/main.py", line 45, in <module>
langApp().run()
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\app.py", line 950, in run
runTouchApp()
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\base.py", line 582, in runTouchApp
EventLoop.mainloop()
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\base.py", line 347, in mainloop
self.idle()
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\base.py", line 391, in idle
self.dispatch_input()
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\base.py", line 342, in dispatch_input
post_dispatch_input(*pop(0))
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\base.py", line 248, in post_dispatch_input
listener.dispatch('on_motion', etype, me)
File "kivy\_event.pyx", line 709, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\core\window\__init__.py", line 1412, in on_motion
self.dispatch('on_touch_down', me)
File "kivy\_event.pyx", line 709, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\core\window\__init__.py", line 1428, in on_touch_down
if w.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 709, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\uix\widget.py", line 545, in on_touch_down
if child.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 709, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\uix\widget.py", line 545, in on_touch_down
if child.dispatch('on_touch_down', touch):
File "kivy\_event.pyx", line 709, in kivy._event.EventDispatcher.dispatch
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\uix\behaviors\button.py", line 151, in on_touch_down
self.dispatch('on_press')
File "kivy\_event.pyx", line 705, in kivy._event.EventDispatcher.dispatch
File "kivy\_event.pyx", line 1248, in kivy._event.EventObservers.dispatch
File "kivy\_event.pyx", line 1132, in kivy._event.EventObservers._dispatch
File "C:\Users\Leon\mobile\env\lib\site-packages\kivy\lang\builder.py", line 57, in custom_callback
exec(__kvlang__.co_value, idmap)
File "c:\Users\Leon\mobile\lang.kv", line 15, in <module>
on_press: root.swap()
File "c:/Users/Leon/mobile/main.py", line 37, in swap
Picture().change()
File "c:/Users/Leon/mobile/main.py", line 19, in change
self.ids.rec.source = 'download.jpg'
File "kivy\properties.pyx", line 864, in kivy.properties.ObservableDict.__getattr__
AttributeError: 'super' object has no attribute '__getattr__'
答:
0赞
John Anderson
4/22/2021
#1
代码存在两个问题:
方法:swap()
def swap(self):
x.append("0")
Picture().change()
正在创建新实例并调用该新实例。这对实际位于 GUI 中的实例没有影响。解决此问题的一种简单方法是保留对 GUI 中实际存在的实例的引用,并在方法中使用该引用:Picture
change()
Picture
Picture
swap()
class TileWidget(FloatLayout):
def __init__(self, **kwargs):
super(TileWidget, self).__init__(**kwargs)
self.pos = (0, 0)
self.size = (1,1)
self.d = Picture()
self.add_widget(self.d)
def swap(self):
x.append("0")
self.d.change()
第二个问题是你不能使用 for canvas 指令,但你可以使用 .因此,您可以将指令放在自己的组中:ids
groups
Rectangle
<Picture>:
pos_hint: {'x':.25,'y':.4}
canvas:
Rectangle:
group: 'rec' # place this instruction in its own group
size: self.size[0]*0.5,self.size[1]*0.5
pos: self.pos[0],self.pos[1]
source: "images.jpg"
然后你可以用它来修改:group
Rectangle
def change(self,**kwargs):
y = len(x)
if y % 2 == 0:
rec = self.canvas.get_group('rec')[0]
rec.source = 'download.jpg'
tilesource = 'download.jpg'
print("aaaa")
else:
tilesource = 'images.jpg'
print("bbbbb")
评论