signal-desktop/ts/components/leftPane/getConversationInDirection.ts

63 lines
2.2 KiB
TypeScript

// Copyright 2021 Signal Messenger, LLC
// SPDX-License-Identifier: AGPL-3.0-only
import { find as findFirst, findLast, first, last } from 'lodash';
import { PropsData as ConversationListItemPropsType } from '../conversationList/ConversationListItem';
import { isConversationUnread } from '../../util/isConversationUnread';
import { FindDirection, ToFindType } from './LeftPaneHelper';
/**
* This will look up or down in an array of conversations for the next one to select.
* Refer to the tests for the intended behavior.
*/
export const getConversationInDirection = (
conversations: ReadonlyArray<ConversationListItemPropsType>,
toFind: Readonly<ToFindType>,
selectedConversationId: undefined | string
): undefined | { conversationId: string } => {
// As an optimization, we don't need to search if no conversation is selected.
const selectedConversationIndex = selectedConversationId
? conversations.findIndex(({ id }) => id === selectedConversationId)
: -1;
let conversation: ConversationListItemPropsType | undefined;
if (selectedConversationIndex < 0) {
if (toFind.unreadOnly) {
conversation =
toFind.direction === FindDirection.Up
? findLast(conversations, isConversationUnread)
: findFirst(conversations, isConversationUnread);
} else {
conversation =
toFind.direction === FindDirection.Up
? last(conversations)
: first(conversations);
}
} else if (toFind.unreadOnly) {
conversation =
toFind.direction === FindDirection.Up
? findLast(
conversations.slice(0, selectedConversationIndex),
isConversationUnread
)
: findFirst(
conversations.slice(selectedConversationIndex + 1),
isConversationUnread
);
} else {
const newIndex =
selectedConversationIndex +
(toFind.direction === FindDirection.Up ? -1 : 1);
if (newIndex < 0) {
conversation = last(conversations);
} else if (newIndex >= conversations.length) {
conversation = first(conversations);
} else {
conversation = conversations[newIndex];
}
}
return conversation ? { conversationId: conversation.id } : undefined;
};