Add basic support for multiple windows
This commit is contained in:
parent
19642bc7ab
commit
b75ef07896
@ -232,13 +232,7 @@ Item {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Connections {
|
Window.onActiveChanged: readTimer.running = Window.active
|
||||||
function onFocusChanged() {
|
|
||||||
readTimer.running = TimelineManager.isWindowFocused;
|
|
||||||
}
|
|
||||||
|
|
||||||
target: TimelineManager
|
|
||||||
}
|
|
||||||
|
|
||||||
Timer {
|
Timer {
|
||||||
id: readTimer
|
id: readTimer
|
||||||
|
@ -64,6 +64,41 @@ Page {
|
|||||||
target: Rooms
|
target: Rooms
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Component {
|
||||||
|
id: roomWindowComponent
|
||||||
|
|
||||||
|
ApplicationWindow {
|
||||||
|
id: roomWindowW
|
||||||
|
|
||||||
|
property var room: null
|
||||||
|
property var roomPreview: null
|
||||||
|
|
||||||
|
onActiveChanged: if (active) {MainWindow.activeRoom = (room.roomId || roomPreview.roomid)}
|
||||||
|
|
||||||
|
height: 650
|
||||||
|
width: 420
|
||||||
|
minimumWidth: 150
|
||||||
|
minimumHeight: 150
|
||||||
|
palette: Nheko.colors
|
||||||
|
color: Nheko.colors.window
|
||||||
|
title: room.roomName
|
||||||
|
modality: Qt.NonModal
|
||||||
|
flags: Qt.Window | Qt.WindowCloseButtonHint | Qt.WindowTitleHint
|
||||||
|
|
||||||
|
Shortcut {
|
||||||
|
sequence: StandardKey.Cancel
|
||||||
|
onActivated: roomWindowW.close()
|
||||||
|
}
|
||||||
|
|
||||||
|
TimelineView {
|
||||||
|
anchors.fill: parent
|
||||||
|
room: roomWindowW.room
|
||||||
|
roomPreview: roomWindowW.roomPreview.roomid ? roomWindowW.roomPreview : null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
Platform.Menu {
|
Platform.Menu {
|
||||||
id: roomContextMenu
|
id: roomContextMenu
|
||||||
|
|
||||||
@ -86,6 +121,18 @@ Page {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Platform.MenuItem {
|
||||||
|
text: qsTr("Open separately")
|
||||||
|
onTriggered: {
|
||||||
|
var roomWindow = roomWindowComponent.createObject(null, {
|
||||||
|
"room": Rooms.getRoomById(roomContextMenu.roomid),
|
||||||
|
"roomPreview": Rooms.getRoomPreviewById(roomContextMenu.roomid)
|
||||||
|
});
|
||||||
|
roomWindow.showNormal();
|
||||||
|
destroyOnClose(roomWindow);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Platform.MenuItem {
|
Platform.MenuItem {
|
||||||
text: qsTr("Leave room")
|
text: qsTr("Leave room")
|
||||||
onTriggered: TimelineManager.openLeaveRoomDialog(roomContextMenu.roomid)
|
onTriggered: TimelineManager.openLeaveRoomDialog(roomContextMenu.roomid)
|
||||||
@ -97,7 +144,7 @@ Page {
|
|||||||
|
|
||||||
Instantiator {
|
Instantiator {
|
||||||
model: Communities.tagsWithDefault
|
model: Communities.tagsWithDefault
|
||||||
onObjectAdded: roomContextMenu.insertItem(index + 2, object)
|
onObjectAdded: roomContextMenu.insertItem(index + 3, object)
|
||||||
onObjectRemoved: roomContextMenu.removeItem(object)
|
onObjectRemoved: roomContextMenu.removeItem(object)
|
||||||
|
|
||||||
delegate: Platform.MenuItem {
|
delegate: Platform.MenuItem {
|
||||||
|
@ -25,6 +25,8 @@ Pane {
|
|||||||
background: null
|
background: null
|
||||||
padding: 0
|
padding: 0
|
||||||
|
|
||||||
|
Window.onActiveChanged: if (Window.active) {MainWindow.activeRoom = Qt.binding(function() { return Rooms.currentRoom.roomId || Rooms.currentRoomPreview.roomid })}
|
||||||
|
|
||||||
FontMetrics {
|
FontMetrics {
|
||||||
id: fontMetrics
|
id: fontMetrics
|
||||||
}
|
}
|
||||||
|
@ -813,7 +813,7 @@ ChatPage::changeRoom(const QString &room_id)
|
|||||||
void
|
void
|
||||||
ChatPage::inviteUser(QString userid, QString reason)
|
ChatPage::inviteUser(QString userid, QString reason)
|
||||||
{
|
{
|
||||||
auto room = currentRoom();
|
auto room = MainWindow::instance()->activeRoom();
|
||||||
|
|
||||||
if (QMessageBox::question(nullptr,
|
if (QMessageBox::question(nullptr,
|
||||||
tr("Confirm invite"),
|
tr("Confirm invite"),
|
||||||
@ -839,7 +839,7 @@ ChatPage::inviteUser(QString userid, QString reason)
|
|||||||
void
|
void
|
||||||
ChatPage::kickUser(QString userid, QString reason)
|
ChatPage::kickUser(QString userid, QString reason)
|
||||||
{
|
{
|
||||||
auto room = currentRoom();
|
auto room = MainWindow::instance()->activeRoom();
|
||||||
|
|
||||||
bool confirmed;
|
bool confirmed;
|
||||||
reason =
|
reason =
|
||||||
@ -870,7 +870,7 @@ ChatPage::kickUser(QString userid, QString reason)
|
|||||||
void
|
void
|
||||||
ChatPage::banUser(QString userid, QString reason)
|
ChatPage::banUser(QString userid, QString reason)
|
||||||
{
|
{
|
||||||
auto room = currentRoom();
|
auto room = MainWindow::instance()->activeRoom();
|
||||||
|
|
||||||
bool confirmed;
|
bool confirmed;
|
||||||
reason =
|
reason =
|
||||||
@ -901,7 +901,7 @@ ChatPage::banUser(QString userid, QString reason)
|
|||||||
void
|
void
|
||||||
ChatPage::unbanUser(QString userid, QString reason)
|
ChatPage::unbanUser(QString userid, QString reason)
|
||||||
{
|
{
|
||||||
auto room = currentRoom();
|
auto room = MainWindow::instance()->activeRoom();
|
||||||
|
|
||||||
if (QMessageBox::question(nullptr,
|
if (QMessageBox::question(nullptr,
|
||||||
tr("Confirm unban"),
|
tr("Confirm unban"),
|
||||||
@ -1398,9 +1398,11 @@ ChatPage::handleMatrixUri(QString uri)
|
|||||||
|
|
||||||
if (sigil1 == u"u") {
|
if (sigil1 == u"u") {
|
||||||
if (action.isEmpty()) {
|
if (action.isEmpty()) {
|
||||||
auto t = view_manager_->rooms()->currentRoom();
|
auto t = MainWindow::instance()->activeRoom();
|
||||||
if (t && cache::isRoomMember(mxid1.toStdString(), t->roomId().toStdString())) {
|
if (!t.isEmpty() && cache::isRoomMember(mxid1.toStdString(), t.toStdString())) {
|
||||||
t->openUserProfile(mxid1);
|
auto rm = view_manager_->rooms()->getRoomById(t);
|
||||||
|
if (rm)
|
||||||
|
rm->openUserProfile(mxid1);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
emit view_manager_->openGlobalUserProfile(mxid1);
|
emit view_manager_->openGlobalUserProfile(mxid1);
|
||||||
@ -1466,14 +1468,5 @@ ChatPage::handleMatrixUri(const QUrl &uri)
|
|||||||
bool
|
bool
|
||||||
ChatPage::isRoomActive(const QString &room_id)
|
ChatPage::isRoomActive(const QString &room_id)
|
||||||
{
|
{
|
||||||
return MainWindow::instance()->isActive() && currentRoom() == room_id;
|
return QGuiApplication::focusWindow() && MainWindow::instance()->activeRoom() == room_id;
|
||||||
}
|
|
||||||
|
|
||||||
QString
|
|
||||||
ChatPage::currentRoom() const
|
|
||||||
{
|
|
||||||
if (view_manager_->rooms()->currentRoom())
|
|
||||||
return view_manager_->rooms()->currentRoom()->roomId();
|
|
||||||
else
|
|
||||||
return QString();
|
|
||||||
}
|
}
|
||||||
|
@ -72,8 +72,6 @@ public:
|
|||||||
|
|
||||||
mtx::presence::PresenceState currentPresence() const;
|
mtx::presence::PresenceState currentPresence() const;
|
||||||
|
|
||||||
// TODO(Nico): Get rid of this!
|
|
||||||
QString currentRoom() const;
|
|
||||||
void startChat(QString userid, std::optional<bool> encryptionEnabled);
|
void startChat(QString userid, std::optional<bool> encryptionEnabled);
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
|
@ -40,6 +40,7 @@ class ReCaptcha;
|
|||||||
class MainWindow : public QQuickView
|
class MainWindow : public QQuickView
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(QString activeRoom READ activeRoom WRITE updateActiveRoom NOTIFY activeRoomChanged)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit MainWindow(QWindow *parent = nullptr);
|
explicit MainWindow(QWindow *parent = nullptr);
|
||||||
@ -58,6 +59,15 @@ public:
|
|||||||
bool dbusAvailable() const { return dbusAvailable_; }
|
bool dbusAvailable() const { return dbusAvailable_; }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
QString activeRoom() const { return activeRoom_; }
|
||||||
|
void updateActiveRoom(QString r)
|
||||||
|
{
|
||||||
|
if (activeRoom_ != r) {
|
||||||
|
activeRoom_ = std::move(r);
|
||||||
|
emit activeRoomChanged();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void closeEvent(QCloseEvent *event);
|
void closeEvent(QCloseEvent *event);
|
||||||
bool event(QEvent *event) override;
|
bool event(QEvent *event) override;
|
||||||
@ -78,6 +88,8 @@ signals:
|
|||||||
void switchToWelcomePage();
|
void switchToWelcomePage();
|
||||||
void switchToLoginPage(QString error);
|
void switchToLoginPage(QString error);
|
||||||
|
|
||||||
|
void activeRoomChanged();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void showDialog(QWidget *dialog);
|
void showDialog(QWidget *dialog);
|
||||||
bool hasActiveUser();
|
bool hasActiveUser();
|
||||||
@ -101,6 +113,8 @@ private:
|
|||||||
|
|
||||||
MxcImageProvider *imgProvider = nullptr;
|
MxcImageProvider *imgProvider = nullptr;
|
||||||
|
|
||||||
|
QString activeRoom_;
|
||||||
|
|
||||||
#ifdef NHEKO_DBUS_SYS
|
#ifdef NHEKO_DBUS_SYS
|
||||||
bool dbusAvailable_{false};
|
bool dbusAvailable_{false};
|
||||||
#endif
|
#endif
|
||||||
|
@ -692,6 +692,34 @@ RoomlistModel::leave(QString roomid, QString reason)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
RoomPreview
|
||||||
|
RoomlistModel::getRoomPreviewById(QString roomid) const
|
||||||
|
{
|
||||||
|
RoomPreview preview{};
|
||||||
|
|
||||||
|
if (invites.contains(roomid) || previewedRooms.contains(roomid)) {
|
||||||
|
std::optional<RoomInfo> i;
|
||||||
|
if (invites.contains(roomid)) {
|
||||||
|
i = invites.value(roomid);
|
||||||
|
preview.isInvite_ = true;
|
||||||
|
} else {
|
||||||
|
i = previewedRooms.value(roomid);
|
||||||
|
preview.isInvite_ = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (i) {
|
||||||
|
preview.roomid_ = roomid;
|
||||||
|
preview.roomName_ = QString::fromStdString(i->name);
|
||||||
|
preview.roomTopic_ = QString::fromStdString(i->topic);
|
||||||
|
preview.roomAvatarUrl_ = QString::fromStdString(i->avatar_url);
|
||||||
|
} else {
|
||||||
|
preview.roomid_ = roomid;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return preview;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
RoomlistModel::setCurrentRoom(QString roomid)
|
RoomlistModel::setCurrentRoom(QString roomid)
|
||||||
{
|
{
|
||||||
|
@ -89,6 +89,7 @@ public:
|
|||||||
else
|
else
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
|
RoomPreview getRoomPreviewById(QString roomid) const;
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void initializeRooms();
|
void initializeRooms();
|
||||||
@ -185,6 +186,10 @@ public slots:
|
|||||||
{
|
{
|
||||||
return roomlistmodel->getRoomById(id).data();
|
return roomlistmodel->getRoomById(id).data();
|
||||||
}
|
}
|
||||||
|
RoomPreview getRoomPreviewById(QString roomid) const
|
||||||
|
{
|
||||||
|
return roomlistmodel->getRoomPreviewById(roomid);
|
||||||
|
}
|
||||||
|
|
||||||
void nextRoomWithActivity();
|
void nextRoomWithActivity();
|
||||||
void nextRoom();
|
void nextRoom();
|
||||||
|
@ -1072,7 +1072,7 @@ TimelineModel::setCurrentIndex(int index)
|
|||||||
if (index != oldIndex)
|
if (index != oldIndex)
|
||||||
emit currentIndexChanged(index);
|
emit currentIndexChanged(index);
|
||||||
|
|
||||||
if (MainWindow::instance() != QGuiApplication::focusWindow())
|
if (MainWindow::instance()->activeRoom() != roomId())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (!currentId.startsWith('m')) {
|
if (!currentId.startsWith('m')) {
|
||||||
|
@ -138,10 +138,6 @@ TimelineViewManager::TimelineViewManager(CallManager *, ChatPage *parent)
|
|||||||
isInitialSync_ = true;
|
isInitialSync_ = true;
|
||||||
emit initialSyncChanged(true);
|
emit initialSyncChanged(true);
|
||||||
});
|
});
|
||||||
connect(qobject_cast<QApplication *>(QApplication::instance()),
|
|
||||||
&QApplication::focusWindowChanged,
|
|
||||||
this,
|
|
||||||
&TimelineViewManager::focusChanged);
|
|
||||||
connect(parent, &ChatPage::connectionLost, this, [this] {
|
connect(parent, &ChatPage::connectionLost, this, [this] {
|
||||||
isConnected_ = false;
|
isConnected_ = false;
|
||||||
emit isConnectedChanged(false);
|
emit isConnectedChanged(false);
|
||||||
@ -152,12 +148,6 @@ TimelineViewManager::TimelineViewManager(CallManager *, ChatPage *parent)
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
|
||||||
TimelineViewManager::isWindowFocused() const
|
|
||||||
{
|
|
||||||
return MainWindow::instance() == QApplication::focusWindow();
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
TimelineViewManager::openRoomMembers(TimelineModel *room)
|
TimelineViewManager::openRoomMembers(TimelineModel *room)
|
||||||
{
|
{
|
||||||
|
@ -41,7 +41,6 @@ class TimelineViewManager : public QObject
|
|||||||
|
|
||||||
Q_PROPERTY(
|
Q_PROPERTY(
|
||||||
bool isInitialSync MEMBER isInitialSync_ READ isInitialSync NOTIFY initialSyncChanged)
|
bool isInitialSync MEMBER isInitialSync_ READ isInitialSync NOTIFY initialSyncChanged)
|
||||||
Q_PROPERTY(bool isWindowFocused READ isWindowFocused NOTIFY focusChanged)
|
|
||||||
Q_PROPERTY(bool isConnected READ isConnected NOTIFY isConnectedChanged)
|
Q_PROPERTY(bool isConnected READ isConnected NOTIFY isConnectedChanged)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
@ -54,7 +53,6 @@ public:
|
|||||||
void clearAll() { rooms_->clear(); }
|
void clearAll() { rooms_->clear(); }
|
||||||
|
|
||||||
Q_INVOKABLE bool isInitialSync() const { return isInitialSync_; }
|
Q_INVOKABLE bool isInitialSync() const { return isInitialSync_; }
|
||||||
bool isWindowFocused() const;
|
|
||||||
bool isConnected() const { return isConnected_; }
|
bool isConnected() const { return isConnected_; }
|
||||||
Q_INVOKABLE void openImageOverlay(TimelineModel *room, QString mxcUrl, QString eventId);
|
Q_INVOKABLE void openImageOverlay(TimelineModel *room, QString mxcUrl, QString eventId);
|
||||||
Q_INVOKABLE void openImagePackSettings(QString roomid);
|
Q_INVOKABLE void openImagePackSettings(QString roomid);
|
||||||
@ -82,7 +80,6 @@ signals:
|
|||||||
void inviteUsers(QString roomId, QStringList users);
|
void inviteUsers(QString roomId, QStringList users);
|
||||||
void showRoomList();
|
void showRoomList();
|
||||||
void narrowViewChanged();
|
void narrowViewChanged();
|
||||||
void focusChanged();
|
|
||||||
void focusInput();
|
void focusInput();
|
||||||
void openRoomMembersDialog(MemberList *members, TimelineModel *room);
|
void openRoomMembersDialog(MemberList *members, TimelineModel *room);
|
||||||
void openRoomSettingsDialog(RoomSettings *settings);
|
void openRoomSettingsDialog(RoomSettings *settings);
|
||||||
|
Loading…
Reference in New Issue
Block a user