summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--resources/qml/RoomList.qml19
-rw-r--r--src/MainWindow.cpp1
-rw-r--r--src/SideBarActions.cpp120
-rw-r--r--src/SideBarActions.h54
-rw-r--r--src/Splitter.cpp166
-rw-r--r--src/Splitter.h49
-rw-r--r--src/UserInfoWidget.cpp219
-rw-r--r--src/UserInfoWidget.h68
-rw-r--r--src/ui/NhekoGlobalObject.cpp27
-rw-r--r--src/ui/NhekoGlobalObject.h4
10 files changed, 50 insertions, 677 deletions
diff --git a/resources/qml/RoomList.qml b/resources/qml/RoomList.qml
index c5e07032..3109b75c 100644
--- a/resources/qml/RoomList.qml
+++ b/resources/qml/RoomList.qml
@@ -477,6 +477,7 @@ Page {
                     image: ":/icons/icons/ui/power-button-off.png"
                     ToolTip.visible: hovered
                     ToolTip.text: qsTr("Logout")
+                    onClicked: Nheko.openLogoutDialog()
                 }
 
             }
@@ -523,6 +524,23 @@ Page {
                     ToolTip.visible: hovered
                     ToolTip.text: qsTr("Start a new chat")
                     Layout.margins: Nheko.paddingMedium
+
+                    onClicked: roomJoinCreateMenu.open(parent)
+
+                    Platform.Menu {
+                        id: roomJoinCreateMenu
+
+                        Platform.MenuItem {
+                            text: qsTr("Join a room")
+                            onTriggered: Nheko.openJoinRoomDialog()
+                        }
+
+                        Platform.MenuItem {
+                            text: qsTr("Create a new room")
+                            onTriggered: Nheko.openCreateRoomDialog()
+                        }
+
+                    }
                 }
 
                 ImageButton {
@@ -545,6 +563,7 @@ Page {
                     ToolTip.visible: hovered
                     ToolTip.text: qsTr("User settings")
                     Layout.margins: Nheko.paddingMedium
+                    onClicked: Nheko.showUserSettingsPage()
                 }
 
             }
diff --git a/src/MainWindow.cpp b/src/MainWindow.cpp
index 057ee4af..ed337ca4 100644
--- a/src/MainWindow.cpp
+++ b/src/MainWindow.cpp
@@ -22,7 +22,6 @@
 #include "MainWindow.h"
 #include "MatrixClient.h"
 #include "RegisterPage.h"
-#include "Splitter.h"
 #include "TrayIcon.h"
 #include "UserSettingsPage.h"
 #include "Utils.h"
diff --git a/src/SideBarActions.cpp b/src/SideBarActions.cpp
deleted file mode 100644
index 0b7756f0..00000000
--- a/src/SideBarActions.cpp
+++ /dev/null
@@ -1,120 +0,0 @@
-// SPDX-FileCopyrightText: 2021 Nheko Contributors
-//
-// SPDX-License-Identifier: GPL-3.0-or-later
-
-#include <QIcon>
-#include <QPainter>
-#include <QResizeEvent>
-#include <QStyle>
-#include <QStyleOption>
-
-#include <mtx/requests.hpp>
-
-#include "Config.h"
-#include "MainWindow.h"
-#include "SideBarActions.h"
-#include "Splitter.h"
-#include "ui/FlatButton.h"
-#include "ui/Menu.h"
-
-SideBarActions::SideBarActions(QWidget *parent)
-  : QWidget{parent}
-{
-        QFont f;
-        f.setPointSizeF(f.pointSizeF());
-
-        const int fontHeight    = QFontMetrics(f).height();
-        const int contentHeight = fontHeight * 2.5;
-
-        setFixedHeight(contentHeight);
-
-        layout_ = new QHBoxLayout(this);
-        layout_->setMargin(0);
-
-        QIcon settingsIcon;
-        settingsIcon.addFile(":/icons/icons/ui/settings.png");
-
-        QIcon createRoomIcon;
-        createRoomIcon.addFile(":/icons/icons/ui/add-square-button.png");
-
-        QIcon joinRoomIcon;
-        joinRoomIcon.addFile(":/icons/icons/ui/speech-bubbles-comment-option.png");
-
-        settingsBtn_ = new FlatButton(this);
-        settingsBtn_->setToolTip(tr("User settings"));
-        settingsBtn_->setIcon(settingsIcon);
-        settingsBtn_->setCornerRadius(conf::sidebarActions::iconSize / 2);
-        settingsBtn_->setIconSize(
-          QSize(conf::sidebarActions::iconSize, conf::sidebarActions::iconSize));
-
-        addMenu_          = new Menu(this);
-        createRoomAction_ = new QAction(tr("Create new room"), this);
-        joinRoomAction_   = new QAction(tr("Join a room"), this);
-
-        connect(joinRoomAction_, &QAction::triggered, this, [this]() {
-                MainWindow::instance()->openJoinRoomDialog(
-                  [this](const QString &room_id) { emit joinRoom(room_id); });
-        });
-
-        connect(createRoomAction_, &QAction::triggered, this, [this]() {
-                MainWindow::instance()->openCreateRoomDialog(
-                  [this](const mtx::requests::CreateRoom &req) { emit createRoom(req); });
-        });
-
-        addMenu_->addAction(createRoomAction_);
-        addMenu_->addAction(joinRoomAction_);
-
-        createRoomBtn_ = new FlatButton(this);
-        createRoomBtn_->setToolTip(tr("Start a new chat"));
-        createRoomBtn_->setIcon(createRoomIcon);
-        createRoomBtn_->setCornerRadius(conf::sidebarActions::iconSize / 2);
-        createRoomBtn_->setIconSize(
-          QSize(conf::sidebarActions::iconSize, conf::sidebarActions::iconSize));
-
-        connect(createRoomBtn_, &QPushButton::clicked, this, [this]() {
-                auto pos     = mapToGlobal(createRoomBtn_->pos());
-                auto padding = conf::sidebarActions::iconSize / 2;
-
-                addMenu_->popup(
-                  QPoint(pos.x() + padding, pos.y() - padding - addMenu_->sizeHint().height()));
-        });
-
-        roomDirectory_ = new FlatButton(this);
-        roomDirectory_->setToolTip(tr("Room directory"));
-        roomDirectory_->setEnabled(false);
-        roomDirectory_->setIcon(joinRoomIcon);
-        roomDirectory_->setCornerRadius(conf::sidebarActions::iconSize / 2);
-        roomDirectory_->setIconSize(
-          QSize(conf::sidebarActions::iconSize, conf::sidebarActions::iconSize));
-
-        layout_->addWidget(createRoomBtn_);
-        layout_->addWidget(roomDirectory_);
-        layout_->addWidget(settingsBtn_);
-
-        connect(settingsBtn_, &QPushButton::clicked, this, &SideBarActions::showSettings);
-}
-
-void
-SideBarActions::resizeEvent(QResizeEvent *event)
-{
-        Q_UNUSED(event);
-
-        const auto sidebarSizes = splitter::calculateSidebarSizes(QFont{});
-
-        if (width() <= sidebarSizes.small) {
-                roomDirectory_->hide();
-                createRoomBtn_->hide();
-        } else {
-                roomDirectory_->show();
-                createRoomBtn_->show();
-        }
-}
-
-void
-SideBarActions::paintEvent(QPaintEvent *)
-{
-        QStyleOption opt;
-        opt.init(this);
-        QPainter p(this);
-        style()->drawPrimitive(QStyle::PE_Widget, &opt, &p, this);
-}
diff --git a/src/SideBarActions.h b/src/SideBarActions.h
deleted file mode 100644
index 566aa76b..00000000
--- a/src/SideBarActions.h
+++ /dev/null
@@ -1,54 +0,0 @@
-// SPDX-FileCopyrightText: 2021 Nheko Contributors
-//
-// SPDX-License-Identifier: GPL-3.0-or-later
-
-#pragma once
-
-#include <QAction>
-#include <QHBoxLayout>
-#include <QWidget>
-
-namespace mtx {
-namespace requests {
-struct CreateRoom;
-}
-}
-
-class Menu;
-class FlatButton;
-class QResizeEvent;
-
-class SideBarActions : public QWidget
-{
-        Q_OBJECT
-
-        Q_PROPERTY(QColor borderColor READ borderColor WRITE setBorderColor)
-
-public:
-        SideBarActions(QWidget *parent = nullptr);
-
-        QColor borderColor() const { return borderColor_; }
-        void setBorderColor(QColor &color) { borderColor_ = color; }
-
-signals:
-        void showSettings();
-        void joinRoom(const QString &room);
-        void createRoom(const mtx::requests::CreateRoom &request);
-
-protected:
-        void resizeEvent(QResizeEvent *event) override;
-        void paintEvent(QPaintEvent *event) override;
-
-private:
-        QHBoxLayout *layout_;
-
-        Menu *addMenu_;
-        QAction *createRoomAction_;
-        QAction *joinRoomAction_;
-
-        FlatButton *settingsBtn_;
-        FlatButton *createRoomBtn_;
-        FlatButton *roomDirectory_;
-
-        QColor borderColor_;
-};
diff --git a/src/Splitter.cpp b/src/Splitter.cpp
deleted file mode 100644
index 15e3f5c5..00000000
--- a/src/Splitter.cpp
+++ /dev/null
@@ -1,166 +0,0 @@
-// SPDX-FileCopyrightText: 2017 Konstantinos Sideris <siderisk@auth.gr>
-// SPDX-FileCopyrightText: 2021 Nheko Contributors
-//
-// SPDX-License-Identifier: GPL-3.0-or-later
-
-#include <QSettings>
-
-#include "Logging.h"
-#include "Splitter.h"
-
-constexpr auto MaxWidth = (1 << 24) - 1;
-
-Splitter::Splitter(QWidget *parent)
-  : QSplitter(parent)
-  , sz_{splitter::calculateSidebarSizes(QFont{})}
-{
-        connect(this, &QSplitter::splitterMoved, this, &Splitter::onSplitterMoved);
-        setChildrenCollapsible(false);
-}
-
-void
-Splitter::restoreSizes(int fallback)
-{
-        QSettings settings;
-        int savedWidth = settings.value("sidebar/width").toInt();
-
-        auto left = widget(0);
-        if (savedWidth <= 0) {
-                hideSidebar();
-                return;
-        } else if (savedWidth <= sz_.small) {
-                if (left) {
-                        left->setMinimumWidth(sz_.small);
-                        left->setMaximumWidth(sz_.small);
-                        return;
-                }
-        } else if (savedWidth < sz_.normal) {
-                savedWidth = sz_.normal;
-        }
-
-        left->setMinimumWidth(sz_.normal);
-        left->setMaximumWidth(2 * sz_.normal);
-        setSizes({savedWidth, fallback - savedWidth});
-
-        setStretchFactor(0, 0);
-        setStretchFactor(1, 1);
-}
-
-Splitter::~Splitter()
-{
-        auto left = widget(0);
-
-        if (left) {
-                QSettings settings;
-                settings.setValue("sidebar/width", left->width());
-        }
-}
-
-void
-Splitter::onSplitterMoved(int pos, int index)
-{
-        Q_UNUSED(pos);
-        Q_UNUSED(index);
-
-        auto s = sizes();
-
-        if (s.count() < 2) {
-                nhlog::ui()->warn("Splitter needs at least two children");
-                return;
-        }
-
-        if (s[0] == sz_.normal) {
-                rightMoveCount_ += 1;
-
-                if (rightMoveCount_ > moveEventLimit_) {
-                        auto left           = widget(0);
-                        auto cursorPosition = left->mapFromGlobal(QCursor::pos());
-
-                        // if we are coming from the right, the cursor should
-                        // end up on the first widget.
-                        if (left->rect().contains(cursorPosition)) {
-                                left->setMinimumWidth(sz_.small);
-                                left->setMaximumWidth(sz_.small);
-
-                                rightMoveCount_ = 0;
-                        }
-                }
-        } else if (s[0] == sz_.small) {
-                leftMoveCount_ += 1;
-
-                if (leftMoveCount_ > moveEventLimit_) {
-                        auto left           = widget(0);
-                        auto right          = widget(1);
-                        auto cursorPosition = right->mapFromGlobal(QCursor::pos());
-
-                        // We move the start a little further so the transition isn't so abrupt.
-                        auto extended = right->rect();
-                        extended.translate(100, 0);
-
-                        // if we are coming from the left, the cursor should
-                        // end up on the second widget.
-                        if (extended.contains(cursorPosition) &&
-                            right->size().width() >= sz_.collapsePoint + sz_.normal) {
-                                left->setMinimumWidth(sz_.normal);
-                                left->setMaximumWidth(2 * sz_.normal);
-
-                                leftMoveCount_ = 0;
-                        }
-                }
-        }
-}
-
-void
-Splitter::hideSidebar()
-{
-        auto left = widget(0);
-        if (left)
-                left->hide();
-}
-
-void
-Splitter::showChatView()
-{
-        auto left  = widget(0);
-        auto right = widget(1);
-
-        if (right->isHidden()) {
-                left->hide();
-                right->show();
-
-                // Restore previous size.
-                if (left->minimumWidth() == sz_.small) {
-                        left->setMinimumWidth(sz_.small);
-                        left->setMaximumWidth(sz_.small);
-                } else {
-                        left->setMinimumWidth(sz_.normal);
-                        left->setMaximumWidth(2 * sz_.normal);
-                }
-        }
-}
-
-void
-Splitter::showFullRoomList()
-{
-        auto left  = widget(0);
-        auto right = widget(1);
-
-        right->hide();
-
-        left->show();
-        left->setMaximumWidth(MaxWidth);
-}
-
-splitter::SideBarSizes
-splitter::calculateSidebarSizes(const QFont &f)
-{
-        const auto height = static_cast<double>(QFontMetrics{f}.lineSpacing());
-
-        SideBarSizes sz;
-        sz.small         = std::ceil(3.8 * height);
-        sz.normal        = std::ceil(16 * height);
-        sz.groups        = std::ceil(3 * height);
-        sz.collapsePoint = 2 * sz.normal;
-
-        return sz;
-}
diff --git a/src/Splitter.h b/src/Splitter.h
deleted file mode 100644
index 94622f89..00000000
--- a/src/Splitter.h
+++ /dev/null
@@ -1,49 +0,0 @@
-// SPDX-FileCopyrightText: 2017 Konstantinos Sideris <siderisk@auth.gr>
-// SPDX-FileCopyrightText: 2021 Nheko Contributors
-//
-// SPDX-License-Identifier: GPL-3.0-or-later
-
-#pragma once
-
-#include <QSplitter>
-
-namespace splitter {
-struct SideBarSizes
-{
-        int small;
-        int normal;
-        int groups;
-        int collapsePoint;
-};
-
-SideBarSizes
-calculateSidebarSizes(const QFont &f);
-}
-
-class Splitter : public QSplitter
-{
-        Q_OBJECT
-public:
-        explicit Splitter(QWidget *parent = nullptr);
-        ~Splitter() override;
-
-        void restoreSizes(int fallback);
-
-public slots:
-        void hideSidebar();
-        void showFullRoomList();
-        void showChatView();
-
-signals:
-        void hiddenSidebar();
-
-private:
-        void onSplitterMoved(int pos, int index);
-
-        int moveEventLimit_ = 50;
-
-        int leftMoveCount_  = 0;
-        int rightMoveCount_ = 0;
-
-        splitter::SideBarSizes sz_;
-};
diff --git a/src/UserInfoWidget.cpp b/src/UserInfoWidget.cpp
deleted file mode 100644
index 3d526b8b..00000000
--- a/src/UserInfoWidget.cpp
+++ /dev/null
@@ -1,219 +0,0 @@
-// SPDX-FileCopyrightText: 2017 Konstantinos Sideris <siderisk@auth.gr>
-// SPDX-FileCopyrightText: 2021 Nheko Contributors
-//
-// SPDX-License-Identifier: GPL-3.0-or-later
-
-#include <QInputDialog>
-#include <QLabel>
-#include <QMenu>
-#include <QPainter>
-#include <QStyle>
-#include <QStyleOption>
-#include <QTimer>
-
-#include <iostream>
-
-#include "ChatPage.h"
-#include "Config.h"
-#include "MainWindow.h"
-#include "Splitter.h"
-#include "UserInfoWidget.h"
-#include "UserSettingsPage.h"
-#include "ui/Avatar.h"
-#include "ui/FlatButton.h"
-#include "ui/OverlayModal.h"
-
-UserInfoWidget::UserInfoWidget(QWidget *parent)
-  : QWidget(parent)
-  , display_name_("User")
-  , user_id_("@user:homeserver.org")
-{
-        QFont f;
-        f.setPointSizeF(f.pointSizeF());
-
-        const int fontHeight    = QFontMetrics(f).height();
-        const int widgetMargin  = fontHeight / 3;
-        const int contentHeight = fontHeight * 3;
-
-        logoutButtonSize_ = std::min(fontHeight, 20);
-
-        setFixedHeight(contentHeight + widgetMargin);
-
-        topLayout_ = new QHBoxLayout(this);
-        topLayout_->setSpacing(0);
-        topLayout_->setMargin(widgetMargin);
-
-        avatarLayout_ = new QHBoxLayout();
-        textLayout_   = new QVBoxLayout();
-        textLayout_->setSpacing(widgetMargin / 2);
-        textLayout_->setContentsMargins(widgetMargin * 2, widgetMargin, widgetMargin, widgetMargin);
-
-        userAvatar_ = new Avatar(this, fontHeight * 2.5);
-        userAvatar_->setObjectName("userAvatar");
-        userAvatar_->setLetter(QChar('?'));
-
-        QFont nameFont;
-        nameFont.setPointSizeF(nameFont.pointSizeF() * 1.1);
-        nameFont.setWeight(QFont::Medium);
-
-        displayNameLabel_ = new QLabel(this);
-        displayNameLabel_->setFont(nameFont);
-        displayNameLabel_->setObjectName("displayNameLabel");
-        displayNameLabel_->setAlignment(Qt::AlignLeading | Qt::AlignLeft | Qt::AlignTop);
-
-        userIdLabel_ = new QLabel(this);
-        userIdLabel_->setFont(f);
-        userIdLabel_->setObjectName("userIdLabel");
-        userIdLabel_->setAlignment(Qt::AlignLeading | Qt::AlignLeft | Qt::AlignVCenter);
-
-        avatarLayout_->addWidget(userAvatar_);
-        textLayout_->addWidget(displayNameLabel_, 0, Qt::AlignBottom);
-        textLayout_->addWidget(userIdLabel_, 0, Qt::AlignTop);
-
-        topLayout_->addLayout(avatarLayout_);
-        topLayout_->addLayout(textLayout_);
-        topLayout_->addStretch(1);
-
-        buttonLayout_ = new QHBoxLayout();
-        buttonLayout_->setSpacing(0);
-        buttonLayout_->setMargin(0);
-
-        logoutButton_ = new FlatButton(this);
-        logoutButton_->setToolTip(tr("Logout"));
-        logoutButton_->setCornerRadius(logoutButtonSize_ / 2);
-
-        QIcon icon;
-        icon.addFile(":/icons/icons/ui/power-button-off.png");
-
-        logoutButton_->setIcon(icon);
-        logoutButton_->setIconSize(QSize(logoutButtonSize_, logoutButtonSize_));
-
-        buttonLayout_->addWidget(logoutButton_);
-
-        topLayout_->addLayout(buttonLayout_);
-
-        // Show the confirmation dialog.
-        connect(logoutButton_, &QPushButton::clicked, this, []() {
-                MainWindow::instance()->openLogoutDialog();
-        });
-
-        menu = new QMenu(this);
-
-        auto setStatusAction = menu->addAction(tr("Set custom status message"));
-        connect(setStatusAction, &QAction::triggered, this, [this]() {
-                bool ok      = false;
-                QString text = QInputDialog::getText(this,
-                                                     tr("Custom status message"),
-                                                     tr("Status:"),
-                                                     QLineEdit::Normal,
-                                                     ChatPage::instance()->status(),
-                                                     &ok);
-                if (ok)
-                        ChatPage::instance()->setStatus(text);
-        });
-
-        auto userProfileAction = menu->addAction(tr("User Profile Settings"));
-        connect(
-          userProfileAction, &QAction::triggered, this, [this]() { emit openGlobalUserProfile(); });
-
-#if 0 // disable presence menu until issues in synapse are resolved
-        auto setAutoPresence = menu->addAction(tr("Set presence automatically"));
-        connect(setAutoPresence, &QAction::triggered, this, []() {
-                ChatPage::instance()->userSettings()->setPresence(
-                  UserSettings::Presence::AutomaticPresence);
-                ChatPage::instance()->setStatus(ChatPage::instance()->status());
-        });
-        auto setOnline = menu->addAction(tr("Online"));
-        connect(setOnline, &QAction::triggered, this, []() {
-                ChatPage::instance()->userSettings()->setPresence(UserSettings::Presence::Online);
-                ChatPage::instance()->setStatus(ChatPage::instance()->status());
-        });
-        auto setUnavailable = menu->addAction(tr("Unavailable"));
-        connect(setUnavailable, &QAction::triggered, this, []() {
-                ChatPage::instance()->userSettings()->setPresence(
-                  UserSettings::Presence::Unavailable);
-                ChatPage::instance()->setStatus(ChatPage::instance()->status());
-        });
-        auto setOffline = menu->addAction(tr("Offline"));
-        connect(setOffline, &QAction::triggered, this, []() {
-                ChatPage::instance()->userSettings()->setPresence(UserSettings::Presence::Offline);
-                ChatPage::instance()->setStatus(ChatPage::instance()->status());
-        });
-#endif
-}
-
-void
-UserInfoWidget::contextMenuEvent(QContextMenuEvent *event)
-{
-        menu->popup(event->globalPos());
-}
-
-void
-UserInfoWidget::resizeEvent(QResizeEvent *event)
-{
-        Q_UNUSED(event);
-
-        const auto sz = splitter::calculateSidebarSizes(QFont{});
-
-        if (width() <= sz.small) {
-                topLayout_->setContentsMargins(0, 0, logoutButtonSize_, 0);
-
-                userAvatar_->hide();
-                displayNameLabel_->hide();
-                userIdLabel_->hide();
-        } else {
-                topLayout_->setMargin(5);
-                userAvatar_->show();
-                displayNameLabel_->show();
-                userIdLabel_->show();
-        }
-
-        QWidget::resizeEvent(event);
-}
-
-void
-UserInfoWidget::reset()
-{
-        displayNameLabel_->setText("");
-        userIdLabel_->setText("");
-        userAvatar_->setLetter(QChar('?'));
-}
-
-void
-UserInfoWidget::setDisplayName(const QString &name)
-{
-        if (name.isEmpty())
-                display_name_ = user_id_.split(':')[0].split('@')[1];
-        else
-                display_name_ = name;
-
-        displayNameLabel_->setText(display_name_);
-        userAvatar_->setLetter(QChar(display_name_[0]));
-        update();
-}
-
-void
-UserInfoWidget::setUserId(const QString &userid)
-{
-        user_id_ = userid;
-        userIdLabel_->setText(userid);
-        update();
-}
-
-void
-UserInfoWidget::setAvatar(const QString &url)
-{
-        userAvatar_->setImage(url);
-        update();
-}
-
-void
-UserInfoWidget::paintEvent(QPaintEvent *event)
-{
-        Q_UNUSED(event);
-
-        QStyleOption opt;
-        opt.init(this);
-        QPainter p(this);
-        style()->drawPrimitive(QStyle::PE_Widget, &opt, &p, this);
-}
diff --git a/src/UserInfoWidget.h b/src/UserInfoWidget.h
deleted file mode 100644
index 5aec1cda..00000000
--- a/src/UserInfoWidget.h
+++ /dev/null
@@ -1,68 +0,0 @@
-// SPDX-FileCopyrightText: 2017 Konstantinos Sideris <siderisk@auth.gr>
-// SPDX-FileCopyrightText: 2021 Nheko Contributors
-//
-// SPDX-License-Identifier: GPL-3.0-or-later
-
-#pragma once
-
-#include <QWidget>
-
-class Avatar;
-class FlatButton;
-class OverlayModal;
-
-class QLabel;
-class QHBoxLayout;
-class QVBoxLayout;
-class QMenu;
-
-class UserInfoWidget : public QWidget
-{
-        Q_OBJECT
-
-        Q_PROPERTY(QColor borderColor READ borderColor WRITE setBorderColor)
-
-public:
-        UserInfoWidget(QWidget *parent = nullptr);
-
-        void setDisplayName(const QString &name);
-        void setUserId(const QString &userid);
-        void setAvatar(const QString &url);
-
-        void reset();
-
-        QColor borderColor() const { return borderColor_; }
-        void setBorderColor(QColor &color) { borderColor_ = color; }
-
-protected:
-        void resizeEvent(QResizeEvent *event) override;
-        void paintEvent(QPaintEvent *event) override;
-        void contextMenuEvent(QContextMenuEvent *) override;
-
-signals:
-        void openGlobalUserProfile();
-
-private:
-        Avatar *userAvatar_;
-
-        QHBoxLayout *topLayout_;
-        QHBoxLayout *avatarLayout_;
-        QVBoxLayout *textLayout_;
-        QHBoxLayout *buttonLayout_;
-
-        FlatButton *logoutButton_;
-
-        QLabel *displayNameLabel_;
-        QLabel *userIdLabel_;
-
-        QString display_name_;
-        QString user_id_;
-
-        QImage avatar_image_;
-
-        int logoutButtonSize_;
-
-        QColor borderColor_;
-
-        QMenu *menu = nullptr;
-};
diff --git a/src/ui/NhekoGlobalObject.cpp b/src/ui/NhekoGlobalObject.cpp
index fd572b4b..fea10839 100644
--- a/src/ui/NhekoGlobalObject.cpp
+++ b/src/ui/NhekoGlobalObject.cpp
@@ -10,6 +10,7 @@
 #include "Cache_p.h"
 #include "ChatPage.h"
 #include "Logging.h"
+#include "MainWindow.h"
 #include "UserSettingsPage.h"
 #include "Utils.h"
 
@@ -113,3 +114,29 @@ Nheko::currentUser() const
 
         return currentUser_.get();
 }
+
+void
+Nheko::showUserSettingsPage() const
+{
+        ChatPage::instance()->showUserSettingsPage();
+}
+
+void
+Nheko::openLogoutDialog() const
+{
+        MainWindow::instance()->openLogoutDialog();
+}
+
+void
+Nheko::openCreateRoomDialog() const
+{
+        MainWindow::instance()->openCreateRoomDialog(
+          [](const mtx::requests::CreateRoom &req) { ChatPage::instance()->createRoom(req); });
+}
+
+void
+Nheko::openJoinRoomDialog() const
+{
+        MainWindow::instance()->openJoinRoomDialog(
+          [](const QString &room_id) { ChatPage::instance()->joinRoom(room_id); });
+}
diff --git a/src/ui/NhekoGlobalObject.h b/src/ui/NhekoGlobalObject.h
index 593514fa..14135fd1 100644
--- a/src/ui/NhekoGlobalObject.h
+++ b/src/ui/NhekoGlobalObject.h
@@ -40,6 +40,10 @@ public:
 
         Q_INVOKABLE void openLink(QString link) const;
         Q_INVOKABLE void setStatusMessage(QString msg) const;
+        Q_INVOKABLE void showUserSettingsPage() const;
+        Q_INVOKABLE void openLogoutDialog() const;
+        Q_INVOKABLE void openCreateRoomDialog() const;
+        Q_INVOKABLE void openJoinRoomDialog() const;
 
 public slots:
         void updateUserProfile();