I have a 16x16 matrix of tkinter buttons:
for c in range(self.track_size):
row = []
for r in range(self.track_size):
button = tk.Button(
self.ground_data_frame,
text="0"
)
button.grid(row=r, column=c, sticky=tk.NW+tk.NE+tk.SW+tk.SE+tk.W+tk.E+tk.N+tk.S)
row.append(button)
self.ground_data_buttons.append(row)
I define a command function to each one of them post-definition:
for r in self.ground_data_buttons:
for b in r:
b.config(command=lambda: b.config(text=self.ground_data_values[
self.values_list_box.get(tk.ACTIVE)
]))
The idea is to update the clicked button text with the value selected in the ListBox. The problem is, when I click on the first button, for example, this is what happens:
It updates only the last button. It completely ignores the commands of all the previous buttons. It's ridiculous to not use a loop for this, to create all of the buttons manually. Why this happens?
EDIT: The problem persists even if I try with tk.StringVar()
.
for c in range(self.track_size):
row = []
for r in range(self.track_size):
button_text = tk.StringVar()
button = tk.Button(
self.ground_data_frame,
textvariable=button_text
)
button.grid(row=r, column=c, sticky=tk.NW+tk.NE+tk.SW+tk.SE+tk.W+tk.E+tk.N+tk.S)
row.append((button, button_text))
self.ground_data_buttons.append(row)
for r in self.ground_data_buttons:
for b in r:
b[0].config(command=lambda: b[1].set(self.ground_data_values[
self.values_list_box.get(tk.ACTIVE)
]))
EDIT2: Even using a class, the problem persists.
class Button(tk.Button):
def __init__(self, frame):
self.textvariable = tk.StringVar()
tk.Button.__init__(self, frame, textvariable=self.textvariable)
self.update_value("0")
def update_value(self, value):
self.textvariable.set(value)
def set_command(self, f):
self.config(command=f)
...
for c in range(self.track_size):
row = []
for r in range(self.track_size):
button = Button(self.ground_data_frame)
button.grid(row=r, column=c, sticky=tk.NW+tk.NE+tk.SW+tk.SE+tk.W+tk.E+tk.N+tk.S)
row.append(button)
self.ground_data_buttons.append(row)
for r in self.ground_data_buttons:
for b in r:
b.set_command(lambda: b.update_value(self.ground_data_values[self.values_list_box.get(tk.ACTIVE)]))