Kivy中打开屏幕时动态更新Inventory部件数量的问题
问题分析与解决方案
核心问题
你在updateInv方法里执行InventoryStack().viewInventory()时,创建了一个全新的InventoryStack实例——这个实例并没有被添加到当前界面的布局中,所以调用add_widget只是给这个新实例加了按钮,屏幕上的旧实例完全没变化。另外,viewInventory每次调用都会重复添加所有按钮,会导致按钮重复出现。
修复步骤
- 给界面上的InventoryStack添加ID:在KV语言里给InventoryStack设置id,方便在Python代码中获取界面上已存在的实例。
- 修改updateInv方法:通过ID获取界面上的InventoryStack实例,再调用它的viewInventory方法。
- 优化viewInventory方法:每次更新前先清空现有按钮,避免重复添加。
修改后的代码
KV部分(添加id)
<InventoryScreen>: on_pre_enter: root.updateInv(self) name: "inventory" BoxLayout: orientation: "vertical" Label: text: "Inventory" size_hint: 1, .25 ScrollInventory: Button: text: "Back" size_hint: 1, None on_release: app.root.current = "Options" root.manager.transition.direction = "right" <ScrollInventory@ScrollView>: InventoryStack: id: inv_stack # 添加id用于获取实例 size_hint: 1, None height: self.minimum_height <InventoryStack>: orientation: "lr-tb" padding: ("20dp", "20dp") spacing: "20dp", "20dp"
Python部分(修改方法逻辑)
class InventoryStack(StackLayout): def __init__(self,** kwargs): super().__init__(**kwargs) self.viewInventory() # 初始化时直接调用统一的加载方法 def viewInventory(self): # 先清空现有所有按钮,避免重复添加 self.clear_widgets() for i in Inventory.select(): size = dp(100) dictItem = model_to_dict(i) print(dictItem['name']) invButton = Button(text=dictItem['name'], size_hint=(None, None), size=(size, size)) self.add_widget(invButton) print("-" * 35) class InventoryScreen(Screen): def updateInv(self, *largs): # 获取界面上已存在的InventoryStack实例 inv_stack = self.ids.get('inv_stack') if inv_stack: inv_stack.viewInventory()
关键知识点
- Kivy中通过
ids可以获取KV语言里定义的控件实例,这是界面控件和Python逻辑交互的核心方式,相关内容可在Kivy官方文档的「Widget IDs」章节找到。 clear_widgets()方法用于清空布局内的所有子控件,是动态更新界面元素时避免重复的常用操作。
内容的提问来源于stack exchange,提问作者schutta
相关产品推荐
相关产品推荐

