Tkinter单选按钮与复选框无法更新变量值问题求助
Tkinter弹窗控件变量不更新问题修复
问题现象
用Tkinter开发GUI时,通过类方法创建弹窗窗口,弹窗包含目录选择按钮、一对单选按钮(RadioG、RadioY)和一个复选框(state_checkbox),预期实现:
- 单选按钮切换更新
driveletter变量 - 复选框勾选/取消更新
statevalue变量
实际出现异常:
driveletter初始设为“G:”有效,但选择“Y:”单选按钮时变量值不更新statevalue通过IntVar.set(1)设置初始值,复选框未默认勾选,且勾选/取消时值始终为1,不会变为0
问题代码
class preferences(Preferences): def save_preferences(self): # Used to reset the folder location desired by the user self.prefdialog = tk.Tk() self.prefdialog.title('Set Preferences') self.driveletter = tk.StringVar() self.driveletter.set("G:") self.statevalue = tk.IntVar() self.statevalue.set(1) self.fpath = '\Desktop' self.RadioG = tk.Radiobutton(self.prefdialog, text="G:", variable=self.driveletter, value="G:", command=lambda: print(self.driveletter.get())) self.RadioG.grid(row=3,column=0,sticky=tk.W,pady=4) self.RadioY = tk.Radiobutton(self.prefdialog, text="Y:", variable=self.driveletter, value="Y:", command=lambda: print(self.driveletter.get())) self.RadioY.grid(row=3,column=1,sticky=tk.W,pady=4) self.state_checkbox = tk.Checkbutton( self.prefdialog, text="Check to use state folders", variable=self.statevalue, command=lambda: print(self.statevalue.get())) self.state_checkbox.grid(row=4,column=0,sticky=tk.W,pady=4) self.prefdialog.mainloop()
问题根源
排查后确认问题出在两个关键错误:
- 弹窗错误使用
tk.Tk()创建实例:Tkinter要求一个应用只能有一个Tk()主窗口,弹窗应使用Toplevel()创建,它会依附于已存在的主窗口 - 重复调用
mainloop():主窗口已经运行了一个mainloop(),弹窗再次调用会导致Tkinter的变量绑定机制混乱,控件无法正确更新变量值
修复后的代码
class preferences(Preferences): def save_preferences(self): # Used to reset the folder location desired by the user # 用Toplevel创建弹窗,依附于主窗口 self.prefdialog = tk.Toplevel(self) self.prefdialog.title('Set Preferences') self.driveletter = tk.StringVar() self.driveletter.set("G:") self.statevalue = tk.IntVar() self.statevalue.set(1) self.fpath = '\Desktop' self.RadioG = tk.Radiobutton(self.prefdialog, text="G:", variable=self.driveletter, value="G:", command=lambda: print(self.driveletter.get())) self.RadioG.grid(row=3,column=0,sticky=tk.W,pady=4) self.RadioY = tk.Radiobutton(self.prefdialog, text="Y:", variable=self.driveletter, value="Y:", command=lambda: print(self.driveletter.get())) self.RadioY.grid(row=3,column=1,sticky=tk.W,pady=4) self.state_checkbox = tk.Checkbutton( self.prefdialog, text="Check to use state folders", variable=self.statevalue, command=lambda: print(self.statevalue.get())) self.state_checkbox.grid(row=4,column=0,sticky=tk.W,pady=4) # 移除弹窗的mainloop(),依赖主窗口的mainloop()即可 # self.prefdialog.mainloop()
内容的提问来源于stack exchange,提问作者Ryan
相关产品推荐
相关产品推荐

