]> git.saurik.com Git - wxWidgets.git/blob - wxPython/wx/tools/XRCed/panel.py
Fixed a couple namespace issues
[wxWidgets.git] / wxPython / wx / tools / XRCed / panel.py
1 # Name: panel.py
2 # Purpose: XRC editor, Panel class and related
3 # Author: Roman Rolinsky <rolinsky@mema.ucl.ac.be>
4 # Created: 02.12.2002
5 # RCS-ID: $Id$
6
7 from xxx import * # xxx imports globals and params
8 from undo import *
9 from wxPython.html import wxHtmlWindow
10
11 # Properties panel containing notebook
12 class Panel(wxNotebook):
13 def __init__(self, parent, id = -1):
14 if wxPlatform != '__WXMAC__': # some problems with this style on macs
15 wxNotebook.__init__(self, parent, id, style=wxNB_BOTTOM)
16 else:
17 wxNotebook.__init__(self, parent, id)
18 global panel
19 g.panel = panel = self
20 self.modified = False
21
22 # Set common button size for parameter buttons
23 bTmp = wxButton(self, -1, '')
24 import params
25 params.buttonSize = (self.DLG_SZE(buttonSize)[0], bTmp.GetSize()[1])
26 bTmp.Destroy()
27 del bTmp
28
29 # List of child windows
30 self.pages = []
31 # Create scrolled windows for pages
32 self.page1 = wxScrolledWindow(self, -1)
33 sizer = wxBoxSizer()
34 sizer.Add(wxBoxSizer()) # dummy sizer
35 self.page1.SetAutoLayout(True)
36 self.page1.SetSizer(sizer)
37 self.AddPage(self.page1, 'Properties')
38 # Second page
39 self.page2 = wxScrolledWindow(self, -1)
40 sizer = wxBoxSizer()
41 sizer.Add(wxBoxSizer()) # dummy sizer
42 self.page2.SetAutoLayout(True)
43 self.page2.SetSizer(sizer)
44 # Cache for already used panels
45 self.pageCache = {} # cached property panels
46 self.stylePageCache = {} # cached style panels
47 # Dummy parent window for cache pages
48 self.cacheParent = wxFrame(None, -1, 'i am invisible')
49 # Delete child windows and recreate page sizer
50 def ResetPage(self, page):
51 topSizer = page.GetSizer()
52 sizer = topSizer.GetChildren()[0].GetSizer()
53 for w in page.GetChildren():
54 sizer.RemoveWindow(w)
55 if isinstance(w, ParamPage):
56 # With SetParent, we wouldn't need this
57 w.Reparent(self.cacheParent)
58 else:
59 w.Destroy()
60 topSizer.RemoveSizer(sizer)
61 # Create new windows
62 sizer = wxBoxSizer(wxVERTICAL)
63 # Special case - resize html window
64 if g.conf.panic:
65 topSizer.Add(sizer, 1, wxEXPAND)
66 else:
67 topSizer.Add(sizer, 0, wxALL, 5)
68 return sizer
69 def SetData(self, xxx):
70 self.pages = []
71 # First page
72 # Set cached or new page
73 # Remove current objects and sizer
74 sizer = self.ResetPage(self.page1)
75 if not xxx or (not xxx.allParams and not xxx.hasName):
76 if g.tree.selection:
77 sizer.Add(wxStaticText(self.page1, -1, 'This item has no properties.'))
78 else: # nothing selected
79 # If first time, show some help
80 if g.conf.panic:
81 html = wxHtmlWindow(self.page1, -1, wxDefaultPosition,
82 wxDefaultSize, wxSUNKEN_BORDER)
83 html.SetPage(g.helpText)
84 sizer.Add(html, 1, wxEXPAND)
85 g.conf.panic = False
86 else:
87 sizer.Add(wxStaticText(self.page1, -1, 'Select a tree item.'))
88 else:
89 g.currentXXX = xxx.treeObject()
90 try:
91 page = self.pageCache[xxx.__class__]
92 page.Reparent(self.page1)
93 except KeyError:
94 page = PropPage(self.page1, xxx.className, xxx)
95 self.pageCache[xxx.__class__] = page
96 page.SetValues(xxx)
97 self.pages.append(page)
98 sizer.Add(page, 1, wxEXPAND)
99 if xxx.hasChild:
100 # Special label for child objects - they may have different GUI
101 cacheID = (xxx.child.__class__, xxx.__class__)
102 try:
103 page = self.pageCache[cacheID]
104 page.Reparent(self.page1)
105 except KeyError:
106 page = PropPage(self.page1, xxx.child.className, xxx.child)
107 self.pageCache[cacheID] = page
108 page.SetValues(xxx.child)
109 self.pages.append(page)
110 sizer.Add(page, 0, wxEXPAND | wxTOP, 5)
111 self.page1.Layout()
112 size = self.page1.GetSizer().GetMinSize()
113 self.page1.SetScrollbars(1, 1, size.width, size.height, 0, 0, True)
114
115 # Second page
116 # Create if does not exist
117 if xxx and xxx.treeObject().hasStyle:
118 xxx = xxx.treeObject()
119 # Simplest case: set data if class is the same
120 sizer = self.ResetPage(self.page2)
121 try:
122 page = self.stylePageCache[xxx.__class__]
123 page.Reparent(self.page2)
124 except KeyError:
125 page = StylePage(self.page2, xxx.className + ' style', xxx)
126 self.stylePageCache[xxx.__class__] = page
127 page.SetValues(xxx)
128 self.pages.append(page)
129 sizer.Add(page, 0, wxEXPAND)
130 # Add page if not exists
131 if not self.GetPageCount() == 2:
132 self.AddPage(self.page2, 'Style')
133 self.page2.Layout()
134 size = self.page2.GetSizer().GetMinSize()
135 self.page2.SetScrollbars(1, 1, size.width, size.height, 0, 0, True)
136 else:
137 # Remove page if exists
138 if self.GetPageCount() == 2:
139 self.SetSelection(0)
140 self.page1.Refresh()
141 self.RemovePage(1)
142 self.modified = False
143 def Clear(self):
144 self.SetData(None)
145 self.modified = False
146 # If some parameter has changed
147 def IsModified(self):
148 return self.modified
149 def SetModified(self, value):
150 # Register undo object when modifying first time
151 if not self.modified and value:
152 g.undoMan.RegisterUndo(UndoEdit())
153 self.modified = value
154 def Apply(self):
155 for p in self.pages: p.Apply()
156
157 ################################################################################
158
159 # General class for notebook pages
160 class ParamPage(wxPanel):
161 def __init__(self, parent, xxx):
162 wxPanel.__init__(self, parent, -1)
163 self.xxx = xxx
164 # Register event handlers
165 for id in paramIDs.values():
166 EVT_CHECKBOX(self, id, self.OnCheckParams)
167 self.checks = {}
168 self.controls = {} # save python objects
169 self.controlName = None
170
171 def OnCheckParams(self, evt):
172 xxx = self.xxx
173 param = evt.GetEventObject().GetName()
174 w = self.controls[param]
175 w.Enable(True)
176 objElem = xxx.element
177 if evt.IsChecked():
178 # Ad new text node in order of allParams
179 w.SetValue('') # set empty (default) value
180 w.SetModified() # mark as changed
181 elem = g.tree.dom.createElement(param)
182 # Some classes are special
183 if param == 'font':
184 xxx.params[param] = xxxParamFont(xxx.element, elem)
185 elif param in xxxObject.bitmapTags:
186 xxx.params[param] = xxxParamBitmap(elem)
187 else:
188 xxx.params[param] = xxxParam(elem)
189 # Find place to put new element: first present element after param
190 found = False
191 paramStyles = xxx.allParams + xxx.styles
192 for p in paramStyles[paramStyles.index(param) + 1:]:
193 # Content params don't have same type
194 if xxx.params.has_key(p) and p != 'content':
195 found = True
196 break
197 if found:
198 nextTextElem = xxx.params[p].node
199 objElem.insertBefore(elem, nextTextElem)
200 else:
201 objElem.appendChild(elem)
202 else:
203 # Remove parameter
204 xxx.params[param].remove()
205 del xxx.params[param]
206 w.SetValue('')
207 w.modified = False # mark as not changed
208 w.Enable(False)
209 # Set modified flag (provokes undo storing is necessary)
210 panel.SetModified(True)
211 def Apply(self):
212 xxx = self.xxx
213 if self.controlName:
214 name = self.controlName.GetValue()
215 if xxx.name != name:
216 xxx.name = name
217 xxx.element.setAttribute('name', name)
218 for param, w in self.controls.items():
219 if w.modified:
220 paramObj = xxx.params[param]
221 value = w.GetValue()
222 if param in xxx.specials:
223 xxx.setSpecial(param, value)
224 else:
225 paramObj.update(value)
226 # Save current state
227 def SaveState(self):
228 self.origChecks = map(lambda i: (i[0], i[1].GetValue()), self.checks.items())
229 self.origControls = map(lambda i: (i[0], i[1].GetValue(), i[1].IsEnabled()),
230 self.controls.items())
231 if self.controlName:
232 self.origName = self.controlName.GetValue()
233 # Return original values
234 def GetState(self):
235 if self.controlName:
236 return (self.origChecks, self.origControls, self.origName)
237 else:
238 return (self.origChecks, self.origControls)
239 # Set values from undo data
240 def SetState(self, state):
241 for k,v in state[0]:
242 self.checks[k].SetValue(v)
243 for k,v,e in state[1]:
244 self.controls[k].SetValue(v)
245 self.controls[k].Enable(e)
246 if e: self.controls[k].modified = True
247 if self.controlName:
248 self.controlName.SetValue(state[2])
249
250 ################################################################################
251
252 # Panel for displaying properties
253 class PropPage(ParamPage):
254 def __init__(self, parent, label, xxx):
255 ParamPage.__init__(self, parent, xxx)
256 box = wxStaticBox(self, -1, label)
257 box.SetFont(labelFont)
258 topSizer = wxStaticBoxSizer(box, wxVERTICAL)
259 sizer = wxFlexGridSizer(len(xxx.allParams), 2, 1, 1)
260 sizer.AddGrowableCol(1)
261 if xxx.hasName:
262 label = wxStaticText(self, -1, 'XML ID:', size=(100,-1))
263 control = ParamText(self, 'XML_name', 200)
264 sizer.AddMany([ (label, 0, wxALIGN_CENTER_VERTICAL),
265 (control, 0, wxALIGN_CENTER_VERTICAL | wxBOTTOM | wxGROW, 5) ])
266 self.controlName = control
267 for param in xxx.allParams:
268 present = xxx.params.has_key(param)
269 if param in xxx.required:
270 label = wxStaticText(self, paramIDs[param], param + ':',
271 size = (100,-1), name = param)
272 else:
273 # Notebook has one very loooooong parameter
274 if param == 'usenotebooksizer': sParam = 'usesizer:'
275 else: sParam = param + ':'
276 label = wxCheckBox(self, paramIDs[param], sParam,
277 size = (100,-1), name = param)
278 self.checks[param] = label
279 try:
280 typeClass = xxx.paramDict[param]
281 except KeyError:
282 try:
283 # Standart type
284 typeClass = paramDict[param]
285 except KeyError:
286 # Default
287 typeClass = ParamText
288 control = typeClass(self, param)
289 control.Enable(present)
290 sizer.AddMany([ (label, 0, wxALIGN_CENTER_VERTICAL),
291 (control, 0, wxALIGN_CENTER_VERTICAL | wxGROW) ])
292 self.controls[param] = control
293 topSizer.Add(sizer, 1, wxALL | wxEXPAND, 3)
294 self.SetAutoLayout(True)
295 self.SetSizer(topSizer)
296 topSizer.Fit(self)
297 def SetValues(self, xxx):
298 self.xxx = xxx
299 self.origChecks = []
300 self.origControls = []
301 # Set values, checkboxes to False, disable defaults
302 if xxx.hasName:
303 self.controlName.SetValue(xxx.name)
304 self.origName = xxx.name
305 for param in xxx.allParams:
306 w = self.controls[param]
307 w.modified = False
308 try:
309 value = xxx.params[param].value()
310 w.Enable(True)
311 w.SetValue(value)
312 if not param in xxx.required:
313 self.checks[param].SetValue(True)
314 self.origChecks.append((param, True))
315 self.origControls.append((param, value, True))
316 except KeyError:
317 self.checks[param].SetValue(False)
318 w.SetValue('')
319 w.Enable(False)
320 self.origChecks.append((param, False))
321 self.origControls.append((param, '', False))
322
323 ################################################################################
324
325 # Style notebook page
326 class StylePage(ParamPage):
327 def __init__(self, parent, label, xxx):
328 ParamPage.__init__(self, parent, xxx)
329 box = wxStaticBox(self, -1, label)
330 box.SetFont(labelFont)
331 topSizer = wxStaticBoxSizer(box, wxVERTICAL)
332 sizer = wxFlexGridSizer(len(xxx.styles), 2, 1, 1)
333 sizer.AddGrowableCol(1)
334 for param in xxx.styles:
335 present = xxx.params.has_key(param)
336 check = wxCheckBox(self, paramIDs[param],
337 param + ':', size = (100,-1), name = param)
338 check.SetValue(present)
339 control = paramDict[param](self, name = param)
340 control.Enable(present)
341 sizer.AddMany([ (check, 0, wxALIGN_CENTER_VERTICAL),
342 (control, 0, wxALIGN_CENTER_VERTICAL | wxGROW) ])
343 self.checks[param] = check
344 self.controls[param] = control
345 topSizer.Add(sizer, 1, wxALL | wxEXPAND, 3)
346 self.SetAutoLayout(True)
347 self.SetSizer(topSizer)
348 topSizer.Fit(self)
349 # Set data for a cahced page
350 def SetValues(self, xxx):
351 self.xxx = xxx
352 self.origChecks = []
353 self.origControls = []
354 for param in xxx.styles:
355 present = xxx.params.has_key(param)
356 check = self.checks[param]
357 check.SetValue(present)
358 w = self.controls[param]
359 w.modified = False
360 if present:
361 value = xxx.params[param].value()
362 else:
363 value = ''
364 w.SetValue(value)
365 w.Enable(present)
366 self.origChecks.append((param, present))
367 self.origControls.append((param, value, present))
368