mirror of
https://github.com/Nheko-Reborn/nheko.git
synced 2024-11-22 03:00:46 +03:00
Communities (#195)
This commit is contained in:
parent
81a706bf20
commit
312df6f3bb
23 changed files with 1054 additions and 13 deletions
3
.gitignore
vendored
3
.gitignore
vendored
|
@ -35,6 +35,9 @@ ui_*.h
|
||||||
|
|
||||||
*.autosave
|
*.autosave
|
||||||
|
|
||||||
|
# VSCode
|
||||||
|
.vscode/*
|
||||||
|
|
||||||
#QtCtreator Qml
|
#QtCtreator Qml
|
||||||
*.qmlproject.user
|
*.qmlproject.user
|
||||||
*.qmlproject.user.*
|
*.qmlproject.user.*
|
||||||
|
|
|
@ -186,6 +186,9 @@ set(SRC_FILES
|
||||||
src/AvatarProvider.cc
|
src/AvatarProvider.cc
|
||||||
src/Cache.cc
|
src/Cache.cc
|
||||||
src/ChatPage.cc
|
src/ChatPage.cc
|
||||||
|
src/CommunitiesListItem.cc
|
||||||
|
src/CommunitiesList.cc
|
||||||
|
src/Community.cc
|
||||||
src/Deserializable.cc
|
src/Deserializable.cc
|
||||||
src/InviteeItem.cc
|
src/InviteeItem.cc
|
||||||
src/InputValidator.cc
|
src/InputValidator.cc
|
||||||
|
@ -265,6 +268,9 @@ qt5_wrap_cpp(MOC_HEADERS
|
||||||
|
|
||||||
include/AvatarProvider.h
|
include/AvatarProvider.h
|
||||||
include/ChatPage.h
|
include/ChatPage.h
|
||||||
|
include/CommunitiesListItem.h
|
||||||
|
include/CommunitiesList.h
|
||||||
|
include/Community.h
|
||||||
include/LoginPage.h
|
include/LoginPage.h
|
||||||
include/MainWindow.h
|
include/MainWindow.h
|
||||||
include/InviteeItem.h
|
include/InviteeItem.h
|
||||||
|
|
|
@ -24,6 +24,8 @@
|
||||||
#include <QTimer>
|
#include <QTimer>
|
||||||
#include <QWidget>
|
#include <QWidget>
|
||||||
|
|
||||||
|
#include "CommunitiesList.h"
|
||||||
|
#include "Community.h"
|
||||||
#include <mtx.hpp>
|
#include <mtx.hpp>
|
||||||
|
|
||||||
class Cache;
|
class Cache;
|
||||||
|
@ -80,6 +82,7 @@ private slots:
|
||||||
void showUnreadMessageNotification(int count);
|
void showUnreadMessageNotification(int count);
|
||||||
void updateTopBarAvatar(const QString &roomid, const QPixmap &img);
|
void updateTopBarAvatar(const QString &roomid, const QPixmap &img);
|
||||||
void updateOwnProfileInfo(const QUrl &avatar_url, const QString &display_name);
|
void updateOwnProfileInfo(const QUrl &avatar_url, const QString &display_name);
|
||||||
|
void updateOwnCommunitiesInfo(const QList<QString> &own_communities);
|
||||||
void setOwnAvatar(const QPixmap &img);
|
void setOwnAvatar(const QPixmap &img);
|
||||||
void initialSyncCompleted(const mtx::responses::Sync &response);
|
void initialSyncCompleted(const mtx::responses::Sync &response);
|
||||||
void syncCompleted(const mtx::responses::Sync &response);
|
void syncCompleted(const mtx::responses::Sync &response);
|
||||||
|
@ -126,13 +129,21 @@ private:
|
||||||
QHBoxLayout *topLayout_;
|
QHBoxLayout *topLayout_;
|
||||||
Splitter *splitter;
|
Splitter *splitter;
|
||||||
|
|
||||||
QFrame *sideBar_;
|
QWidget *sideBar_;
|
||||||
|
QWidget *communitiesSideBar_;
|
||||||
|
QVBoxLayout *communitiesSideBarLayout_;
|
||||||
QVBoxLayout *sideBarLayout_;
|
QVBoxLayout *sideBarLayout_;
|
||||||
|
QVBoxLayout *sideBarTopLayout_;
|
||||||
|
QVBoxLayout *sideBarMainLayout_;
|
||||||
|
QWidget *sideBarTopWidget_;
|
||||||
|
QVBoxLayout *sideBarTopWidgetLayout_;
|
||||||
|
|
||||||
QFrame *content_;
|
QFrame *content_;
|
||||||
QVBoxLayout *contentLayout_;
|
QVBoxLayout *contentLayout_;
|
||||||
|
|
||||||
|
CommunitiesList *communitiesList_;
|
||||||
RoomList *room_list_;
|
RoomList *room_list_;
|
||||||
|
|
||||||
TimelineViewManager *view_manager_;
|
TimelineViewManager *view_manager_;
|
||||||
SideBarActions *sidebarActions_;
|
SideBarActions *sidebarActions_;
|
||||||
|
|
||||||
|
@ -145,13 +156,18 @@ private:
|
||||||
QTimer *consensusTimer_;
|
QTimer *consensusTimer_;
|
||||||
|
|
||||||
QString current_room_;
|
QString current_room_;
|
||||||
|
QString current_community_;
|
||||||
|
|
||||||
QMap<QString, QPixmap> room_avatars_;
|
QMap<QString, QPixmap> room_avatars_;
|
||||||
|
QMap<QString, QPixmap> community_avatars_;
|
||||||
|
|
||||||
UserInfoWidget *user_info_widget_;
|
UserInfoWidget *user_info_widget_;
|
||||||
|
|
||||||
QMap<QString, RoomState> state_manager_;
|
QMap<QString, RoomState> state_manager_;
|
||||||
QMap<QString, QSharedPointer<RoomSettings>> settingsManager_;
|
QMap<QString, QSharedPointer<RoomSettings>> settingsManager_;
|
||||||
|
|
||||||
|
QMap<QString, QSharedPointer<Community>> communityManager_;
|
||||||
|
|
||||||
// Keeps track of the users currently typing on each room.
|
// Keeps track of the users currently typing on each room.
|
||||||
QMap<QString, QList<QString>> typingUsers_;
|
QMap<QString, QList<QString>> typingUsers_;
|
||||||
QTimer *typingRefresher_;
|
QTimer *typingRefresher_;
|
||||||
|
|
42
include/CommunitiesList.h
Normal file
42
include/CommunitiesList.h
Normal file
|
@ -0,0 +1,42 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <QScrollArea>
|
||||||
|
#include <QSharedPointer>
|
||||||
|
#include <QVBoxLayout>
|
||||||
|
#include <QWidget>
|
||||||
|
|
||||||
|
#include "CommunitiesListItem.h"
|
||||||
|
#include "Community.h"
|
||||||
|
#include "MatrixClient.h"
|
||||||
|
#include "ui/Theme.h"
|
||||||
|
|
||||||
|
class CommunitiesList : public QWidget
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
public:
|
||||||
|
CommunitiesList(QSharedPointer<MatrixClient> client, QWidget *parent = nullptr);
|
||||||
|
~CommunitiesList();
|
||||||
|
|
||||||
|
void setCommunities(const QMap<QString, QSharedPointer<Community>> &communities);
|
||||||
|
void clear();
|
||||||
|
|
||||||
|
void addCommunity(QSharedPointer<Community> community, const QString &community_id);
|
||||||
|
void removeCommunity(const QString &community_id);
|
||||||
|
signals:
|
||||||
|
void communityChanged(const QString &community_id);
|
||||||
|
|
||||||
|
public slots:
|
||||||
|
void updateCommunityAvatar(const QString &community_id, const QPixmap &img);
|
||||||
|
void highlightSelectedCommunity(const QString &community_id);
|
||||||
|
|
||||||
|
private:
|
||||||
|
QVBoxLayout *topLayout_;
|
||||||
|
QVBoxLayout *contentsLayout_;
|
||||||
|
QWidget *scrollAreaContents_;
|
||||||
|
QScrollArea *scrollArea_;
|
||||||
|
|
||||||
|
QMap<QString, QSharedPointer<CommunitiesListItem>> communities_;
|
||||||
|
|
||||||
|
QSharedPointer<MatrixClient> client_;
|
||||||
|
};
|
98
include/CommunitiesListItem.h
Normal file
98
include/CommunitiesListItem.h
Normal file
|
@ -0,0 +1,98 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <QDebug>
|
||||||
|
#include <QMouseEvent>
|
||||||
|
#include <QPainter>
|
||||||
|
#include <QSharedPointer>
|
||||||
|
#include <QWidget>
|
||||||
|
|
||||||
|
#include "Community.h"
|
||||||
|
#include "Menu.h"
|
||||||
|
#include "ui/Theme.h"
|
||||||
|
|
||||||
|
class CommunitiesListItem : public QWidget
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(QColor highlightedBackgroundColor READ highlightedBackgroundColor WRITE
|
||||||
|
setHighlightedBackgroundColor)
|
||||||
|
Q_PROPERTY(
|
||||||
|
QColor hoverBackgroundColor READ hoverBackgroundColor WRITE setHoverBackgroundColor)
|
||||||
|
Q_PROPERTY(QColor backgroundColor READ backgroundColor WRITE setBackgroundColor)
|
||||||
|
|
||||||
|
public:
|
||||||
|
CommunitiesListItem(QSharedPointer<Community> community,
|
||||||
|
QString community_id,
|
||||||
|
QWidget *parent = nullptr);
|
||||||
|
|
||||||
|
~CommunitiesListItem();
|
||||||
|
|
||||||
|
void setCommunity(QSharedPointer<Community> community);
|
||||||
|
|
||||||
|
inline bool isPressed() const;
|
||||||
|
inline void setAvatar(const QImage &avatar_image);
|
||||||
|
|
||||||
|
QColor highlightedBackgroundColor() const { return highlightedBackgroundColor_; }
|
||||||
|
QColor hoverBackgroundColor() const { return hoverBackgroundColor_; }
|
||||||
|
QColor backgroundColor() const { return backgroundColor_; }
|
||||||
|
|
||||||
|
void setHighlightedBackgroundColor(QColor &color) { highlightedBackgroundColor_ = color; }
|
||||||
|
void setHoverBackgroundColor(QColor &color) { hoverBackgroundColor_ = color; }
|
||||||
|
void setBackgroundColor(QColor &color) { backgroundColor_ = color; }
|
||||||
|
|
||||||
|
QColor highlightedBackgroundColor_;
|
||||||
|
QColor hoverBackgroundColor_;
|
||||||
|
QColor backgroundColor_;
|
||||||
|
|
||||||
|
signals:
|
||||||
|
void clicked(const QString &community_id);
|
||||||
|
|
||||||
|
public slots:
|
||||||
|
void setPressedState(bool state);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void mousePressEvent(QMouseEvent *event) override;
|
||||||
|
void paintEvent(QPaintEvent *event) override;
|
||||||
|
void contextMenuEvent(QContextMenuEvent *event) override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
const int IconSize = 55;
|
||||||
|
|
||||||
|
QSharedPointer<Community> community_;
|
||||||
|
QString communityId_;
|
||||||
|
QString communityName_;
|
||||||
|
QString communityShortDescription;
|
||||||
|
|
||||||
|
QPixmap communityAvatar_;
|
||||||
|
|
||||||
|
Menu *menu_;
|
||||||
|
bool isPressed_ = false;
|
||||||
|
};
|
||||||
|
|
||||||
|
inline bool
|
||||||
|
CommunitiesListItem::isPressed() const
|
||||||
|
{
|
||||||
|
return isPressed_;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void
|
||||||
|
CommunitiesListItem::setAvatar(const QImage &avatar_image)
|
||||||
|
{
|
||||||
|
communityAvatar_ = QPixmap::fromImage(
|
||||||
|
avatar_image.scaled(IconSize, IconSize, Qt::IgnoreAspectRatio, Qt::SmoothTransformation));
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
|
||||||
|
class WorldCommunityListItem : public CommunitiesListItem
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
WorldCommunityListItem(QWidget *parent = nullptr);
|
||||||
|
~WorldCommunityListItem();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void mousePressEvent(QMouseEvent *event) override;
|
||||||
|
void paintEvent(QPaintEvent *event) override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
const int IconSize = 55;
|
||||||
|
};
|
62
include/Community.h
Normal file
62
include/Community.h
Normal file
|
@ -0,0 +1,62 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <QJsonObject>
|
||||||
|
#include <QObject>
|
||||||
|
#include <QString>
|
||||||
|
#include <QUrl>
|
||||||
|
|
||||||
|
class Community : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
public:
|
||||||
|
void parseProfile(const QJsonObject &profile);
|
||||||
|
void parseRooms(const QJsonObject &rooms);
|
||||||
|
|
||||||
|
inline QUrl getAvatar() const;
|
||||||
|
inline QString getName() const;
|
||||||
|
inline QString getShortDescription() const;
|
||||||
|
inline QString getLongDescription() const;
|
||||||
|
inline const QList<QString> getRoomList() const;
|
||||||
|
|
||||||
|
signals:
|
||||||
|
void roomsChanged(QList<QString> &rooms);
|
||||||
|
|
||||||
|
private:
|
||||||
|
QUrl avatar_;
|
||||||
|
QString name_;
|
||||||
|
QString short_description_;
|
||||||
|
QString long_description_;
|
||||||
|
|
||||||
|
QList<QString> rooms_;
|
||||||
|
};
|
||||||
|
|
||||||
|
inline QUrl
|
||||||
|
Community::getAvatar() const
|
||||||
|
{
|
||||||
|
return avatar_;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline QString
|
||||||
|
Community::getName() const
|
||||||
|
{
|
||||||
|
return name_;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline QString
|
||||||
|
Community::getShortDescription() const
|
||||||
|
{
|
||||||
|
return short_description_;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline QString
|
||||||
|
Community::getLongDescription() const
|
||||||
|
{
|
||||||
|
return long_description_;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline const QList<QString>
|
||||||
|
Community::getRoomList() const
|
||||||
|
{
|
||||||
|
return rooms_;
|
||||||
|
}
|
|
@ -48,6 +48,9 @@ public:
|
||||||
void versions() noexcept;
|
void versions() noexcept;
|
||||||
void fetchRoomAvatar(const QString &roomid, const QUrl &avatar_url);
|
void fetchRoomAvatar(const QString &roomid, const QUrl &avatar_url);
|
||||||
void fetchUserAvatar(const QString &userId, const QUrl &avatarUrl);
|
void fetchUserAvatar(const QString &userId, const QUrl &avatarUrl);
|
||||||
|
void fetchCommunityAvatar(const QString &communityId, const QUrl &avatarUrl);
|
||||||
|
void fetchCommunityProfile(const QString &communityId);
|
||||||
|
void fetchCommunityRooms(const QString &communityId);
|
||||||
void fetchOwnAvatar(const QUrl &avatar_url);
|
void fetchOwnAvatar(const QUrl &avatar_url);
|
||||||
void downloadImage(const QString &event_id, const QUrl &url);
|
void downloadImage(const QString &event_id, const QUrl &url);
|
||||||
void downloadFile(const QString &event_id, const QUrl &url);
|
void downloadFile(const QString &event_id, const QUrl &url);
|
||||||
|
@ -71,6 +74,7 @@ public:
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void getOwnProfile() noexcept;
|
void getOwnProfile() noexcept;
|
||||||
|
void getOwnCommunities() noexcept;
|
||||||
void logout() noexcept;
|
void logout() noexcept;
|
||||||
|
|
||||||
void setServer(const QString &server)
|
void setServer(const QString &server)
|
||||||
|
@ -103,12 +107,16 @@ signals:
|
||||||
const QString &url,
|
const QString &url,
|
||||||
const QByteArray &data);
|
const QByteArray &data);
|
||||||
void userAvatarRetrieved(const QString &userId, const QImage &img);
|
void userAvatarRetrieved(const QString &userId, const QImage &img);
|
||||||
|
void communityAvatarRetrieved(const QString &communityId, const QPixmap &img);
|
||||||
|
void communityProfileRetrieved(const QString &communityId, const QJsonObject &profile);
|
||||||
|
void communityRoomsRetrieved(const QString &communityId, const QJsonObject &rooms);
|
||||||
void ownAvatarRetrieved(const QPixmap &img);
|
void ownAvatarRetrieved(const QPixmap &img);
|
||||||
void imageDownloaded(const QString &event_id, const QPixmap &img);
|
void imageDownloaded(const QString &event_id, const QPixmap &img);
|
||||||
void fileDownloaded(const QString &event_id, const QByteArray &data);
|
void fileDownloaded(const QString &event_id, const QByteArray &data);
|
||||||
|
|
||||||
// Returned profile data for the user's account.
|
// Returned profile data for the user's account.
|
||||||
void getOwnProfileResponse(const QUrl &avatar_url, const QString &display_name);
|
void getOwnProfileResponse(const QUrl &avatar_url, const QString &display_name);
|
||||||
|
void getOwnCommunitiesResponse(const QList<QString> &own_communities);
|
||||||
void initialSyncCompleted(const mtx::responses::Sync &response);
|
void initialSyncCompleted(const mtx::responses::Sync &response);
|
||||||
void initialSyncFailed(const QString &msg);
|
void initialSyncFailed(const QString &msg);
|
||||||
void syncCompleted(const mtx::responses::Sync &response);
|
void syncCompleted(const mtx::responses::Sync &response);
|
||||||
|
|
|
@ -73,9 +73,10 @@ public:
|
||||||
void clearUnreadMessageCount();
|
void clearUnreadMessageCount();
|
||||||
void setState(const RoomState &state);
|
void setState(const RoomState &state);
|
||||||
|
|
||||||
bool isPressed() const { return isPressed_; }
|
QString roomId();
|
||||||
RoomState state() const { return state_; }
|
bool isPressed() const { return isPressed_; };
|
||||||
int unreadMessageCount() const { return unreadMsgCount_; }
|
RoomState state() const { return state_; };
|
||||||
|
int unreadMessageCount() const { return unreadMsgCount_; };
|
||||||
|
|
||||||
void setAvatar(const QImage &avatar_image);
|
void setAvatar(const QImage &avatar_image);
|
||||||
void setDescriptionMessage(const DescInfo &info);
|
void setDescriptionMessage(const DescInfo &info);
|
||||||
|
@ -182,3 +183,9 @@ private:
|
||||||
QRectF acceptBtnRegion_;
|
QRectF acceptBtnRegion_;
|
||||||
QRectF declineBtnRegion_;
|
QRectF declineBtnRegion_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
inline QString
|
||||||
|
RoomInfoListItem::roomId()
|
||||||
|
{
|
||||||
|
return roomId_;
|
||||||
|
}
|
||||||
|
|
|
@ -64,6 +64,8 @@ public:
|
||||||
const QString &room_id);
|
const QString &room_id);
|
||||||
void addInvitedRoom(const QString &room_id, const mtx::responses::InvitedRoom &room);
|
void addInvitedRoom(const QString &room_id, const mtx::responses::InvitedRoom &room);
|
||||||
void removeRoom(const QString &room_id, bool reset);
|
void removeRoom(const QString &room_id, bool reset);
|
||||||
|
void setFilterRooms(bool filterRooms);
|
||||||
|
void setRoomFilter(QList<QString> room_ids);
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void roomChanged(const QString &room_id);
|
void roomChanged(const QString &room_id);
|
||||||
|
@ -105,6 +107,10 @@ private:
|
||||||
QSharedPointer<dialogs::LeaveRoom> leaveRoomDialog_;
|
QSharedPointer<dialogs::LeaveRoom> leaveRoomDialog_;
|
||||||
|
|
||||||
QMap<QString, QSharedPointer<RoomInfoListItem>> rooms_;
|
QMap<QString, QSharedPointer<RoomInfoListItem>> rooms_;
|
||||||
|
QString selectedRoom_;
|
||||||
|
|
||||||
|
bool filterRooms_ = false;
|
||||||
|
QList<QString> roomFilter_ = QList<QString>(); // which rooms to include in the room list
|
||||||
|
|
||||||
QSharedPointer<MatrixClient> client_;
|
QSharedPointer<MatrixClient> client_;
|
||||||
QSharedPointer<Cache> cache_;
|
QSharedPointer<Cache> cache_;
|
||||||
|
|
|
@ -13,8 +13,9 @@ enum class AvatarType
|
||||||
};
|
};
|
||||||
|
|
||||||
namespace sidebar {
|
namespace sidebar {
|
||||||
static const int SmallSize = 60;
|
static const int SmallSize = 60;
|
||||||
static const int NormalSize = 300;
|
static const int NormalSize = 300;
|
||||||
|
static const int CommunitiesSidebarSize = 64;
|
||||||
}
|
}
|
||||||
// Default font size.
|
// Default font size.
|
||||||
const int FontSize = 16;
|
const int FontSize = 16;
|
||||||
|
|
BIN
resources/icons/ui/world.png
Normal file
BIN
resources/icons/ui/world.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 2.8 KiB |
98
resources/icons/ui/world.svg
Normal file
98
resources/icons/ui/world.svg
Normal file
|
@ -0,0 +1,98 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||||
|
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||||
|
|
||||||
|
<svg
|
||||||
|
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||||
|
xmlns:cc="http://creativecommons.org/ns#"
|
||||||
|
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||||
|
xmlns:svg="http://www.w3.org/2000/svg"
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||||
|
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||||
|
width="48px"
|
||||||
|
height="48px"
|
||||||
|
id="svg3304"
|
||||||
|
sodipodi:version="0.32"
|
||||||
|
inkscape:version="0.92.2 (5c3e80d, 2017-08-06)"
|
||||||
|
sodipodi:docname="world.svg"
|
||||||
|
version="1.1"
|
||||||
|
inkscape:export-filename="/home/max/Program/nheko/resources/icons/world.png"
|
||||||
|
inkscape:export-xdpi="256"
|
||||||
|
inkscape:export-ydpi="256">
|
||||||
|
<defs
|
||||||
|
id="defs3306" />
|
||||||
|
<sodipodi:namedview
|
||||||
|
id="base"
|
||||||
|
pagecolor="#ffffff"
|
||||||
|
bordercolor="#666666"
|
||||||
|
borderopacity="1.0"
|
||||||
|
inkscape:pageopacity="0.0"
|
||||||
|
inkscape:pageshadow="2"
|
||||||
|
inkscape:zoom="7.9375"
|
||||||
|
inkscape:cx="11.531663"
|
||||||
|
inkscape:cy="15.491127"
|
||||||
|
inkscape:current-layer="layer1"
|
||||||
|
showgrid="true"
|
||||||
|
inkscape:grid-bbox="true"
|
||||||
|
inkscape:document-units="px"
|
||||||
|
inkscape:grid-points="true"
|
||||||
|
showguides="true"
|
||||||
|
inkscape:guide-bbox="true"
|
||||||
|
inkscape:window-width="1280"
|
||||||
|
inkscape:window-height="704"
|
||||||
|
inkscape:window-x="0"
|
||||||
|
inkscape:window-y="27"
|
||||||
|
inkscape:window-maximized="0" />
|
||||||
|
<metadata
|
||||||
|
id="metadata3309">
|
||||||
|
<rdf:RDF>
|
||||||
|
<cc:Work
|
||||||
|
rdf:about="">
|
||||||
|
<dc:format>image/svg+xml</dc:format>
|
||||||
|
<dc:type
|
||||||
|
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||||
|
<dc:title></dc:title>
|
||||||
|
</cc:Work>
|
||||||
|
</rdf:RDF>
|
||||||
|
</metadata>
|
||||||
|
<g
|
||||||
|
id="layer1"
|
||||||
|
inkscape:label="Layer 1"
|
||||||
|
inkscape:groupmode="layer">
|
||||||
|
<path
|
||||||
|
style="fill:none;fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:2;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||||
|
d="m 12.998425,32.054724 c 6.286614,-2.35748 15.716536,-2.35748 22.00315,0"
|
||||||
|
id="path5512"
|
||||||
|
sodipodi:nodetypes="cc"
|
||||||
|
inkscape:connector-curvature="0" />
|
||||||
|
<path
|
||||||
|
style="fill:none;fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||||
|
d="M 11.402021,24 H 36.597979"
|
||||||
|
id="path5516"
|
||||||
|
inkscape:connector-curvature="0" />
|
||||||
|
<path
|
||||||
|
style="fill:none;fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:2;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||||
|
d="m 20.856693,11.074078 c -3.929134,8.210961 -3.929134,18.426709 0,26.284977"
|
||||||
|
id="path5520"
|
||||||
|
sodipodi:nodetypes="cc"
|
||||||
|
inkscape:connector-curvature="0" />
|
||||||
|
<path
|
||||||
|
sodipodi:nodetypes="cc"
|
||||||
|
id="path6250"
|
||||||
|
d="m 12.998425,15.945276 c 6.286614,2.35748 15.716536,2.35748 22.00315,0"
|
||||||
|
style="fill:none;fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:2;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||||
|
inkscape:connector-curvature="0" />
|
||||||
|
<path
|
||||||
|
sodipodi:nodetypes="cc"
|
||||||
|
id="path9156"
|
||||||
|
d="m 27.143307,11.074078 c 3.929134,8.210961 3.929134,18.426709 0,26.284977"
|
||||||
|
style="fill:none;fill-opacity:0.75;fill-rule:evenodd;stroke:#000000;stroke-width:2;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||||
|
inkscape:connector-curvature="0" />
|
||||||
|
<circle
|
||||||
|
style="fill:none;fill-opacity:0.67634858;stroke:#000000;stroke-width:2;stroke-linecap:square;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
|
||||||
|
id="path1767"
|
||||||
|
cx="24"
|
||||||
|
cy="24"
|
||||||
|
r="13.609846" />
|
||||||
|
</g>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 3.9 KiB |
|
@ -22,6 +22,7 @@
|
||||||
<file>icons/ui/paper-clip-outline@2x.png</file>
|
<file>icons/ui/paper-clip-outline@2x.png</file>
|
||||||
<file>icons/ui/angle-pointing-to-left.png</file>
|
<file>icons/ui/angle-pointing-to-left.png</file>
|
||||||
<file>icons/ui/angle-pointing-to-left@2x.png</file>
|
<file>icons/ui/angle-pointing-to-left@2x.png</file>
|
||||||
|
<file>icons/ui/world.png</file>
|
||||||
<file>icons/ui/angle-arrow-down.png</file>
|
<file>icons/ui/angle-arrow-down.png</file>
|
||||||
<file>icons/ui/angle-arrow-down@2x.png</file>
|
<file>icons/ui/angle-arrow-down@2x.png</file>
|
||||||
<file>icons/ui/arrow-pointing-down.png</file>
|
<file>icons/ui/arrow-pointing-down.png</file>
|
||||||
|
|
|
@ -17,6 +17,10 @@ RoomList > * {
|
||||||
background-color: #383c4a;
|
background-color: #383c4a;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CommunitiesList,
|
||||||
|
CommunitiesList > * {
|
||||||
|
background-color: #383c4a;
|
||||||
|
}
|
||||||
FlatButton {
|
FlatButton {
|
||||||
qproperty-foregroundColor: #caccd1;
|
qproperty-foregroundColor: #caccd1;
|
||||||
qproperty-backgroundColor: #333;
|
qproperty-backgroundColor: #333;
|
||||||
|
@ -54,6 +58,12 @@ RoomInfoListItem {
|
||||||
qproperty-btnTextColor: white;
|
qproperty-btnTextColor: white;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CommunitiesListItem {
|
||||||
|
qproperty-highlightedBackgroundColor: #5294e2;
|
||||||
|
qproperty-hoverBackgroundColor: #39679e;
|
||||||
|
qproperty-backgroundColor: #383c4a;
|
||||||
|
}
|
||||||
|
|
||||||
LoadingIndicator {
|
LoadingIndicator {
|
||||||
qproperty-color: #caccd1;
|
qproperty-color: #caccd1;
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,6 +17,11 @@ RoomList > * {
|
||||||
background-color: white;
|
background-color: white;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CommunitiesList,
|
||||||
|
CommunitiesList > * {
|
||||||
|
background-color: white;
|
||||||
|
}
|
||||||
|
|
||||||
FlatButton {
|
FlatButton {
|
||||||
qproperty-foregroundColor: #333;
|
qproperty-foregroundColor: #333;
|
||||||
}
|
}
|
||||||
|
@ -52,6 +57,12 @@ RoomInfoListItem {
|
||||||
qproperty-btnTextColor: #333;
|
qproperty-btnTextColor: #333;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CommunitiesListItem {
|
||||||
|
qproperty-highlightedBackgroundColor: #38A3D8;
|
||||||
|
qproperty-hoverBackgroundColor: rgba(200, 200, 200, 128);
|
||||||
|
qproperty-backgroundColor: white;
|
||||||
|
}
|
||||||
|
|
||||||
#ChatPageLoadSpinner {
|
#ChatPageLoadSpinner {
|
||||||
qproperty-color: #acc7dc;
|
qproperty-color: #acc7dc;
|
||||||
}
|
}
|
||||||
|
|
|
@ -60,6 +60,12 @@ RoomInfoListItem {
|
||||||
qproperty-btnTextColor: palette(text);
|
qproperty-btnTextColor: palette(text);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CommunitiesListItem {
|
||||||
|
qproperty-highlightedBackgroundColor: palette(highlight);
|
||||||
|
qproperty-hoverBackgroundColor: palette(mid);
|
||||||
|
qproperty-backgroundColor: palette(window);
|
||||||
|
}
|
||||||
|
|
||||||
LoadingIndicator {
|
LoadingIndicator {
|
||||||
qproperty-color: palette(highlight);
|
qproperty-color: palette(highlight);
|
||||||
}
|
}
|
||||||
|
|
|
@ -60,6 +60,17 @@ ChatPage::ChatPage(QSharedPointer<MatrixClient> client,
|
||||||
topLayout_->setSpacing(0);
|
topLayout_->setSpacing(0);
|
||||||
topLayout_->setMargin(0);
|
topLayout_->setMargin(0);
|
||||||
|
|
||||||
|
communitiesSideBar_ = new QWidget(this);
|
||||||
|
communitiesSideBar_->setFixedWidth(ui::sidebar::CommunitiesSidebarSize);
|
||||||
|
communitiesSideBarLayout_ = new QVBoxLayout(communitiesSideBar_);
|
||||||
|
communitiesSideBarLayout_->setSpacing(0);
|
||||||
|
communitiesSideBarLayout_->setMargin(0);
|
||||||
|
|
||||||
|
communitiesList_ = new CommunitiesList(client, this);
|
||||||
|
communitiesSideBarLayout_->addWidget(communitiesList_);
|
||||||
|
// communitiesSideBarLayout_->addStretch(1);
|
||||||
|
topLayout_->addWidget(communitiesSideBar_);
|
||||||
|
|
||||||
auto splitter = new Splitter(this);
|
auto splitter = new Splitter(this);
|
||||||
splitter->setHandleWidth(0);
|
splitter->setHandleWidth(0);
|
||||||
|
|
||||||
|
@ -72,7 +83,18 @@ ChatPage::ChatPage(QSharedPointer<MatrixClient> client,
|
||||||
sideBarLayout_->setSpacing(0);
|
sideBarLayout_->setSpacing(0);
|
||||||
sideBarLayout_->setMargin(0);
|
sideBarLayout_->setMargin(0);
|
||||||
|
|
||||||
sidebarActions_ = new SideBarActions(this);
|
sideBarTopLayout_ = new QVBoxLayout();
|
||||||
|
sideBarTopLayout_->setSpacing(0);
|
||||||
|
sideBarTopLayout_->setMargin(0);
|
||||||
|
sideBarMainLayout_ = new QVBoxLayout();
|
||||||
|
sideBarMainLayout_->setSpacing(0);
|
||||||
|
sideBarMainLayout_->setMargin(0);
|
||||||
|
|
||||||
|
sideBarLayout_->addLayout(sideBarTopLayout_);
|
||||||
|
sideBarLayout_->addLayout(sideBarMainLayout_);
|
||||||
|
|
||||||
|
sideBarTopWidget_ = new QWidget(sideBar_);
|
||||||
|
sidebarActions_ = new SideBarActions(this);
|
||||||
connect(
|
connect(
|
||||||
sidebarActions_, &SideBarActions::showSettings, this, &ChatPage::showUserSettingsPage);
|
sidebarActions_, &SideBarActions::showSettings, this, &ChatPage::showUserSettingsPage);
|
||||||
connect(
|
connect(
|
||||||
|
@ -87,6 +109,10 @@ ChatPage::ChatPage(QSharedPointer<MatrixClient> client,
|
||||||
sideBarLayout_->addWidget(room_list_);
|
sideBarLayout_->addWidget(room_list_);
|
||||||
sideBarLayout_->addWidget(sidebarActions_);
|
sideBarLayout_->addWidget(sidebarActions_);
|
||||||
|
|
||||||
|
sideBarTopWidgetLayout_ = new QVBoxLayout(sideBarTopWidget_);
|
||||||
|
sideBarTopWidgetLayout_->setSpacing(0);
|
||||||
|
sideBarTopWidgetLayout_->setMargin(0);
|
||||||
|
|
||||||
// Content
|
// Content
|
||||||
content_ = new QFrame(this);
|
content_ = new QFrame(this);
|
||||||
content_->setObjectName("mainContent");
|
content_->setObjectName("mainContent");
|
||||||
|
@ -274,6 +300,32 @@ ChatPage::ChatPage(QSharedPointer<MatrixClient> client,
|
||||||
&MatrixClient::getOwnProfileResponse,
|
&MatrixClient::getOwnProfileResponse,
|
||||||
this,
|
this,
|
||||||
&ChatPage::updateOwnProfileInfo);
|
&ChatPage::updateOwnProfileInfo);
|
||||||
|
connect(client_.data(),
|
||||||
|
SIGNAL(getOwnCommunitiesResponse(QList<QString>)),
|
||||||
|
this,
|
||||||
|
SLOT(updateOwnCommunitiesInfo(QList<QString>)));
|
||||||
|
connect(client_.data(),
|
||||||
|
&MatrixClient::communityProfileRetrieved,
|
||||||
|
this,
|
||||||
|
[=](QString communityId, QJsonObject profile) {
|
||||||
|
communityManager_[communityId]->parseProfile(profile);
|
||||||
|
});
|
||||||
|
connect(client_.data(),
|
||||||
|
&MatrixClient::communityRoomsRetrieved,
|
||||||
|
this,
|
||||||
|
[=](QString communityId, QJsonObject rooms) {
|
||||||
|
communityManager_[communityId]->parseRooms(rooms);
|
||||||
|
|
||||||
|
if (communityId == current_community_) {
|
||||||
|
if (communityId == "world") {
|
||||||
|
room_list_->setFilterRooms(false);
|
||||||
|
} else {
|
||||||
|
room_list_->setRoomFilter(
|
||||||
|
communityManager_[communityId]->getRoomList());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
connect(client_.data(), &MatrixClient::ownAvatarRetrieved, this, &ChatPage::setOwnAvatar);
|
connect(client_.data(), &MatrixClient::ownAvatarRetrieved, this, &ChatPage::setOwnAvatar);
|
||||||
connect(client_.data(), &MatrixClient::joinedRoom, this, [=](const QString &room_id) {
|
connect(client_.data(), &MatrixClient::joinedRoom, this, [=](const QString &room_id) {
|
||||||
emit showNotification("You joined the room.");
|
emit showNotification("You joined the room.");
|
||||||
|
@ -304,6 +356,19 @@ ChatPage::ChatPage(QSharedPointer<MatrixClient> client,
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
connect(communitiesList_,
|
||||||
|
&CommunitiesList::communityChanged,
|
||||||
|
this,
|
||||||
|
[=](const QString &communityId) {
|
||||||
|
current_community_ = communityId;
|
||||||
|
if (communityId == "world") {
|
||||||
|
room_list_->setFilterRooms(false);
|
||||||
|
} else {
|
||||||
|
room_list_->setRoomFilter(
|
||||||
|
communityManager_[communityId]->getRoomList());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
AvatarProvider::init(client);
|
AvatarProvider::init(client);
|
||||||
|
|
||||||
instance_ = this;
|
instance_ = this;
|
||||||
|
@ -359,6 +424,7 @@ ChatPage::bootstrap(QString userid, QString homeserver, QString token)
|
||||||
client_->setServer(homeserver);
|
client_->setServer(homeserver);
|
||||||
client_->setAccessToken(token);
|
client_->setAccessToken(token);
|
||||||
client_->getOwnProfile();
|
client_->getOwnProfile();
|
||||||
|
client_->getOwnCommunities();
|
||||||
|
|
||||||
cache_ = QSharedPointer<Cache>(new Cache(userid));
|
cache_ = QSharedPointer<Cache>(new Cache(userid));
|
||||||
room_list_->setCache(cache_);
|
room_list_->setCache(cache_);
|
||||||
|
@ -500,6 +566,18 @@ ChatPage::updateOwnProfileInfo(const QUrl &avatar_url, const QString &display_na
|
||||||
client_->fetchOwnAvatar(avatar_url);
|
client_->fetchOwnAvatar(avatar_url);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
ChatPage::updateOwnCommunitiesInfo(const QList<QString> &own_communities)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < own_communities.size(); i++) {
|
||||||
|
QSharedPointer<Community> community = QSharedPointer<Community>(new Community());
|
||||||
|
|
||||||
|
communityManager_[own_communities[i]] = community;
|
||||||
|
}
|
||||||
|
|
||||||
|
communitiesList_->setCommunities(communityManager_);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
ChatPage::changeTopRoomInfo(const QString &room_id)
|
ChatPage::changeTopRoomInfo(const QString &room_id)
|
||||||
{
|
{
|
||||||
|
|
150
src/CommunitiesList.cc
Normal file
150
src/CommunitiesList.cc
Normal file
|
@ -0,0 +1,150 @@
|
||||||
|
#include "CommunitiesList.h"
|
||||||
|
|
||||||
|
#include <QLabel>
|
||||||
|
|
||||||
|
CommunitiesList::CommunitiesList(QSharedPointer<MatrixClient> client, QWidget *parent)
|
||||||
|
: QWidget(parent)
|
||||||
|
, client_(client)
|
||||||
|
{
|
||||||
|
QSizePolicy sizePolicy(QSizePolicy::Fixed, QSizePolicy::Expanding);
|
||||||
|
sizePolicy.setHorizontalStretch(0);
|
||||||
|
sizePolicy.setVerticalStretch(1);
|
||||||
|
setSizePolicy(sizePolicy);
|
||||||
|
|
||||||
|
setStyleSheet("border-style: none;");
|
||||||
|
|
||||||
|
topLayout_ = new QVBoxLayout(this);
|
||||||
|
topLayout_->setSpacing(0);
|
||||||
|
topLayout_->setMargin(0);
|
||||||
|
|
||||||
|
setFixedWidth(ui::sidebar::CommunitiesSidebarSize);
|
||||||
|
|
||||||
|
scrollArea_ = new QScrollArea(this);
|
||||||
|
scrollArea_->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
|
||||||
|
scrollArea_->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
|
||||||
|
scrollArea_->setSizeAdjustPolicy(QAbstractScrollArea::AdjustToContents);
|
||||||
|
scrollArea_->setWidgetResizable(true);
|
||||||
|
scrollArea_->setAlignment(Qt::AlignLeading | Qt::AlignTop | Qt::AlignVCenter);
|
||||||
|
|
||||||
|
scrollAreaContents_ = new QWidget();
|
||||||
|
|
||||||
|
contentsLayout_ = new QVBoxLayout(scrollAreaContents_);
|
||||||
|
contentsLayout_->setSpacing(0);
|
||||||
|
contentsLayout_->setMargin(0);
|
||||||
|
|
||||||
|
WorldCommunityListItem *world_list_item = new WorldCommunityListItem();
|
||||||
|
contentsLayout_->addWidget(world_list_item);
|
||||||
|
communities_.insert("world", QSharedPointer<CommunitiesListItem>(world_list_item));
|
||||||
|
connect(world_list_item,
|
||||||
|
&WorldCommunityListItem::clicked,
|
||||||
|
this,
|
||||||
|
&CommunitiesList::highlightSelectedCommunity);
|
||||||
|
contentsLayout_->addStretch(1);
|
||||||
|
|
||||||
|
scrollArea_->setWidget(scrollAreaContents_);
|
||||||
|
topLayout_->addWidget(scrollArea_);
|
||||||
|
|
||||||
|
connect(client_.data(),
|
||||||
|
&MatrixClient::communityProfileRetrieved,
|
||||||
|
this,
|
||||||
|
[=](QString communityId, QJsonObject profile) {
|
||||||
|
client_->fetchCommunityAvatar(communityId,
|
||||||
|
QUrl(profile["avatar_url"].toString()));
|
||||||
|
});
|
||||||
|
connect(client_.data(),
|
||||||
|
SIGNAL(communityAvatarRetrieved(const QString &, const QPixmap &)),
|
||||||
|
this,
|
||||||
|
SLOT(updateCommunityAvatar(const QString &, const QPixmap &)));
|
||||||
|
}
|
||||||
|
|
||||||
|
CommunitiesList::~CommunitiesList() {}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesList::setCommunities(const QMap<QString, QSharedPointer<Community>> &communities)
|
||||||
|
{
|
||||||
|
communities_.clear();
|
||||||
|
|
||||||
|
// TODO: still not sure how to handle the "world" special-case
|
||||||
|
WorldCommunityListItem *world_list_item = new WorldCommunityListItem();
|
||||||
|
communities_.insert("world", QSharedPointer<CommunitiesListItem>(world_list_item));
|
||||||
|
connect(world_list_item,
|
||||||
|
&WorldCommunityListItem::clicked,
|
||||||
|
this,
|
||||||
|
&CommunitiesList::highlightSelectedCommunity);
|
||||||
|
contentsLayout_->insertWidget(0, world_list_item);
|
||||||
|
|
||||||
|
for (auto it = communities.constBegin(); it != communities.constEnd(); it++) {
|
||||||
|
const auto community_id = it.key();
|
||||||
|
const auto community = it.value();
|
||||||
|
|
||||||
|
addCommunity(community, community_id);
|
||||||
|
|
||||||
|
client_->fetchCommunityProfile(community_id);
|
||||||
|
client_->fetchCommunityRooms(community_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
world_list_item->setPressedState(true);
|
||||||
|
emit communityChanged("world");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesList::clear()
|
||||||
|
{
|
||||||
|
communities_.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesList::addCommunity(QSharedPointer<Community> community, const QString &community_id)
|
||||||
|
{
|
||||||
|
CommunitiesListItem *list_item =
|
||||||
|
new CommunitiesListItem(community, community_id, scrollArea_);
|
||||||
|
|
||||||
|
communities_.insert(community_id, QSharedPointer<CommunitiesListItem>(list_item));
|
||||||
|
|
||||||
|
client_->fetchCommunityAvatar(community_id, community->getAvatar());
|
||||||
|
|
||||||
|
contentsLayout_->insertWidget(contentsLayout_->count() - 1, list_item);
|
||||||
|
|
||||||
|
connect(list_item,
|
||||||
|
&CommunitiesListItem::clicked,
|
||||||
|
this,
|
||||||
|
&CommunitiesList::highlightSelectedCommunity);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesList::removeCommunity(const QString &community_id)
|
||||||
|
{
|
||||||
|
communities_.remove(community_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesList::updateCommunityAvatar(const QString &community_id, const QPixmap &img)
|
||||||
|
{
|
||||||
|
if (!communities_.contains(community_id)) {
|
||||||
|
qWarning() << "Avatar update on nonexistent community" << community_id;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
communities_.value(community_id)->setAvatar(img.toImage());
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesList::highlightSelectedCommunity(const QString &community_id)
|
||||||
|
{
|
||||||
|
emit communityChanged(community_id);
|
||||||
|
|
||||||
|
if (!communities_.contains(community_id)) {
|
||||||
|
qDebug() << "CommunitiesList: clicked unknown community";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (auto it = communities_.constBegin(); it != communities_.constEnd(); it++) {
|
||||||
|
if (it.key() != community_id) {
|
||||||
|
it.value()->setPressedState(false);
|
||||||
|
} else {
|
||||||
|
it.value()->setPressedState(true);
|
||||||
|
scrollArea_->ensureWidgetVisible(
|
||||||
|
qobject_cast<QWidget *>(it.value().data()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
200
src/CommunitiesListItem.cc
Normal file
200
src/CommunitiesListItem.cc
Normal file
|
@ -0,0 +1,200 @@
|
||||||
|
#include "CommunitiesListItem.h"
|
||||||
|
|
||||||
|
CommunitiesListItem::CommunitiesListItem(QSharedPointer<Community> community,
|
||||||
|
QString community_id,
|
||||||
|
QWidget *parent)
|
||||||
|
: QWidget(parent)
|
||||||
|
, community_(community)
|
||||||
|
, communityId_(community_id)
|
||||||
|
{
|
||||||
|
// menu_ = new Menu(this);
|
||||||
|
setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
|
||||||
|
setFixedHeight(ui::sidebar::CommunitiesSidebarSize);
|
||||||
|
setFixedWidth(ui::sidebar::CommunitiesSidebarSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
CommunitiesListItem::~CommunitiesListItem() {}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesListItem::setCommunity(QSharedPointer<Community> community)
|
||||||
|
{
|
||||||
|
community_ = community;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesListItem::setPressedState(bool state)
|
||||||
|
{
|
||||||
|
if (isPressed_ != state) {
|
||||||
|
isPressed_ = state;
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesListItem::mousePressEvent(QMouseEvent *event)
|
||||||
|
{
|
||||||
|
if (event->buttons() == Qt::RightButton) {
|
||||||
|
QWidget::mousePressEvent(event);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
emit clicked(communityId_);
|
||||||
|
|
||||||
|
setPressedState(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesListItem::paintEvent(QPaintEvent *event)
|
||||||
|
{
|
||||||
|
Q_UNUSED(event);
|
||||||
|
|
||||||
|
QPainter p(this);
|
||||||
|
p.setRenderHint(QPainter::TextAntialiasing);
|
||||||
|
p.setRenderHint(QPainter::SmoothPixmapTransform);
|
||||||
|
p.setRenderHint(QPainter::Antialiasing);
|
||||||
|
|
||||||
|
if (isPressed_)
|
||||||
|
p.fillRect(rect(), highlightedBackgroundColor_);
|
||||||
|
else if (underMouse())
|
||||||
|
p.fillRect(rect(), hoverBackgroundColor_);
|
||||||
|
else
|
||||||
|
p.fillRect(rect(), backgroundColor_);
|
||||||
|
|
||||||
|
QFont font;
|
||||||
|
font.setPixelSize(conf::fontSize);
|
||||||
|
|
||||||
|
p.setPen(QColor("#333"));
|
||||||
|
|
||||||
|
QRect avatarRegion((width() - IconSize) / 2, (height() - IconSize) / 2, IconSize, IconSize);
|
||||||
|
|
||||||
|
font.setBold(false);
|
||||||
|
p.setPen(Qt::NoPen);
|
||||||
|
|
||||||
|
// We using the first letter of room's name.
|
||||||
|
if (communityAvatar_.isNull()) {
|
||||||
|
QBrush brush;
|
||||||
|
brush.setStyle(Qt::SolidPattern);
|
||||||
|
brush.setColor("#eee");
|
||||||
|
|
||||||
|
p.setPen(Qt::NoPen);
|
||||||
|
p.setBrush(brush);
|
||||||
|
|
||||||
|
p.drawEllipse(avatarRegion.center(), IconSize / 2, IconSize / 2);
|
||||||
|
|
||||||
|
font.setPixelSize(conf::roomlist::fonts::bubble);
|
||||||
|
p.setFont(font);
|
||||||
|
p.setPen(QColor("#000"));
|
||||||
|
p.setBrush(Qt::NoBrush);
|
||||||
|
p.drawText(
|
||||||
|
avatarRegion.translated(0, -1), Qt::AlignCenter, QChar(community_->getName()[0]));
|
||||||
|
} else {
|
||||||
|
p.save();
|
||||||
|
|
||||||
|
QPainterPath path;
|
||||||
|
path.addEllipse(
|
||||||
|
(width() - IconSize) / 2, (height() - IconSize) / 2, IconSize, IconSize);
|
||||||
|
p.setClipPath(path);
|
||||||
|
|
||||||
|
p.drawPixmap(avatarRegion, communityAvatar_);
|
||||||
|
p.restore();
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: Discord-style community ping counts?
|
||||||
|
/*if (unreadMsgCount_ > 0) {
|
||||||
|
QColor textColor("white");
|
||||||
|
QColor backgroundColor("#38A3D8");
|
||||||
|
|
||||||
|
QBrush brush;
|
||||||
|
brush.setStyle(Qt::SolidPattern);
|
||||||
|
brush.setColor(backgroundColor);
|
||||||
|
|
||||||
|
if (isPressed_)
|
||||||
|
brush.setColor(textColor);
|
||||||
|
|
||||||
|
QFont unreadCountFont;
|
||||||
|
unreadCountFont.setPixelSize(conf::roomlist::fonts::badge);
|
||||||
|
unreadCountFont.setBold(true);
|
||||||
|
|
||||||
|
p.setBrush(brush);
|
||||||
|
p.setPen(Qt::NoPen);
|
||||||
|
p.setFont(unreadCountFont);
|
||||||
|
|
||||||
|
int diameter = 20;
|
||||||
|
|
||||||
|
QRectF r(
|
||||||
|
width() - diameter - 5, height() - diameter - 5, diameter, diameter);
|
||||||
|
|
||||||
|
p.setPen(Qt::NoPen);
|
||||||
|
p.drawEllipse(r);
|
||||||
|
|
||||||
|
p.setPen(QPen(textColor));
|
||||||
|
|
||||||
|
if (isPressed_)
|
||||||
|
p.setPen(QPen(backgroundColor));
|
||||||
|
|
||||||
|
p.setBrush(Qt::NoBrush);
|
||||||
|
p.drawText(
|
||||||
|
r.translated(0, -0.5), Qt::AlignCenter, QString::number(unreadMsgCount_));
|
||||||
|
}*/
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CommunitiesListItem::contextMenuEvent(QContextMenuEvent *event)
|
||||||
|
{
|
||||||
|
Q_UNUSED(event);
|
||||||
|
|
||||||
|
// menu_->popup(event->globalPos());
|
||||||
|
}
|
||||||
|
|
||||||
|
WorldCommunityListItem::WorldCommunityListItem(QWidget *parent)
|
||||||
|
: CommunitiesListItem(QSharedPointer<Community>(), "", parent)
|
||||||
|
{}
|
||||||
|
|
||||||
|
WorldCommunityListItem::~WorldCommunityListItem() {}
|
||||||
|
|
||||||
|
void
|
||||||
|
WorldCommunityListItem::mousePressEvent(QMouseEvent *event)
|
||||||
|
{
|
||||||
|
if (event->buttons() == Qt::RightButton) {
|
||||||
|
QWidget::mousePressEvent(event);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
emit CommunitiesListItem::clicked("world");
|
||||||
|
|
||||||
|
setPressedState(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
WorldCommunityListItem::paintEvent(QPaintEvent *event)
|
||||||
|
{
|
||||||
|
Q_UNUSED(event);
|
||||||
|
|
||||||
|
static QPixmap worldIcon(":/icons/icons/ui/world.png");
|
||||||
|
|
||||||
|
QPainter p(this);
|
||||||
|
p.setRenderHint(QPainter::SmoothPixmapTransform);
|
||||||
|
p.setRenderHint(QPainter::Antialiasing);
|
||||||
|
|
||||||
|
if (isPressed())
|
||||||
|
p.fillRect(rect(), highlightedBackgroundColor_);
|
||||||
|
else if (underMouse())
|
||||||
|
p.fillRect(rect(), hoverBackgroundColor_);
|
||||||
|
else
|
||||||
|
p.fillRect(rect(), backgroundColor_);
|
||||||
|
|
||||||
|
QBrush brush;
|
||||||
|
brush.setStyle(Qt::SolidPattern);
|
||||||
|
brush.setColor("#FFFFFF");
|
||||||
|
|
||||||
|
p.setPen(Qt::NoPen);
|
||||||
|
p.setBrush(brush);
|
||||||
|
|
||||||
|
QRect avatarRegion((width() - IconSize) / 2, (height() - IconSize) / 2, IconSize, IconSize);
|
||||||
|
p.drawEllipse(avatarRegion.center(), IconSize / 2, IconSize / 2);
|
||||||
|
QPainterPath path;
|
||||||
|
path.addEllipse((width() - IconSize) / 2, (height() - IconSize) / 2, IconSize, IconSize);
|
||||||
|
p.setClipPath(path);
|
||||||
|
|
||||||
|
p.drawPixmap(avatarRegion, worldIcon);
|
||||||
|
}
|
44
src/Community.cc
Normal file
44
src/Community.cc
Normal file
|
@ -0,0 +1,44 @@
|
||||||
|
#include "include/Community.h"
|
||||||
|
|
||||||
|
#include <QJsonArray>
|
||||||
|
#include <QJsonValue>
|
||||||
|
|
||||||
|
void
|
||||||
|
Community::parseProfile(const QJsonObject &profile)
|
||||||
|
{
|
||||||
|
if (profile["name"].type() == QJsonValue::Type::String) {
|
||||||
|
name_ = profile["name"].toString();
|
||||||
|
} else {
|
||||||
|
name_ = "Unnamed Community"; // TODO: what is correct here?
|
||||||
|
}
|
||||||
|
|
||||||
|
if (profile["avatar_url"].type() == QJsonValue::Type::String) {
|
||||||
|
avatar_ = QUrl(profile["avatar_url"].toString());
|
||||||
|
} else {
|
||||||
|
avatar_ = QUrl();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (profile["short_description"].type() == QJsonValue::Type::String) {
|
||||||
|
short_description_ = profile["short_description"].toString();
|
||||||
|
} else {
|
||||||
|
short_description_ = "";
|
||||||
|
}
|
||||||
|
|
||||||
|
if (profile["long_description"].type() == QJsonValue::Type::String) {
|
||||||
|
long_description_ = profile["long_description"].toString();
|
||||||
|
} else {
|
||||||
|
long_description_ = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
Community::parseRooms(const QJsonObject &rooms)
|
||||||
|
{
|
||||||
|
rooms_.clear();
|
||||||
|
|
||||||
|
for (auto i = 0; i < rooms["chunk"].toArray().size(); i++) {
|
||||||
|
rooms_.append(rooms["chunk"].toArray()[i].toObject()["room_id"].toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
emit roomsChanged(rooms_);
|
||||||
|
}
|
|
@ -112,7 +112,6 @@ MatrixClient::login(const QString &username, const QString &password) noexcept
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
MatrixClient::logout() noexcept
|
MatrixClient::logout() noexcept
|
||||||
{
|
{
|
||||||
|
@ -444,6 +443,46 @@ MatrixClient::getOwnProfile() noexcept
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MatrixClient::getOwnCommunities() noexcept
|
||||||
|
{
|
||||||
|
QUrlQuery query;
|
||||||
|
query.addQueryItem("access_token", token_);
|
||||||
|
|
||||||
|
QUrl endpoint(server_);
|
||||||
|
endpoint.setPath(clientApiUrl_ + "/joined_groups");
|
||||||
|
endpoint.setQuery(query);
|
||||||
|
|
||||||
|
QNetworkRequest request(QString(endpoint.toEncoded()));
|
||||||
|
|
||||||
|
QNetworkReply *reply = get(request);
|
||||||
|
connect(reply, &QNetworkReply::finished, this, [this, reply]() {
|
||||||
|
reply->deleteLater();
|
||||||
|
|
||||||
|
int status = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
|
||||||
|
|
||||||
|
if (status >= 400) {
|
||||||
|
qWarning() << reply->errorString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto data = reply->readAll();
|
||||||
|
auto json = QJsonDocument::fromJson(data).object();
|
||||||
|
|
||||||
|
try {
|
||||||
|
QList<QString> response;
|
||||||
|
for (auto it = json["groups"].toArray().constBegin();
|
||||||
|
it != json["groups"].toArray().constEnd();
|
||||||
|
it++) {
|
||||||
|
response.append(it->toString());
|
||||||
|
}
|
||||||
|
emit getOwnCommunitiesResponse(response);
|
||||||
|
} catch (DeserializationException &e) {
|
||||||
|
qWarning() << "Own communities:" << e.what();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
MatrixClient::fetchRoomAvatar(const QString &roomid, const QUrl &avatar_url)
|
MatrixClient::fetchRoomAvatar(const QString &roomid, const QUrl &avatar_url)
|
||||||
{
|
{
|
||||||
|
@ -490,6 +529,113 @@ MatrixClient::fetchRoomAvatar(const QString &roomid, const QUrl &avatar_url)
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MatrixClient::fetchCommunityAvatar(const QString &communityId, const QUrl &avatar_url)
|
||||||
|
{
|
||||||
|
QList<QString> url_parts = avatar_url.toString().split("mxc://");
|
||||||
|
|
||||||
|
if (url_parts.size() != 2) {
|
||||||
|
qDebug() << "Invalid format for community avatar " << avatar_url.toString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
QUrlQuery query;
|
||||||
|
query.addQueryItem("width", "512");
|
||||||
|
query.addQueryItem("height", "512");
|
||||||
|
query.addQueryItem("method", "crop");
|
||||||
|
|
||||||
|
QString media_url =
|
||||||
|
QString("%1/_matrix/media/r0/thumbnail/%2").arg(getHomeServer().toString(), url_parts[1]);
|
||||||
|
|
||||||
|
QUrl endpoint(media_url);
|
||||||
|
endpoint.setQuery(query);
|
||||||
|
|
||||||
|
QNetworkRequest avatar_request(endpoint);
|
||||||
|
|
||||||
|
QNetworkReply *reply = get(avatar_request);
|
||||||
|
connect(reply, &QNetworkReply::finished, this, [this, reply, communityId]() {
|
||||||
|
reply->deleteLater();
|
||||||
|
|
||||||
|
int status = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
|
||||||
|
|
||||||
|
if (status == 0 || status >= 400) {
|
||||||
|
qWarning() << reply->errorString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto img = reply->readAll();
|
||||||
|
|
||||||
|
if (img.size() == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
QPixmap pixmap;
|
||||||
|
pixmap.loadFromData(img);
|
||||||
|
|
||||||
|
emit communityAvatarRetrieved(communityId, pixmap);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MatrixClient::fetchCommunityProfile(const QString &communityId)
|
||||||
|
{
|
||||||
|
QUrlQuery query;
|
||||||
|
query.addQueryItem("access_token", token_);
|
||||||
|
|
||||||
|
QUrl endpoint(server_);
|
||||||
|
endpoint.setPath(clientApiUrl_ + "/groups/" + communityId + "/profile");
|
||||||
|
endpoint.setQuery(query);
|
||||||
|
|
||||||
|
QNetworkRequest request(QString(endpoint.toEncoded()));
|
||||||
|
|
||||||
|
QNetworkReply *reply = get(request);
|
||||||
|
|
||||||
|
connect(reply, &QNetworkReply::finished, this, [this, reply, communityId]() {
|
||||||
|
reply->deleteLater();
|
||||||
|
|
||||||
|
int status = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
|
||||||
|
|
||||||
|
if (status >= 400) {
|
||||||
|
qWarning() << reply->errorString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto data = reply->readAll();
|
||||||
|
const auto json = QJsonDocument::fromJson(data).object();
|
||||||
|
|
||||||
|
emit communityProfileRetrieved(communityId, json);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
MatrixClient::fetchCommunityRooms(const QString &communityId)
|
||||||
|
{
|
||||||
|
QUrlQuery query;
|
||||||
|
query.addQueryItem("access_token", token_);
|
||||||
|
|
||||||
|
QUrl endpoint(server_);
|
||||||
|
endpoint.setPath(clientApiUrl_ + "/groups/" + communityId + "/rooms");
|
||||||
|
endpoint.setQuery(query);
|
||||||
|
|
||||||
|
QNetworkRequest request(QString(endpoint.toEncoded()));
|
||||||
|
|
||||||
|
QNetworkReply *reply = get(request);
|
||||||
|
connect(reply, &QNetworkReply::finished, this, [this, reply, communityId]() {
|
||||||
|
reply->deleteLater();
|
||||||
|
|
||||||
|
int status = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
|
||||||
|
|
||||||
|
if (status >= 400) {
|
||||||
|
qWarning() << reply->errorString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto data = reply->readAll();
|
||||||
|
const auto json = QJsonDocument::fromJson(data).object();
|
||||||
|
|
||||||
|
emit communityRoomsRetrieved(communityId, json);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
MatrixClient::fetchUserAvatar(const QString &userId, const QUrl &avatarUrl)
|
MatrixClient::fetchUserAvatar(const QString &userId, const QUrl &avatarUrl)
|
||||||
{
|
{
|
||||||
|
|
|
@ -315,10 +315,7 @@ RoomInfoListItem::clearUnreadMessageCount()
|
||||||
void
|
void
|
||||||
RoomInfoListItem::setPressedState(bool state)
|
RoomInfoListItem::setPressedState(bool state)
|
||||||
{
|
{
|
||||||
if (!isPressed_ && state) {
|
if (isPressed_ != state) {
|
||||||
isPressed_ = state;
|
|
||||||
update();
|
|
||||||
} else if (isPressed_ && !state) {
|
|
||||||
isPressed_ = state;
|
isPressed_ = state;
|
||||||
update();
|
update();
|
||||||
}
|
}
|
||||||
|
|
|
@ -47,7 +47,7 @@ RoomList::RoomList(QSharedPointer<MatrixClient> client,
|
||||||
scrollArea_->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
|
scrollArea_->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
|
||||||
scrollArea_->setSizeAdjustPolicy(QAbstractScrollArea::AdjustToContents);
|
scrollArea_->setSizeAdjustPolicy(QAbstractScrollArea::AdjustToContents);
|
||||||
scrollArea_->setWidgetResizable(true);
|
scrollArea_->setWidgetResizable(true);
|
||||||
scrollArea_->setAlignment(Qt::AlignLeading | Qt::AlignLeft | Qt::AlignVCenter);
|
scrollArea_->setAlignment(Qt::AlignLeading | Qt::AlignTop | Qt::AlignVCenter);
|
||||||
|
|
||||||
scrollAreaContents_ = new QWidget(this);
|
scrollAreaContents_ = new QWidget(this);
|
||||||
|
|
||||||
|
@ -181,6 +181,8 @@ RoomList::setInitialRooms(const QMap<QString, QSharedPointer<RoomSettings>> &set
|
||||||
if (rooms_.isEmpty())
|
if (rooms_.isEmpty())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
setFilterRooms(filterRooms_);
|
||||||
|
|
||||||
auto first_room = rooms_.first();
|
auto first_room = rooms_.first();
|
||||||
first_room->setPressedState(true);
|
first_room->setPressedState(true);
|
||||||
|
|
||||||
|
@ -271,6 +273,8 @@ RoomList::highlightSelectedRoom(const QString &room_id)
|
||||||
qobject_cast<QWidget *>(it.value().data()));
|
qobject_cast<QWidget *>(it.value().data()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
selectedRoom_ = room_id;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -373,6 +377,46 @@ RoomList::closeLeaveRoomDialog(bool leaving, const QString &room_id)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
RoomList::setFilterRooms(bool filterRooms)
|
||||||
|
{
|
||||||
|
filterRooms_ = filterRooms;
|
||||||
|
|
||||||
|
for (int i = 0; i < contentsLayout_->count(); i++) {
|
||||||
|
// If roomFilter_ contains the room for the current RoomInfoListItem,
|
||||||
|
// show the list item, otherwise hide it
|
||||||
|
RoomInfoListItem *listitem =
|
||||||
|
(RoomInfoListItem *)contentsLayout_->itemAt(i)->widget();
|
||||||
|
|
||||||
|
if (listitem != nullptr) {
|
||||||
|
if (!filterRooms) {
|
||||||
|
contentsLayout_->itemAt(i)->widget()->show();
|
||||||
|
} else if (roomFilter_.contains(listitem->roomId())) {
|
||||||
|
contentsLayout_->itemAt(i)->widget()->show();
|
||||||
|
} else {
|
||||||
|
contentsLayout_->itemAt(i)->widget()->hide();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (filterRooms_ && !roomFilter_.contains(selectedRoom_)) {
|
||||||
|
RoomInfoListItem *firstVisibleRoom = nullptr;
|
||||||
|
for (int i = 0; i < contentsLayout_->count(); i++) {
|
||||||
|
QWidget *item = contentsLayout_->itemAt(i)->widget();
|
||||||
|
if (item != nullptr && item->isVisible()) {
|
||||||
|
firstVisibleRoom = (RoomInfoListItem *)item;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (firstVisibleRoom != nullptr) {
|
||||||
|
highlightSelectedRoom(firstVisibleRoom->roomId());
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
scrollArea_->ensureWidgetVisible(
|
||||||
|
qobject_cast<QWidget *>(rooms_.value(selectedRoom_).data()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
RoomList::paintEvent(QPaintEvent *)
|
RoomList::paintEvent(QPaintEvent *)
|
||||||
{
|
{
|
||||||
|
@ -393,6 +437,13 @@ RoomList::syncInvites(const std::map<std::string, mtx::responses::InvitedRoom> &
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
RoomList::setRoomFilter(QList<QString> room_ids)
|
||||||
|
{
|
||||||
|
roomFilter_ = room_ids;
|
||||||
|
setFilterRooms(true);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
RoomList::addInvitedRoom(const QString &room_id, const mtx::responses::InvitedRoom &room)
|
RoomList::addInvitedRoom(const QString &room_id, const mtx::responses::InvitedRoom &room)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue