Kam Sen
Kam Sen

Reputation: 1148

Qt treewidget python; iterate columns

Given a tree widget in PyQt4 with some rows and columns:

1) Is there a way to easily iterate over all cells?

2) How can one check if a checkbox is checked apart from the first column?

So far I only managed to get the results of the checkboxes in the first column, see here.

For clarification here is the widget how I imagine it to look like: (the fourth column should be editable)

widget structure

from PyQt4.QtCore import * 
from PyQt4.QtGui import * 
import sys


def main(): 
    app     = QApplication (sys.argv)
    tree    = QTreeWidget ()
    item    = QTreeWidgetItem()

    tree.headerItem().setText(0, "col1")
    tree.headerItem().setText(1, "col2")
    tree.headerItem().setText(2, "col3")
    tree.headerItem().setText(3, "Notes")

    for ii in xrange(3):
        parent = QTreeWidgetItem(tree)
        parent.setText(0, "Parent {}".format(ii))
        parent.setFlags(parent.flags() | Qt.ItemIsTristate | Qt.ItemIsUserCheckable)
        for x in xrange(4):
            child = QTreeWidgetItem(parent)
            child.setFlags(child.flags() | Qt.ItemIsUserCheckable)
            child.setText(0, "Child {}".format(x))
            child.setCheckState(0, Qt.Unchecked)

            #create the checkbox
            for i in xrange(1, 5):
                if i < 3:
                    child.setText(i, "")
                    child.setCheckState(i, Qt.Unchecked)
                if i == 3:
                    child.setText(i, "Any Notes?")
                    child.setFlags(child.flags() | Qt.ItemIsEditable)

    tree.show() 
    sys.exit(app.exec_())

if __name__ == '__main__':
    main()

Upvotes: 2

Views: 4039

Answers (1)

ekhumoro
ekhumoro

Reputation: 120578

One way to iterate over a tree-widget is to use QTreeWidgetItemIterator:

def iter_tree_widget(root):
    iterator = QtGui.QTreeWidgetItemIterator(root)
    while True:
        item = iterator.value()
        if item is not None:
            yield item
            iterator += 1
        else:
            break

The root argument can be either a tree-widget (to iterate over the whole tree), or a tree-widget-item (to iterate over a single branch).

The iterator produces one item per row, and the columns of this item are accessed by simply specifying the column index:

column = 0
for item in iter_tree_widget(tree):
    print('State: %s, Text: "%s"' % (
          item.checkState(column), item.text(column)))

Upvotes: 3

Related Questions