matrixion/src/timeline/CommunitiesModel.h

175 lines
4.9 KiB
C
Raw Normal View History

2021-06-10 00:52:28 +03:00
// SPDX-FileCopyrightText: 2021 Nheko Contributors
// SPDX-FileCopyrightText: 2022 Nheko Contributors
2021-06-10 00:52:28 +03:00
//
// SPDX-License-Identifier: GPL-3.0-or-later
#pragma once
#include <QAbstractListModel>
#include <QHash>
2021-12-01 02:02:41 +03:00
#include <QSortFilterProxyModel>
2021-06-10 00:52:28 +03:00
#include <QString>
#include <QStringList>
2022-07-16 05:09:52 +03:00
#include <unordered_map>
2021-06-10 00:52:28 +03:00
#include <mtx/responses/sync.hpp>
#include "CacheStructs.h"
2021-12-01 02:02:41 +03:00
class CommunitiesModel;
class FilteredCommunitiesModel : public QSortFilterProxyModel
{
Q_OBJECT
public:
2022-07-15 17:19:06 +03:00
explicit FilteredCommunitiesModel(CommunitiesModel *model, QObject *parent = nullptr);
2021-12-01 02:02:41 +03:00
bool lessThan(const QModelIndex &left, const QModelIndex &right) const override;
bool filterAcceptsRow(int sourceRow, const QModelIndex &) const override;
};
2021-06-10 00:52:28 +03:00
class CommunitiesModel : public QAbstractListModel
{
2021-09-18 01:22:33 +03:00
Q_OBJECT
Q_PROPERTY(QString currentTagId READ currentTagId WRITE setCurrentTagId NOTIFY
currentTagIdChanged RESET resetCurrentTagId)
Q_PROPERTY(QStringList tags READ tags NOTIFY tagsChanged)
Q_PROPERTY(QStringList tagsWithDefault READ tagsWithDefault NOTIFY tagsChanged)
Q_PROPERTY(bool containsSubspaces READ containsSubspaces NOTIFY containsSubspacesChanged)
2021-06-10 00:52:28 +03:00
public:
2021-09-18 01:22:33 +03:00
enum Roles
{
AvatarUrl = Qt::UserRole,
DisplayName,
Tooltip,
2021-12-01 02:02:41 +03:00
Collapsed,
Collapsible,
2021-09-18 01:22:33 +03:00
Hidden,
2021-12-01 02:02:41 +03:00
Parent,
Depth,
2021-09-18 01:22:33 +03:00
Id,
UnreadMessages,
2022-04-21 04:30:16 +03:00
HasLoudNotification,
Muted,
2022-04-26 03:54:40 +03:00
IsDirect,
2021-09-18 01:22:33 +03:00
};
2021-06-10 00:52:28 +03:00
2021-12-01 02:02:41 +03:00
struct FlatTree
{
struct Elem
{
QString id;
2022-07-15 17:19:06 +03:00
int depth = 0;
mtx::responses::UnreadNotifications notificationCounts = {0, 0};
2021-12-01 02:02:41 +03:00
bool collapsed = false;
};
std::vector<Elem> tree;
int size() const { return static_cast<int>(tree.size()); }
int indexOf(const QString &s) const
{
for (int i = 0; i < size(); i++)
if (tree[i].id == s)
2021-12-01 02:02:41 +03:00
return i;
return -1;
}
int lastChild(int index) const
{
if (index >= size() || index < 0)
return index;
const auto depth = tree[index].depth;
int i = index + 1;
for (; i < size(); i++)
2021-12-01 02:24:57 +03:00
if (tree[i].depth <= depth)
2021-12-01 02:02:41 +03:00
break;
return i - 1;
}
int parent(int index) const
{
if (index >= size() || index < 0)
return -1;
const auto depth = tree[index].depth;
if (depth == 0)
return -1;
int i = index - 1;
for (; i >= 0; i--)
if (tree[i].depth < depth)
break;
return i;
}
2021-12-01 05:46:55 +03:00
void storeCollapsed();
void restoreCollapsed();
2021-12-01 02:02:41 +03:00
};
2021-09-18 01:22:33 +03:00
CommunitiesModel(QObject *parent = nullptr);
QHash<int, QByteArray> roleNames() const override;
int rowCount(const QModelIndex &parent = QModelIndex()) const override
{
(void)parent;
return 2 + tags_.size() + spaceOrder_.size();
2021-09-18 01:22:33 +03:00
}
QVariant data(const QModelIndex &index, int role) const override;
2021-12-01 02:02:41 +03:00
bool setData(const QModelIndex &index, const QVariant &value, int role = Qt::EditRole) override;
2021-06-10 00:52:28 +03:00
bool containsSubspaces() const
{
for (const auto &e : spaceOrder_.tree)
if (e.depth > 0)
return true;
return false;
}
2021-06-10 00:52:28 +03:00
public slots:
2021-09-18 01:22:33 +03:00
void initializeSidebar();
void sync(const mtx::responses::Sync &sync_);
2021-09-18 01:22:33 +03:00
void clear();
QString currentTagId() const { return currentTagId_; }
void setCurrentTagId(const QString &tagId);
2021-09-18 01:22:33 +03:00
void resetCurrentTagId()
{
currentTagId_.clear();
emit currentTagIdChanged(currentTagId_);
}
QStringList tags() const { return tags_; }
QStringList tagsWithDefault() const
{
QStringList tagsWD = tags_;
tagsWD.prepend(QStringLiteral("m.lowpriority"));
tagsWD.prepend(QStringLiteral("m.favourite"));
tagsWD.removeOne(QStringLiteral("m.server_notice"));
2021-09-18 01:22:33 +03:00
tagsWD.removeDuplicates();
return tagsWD;
}
void toggleTagId(QString tagId);
void toggleTagMute(QString tagId);
2021-12-01 02:02:41 +03:00
FilteredCommunitiesModel *filtered() { return new FilteredCommunitiesModel(this, this); }
2021-06-10 00:52:28 +03:00
signals:
2021-09-18 01:22:33 +03:00
void currentTagIdChanged(QString tagId);
void hiddenTagsChanged();
void tagsChanged();
void containsSubspacesChanged();
2021-06-10 00:52:28 +03:00
private:
2021-09-18 01:22:33 +03:00
QStringList tags_;
QString currentTagId_;
2022-04-20 03:49:37 +03:00
QStringList hiddenTagIds_;
QStringList mutedTagIds_;
2021-12-01 02:02:41 +03:00
FlatTree spaceOrder_;
2021-09-18 01:22:33 +03:00
std::map<QString, RoomInfo> spaces_;
2022-04-26 03:54:40 +03:00
std::vector<std::string> directMessages_;
2021-12-01 02:02:41 +03:00
2022-07-15 17:19:06 +03:00
std::unordered_map<QString, mtx::responses::UnreadNotifications> roomNotificationCache;
std::unordered_map<QString, mtx::responses::UnreadNotifications> tagNotificationCache;
mtx::responses::UnreadNotifications globalUnreads{};
mtx::responses::UnreadNotifications dmUnreads{};
2021-12-01 02:02:41 +03:00
friend class FilteredCommunitiesModel;
2021-06-10 00:52:28 +03:00
};