【发布时间】:2015-08-22 06:01:42
【问题描述】:
我尝试通过将这个属性与当前显示在 QComboBox 中的文本进行比较,从 QAbstractTableModel 的 data() 方法内部通过 self.category 属性过滤 self.items 的对象。但是,代码无法正常运行。
不应该将 QAbstractTableModel 的 data() 方法用作“代理模型的accepts row() 方法的替代品吗?
不使用QSortFilterProxyModel是否可以实现过滤?如果我们必须使用代理来过滤模型项,那么最 Pythonic 的方式是什么?
from PySide import QtGui, QtCore
class Item(object):
def __init__(self):
self.ID=None
self.name=None
self.category=None
class TableModel(QtCore.QAbstractTableModel):
def __init__(self, parent=None):
QtCore.QAbstractTableModel.__init__(self, parent)
self.items = []
self.filterCategory = None
def rowCount(self, parent=QtCore.QModelIndex()):
return len( [item for item in self.items if item.category==self.filterCategory] )
def columnCount(self, parent=QtCore.QModelIndex()):
return 1
def data(self, index, role):
if not index.isValid(): return
row=index.row()
item=self.items[row]
if item.category!=self.filterCategory:
return
if role == QtCore.Qt.DisplayRole:
return self.items[row].name
if role == QtCore.Qt.UserRole:
return self.items[row]
def insertRows(self, row, item, column=1, index=QtCore.QModelIndex()):
self.beginInsertRows(QtCore.QModelIndex(), row, row+1)
self.items.append(item)
self.endInsertRows()
def setFilter(self, comboText):
self.filterCategory = comboText
self.layoutChanged.emit()
def filterAcceptsRow(self, row, proc):
index=self.sourceModel().index(row, 0, proc)
item=self.sourceModel().data(index, QtCore.Qt.UserRole)
if not item: return True
resourceType=item.category
if self.filters.get(category)==False:
return False
if self.searchText and len(self.searchText)>0 and item.searchString(self.searchText)==False:
return False
return True
class MyWindow(QtGui.QWidget):
def __init__(self, *args):
QtGui.QWidget.__init__(self, *args)
vLayout=QtGui.QVBoxLayout(self)
self.setLayout(vLayout)
self.tableModel = TableModel()
self.ViewA=QtGui.QTableView(self)
self.ViewA.clicked.connect(self.viewClicked)
vLayout.addWidget(self.ViewA)
for row in range(5):
item=Item()
item.ID=row
if item.ID%2: item.category='Pet'
else: item.category='Birds'
item.name='%s_%s'%(item.category, row)
self.tableModel.insertRows(row, item)
self.ViewA.setModel(self.tableModel)
self.combo=QtGui.QComboBox()
self.combo.addItems(['Pet','Birds'])
self.combo.activated.connect(self.comboActivated)
vLayout.addWidget(self.combo)
currentComboCategory=self.combo.currentText()
self.tableModel.setFilter(currentComboCategory)
def viewClicked(self, indexClicked):
print('indexClicked() row: %s column: %s'%(indexClicked.row(), indexClicked.column() ))
def comboActivated(self, arg=None):
comboText=self.combo.currentText()
self.tableModel.setFilter(comboText)
if __name__ == "__main__":
app = QtGui.QApplication(sys.argv)
w = MyWindow()
w.show()
sys.exit(app.exec_())
【问题讨论】:
标签: python qt model pyqt qsortfilterproxymodel