Search code examples
pythonvariablespython-3.xsimpledialog

Declared variables not initialised when using 'simpledialog'


I have a problem with some code that I have been working on where I am trying to pass a variable to a 'simpledialog' box. However, when I declare the variable in the __init__ section, the variable cannot be accessed from any other method in the class.

I have created a simplified working example in which I am trying to pass a string to an Entry box so that when the 'simpledialog' is created, the Entry box is already populated. The value can then be changed and the new value is printed to the console.

from tkinter import *
from tkinter.simpledialog import Dialog


class App(Frame):
    def __init__(self, parent):
        Frame.__init__(self, parent)
        self.parent = parent

        Button(parent, text="Press Me", command=self.run).grid()

    def run(self):
        number = "one"
        box = PopUpDialog(self, title="Example", number=number)
        print(box.values)

class PopUpDialog(Dialog):
    def __init__(self, parent, title, number, *args, **kwargs):
        Dialog.__init__(self, parent, title)
        self.number = number

    def body(self, master):
        Label(master, text="My Label: ").grid(row=0)
        self.e1 = Entry(master)
        self.e1.insert(0, self.number)  # <- This is the problem line
        self.e1.grid(row=0, column=1)

    def apply(self):
        self.values = (self.e1.get())
        return self.values

if __name__ == '__main__':
    root = Tk()
    app = App(root)
    root.mainloop()

When the code is run, and the 'Press Me' button is pressed, I get the following error message:

Exception in Tkinter callback
Traceback (most recent call last):
  File "C:\Python34\lib\tkinter\__init__.py", line 1533, in __call__
    return self.func(*args)
  File "C:/Python/scratch.py", line 14, in run
    box = PopUpDialog(self, title="Example", number=number)
  File "C:/Python/scratch.py", line 20, in __init__
    Dialog.__init__(self, parent, title)
  File "C:\Python34\lib\tkinter\simpledialog.py", line 148, in __init__
    self.initial_focus = self.body(body)
  File "C:/Python/scratch.py", line 26, in body
    self.e1.insert(0, self.number)
AttributeError: 'PopUpDialog' object has no attribute 'number'

If I comment out the self.e1.insert(0, self.number), the code will otherwise work.

There seems to be little documentation on the 'simpledialog', and I've been using the examples on effbot.org to try and learn more about dialog boxes.

As a side note, if I insert a print(number) line in the __init__ method of the PopUpDialog class, the number will print to the console. Also, if I initialise the self.number variable (eg, self.number = "example") in the body() method, the code works as expected.

I'm sure I'm missing something silly here, but if you could offer any suggestions as to what might be happening, it would be most appreciated.


Solution

  • The problem is in your PopUpDialog class, At the function __init__ you call the line Dialog.__init__(self, parent, title) that calls the body method. The problem is that you initialize the self.number at the next line and that's why self.number is not initialized yet at the body method.

    If you switch the lines it will work for you, just like this:

    class PopUpDialog(Dialog):
        def __init__(self, parent, title, number, *args, **kwargs):
            self.number = number
            Dialog.__init__(self, parent, title)
    

    EDIT:

    As you can see at the __init__ method of the Dialog there is the above line :

    self.initial_focus = self.body(body) that calls your body method.