You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于Tkinter实现类似EasyGUI buttonbox的选择框函数,解决无法返回选中值问题

Fixing the Return Value Issue in Your Tkinter ChoiceBox Function

Hey there! Let's break down why your mychoicebox isn't returning the selected value when you click "Done" and how to fix it.

The Problem with Your Current Code

Your buttonfn callback just returns var.get(), but Tkinter command functions don't pass return values back to the parent function. Plus, your window stays open (since you never destroy it), so choicewin.mainloop() keeps running indefinitely—your function never gets to the point where it can return anything to the reply variable.

The Solution

We need two key changes:

  1. Store the selected value in a mutable object (like a list) so the callback can modify it and the parent function can access it.
  2. Close the window when "Done" is clicked, which will exit the mainloop and let the function return the selected value.

Here's the revised code:

from tkinter import *

def mychoicebox(choicelist):
    # Use a list to store the result (mutable objects let us modify values across scopes)
    selected_value = [None]
    
    def on_done_click():
        # Save the selected option
        selected_value[0] = var.get()
        # Close the window to exit the mainloop
        choicewin.destroy()
    
    choicewin = Tk()
    choicewin.resizable(False, False)
    choicewin.title("ChoiceBox")
    
    # Add the prompt label
    Label(choicewin, text="Select an item:").grid(row=0, column=0, sticky="W")
    
    # Set up the dropdown menu
    var = StringVar(choicewin)
    # Set default to first item if choicelist isn't empty, else "No data"
    var.set(choicelist[0] if choicelist else 'No data')
    popupMenu = OptionMenu(choicewin, var, *choicelist)
    popupMenu.grid(sticky=N+S+E+W, row=1, column=0)
    
    # Add the Done button with our updated callback
    Button(choicewin, text='Done', command=on_done_click).grid(row=2, column=0)
    
    # Start the GUI loop
    choicewin.mainloop()
    # Return the selected value once the window closes
    return selected_value[0]

How It Works

  • Mutable Storage: We use selected_value = [None] because lists are mutable. If we used a regular variable, the callback would treat it as a local variable instead of modifying the parent function's variable.
  • Close the Window: choicewin.destroy() shuts down the GUI window, which exits mainloop(). This lets the function proceed to the return statement, passing the selected value back to your reply variable.
  • Better Default: We updated the default value to use the first item in choicelist (if it exists) instead of always showing "No data"—this makes the UI more intuitive.

Test It Out

Run your test code again:

reply = mychoicebox(['one','two','three'])
print("reply:", reply)

Now when you select an option and click "Done", the window will close, and you'll see your selected value printed in the console.

Bonus Alternative: Using wait_window

If you prefer, you can use wait_window() instead of relying on mainloop() directly. This waits for the window to be destroyed before proceeding, which works similarly:

def mychoicebox(choicelist):
    selected_value = [None]
    
    def on_done_click():
        selected_value[0] = var.get()
        choicewin.destroy()
    
    choicewin = Tk()
    choicewin.resizable(False, False)
    choicewin.title("ChoiceBox")
    
    Label(choicewin, text="Select an item:").grid(row=0, column=0, sticky="W")
    
    var = StringVar(choicewin)
    var.set(choicelist[0] if choicelist else 'No data')
    popupMenu = OptionMenu(choicewin, var, *choicelist)
    popupMenu.grid(sticky=N+S+E+W, row=1, column=0)
    
    Button(choicewin, text='Done', command=on_done_click).grid(row=2, column=0)
    
    # Wait until the window is destroyed before returning
    choicewin.wait_window(choicewin)
    return selected_value[0]

内容的提问来源于stack exchange,提问作者rnso

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 06:58:37