-2

I have an array of binary values, that shall be represented by toggle buttons. Each button, when pressed, should toggle the state of the binary value in the array.

Long and tedious solution it to manually create separate buttons and separate button event handler's. However, if you have 100 binary values to be represented by toggle buttons, then I'd want this to be solved with a for loop dynamically.

tomatoeshift
  • 465
  • 7
  • 23

2 Answers2

1

You're doing a bit more work than you have to. If you bind a callback to the button's click-event explicitly using .bind(...), the associated callback takes an event object as a parameter, which has a handle to the widget (button) that triggered the event.

import tkinter as tk


class Application(tk.Tk):

    def __init__(self, *args, **kwargs):
        tk.Tk.__init__(self, *args, **kwargs)
        self.title("Buttons")
        self.geometry("256x64")
        self.resizable(width=False, height=False)

        self.buttons = [tk.Button(self, width=4) for _ in range(4)]
        for x, button in enumerate(self.buttons):
            button.grid(row=0, column=x)
            button.bind("<1>", self.on_click)

    def on_click(self, event):
        event.widget.config(bg="red")


def main():

    application = Application()
    application.mainloop()

    return 0


if __name__ == "__main__":
    import sys
    sys.exit(main())
Paul M.
  • 10,481
  • 2
  • 9
  • 15
-2

I spent way too long getting this to work, but I got it working now. So I hope someone else finds this helpful at some point in the future

import tkinter  as tk

root = tk.Tk()
root.geometry("500x300")

"""
Images:
https://drive.google.com/file/d/1tlLl2hjPq38mc_c_PpMhkKDlP1HqvDY5/view
https://drive.google.com/file/d/1bejSlQtIokdQw7d-5Qbqw1X3Sw5Y2bWO/view
"""
# The following 2 'PhotoImage' reads CANNOT be within bellow 'UpdateValue' method
# ( won't read the image into memory quick enough. )
# Option A) use a global variable  
# Option B) create class object ( self.on, self.off ) 
on = tk.PhotoImage(file =  "button_on.png")
off = tk.PhotoImage(file = "button_off.png")
 
def UpdateValue(ar_wid, ar_var,jj):
    if ar_var[jj].get() == '0':
        img = on  
        ar_var[jj].set('1')
    else:
       img = off
       ar_var[jj].set('0') 
    ar_wid[jj].config(image = img)

arr_widgets = []
arr_vars = []
# create 5 toggle buttons
for i in range(5):
    ThisVar = tk.StringVar(master=root, name= f'button_{i}', value='1')
    on_button = tk.Button(root, image = on, bd = 0, textvariable=ThisVar)
    on_button.config(command=  lambda j=i : UpdateValue(arr_widgets, arr_vars, j) )
    on_button.pack(pady = 10)
    arr_widgets.append(on_button)
    arr_vars.append(ThisVar)

root.mainloop()
tomatoeshift
  • 465
  • 7
  • 23