diff --git a/src/components/middle/FloatingActionButtons.tsx b/src/components/middle/FloatingActionButtons.tsx index dfcebcd2b..ccbbdde0a 100644 --- a/src/components/middle/FloatingActionButtons.tsx +++ b/src/components/middle/FloatingActionButtons.tsx @@ -26,6 +26,7 @@ type StateProps = { messageListType?: MessageListType; unreadCount?: number; unreadReactions?: number[]; + unreadMentions?: number[]; reactionsCount?: number; mentionsCount?: number; }; @@ -39,6 +40,7 @@ const FloatingActionButtons: FC = ({ chatId, unreadCount, unreadReactions, + unreadMentions, reactionsCount, mentionsCount, withExtraShift, @@ -66,6 +68,12 @@ const FloatingActionButtons: FC = ({ } }, [chatId, fetchUnreadReactions, hasUnreadReactions]); + useEffect(() => { + if (hasUnreadMentions && chatId && !unreadMentions?.length) { + fetchUnreadMentions({ chatId }); + } + }, [chatId, fetchUnreadMentions, hasUnreadMentions, unreadMentions?.length]); + useEffect(() => { if (hasUnreadMentions && chatId) { fetchUnreadMentions({ chatId }); @@ -153,6 +161,7 @@ export default memo(withGlobal( chatId, reactionsCount: shouldShowCount ? chat.unreadReactionsCount : undefined, unreadReactions: shouldShowCount ? chat.unreadReactions : undefined, + unreadMentions: shouldShowCount ? chat.unreadMentions : undefined, mentionsCount: shouldShowCount ? chat.unreadMentionsCount : undefined, unreadCount: shouldShowCount ? chat.unreadCount : undefined, }; diff --git a/src/global/actions/api/messages.ts b/src/global/actions/api/messages.ts index d1be24525..9ac10129b 100644 --- a/src/global/actions/api/messages.ts +++ b/src/global/actions/api/messages.ts @@ -67,10 +67,12 @@ import { import { addChatMessagesById, addChats, + addUnreadMentions, addUsers, deleteSponsoredMessage, removeOutlyingList, removeRequestedMessageTranslation, + removeUnreadMentions, replaceSettings, replaceThreadParam, replaceUserStatuses, @@ -1655,9 +1657,7 @@ async function fetchUnreadMentions(global: T, chatId: str global = addChatMessagesById(global, chat.id, byId); global = addUsers(global, buildCollectionByKey(users, 'id')); global = addChats(global, buildCollectionByKey(chats, 'id')); - global = updateChat(global, chatId, { - unreadMentions: [...(chat.unreadMentions || []), ...ids], - }); + global = addUnreadMentions(global, chatId, chat, ids); setGlobal(global); } @@ -1668,18 +1668,7 @@ addActionHandler('markMentionsRead', (global, actions, payload): ActionReturnTyp const chat = selectCurrentChat(global, tabId); if (!chat) return; - const currentUnreadMentions = chat.unreadMentions || []; - - const unreadMentions = currentUnreadMentions.filter((id) => !messageIds.includes(id)); - const removedCount = currentUnreadMentions.length - unreadMentions.length; - - global = updateChat(global, chat.id, { - ...(chat.unreadMentionsCount && { - unreadMentionsCount: Math.max(chat.unreadMentionsCount - removedCount, 0) || undefined, - }), - unreadMentions, - }); - + global = removeUnreadMentions(global, chat.id, chat, messageIds, true); setGlobal(global); actions.markMessagesRead({ messageIds, tabId }); diff --git a/src/global/actions/apiUpdaters/chats.ts b/src/global/actions/apiUpdaters/chats.ts index 24ad5debd..acaab23d6 100644 --- a/src/global/actions/apiUpdaters/chats.ts +++ b/src/global/actions/apiUpdaters/chats.ts @@ -12,8 +12,10 @@ import { addActionHandler, getGlobal, setGlobal, } from '../../index'; import { + addUnreadMentions, deleteChatMessages, leaveChat, + removeUnreadMentions, replaceThreadParam, updateChat, updateChatFullInfo, @@ -177,13 +179,10 @@ addActionHandler('apiUpdate', (global, actions, update): ActionReturnType => { global = updateChat(global, update.chatId, { unreadCount: chat.unreadCount ? chat.unreadCount + 1 : 1, - ...(hasMention && { unreadMentionsCount: (chat.unreadMentionsCount || 0) + 1 }), }); if (hasMention) { - global = updateChat(global, update.chatId, { - unreadMentions: [...(chat.unreadMentions || []), update.message.id!], - }); + global = addUnreadMentions(global, update.chatId, chat, [update.message.id!], true); } const topic = chat.isForum ? selectTopicFromMessage(global, message as ApiMessage) : undefined; @@ -220,10 +219,7 @@ addActionHandler('apiUpdate', (global, actions, update): ActionReturnType => { } if (!messageUpdate.hasUnreadMention && chat?.unreadMentionsCount) { - global = updateChat(global, chatId, { - unreadMentionsCount: Math.max(chat.unreadMentionsCount - 1, 0) || undefined, - unreadMentions: chat.unreadMentions?.filter((i) => i !== id), - }); + global = removeUnreadMentions(global, chatId, chat, [id], true); } }); diff --git a/src/global/reducers/chats.ts b/src/global/reducers/chats.ts index 38e705f0d..a0b1e6e65 100644 --- a/src/global/reducers/chats.ts +++ b/src/global/reducers/chats.ts @@ -96,6 +96,47 @@ export function replaceChats(global: T, newById: Record( + global: T, chatId: string, chat: ApiChat, ids: number[], shouldUpdateCount: boolean = false, +): T { + const prevChatUnreadMentions = (chat.unreadMentions || []); + const updatedUnreadMentions = unique([...prevChatUnreadMentions, ...ids]).sort((a, b) => b - a); + global = updateChat(global, chatId, { + unreadMentions: updatedUnreadMentions, + }); + + if (shouldUpdateCount) { + const updatedUnreadMentionsCount = (chat.unreadMentionsCount || 0) + + Math.max(0, updatedUnreadMentions.length - prevChatUnreadMentions.length); + + global = updateChat(global, chatId, { + unreadMentionsCount: updatedUnreadMentionsCount, + }); + } + return global; +} + +export function removeUnreadMentions( + global: T, chatId: string, chat: ApiChat, ids: number[], shouldUpdateCount: boolean = false, +): T { + const prevChatUnreadMentions = (chat.unreadMentions || []); + const updatedUnreadMentions = prevChatUnreadMentions?.filter((id) => !ids.includes(id)); + + global = updateChat(global, chatId, { + unreadMentions: updatedUnreadMentions, + }); + + if (shouldUpdateCount && chat.unreadMentionsCount) { + const removedCount = prevChatUnreadMentions.length - updatedUnreadMentions.length; + const updatedUnreadMentionsCount = Math.max(chat.unreadMentionsCount - removedCount, 0) || undefined; + + global = updateChat(global, chatId, { + unreadMentionsCount: updatedUnreadMentionsCount, + }); + } + return global; +} + export function updateChat( global: T, chatId: string, chatUpdate: Partial, photo?: ApiPhoto, noOmitUnreadReactionCount = false,