]>
git.saurik.com Git - wxWidgets.git/blob - wxPython/demo/pyTree.py
   2 Hello, and welcome to this test of the wxTreeItemData 
   5 The wxTreeItemData class can be used to associate a python 
   6 object with a wxTreeCtrl item. In this sample, its use is 
   7 demonstrated via a tree control that shows the contents of a 
   8 python namespace according to the standard dir() 
   9 command. Every item in the tree has its label taken from the 
  10 dir() output, and 'behind it' a reference to the python 
  11 object is stored in a wxTreeItemData object. 
  13 As you may have guessed by now, this sample automatically 
  14 displays '__doc__' strings if the selected python object 
  15 happens to have one. Please expand the pyTree object to 
  16 learn more about the implementation. 
  18 Version 1.0, April 4 1999. 
  19 Harm van der Heijden (H.v.d.Heijden@phys.tue.nl) 
  21 P.S. Check out the string module. It's imported in this 
  22 sample not because it's used, but because it's so 
  23 beautifully documented... 
  26 import  string  
# Used for demo purposes, nothing more. :-) 
  31 #---------------------------------------------------------------------- 
  34     """Returns the indentation level of the given line.""" 
  37         if c 
== ' ': indent 
= indent 
+ 1 
  38         elif c 
== '\t': indent 
= indent 
+ 8 
  42 def _sourcefinder(func
): 
  43     """Given a func_code object, this function tries to find and return 
  44     the python source code of the function.""" 
  46         f 
= open(func
.co_filename
,"r") 
  48         return "(could not open file %s)" % (func
.co_filename
,) 
  50     for i 
in range(func
.co_firstlineno
): 
  53     ind 
= _getindent(line
) 
  59         # the following should be <= ind, but then we get 
  60         # confused by multiline docstrings. Using == works most of 
  61         # the time... but not always! 
  62         if _getindent(line
) == ind
: break 
  66 #---------------------------------------------------------------------- 
  68 class pyTree(wx
.TreeCtrl
): 
  70     This wx.TreeCtrl derivative displays a tree view of a Python namespace. 
  71     Anything from which the dir() command returns a non-empty list is a branch 
  75     def __init__(self
, parent
, id, root
): 
  77         Initialize function; because we insert branches into the tree 
  78         as needed, we use the ITEM_EXPANDING event handler. The 
  79         ITEM_COLLAPSED handler removes the stuff afterwards. The 
  80         SEL_CHANGED handler attempts to display interesting 
  81         information about the selected object. 
  83         wx
.TreeCtrl
.__init
__(self
, parent
, id) 
  84         self
.root 
= self
.AddRoot(str(root
), -1, -1, wx
.TreeItemData(root
)) 
  87             self
.SetItemHasChildren(self
.root
, True) 
  89         self
.Bind(wx
.EVT_TREE_ITEM_EXPANDING
, self
.OnItemExpanding
, id=self
.GetId()) 
  90         self
.Bind(wx
.EVT_TREE_ITEM_COLLAPSED
, self
.OnItemCollapsed
, id=self
.GetId()) 
  91         self
.Bind(wx
.EVT_TREE_SEL_CHANGED
, self
.OnSelChanged
, id=self
.GetId()) 
  94         self
.Expand(self
.root
) 
  97     def SetOutput(self
, output
): 
  99         Set output function (accepts single string). Used to display string 
 100         representation of the selected object by OnSelChanged. 
 105     def OnItemExpanding(self
,event
): 
 107         The real workhorse of this class. First we retrieve the object 
 108         (parent) belonging to the branch that is to be expanded. This 
 109         is done by calling GetPyData(parent), which is a short-cut for 
 110         GetPyItemData(parent).Get(). 
 112         Then we get the dir() list of that object. For each item in 
 113         this list, a tree item is created with associated 
 114         wxTreeItemData referencing the child object. We get this 
 115         object using child = getattr(parent, item). 
 117         Finally, we check wether the child returns a non-empty dir() 
 118         list. If so, it is labeled as 'having children', so that it 
 119         may be expanded. When it actually is expanded, this function 
 120         will again figure out what the offspring is. 
 122         item 
= event
.GetItem() 
 124         if self
.IsExpanded(item
):  # This event can happen twice in the self.Expand call 
 127         obj 
= self
.GetPyData( item 
) 
 131             new_obj 
= getattr(obj
,key
) 
 132             new_item 
= self
.AppendItem( item
, key
, -1, -1, 
 133                                         wx
.TreeItemData(new_obj
) ) 
 136                 self
.SetItemHasChildren(new_item
, True) 
 138     def OnItemCollapsed(self
, event
): 
 140         We need to remove all children here, otherwise we'll see all 
 141         that old rubbish again after the next expansion. 
 143         item 
= event
.GetItem() 
 144         self
.DeleteChildren(item
) 
 146     def OnSelChanged(self
, event
): 
 148         If an output function is defined, we try to print some 
 149         informative, interesting and thought-provoking stuff to it. 
 150         If it has a __doc__ string, we print it. If it's a function or 
 151         unbound class method, we attempt to find the python source. 
 156         obj 
= self
.GetPyData( event
.GetItem() ) 
 159         if hasattr(obj
, '__doc__'): 
 160             msg 
= msg
+"\n\nDocumentation string:\n\n%s" % ( getattr(obj
, '__doc__'),) 
 165         if hasattr(obj
, "func_code"): # normal function 
 166             func 
= getattr(obj
, "func_code") 
 168         elif hasattr(obj
, "im_func"): # unbound class method 
 169             func 
= getattr(getattr(obj
, "im_func"), "func_code") 
 171         if func
: # if we found one, let's try to print the source 
 172             msg 
= msg
+"\n\nFunction source:\n\n" + _sourcefinder(func
) 
 174         apply(self
.output
, (msg
,)) 
 176 #---------------------------------------------------------------------- 
 180 def runTest(frame
, nb
, log
): 
 182     This method is used by the wxPython Demo Framework for integrating 
 183     this demo with the rest. 
 185     thisModule 
= sys
.modules
[__name__
] 
 186     win 
= wx
.Frame(frame
, -1, "PyTreeItemData Test") 
 187     split 
= wx
.SplitterWindow(win
, -1) 
 188     tree 
= pyTree(split
, -1, thisModule
) 
 189     text 
= wx
.TextCtrl(split
, -1, "", style
=wx
.TE_MULTILINE
) 
 190     split
.SplitVertically(tree
, text
, 200) 
 191     tree
.SetOutput(text
.SetValue
) 
 192     tree
.SelectItem(tree
.root
) 
 193     win
.SetSize((800,500)) 
 199 #---------------------------------------------------------------------- 
 200 if __name__ 
== '__main__': 
 202     class MyFrame(wx
.Frame
): 
 203         """Very standard Frame class. Nothing special here!""" 
 206             """Make a splitter window; left a tree, right a textctrl. Wow.""" 
 208             wx
.Frame
.__init
__(self
, None, -1, "PyTreeItemData Test", size
=(800,500)) 
 209             split 
= wx
.SplitterWindow(self
, -1) 
 210             tree 
= pyTree(split
, -1, __main__
) 
 211             text 
= wx
.TextCtrl(split
, -1, "", style
=wx
.TE_MULTILINE
) 
 212             split
.SplitVertically(tree
, text
, 200) 
 213             tree
.SetOutput(text
.SetValue
) 
 214             tree
.SelectItem(tree
.root
) 
 217         """This class is even less interesting than MyFrame.""" 
 220             """OnInit. Boring, boring, boring!""" 
 223             self
.SetTopWindow(frame
)