mirror of
https://github.com/Nheko-Reborn/nheko.git
synced 2024-11-22 11:00:48 +03:00
Show widgets as links
This commit is contained in:
parent
00116e8128
commit
7b00411dc4
8 changed files with 132 additions and 11 deletions
|
@ -402,7 +402,7 @@ if(USE_BUNDLED_MTXCLIENT)
|
|||
FetchContent_Declare(
|
||||
MatrixClient
|
||||
GIT_REPOSITORY https://github.com/Nheko-Reborn/mtxclient.git
|
||||
GIT_TAG dc55f64862aeaf02d75383fbdadcbf64ea585506
|
||||
GIT_TAG 29b46c872576d88797178d3c147e8b12b1ac8693
|
||||
)
|
||||
set(BUILD_LIB_EXAMPLES OFF CACHE INTERNAL "")
|
||||
set(BUILD_LIB_TESTS OFF CACHE INTERNAL "")
|
||||
|
|
|
@ -191,7 +191,7 @@ modules:
|
|||
buildsystem: cmake-ninja
|
||||
name: mtxclient
|
||||
sources:
|
||||
- commit: dc55f64862aeaf02d75383fbdadcbf64ea585506
|
||||
- commit: 29b46c872576d88797178d3c147e8b12b1ac8693
|
||||
#tag: v0.6.1
|
||||
type: git
|
||||
url: https://github.com/Nheko-Reborn/mtxclient.git
|
||||
|
|
|
@ -36,7 +36,7 @@ Pane {
|
|||
|
||||
TapHandler {
|
||||
onSingleTapped: {
|
||||
if (eventPoint.position.y > topBar.height - (pinnedMessages.visible ? pinnedMessages.height : 0)) {
|
||||
if (eventPoint.position.y > topBar.height - (pinnedMessages.visible ? pinnedMessages.height : 0) - (widgets.visible ? widgets.height : 0)) {
|
||||
eventPoint.accepted = true
|
||||
return;
|
||||
}
|
||||
|
@ -300,6 +300,42 @@ Pane {
|
|||
}
|
||||
|
||||
|
||||
ScrollHelper {
|
||||
flickable: parent
|
||||
anchors.fill: parent
|
||||
enabled: !Settings.mobileMode
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ScrollView {
|
||||
id: widgets
|
||||
|
||||
Layout.row: 3
|
||||
Layout.column: 2
|
||||
Layout.columnSpan: 3
|
||||
|
||||
Layout.fillWidth: true
|
||||
Layout.preferredHeight: Math.min(contentHeight, Nheko.avatarSize * 1.5)
|
||||
|
||||
visible: !!room && room.widgetLinks.length > 0 && !Settings.hiddenWidgets.includes(roomId)
|
||||
clip: true
|
||||
|
||||
palette: Nheko.colors
|
||||
ScrollBar.horizontal.visible: false
|
||||
|
||||
ListView {
|
||||
|
||||
spacing: Nheko.paddingSmall
|
||||
model: room ? room.widgetLinks : undefined
|
||||
delegate: MatrixText {
|
||||
required property var modelData
|
||||
|
||||
color: Nheko.colors.text
|
||||
text: modelData
|
||||
}
|
||||
|
||||
|
||||
ScrollHelper {
|
||||
flickable: parent
|
||||
anchors.fill: parent
|
||||
|
@ -311,7 +347,7 @@ Pane {
|
|||
|
||||
CursorShape {
|
||||
anchors.fill: parent
|
||||
anchors.bottomMargin: pinnedMessages.visible ? pinnedMessages.height : 0
|
||||
anchors.bottomMargin: (pinnedMessages.visible ? pinnedMessages.height : 0) + (widgets.visible ? widgets.height : 0)
|
||||
cursorShape: Qt.PointingHandCursor
|
||||
}
|
||||
}
|
||||
|
|
|
@ -96,10 +96,12 @@ public:
|
|||
return getStateEvent<T>(txn, room_id, state_key);
|
||||
}
|
||||
template<typename T>
|
||||
std::vector<mtx::events::StateEvent<T>> getStateEventsWithType(const std::string &room_id)
|
||||
std::vector<mtx::events::StateEvent<T>>
|
||||
getStateEventsWithType(const std::string &room_id,
|
||||
mtx::events::EventType type = mtx::events::state_content_to_type<T>)
|
||||
{
|
||||
auto txn = lmdb::txn::begin(env_, nullptr, MDB_RDONLY);
|
||||
return getStateEventsWithType<T>(txn, room_id);
|
||||
return getStateEventsWithType<T>(txn, room_id, type);
|
||||
}
|
||||
|
||||
//! retrieve a specific event from account data
|
||||
|
@ -494,13 +496,11 @@ private:
|
|||
|
||||
template<typename T>
|
||||
std::vector<mtx::events::StateEvent<T>>
|
||||
getStateEventsWithType(lmdb::txn &txn, const std::string &room_id)
|
||||
getStateEventsWithType(lmdb::txn &txn,
|
||||
const std::string &room_id,
|
||||
mtx::events::EventType type = mtx::events::state_content_to_type<T>)
|
||||
|
||||
{
|
||||
constexpr auto type = mtx::events::state_content_to_type<T>;
|
||||
static_assert(type != mtx::events::EventType::Unsupported,
|
||||
"Not a supported type in state events.");
|
||||
|
||||
if (room_id.empty())
|
||||
return {};
|
||||
|
||||
|
|
|
@ -124,6 +124,7 @@ UserSettings::load(std::optional<QString> profile)
|
|||
deviceId_ = settings.value(prefix + "auth/device_id", "").toString();
|
||||
hiddenTags_ = settings.value(prefix + "user/hidden_tags", QStringList{}).toStringList();
|
||||
hiddenPins_ = settings.value(prefix + "user/hidden_pins", QStringList{}).toStringList();
|
||||
hiddenWidgets_ = settings.value(prefix + "user/hidden_widgets", QStringList{}).toStringList();
|
||||
recentReactions_ =
|
||||
settings.value(prefix + "user/recent_reactions", QStringList{}).toStringList();
|
||||
|
||||
|
@ -217,6 +218,14 @@ UserSettings::setHiddenPins(QStringList hiddenTags)
|
|||
emit hiddenPinsChanged();
|
||||
}
|
||||
|
||||
void
|
||||
UserSettings::setHiddenWidgets(QStringList hiddenTags)
|
||||
{
|
||||
hiddenWidgets_ = hiddenTags;
|
||||
save();
|
||||
emit hiddenWidgetsChanged();
|
||||
}
|
||||
|
||||
void
|
||||
UserSettings::setRecentReactions(QStringList recent)
|
||||
{
|
||||
|
@ -735,6 +744,7 @@ UserSettings::save()
|
|||
settings.setValue(prefix + "user/online_key_backup", useOnlineKeyBackup_);
|
||||
settings.setValue(prefix + "user/hidden_tags", hiddenTags_);
|
||||
settings.setValue(prefix + "user/hidden_pins", hiddenPins_);
|
||||
settings.setValue(prefix + "user/hidden_widgets", hiddenWidgets_);
|
||||
settings.setValue(prefix + "user/recent_reactions", recentReactions_);
|
||||
|
||||
QVariantList v;
|
||||
|
|
|
@ -107,6 +107,8 @@ class UserSettings : public QObject
|
|||
Q_PROPERTY(QStringList hiddenPins READ hiddenPins WRITE setHiddenPins NOTIFY hiddenPinsChanged)
|
||||
Q_PROPERTY(QStringList recentReactions READ recentReactions WRITE setRecentReactions NOTIFY
|
||||
recentReactionsChanged)
|
||||
Q_PROPERTY(QStringList hiddenWidgets READ hiddenWidgets WRITE setHiddenWidgets NOTIFY
|
||||
hiddenWidgetsChanged)
|
||||
|
||||
UserSettings();
|
||||
|
||||
|
@ -175,6 +177,7 @@ public:
|
|||
void setDisableCertificateValidation(bool disabled);
|
||||
void setHiddenTags(QStringList hiddenTags);
|
||||
void setHiddenPins(QStringList hiddenTags);
|
||||
void setHiddenWidgets(QStringList hiddenTags);
|
||||
void setRecentReactions(QStringList recent);
|
||||
void setUseIdenticon(bool state);
|
||||
void setCollapsedSpaces(QList<QStringList> spaces);
|
||||
|
@ -234,6 +237,7 @@ public:
|
|||
bool disableCertificateValidation() const { return disableCertificateValidation_; }
|
||||
QStringList hiddenTags() const { return hiddenTags_; }
|
||||
QStringList hiddenPins() const { return hiddenPins_; }
|
||||
QStringList hiddenWidgets() const { return hiddenWidgets_; }
|
||||
QStringList recentReactions() const { return recentReactions_; }
|
||||
bool useIdenticon() const { return useIdenticon_ && JdenticonProvider::isAvailable(); }
|
||||
QList<QStringList> collapsedSpaces() const { return collapsedSpaces_; }
|
||||
|
@ -286,6 +290,7 @@ signals:
|
|||
void disableCertificateValidationChanged(bool disabled);
|
||||
void useIdenticonChanged(bool state);
|
||||
void hiddenPinsChanged();
|
||||
void hiddenWidgetsChanged();
|
||||
void recentReactionsChanged();
|
||||
|
||||
private:
|
||||
|
@ -342,6 +347,7 @@ private:
|
|||
QString homeserver_;
|
||||
QStringList hiddenTags_;
|
||||
QStringList hiddenPins_;
|
||||
QStringList hiddenWidgets_;
|
||||
QStringList recentReactions_;
|
||||
QList<QStringList> collapsedSpaces_;
|
||||
bool useIdenticon_;
|
||||
|
|
|
@ -285,6 +285,9 @@ qml_mtx_events::fromRoomEventType(qml_mtx_events::EventType t)
|
|||
/// m.room.pinned_events
|
||||
case qml_mtx_events::PinnedEvents:
|
||||
return mtx::events::EventType::RoomPinnedEvents;
|
||||
/// m.widget
|
||||
case qml_mtx_events::Widget:
|
||||
return mtx::events::EventType::Widget;
|
||||
// m.sticker
|
||||
case qml_mtx_events::Sticker:
|
||||
return mtx::events::EventType::Sticker;
|
||||
|
@ -852,6 +855,8 @@ TimelineModel::syncState(const mtx::responses::State &s)
|
|||
emit roomTopicChanged();
|
||||
else if (std::holds_alternative<StateEvent<state::PinnedEvents>>(e))
|
||||
emit pinnedMessagesChanged();
|
||||
else if (std::holds_alternative<StateEvent<state::Widget>>(e))
|
||||
emit widgetLinksChanged();
|
||||
else if (std::holds_alternative<StateEvent<state::PowerLevels>>(e)) {
|
||||
permissions_.invalidate();
|
||||
emit permissionsChanged();
|
||||
|
@ -916,6 +921,8 @@ TimelineModel::addEvents(const mtx::responses::Timeline &timeline)
|
|||
emit roomTopicChanged();
|
||||
else if (std::holds_alternative<StateEvent<state::PinnedEvents>>(e))
|
||||
emit pinnedMessagesChanged();
|
||||
else if (std::holds_alternative<StateEvent<state::Widget>>(e))
|
||||
emit widgetLinksChanged();
|
||||
else if (std::holds_alternative<StateEvent<state::PowerLevels>>(e)) {
|
||||
permissions_.invalidate();
|
||||
emit permissionsChanged();
|
||||
|
@ -2225,6 +2232,63 @@ TimelineModel::pinnedMessages() const
|
|||
return list;
|
||||
}
|
||||
|
||||
QStringList
|
||||
TimelineModel::widgetLinks() const
|
||||
{
|
||||
auto evs =
|
||||
cache::client()->getStateEventsWithType<mtx::events::state::Widget>(room_id_.toStdString());
|
||||
auto evs2 = cache::client()->getStateEventsWithType<mtx::events::state::Widget>(
|
||||
room_id_.toStdString(), mtx::events::EventType::Widget);
|
||||
evs.insert(
|
||||
evs.end(), std::make_move_iterator(evs2.begin()), std::make_move_iterator(evs2.end()));
|
||||
|
||||
if (evs.empty())
|
||||
return {};
|
||||
|
||||
QStringList list;
|
||||
|
||||
auto user = utils::localUser();
|
||||
auto av = QUrl::toPercentEncoding(avatarUrl(user));
|
||||
auto disp = QUrl::toPercentEncoding(displayName(user));
|
||||
auto theme = UserSettings::instance()->theme();
|
||||
if (theme == QStringLiteral("system"))
|
||||
theme.clear();
|
||||
user = QUrl::toPercentEncoding(user);
|
||||
|
||||
list.reserve(evs.size());
|
||||
for (const auto &p : evs) {
|
||||
auto url = QString::fromStdString(p.content.url);
|
||||
for (const auto &[k, v] : p.content.data)
|
||||
url.replace("$" + QString::fromStdString(k),
|
||||
QUrl::toPercentEncoding(QString::fromStdString(v)));
|
||||
|
||||
url.replace("$matrix_user_id", user);
|
||||
url.replace("$matrix_room_id", QUrl::toPercentEncoding(room_id_));
|
||||
url.replace("$matrix_display_name", disp);
|
||||
url.replace("$matrix_avatar_url", av);
|
||||
|
||||
url.replace("$matrix_widget_id",
|
||||
QUrl::toPercentEncoding(QString::fromStdString(p.content.id)));
|
||||
|
||||
// url.replace("$matrix_client_theme", theme);
|
||||
url.replace("$org.matrix.msc2873.client_theme", theme);
|
||||
url.replace("$org.matrix.msc2873.client_id", "im.nheko");
|
||||
|
||||
// compat with some widgets, i.e. FOSDEM
|
||||
url.replace("$theme", theme);
|
||||
|
||||
url = QUrl::toPercentEncoding(url, "/:?&@=%");
|
||||
|
||||
list.push_back(
|
||||
QLatin1String("<a href='%1'>%2</a>")
|
||||
.arg(url,
|
||||
QString::fromStdString(p.content.name.empty() ? p.state_key : p.content.name)
|
||||
.toHtmlEscaped()));
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
|
||||
crypto::Trust
|
||||
TimelineModel::trustlevel() const
|
||||
{
|
||||
|
|
|
@ -91,6 +91,8 @@ enum EventType
|
|||
Sticker,
|
||||
// m.tag
|
||||
Tag,
|
||||
// m.widget
|
||||
Widget,
|
||||
/// m.room.message
|
||||
AudioMessage,
|
||||
EmoteMessage,
|
||||
|
@ -178,6 +180,7 @@ class TimelineModel : public QAbstractListModel
|
|||
Q_PROPERTY(QString roomAvatarUrl READ roomAvatarUrl NOTIFY roomAvatarUrlChanged)
|
||||
Q_PROPERTY(QString roomTopic READ roomTopic NOTIFY roomTopicChanged)
|
||||
Q_PROPERTY(QStringList pinnedMessages READ pinnedMessages NOTIFY pinnedMessagesChanged)
|
||||
Q_PROPERTY(QStringList widgetLinks READ widgetLinks NOTIFY widgetLinksChanged)
|
||||
Q_PROPERTY(int roomMemberCount READ roomMemberCount NOTIFY roomMemberCountChanged)
|
||||
Q_PROPERTY(bool isEncrypted READ isEncrypted NOTIFY encryptionChanged)
|
||||
Q_PROPERTY(bool isSpace READ isSpace CONSTANT)
|
||||
|
@ -365,6 +368,7 @@ public slots:
|
|||
QString plainRoomName() const;
|
||||
QString roomTopic() const;
|
||||
QStringList pinnedMessages() const;
|
||||
QStringList widgetLinks() const;
|
||||
InputBar *input() { return &input_; }
|
||||
Permissions *permissions() { return &permissions_; }
|
||||
QString roomAvatarUrl() const;
|
||||
|
@ -407,6 +411,7 @@ signals:
|
|||
void plainRoomNameChanged();
|
||||
void roomTopicChanged();
|
||||
void pinnedMessagesChanged();
|
||||
void widgetLinksChanged();
|
||||
void roomAvatarUrlChanged();
|
||||
void roomMemberCountChanged();
|
||||
void isDirectChanged();
|
||||
|
|
Loading…
Reference in a new issue