Version 23 of binding to a toplevel window

Updated 2007-05-03 12:47:54 by MJ

MGS [2003/09/20] - Sometimes it is necessary/desirable to bind to a toplevel window. For example, I might want to withdraw a toplevel window, instead of having it iconify, when clicking the minimize button. There are several ways to do this:

1. Bind directly to the window name. e.g.

   bind . <Unmap> [list wm withdraw .]

However, the binding will trigger if you decide to unmanage any of the window's child widgets, due to their default binding tags.

2. Bind to the toplevel window's class. e.g.

   bind [winfo class .] <Unmap> [list wm withdraw %W]

However, this binding will fire for all windows with the same class as . .

3. Create a new binding tag for the toplevel window and then create the binding to that tag. e.g.

  bindtags . [list . bind. [winfo class .] all]
  bind bind. <Unmap> [list wm withdraw %W]

or more generally:

  set W [toplevel .mywin]
  bindtags $W [linsert [bindtags $W] 1 bind$W]
  bind bind$W <Unmap> [list wm withdraw %W]

RUJ: Hi, I would like to know ... How to bind a "Leave" command to main toplevel but it should be work on its child widgets also. I want to make popupwindow which will have some entries and labels & this window should destroyed after cursor moved away from window.

MJ - Just destroy the toplevel and all its child widgets are destroyed as well. In the <Leave> event binding make sure you only call the destroy when the toplevel is closed. Leaving a child widget will also call the binding, because the toplevel is in every child widgets bindtags list.

 toplevel .l
 bind .l <Leave> {tlclose %W}
 proc tlclose {w} {if {$w == [winfo toplevel $w]} {destroy $w}}

See also: