Tk Canvas objects - Deletable?

Randall Hopper aa8vb at vislab.epa.gov
Fri May 7 06:37:55 EDT 1999


Fredrik Lundh:
 |Randall Hopper <aa8vb at vislab.epa.gov> wrote:
 |> How does one delete Tkinter Canvas objects?  Or do they ever get deleted?
 |
 |if you're using the Canvas.py module (I never do),
 |you need to explicitly call the delete method for
 |each item.

Thanks for the reply.

I actually meant the Tkinter Canvas objects, not the Tk canvas items under
the hood.

 |if you use the create methods, use the delete
 |method to destroy the items.

I'm not sure I know what you mean.  I didn't find any "create()" methods --
just __init__ methods (were you referring to those).  So by symmetry, I'd
like to use the __del__ methods of the Tkinter wrapper objects to do
cleanup of the underlying Tk objects, if possible.

 |> The attached Tk script illustrates my problem.  group doesn't ever get
 |> deleted for some reason.
 |
 |the bindings you added to the canvas point back
 |to the group object.

Ok.  So I'll need to call an "unbind" routine to allow the reference count
to drop to zero.  That's unfortunate and gives me a little concern.  Is
that to say that calling delete on the Tkinter wrapper objects may still
leave extraneous wrapper objects lying around because callbacks for them
are still bound and reference counts aren't zero?

As an exercise in learning how to avoid this, I'd like to get my example to
destroy the Tkinter Group object.  I tried unbinding it as you suggested.
I also tried deleting it.

As you can see, the reference count never drops.  It starts at 2 and stays
at 2.  One reference is to the module "group" variable of course, but
there's one other hiding somewhere.  Do you see where it is?

 |> What's a good way to debug this?  Is there any way to inspect the Python
 |> reference counts for an object?
 |
 |sys.getrefcount (it'll always return one more than
 |the actual count, by technical reasons).

Thanks,

Randall
-------------- next part --------------
#!/usr/bin/env python

import sys
from Tkinter import *
from Canvas import *

class PlaceableGroup( Group ):

  def __init__( self, canvas, tag = None ):
    Group.__init__( self, canvas, tag )
    self.canvas = canvas
    Widget.bind( self.canvas, "<Button-1>", self.__MouseDownCB )

  def __del__( self ):
    print "del method invoked"
    #self.unbind()
    #self.delete()

  def unbind( self ):
    Widget.unbind( self.canvas, "<Button-1>" )

  def __MouseDownCB( self, event ):
    rect = Rectangle( self.canvas, event.x-5, event.y-5,
                                   event.x+5, event.y+5 )
    self.addtag_withtag( rect )

root = Tk()
canvas = Canvas( root )
canvas.pack()
btn = Button( text="Click canvas, and hit me to destroy the group",
              command=root.quit )
btn.pack()
group = PlaceableGroup( canvas )
root.mainloop()

#
# We would like to kill "group" here, but no such luck
#
print "Ref count = ", sys.getrefcount(group) - 1
group.unbind()
print "Ref count = ", sys.getrefcount(group) - 1
group.delete()
print "Ref count = ", sys.getrefcount(group) - 1
group = None
btn.configure( text="You'd think the group had been killed, but..." )
root.mainloop()


More information about the Python-list mailing list