Site Overlay

pyGTK pack_start parameters

When I started to work with pyGTK, I had the impression that documentation is not as abundant and detailed as for learning the standard Python language in general. Among the most popular tutorials are an introduction to pyGTK by tutorialspoint.com and (so far my favourite) an intro by readthedocs.io. While these tutorials will explain the technical basics, I would have sometimes preferred a few more graphical illustrations to understand the effects of different commands to arrange graphical elements (‘widgets’) in a window.

A method frequently needed to arrange widgets in so called Box containers that pops up in early introductory examples is pack_start. I had a particular hard time of imagining what effects each of its parameters would have. So here’s a graphical illustration.

The function parameters

Taking the examples from the pyGTK tutorials and the official GTK documentation (which is not Python specific, but C++), the template for the pack_start function is as follows:

    •  Unsurprisingly, box is the destination Box object into which the childWidget is packed.
    • childWidgetcan be almost any widget – a Label, a CheckButton, a ComboBox, an image etc.
    • expand is of type boolean. If set to True, Gtk will distribute all child objects with equal spaces in between. The name is a quite misleading, because the effect is not to alter the size of the object. Rather, the parameter influences the positioning of the object (with respect to the height of the VBox or the width of an HBox).Those who do PowerPoint will know the horizontally and vertically arrange buttons which have the same effect:
      • In case we have a VBox, the objects each object will be horizontally stretched to the full width of the VBox, and they will vertically be arranged so that the space before and after each object is identical.
      • In case we have an HBox, each widget will be vertically stretched to the full height of the box. Horizontally, the objects will be arranged so that the space before and after each object has the same width.
    • Similar ill-labelled is the fill parameter. First of all, the parameter is without any effect if expand is set to False. This parameter actually stretches each widget arranged along the Box object so that any blank space is filled (evidently, this does only make sense when the objects are aligned with equal spaces along the Box by expand=True.
    • The padding parameter has an equally strange defintion. According to the GTK+3 reference (which again isn’t Python specific) padding is basically the amount of Pixels that a widget is shifted along the orientation of the Box (i.e. horizontally to the right in case of an HBox, vertically to the bottom in case of a VBox) “over and above the global amount specified by the spacing property”. The spacing property is by default set to 0 and determines the distance of a widget from its neighbours.

A less confusing way to name the function parameters would be something like:

The Basic Code

The code I am using produces 4 objects (a Button, a CheckButton, a Label and a ComboBox) and puts them all in a VBox that fills the whole main window. As a consequence, the pack_start function is called 4 times – once each for placing the 4 objects.

Parameter Testing

arrange = False

We start with calling pack_start with arrange=False as in the above base example:

Note without any arranging along the orientation of the Box object, the stretch parameter is completely without any effect whether it’s set to True or False. The left Window in the image below is with padding=0, the right image is with padding=20 for the second pack_start command that packs the Button.

pack_start called with arrange=False and padding=0 for all widgets (left) and with padding=20 for the first widget (right)

As expected, each widget is packed along the vertical orientation of the VBox. Note that pack_start by enforces stretching each widget in its width to match the full width of the VBox. In case an HBox, pack_start would stuff any widget without any horizontal space from left to right but would stretch any widget vertically to meet the height of the HBox.

We also see, that setting padding to a non-zero value enforces the space to the neighboring items before and after the widget that was packed with that padding value. The (vertical) distance between the preceding CheckBox and the Button has increased as well as the (vertical) distance between the Button and the following Label.

arrange = True, stretch = False

When calling pack_start with arrange=True and stretch=False, Gtk spreads the  widgets evenly on the vertical axis (in case of a VBox), with equal vertical white space being put before and after each widget.

pack_start function invoked with arrange=True and stretch=False with padding=0 (left) and padding=20 (right) for the CheckBox

Again to test for the effect of a non-zero padding parameter, we have set padding=20 (this time for the first element packed which is the CheckBox). This increases the vertical space above and below the CheckBox by 20px while the remaining 3 widgets are equally spaced apart along the remaining vertical space.

arrange = True, stretch = True

Setting both arrange and stretch to True will first distribute all widgets evenly spaced along the orientation of the box (i.e. vertically in case of a VBox and horizontally in case of an Hbox) and then stretch any widgets to fill the gaps left arranging the widgets with equal spacing.

Again, in order to observe the effect of the padding parameter, padding was set to 20 for one single widget (this time the Label widget, i.e. the 3rd element to be placed in the containing VBox) while all the others were set to 0.

pack_start function with both arrange and expand parameter set to True, once with padding=0 for all widgets and once with padding=20 for the 3rd widget

As expected setting padding=20 for the Label widget with arrange=True will first align all widgets with equal vertical free space among them, then stretch=True will stretch each widget equally in height (for VBox, width for Hbox) until all empty space between the widgets is consumed. Finally the Label will be extended 20px up and 20px down at the expanse of shrinking all remaining Labels proportionally.