How do you populate a Combobox based on the selection of another Combobox?

8.1k views Asked by At

I am trying to populate a combobox based on the selection of another combobox. I can do this if I use an update button to update the combobox#1 selection.However, I would like to do the update dynamically.

I have attached a simple example of code that seems to work as expected except for one problem. You have to make the selection of combobox #1 twice in order to update combobox #2. If anybody has any ideas on how two solve this problem it would be deeply appreciated. Since I learn by example would you please include a code sample.

Thank You in advance: begez

from tkinter import *
import tkinter.ttk,csv

global CategoryCombo

def getUpdateData():

    cat = CategoryCombo.get()
    if cat == 'car':
        AccountCombo = tkinter.ttk.Combobox( width = 15,value = car)
        AccountCombo.grid(row = 5,column = 1,pady = 25,sticky = E)
    elif cat == 'home':
        AccountCombo = tkinter.ttk.Combobox( width = 15,value = home)
        AccountCombo.grid(row = 5,column = 1,pady = 25,sticky = E)
    elif cat == 'rv':
        AccountCombo = tkinter.ttk.Combobox( width = 15,value = rv)
        AccountCombo.grid(row = 5,column = 1,pady = 25,sticky = E)


category = ['home','car','rv']

home = ['utilities','rent','cable']

car = ['gas','oil','repairs']

rv = ['parks','maintenance','payment']
v = StringVar

root = tkinter.Tk()

class Application(Frame):

    def __init__(self, master=None, Frame=None):
        Frame.__init__(self, master)
        super(Application,self).__init__()
        self.grid(column = 5,row = 20,padx = 50,pady = 50)
        self.createWidgets()


    def createWidgets(self):
        global CategoryCombo

        CatCBLabel = Label(text = 'Combo Box #1:').grid(row = 2,column = 1,padx = 10)
        ActCBLabel = Label(text = 'Combo Box #2:').grid(row = 4,column = 1,padx = 10)
        AccountCombo = tkinter.ttk.Combobox( width = 15)
        AccountCombo.grid(row = 5,column = 1,pady = 25,padx = 10)
        CategoryCombo = tkinter.ttk.Combobox(width = 15,values = category,textvariable = v,postcommand = getUpdateData)
        CategoryCombo.grid(row = 3,column = 1,padx = 10,pady = 25)
        print(v)



app = Application()

app.master.title('Yearly Budget Setup')

app.mainloop()
1

There are 1 answers

2
Eric Levieil On BEST ANSWER
  1. Don't use global variables. Use class variables instead.
  2. Use dictionaries instead of multiple variables.
  3. Use ComboboxSelected event

Result:

from tkinter import *
import tkinter.ttk

category = {'home': ['utilities','rent','cable'],
    'car': ['gas','oil','repairs'],
    'rv':['parks','maintenance','payment']}

class Application(Frame):

    def __init__(self, master=None, Frame=None):
        Frame.__init__(self, master)
        super(Application,self).__init__()
        self.grid(column = 5,row = 20,padx = 50,pady = 50)
        self.createWidgets()

    def getUpdateData(self,  event):
        self.AccountCombo['values'] = category[self.CategoryCombo.get()]

    def createWidgets(self):
        Label(text = 'Combo Box #1:').grid(row = 2,column = 1,padx = 10)
        Label(text = 'Combo Box #2:').grid(row = 4,column = 1,padx = 10)
        self.AccountCombo = tkinter.ttk.Combobox( width = 15)
        self.AccountCombo.grid(row = 5,column = 1,pady = 25,padx = 10)

        self.CategoryCombo = tkinter.ttk.Combobox(width = 15,  values = list(category.keys()))
        self.CategoryCombo.bind('<<ComboboxSelected>>', self.getUpdateData)
        self.CategoryCombo.grid(row = 3,column = 1,padx = 10,pady = 25)

app = Application()
app.master.title('Yearly Budget Setup')
app.mainloop()