QTreeview Pyside 中的搜索过滤器
Search Filter in QTreeview Pyside
我在下面有一个工作示例,它添加了搜索过滤器功能。我觉得我这样做有点矫枉过正。它是从我在网上找到的项目拼凑而成的。我真的必须创建整个 SearchProxyFilter 才能对我的项目列表进行简单的字符串过滤搜索吗?
我感觉自己做错了什么,或者做错了。如有任何建议,我们将不胜感激。
#######
# Imports
#######
import sys
import os
from PySide import QtGui, QtCore
#######
# Main
#######
class SortModel(QtGui.QSortFilterProxyModel):
def __init__(self, *args, **kwargs):
super(SortModel, self).__init__(*args, **kwargs)
self._pattern = ''
@property
def pattern(self):
return self._pattern
def filterAcceptsRow(self, sourceRow, sourceParent):
if not self.pattern:
return True
sm = self.sourceModel()
modelIdx = sm.index(sourceRow, 0)
if modelIdx.isValid():
txt = modelIdx.data(role=QtCore.Qt.DisplayRole)
if not self.pattern.lower() in txt.lower():
return False
return True
def lessThan(self, left, right):
leftData = self.sourceModel().data(left)
rightData = self.sourceModel().data(right)
if leftData:
leftData = leftData.lower()
if rightData:
rightData = rightData.lower()
return leftData < rightData
class UserBrowser(QtGui.QDialog):
def __init__(self, parent=None):
super(UserBrowser, self).__init__(parent)
self.resize(300, 500)
self.setWindowTitle('Users')
self.setModal(True)
self.initUI()
def initUI(self):
self.results = ''
self.filepath = ''
self.ui_search = QtGui.QLineEdit()
self.ui_search.setPlaceholderText('Search...')
self.source_model = QtGui.QStandardItemModel()
self.user_model = SortModel(self)
self.user_model.setSourceModel(self.source_model)
self.user_model.setDynamicSortFilter(True)
self.user_model.setFilterCaseSensitivity(QtCore.Qt.CaseInsensitive)
self.ui_items = QtGui.QTreeView()
self.ui_items.setModel(self.user_model)
self.ui_items.setAlternatingRowColors(False)
self.ui_items.setSortingEnabled(True)
self.ui_items.sortByColumn(0, QtCore.Qt.AscendingOrder)
self.ui_items.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)
self.ui_items.header().setResizeMode(QtGui.QHeaderView.ResizeToContents)
self.ui_items.setHeaderHidden(True)
self.ui_items.setRootIsDecorated(False)
gdl = QtGui.QGridLayout()
gdl.setContentsMargins(10, 10, 10, 10)
gdl.addWidget(self.ui_search, 0, 0)
gdl.addWidget(self.ui_items, 1, 0)
self.setLayout(gdl)
self.create_model()
self.ui_search.textChanged.connect(self.changed_text)
# Methods
def create_model(self):
model = self.source_model
model.clear()
model.setHorizontalHeaderLabels(['Names'])
users = ['kevin','Marry','Doug','Leslie','Michelle','John']
for x in users:
item = QtGui.QStandardItem()
item.setData(x , role=QtCore.Qt.DisplayRole)
model.appendRow(item)
self.ui_items.sortByColumn(0, QtCore.Qt.AscendingOrder)
# Actions
def changed_text(self, text):
self.user_model._pattern = text
self.user_model.invalidateFilter()
def main():
app = QtGui.QApplication(sys.argv)
ex = UserBrowser()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
这可以通过 QCompleter:
更简单地完成
class UserBrowser(QtGui.QDialog):
...
def initUI(self):
...
self.completer = QtGui.QCompleter(self)
self.completer.setCaseSensitivity(QtCore.Qt.CaseInsensitive)
self.completer.setModelSorting(
QtGui.QCompleter.CaseInsensitivelySortedModel)
self.ui_items = QtGui.QTreeView()
self.ui_items.setModel(self.completer.completionModel())
...
self.create_model()
...
self.ui_search.textChanged.connect(self.completer.setCompletionPrefix)
# Methods
def create_model(self):
users = ['kevin','Marry','Doug','Leslie','Michelle','John']
users.sort(key=str.lower)
self.completer.setModel(QtGui.QStringListModel(users))
我在下面有一个工作示例,它添加了搜索过滤器功能。我觉得我这样做有点矫枉过正。它是从我在网上找到的项目拼凑而成的。我真的必须创建整个 SearchProxyFilter 才能对我的项目列表进行简单的字符串过滤搜索吗?
我感觉自己做错了什么,或者做错了。如有任何建议,我们将不胜感激。
#######
# Imports
#######
import sys
import os
from PySide import QtGui, QtCore
#######
# Main
#######
class SortModel(QtGui.QSortFilterProxyModel):
def __init__(self, *args, **kwargs):
super(SortModel, self).__init__(*args, **kwargs)
self._pattern = ''
@property
def pattern(self):
return self._pattern
def filterAcceptsRow(self, sourceRow, sourceParent):
if not self.pattern:
return True
sm = self.sourceModel()
modelIdx = sm.index(sourceRow, 0)
if modelIdx.isValid():
txt = modelIdx.data(role=QtCore.Qt.DisplayRole)
if not self.pattern.lower() in txt.lower():
return False
return True
def lessThan(self, left, right):
leftData = self.sourceModel().data(left)
rightData = self.sourceModel().data(right)
if leftData:
leftData = leftData.lower()
if rightData:
rightData = rightData.lower()
return leftData < rightData
class UserBrowser(QtGui.QDialog):
def __init__(self, parent=None):
super(UserBrowser, self).__init__(parent)
self.resize(300, 500)
self.setWindowTitle('Users')
self.setModal(True)
self.initUI()
def initUI(self):
self.results = ''
self.filepath = ''
self.ui_search = QtGui.QLineEdit()
self.ui_search.setPlaceholderText('Search...')
self.source_model = QtGui.QStandardItemModel()
self.user_model = SortModel(self)
self.user_model.setSourceModel(self.source_model)
self.user_model.setDynamicSortFilter(True)
self.user_model.setFilterCaseSensitivity(QtCore.Qt.CaseInsensitive)
self.ui_items = QtGui.QTreeView()
self.ui_items.setModel(self.user_model)
self.ui_items.setAlternatingRowColors(False)
self.ui_items.setSortingEnabled(True)
self.ui_items.sortByColumn(0, QtCore.Qt.AscendingOrder)
self.ui_items.setEditTriggers(QtGui.QAbstractItemView.NoEditTriggers)
self.ui_items.header().setResizeMode(QtGui.QHeaderView.ResizeToContents)
self.ui_items.setHeaderHidden(True)
self.ui_items.setRootIsDecorated(False)
gdl = QtGui.QGridLayout()
gdl.setContentsMargins(10, 10, 10, 10)
gdl.addWidget(self.ui_search, 0, 0)
gdl.addWidget(self.ui_items, 1, 0)
self.setLayout(gdl)
self.create_model()
self.ui_search.textChanged.connect(self.changed_text)
# Methods
def create_model(self):
model = self.source_model
model.clear()
model.setHorizontalHeaderLabels(['Names'])
users = ['kevin','Marry','Doug','Leslie','Michelle','John']
for x in users:
item = QtGui.QStandardItem()
item.setData(x , role=QtCore.Qt.DisplayRole)
model.appendRow(item)
self.ui_items.sortByColumn(0, QtCore.Qt.AscendingOrder)
# Actions
def changed_text(self, text):
self.user_model._pattern = text
self.user_model.invalidateFilter()
def main():
app = QtGui.QApplication(sys.argv)
ex = UserBrowser()
ex.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
这可以通过 QCompleter:
更简单地完成class UserBrowser(QtGui.QDialog):
...
def initUI(self):
...
self.completer = QtGui.QCompleter(self)
self.completer.setCaseSensitivity(QtCore.Qt.CaseInsensitive)
self.completer.setModelSorting(
QtGui.QCompleter.CaseInsensitivelySortedModel)
self.ui_items = QtGui.QTreeView()
self.ui_items.setModel(self.completer.completionModel())
...
self.create_model()
...
self.ui_search.textChanged.connect(self.completer.setCompletionPrefix)
# Methods
def create_model(self):
users = ['kevin','Marry','Doug','Leslie','Michelle','John']
users.sort(key=str.lower)
self.completer.setModel(QtGui.QStringListModel(users))