X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/fd4081aa33f41ccd3d373b3cac9e9172e69d888b..cbfc9df6768069f770bf8299fc0e6f528a92d4a8:/wxPython/demo/TreeMixin.py diff --git a/wxPython/demo/TreeMixin.py b/wxPython/demo/TreeMixin.py new file mode 100644 index 0000000000..8a3245571b --- /dev/null +++ b/wxPython/demo/TreeMixin.py @@ -0,0 +1,265 @@ +import wx, wx.lib.customtreectrl, wx.gizmos +try: + import treemixin +except ImportError: + from wx.lib.mixins import treemixin + +overview = treemixin.__doc__ + +class TreeModel(object): + ''' TreeModel holds the domain objects that are shown in the different + tree controls. Each domain object is simply a two-tuple consisting of + a label and a list of child tuples, i.e. (label, [list of child tuples]). + ''' + def __init__(self, *args, **kwargs): + self.items = [] + self.itemCounter = 0 + super(TreeModel, self).__init__(*args, **kwargs) + + def GetItem(self, indices): + text, children = 'Hidden root', self.items + for index in indices: + text, children = children[index] + return text, children + + def GetText(self, indices): + return self.GetItem(indices)[0] + + def GetChildren(self, indices): + return self.GetItem(indices)[1] + + def GetChildrenCount(self, indices): + return len(self.GetChildren(indices)) + + def SetChildrenCount(self, indices, count): + children = self.GetChildren(indices) + while len(children) > count: + children.pop() + while len(children) < count: + children.append(('item %d'%self.itemCounter, [])) + self.itemCounter += 1 + + def MoveItem(self, itemToMoveIndex, newParentIndex): + itemToMove = self.GetItem(itemToMoveIndex) + newParentChildren = self.GetChildren(newParentIndex) + newParentChildren.append(itemToMove) + oldParentChildren = self.GetChildren(itemToMoveIndex[:-1]) + oldParentChildren.remove(itemToMove) + + +class DemoTreeMixin(treemixin.VirtualTree, treemixin.DragAndDrop, + treemixin.ExpansionState): + def __init__(self, *args, **kwargs): + self.model = kwargs.pop('treemodel') + self.log = kwargs.pop('log') + super(DemoTreeMixin, self).__init__(*args, **kwargs) + self.CreateImageList() + + def CreateImageList(self): + size = (16, 16) + self.imageList = wx.ImageList(*size) + for art in wx.ART_FOLDER, wx.ART_FILE_OPEN, wx.ART_NORMAL_FILE: + self.imageList.Add(wx.ArtProvider.GetBitmap(art, wx.ART_OTHER, + size)) + self.AssignImageList(self.imageList) + + def OnGetItemText(self, indices): + return self.model.GetText(indices) + + def OnGetChildrenCount(self, indices): + return self.model.GetChildrenCount(indices) + + def OnGetItemFont(self, indices): + # Show how to change the item font. Here we use a small font for + # items that have children and the default font otherwise. + if self.model.GetChildrenCount(indices) > 0: + return wx.SMALL_FONT + else: + return super(DemoTreeMixin, self).OnGetItemFont(indices) + + def OnGetItemTextColour(self, indices): + # Show how to change the item text colour. In this case second level + # items are coloured red and third level items are blue. All other + # items have the default text colour. + if len(indices) % 2 == 0: + return wx.RED + elif len(indices) % 3 == 0: + return wx.BLUE + else: + return super(DemoTreeMixin, self).OnGetItemTextColour(indices) + + def OnGetItemBackgroundColour(self, indices): + # Show how to change the item background colour. In this case the + # background colour of each third item is green. + if indices[-1] == 2: + return wx.GREEN + else: + return super(DemoTreeMixin, + self).OnGetItemBackgroundColour(indices) + + def OnGetItemImage(self, indices, which): + # Return the right icon depending on whether the item has children. + if which in [wx.TreeItemIcon_Normal, wx.TreeItemIcon_Selected]: + if self.model.GetChildrenCount(indices): + return 0 + else: + return 2 + else: + return 1 + + def OnDrop(self, dropTarget, dragItem): + dropIndex = self.GetIndexOfItem(dropTarget) + dropText = self.model.GetText(dropIndex) + dragIndex = self.GetIndexOfItem(dragItem) + dragText = self.model.GetText(dragIndex) + self.log.write('drop %s %s on %s %s'%(dragText, dragIndex, + dropText, dropIndex)) + self.model.MoveItem(dragIndex, dropIndex) + self.GetParent().RefreshItems() + + +class VirtualTreeCtrl(DemoTreeMixin, wx.TreeCtrl): + pass + + +class VirtualTreeListCtrl(DemoTreeMixin, wx.gizmos.TreeListCtrl): + def __init__(self, *args, **kwargs): + kwargs['style'] = wx.TR_DEFAULT_STYLE | wx.TR_FULL_ROW_HIGHLIGHT + super(VirtualTreeListCtrl, self).__init__(*args, **kwargs) + self.AddColumn('Column 0') + self.AddColumn('Column 1') + for art in wx.ART_TIP, wx.ART_WARNING: + self.imageList.Add(wx.ArtProvider.GetBitmap(art, wx.ART_OTHER, + (16, 16))) + + def OnGetItemText(self, indices, column=0): + # Return a different label depending on column. + return '%s, column %d'%\ + (super(VirtualTreeListCtrl, self).OnGetItemText(indices), column) + + def OnGetItemImage(self, indices, which, column=0): + # Also change the image of the other columns when the item has + # children. + if column == 0: + return super(VirtualTreeListCtrl, self).OnGetItemImage(indices, + which) + elif self.OnGetChildrenCount(indices): + return 4 + else: + return 3 + + +class VirtualCustomTreeCtrl(DemoTreeMixin, + wx.lib.customtreectrl.CustomTreeCtrl): + def __init__(self, *args, **kwargs): + self.checked = {} + kwargs['ctstyle'] = wx.TR_DEFAULT_STYLE | wx.TR_HIDE_ROOT | \ + wx.TR_HAS_BUTTONS | wx.TR_FULL_ROW_HIGHLIGHT + super(VirtualCustomTreeCtrl, self).__init__(*args, **kwargs) + self.Bind(wx.lib.customtreectrl.EVT_TREE_ITEM_CHECKED, + self.OnItemChecked) + + def OnGetItemType(self, indices): + if len(indices) == 1: + return 1 + elif len(indices) == 2: + return 2 + else: + return 0 + + def OnGetItemChecked(self, indices): + return self.checked.get(indices, False) + + def OnItemChecked(self, event): + item = event.GetItem() + itemIndex = self.GetIndexOfItem(item) + if self.GetItemType(item) == 2: + # It's a radio item; reset other items on the same level + for nr in range(self.GetChildrenCount(self.GetItemParent(item))): + self.checked[itemIndex[:-1]+(nr,)] = False + self.checked[itemIndex] = True + + + +class TreeNotebook(wx.Notebook): + def __init__(self, *args, **kwargs): + treemodel = kwargs.pop('treemodel') + log = kwargs.pop('log') + super(TreeNotebook, self).__init__(*args, **kwargs) + self.trees = [] + for class_, title in [(VirtualTreeCtrl, 'TreeCtrl'), + (VirtualTreeListCtrl, 'TreeListCtrl'), + (VirtualCustomTreeCtrl, 'CustomTreeCtrl')]: + tree = class_(self, treemodel=treemodel, log=log) + self.trees.append(tree) + self.AddPage(tree, title) + self.Bind(wx.EVT_NOTEBOOK_PAGE_CHANGED, self.OnPageChanged) + + def OnPageChanged(self, event): + oldTree = self.GetPage(event.OldSelection) + newTree = self.GetPage(event.Selection) + newTree.RefreshItems() + newTree.SetExpansionState(oldTree.GetExpansionState()) + event.Skip() + + def GetIndicesOfSelectedItems(self): + tree = self.trees[self.GetSelection()] + if tree.GetSelections(): + return [tree.GetIndexOfItem(item) for item in tree.GetSelections()] + else: + return [()] + + def RefreshItems(self): + tree = self.trees[self.GetSelection()] + tree.RefreshItems() + tree.UnselectAll() + + +class TestPanel(wx.Panel): + def __init__(self, parent, log): + self.log = log + super(TestPanel, self).__init__(parent) + self.treemodel = TreeModel() + self.CreateControls() + self.LayoutControls() + + def CreateControls(self): + self.notebook = TreeNotebook(self, treemodel=self.treemodel, + log=self.log) + self.label = wx.StaticText(self, label='Number of children: ') + self.childrenCountCtrl = wx.SpinCtrl(self, value='0', max=10000) + self.button = wx.Button(self, label='Update children') + self.button.Bind(wx.EVT_BUTTON, self.OnEnter) + + def LayoutControls(self): + hSizer = wx.BoxSizer(wx.HORIZONTAL) + options = dict(flag=wx.ALIGN_CENTER_VERTICAL|wx.ALL, border=2) + hSizer.Add(self.label, **options) + hSizer.Add(self.childrenCountCtrl, 2, **options) + hSizer.Add(self.button, **options) + sizer = wx.BoxSizer(wx.VERTICAL) + sizer.Add(self.notebook, 1, wx.EXPAND) + sizer.Add(hSizer, 0, wx.EXPAND) + self.SetSizer(sizer) + + def OnEnter(self, event): + indicesList = self.notebook.GetIndicesOfSelectedItems() + newChildrenCount = self.childrenCountCtrl.GetValue() + for indices in indicesList: + text = self.treemodel.GetText(indices) + oldChildrenCount = self.treemodel.GetChildrenCount(indices) + self.log.write('%s %s now has %d children (was %d)'%(text, indices, + newChildrenCount, oldChildrenCount)) + self.treemodel.SetChildrenCount(indices, newChildrenCount) + self.notebook.RefreshItems() + + +def runTest(frame, nb, log): + win = TestPanel(nb, log) + return win + + +if __name__ == '__main__': + import sys, os, run + run.main(['', os.path.basename(sys.argv[0])] + sys.argv[1:]) +