From 7ce02ef0db00a938c7a246c349237622f5553190 Mon Sep 17 00:00:00 2001 From: James Graham Date: Tue, 22 Nov 2022 20:25:04 +0000 Subject: [PATCH] Improve read marker - Update from deprecated readMarkerEventId to lastFullyReadEventId for quotient 0.7. - Removed duplicate code for marking read from the read marker delegate. - Make sure that mark as read only trigger at the end of the timeline - Allow the read marker to be highlighted when jumped to --- src/messageeventmodel.cpp | 8 +++ src/neochatroom.cpp | 4 ++ .../Component/Timeline/ReadMarkerDelegate.qml | 67 ++++++------------- src/qml/Page/RoomPage.qml | 2 +- 4 files changed, 34 insertions(+), 47 deletions(-) diff --git a/src/messageeventmodel.cpp b/src/messageeventmodel.cpp index 46c958193..ccf2f91d0 100644 --- a/src/messageeventmodel.cpp +++ b/src/messageeventmodel.cpp @@ -102,7 +102,11 @@ void MessageEventModel::setRoom(NeoChatRoom *room) if (m_currentRoom->timelineSize() < 10 && !room->allHistoryLoaded()) { room->getPreviousContent(50); } +#ifdef QUOTIENT_07 + lastReadEventId = room->lastFullyReadEventId(); +#else lastReadEventId = room->readMarkerEventId(); +#endif using namespace Quotient; connect(m_currentRoom, &Room::aboutToAddNewMessages, this, [this](RoomEventsRange events) { @@ -151,7 +155,11 @@ void MessageEventModel::setRoom(NeoChatRoom *room) endInsertRows(); if (!m_lastReadEventIndex.isValid()) { // no read marker, so see if we need to create one. +#ifdef QUOTIENT_07 + moveReadMarker(m_currentRoom->lastFullyReadEventId()); +#else moveReadMarker(m_currentRoom->readMarkerEventId()); +#endif } if (biggest < m_currentRoom->maxTimelineIndex()) { auto rowBelowInserted = m_currentRoom->maxTimelineIndex() - biggest + timelineBaseIndex() - 1; diff --git a/src/neochatroom.cpp b/src/neochatroom.cpp index 98c3d7726..853b83173 100644 --- a/src/neochatroom.cpp +++ b/src/neochatroom.cpp @@ -851,7 +851,11 @@ bool NeoChatRoom::canSendState(const QString &eventType) const bool NeoChatRoom::readMarkerLoaded() const { +#ifdef QUOTIENT_07 + const auto it = findInTimeline(lastFullyReadEventId()); +#else const auto it = findInTimeline(readMarkerEventId()); +#endif return it != historyEdge(); } diff --git a/src/qml/Component/Timeline/ReadMarkerDelegate.qml b/src/qml/Component/Timeline/ReadMarkerDelegate.qml index b2856ac71..db1b8da6f 100644 --- a/src/qml/Component/Timeline/ReadMarkerDelegate.qml +++ b/src/qml/Component/Timeline/ReadMarkerDelegate.qml @@ -20,6 +20,17 @@ QQC2.ItemDelegate { readonly property int extraWidth: messageListView.width >= Kirigami.Units.gridUnit * 46 ? Math.min((messageListView.width - Kirigami.Units.gridUnit * 46), Kirigami.Units.gridUnit * 20) : 0 readonly property int delegateMaxWidth: Config.compactLayout ? messageListView.width - Kirigami.Units.largeSpacing * 2 : Math.min(messageListView.width - Kirigami.Units.largeSpacing * 2, Kirigami.Units.gridUnit * 40 + extraWidth) + property bool isTemporaryHighlighted: false + + onIsTemporaryHighlightedChanged: if (isTemporaryHighlighted) temporaryHighlightTimer.start() + + Timer { + id: temporaryHighlightTimer + + interval: 1500 + onTriggered: isTemporaryHighlighted = false + } + width: delegateMaxWidth anchors.leftMargin: Kirigami.Units.largeSpacing anchors.rightMargin: Kirigami.Units.largeSpacing @@ -59,58 +70,22 @@ QQC2.ItemDelegate { } background: Kirigami.ShadowedRectangle { - color: Kirigami.Theme.backgroundColor - opacity: 0.6 + color: { + if (readMarkerDelegate.isTemporaryHighlighted) { + return Kirigami.Theme.positiveBackgroundColor + } else { + return Kirigami.Theme.backgroundColor + } + } + opacity: readMarkerDelegate.isTemporaryHighlighted ? 1 : 0.6 radius: Kirigami.Units.smallSpacing shadow.size: Kirigami.Units.smallSpacing shadow.color: Qt.rgba(0.0, 0.0, 0.0, 0.10) border.color: Kirigami.ColorUtils.tintWithAlpha(color, Kirigami.Theme.textColor, 0.15) border.width: 1 - } - Timer { - id: makeMeDisapearTimer - interval: Kirigami.Units.humanMoment * 2 - onTriggered: if (QQC2.ApplicationWindow.window.visibility !== QQC2.ApplicationWindow.Hidden) { - currentRoom.markAllMessagesAsRead(); - } - } - - ListView.onPooled: makeMeDisapearTimer.stop() - - ListView.onAdd: { - const view = ListView.view; - if (view.atYEnd) { - makeMeDisapearTimer.start() - } - } - - // When the read marker is visible and we are at the end of the list, - // start the makeMeDisapearTimer - Connections { - target: ListView.view - function onAtYEndChanged() { - makeMeDisapearTimer.start(); - } - } - - - ListView.onRemove: { - const view = ListView.view; - - if (view.atYEnd) { - // easy case just mark everything as read - if (QQC2.ApplicationWindow.window.visibility !== QQC2.ApplicationWindow.Hidden) { - currentRoom.markAllMessagesAsRead(); - } - return; - } - - // mark the last visible index - const lastVisibleIdx = lastVisibleIndex(); - - if (lastVisibleIdx < index) { - currentRoom.readMarkerEventId = sortedMessageEventModel.data(sortedMessageEventModel.index(lastVisibleIdx, 0), MessageEventModel.EventIdRole) + Behavior on color { + ColorAnimation {target: bubbleBackground; duration: Kirigami.Units.veryLongDuration; easing.type: Easing.InOutCubic} } } } diff --git a/src/qml/Page/RoomPage.qml b/src/qml/Page/RoomPage.qml index db0519ef9..db1254f5d 100644 --- a/src/qml/Page/RoomPage.qml +++ b/src/qml/Page/RoomPage.qml @@ -649,7 +649,7 @@ Kirigami.ScrollablePage { // Mark all messages as read if all unread messages are visible to the user function markReadIfVisible() { let readMarkerRow = eventToIndex(currentRoom.readMarkerEventId) - if (readMarkerRow > 0 && readMarkerRow < firstVisibleIndex()) { + if (readMarkerRow > 0 && readMarkerRow < firstVisibleIndex() && messageListView.atYEnd) { currentRoom.markAllMessagesAsRead() } }