Kivy中存储函数返回值至变量?解决属性调用AttributeError报错
解决Kivy中
AttributeError: 'ObjectProperty' object has no attribute 'get_key_nicks'的问题 这个报错的核心原因很好理解:你在类定义阶段直接调用了data.get_key_nicks(),但此时的data是Kivy的ObjectProperty包装器对象,而非你期望的Data类实例。Kivy的属性系统在类定义时仅完成属性的声明,真正的实例绑定要等到组件初始化后才会完成。
下面是两种可行的解决方案:
方案一:在__init__方法中初始化数据
把获取key和nicks的逻辑放到类的初始化方法里,这样能确保data已经是实际的Data实例:
from kivy.uix.floatlayout import FloatLayout from kivy.properties import ObjectProperty, ListProperty import pickle class Data(object): def __init__(self): # 记得初始化你的文件路径属性 self.key_address = "key.pkl" self.nicks_address = "nicks.pkl" def get_key_nicks(self): ''' It returns key and nicks object ''' with open(self.key_address, 'rb') as f: key = pickle.load(f) with open(self.nicks_address, 'rb') as f: nicks = pickle.load(f) return (key, nicks) class MainScreen(FloatLayout): data = ObjectProperty(Data()) # 分开定义属性更符合Kivy的设计习惯,也可以用ListProperty存储元组 key = ObjectProperty(None) nicks = ObjectProperty(None) def __init__(self, **kwargs): super().__init__(**kwargs) self.key, self.nicks = self.data.get_key_nicks()
方案二:使用属性回调(on_data)
如果data可能在后续被动态替换,用属性回调会更灵活——当data属性发生变化时,自动更新key和nicks:
class MainScreen(FloatLayout): data = ObjectProperty(Data()) key = ObjectProperty(None) nicks = ObjectProperty(None) def on_data(self, instance, new_data): # 当data属性被赋值时自动触发此方法 self.key, self.nicks = new_data.get_key_nicks()
补充说明:为什么原写法会报错?
在类定义时,data = ObjectProperty(Data())只是创建了一个ObjectProperty包装器,并把Data()设为默认值,但此时这个属性还未与MainScreen的实例绑定。当你尝试调用data.get_key_nicks()时,调用对象是ObjectProperty实例,而非Data实例,自然不存在get_key_nicks方法。
另外,ListProperty通常用于存储列表类型数据,如果你只是要存储两个独立对象,分开使用ObjectProperty会更贴合Kivy的属性设计逻辑。
内容的提问来源于stack exchange,提问作者user378625
相关产品推荐
相关产品推荐

