Search code examples
pythontkintercommandoptionmenu

OptionMenu loses command when updated


When updating my tkinter OptionMenu called ClientMenu like this:

    for i in range(0, len(Clientlist)-1):
    client1d.append(Clientlist[i][0])
ClientMenu.children["menu"].delete(0,len(Clientlist))

for i in range(0, len(Clientlist)):
    nm = Clientlist[i][0]
    client1d.append(nm)
    ClientMenu.children["menu"].add_command(label = nm)

ClientMenu.children["menu"].add_command(label="Add new Client+")

This deletes all the entries on the list and then goes through a 1d array containing all the options which go in the menu. This works fine and adds all the options properly onto the menu.

However the initial command which was in the ClientMenu when it was first defined

ClientMenu = OptionMenu(screen, dropdown, *client1d,"Add new Client+", command = dropdowncheck)

the command dropdowncheck doesnt run when the menu is recreated however it does before everything is deleted and re added. Is there a way to add back the options as well as add back the "dropdowncheck" command to the OptionMenu


Solution

  • The command you give to the OptionMenu is automatically passed to all add_command methods in the menu created at that moment. In the __init__ of the OptionMenu, you can see this like

    menu.add_command(label=v,
                     command=_setit(variable, v, callback))
    

    Because your add_command functions pass no command, clicking these options triggers nothing.
    In the code above, _setit is described as

    class _setit:
        """Internal class. It wraps the command in the widget OptionMenu."""
    

    Basically, this class does two things when called:

    1. Set the variable to the new value
    2. Call the command with the new value as argument

    You could recreate this behavior in a function you write yourself, but the easiest would be to just reuse this class something like:

    ClientMenu.children["menu"].add_command(label = nm
                                            command =_setit(dropdown, nm, dropdowncheck))