As mentioned in post IIC, if our ultimate goal were to display a tree as simple as the one in the simpletreemodel, we would probably just use QTreeWidget or QStandardItemModel. In both cases, it is almost embarrassing how much easier it is to create the tree. This is because we don't need to roll our own model or data item classes.
In what follows, we will see how to use QTreeWidget and QStandardItemModel to create and view a read-only tree with multiple columns of data in each row. To keep it simple, we won't load data from a file, and the code only creates a very simple little tree. It would be a useful exercise to expand these examples to exactly mimic the GUI created in simpletreemodel.
QTreeWidget
While it is often poo-poohed as slow and inflexible, for simple projects QTreeWidget is extremely convenient and easy to use. Simply instantiate an instance of QTreeWidget, populate the tree with QTreeWidgetItem instances, and then call show() on the widget:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | from PySide import QtGui import sys app = QtGui.QApplication(sys.argv) treeWidget = QtGui.QTreeWidget() treeWidget.setColumnCount(2) treeWidget.setHeaderLabels(['Title', 'Summary']); #First top level item and its kids item0 = QtGui.QTreeWidgetItem(treeWidget, ['Title 0', 'Summary 0']) item00 = QtGui.QTreeWidgetItem(item0, ['Title 00', 'Summary 00'] ) item01 = QtGui.QTreeWidgetItem(item0, ['Title 01', 'Summary 01']) #Second top level item and its kids item1 = QtGui.QTreeWidgetItem(treeWidget, ['Title 1', 'Summary 1']) item10 = QtGui.QTreeWidgetItem(item1, ['Title 10', 'Summary 10']) item11 = QtGui.QTreeWidgetItem(item1, ['Title 11', 'Summary 11']) item12 = QtGui.QTreeWidgetItem(item1, ['Title 12', 'Summary 12']) #Children of item11 item110 = QtGui.QTreeWidgetItem(item11, ['Title 110', 'Summary 110']) item111 = QtGui.QTreeWidgetItem(item11, ['Title 111', 'Summary 111']) treeWidget.show() sys.exit(app.exec_()) |
QStandardItemModel
This is only slightly more complicated than QTreeWidget. We populate the tree with lists of QStandardItems. To add a child to a row, we apply appendRow() to the first element (i.e., the first column) of the parent row:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | from PySide import QtGui import sys app = QtGui.QApplication(sys.argv) model = QtGui.QStandardItemModel() model.setHorizontalHeaderLabels(['Title', 'Summary']) rootItem = model.invisibleRootItem() #First top-level row and children item0 = [QtGui.QStandardItem('Title0'), QtGui.QStandardItem('Summary0')] item00 = [QtGui.QStandardItem('Title00'), QtGui.QStandardItem('Summary00')] item01 = [QtGui.QStandardItem('Title01'), QtGui.QStandardItem('Summary01')] rootItem.appendRow(item0) item0[0].appendRow(item00) item0[0].appendRow(item01) #Second top-level item and its children item1 = [QtGui.QStandardItem('Title1'), QtGui.QStandardItem('Summary1')] item10 = [QtGui.QStandardItem('Title10'), QtGui.QStandardItem('Summary10')] item11 = [QtGui.QStandardItem('Title11'), QtGui.QStandardItem('Summary11')] item12 = [QtGui.QStandardItem('Title12'), QtGui.QStandardItem('Summary12')] rootItem.appendRow(item1) item1[0].appendRow(item10) item1[0].appendRow(item11) item1[0].appendRow(item12) #Children of item11 (third level items) item110 = [QtGui.QStandardItem('Title110'), QtGui.QStandardItem('Summary110')] item111 = [QtGui.QStandardItem('Title111'), QtGui.QStandardItem('Summary111')] item11[0].appendRow(item110) item11[0].appendRow(item111) treeView= QtGui.QTreeView() treeView.setModel(model) treeView.show() sys.exit(app.exec_()) |
While a tad more complicated than using QTreeWidget, this is still drastically simpler than subclassing QAbstractItemModel.
Conclusion
As is usually the case, there are many ways to get to the same destination. The route you take will depend on your goals, the complexity of your data, how much time you have to write your code, and how fast you want the program to be. As mentioned before, it would be overkill to subclass QAbstractItemModel for a data store as simple as the one in simpletreemodel. This post shows just how easy it would be to create the exact same tree with an order of magnitude less code.
Those that have read any of these posts, thanks for reading! I'll be putting a PDF of all the posts together so you don't have to fight through a maze of posts for all the information.