如何处理 Tkinter 菜单内多个复选按钮的变量?
How to handle variables of multiple check buttons inside a menu in Tkinter?
我想在 Tkinter 中制作一个多选下拉列表,所以在线浏览时我想到了在菜单中使用 add_checkbuttons
的解决方案。它的解决方案至少在图形上有效,但现在我希望 GUI 在标记检查时实际执行某些操作。我尝试了一个简单的函数,该函数将值打印为每个复选按钮的命令,但它只被调用一次。
到目前为止,这是我的代码:
root = tk.Tk()
groceries = ['Apple', 'Banana', 'Carrot']
def print_groceries(bucket,item):
print(bucket[item].get())
menubar = tk.Menu(root)
viewMenu = tk.Menu(menubar, tearoff = 0)
bucket={}
for item in groceries:
bucket[item] = tk.BooleanVar(False)
viewMenu.add_checkbutton(label = item, variable = bucket[item], command=print_groceries(bucket,item))
menubar.add_cascade(menu = viewMenu, label = "Buy")
root.config(menu = menubar)
root.mainloop()
您已将 print_groceries
的 return 值分配给 command
参数。因此,当您的代码被执行时,print_groceries
在 定义 复选按钮时执行了三次。由于所有复选按钮最初都未选中,因此您会看到 False
打印了三次。
解决方案:
command
参数接受一个函数,而不是 return 由函数编辑的值(除非 return 值本身就是一个函数)。
要创建一个简单的函数,您可以使用 lambda
,如下所示:
lambda <parameter-1>,<parameter-2>,... : <task-to-perform>
此外,您必须使用 lambda bucket=bucket, item=item: print_groceries(bucket,item)
而不是 lambda : print_groceries(bucket,item)
。您可以在 答案中找到相同原因。
工作代码:
import tkinter as tk
root = tk.Tk()
groceries = ['Apple', 'Banana', 'Carrot']
def print_groceries(bucket,item):
print(bucket[item].get())
menubar = tk.Menu(root)
viewMenu = tk.Menu(menubar, tearoff = 0)
bucket={}
for item in groceries:
bucket[item] = tk.BooleanVar(False)
func = lambda bucket=bucket, item=item: print_groceries(bucket,item)
viewMenu.add_checkbutton(label = item, variable = bucket[item], command = func)
menubar.add_cascade(menu = viewMenu, label = "Buy")
root.config(menu = menubar)
root.mainloop()
我想在 Tkinter 中制作一个多选下拉列表,所以在线浏览时我想到了在菜单中使用 add_checkbuttons
的解决方案。它的解决方案至少在图形上有效,但现在我希望 GUI 在标记检查时实际执行某些操作。我尝试了一个简单的函数,该函数将值打印为每个复选按钮的命令,但它只被调用一次。
到目前为止,这是我的代码:
root = tk.Tk()
groceries = ['Apple', 'Banana', 'Carrot']
def print_groceries(bucket,item):
print(bucket[item].get())
menubar = tk.Menu(root)
viewMenu = tk.Menu(menubar, tearoff = 0)
bucket={}
for item in groceries:
bucket[item] = tk.BooleanVar(False)
viewMenu.add_checkbutton(label = item, variable = bucket[item], command=print_groceries(bucket,item))
menubar.add_cascade(menu = viewMenu, label = "Buy")
root.config(menu = menubar)
root.mainloop()
您已将 print_groceries
的 return 值分配给 command
参数。因此,当您的代码被执行时,print_groceries
在 定义 复选按钮时执行了三次。由于所有复选按钮最初都未选中,因此您会看到 False
打印了三次。
解决方案:
command
参数接受一个函数,而不是 return 由函数编辑的值(除非 return 值本身就是一个函数)。
要创建一个简单的函数,您可以使用 lambda
,如下所示:
lambda <parameter-1>,<parameter-2>,... : <task-to-perform>
此外,您必须使用 lambda bucket=bucket, item=item: print_groceries(bucket,item)
而不是 lambda : print_groceries(bucket,item)
。您可以在
工作代码:
import tkinter as tk
root = tk.Tk()
groceries = ['Apple', 'Banana', 'Carrot']
def print_groceries(bucket,item):
print(bucket[item].get())
menubar = tk.Menu(root)
viewMenu = tk.Menu(menubar, tearoff = 0)
bucket={}
for item in groceries:
bucket[item] = tk.BooleanVar(False)
func = lambda bucket=bucket, item=item: print_groceries(bucket,item)
viewMenu.add_checkbutton(label = item, variable = bucket[item], command = func)
menubar.add_cascade(menu = viewMenu, label = "Buy")
root.config(menu = menubar)
root.mainloop()