From 643b547bd0b03fe9abdc5e933d50e2a200966246 Mon Sep 17 00:00:00 2001 From: talksik Date: Sat, 11 Jun 2022 13:50:36 -0500 Subject: [PATCH] nice search and quick dial right there --- .../desktop/src/providers/SearchProvider.tsx | 63 ++++----- .../desktop/src/tree/ConversationList.tsx | 8 +- .../desktop/src/tree/OmniSearchResults.tsx | 131 ++++++++++++++++++ packages/desktop/src/tree/Terminal.tsx | 8 +- 4 files changed, 175 insertions(+), 35 deletions(-) create mode 100644 packages/desktop/src/tree/OmniSearchResults.tsx diff --git a/packages/desktop/src/providers/SearchProvider.tsx b/packages/desktop/src/providers/SearchProvider.tsx index 02244b0..585b458 100644 --- a/packages/desktop/src/providers/SearchProvider.tsx +++ b/packages/desktop/src/providers/SearchProvider.tsx @@ -1,9 +1,10 @@ +import { ConversationMap, MasterConversation } from '../util/types'; import React, { useCallback, useContext, useState } from 'react'; import Conversation from '@nirvana/core/models/conversation.model'; -import { ConversationMap } from '../util/types'; import User from '@nirvana/core/models/user.model'; import useAuth from './AuthProvider'; +import useConversations from './ConversationProvider'; import { useDebounce } from 'react-use'; import { userSearch } from '../api/NirvanaApi'; @@ -12,7 +13,7 @@ interface ISearchContext { omniSearch?: (searchQuery: string) => void; searchConversations?: (searchQuery: string) => void; - conversationResults: Conversation[]; + conversationResults: MasterConversation[]; userResults: User[]; isSearching: boolean; @@ -31,12 +32,12 @@ const SearchContext = React.createContext({ export function SearchProvider({ children }: { children: React.ReactNode }) { const { user } = useAuth(); - // const { conversationMap } = useConversations(); + const { conversationMap } = useConversations(); const [searchQuery, setSearchQuery] = useState(''); const [userResults, setUserResultsResults] = useState([]); - const [conversationResults, setConversationResultsResults] = useState([]); + const [conversationResults, setConversationResultsResults] = useState([]); const [isSearching, setIsSearching] = useState(false); // debounce user search and any other async ones @@ -71,39 +72,39 @@ export function SearchProvider({ children }: { children: React.ReactNode }) { */ const searchRelevantConversations = useCallback( - async (searchQuery: string): Promise => { - const relevantConversations: Conversation[] = []; + async (searchQuery: string): Promise => { + const relevantConversations: MasterConversation[] = []; - // Object.values(conversationMap).forEach((conversation) => { - // for (const cachedConversationUser of conversation.userCache) { - // if ( - // cachedConversationUser.email - // .toLocaleLowerCase() - // .includes(searchQuery.toLocaleLowerCase()) - // ) { - // relevantConversations.push(conversation); - // return; - // } + Object.values(conversationMap).forEach((conversation) => { + for (const cachedConversationUser of conversation.members) { + if ( + cachedConversationUser.email + .toLocaleLowerCase() + .includes(searchQuery.toLocaleLowerCase()) + ) { + relevantConversations.push(conversation); + return; + } - // if ( - // cachedConversationUser.displayName - // .toLocaleLowerCase() - // .includes(searchQuery.toLocaleLowerCase()) - // ) { - // relevantConversations.push(conversation); - // return; - // } - // } + if ( + cachedConversationUser.name + .toLocaleLowerCase() + .includes(searchQuery.toLocaleLowerCase()) + ) { + relevantConversations.push(conversation); + return; + } + } - // if (conversation.name?.toLocaleLowerCase().includes(searchQuery.toLocaleLowerCase())) { - // relevantConversations.push(conversation); - // return; - // } - // }); + if (conversation.name?.toLocaleLowerCase().includes(searchQuery.toLocaleLowerCase())) { + relevantConversations.push(conversation); + return; + } + }); return relevantConversations; }, - [], + [conversationMap], ); const omniSearch = useCallback( diff --git a/packages/desktop/src/tree/ConversationList.tsx b/packages/desktop/src/tree/ConversationList.tsx index ab3754c..40e533f 100644 --- a/packages/desktop/src/tree/ConversationList.tsx +++ b/packages/desktop/src/tree/ConversationList.tsx @@ -106,9 +106,11 @@ export function ConversationList() { export function ConversationRow({ conversation, index, + onClick, }: { conversation: MasterConversation; index?: number; + onClick?: () => void; }) { const { user } = useAuth(); @@ -126,8 +128,12 @@ export function ConversationRow({ }, [index]); const handleSelectConversation = useCallback(() => { + if (onClick) { + onClick(); + } + selectConversation(conversation._id.toString(), false); - }, [conversation, selectConversation]); + }, [conversation, selectConversation, onClick]); useKeyPressEvent(`${keyboardShortcut?.toString()}`, handleSelectConversation); diff --git a/packages/desktop/src/tree/OmniSearchResults.tsx b/packages/desktop/src/tree/OmniSearchResults.tsx new file mode 100644 index 0000000..b4a97c0 --- /dev/null +++ b/packages/desktop/src/tree/OmniSearchResults.tsx @@ -0,0 +1,131 @@ +import { + Avatar, + List, + ListItem, + ListItemAvatar, + ListItemButton, + ListItemSecondaryAction, + ListItemText, + ListSubheader, + Tooltip, + Typography, +} from '@mui/material'; +import React, { useCallback } from 'react'; + +import Conversation from '@nirvana/core/models/conversation.model'; +import { ConversationRow } from './ConversationList'; +import { FiZap } from 'react-icons/fi'; +import User from '@nirvana/core/models/user.model'; +import useConversations from '../providers/ConversationProvider'; +import useSearch from '../providers/SearchProvider'; +import useTerminal from './Terminal'; + +export default function OmniSearchResults() { + const { handleStartConversation } = useConversations(); + + const { userResults: people, conversationResults: conversations, clearSearch } = useSearch(); + + const handleQuickDial = useCallback( + async (otherUser: User) => { + const succeededDialed = await handleStartConversation([otherUser]); + + if (succeededDialed) { + clearSearch(); + } + }, + [handleStartConversation, clearSearch], + ); + + return ( + <> + + + People + + + } + > + + {people.length === 0 && ( + + {`Can't find someone? Invite them!`} + + )} + + + {people.map((person) => ( + + + handleQuickDial(person)}> + + + + + + + + + + + + + ))} + + + + + Conversations + + + } + > + + {conversations.length === 0 && ( + + {`Can't find a conversation? Just create one!`} + + )} + + + {conversations.map((conversation) => ( + + + + ))} + + + ); +} diff --git a/packages/desktop/src/tree/Terminal.tsx b/packages/desktop/src/tree/Terminal.tsx index aecd958..bc65966 100644 --- a/packages/desktop/src/tree/Terminal.tsx +++ b/packages/desktop/src/tree/Terminal.tsx @@ -4,13 +4,17 @@ import { ConversationList } from './ConversationList'; import MainPanel from './MainPanel'; import Navbar from './Navbar'; import NewConversationDialog from './NewConversationDialog'; +import OmniSearchResults from './OmniSearchResults'; import React from 'react'; import { blueGrey } from '@mui/material/colors'; import useRouter from '../providers/RouterProvider'; +import useSearch from '../providers/SearchProvider'; export default function Terminal() { const { page } = useRouter(); + const { searchQuery } = useSearch(); + return ( - - - + {searchQuery ? : }