Python如何让绑定点击事件的控件触发时返回自身实例名称?
解决方案
你的问题核心是Python闭包的延迟绑定特性:循环中定义的lambda捕获的变量i会在lambda实际执行的时候才取值,这时候循环已经跑完了,所有lambda拿到的都是最后一次循环的i值,没法得到对应控件的名称。
方法1:用默认参数捕获当前循环值(最通用)
默认参数会在函数定义阶段就完成求值,刚好可以把每次循环对应的控件名称固定下来,代码如下:
for i in list_tasks: current_name = f'icon1{i}' globals()[current_name].bind( on_press=lambda x, name=current_name: print(name) )
点击对应的控件时,就会直接打印出你想要的icon1clock这类名称。
方法2:直接从事件触发对象取值(需要提前给控件设置标识)
如果你给对应控件提前设置了id属性为对应的名称,也可以直接从事件回调的第一个参数(就是触发事件的控件实例本身)里取:
for i in list_tasks: globals()[f'icon1{i}'].bind( on_press=lambda x: print(x.id) )
优化建议
不推荐用globals()来存储控件实例,会污染全局命名空间,建议单独用一个字典管理,比如:
# 提前把所有控件存到字典里 task_widgets = {} for i in list_tasks: task_widgets[f'icon1{i}'] = 你的控件实例 # 绑定事件的时候直接从字典取 for name, widget in task_widgets.items(): widget.bind(on_press=lambda x, n=name: print(n))
内容的提问来源于stack exchange,提问作者יואב שלו
相关产品推荐
相关产品推荐

