]> git.saurik.com Git - wxWidgets.git/blame - wxPython/demo/TreeMixin.py
The great wxVScrolledWindow refactoring: allow using it both horizontal and
[wxWidgets.git] / wxPython / demo / TreeMixin.py
CommitLineData
cbfc9df6
RD
1import wx, wx.lib.customtreectrl, wx.gizmos
2try:
3 import treemixin
4except ImportError:
5 from wx.lib.mixins import treemixin
6
7overview = treemixin.__doc__
8
9class TreeModel(object):
10 ''' TreeModel holds the domain objects that are shown in the different
11 tree controls. Each domain object is simply a two-tuple consisting of
12 a label and a list of child tuples, i.e. (label, [list of child tuples]).
13 '''
14 def __init__(self, *args, **kwargs):
15 self.items = []
16 self.itemCounter = 0
17 super(TreeModel, self).__init__(*args, **kwargs)
18
19 def GetItem(self, indices):
20 text, children = 'Hidden root', self.items
21 for index in indices:
22 text, children = children[index]
23 return text, children
24
25 def GetText(self, indices):
26 return self.GetItem(indices)[0]
27
28 def GetChildren(self, indices):
29 return self.GetItem(indices)[1]
30
31 def GetChildrenCount(self, indices):
32 return len(self.GetChildren(indices))
33
34 def SetChildrenCount(self, indices, count):
35 children = self.GetChildren(indices)
36 while len(children) > count:
37 children.pop()
38 while len(children) < count:
39 children.append(('item %d'%self.itemCounter, []))
40 self.itemCounter += 1
41
42 def MoveItem(self, itemToMoveIndex, newParentIndex):
43 itemToMove = self.GetItem(itemToMoveIndex)
44 newParentChildren = self.GetChildren(newParentIndex)
45 newParentChildren.append(itemToMove)
46 oldParentChildren = self.GetChildren(itemToMoveIndex[:-1])
47 oldParentChildren.remove(itemToMove)
48
49
50class DemoTreeMixin(treemixin.VirtualTree, treemixin.DragAndDrop,
51 treemixin.ExpansionState):
52 def __init__(self, *args, **kwargs):
53 self.model = kwargs.pop('treemodel')
54 self.log = kwargs.pop('log')
55 super(DemoTreeMixin, self).__init__(*args, **kwargs)
56 self.CreateImageList()
57
58 def CreateImageList(self):
59 size = (16, 16)
60 self.imageList = wx.ImageList(*size)
61 for art in wx.ART_FOLDER, wx.ART_FILE_OPEN, wx.ART_NORMAL_FILE:
62 self.imageList.Add(wx.ArtProvider.GetBitmap(art, wx.ART_OTHER,
63 size))
64 self.AssignImageList(self.imageList)
65
66 def OnGetItemText(self, indices):
67 return self.model.GetText(indices)
68
69 def OnGetChildrenCount(self, indices):
70 return self.model.GetChildrenCount(indices)
71
72 def OnGetItemFont(self, indices):
73 # Show how to change the item font. Here we use a small font for
74 # items that have children and the default font otherwise.
75 if self.model.GetChildrenCount(indices) > 0:
76 return wx.SMALL_FONT
77 else:
78 return super(DemoTreeMixin, self).OnGetItemFont(indices)
79
80 def OnGetItemTextColour(self, indices):
81 # Show how to change the item text colour. In this case second level
82 # items are coloured red and third level items are blue. All other
83 # items have the default text colour.
84 if len(indices) % 2 == 0:
85 return wx.RED
86 elif len(indices) % 3 == 0:
87 return wx.BLUE
88 else:
89 return super(DemoTreeMixin, self).OnGetItemTextColour(indices)
90
91 def OnGetItemBackgroundColour(self, indices):
92 # Show how to change the item background colour. In this case the
93 # background colour of each third item is green.
94 if indices[-1] == 2:
95 return wx.GREEN
96 else:
97 return super(DemoTreeMixin,
98 self).OnGetItemBackgroundColour(indices)
99
100 def OnGetItemImage(self, indices, which):
101 # Return the right icon depending on whether the item has children.
102 if which in [wx.TreeItemIcon_Normal, wx.TreeItemIcon_Selected]:
103 if self.model.GetChildrenCount(indices):
104 return 0
105 else:
106 return 2
107 else:
108 return 1
109
110 def OnDrop(self, dropTarget, dragItem):
111 dropIndex = self.GetIndexOfItem(dropTarget)
112 dropText = self.model.GetText(dropIndex)
113 dragIndex = self.GetIndexOfItem(dragItem)
114 dragText = self.model.GetText(dragIndex)
115 self.log.write('drop %s %s on %s %s'%(dragText, dragIndex,
116 dropText, dropIndex))
117 self.model.MoveItem(dragIndex, dropIndex)
118 self.GetParent().RefreshItems()
119
120
121class VirtualTreeCtrl(DemoTreeMixin, wx.TreeCtrl):
122 pass
123
124
125class VirtualTreeListCtrl(DemoTreeMixin, wx.gizmos.TreeListCtrl):
126 def __init__(self, *args, **kwargs):
127 kwargs['style'] = wx.TR_DEFAULT_STYLE | wx.TR_FULL_ROW_HIGHLIGHT
128 super(VirtualTreeListCtrl, self).__init__(*args, **kwargs)
129 self.AddColumn('Column 0')
130 self.AddColumn('Column 1')
131 for art in wx.ART_TIP, wx.ART_WARNING:
132 self.imageList.Add(wx.ArtProvider.GetBitmap(art, wx.ART_OTHER,
133 (16, 16)))
134
135 def OnGetItemText(self, indices, column=0):
136 # Return a different label depending on column.
137 return '%s, column %d'%\
138 (super(VirtualTreeListCtrl, self).OnGetItemText(indices), column)
139
140 def OnGetItemImage(self, indices, which, column=0):
141 # Also change the image of the other columns when the item has
142 # children.
143 if column == 0:
144 return super(VirtualTreeListCtrl, self).OnGetItemImage(indices,
145 which)
146 elif self.OnGetChildrenCount(indices):
147 return 4
148 else:
149 return 3
150
151
152class VirtualCustomTreeCtrl(DemoTreeMixin,
153 wx.lib.customtreectrl.CustomTreeCtrl):
154 def __init__(self, *args, **kwargs):
155 self.checked = {}
156 kwargs['ctstyle'] = wx.TR_DEFAULT_STYLE | wx.TR_HIDE_ROOT | \
157 wx.TR_HAS_BUTTONS | wx.TR_FULL_ROW_HIGHLIGHT
158 super(VirtualCustomTreeCtrl, self).__init__(*args, **kwargs)
159 self.Bind(wx.lib.customtreectrl.EVT_TREE_ITEM_CHECKED,
160 self.OnItemChecked)
161
162 def OnGetItemType(self, indices):
163 if len(indices) == 1:
164 return 1
165 elif len(indices) == 2:
166 return 2
167 else:
168 return 0
169
170 def OnGetItemChecked(self, indices):
171 return self.checked.get(indices, False)
172
173 def OnItemChecked(self, event):
174 item = event.GetItem()
175 itemIndex = self.GetIndexOfItem(item)
176 if self.GetItemType(item) == 2:
177 # It's a radio item; reset other items on the same level
178 for nr in range(self.GetChildrenCount(self.GetItemParent(item))):
179 self.checked[itemIndex[:-1]+(nr,)] = False
180 self.checked[itemIndex] = True
181
182
183
184class TreeNotebook(wx.Notebook):
185 def __init__(self, *args, **kwargs):
186 treemodel = kwargs.pop('treemodel')
187 log = kwargs.pop('log')
188 super(TreeNotebook, self).__init__(*args, **kwargs)
189 self.trees = []
190 for class_, title in [(VirtualTreeCtrl, 'TreeCtrl'),
191 (VirtualTreeListCtrl, 'TreeListCtrl'),
192 (VirtualCustomTreeCtrl, 'CustomTreeCtrl')]:
193 tree = class_(self, treemodel=treemodel, log=log)
194 self.trees.append(tree)
195 self.AddPage(tree, title)
196 self.Bind(wx.EVT_NOTEBOOK_PAGE_CHANGED, self.OnPageChanged)
197
198 def OnPageChanged(self, event):
199 oldTree = self.GetPage(event.OldSelection)
200 newTree = self.GetPage(event.Selection)
201 newTree.RefreshItems()
202 newTree.SetExpansionState(oldTree.GetExpansionState())
203 event.Skip()
204
205 def GetIndicesOfSelectedItems(self):
206 tree = self.trees[self.GetSelection()]
207 if tree.GetSelections():
208 return [tree.GetIndexOfItem(item) for item in tree.GetSelections()]
209 else:
210 return [()]
211
212 def RefreshItems(self):
213 tree = self.trees[self.GetSelection()]
214 tree.RefreshItems()
215 tree.UnselectAll()
216
217
218class TestPanel(wx.Panel):
219 def __init__(self, parent, log):
220 self.log = log
221 super(TestPanel, self).__init__(parent)
222 self.treemodel = TreeModel()
223 self.CreateControls()
224 self.LayoutControls()
225
226 def CreateControls(self):
227 self.notebook = TreeNotebook(self, treemodel=self.treemodel,
228 log=self.log)
229 self.label = wx.StaticText(self, label='Number of children: ')
230 self.childrenCountCtrl = wx.SpinCtrl(self, value='0', max=10000)
231 self.button = wx.Button(self, label='Update children')
232 self.button.Bind(wx.EVT_BUTTON, self.OnEnter)
233
234 def LayoutControls(self):
235 hSizer = wx.BoxSizer(wx.HORIZONTAL)
236 options = dict(flag=wx.ALIGN_CENTER_VERTICAL|wx.ALL, border=2)
237 hSizer.Add(self.label, **options)
238 hSizer.Add(self.childrenCountCtrl, 2, **options)
239 hSizer.Add(self.button, **options)
240 sizer = wx.BoxSizer(wx.VERTICAL)
241 sizer.Add(self.notebook, 1, wx.EXPAND)
242 sizer.Add(hSizer, 0, wx.EXPAND)
243 self.SetSizer(sizer)
244
245 def OnEnter(self, event):
246 indicesList = self.notebook.GetIndicesOfSelectedItems()
247 newChildrenCount = self.childrenCountCtrl.GetValue()
248 for indices in indicesList:
249 text = self.treemodel.GetText(indices)
250 oldChildrenCount = self.treemodel.GetChildrenCount(indices)
251 self.log.write('%s %s now has %d children (was %d)'%(text, indices,
252 newChildrenCount, oldChildrenCount))
253 self.treemodel.SetChildrenCount(indices, newChildrenCount)
254 self.notebook.RefreshItems()
255
256
257def runTest(frame, nb, log):
258 win = TestPanel(nb, log)
259 return win
260
261
262if __name__ == '__main__':
263 import sys, os, run
264 run.main(['', os.path.basename(sys.argv[0])] + sys.argv[1:])
265