Search code examples
pythonpython-3.xtkinterdrop-down-menuoptionmenu

Running commands based on OptionMenu's selection


How can I tweak this so that if xyz17 is selected from the Menu the function xyz17() is run?

I'm aware of command = xyz17 but I'm not sure how to make that dynamic so that it depends on the menu selection.

from tkinter import *

def xyz17():
    print('xyz17')
def abc27():
    print('abc27')
def qwe90():
    print('qwe90')
def uio19():
    print('uio19')
def jkl09():
    print('jkl09')
def zxc28():
    print('zxc28')

class Menu(OptionMenu):
    def __init__(self, master, status, *options):
        self.var = StringVar(master)
        self.var.set(status)
        OptionMenu.__init__(self, master, self.var, *options)

def main():        
    TopFrame = Frame(root)
    TopFrame.pack()

    Menu1 = Menu(TopFrame, 'xyz', 'xyz17','abc27','qwe90')
    Menu2 = Menu(TopFrame, 'uio', 'uio19','jkl09','zxc28')

    Menu1.pack()
    Menu2.pack()

root = Tk()
main()
root.mainloop()

Please note that the functions each priniting the value is just for an example, I would like the code to run the function itself. I'm aware of this:

class Menu(OptionMenu):
    def __init__(self, master, status, *options):
        self.var = StringVar(master)
        self.var.set(status)
        OptionMenu.__init__(self, master, self.var, *options, command=self.func)
    def func(self,value):
        print (value)

But, this isn't relevant to my scenario as it simply just gets the value and prints it, and I would like it to actually run the function itself.


Solution

  • If you want to run specific methods for options, simply check the sent string and select the method based on the string using if / elif statements:

    from tkinter import *
    
    
    def xyz17():
        print('xyz17')
    def abc27():
        print('abc27')
    def qwe90():
        print('qwe90')
    def uio19():
        print('uio19')
    def jkl09():
        print('jkl09')
    def zxc28():
        print('zxc28')
    
    class Menu(OptionMenu):
        def __init__(self, master, status, *options):
            self.var = StringVar(master)
            self.var.set(status)
            OptionMenu.__init__(self, master, self.var, *options, command=self.option_handle)
    
    
        def option_handle(self, selected):
            # above specific case is simply print(selected) but
            if selected == "xyz17":
                xyz17()
            elif selected == "abc27":
                abc27()
            elif selected == "qwe90":
                qwe90()
            elif selected == "uio19":
                uio19()
            elif selected == "jkl09":
                jkl09()
            elif selected == "zxc28":
                zxc28()
            # if you specifically want to call methods that has exactly
            # the same name as options
            # eval(selected + "()")
    
    
    def main():        
        TopFrame = Frame(root)
        TopFrame.pack()
    
        Menu1 = Menu(TopFrame, 'xyz', 'xyz17','abc27','qwe90')
        Menu2 = Menu(TopFrame, 'uio', 'uio19','jkl09','zxc28')
    
        Menu1.pack()
        Menu2.pack()
    
    root = Tk()
    main()
    root.mainloop()