root/trunk/RBSkinning/RBSkinning/wxPythonSkin/layout.py

Revision 718, 6.6 kB (checked in by sholloway, 5 years ago)

*** empty log message ***

Line 
1 #!/usr/bin/env python
2 ##~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3 ##~ License
4 ##~
5 ##- The RuneBlade Foundation library is intended to ease some
6 ##- aspects of writing intricate Jabber, XML, and User Interface (wxPython, etc.)
7 ##- applications, while providing the flexibility to modularly change the
8 ##- architecture. Enjoy.
9 ##~
10 ##~ Copyright (C) 2002  TechGame Networks, LLC.
11 ##~
12 ##~ This library is free software; you can redistribute it and/or
13 ##~ modify it under the terms of the BSD style License as found in the
14 ##~ LICENSE file included with this distribution.
15 ##~
16 ##~ TechGame Networks, LLC can be reached at:
17 ##~ 3578 E. Hartsel Drive #211
18 ##~ Colorado Springs, Colorado, USA, 80920
19 ##~
20 ##~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
21
22 #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
23 #~ Imports
24 #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
25
26 import warnings
27 from wxSkinLayoutObject import wx, wxSkinLayoutObject, wxSkinObjectNoData
28 from RBSkinning.wxTools import SetLayoutContainerSizeHints
29
30 #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
31 #~ Definitions
32 #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
33
34 class layout(wxSkinLayoutObject, wxSkinObjectNoData):
35     #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
36     #~ Constants / Variables / Etc.
37     #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
38
39     default_settings = wxSkinLayoutObject.default_settings.copy()
40     default_settings.update({
41         'ctxvar': 'layout',
42
43         #'orientation': 'opposite',
44         #'autosize': '1',
45         #'sethints': '1',
46         #'fit': '0',
47
48         #'args': '()',
49         })
50
51     orientation_aliases = {
52         'opp': 'opposite',
53         'o': 'opposite',
54         's': 'same',
55         'vert': 'vertical',
56         'v': 'vertical',
57         'horiz':'horizontal',
58         'h':'horizontal',
59         }
60
61     orientation_map = {
62         # Opposite is default vertical
63         'opposite': (wx.wxBoxSizer, (wx.wxVERTICAL,)),
64         'same': (wx.wxBoxSizer, (wx.wxVERTICAL,)),
65         'vertical': (wx.wxBoxSizer, (wx.wxVERTICAL,)),
66         'horizontal': (wx.wxBoxSizer, (wx.wxHORIZONTAL,)),
67         'box': (wx.wxBoxSizer, tuple()),
68         'grid': (wx.wxGridSizer, tuple()),
69         }
70
71     #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
72     #~ Public
73     #~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
74
75     def SkinInitialize(self):
76
77         # Create the layout sizer
78         orientation = self._GetOrientation()
79         sizerClass, preArgs = self.orientation_map[orientation]
80         postArgs = self.wxEvalCond('args', ())
81         self.object = sizerClass(*(preArgs + postArgs))
82         self.wxInitialStandardOptions()
83
84         # Tinker with the context to make things available
85         self.PushContext()
86
87     def SkinFinalize(self):
88         minsize = self.wxEvalCond('sizehints', (-1, -1))[:2]
89         if minsize != (-1,-1):
90             self.object.SetMinSize(minsize)
91
92         self.wxFinalStandardOptions()
93
94         parent = self.wxGetParentObject((wx.wxSizerPtr, wx.wxWindowPtr))
95         if parent is self.winParent:
96             self.winParent.SetSizer(self.object)
97             self.winParent.SetAutoLayout(self.wxEvalCond('autosize', 1))
98
99             # Set size hints
100             if self.wxEvalCond('sethints', 1):
101                 SetLayoutContainerSizeHints(self.object, self.winParent)
102
103             if self.wxEvalCond('fit', 1):
104                 self.object.Fit(self.winParent)
105         del self.winParent
106
107     def wxAddChild(self, ChildNode):
108         if isinstance(ChildNode.object, tuple):
109             args = ChildNode.object
110         elif isinstance(ChildNode.object, wx.wxNotebookPtr):
111             ChildNode.sizerobject = wx.wxNotebookSizer(ChildNode.object)
112             args = (ChildNode.sizerobject,)
113         elif isinstance(ChildNode.object, wx.wxWindowPtr):
114             if ChildNode.object.IsTopLevel():
115                 # Skip things like wxFrames, and wxDialogs
116                 return super(layout, self).wxAddChild(ChildNode)
117             else:
118                 args = (ChildNode.object,)
119         elif isinstance(ChildNode.object, wx.wxSizerPtr):
120             args = (ChildNode.object,)
121         else:
122             # Whatever it is, this layout doesn't know what to do with it...
123             return super(layout, self).wxAddChild(ChildNode)
124
125         sizerargs, sizerkw = ChildNode.wxEvalCond('sizercfg', ((), {}), codefmtstr='argskw(%s)')
126        
127         # Add to our layout object
128         self.object.Add(*(args+sizerargs), **sizerkw)
129
130         # Check for minsize directives...
131         if not isinstance(ChildNode.object, tuple):
132             minsize = ChildNode.wxEvalCond('sizehints', (-1, -1))[:2]
133             if minsize != (-1,-1):
134                 self.object.SetItemMinSize(ChildNode.object, *minsize)
135
136     def _GetOrientation(self, orientation=None, default='opposite'):
137         orientation = orientation or self.settings.get('orientation', None) or self.settings.get('orient', None) or default
138         orientation = self.orientation_aliases.get(orientation, orientation)
139         # Grab the window parent object, or the first layout derived parent
140         self.winParent = self.wxGetParentObject((wx.wxWindowPtr, layout))
141         if isinstance(self.winParent, wx.wxWindowPtr):
142             # Set sizercfg default for context, if not set
143             if 'sizercfg' not in self.settings:
144                 self.settings['sizercfg'] = '1, wxEXPAND'
145         else:
146             # Set sizercfg default for context, if not set
147             if 'sizercfg' not in self.settings:
148                 self.settings['sizercfg'] = '0, wxEXPAND'
149
150             # Layouts cancel the window parent
151             parentLayout = self.winParent
152             self.winParent = None
153
154             # Figure out what type of sizer we should be creating
155             if orientation == 'opposite':
156                 orientation = 'vertical' # New Default
157                 # Calculate the "real" opposite
158                 try: GetOrientation = parentLayout.GetOrientation
159                 except AttributeError: pass
160                 else:
161                     if GetOrientation() == wx.wxVERTICAL:
162                         orientation = 'horizontal'
163                     else: orientation = 'vertical'
164             elif orientation == 'same':
165                 orientation = 'vertical' # New Default
166                 # Calculate the "real" value
167                 try: GetOrientation = parentLayout.GetOrientation
168                 except AttributeError: pass
169                 else:
170                     if GetOrientation() == wx.wxVERTICAL:
171                         orientation = 'vertical'
172                     else: orientation = 'horizontal'
173
174         orientation = self.orientation_aliases.get(orientation, orientation)
175         return orientation
Note: See TracBrowser for help on using the browser.