Application Windows

Base Windows

In the simple examples we’ve used this far, there’s only one
window on the screen; the root window. This is automatically
created when you call the Tk constructor, and is of course
very convenient for simple applications:

There’s no need to use pack to display the Toplevel,
since it is automatically displayed by the window manager (in fact,
you’ll get an error message if you try to use pack or any
other geometry manager with a Toplevel widget).

Menus

Tkinter provides a special widget type for menus. To create a
menu, you create an instance of the Menu class, and use
add methods to add entries to it:

In this example, we start out by creating a Menu
instance, and we then use the config method to attach it
to the root window. The contents of that menu will be used to
create a menubar at the top of the root window. You don’t have to
pack the menu, since it is automatically displayed by Tkinter.

Next, we create a new Menu instance, using the menubar
as the widget parent, and the add_cascade method to make
it a pulldown menu. We then call add_command to add
commands to the menu (note that all commands in this example use
the same callback), and add_separator to add a line
between the file commands and the exit command.

Finally, we create a small help menu in the same fashion.

Toolbars

Many applications place a toolbar just under the menubar, which
typically contains a number of buttons for common functions like
open file, print, undo, etc.

In the following example, we use a Frame widget as the
toolbar, and pack a number of ordinary buttons into it.

The buttons are packed against the left side, and the toolbar
itself is packed against the topmost side, with the fill
option set to X. As a result, the widget is resized if
necssary, to cover the full with of the parent widget.

Also note that I’ve used text labels rather than icons, to keep
things simple. To display an icon, you can use the PhotoImage
constructor to load a small image from disk, and use the image
option to display it.

Status Bars

Finally, most applications sport a status bar at the bottom of
each application window. Implementing a status bar with Tkinter is
trivial: you can simply use a suitably configured Label
widget, and reconfigure the text option now and then.
Here’s one way to do it:

The set method works like C’s printf function;
it takes a format string, possibly followed by a set of arguments
(a drawback is that if you wish to print an arbitrary string, you
must do that as set(“%s”, string)). Also note that this
method calls the update_idletasks method, to make sure
pending draw operations (like the status bar update) are carried
out immediately.

But the real trick here is that we’ve inherited from the
Frame widget. At the cost of a somewhat awkward call to the
frame widget’s constructor, we’ve created a new kind of custom widget
that can be treated as any other widget. You can create and display
the status bar using the usual widget syntax:

status = StatusBar(root)
status.pack(side=BOTTOM, fill=X)

We could have inherited from the Label widget itself, and just
extended it with set and clear methods. This approach
have a few drawbacks, though:

It makes it harder to maintain the status bar’s integrity. Some
team members may cheat, and use config instead of set.
That’s not a big deal, until the day you decide to do some extra
processing in the set method. Or the day you decide to use a
Canvas widget to implement a fancier status bar.

It increases the risk that your additional methods conflict with
attributes or methods used by Tkinter. While the Frame and
Toplevel widgets have relatively few methods, other widgets can
have several dozens of widget specific attributes and methods.

Future versions of Tkinter may use factory functions rather than
class constructors for most widgets. However, it’s more or less
guaranteed that such versions will still provide Frame and
Toplevel classes. Better safe than sorry, in other words.