2 This test app is meant to help check if a widget has a good
3 DoGetBestSize method (in C++) by allowing the user to dynamically
4 create any non-toplevel widget which will be placed in a Sizer
5 designed to show how the widget will be sized naturally.
13 print "wx.VERSION_STRING = ", wx
.VERSION_STRING
14 print "pid:", os
.getpid()
15 #raw_input("Press Enter...")
17 class LayoutTestFrame(wx
.Frame
):
19 wx
.Frame
.__init
__(self
, None, -1, "Widget Layout Tester")
23 # Create control widgets
24 self
.testHistory
= wx
.ListBox(p
, -1, size
=(150, 300))
25 self
.moduleName
= wx
.TextCtrl(p
, -1, "wx")
26 self
.className
= wx
.TextCtrl(p
, -1, "")
27 self
.parameters
= wx
.TextCtrl(p
, -1, "")
28 self
.postCreate
= wx
.TextCtrl(p
, -1, "", size
=(1,75),
29 style
=wx
.TE_MULTILINE|wx
.TE_DONTWRAP
)
30 self
.expression
= wx
.TextCtrl(p
, -1, "", style
=wx
.TE_READONLY
)
31 self
.docstring
= wx
.TextCtrl(p
, -1, "", size
=(1,75),
32 style
=wx
.TE_READONLY|wx
.TE_MULTILINE|wx
.TE_DONTWRAP
)
34 self
.expression
.SetBackgroundColour(
35 wx
.SystemSettings
.GetColour(wx
.SYS_COLOUR_INFOBK
))
36 self
.docstring
.SetBackgroundColour(
37 wx
.SystemSettings
.GetColour(wx
.SYS_COLOUR_INFOBK
))
40 addBtn
= wx
.Button(p
, -1, "Add")
41 remBtn
= wx
.Button(p
, -1, "Remove")
42 repBtn
= wx
.Button(p
, -1, "Replace")
43 createBtn
= wx
.Button(p
, -1, " Create Widget ")
44 createBtn
.SetDefault()
45 destroyBtn
= wx
.Button(p
, -1, "Destroy Widget")
46 clearBtn
= wx
.Button(p
, -1, "Clear")
48 self
.createBtn
= createBtn
49 self
.destroyBtn
= destroyBtn
51 bottomPanel
= wx
.Panel(p
, style
=wx
.SUNKEN_BORDER
, name
="bottomPanel")
52 bottomPanel
.SetSizeHints((640,240))
53 bottomPanel
.SetDefaultBackgroundColour("light blue")
55 self
.testPanel
= wx
.Panel(bottomPanel
, name
="testPanel")
56 self
.testPanel
.SetDefaultBackgroundColour((205, 183, 181)) # mistyrose3
57 self
.testWidget
= None
59 self
.infoPane
= InfoPane(p
)
61 # setup event bindings
62 self
.Bind(wx
.EVT_TEXT
, self
.OnUpdate
, self
.moduleName
)
63 self
.Bind(wx
.EVT_TEXT
, self
.OnUpdate
, self
.className
)
64 self
.Bind(wx
.EVT_TEXT
, self
.OnUpdate
, self
.parameters
)
65 self
.Bind(wx
.EVT_UPDATE_UI
, self
.OnEnableCreate
, createBtn
)
66 self
.Bind(wx
.EVT_UPDATE_UI
, self
.OnEnableDestroy
, destroyBtn
)
67 self
.Bind(wx
.EVT_BUTTON
, self
.OnCreateWidget
, createBtn
)
68 self
.Bind(wx
.EVT_BUTTON
, self
.OnDestroyWidget
, destroyBtn
)
69 self
.Bind(wx
.EVT_BUTTON
, self
.OnClear
, clearBtn
)
71 self
.Bind(wx
.EVT_CLOSE
, self
.OnSaveHistory
)
73 self
.Bind(wx
.EVT_BUTTON
, self
.OnAddHistory
, addBtn
)
74 self
.Bind(wx
.EVT_BUTTON
, self
.OnRemoveHistory
, remBtn
)
75 self
.Bind(wx
.EVT_BUTTON
, self
.OnReplaceHistory
, repBtn
)
76 self
.Bind(wx
.EVT_LISTBOX
, self
.OnHistorySelect
, self
.testHistory
)
77 self
.Bind(wx
.EVT_LISTBOX_DCLICK
, self
.OnHistoryActivate
, self
.testHistory
)
81 mainSizer
= wx
.BoxSizer(wx
.VERTICAL
)
82 topSizer
= wx
.BoxSizer(wx
.HORIZONTAL
)
83 ctlsSizer
= wx
.FlexGridSizer(2, 2, 5, 5)
84 ctlsSizer
.AddGrowableCol(1)
85 btnSizer
= wx
.BoxSizer(wx
.HORIZONTAL
)
87 topSizer
.Add(self
.testHistory
, 0, wx
.RIGHT
, 30)
89 ctlsSizer
.Add(wx
.StaticText(p
, -1, "Module name:"),
90 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
91 mcSizer
= wx
.BoxSizer(wx
.HORIZONTAL
)
92 mcSizer
.Add(self
.moduleName
, 0, 0)
93 mcSizer
.Add(wx
.StaticText(p
, -1, "Class name:"),
94 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL |wx
.LEFT
, 10)
95 mcSizer
.Add(self
.className
, 1, 0)
96 ctlsSizer
.Add(mcSizer
, 0, wx
.EXPAND
)
98 ctlsSizer
.Add(wx
.StaticText(p
, -1, "Parameters:"),
99 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
100 ctlsSizer
.Add(self
.parameters
, 0, wx
.EXPAND
)
101 ctlsSizer
.Add(wx
.StaticText(p
, -1, "Create Expr:"),
102 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
103 ctlsSizer
.Add(self
.expression
, 0, wx
.EXPAND
)
104 ctlsSizer
.Add(wx
.StaticText(p
, -1, "Post create:"), 0, wx
.ALIGN_RIGHT
)
105 ctlsSizer
.Add(self
.postCreate
, 0, wx
.EXPAND
)
106 ctlsSizer
.Add(wx
.StaticText(p
, -1, "DocString:"), 0, wx
.ALIGN_RIGHT
)
107 ctlsSizer
.Add(self
.docstring
, 0, wx
.EXPAND
)
108 ctlsSizer
.AddGrowableRow(4)
109 topSizer
.Add(ctlsSizer
, 1, wx
.EXPAND
)
112 btnSizer
.Add(addBtn
, 0, wx
.RIGHT
, 5)
113 btnSizer
.Add(remBtn
, 0, wx
.RIGHT
, 5)
114 btnSizer
.Add(repBtn
, 0, wx
.RIGHT
, 5)
115 btnSizer
.Add((0,0), 1)
116 btnSizer
.Add(createBtn
, 0, wx
.RIGHT
, 5)
117 btnSizer
.Add(destroyBtn
, 0, wx
.RIGHT
, 5)
118 btnSizer
.Add(clearBtn
, 0, wx
.RIGHT
, 5)
119 btnSizer
.Add((0,0), 1)
121 mainSizer
.Add(topSizer
, 0, wx
.EXPAND|wx
.ALL
, 10)
122 mainSizer
.Add(btnSizer
, 0, wx
.EXPAND
)
123 mainSizer
.Add((10,10))
124 ##mainSizer.Add(wx.StaticLine(p, -1), 0, wx.EXPAND)
125 mainSizer
.Add(bottomPanel
, 1, wx
.EXPAND
)
127 mainSizer
.Add(self
.infoPane
, 0, wx
.EXPAND
)
129 self
.bottomSizer
= sz
= wx
.BoxSizer(wx
.VERTICAL
)
131 sz
.Add(self
.testPanel
, 0, wx
.ALIGN_CENTER
)
133 bottomPanel
.SetSizer(sz
)
135 p
.SetSizerAndFit(mainSizer
)
138 self
.PopulateHistory()
143 def PopulateHistory(self
):
145 Load and eval a list of lists from a file, load the contents
146 into self.testHistory
148 fname
= os
.path
.join(os
.path
.dirname(sys
.argv
[0]),
149 'widgetLayoutTest.cfg')
151 self
.history
= eval(open(fname
).read())
155 self
.testHistory
.Clear()
157 for idx
in range(len(self
.history
)):
158 item
= self
.history
[idx
]
159 # check if it is too short
163 # add it to the listbox
164 self
.testHistory
.Append(item
[0] + '.' + item
[1])
166 self
.needSaved
= False
169 def OnSaveHistory(self
, evt
):
171 fname
= os
.path
.join(os
.path
.dirname(sys
.argv
[0]),
172 'widgetLayoutTest.cfg')
173 f
= open(fname
, 'wb')
175 for item
in self
.history
:
176 f
.write(str(item
) + ',\n')
182 def OnAddHistory(self
, evt
):
183 moduleName
= self
.moduleName
.GetValue()
184 className
= self
.className
.GetValue()
185 parameters
= self
.parameters
.GetValue()
186 postCreate
= self
.postCreate
.GetValue()
188 item
= [str(moduleName
), str(className
), str(parameters
), str(postCreate
)]
189 self
.history
.append(item
)
190 self
.testHistory
.Append(item
[0] + '.' + item
[1])
192 self
.testHistory
.SetSelection(len(self
.history
)-1)
193 self
.needSaved
= True
196 def OnRemoveHistory(self
, evt
):
197 idx
= self
.testHistory
.GetSelection()
198 if idx
!= wx
.NOT_FOUND
:
199 del self
.history
[idx
]
200 self
.testHistory
.Delete(idx
)
201 self
.needSaved
= True
205 def OnReplaceHistory(self
, evt
):
206 idx
= self
.testHistory
.GetSelection()
207 if idx
!= wx
.NOT_FOUND
:
208 moduleName
= self
.moduleName
.GetValue()
209 className
= self
.className
.GetValue()
210 parameters
= self
.parameters
.GetValue()
211 postCreate
= self
.postCreate
.GetValue()
213 item
= [str(moduleName
), str(className
), str(parameters
), str(postCreate
)]
214 self
.history
[idx
] = item
215 self
.testHistory
.SetString(idx
, item
[0] + '.' + item
[1])
216 self
.needSaved
= True
219 def OnHistorySelect(self
, evt
):
220 idx
= self
.testHistory
.GetSelection()
221 if idx
!= wx
.NOT_FOUND
:
222 item
= self
.history
[idx
]
223 self
.moduleName
.SetValue(item
[0])
224 self
.className
.SetValue(item
[1])
225 self
.parameters
.SetValue(item
[2])
226 self
.postCreate
.SetValue(item
[3])
229 def OnHistoryActivate(self
, evt
):
230 btn
= self
.testHistory
.GetParent().GetDefaultItem()
232 e
= wx
.CommandEvent(wx
.wxEVT_COMMAND_BUTTON_CLICKED
, btn
.GetId())
237 def OnUpdate(self
, evt
):
238 # get the details from the form
239 moduleName
= self
.moduleName
.GetValue()
240 className
= self
.className
.GetValue()
241 parameters
= self
.parameters
.GetValue()
243 expr
= "w = %s.%s( testPanel, %s )" % (moduleName
, className
, parameters
)
244 self
.expression
.SetValue(expr
)
248 docstring
= eval("%s.%s.__init__.__doc__" % (moduleName
, className
))
251 self
.docstring
.SetValue(docstring
)
254 def OnEnableDestroy(self
, evt
):
255 evt
.Enable(self
.testWidget
is not None)
257 def OnEnableCreate(self
, evt
):
258 evt
.Enable(self
.testWidget
is None)
261 def OnCreateWidget(self
, evt
):
262 if self
.testWidget
is not None:
265 testPanel
= self
.testPanel
267 # get the details from the form
268 moduleName
= self
.moduleName
.GetValue()
269 className
= self
.className
.GetValue()
270 parameters
= self
.parameters
.GetValue()
271 expr
= self
.expression
.GetValue()[4:]
272 postCreate
= self
.postCreate
.GetValue()
274 # make sure the module is imported already
275 if not sys
.modules
.has_key(moduleName
):
277 m
= __import__(moduleName
)
279 wx
.MessageBox("Unable to import module!", "Error")
286 wx
.MessageBox("Got a '%s' Exception!" % e
.__class
__.__name
__, "Error")
288 traceback
.print_exc()
291 # Is there postCreate code?
297 exec postCreate
in ns
299 wx
.MessageBox("Got a '%s' Exception!" % e
.__class
__.__name
__, "Error")
301 traceback
.print_exc()
305 # Put the widget in a sizer and the sizer in the testPanel
306 sizer
= wx
.BoxSizer(wx
.VERTICAL
)
307 sizer
.Add(w
, 0, wx
.ALL
, 5)
308 self
.testPanel
.SetSizer(sizer
)
310 self
.bottomSizer
.Layout()
312 # make the destroy button be default now
313 self
.destroyBtn
.SetDefault()
315 self
.infoPane
.Update(w
, testPanel
)
318 def OnDestroyWidget(self
, evt
):
319 self
.testWidget
.Destroy()
320 self
.testWidget
= None
321 self
.testPanel
.SetSizer(None, True)
322 self
.testPanel
.Refresh()
324 # ensure the panel shrinks again
325 self
.testPanel
.SetSizeHints((20,20))
326 self
.bottomSizer
.Layout()
327 self
.testPanel
.SetSizeHints(wx
.DefaultSize
)
329 # make the create button be default now
330 self
.createBtn
.SetDefault()
332 self
.infoPane
.Clear()
335 def OnClear(self
, evt
):
336 self
.moduleName
.SetValue("")
337 self
.className
.SetValue("")
338 self
.parameters
.SetValue("")
339 self
.expression
.SetValue("")
340 self
.docstring
.SetValue("")
341 self
.postCreate
.SetValue("")
348 class InfoPane(wx
.Panel
):
350 This class is used to display details of various properties of the
351 widget and the testPanel to aid with debugging.
353 def __init__(self
, parent
):
354 wx
.Panel
.__init
__(self
, parent
)
357 self
.wPane
= SizeInfoPane(self
, "Widget")
358 self
.tpPane
= SizeInfoPane(self
, "testPanel")
359 self
.cPane
= ColourInfoPanel(self
, "Widget colours")
362 sizer
= wx
.BoxSizer(wx
.HORIZONTAL
)
363 sizer
.Add(self
.wPane
, 0, wx
.EXPAND|wx
.ALL
, 5)
364 sizer
.Add(self
.tpPane
, 0, wx
.EXPAND|wx
.ALL
, 5)
365 sizer
.Add(self
.cPane
, 0, wx
.EXPAND|wx
.ALL
, 5)
370 def Update(self
, w
, tp
):
372 self
.tpPane
.Update(tp
)
382 class SizeInfoPane(wx
.Panel
):
384 A component of the InfoPane that shows vaious window size attributes.
386 def __init__(self
, parent
, label
):
387 wx
.Panel
.__init
__(self
, parent
)
390 sb
= wx
.StaticBox(self
, -1, label
)
391 self
._size
= wx
.TextCtrl(self
, -1, "", style
=wx
.TE_READONLY
)
392 self
._minsize
= wx
.TextCtrl(self
, -1, "", style
=wx
.TE_READONLY
)
393 self
._bestsize
= wx
.TextCtrl(self
, -1, "", style
=wx
.TE_READONLY
)
394 self
._adjbstsize
= wx
.TextCtrl(self
, -1, "", style
=wx
.TE_READONLY
)
397 fgs
= wx
.FlexGridSizer(2, 2, 5, 5)
398 fgs
.AddGrowableCol(1)
400 fgs
.Add(wx
.StaticText(self
, -1, "Size:"),
401 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
402 fgs
.Add(self
._size
, 0, wx
.EXPAND
)
404 fgs
.Add(wx
.StaticText(self
, -1, "MinSize:"),
405 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
406 fgs
.Add(self
._minsize
, 0, wx
.EXPAND
)
408 fgs
.Add(wx
.StaticText(self
, -1, "BestSize:"),
409 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
410 fgs
.Add(self
._bestsize
, 0, wx
.EXPAND
)
412 fgs
.Add(wx
.StaticText(self
, -1, "AdjustedBestSize:"),
413 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
414 fgs
.Add(self
._adjbstsize
, 0, wx
.EXPAND
)
416 sbs
= wx
.StaticBoxSizer(sb
, wx
.VERTICAL
)
417 sbs
.Add(fgs
, 0, wx
.EXPAND|wx
.ALL
, 4)
422 def Update(self
, win
):
423 self
._size
.SetValue( str(win
.GetSize()) )
424 self
._minsize
.SetValue( str(win
.GetMinSize()) )
425 self
._bestsize
.SetValue( str(win
.GetBestSize()) )
426 self
._adjbstsize
.SetValue( str(win
.GetAdjustedBestSize()) )
430 self
._size
.SetValue("")
431 self
._minsize
.SetValue("")
432 self
._bestsize
.SetValue("")
433 self
._adjbstsize
.SetValue("")
437 class ColourInfoPanel(wx
.Panel
):
439 A component of the InfoPane that shows fg and bg colour attributes.
441 def __init__(self
, parent
, label
):
442 wx
.Panel
.__init
__(self
, parent
)
445 sb
= wx
.StaticBox(self
, -1, label
)
446 self
._fgtxt
= wx
.TextCtrl(self
, -1, "", style
=wx
.TE_READONLY
)
447 self
._fgclr
= wx
.Panel(self
, style
=wx
.SIMPLE_BORDER
)
448 self
._fgclr
.SetSizeHints((20,20))
449 self
._bgtxt
= wx
.TextCtrl(self
, -1, "", style
=wx
.TE_READONLY
)
450 self
._bgclr
= wx
.Panel(self
, style
=wx
.SIMPLE_BORDER
)
451 self
._bgclr
.SetSizeHints((20,20))
454 fgs
= wx
.FlexGridSizer(2, 3, 5, 5)
455 fgs
.AddGrowableCol(1)
457 fgs
.Add(wx
.StaticText(self
, -1, "FG colour:"),
458 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
459 fgs
.Add(self
._fgtxt
, 0, wx
.EXPAND
)
462 fgs
.Add(wx
.StaticText(self
, -1, "BG colour:"),
463 0, wx
.ALIGN_RIGHT|wx
.ALIGN_CENTER_VERTICAL
)
464 fgs
.Add(self
._bgtxt
, 0, wx
.EXPAND
)
467 sbs
= wx
.StaticBoxSizer(sb
, wx
.VERTICAL
)
468 sbs
.Add(fgs
, 0, wx
.EXPAND|wx
.ALL
, 4)
473 def Update(self
, win
):
475 cp
.SetBackgroundColour(c
)
477 return "#%02X%02X%02X" % c
.Get()
479 self
._fgtxt
.SetValue( clr2hex(win
.GetForegroundColour(), self
._fgclr
) )
480 self
._bgtxt
.SetValue( clr2hex(win
.GetBackgroundColour(), self
._bgclr
) )
483 ## print f.GetNativeFontInfo().ToString()
487 self
._fgtxt
.SetValue("")
488 self
._bgtxt
.SetValue("")
489 self
._fgclr
.SetBackgroundColour(self
.GetBackgroundColour())
490 self
._bgclr
.SetBackgroundColour(self
.GetBackgroundColour())
491 self
._fgclr
.Refresh()
492 self
._bgclr
.Refresh()
497 app
= wx
.PySimpleApp(redirect
=True)
498 frame
= LayoutTestFrame()
499 app
.SetTopWindow(frame
)