Recipe 11.10. Using IDLE's Tree Widget in TkinterCredit: Sanghyeon Seo ProblemYou need to use a Tree widget in your Tkinter application, and you know that such a widget comes with IDLE, the Integrated Development Environment that comes with Python. SolutionIDLE's functionality is available in the Python Standard Library in package idlelib, so it is easy to import and use in your applications. The Tree widget is in idlelib.TreeWidget. Here, as an example, is how to use that widget to display an XML document's DOM as a tree: from Tkinter import Tk, Canvas from xml.dom.minidom import parseString from idlelib.TreeWidget import TreeItem, TreeNode class DomTreeItem(TreeItem): def _ _init_ _(self, node): self.node = node def GetText(self): node = self.node if node.nodeType == node.ELEMENT_NODE: return node.nodeName elif node.nodeType == node.TEXT_NODE: return node.nodeValue def IsExpandable(self): node = self.node return node.hasChildNodes( ) def GetSubList(self): parent = self.node children = parent.childNodes prelist = [DomTreeItem(node) for node in children] itemlist = [item for item in prelist if item.GetText( ).strip( )] return itemlist if _ _name_ _ == '_ _main_ _': example_data = ''' <A> <B> <C>d</C> <C>e</C> </B> <B> <C>f</C> </B> </A> ''' root = Tk( ) canvas = Canvas(root) canvas.config(bg='white') canvas.pack( ) dom = parseString(data) item = DomTreeItem(dom.documentElement) node = TreeNode(canvas, None, item) node.update( ) node.expand( ) root.mainloop( ) DiscussionMy applications needed Tree widgets, and Tkinter does not have such a widget among its built-in ones. So I started looking around the Internet to see the Tree widgets that had been implemented for Tkinter. After a while, I was pleasantly surprised to learn that quite a useful one was already installed and working on my computer! Specifically, I had IDLE, the free Integrated DeveLopment Environment that comes with Python, and therefore I had idlelib, the package within the standard Python library that contains just about all of the functionality of IDLE. A Tree widget is among the widgets that IDLE uses for its own GUI, so idlelib.TreeWidget is just sitting there in the standard Python library, quite usable and useful. The only problem with idlelib is that it is not well documented as a part of the Python Standard Library documentation, nor elsewhere. The best documentation I could find is the pydoc-generated one at http://pydoc.org/2.3/idlelib.html. treeWidget is one of the modules documented there. I suggest reading the sources on your disk, which include the docstrings that pydoc is using to build the useful documentation site. Between sources and pydoc, it is quite possible to reuse some of the rich functionality that's included in idlelib, although having real docs about it would definitely not hurt. Python is known as the language that comes "with batteries included." When you consider, not just the hundreds of library modules that are fully documented in Python's official docs, but also the many additional library modules that aren't (such as those in idlelib), it's hard to deny this characterization. This recipe shows how to implement a simple GUI Tree: define a node-item class by subclassing idlelib.TreeWidget.TreeItem, and override some methods. You may want to override ten methods (http://pydoc.org/2.3/idlelib.TreeWidget.html#TreeItem has the complete list), and this recipe only needs three: GetText to define how the item is displayed (textually), IsExpandable to tell the Tree whether to put a clickable + character next to the node to allow expansion, GetSubList to return a list of children items in case expansion is required. Other optional methods, which this recipe does not need, allow iconic rather than textual display, double-clicking on nodes, and even editing of Tree items. See Alsoidlelib docs at http://pydoc.org/2.3/idlelib.html. |