Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

bind same tkinter trace method to multiple tk variables

Tags:

python

tkinter

I want to create a tkinter application with multiple entry widgets. I am using for-loops to create the widgets, pack them, etc. Finally I want to use the tkinter trace method to validate the user input for each of the entry widgets. How can I bind the same callback-function to multiple tkinter variables using a for-loop? I know that the trace method will provide the callback function with the three arguments name, index and mode. Is there for example any way to use the name-argument as an unique identifier for each variable in that for-loop?

This is my code:

import tkinter as tk

class EntryFormular(tk.Frame):
    def __init__(self,master):
        tk.Frame.__init__(self,master)

        self.entrylist = [
        "entry 1",
        "entry 2",
        "entry 3"
        ]

        self.inputvars = list()
        self.build()

    def build(self):

        for entry in self.entrylist:

            var = tk.StringVar(self.master)
            var.trace("w",self.validateFloatInput)
            element = tk.Entry(self,textvariable=var)
            element.pack()

            self.inputvars.append(var)

    def validateFloatInput(self,name,index,mode):
        # bind this method to all 3 entry widgets
        # get variable content using .get() method
        # only allow float inputs between 0 and 1, such as 1.0 or 0.85
        pass

class Application:
    def __init__(self, master):
        self.master = master
        self.entryformular = EntryFormular(master)
        self.entryformular.pack()


if __name__ == "__main__":
    root = tk.Tk()
    my_gui = Application(root)
    root.mainloop()
like image 241
Johannes Wiesner Avatar asked Apr 27 '26 23:04

Johannes Wiesner


1 Answers

thanks to jasonharper! That solved my problem.

Here's my code:

import tkinter as tk
import re

class EntryFormular(tk.Frame):
    def __init__(self,master):
        tk.Frame.__init__(self,master)

        self.entrylist = [
        "entry 1",
        "entry 2",
        "entry 3"
        ]

        self.inputvars = list()
        self.build()

    def build(self):

        for entry in self.entrylist:

            var = tk.StringVar(self.master)
            var.trace("w",self.validateFloatInput)
            element = tk.Entry(self,textvariable=var)
            element.pack()
            self.inputvars.append(var)

    def validateFloatInput(self,name,index,mode):

        regex = re.compile(r'^0(\.\d+)?|1(\.0?)?$')

        for var in self.inputvars:
            if name == str(var):
                if regex.match(var.get()):
                    pass
                else:
                    var.set(var.get()[:-1])
                    self.master.bell()

class Application:
    def __init__(self, master):
        self.master = master
        self.entryformular = EntryFormular(master)
        self.entryformular.pack()


if __name__ == "__main__":
    root = tk.Tk()
    my_gui = Application(root)
    root.mainloop()
like image 110
Johannes Wiesner Avatar answered Apr 29 '26 11:04

Johannes Wiesner



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!