Use builtin SortFilter regex functionality.
With the new completion API, we no longer need a custom filterAcceptsRow function. This was necessary to handle the tree structure of the model, but now we use a separate QSortFilterProxyModel for each category, so the data it filters is flat. We can simplify the code by using the builtin setFilterRegExp. This changes the behavior a little, as now all list categories filter on all columns. This should be beneficial if anything. For example, help topics are now filtered on description in addition to name. This also seems to slightly speed up filtering, according to the url model benchmark. Before: ----------------------------------------------- benchmark: 1 tests ---------------------------------------------- Name (time in s) Min Max Mean StdDev Median IQR Outliers(*) Rounds Iterations ----------------------------------------------------------------------------------------------------------------- test_url_completion_benchmark 1.2806 1.3817 1.3195 0.0390 1.3068 0.0487 1;0 5 1 ----------------------------------------------------------------------------------------------------------------- After: ----------------------------------------------- benchmark: 1 tests ---------------------------------------------- Name (time in s) Min Max Mean StdDev Median IQR Outliers(*) Rounds Iterations ----------------------------------------------------------------------------------------------------------------- test_url_completion_benchmark 1.1183 1.1508 1.1281 0.0132 1.1241 0.0142 1;0 5 1 -----------------------------------------------------------------------------------------------------------------
This commit is contained in:
parent
6ac940fa32
commit
9c0c174534
@ -21,7 +21,7 @@
|
||||
|
||||
import re
|
||||
|
||||
from PyQt5.QtCore import QSortFilterProxyModel, QModelIndex
|
||||
from PyQt5.QtCore import Qt, QSortFilterProxyModel, QModelIndex, QRegExp
|
||||
from PyQt5.QtGui import QStandardItem, QStandardItemModel
|
||||
|
||||
from qutebrowser.utils import qtutils
|
||||
@ -32,14 +32,14 @@ class ListCategory(QSortFilterProxyModel):
|
||||
|
||||
"""Expose a list of items as a category for the CompletionModel."""
|
||||
|
||||
def __init__(self, name, items, columns_to_filter=None,
|
||||
delete_func=None, parent=None):
|
||||
def __init__(self, name, items, delete_func=None, parent=None):
|
||||
super().__init__(parent)
|
||||
self.name = name
|
||||
self.srcmodel = QStandardItemModel(parent=self)
|
||||
self.pattern = ''
|
||||
self.pattern_re = None
|
||||
self.columns_to_filter = columns_to_filter or [0]
|
||||
# ListCategory filters all columns
|
||||
self.columns_to_filter = [0, 1, 2]
|
||||
self.setFilterKeyColumn(-1)
|
||||
for item in items:
|
||||
self.srcmodel.appendRow([QStandardItem(x) for x in item])
|
||||
self.setSourceModel(self.srcmodel)
|
||||
@ -55,38 +55,12 @@ class ListCategory(QSortFilterProxyModel):
|
||||
val = re.sub(r' +', r' ', val) # See #1919
|
||||
val = re.escape(val)
|
||||
val = val.replace(r'\ ', '.*')
|
||||
self.pattern_re = re.compile(val, re.IGNORECASE)
|
||||
rx = QRegExp(val, Qt.CaseInsensitive)
|
||||
self.setFilterRegExp(rx)
|
||||
self.invalidate()
|
||||
sortcol = 0
|
||||
self.sort(sortcol)
|
||||
|
||||
def filterAcceptsRow(self, row, parent):
|
||||
"""Custom filter implementation.
|
||||
|
||||
Override QSortFilterProxyModel::filterAcceptsRow.
|
||||
|
||||
Args:
|
||||
row: The row of the item.
|
||||
parent: The parent item QModelIndex.
|
||||
|
||||
Return:
|
||||
True if self.pattern is contained in item.
|
||||
"""
|
||||
if not self.pattern:
|
||||
return True
|
||||
|
||||
for col in self.columns_to_filter:
|
||||
idx = self.srcmodel.index(row, col, parent)
|
||||
if not idx.isValid(): # pragma: no cover
|
||||
# this is a sanity check not hit by any test case
|
||||
continue
|
||||
data = self.srcmodel.data(idx)
|
||||
if not data:
|
||||
continue
|
||||
elif self.pattern_re.search(data):
|
||||
return True
|
||||
return False
|
||||
|
||||
def lessThan(self, lindex, rindex):
|
||||
"""Custom sorting implementation.
|
||||
|
||||
|
@ -92,9 +92,6 @@ def buffer():
|
||||
|
||||
Used for switching the buffer command.
|
||||
"""
|
||||
idx_column = 0
|
||||
url_column = 1
|
||||
text_column = 2
|
||||
|
||||
def delete_buffer(data):
|
||||
"""Close the selected tab."""
|
||||
@ -117,7 +114,6 @@ def buffer():
|
||||
tab.url().toDisplayString(),
|
||||
tabbed_browser.page_title(idx)))
|
||||
cat = listcategory.ListCategory("{}".format(win_id), tabs,
|
||||
columns_to_filter=[idx_column, url_column, text_column],
|
||||
delete_func=delete_buffer)
|
||||
model.add_category(cat)
|
||||
|
||||
|
@ -62,11 +62,9 @@ def url():
|
||||
bookmarks = objreg.get('bookmark-manager').marks.items()
|
||||
|
||||
model.add_category(listcategory.ListCategory(
|
||||
'Quickmarks', quickmarks, columns_to_filter=[0, 1],
|
||||
delete_func=_delete_quickmark))
|
||||
'Quickmarks', quickmarks, delete_func=_delete_quickmark))
|
||||
model.add_category(listcategory.ListCategory(
|
||||
'Bookmarks', bookmarks, columns_to_filter=[0, 1],
|
||||
delete_func=_delete_bookmark))
|
||||
'Bookmarks', bookmarks, delete_func=_delete_bookmark))
|
||||
|
||||
# replace 's to avoid breaking the query
|
||||
timefmt = config.get('completion', 'timestamp-format').replace("'", "`")
|
||||
|
Loading…
Reference in New Issue
Block a user