Reputation: 121
This is my first python app and I'm aware of many of it's flaws so I'll try to learn on my mistakes.
I would like to understand how to shorten my code a bit by putting declaration of tkinter widgets in a loop.
Here is part of the code(there is quite large list of similar sections, but I would just apply same logic):
varplies = StringVar(root)
varnotch = StringVar(root)
varspreader = StringVar(root)
varorder1 = StringVar(root)
varorder2 = StringVar(root)
def pliesto_uppercase(*args):
varplies.set(varplies.get().upper())
def notchto_uppercase(*args):
varnotch.set(varnotch.get().upper())
def spreaderto_uppercase(*args):
varspreader.set(varspreader.get().upper())
def order1to_uppercase(*args):
varorder1.set(varorder1.get().upper())
def order2to_uppercase(*args):
varorder2.set(varorder2.get().upper())
varplies.trace_add('write', pliesto_uppercase)
varnotch.trace_add('write', notchto_uppercase)
varspreader.trace_add('write', spreaderto_uppercase)
varorder1.trace_add('write', order1to_uppercase)
varorder2.trace_add('write', order2to_uppercase)
self.rnplies_entry = Entry(self.entry_frame, background=rgbcon2((158, 174, 179)),
justify='center', textvariable=varplies, width=4)
self.rnnotch_entry = Entry(self.entry_frame, background=rgbcon2((158, 174, 179)),
justify='center', textvariable=varnotch, width=4)
self.rnspreader_entry = Entry(self.entry_frame, background=rgbcon2((158, 174, 179)),
justify='center', textvariable=varspreader, width=4)
self.rnorder1_entry = Entry(self.entry2_frame, background=rgbcon2((158, 174, 179)),
justify='center', textvariable=varorder1, width=8)
self.rnorder2_entry = Entry(self.entry2_frame, background=rgbcon2((158, 174, 179)),
justify='center', textvariable=varorder2, width=8)
self.rnplies_entry.grid(column=1, row=5, padx=5, sticky="SEW")
self.rnnotch_entry.grid(column=2, row=5, padx=5, sticky="SEW")
self.rnspreader_entry.grid(column=5, row=5, padx=5, sticky="SEW")
self.rnorder1_entry.grid(column=0, row=9, padx=5, pady=5, sticky="SEW")
self.rnorder2_entry.grid(column=0, row=10, padx=5, pady=5, sticky="SEW")
pfdate = StringVar(root)
pfdate.set('All')
pfmarker = StringVar(root)
pfmarker.set('All')
pfdate.trace('w', partial(changeplan, widget=pfdate))
pfmarker.trace('w', partial(changeplan, widget=pfmarker))
def planfilters():
pdatelist = plandatefilter()
pmarkerlist = planmarkerfilter()
self.drop_datepl = OptionMenu(self.optionplan_frame, pfdate, *pdatelist)
self.drop_datepl.config(bg=rgbcon2((39, 46, 46)), width=10, fg='white')
self.drop_datepl.grid(row=5, column=0, sticky="E", padx=5, pady=5)
self.drop_rnpl = OptionMenu(self.optionplan_frame, pfmarker, *pmarkerlist)
self.drop_rnpl.config(bg=rgbcon2((39, 46, 46)), width=22, fg='white')
self.drop_rnpl.grid(row=5, column=1, sticky="E", padx=5, pady=5)
In short, I would like to understand how to put it in the loop to be like for example:
pl_filters = ('pfdate', 'pfmarker')
for opt_item in pl_filters:
pl_filters[opt_item] = StringVar(root)
pl_filters[opt_item].set('All')
pl_filters[opt_item].trace('w', partial(changeplan, widget=pl_filters[opt_item]))
Upvotes: 0
Views: 164
Reputation: 22493
Judging from the first part of your code, it looks like you are using the trace
method on your StringVar
just to convert the inserted characters to upper case. If so, I recommend implementing your own class with such method built in so you can avoid the need to create them later.
Also, you can create your StringVar
and Entry
in a for loop. Just save those references in a list for later use if required.
import tkinter as tk
root = tk.Tk()
class CustomVar(tk.StringVar):
def __init__(self):
tk.StringVar.__init__(self)
self.trace("w",self.trace_method)
def trace_method(self,*args):
self.set(self.get().upper())
class Something(tk.Frame):
def __init__(self,master=None,**kwargs):
tk.Frame.__init__(self,master,**kwargs)
all_vars = [CustomVar() for _ in range(5)] #create 5 vars in one go
entries = []
for num, var in enumerate(all_vars,1): #loop through the vars and create entries
entry = tk.Entry(self,background="yellow",justify="center",
textvariable=var,width=4 if num <4 else 8)
entries.append(entry)
for num, cords in enumerate(((1,5),(2,5),(5,5),(0,9),(0,10))): #your grid row and column number grouped in a tuple
entries[num].grid(column=cords[0],row=cords[1],padx=5,sticky="SEW")
a = Something(root)
a.pack()
root.mainloop()
Upvotes: 1