diff --git a/front/src/AppNavbar.tsx b/front/src/AppNavbar.tsx
index 218d941da..2bbfb4b29 100644
--- a/front/src/AppNavbar.tsx
+++ b/front/src/AppNavbar.tsx
@@ -1,6 +1,7 @@
import { useLocation } from 'react-router-dom';
import { useTheme } from '@emotion/react';
+import { useCommandMenu } from '@/command-menu/hooks/useCommandMenu';
import { SettingsNavbar } from '@/settings/components/SettingsNavbar';
import {
IconBuildingSkyscraper,
@@ -19,6 +20,7 @@ import NavTitle from './modules/ui/layout/navbar/NavTitle';
export function AppNavbar() {
const theme = useTheme();
const currentPath = useLocation().pathname;
+ const { openCommandMenu } = useCommandMenu();
const isSubNavbarDisplayed = useIsSubNavbarDisplayed();
@@ -29,9 +31,10 @@ export function AppNavbar() {
<>
}
- soon={true}
+ onClick={() => {
+ openCommandMenu();
+ }}
/>
{
- handleOpenChange(!open);
+ openCommandMenu();
},
AppHotkeyScope.CommandMenu,
- [setOpen, open, handleOpenChange],
+ [openCommandMenu],
);
- const {
- setHotkeyScopeAndMemorizePreviousScope,
- goBackToPreviousHotkeyScope,
- } = usePreviousHotkeyScope();
-
- function handleOpenChange(newOpenState: boolean) {
- if (newOpenState) {
- setOpen(true);
- setHotkeyScopeAndMemorizePreviousScope(AppHotkeyScope.CommandMenu);
- } else {
- setOpen(false);
- goBackToPreviousHotkeyScope();
- }
- }
+ const people = useFilteredSearchPeopleQuery({
+ searchFilter: search,
+ selectedIds: [],
+ limit: 3,
+ });
+ const companies = useFilteredSearchCompanyQuery({
+ searchFilter: search,
+ selectedIds: [],
+ limit: 3,
+ });
/*
TODO: Allow performing actions on page through CommandBar
@@ -79,15 +82,64 @@ export function CommandMenu() {
);*/
+ const theme = useTheme();
+
return (
{
+ if (!opened) {
+ closeCommandMenu();
+ }
+ }}
label="Global Command Menu"
+ shouldFilter={false}
>
-
+
No results found.
+ {!!people.entitiesToSelect.length && (
+
+ {people.entitiesToSelect.map((person) => (
+
+ }
+ />
+ ))}
+
+ )}
+ {!!companies.entitiesToSelect.length && (
+
+ {companies.entitiesToSelect.map((company) => (
+
+ }
+ />
+ ))}
+
+ )}
;
}
const onItemClick = () => {
- setOpen(false);
+ closeCommandMenu();
if (onClick) {
onClick();
diff --git a/front/src/modules/command-menu/components/CommandMenuStyles.tsx b/front/src/modules/command-menu/components/CommandMenuStyles.tsx
index bef2b483a..44cb3a947 100644
--- a/front/src/modules/command-menu/components/CommandMenuStyles.tsx
+++ b/front/src/modules/command-menu/components/CommandMenuStyles.tsx
@@ -12,8 +12,8 @@ export const StyledDialog = styled(Command.Dialog)`
padding: 0;
padding: ${({ theme }) => theme.spacing(1)};
position: fixed;
- top: 50%;
- transform: translate(-50%, -50%);
+ top: 30%;
+ transform: translateX(-50%);
width: 100%;
z-index: 1000;
`;
diff --git a/front/src/modules/command-menu/hooks/useCommandMenu.ts b/front/src/modules/command-menu/hooks/useCommandMenu.ts
new file mode 100644
index 000000000..ace3ddd7d
--- /dev/null
+++ b/front/src/modules/command-menu/hooks/useCommandMenu.ts
@@ -0,0 +1,31 @@
+import { useRecoilState } from 'recoil';
+
+import { usePreviousHotkeyScope } from '@/lib/hotkeys/hooks/usePreviousHotkeyScope';
+import { AppHotkeyScope } from '@/lib/hotkeys/types/AppHotkeyScope';
+
+import { isCommandMenuOpenedState } from '../states/isCommandMenuOpenedState';
+
+export function useCommandMenu() {
+ const [, setIsCommandMenuOpenedState] = useRecoilState(
+ isCommandMenuOpenedState,
+ );
+ const {
+ setHotkeyScopeAndMemorizePreviousScope,
+ goBackToPreviousHotkeyScope,
+ } = usePreviousHotkeyScope();
+
+ function openCommandMenu() {
+ setIsCommandMenuOpenedState(true);
+ setHotkeyScopeAndMemorizePreviousScope(AppHotkeyScope.CommandMenu);
+ }
+
+ function closeCommandMenu() {
+ setIsCommandMenuOpenedState(false);
+ goBackToPreviousHotkeyScope();
+ }
+
+ return {
+ openCommandMenu,
+ closeCommandMenu,
+ };
+}
diff --git a/front/src/modules/command-menu/states/isCommandMenuOpened.ts b/front/src/modules/command-menu/states/isCommandMenuOpenedState.ts
similarity index 100%
rename from front/src/modules/command-menu/states/isCommandMenuOpened.ts
rename to front/src/modules/command-menu/states/isCommandMenuOpenedState.ts
diff --git a/front/src/modules/comments/components/comment-thread/CommentThreadRelationPicker.tsx b/front/src/modules/comments/components/comment-thread/CommentThreadRelationPicker.tsx
index 2b3516f34..50802e142 100644
--- a/front/src/modules/comments/components/comment-thread/CommentThreadRelationPicker.tsx
+++ b/front/src/modules/comments/components/comment-thread/CommentThreadRelationPicker.tsx
@@ -9,24 +9,21 @@ import {
} from '@floating-ui/react';
import { useHandleCheckableCommentThreadTargetChange } from '@/comments/hooks/useHandleCheckableCommentThreadTargetChange';
-import { CommentableEntityForSelect } from '@/comments/types/CommentableEntityForSelect';
import { CompanyChip } from '@/companies/components/CompanyChip';
+import { useFilteredSearchCompanyQuery } from '@/companies/services';
import { usePreviousHotkeyScope } from '@/lib/hotkeys/hooks/usePreviousHotkeyScope';
import { useScopedHotkeys } from '@/lib/hotkeys/hooks/useScopedHotkeys';
import { PersonChip } from '@/people/components/PersonChip';
+import { useFilteredSearchPeopleQuery } from '@/people/services';
import { RecoilScope } from '@/recoil-scope/components/RecoilScope';
import { MultipleEntitySelect } from '@/relation-picker/components/MultipleEntitySelect';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
import { RelationPickerHotkeyScope } from '@/relation-picker/types/RelationPickerHotkeyScope';
import { useListenClickOutsideArrayOfRef } from '@/ui/hooks/useListenClickOutsideArrayOfRef';
import { flatMapAndSortEntityForSelectArrayOfArrayByName } from '@/ui/utils/flatMapAndSortEntityForSelectArrayByName';
-import { getLogoUrlFromDomainName } from '@/utils/utils';
import {
CommentableType,
CommentThread,
CommentThreadTarget,
- useSearchCompanyQuery,
- useSearchPeopleQuery,
} from '~/generated/graphql';
type OwnProps = {
@@ -90,35 +87,14 @@ export function CommentThreadRelationPicker({ commentThread }: OwnProps) {
?.filter((relation) => relation.commentableType === 'Company')
.map((relation) => relation.commentableId) ?? [];
- const personsForMultiSelect = useFilteredSearchEntityQuery({
- queryHook: useSearchPeopleQuery,
- searchOnFields: ['firstName', 'lastName'],
- orderByField: 'lastName',
- selectedIds: peopleIds,
- mappingFunction: (entity) =>
- ({
- id: entity.id,
- entityType: CommentableType.Person,
- name: `${entity.firstName} ${entity.lastName}`,
- avatarType: 'rounded',
- } as CommentableEntityForSelect),
+ const personsForMultiSelect = useFilteredSearchPeopleQuery({
searchFilter,
+ selectedIds: peopleIds,
});
- const companiesForMultiSelect = useFilteredSearchEntityQuery({
- queryHook: useSearchCompanyQuery,
- searchOnFields: ['name'],
- orderByField: 'name',
- selectedIds: companyIds,
- mappingFunction: (company) =>
- ({
- id: company.id,
- entityType: CommentableType.Company,
- name: company.name,
- avatarUrl: getLogoUrlFromDomainName(company.domainName),
- avatarType: 'squared',
- } as CommentableEntityForSelect),
+ const companiesForMultiSelect = useFilteredSearchCompanyQuery({
searchFilter,
+ selectedIds: companyIds,
});
const {
diff --git a/front/src/modules/companies/components/CompanyAccountOwnerPicker.tsx b/front/src/modules/companies/components/CompanyAccountOwnerPicker.tsx
index f4286142a..2e53b50f7 100644
--- a/front/src/modules/companies/components/CompanyAccountOwnerPicker.tsx
+++ b/front/src/modules/companies/components/CompanyAccountOwnerPicker.tsx
@@ -1,9 +1,9 @@
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { SingleEntitySelect } from '@/relation-picker/components/SingleEntitySelect';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
import { relationPickerSearchFilterScopedState } from '@/relation-picker/states/relationPickerSearchFilterScopedState';
import { EntityForSelect } from '@/relation-picker/types/EntityForSelect';
import { Entity } from '@/relation-picker/types/EntityTypeForSelect';
+import { useFilteredSearchEntityQuery } from '@/search/hooks/useFilteredSearchEntityQuery';
import { useEditableCell } from '@/ui/components/editable-cell/hooks/useEditableCell';
import {
Company,
diff --git a/front/src/modules/companies/components/FilterDropdownCompanySearchSelect.tsx b/front/src/modules/companies/components/FilterDropdownCompanySearchSelect.tsx
index 21ee171b8..b3db8c4bc 100644
--- a/front/src/modules/companies/components/FilterDropdownCompanySearchSelect.tsx
+++ b/front/src/modules/companies/components/FilterDropdownCompanySearchSelect.tsx
@@ -3,11 +3,9 @@ import { filterDropdownSearchInputScopedState } from '@/lib/filters-and-sorts/st
import { filterDropdownSelectedEntityIdScopedState } from '@/lib/filters-and-sorts/states/filterDropdownSelectedEntityIdScopedState';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { useRecoilScopedValue } from '@/recoil-scope/hooks/useRecoilScopedValue';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
-import { Entity } from '@/relation-picker/types/EntityTypeForSelect';
import { TableContext } from '@/ui/tables/states/TableContext';
-import { getLogoUrlFromDomainName } from '@/utils/utils';
-import { useSearchCompanyQuery } from '~/generated/graphql';
+
+import { useFilteredSearchCompanyQuery } from '../services';
export function FilterDropdownCompanySearchSelect() {
const filterDropdownSearchInput = useRecoilScopedValue(
@@ -20,21 +18,11 @@ export function FilterDropdownCompanySearchSelect() {
TableContext,
);
- const usersForSelect = useFilteredSearchEntityQuery({
- queryHook: useSearchCompanyQuery,
- searchOnFields: ['name'],
- orderByField: 'name',
+ const usersForSelect = useFilteredSearchCompanyQuery({
+ searchFilter: filterDropdownSearchInput,
selectedIds: filterDropdownSelectedEntityId
? [filterDropdownSelectedEntityId]
: [],
- mappingFunction: (company) => ({
- id: company.id,
- entityType: Entity.User,
- name: `${company.name}`,
- avatarType: 'squared',
- avatarUrl: getLogoUrlFromDomainName(company.domainName),
- }),
- searchFilter: filterDropdownSearchInput,
});
return (
diff --git a/front/src/modules/companies/components/NewCompanyBoardCard.tsx b/front/src/modules/companies/components/NewCompanyBoardCard.tsx
index b048ef908..4e4ed04a2 100644
--- a/front/src/modules/companies/components/NewCompanyBoardCard.tsx
+++ b/front/src/modules/companies/components/NewCompanyBoardCard.tsx
@@ -2,31 +2,16 @@ import { useCallback } from 'react';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { SingleEntitySelect } from '@/relation-picker/components/SingleEntitySelect';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
import { relationPickerSearchFilterScopedState } from '@/relation-picker/states/relationPickerSearchFilterScopedState';
-import { getLogoUrlFromDomainName } from '@/utils/utils';
-import { CommentableType, useSearchCompanyQuery } from '~/generated/graphql';
+
+import { useFilteredSearchCompanyQuery } from '../services';
export function NewCompanyBoardCard() {
const [searchFilter] = useRecoilScopedState(
relationPickerSearchFilterScopedState,
);
- const companies = useFilteredSearchEntityQuery({
- queryHook: useSearchCompanyQuery,
- selectedIds: [],
- searchFilter: searchFilter,
- mappingFunction: (company) => ({
- entityType: CommentableType.Company,
- id: company.id,
- name: company.name,
- domainName: company.domainName,
- avatarType: 'squared',
- avatarUrl: getLogoUrlFromDomainName(company.domainName),
- }),
- orderByField: 'name',
- searchOnFields: ['name'],
- });
+ const companies = useFilteredSearchCompanyQuery({ searchFilter });
const handleEntitySelect = useCallback(async (companyId: string) => {
return;
diff --git a/front/src/modules/companies/components/NewCompanyProgressButton.tsx b/front/src/modules/companies/components/NewCompanyProgressButton.tsx
index bebbe6233..25132bb41 100644
--- a/front/src/modules/companies/components/NewCompanyProgressButton.tsx
+++ b/front/src/modules/companies/components/NewCompanyProgressButton.tsx
@@ -11,20 +11,18 @@ import { pipelineStageIdScopedState } from '@/pipeline-progress/states/pipelineS
import { RecoilScope } from '@/recoil-scope/components/RecoilScope';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { SingleEntitySelect } from '@/relation-picker/components/SingleEntitySelect';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
import { relationPickerSearchFilterScopedState } from '@/relation-picker/states/relationPickerSearchFilterScopedState';
import { RelationPickerHotkeyScope } from '@/relation-picker/types/RelationPickerHotkeyScope';
import { BoardPipelineStageColumn } from '@/ui/board/components/Board';
import { NewButton } from '@/ui/board/components/NewButton';
-import { getLogoUrlFromDomainName } from '@/utils/utils';
import {
- CommentableType,
PipelineProgressableType,
useCreateOnePipelineProgressMutation,
- useSearchCompanyQuery,
} from '~/generated/graphql';
import { currentPipelineState } from '~/pages/opportunities/currentPipelineState';
+import { useFilteredSearchCompanyQuery } from '../services';
+
export function NewCompanyProgressButton() {
const [isCreatingCard, setIsCreatingCard] = useState(false);
const [board, setBoard] = useRecoilState(boardState);
@@ -93,21 +91,7 @@ export function NewCompanyProgressButton() {
const [searchFilter] = useRecoilScopedState(
relationPickerSearchFilterScopedState,
);
- const companies = useFilteredSearchEntityQuery({
- queryHook: useSearchCompanyQuery,
- selectedIds: [],
- searchFilter: searchFilter,
- mappingFunction: (company) => ({
- entityType: CommentableType.Company,
- id: company.id,
- name: company.name,
- domainName: company.domainName,
- avatarType: 'squared',
- avatarUrl: getLogoUrlFromDomainName(company.domainName),
- }),
- orderByField: 'name',
- searchOnFields: ['name'],
- });
+ const companies = useFilteredSearchCompanyQuery({ searchFilter });
return (
<>
diff --git a/front/src/modules/companies/services/select.ts b/front/src/modules/companies/services/select.ts
index 637eb1bd9..71c916e50 100644
--- a/front/src/modules/companies/services/select.ts
+++ b/front/src/modules/companies/services/select.ts
@@ -1,11 +1,16 @@
import { gql } from '@apollo/client';
+import { CommentableEntityForSelect } from '@/comments/types/CommentableEntityForSelect';
import { SelectedSortType } from '@/lib/filters-and-sorts/interfaces/sorts/interface';
+import { useFilteredSearchEntityQuery } from '@/search/hooks/useFilteredSearchEntityQuery';
+import { getLogoUrlFromDomainName } from '@/utils/utils';
import {
+ CommentableType,
CompanyOrderByWithRelationInput as Companies_Order_By,
CompanyWhereInput as Companies_Bool_Exp,
SortOrder as Order_By,
useGetCompaniesQuery,
+ useSearchCompanyQuery,
} from '~/generated/graphql';
export type CompaniesSelectedSortType = SelectedSortType;
@@ -41,6 +46,33 @@ export function useCompaniesQuery(
return useGetCompaniesQuery({ variables: { orderBy, where } });
}
+export function useFilteredSearchCompanyQuery({
+ searchFilter,
+ selectedIds = [],
+ limit,
+}: {
+ searchFilter: string;
+ selectedIds?: string[];
+ limit?: number;
+}) {
+ return useFilteredSearchEntityQuery({
+ queryHook: useSearchCompanyQuery,
+ searchOnFields: ['name'],
+ orderByField: 'name',
+ selectedIds: selectedIds,
+ mappingFunction: (company) =>
+ ({
+ id: company.id,
+ entityType: CommentableType.Company,
+ name: company.name,
+ avatarUrl: getLogoUrlFromDomainName(company.domainName),
+ avatarType: 'squared',
+ } as CommentableEntityForSelect),
+ searchFilter,
+ limit,
+ });
+}
+
export const defaultOrderBy: Companies_Order_By[] = [
{
createdAt: Order_By.Desc,
diff --git a/front/src/modules/people/components/PeopleCompanyPicker.tsx b/front/src/modules/people/components/PeopleCompanyPicker.tsx
index 0d1fdc101..6696dc391 100644
--- a/front/src/modules/people/components/PeopleCompanyPicker.tsx
+++ b/front/src/modules/people/components/PeopleCompanyPicker.tsx
@@ -1,23 +1,16 @@
import { Key } from 'ts-key-enum';
+import { useFilteredSearchCompanyQuery } from '@/companies/services';
import { useScopedHotkeys } from '@/lib/hotkeys/hooks/useScopedHotkeys';
import { useSetHotkeyScope } from '@/lib/hotkeys/hooks/useSetHotkeyScope';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { SingleEntitySelect } from '@/relation-picker/components/SingleEntitySelect';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
import { relationPickerSearchFilterScopedState } from '@/relation-picker/states/relationPickerSearchFilterScopedState';
import { RelationPickerHotkeyScope } from '@/relation-picker/types/RelationPickerHotkeyScope';
import { useEditableCell } from '@/ui/components/editable-cell/hooks/useEditableCell';
import { isCreateModeScopedState } from '@/ui/components/editable-cell/states/isCreateModeScopedState';
import { TableHotkeyScope } from '@/ui/tables/types/TableHotkeyScope';
-import { getLogoUrlFromDomainName } from '@/utils/utils';
-import {
- CommentableType,
- Company,
- Person,
- useSearchCompanyQuery,
- useUpdatePeopleMutation,
-} from '~/generated/graphql';
+import { Company, Person, useUpdatePeopleMutation } from '~/generated/graphql';
export type OwnProps = {
people: Pick & { company?: Pick | null };
@@ -35,19 +28,9 @@ export function PeopleCompanyPicker({ people }: OwnProps) {
const addToScopeStack = useSetHotkeyScope();
- const companies = useFilteredSearchEntityQuery({
- queryHook: useSearchCompanyQuery,
- selectedIds: [people.company?.id ?? ''],
- searchFilter: searchFilter,
- mappingFunction: (company) => ({
- entityType: CommentableType.Company,
- id: company.id,
- name: company.name,
- avatarType: 'squared',
- avatarUrl: getLogoUrlFromDomainName(company.domainName),
- }),
- orderByField: 'name',
- searchOnFields: ['name'],
+ const companies = useFilteredSearchCompanyQuery({
+ searchFilter,
+ selectedIds: people.company?.id ? [people.company.id] : [],
});
async function handleEntitySelected(entity: any) {
diff --git a/front/src/modules/people/services/select.ts b/front/src/modules/people/services/select.ts
index 76c84c9b4..7e31b9144 100644
--- a/front/src/modules/people/services/select.ts
+++ b/front/src/modules/people/services/select.ts
@@ -1,11 +1,15 @@
import { gql } from '@apollo/client';
+import { CommentableEntityForSelect } from '@/comments/types/CommentableEntityForSelect';
import { SelectedSortType } from '@/lib/filters-and-sorts/interfaces/sorts/interface';
+import { useFilteredSearchEntityQuery } from '@/search/hooks/useFilteredSearchEntityQuery';
import {
+ CommentableType,
PersonOrderByWithRelationInput as People_Order_By,
PersonWhereInput as People_Bool_Exp,
SortOrder,
useGetPeopleQuery,
+ useSearchPeopleQuery,
} from '~/generated/graphql';
export type PeopleSelectedSortType = SelectedSortType;
@@ -43,6 +47,32 @@ export function usePeopleQuery(
});
}
+export function useFilteredSearchPeopleQuery({
+ searchFilter,
+ selectedIds = [],
+ limit,
+}: {
+ searchFilter: string;
+ selectedIds?: string[];
+ limit?: number;
+}) {
+ return useFilteredSearchEntityQuery({
+ queryHook: useSearchPeopleQuery,
+ searchOnFields: ['firstName', 'lastName'],
+ orderByField: 'lastName',
+ selectedIds: selectedIds,
+ mappingFunction: (entity) =>
+ ({
+ id: entity.id,
+ entityType: CommentableType.Person,
+ name: `${entity.firstName} ${entity.lastName}`,
+ avatarType: 'rounded',
+ } as CommentableEntityForSelect),
+ searchFilter,
+ limit,
+ });
+}
+
export const defaultOrderBy: People_Order_By[] = [
{
createdAt: SortOrder.Desc,
diff --git a/front/src/modules/relation-picker/hooks/useFilteredSearchEntityQuery.ts b/front/src/modules/search/hooks/useFilteredSearchEntityQuery.ts
similarity index 100%
rename from front/src/modules/relation-picker/hooks/useFilteredSearchEntityQuery.ts
rename to front/src/modules/search/hooks/useFilteredSearchEntityQuery.ts
diff --git a/front/src/modules/users/components/FilterDropdownUserSearchSelect.tsx b/front/src/modules/users/components/FilterDropdownUserSearchSelect.tsx
index b91b084b9..aa71d1380 100644
--- a/front/src/modules/users/components/FilterDropdownUserSearchSelect.tsx
+++ b/front/src/modules/users/components/FilterDropdownUserSearchSelect.tsx
@@ -3,8 +3,8 @@ import { filterDropdownSearchInputScopedState } from '@/lib/filters-and-sorts/st
import { filterDropdownSelectedEntityIdScopedState } from '@/lib/filters-and-sorts/states/filterDropdownSelectedEntityIdScopedState';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { useRecoilScopedValue } from '@/recoil-scope/hooks/useRecoilScopedValue';
-import { useFilteredSearchEntityQuery } from '@/relation-picker/hooks/useFilteredSearchEntityQuery';
import { Entity } from '@/relation-picker/types/EntityTypeForSelect';
+import { useFilteredSearchEntityQuery } from '@/search/hooks/useFilteredSearchEntityQuery';
import { TableContext } from '@/ui/tables/states/TableContext';
import { useSearchUserQuery } from '~/generated/graphql';