Help please! strange Tkinter behavior has me totally baffled.

Peter Otten __peter__ at web.de
Tue Aug 24 22:56:55 CEST 2010


Steve Ferg wrote:

> I have a short Python script that uses Tkinter to display an image.
> Here is the script
> 
> ===================================================================
> import sys, os
> from   Tkinter import *
> root = Tk()      # A: create a global variable named "root"
> 
> def showPicture(imageFilename):
>     # global root   #C: make root global
>     root = Tk()  # B: create a local variable named "root"
> 
>     imageFrame = Frame(root)
>     imageFrame.pack()
> 
>     imageObject = PhotoImage(file=imageFilename)
> 
>     label = Label(imageFrame,image=imageObject)
>     label.pack()
> 
>     root.mainloop()
> 
> showPicture("python_and_check_logo.gif")
> ===================================================================
> 
> The strange thing is that it crashes with this traceback...
> 
> ===================================================================
> 
> Traceback (most recent call last):
>   File "easygui_test3.py", line 19, in <module>
> showPicture("python_and_check_logo.gif")
>   File "easygui_test3.py", line 14, in showPicture
> label = Label(imageFrame,image=imageObject)
>   File "L:\FergLabstatPublic\Python26\lib\lib-tk\Tkinter.py", line
> 2474, in __init__
> Widget.__init__(self, master, 'label', cnf, kw)
>   File "L:\FergLabstatPublic\Python26\lib\lib-tk\Tkinter.py", line
> 1940, in __init__
> (widgetName, self._w) + extra + self._options(cnf))
> _tkinter.TclError: image "pyimage1" doesn't exist
> 
> ===================================================================
> 
> If I comment out either line A or line B, the script works fine.
> 
> What I don't understand is why creating a global "root" variable and a
> local "root" variable causes the script to crash.
> 
> Even more puzzling... if I uncomment line C, so that "root" in line B
> refers to a global "root" variable, the script still crashes.
> 
> I'm totally baffled.  Does anybody know what is going on here?
> 
> -- Steve Ferg
> (I'm running Python 2.6 under Windows, but  I get the same behavior
> under Solaris.)

Tkinter.Tk() creates a new Tcl interpreter. Are you sure you want that? The 
standard way to create an additional window is Tkinter.Toplevel().

The PhotoImage is created in the default (first) interpreter and then looked 
up in the Label's (second) interpreter. At least that's what I would infer 
from

class Image:
    """Base class for images."""
    _last_id = 0
    def __init__(self, imgtype, name=None, cnf={}, master=None, **kw):
        self.name = None
        if not master:
            master = _default_root
            if not master:
                raise RuntimeError, 'Too early to create image'
        self.tk = master.tk

in the Tkinter source which also makes it plausible that you can avoid the 
problem by specifying an explicit master

def showPicture(imageFilename):
    root = Tk()
    # ...
    imageObject = PhotoImage(file=imageFilename, master=root)
    # ...

Peter



More information about the Python-list mailing list