Allow filtering the timeline for notifications

This commit is contained in:
Nicolas Werner 2025-09-13 01:01:06 +02:00
parent 5b025fa2b0
commit 53cd31d181
No known key found for this signature in database
GPG key ID: C8D75E610773F2D9
7 changed files with 73 additions and 11 deletions

View file

@ -96,6 +96,10 @@ TimelineFilter::setThreadId(const QString &t)
{
nhlog::ui()->debug("Filtering by thread '{}'", t.toStdString());
if (this->threadId != t) {
#if QT_VERSION >= QT_VERSION_CHECK(6, 9, 0)
beginFilterChange();
#endif
this->threadId = t;
emit threadIdChanged();
@ -104,11 +108,30 @@ TimelineFilter::setThreadId(const QString &t)
}
}
void
TimelineFilter::setFilterNotifications(bool filter)
{
nhlog::ui()->debug("Filtering by notifications '{}'", filter);
if (this->filterByNotifications_ != filter) {
#if QT_VERSION >= QT_VERSION_CHECK(6, 9, 0)
beginFilterChange();
#endif
this->filterByNotifications_ = filter;
emit filterNotificationsChanged();
startFiltering();
fetchMore({});
}
}
void
TimelineFilter::setContentFilter(const QString &c)
{
nhlog::ui()->debug("Filtering by content '{}'", c.toStdString());
if (this->contentFilter != c) {
#if QT_VERSION >= QT_VERSION_CHECK(6, 9, 0)
beginFilterChange();
#endif
this->contentFilter = c;
emit contentFilterChanged();
@ -145,7 +168,8 @@ TimelineFilter::sourceDataChanged(const QModelIndex &topLeft,
const QModelIndex &bottomRight,
const QVector<int> &roles)
{
if (!roles.contains(TimelineModel::Roles::Body) && !roles.contains(TimelineModel::ThreadId))
if (!roles.contains(TimelineModel::Roles::Body) && !roles.contains(TimelineModel::ThreadId) &&
!roles.contains(TimelineModel::Notificationlevel))
return;
if (auto s = source()) {
@ -233,19 +257,27 @@ TimelineFilter::filterAcceptsRow(int source_row, const QModelIndex &) const
if (source_row > incrementalSearchIndex)
return false;
if (threadId.isEmpty() && contentFilter.isEmpty())
if (threadId.isEmpty() && contentFilter.isEmpty() && !filterByNotifications_)
return true;
if (auto s = sourceModel()) {
auto idx = s->index(source_row, 0);
if (!contentFilter.isEmpty() && !s->data(idx, TimelineModel::Body)
.toString()
.contains(contentFilter, Qt::CaseInsensitive)) {
return false;
}
if (threadId.isEmpty())
if (filterByNotifications_ && s->data(idx, TimelineModel::Notificationlevel)
.value<qml_mtx_events::NotificationLevel>() !=
qml_mtx_events::NotificationLevel::Highlight) {
return false;
}
if (threadId.isEmpty()) {
return true;
}
return s->data(idx, TimelineModel::EventId) == threadId ||
s->data(idx, TimelineModel::ThreadId) == threadId;

View file

@ -18,6 +18,8 @@ class TimelineFilter : public QSortFilterProxyModel
QML_ELEMENT
Q_PROPERTY(QString filterByThread READ filterByThread WRITE setThreadId NOTIFY threadIdChanged)
Q_PROPERTY(bool filterByNotifications READ filterByNotifications WRITE setFilterNotifications
NOTIFY filterNotificationsChanged)
Q_PROPERTY(QString filterByContent READ filterByContent WRITE setContentFilter NOTIFY
contentFilterChanged)
Q_PROPERTY(TimelineModel *source READ source WRITE setSource NOTIFY sourceChanged)
@ -28,12 +30,14 @@ public:
explicit TimelineFilter(QObject *parent = nullptr);
QString filterByThread() const { return threadId; }
bool filterByNotifications() const { return filterByNotifications_; }
QString filterByContent() const { return contentFilter; }
TimelineModel *source() const;
int currentIndex() const;
bool isFiltering() const;
void setThreadId(const QString &t);
void setFilterNotifications(bool v);
void setContentFilter(const QString &t);
void setSource(TimelineModel *t);
void setCurrentIndex(int idx);
@ -47,6 +51,7 @@ public:
signals:
void threadIdChanged();
void filterNotificationsChanged();
void contentFilterChanged();
void sourceChanged();
void currentIndexChanged();
@ -67,4 +72,5 @@ private:
QString threadId, contentFilter;
int cachedCount = 0, incrementalSearchIndex = 0;
bool filterByNotifications_ = false;
};