How to work with sized controls (Phoenix)

Keywords : SizedControl, SizedFrame, SizedDialog, SizedPanel.


Introduction

SizedControls is an add-on library provided by wx.lib to help simplify the creation of sizer based layouts.

It does this by providing three helper base classes, SizedPanel, SizedFrame, and SizedDialog.

All of which hide some of the details about using sizers by overriding some of the virtual methods of wx.Window in order

to intercept when child windows are created and to then automatically add them to a sizer that the window has created.

This recipe will show how to use the SizedControls to help create a dialog to retrieve an address.


Demonstrating :

Tested py3.x, wx4.x and Win10.

Are you ready to use some samples ? ;)

Test, modify, correct, complete, improve and share your discoveries ! (!)


Example

How to do it : here we will define our custom dialog class by creating a subclass of SizedDialog which will automatically create the Panel and setup all the sizers.

img_sample_one.png

   1 # sample_one.py
   2 
   3 import wx
   4 import wx.lib.sized_controls as sized_ctrls
   5 
   6 # class MyAddressDialog
   7 # class MyApp
   8 
   9 #---------------------------------------------------------------------------
  10 
  11 class MyAddressDialog(sized_ctrls.SizedDialog):
  12     def __init__(self, parent, title="Address form"):
  13 
  14         style = wx.DEFAULT_DIALOG_STYLE
  15 
  16         super(MyAddressDialog, self).__init__(parent,
  17                                               title=title,
  18                                               style=style)
  19 
  20         #------------
  21 
  22         self.SetIcon(wx.Icon("wxwin.ico"))
  23 
  24         #------------
  25 
  26         # Attributes.
  27         self._data = dict(name="", street="", zip="",
  28                           state="", city="")
  29 
  30         #------------
  31 
  32         # Layout.
  33         self.DoLayout()
  34         self.SetInitialSize((300, -1))
  35 
  36         #------------
  37 
  38         self.Bind(wx.EVT_CLOSE, self.OnCloseWindow)
  39 
  40     #-----------------------------------------------------------------------
  41 
  42     def DoLayout(self):
  43         """
  44         Setup all the controls.
  45         """
  46 
  47         # Get the SizedPanel from the SizedDialog.
  48         # This must be used as the parent of the
  49         # controls we are going to create next.
  50         pane = self.GetContentsPane()
  51 
  52         # Set the Layout Type.
  53         pane.SetSizerType("form")
  54 
  55         # Create the Controls.
  56         # Each time through the loop creates one row in
  57         # the dialogs layout ("form" is a two column grid).
  58         for ctrl in ("name", "street", "city",
  59                      "state", "zip"):
  60             lbltext = "%s :" % ctrl.title()
  61             lbl = wx.StaticText(pane, label=lbltext)
  62             lbl.SetSizerProps(valign="center")
  63             txt = wx.TextCtrl(pane, name=ctrl)
  64             txt.SetSizerProps(expand=True)
  65 
  66         # Add some buttons.
  67         btnOk = wx.Button(pane,
  68                           -1,
  69                           "&Ok")
  70         self.Bind(wx.EVT_BUTTON, self.OnCloseMe, btnOk)
  71 
  72         btnCancel = wx.Button(pane,
  73                               -1,
  74                               "&Cancel")
  75         self.Bind(wx.EVT_BUTTON, self.OnCloseMe, btnCancel)
  76 
  77 
  78     def GetAddress(self):
  79         """
  80         Get the address data from the dialog.
  81         """
  82 
  83         # Update data from controls.
  84         for name in self._data:
  85             ctrl = self.FindWindowByName(name)
  86             if ctrl:
  87                 value = ctrl.GetValue()
  88                 self._data[name] = value
  89 
  90         # Create a formatted address label.
  91         template = "%(name)s\n"
  92         template += "%(street)s\n"
  93         template += "%(city)s, %(state)s %(zip)s"
  94         return template % self._data
  95 
  96 
  97     def OnCloseMe(self, event):
  98         """
  99         ...
 100         """
 101 
 102         self.Close(True)
 103 
 104 
 105     def OnCloseWindow(self, event):
 106         """
 107         ...
 108         """
 109 
 110         self.Destroy()
 111 
 112 #---------------------------------------------------------------------------
 113 
 114 class MyApp(wx.App):
 115     def OnInit(self):
 116 
 117         #------------
 118 
 119         frame = MyAddressDialog(None)
 120         self.SetTopWindow(frame)
 121         frame.Show(True)
 122 
 123         return True
 124 
 125 #---------------------------------------------------------------------------
 126 
 127 def main():
 128     app = MyApp(redirect=False)
 129     app.MainLoop()
 130 
 131 #---------------------------------------------------------------------------
 132 
 133 if __name__ == "__main__" :
 134     main()


How it works

Our AddressDialog class derives from SizedDialog which provides the framework that encapsulates the usage of sizers to help simplify the layout. Let’s start with reviewing what we did in the AddressDialog’s __DoLayout method to see how the SizedControls work. The first thing we do as part the __DoLayout is call the SizedDialog’s GetContentsPane method. This returns the dialog’s SizedPanel object. This Panel needs to be used as the parent for all the controls we add to the dialog. Next we call the SizedDialog’s SetSizerType method. This method is used to specify the type of sizer the panel will use to perform the layout of our controls. In this case we choose ‘form’ which will create a two column grid layout. We choose this because we are going to have a number of fields, each with a label and an entry field. The next step is to create all of our controls, the SizedPanel will automatically add them to our layout as they are created as its children. When it does this it dynamically attaches a new method to each object called SetSizerProps. This method can then be used to customize the way the sizer handles each object, such as its proportions and alignments. Since the dialog is going to lay the controls out in a two column grid each time through the loop and create two controls it will end up creating a new row in the layout. Finally we use the Dialog’s CreateButtonSizer method to create our Ok and Cancel buttons and then add the sizer to the layout with the SizedDialog’s SetButtonSizer method.


Theres more :

Included below are some quick references to the different types of sizers types and properties that SizedControls support.


Sizer types

The SizedPanel’s SetSizerType method accepts a string that describes the type of layout to do and optionally a dictionary of sizer options. The following table is a quick reference of the possible types.

horizontal

Use a horizontal BoxSizer layout.

vertical

Use a vertical BoxSizer layout.

form

Use a two column FlexGridSizerLayout.

table

Lays controls out in a table. Requires columns and rows specified in the options.

grid

Like ‘form’ but accepts additional options to configure the grids properties.


Sizer type options

The following table describes the possible options that can be set in the SetSizerType’s options parameter dictionary (i.e { rows : 3, columns : 5 }).

rows

Integer – number of rows

cols

Integer – number of columns

growable_row

Tuple – (row, proportion)

growable_col

Tuple – (col, proportion)

hgap

Integer – horizontal gap in pixels between columns.

vgap

Integer – vertical gap in pixels between rows.


Sizer properties

The properties can be set with the SetSizerProps method for controls that are children of a SizedPanel.

proportion

Integer – proportion value

hgrow

Integer – Grow horizontally

vgrow

Integer – Grow vertically

align

Alignment flag bitmask

border

Tuple – (list_of_directions, pixels). (left, right, top, bottom, all)

minsize

Can be “fixed” or “adjust”.

expand

Bool


Download source

source.zip


Additional Information

Link :

- - - - -

https://wiki.wxpython.org/TitleIndex

https://docs.wxpython.org/


Thanks to

CodyPrecord (sample_one.py coding), the wxPython community...


About this page

Date(d/m/y) Person (bot) Comments :

12/01/20 - Ecco (Updated page for wxPython Phoenix).


Comments

- blah, blah, blah....

How to work with sized controls (Phoenix) (last edited 2020-12-13 13:24:20 by Ecco)

NOTE: To edit pages in this wiki you must be a member of the TrustedEditorsGroup.