递归地收集 QTreeview 中的所有项目
collect all items in QTreeview recursively
我如何收集所有 Qtreeview 项目以便我可以迭代它们并应用必要的更改,如显示文本更新或颜色更改?
有没有一种简单的方法可以使用 'match' 方法收集所有这些?
def get_checked(self):
model = self.treeview.model()
checked = model.match(
model.index(0, 0), QtCore.Qt.CheckStateRole,
QtCore.Qt.Checked, -1,
QtCore.Qt.MatchExactly | QtCore.Qt.MatchRecursive)
for index in checked:
item = model.itemFromIndex(index)
print(item.text())
测试代码:
from PySide import QtGui, QtCore
from PySide import QtSvg, QtXml
import sys
class Person:
def __init__(self, name="", children=None):
self.name = name
self.children = children if children else []
class MainWindow(QtGui.QMainWindow):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.resize(300, 400)
self.init_ui()
def init_ui(self):
# Setup Tabs Widget
# self.treeview = QtGui.QTreeView()
self.treeview = QtGui.QTreeView()
self.treeview.setHeaderHidden(True)
self.treeview.setUniformRowHeights(True)
self.treeview.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)
self.model = QtGui.QStandardItemModel()
self.treeview.setModel(self.model)
self.action = QtGui.QAction('Print', self)
self.action.setShortcut('F5')
self.action.triggered.connect(self.get_checked)
fileMenu = QtGui.QMenu("&File", self)
fileMenu.addAction(self.action)
self.menuBar().addMenu(fileMenu)
# Setup central widget
self.setCentralWidget(self.treeview)
# populate data
self.populate_people()
self.treeview.expandAll()
def populate_people(self):
parent = Person("Kevin", [
Person("Tom", [Person("Sally"), Person("Susan")]),
Person("Snappy", [Person("John"), Person("Kimmy"),
Person("Joe")]),
Person("Chester", [Person("Danny"), Person("Colleen")])
]
)
self.create_nodes(parent, self.model)
def create_nodes(self, node, parent):
tnode = QtGui.QStandardItem()
tnode.setCheckable(True)
tnode.setData(QtCore.Qt.Unchecked, role=QtCore.Qt.CheckStateRole)
tnode.setData(node.name , role=QtCore.Qt.DisplayRole)
tnode.setData(node, role=QtCore.Qt.UserRole) # store object on item
parent.appendRow(tnode)
for x in node.children:
self.create_nodes(x, tnode)
def get_checked(self):
print "collecting..."
def main():
app = QtGui.QApplication(sys.argv)
ex = MainWindow()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
这是一个递归的解决方案(要求Python >= 3.3):
def iterItems(self, root):
def recurse(parent):
for row in range(parent.rowCount()):
for column in range(parent.columnCount()):
child = parent.child(row, column)
yield child
if child.hasChildren():
yield from recurse(child)
if root is not None:
yield from recurse(root)
替代递归解决方案(对于Python2/Python3):
def iterItems(self, root):
def recurse(parent):
if root is not None:
for row in range(parent.rowCount()):
for column in range(parent.columnCount()):
child = parent.child(row, column)
yield child
if child.hasChildren():
for item in recurse(child):
yield item
return recurse(root)
这是一个迭代解决方案(Python2/Python3):
def iterItems(self, root):
if root is not None:
stack = [root]
while stack:
parent = stack.pop(0)
for row in range(parent.rowCount()):
for column in range(parent.columnCount()):
child = parent.child(row, column)
yield child
if child.hasChildren():
stack.append(child)
(注意:此解决方案提供了更可预测的排序,并且速度更快)
用法:
root = self.treeview.model().invisibleRootItem()
for item in self.iterItems(root):
print(item.text())
root
参数可以是 QStandardItemModel
中的任何项目。
我如何收集所有 Qtreeview 项目以便我可以迭代它们并应用必要的更改,如显示文本更新或颜色更改?
有没有一种简单的方法可以使用 'match' 方法收集所有这些?
def get_checked(self):
model = self.treeview.model()
checked = model.match(
model.index(0, 0), QtCore.Qt.CheckStateRole,
QtCore.Qt.Checked, -1,
QtCore.Qt.MatchExactly | QtCore.Qt.MatchRecursive)
for index in checked:
item = model.itemFromIndex(index)
print(item.text())
测试代码:
from PySide import QtGui, QtCore
from PySide import QtSvg, QtXml
import sys
class Person:
def __init__(self, name="", children=None):
self.name = name
self.children = children if children else []
class MainWindow(QtGui.QMainWindow):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.resize(300, 400)
self.init_ui()
def init_ui(self):
# Setup Tabs Widget
# self.treeview = QtGui.QTreeView()
self.treeview = QtGui.QTreeView()
self.treeview.setHeaderHidden(True)
self.treeview.setUniformRowHeights(True)
self.treeview.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)
self.model = QtGui.QStandardItemModel()
self.treeview.setModel(self.model)
self.action = QtGui.QAction('Print', self)
self.action.setShortcut('F5')
self.action.triggered.connect(self.get_checked)
fileMenu = QtGui.QMenu("&File", self)
fileMenu.addAction(self.action)
self.menuBar().addMenu(fileMenu)
# Setup central widget
self.setCentralWidget(self.treeview)
# populate data
self.populate_people()
self.treeview.expandAll()
def populate_people(self):
parent = Person("Kevin", [
Person("Tom", [Person("Sally"), Person("Susan")]),
Person("Snappy", [Person("John"), Person("Kimmy"),
Person("Joe")]),
Person("Chester", [Person("Danny"), Person("Colleen")])
]
)
self.create_nodes(parent, self.model)
def create_nodes(self, node, parent):
tnode = QtGui.QStandardItem()
tnode.setCheckable(True)
tnode.setData(QtCore.Qt.Unchecked, role=QtCore.Qt.CheckStateRole)
tnode.setData(node.name , role=QtCore.Qt.DisplayRole)
tnode.setData(node, role=QtCore.Qt.UserRole) # store object on item
parent.appendRow(tnode)
for x in node.children:
self.create_nodes(x, tnode)
def get_checked(self):
print "collecting..."
def main():
app = QtGui.QApplication(sys.argv)
ex = MainWindow()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
这是一个递归的解决方案(要求Python >= 3.3):
def iterItems(self, root):
def recurse(parent):
for row in range(parent.rowCount()):
for column in range(parent.columnCount()):
child = parent.child(row, column)
yield child
if child.hasChildren():
yield from recurse(child)
if root is not None:
yield from recurse(root)
替代递归解决方案(对于Python2/Python3):
def iterItems(self, root):
def recurse(parent):
if root is not None:
for row in range(parent.rowCount()):
for column in range(parent.columnCount()):
child = parent.child(row, column)
yield child
if child.hasChildren():
for item in recurse(child):
yield item
return recurse(root)
这是一个迭代解决方案(Python2/Python3):
def iterItems(self, root):
if root is not None:
stack = [root]
while stack:
parent = stack.pop(0)
for row in range(parent.rowCount()):
for column in range(parent.columnCount()):
child = parent.child(row, column)
yield child
if child.hasChildren():
stack.append(child)
(注意:此解决方案提供了更可预测的排序,并且速度更快)
用法:
root = self.treeview.model().invisibleRootItem()
for item in self.iterItems(root):
print(item.text())
root
参数可以是 QStandardItemModel
中的任何项目。