diff --git a/front/src/modules/companies/hooks/useCompanyTableContextMenuEntries.tsx b/front/src/modules/companies/hooks/useCompanyTableContextMenuEntries.tsx index a70b8d366..5b00cea3b 100644 --- a/front/src/modules/companies/hooks/useCompanyTableContextMenuEntries.tsx +++ b/front/src/modules/companies/hooks/useCompanyTableContextMenuEntries.tsx @@ -11,7 +11,7 @@ import { } from '@/ui/display/icon'; import { actionBarEntriesState } from '@/ui/navigation/action-bar/states/actionBarEntriesState'; import { contextMenuEntriesState } from '@/ui/navigation/context-menu/states/contextMenuEntriesState'; -import { useResetTableRowSelection } from '@/ui/object/record-table/hooks/useResetTableRowSelection'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { selectedRowIdsSelector } from '@/ui/object/record-table/states/selectors/selectedRowIdsSelector'; import { tableRowIdsState } from '@/ui/object/record-table/states/tableRowIdsState'; import { @@ -30,7 +30,9 @@ export const useCompanyTableContextMenuEntries = () => { const createActivityForCompany = useCreateActivityForCompany(); const setTableRowIds = useSetRecoilState(tableRowIdsState); - const resetRowSelection = useResetTableRowSelection(); + const { resetTableRowSelection } = useRecordTable({ + recordTableScopeId: 'companies', + }); const { data } = useGetFavoritesQuery(); const favorites = data?.findFavorites; @@ -50,7 +52,7 @@ export const useCompanyTableContextMenuEntries = () => { (favorite) => favorite.company?.id === selectedCompanyId, ); - resetRowSelection(); + resetTableRowSelection(); if (isFavorite) deleteCompanyFavorite(selectedCompanyId); else insertCompanyFavorite(selectedCompanyId); }); @@ -64,7 +66,7 @@ export const useCompanyTableContextMenuEntries = () => { .getLoadable(selectedRowIdsSelector) .getValue(); - resetRowSelection(); + resetTableRowSelection(); await deleteManyCompany({ variables: { diff --git a/front/src/modules/companies/hooks/useDeleteCompanies.ts b/front/src/modules/companies/hooks/useDeleteCompanies.ts deleted file mode 100644 index f94216e9b..000000000 --- a/front/src/modules/companies/hooks/useDeleteCompanies.ts +++ /dev/null @@ -1,57 +0,0 @@ -import { getOperationName } from '@apollo/client/utilities'; -import { useRecoilState, useRecoilValue } from 'recoil'; - -import { useOptimisticEvict } from '@/apollo/optimistic-effect/hooks/useOptimisticEvict'; -import { GET_PIPELINES } from '@/pipeline/graphql/queries/getPipelines'; -import { useResetTableRowSelection } from '@/ui/object/record-table/hooks/useResetTableRowSelection'; -import { selectedRowIdsSelector } from '@/ui/object/record-table/states/selectors/selectedRowIdsSelector'; -import { tableRowIdsState } from '@/ui/object/record-table/states/tableRowIdsState'; -import { useDeleteManyCompaniesMutation } from '~/generated/graphql'; - -export const useDeleteSelectedComapnies = () => { - const selectedRowIds = useRecoilValue(selectedRowIdsSelector); - - const resetRowSelection = useResetTableRowSelection(); - - const [deleteCompanies] = useDeleteManyCompaniesMutation({ - refetchQueries: [getOperationName(GET_PIPELINES) ?? ''], - }); - const { performOptimisticEvict } = useOptimisticEvict(); - - const [tableRowIds, setTableRowIds] = useRecoilState(tableRowIdsState); - - const deleteSelectedCompanies = async () => { - const rowIdsToDelete = selectedRowIds; - - resetRowSelection(); - - await deleteCompanies({ - variables: { - ids: rowIdsToDelete, - }, - optimisticResponse: { - __typename: 'Mutation', - deleteManyCompany: { - count: rowIdsToDelete.length, - }, - }, - update: (cache) => { - setTableRowIds( - tableRowIds.filter((id) => !rowIdsToDelete.includes(id)), - ); - - rowIdsToDelete.forEach((companyId) => { - cache.evict({ - id: cache.identify({ __typename: 'Company', id: companyId }), - }); - - performOptimisticEvict('PipelineProgress', 'companyId', companyId); - - cache.gc(); - }); - }, - }); - }; - - return deleteSelectedCompanies; -}; diff --git a/front/src/modules/companies/table/components/CompanyTable.tsx b/front/src/modules/companies/table/components/CompanyTable.tsx index 9527da379..522a5a08f 100644 --- a/front/src/modules/companies/table/components/CompanyTable.tsx +++ b/front/src/modules/companies/table/components/CompanyTable.tsx @@ -1,5 +1,5 @@ import styled from '@emotion/styled'; -import { useRecoilCallback, useSetRecoilState } from 'recoil'; +import { useRecoilCallback } from 'recoil'; import { companiesAvailableFieldDefinitions } from '@/companies/constants/companiesAvailableFieldDefinitions'; import { getCompaniesOptimisticEffectDefinition } from '@/companies/graphql/optimistic-effect-definitions/getCompaniesOptimisticEffectDefinition'; @@ -8,14 +8,12 @@ import { useSpreadsheetCompanyImport } from '@/companies/hooks/useSpreadsheetCom import { RecordTable } from '@/ui/object/record-table/components/RecordTable'; import { RecordTableEffect } from '@/ui/object/record-table/components/RecordTableEffect'; import { TableOptionsDropdownId } from '@/ui/object/record-table/constants/TableOptionsDropdownId'; -import { TableContext } from '@/ui/object/record-table/contexts/TableContext'; -import { useUpsertRecordTableItem } from '@/ui/object/record-table/hooks/useUpsertRecordTableItem'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { TableOptionsDropdown } from '@/ui/object/record-table/options/components/TableOptionsDropdown'; -import { tableColumnsScopedState } from '@/ui/object/record-table/states/tableColumnsScopedState'; -import { tableFiltersScopedState } from '@/ui/object/record-table/states/tableFiltersScopedState'; -import { tableSortsScopedState } from '@/ui/object/record-table/states/tableSortsScopedState'; +import { RecordTableScope } from '@/ui/object/record-table/scopes/RecordTableScope'; import { ViewBar } from '@/views/components/ViewBar'; import { useViewFields } from '@/views/hooks/internal/useViewFields'; +import { useView } from '@/views/hooks/useView'; import { ViewScope } from '@/views/scopes/ViewScope'; import { mapColumnDefinitionsToViewFields } from '@/views/utils/mapColumnDefinitionToViewField'; import { mapViewFieldsToColumnDefinitions } from '@/views/utils/mapViewFieldsToColumnDefinitions'; @@ -42,21 +40,21 @@ const StyledContainer = styled.div` export const CompanyTable = () => { const viewScopeId = 'company-table-view'; const tableScopeId = 'companies'; - const setTableColumns = useSetRecoilState( - tableColumnsScopedState(tableScopeId), - ); - const setTableFilters = useSetRecoilState( - tableFiltersScopedState(tableScopeId), - ); - - const setTableSorts = useSetRecoilState(tableSortsScopedState(tableScopeId)); + const { + setTableFilters, + setTableSorts, + setTableColumns, + upsertRecordTableItem, + } = useRecordTable({ + recordTableScopeId: tableScopeId, + }); const [updateEntityMutation] = useUpdateOneCompanyMutation(); - const upsertRecordTableItem = useUpsertRecordTableItem(); const [getWorkspaceMember] = useGetWorkspaceMembersLazyQuery(); const { persistViewFields } = useViewFields(viewScopeId); + const { setEntityCountInCurrentView } = useView({ viewScopeId }); const { setContextMenuEntries, setActionBarEntries } = useCompanyTableContextMenuEntries(); @@ -112,12 +110,14 @@ export const CompanyTable = () => { }} > - (columns) => { - persistViewFields(mapColumnDefinitionsToViewFields(columns)); - }), - }} + (columns) => { + persistViewFields(mapColumnDefinitionsToViewFields(columns)); + })} + onEntityCountChange={useRecoilCallback(() => (entityCount) => { + setEntityCountInCurrentView(entityCount); + })} > } @@ -142,7 +142,7 @@ export const CompanyTable = () => { variables: UpdateOneCompanyMutationVariables; }) => updateCompany(variables)} /> - + ); diff --git a/front/src/modules/companies/table/components/CompanyTableEffect.tsx b/front/src/modules/companies/table/components/CompanyTableEffect.tsx index f88b8d90e..e04033421 100644 --- a/front/src/modules/companies/table/components/CompanyTableEffect.tsx +++ b/front/src/modules/companies/table/components/CompanyTableEffect.tsx @@ -1,9 +1,7 @@ import { useEffect } from 'react'; import { companiesAvailableFieldDefinitions } from '@/companies/constants/companiesAvailableFieldDefinitions'; -import { availableTableColumnsScopedState } from '@/ui/object/record-table/states/availableTableColumnsScopedState'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { useRecoilScopedState } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedState'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { useView } from '@/views/hooks/useView'; import { ViewType } from '@/views/types/ViewType'; import { companyTableFilterDefinitions } from '~/pages/companies/constants/companyTableFilterDefinitions'; @@ -18,10 +16,7 @@ const CompanyTableEffect = () => { setViewObjectId, } = useView(); - const [, setAvailableTableColumns] = useRecoilScopedState( - availableTableColumnsScopedState, - TableRecoilScopeContext, - ); + const { setAvailableTableColumns } = useRecordTable(); useEffect(() => { setAvailableSortDefinitions?.(companyTableSortDefinitions); diff --git a/front/src/modules/companies/table/components/CompanyTableMockDataEffect.tsx b/front/src/modules/companies/table/components/CompanyTableMockDataEffect.tsx index e75201d2d..b71462416 100644 --- a/front/src/modules/companies/table/components/CompanyTableMockDataEffect.tsx +++ b/front/src/modules/companies/table/components/CompanyTableMockDataEffect.tsx @@ -1,19 +1,12 @@ import { useEffect } from 'react'; import { companiesAvailableFieldDefinitions } from '@/companies/constants/companiesAvailableFieldDefinitions'; -import { useSetRecordTableData } from '@/ui/object/record-table/hooks/useSetRecordTableData'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { tableColumnsScopedState } from '@/ui/object/record-table/states/tableColumnsScopedState'; -import { useRecoilScopedState } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedState'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { mockedCompaniesData } from './companies-mock-data'; export const CompanyTableMockDataEffect = () => { - const [, setTableColumns] = useRecoilScopedState( - tableColumnsScopedState, - TableRecoilScopeContext, - ); - const setRecordTableData = useSetRecordTableData(); + const { setRecordTableData, setTableColumns } = useRecordTable(); useEffect(() => { setRecordTableData(mockedCompaniesData); diff --git a/front/src/modules/companies/table/components/CompanyTableMockMode.tsx b/front/src/modules/companies/table/components/CompanyTableMockMode.tsx index 28ae7fad6..09a033e3c 100644 --- a/front/src/modules/companies/table/components/CompanyTableMockMode.tsx +++ b/front/src/modules/companies/table/components/CompanyTableMockMode.tsx @@ -3,6 +3,7 @@ import styled from '@emotion/styled'; import { RecordTable } from '@/ui/object/record-table/components/RecordTable'; import { TableOptionsDropdownId } from '@/ui/object/record-table/constants/TableOptionsDropdownId'; import { TableOptionsDropdown } from '@/ui/object/record-table/options/components/TableOptionsDropdown'; +import { RecordTableScope } from '@/ui/object/record-table/scopes/RecordTableScope'; import { ViewBar } from '@/views/components/ViewBar'; import { ViewScope } from '@/views/scopes/ViewScope'; import { useUpdateOneCompanyMutation } from '~/generated/graphql'; @@ -21,14 +22,20 @@ export const CompanyTableMockMode = () => { return ( - - - } - optionsDropdownScopeId={TableOptionsDropdownId} - /> + {}} + onEntityCountChange={() => {}} + > + + + } + optionsDropdownScopeId={TableOptionsDropdownId} + /> - + + ); diff --git a/front/src/modules/metadata/components/RecordTableContainer.tsx b/front/src/modules/metadata/components/RecordTableContainer.tsx index 1e21fba6c..8a63d1e68 100644 --- a/front/src/modules/metadata/components/RecordTableContainer.tsx +++ b/front/src/modules/metadata/components/RecordTableContainer.tsx @@ -1,22 +1,21 @@ import styled from '@emotion/styled'; -import { useRecoilCallback, useSetRecoilState } from 'recoil'; +import { useRecoilCallback } from 'recoil'; import { RecordTable } from '@/ui/object/record-table/components/RecordTable'; import { TableOptionsDropdownId } from '@/ui/object/record-table/constants/TableOptionsDropdownId'; -import { TableContext } from '@/ui/object/record-table/contexts/TableContext'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { TableOptionsDropdown } from '@/ui/object/record-table/options/components/TableOptionsDropdown'; -import { tableColumnsScopedState } from '@/ui/object/record-table/states/tableColumnsScopedState'; -import { tableFiltersScopedState } from '@/ui/object/record-table/states/tableFiltersScopedState'; -import { tableSortsScopedState } from '@/ui/object/record-table/states/tableSortsScopedState'; +import { RecordTableScope } from '@/ui/object/record-table/scopes/RecordTableScope'; import { ViewBar } from '@/views/components/ViewBar'; import { useViewFields } from '@/views/hooks/internal/useViewFields'; +import { useView } from '@/views/hooks/useView'; import { ViewScope } from '@/views/scopes/ViewScope'; import { mapColumnDefinitionsToViewFields } from '@/views/utils/mapColumnDefinitionToViewField'; import { mapViewFieldsToColumnDefinitions } from '@/views/utils/mapViewFieldsToColumnDefinitions'; import { mapViewFiltersToFilters } from '@/views/utils/mapViewFiltersToFilters'; import { mapViewSortsToSorts } from '@/views/utils/mapViewSortsToSorts'; -import { useObjectMetadataItemInContext } from '../hooks/useObjectMetadataItemInContext'; +import { useFindOneObjectMetadataItem } from '../hooks/useFindOneObjectMetadataItem'; import { useUpdateOneObject } from '../hooks/useUpdateOneObject'; import { RecordTableEffect } from './RecordTableEffect'; @@ -28,28 +27,29 @@ const StyledContainer = styled.div` overflow: auto; `; -export const RecordTableContainer = () => { - const { columnDefinitions, foundObjectMetadataItem, objectNamePlural } = - useObjectMetadataItemInContext(); +export const RecordTableContainer = ({ + objectNamePlural, +}: { + objectNamePlural: string; +}) => { + const { columnDefinitions } = useFindOneObjectMetadataItem({ + objectNamePlural, + }); const { updateOneObject } = useUpdateOneObject({ objectNamePlural, }); - const tableScopeId = foundObjectMetadataItem?.namePlural ?? ''; + const tableScopeId = objectNamePlural ?? ''; const viewScopeId = objectNamePlural ?? ''; const { persistViewFields } = useViewFields(viewScopeId); - const setTableColumns = useSetRecoilState( - tableColumnsScopedState(tableScopeId), - ); + const { setTableFilters, setTableSorts, setTableColumns } = useRecordTable({ + recordTableScopeId: tableScopeId, + }); - const setTableFilters = useSetRecoilState( - tableFiltersScopedState(tableScopeId), - ); - - const setTableSorts = useSetRecoilState(tableSortsScopedState(tableScopeId)); + const { setEntityCountInCurrentView } = useView({ viewScopeId }); const updateEntity = ({ variables, @@ -83,11 +83,13 @@ export const RecordTableContainer = () => { }} > - (columns) => { - persistViewFields(mapColumnDefinitionsToViewFields(columns)); - }), + (columns) => { + persistViewFields(mapColumnDefinitionsToViewFields(columns)); + })} + onEntityCountChange={(entityCount) => { + setEntityCountInCurrentView(entityCount); }} > { /> - + ); diff --git a/front/src/modules/metadata/components/RecordTableEffect.tsx b/front/src/modules/metadata/components/RecordTableEffect.tsx index 90ddde0e4..4e3cf803c 100644 --- a/front/src/modules/metadata/components/RecordTableEffect.tsx +++ b/front/src/modules/metadata/components/RecordTableEffect.tsx @@ -1,29 +1,27 @@ import { useEffect } from 'react'; -import { useSetRecoilState } from 'recoil'; +import { useRecoilValue } from 'recoil'; import { turnFiltersIntoWhereClauseV2 } from '@/ui/object/object-filter-dropdown/utils/turnFiltersIntoWhereClauseV2'; import { turnSortsIntoOrderByV2 } from '@/ui/object/object-sort-dropdown/utils/turnSortsIntoOrderByV2'; -import { useSetRecordTableData } from '@/ui/object/record-table/hooks/useSetRecordTableData'; -import { availableTableColumnsScopedState } from '@/ui/object/record-table/states/availableTableColumnsScopedState'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { tableFiltersScopedState } from '@/ui/object/record-table/states/tableFiltersScopedState'; -import { tableSortsScopedState } from '@/ui/object/record-table/states/tableSortsScopedState'; -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; +import { useRecordTableScopedStates } from '@/ui/object/record-table/hooks/internal/useRecordTableScopedStates'; import { useView } from '@/views/hooks/useView'; import { ViewType } from '@/views/types/ViewType'; +import { useRecordTable } from '../../ui/object/record-table/hooks/useRecordTable'; import { useFindManyObjects } from '../hooks/useFindManyObjects'; -import { useObjectMetadataItemInContext } from '../hooks/useObjectMetadataItemInContext'; +import { useFindOneObjectMetadataItem } from '../hooks/useFindOneObjectMetadataItem'; export const RecordTableEffect = () => { + const { scopeId } = useRecordTable(); + const { + foundObjectMetadataItem, columnDefinitions, filterDefinitions, sortDefinitions, - foundObjectMetadataItem, - objectNamePlural, - } = useObjectMetadataItemInContext(); - + } = useFindOneObjectMetadataItem({ + objectNamePlural: scopeId, + }); const { setAvailableSortDefinitions, setAvailableFilterDefinitions, @@ -32,20 +30,15 @@ export const RecordTableEffect = () => { setViewObjectId, } = useView(); - const setRecordTableData = useSetRecordTableData(); + const { setRecordTableData, setAvailableTableColumns } = useRecordTable(); - const tableFilters = useRecoilScopedValue( - tableFiltersScopedState, - TableRecoilScopeContext, - ); + const { tableFiltersState, tableSortsState } = useRecordTableScopedStates(); - const tableSorts = useRecoilScopedValue( - tableSortsScopedState, - TableRecoilScopeContext, - ); + const tableFilters = useRecoilValue(tableFiltersState); + const tableSorts = useRecoilValue(tableSortsState); const { objects, loading } = useFindManyObjects({ - objectNamePlural: objectNamePlural, + objectNamePlural: scopeId, filter: turnFiltersIntoWhereClauseV2( tableFilters, foundObjectMetadataItem?.fields ?? [], @@ -64,12 +57,6 @@ export const RecordTableEffect = () => { } }, [objects, setRecordTableData, loading]); - const tableScopeId = foundObjectMetadataItem?.namePlural ?? ''; - - const setAvailableTableColumns = useSetRecoilState( - availableTableColumnsScopedState(tableScopeId), - ); - useEffect(() => { if (!foundObjectMetadataItem) { return; diff --git a/front/src/modules/metadata/components/RecordTablePage.tsx b/front/src/modules/metadata/components/RecordTablePage.tsx index 49ab9c675..34a0da0a4 100644 --- a/front/src/modules/metadata/components/RecordTablePage.tsx +++ b/front/src/modules/metadata/components/RecordTablePage.tsx @@ -12,12 +12,9 @@ import { PageHeader } from '@/ui/layout/page/PageHeader'; import { PageHotkeysEffect } from '@/ui/layout/page/PageHotkeysEffect'; import { RecordTableActionBar } from '@/ui/object/record-table/action-bar/components/RecordTableActionBar'; import { RecordTableContextMenu } from '@/ui/object/record-table/context-menu/components/RecordTableContextMenu'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope'; import { useCreateOneObject } from '../hooks/useCreateOneObject'; import { useFindOneObjectMetadataItem } from '../hooks/useFindOneObjectMetadataItem'; -import { ObjectMetadataItemScope } from '../scopes/ObjectMetadataItemScope'; const StyledTableContainer = styled.div` display: flex; @@ -59,20 +56,11 @@ export const RecordTablePage = () => { - - - - - - - - - + + + + + ); diff --git a/front/src/modules/metadata/hooks/useObjectMetadataItem.ts b/front/src/modules/metadata/hooks/useObjectMetadataItem.ts deleted file mode 100644 index 58da43f3b..000000000 --- a/front/src/modules/metadata/hooks/useObjectMetadataItem.ts +++ /dev/null @@ -1,18 +0,0 @@ -import { useAvailableScopeIdOrThrow } from '@/ui/utilities/recoil-scope/scopes-internal/hooks/useAvailableScopeId'; - -import { ObjectMetadataItemScopeInternalContext } from '../scopes/scope-internal-context/ObjectMetadataItemScopeInternalContext'; - -type UseObjectMetadataItemProps = { - objectMetadataItemNamePlural?: string; -}; - -export const useObjectMetadataItem = (props?: UseObjectMetadataItemProps) => { - const scopeId = useAvailableScopeIdOrThrow( - ObjectMetadataItemScopeInternalContext, - props?.objectMetadataItemNamePlural, - ); - - return { - scopeId, - }; -}; diff --git a/front/src/modules/metadata/hooks/useObjectMetadataItemInContext.ts b/front/src/modules/metadata/hooks/useObjectMetadataItemInContext.ts deleted file mode 100644 index f3e1f4df3..000000000 --- a/front/src/modules/metadata/hooks/useObjectMetadataItemInContext.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { useContext } from 'react'; - -import { ObjectMetadataItemScopeInternalContext } from '../scopes/scope-internal-context/ObjectMetadataItemScopeInternalContext'; - -import { useFindOneObjectMetadataItem } from './useFindOneObjectMetadataItem'; - -export const useObjectMetadataItemInContext = () => { - const context = useContext(ObjectMetadataItemScopeInternalContext); - - if (!context) { - throw new Error( - 'Could not find ObjectMetadataItemScopeInternalContext while in useObjectMetadataItemInContext', - ); - } - - const { - foundObjectMetadataItem, - loading, - columnDefinitions, - filterDefinitions, - sortDefinitions, - } = useFindOneObjectMetadataItem({ - objectNamePlural: context.objectNamePlural, - }); - - return { - ...context, - foundObjectMetadataItem, - loading, - columnDefinitions, - filterDefinitions, - sortDefinitions, - }; -}; diff --git a/front/src/modules/metadata/hooks/useSetDataTableData.ts b/front/src/modules/metadata/hooks/useSetRecordTableData.ts similarity index 87% rename from front/src/modules/metadata/hooks/useSetDataTableData.ts rename to front/src/modules/metadata/hooks/useSetRecordTableData.ts index 41a03b9b2..a6f0b9272 100644 --- a/front/src/modules/metadata/hooks/useSetDataTableData.ts +++ b/front/src/modules/metadata/hooks/useSetRecordTableData.ts @@ -1,14 +1,14 @@ import { useRecoilCallback } from 'recoil'; import { entityFieldsFamilyState } from '@/ui/object/field/states/entityFieldsFamilyState'; -import { useResetTableRowSelection } from '@/ui/object/record-table/hooks/useResetTableRowSelection'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { isFetchingRecordTableDataState } from '@/ui/object/record-table/states/isFetchingRecordTableDataState'; import { numberOfTableRowsState } from '@/ui/object/record-table/states/numberOfTableRowsState'; import { tableRowIdsState } from '@/ui/object/record-table/states/tableRowIdsState'; import { useView } from '@/views/hooks/useView'; -export const useSetObjectRecordTableData = () => { - const resetTableRowSelection = useResetTableRowSelection(); +export const useSetRecordTableData = () => { + const { resetTableRowSelection } = useRecordTable(); const { setEntityCountInCurrentView } = useView(); return useRecoilCallback( diff --git a/front/src/modules/metadata/scopes/ObjectMetadataItemScope.tsx b/front/src/modules/metadata/scopes/ObjectMetadataItemScope.tsx deleted file mode 100644 index 4ef34d4ac..000000000 --- a/front/src/modules/metadata/scopes/ObjectMetadataItemScope.tsx +++ /dev/null @@ -1,24 +0,0 @@ -import { ReactNode } from 'react'; - -import { ObjectMetadataItemScopeInternalContext } from './scope-internal-context/ObjectMetadataItemScopeInternalContext'; - -type ObjectMetadataItemScopeProps = { - children: ReactNode; - objectMetadataItemNamePlural: string; -}; - -export const ObjectMetadataItemScope = ({ - children, - objectMetadataItemNamePlural, -}: ObjectMetadataItemScopeProps) => { - return ( - - {children} - - ); -}; diff --git a/front/src/modules/metadata/scopes/scope-internal-context/ObjectMetadataItemScopeInternalContext.ts b/front/src/modules/metadata/scopes/scope-internal-context/ObjectMetadataItemScopeInternalContext.ts deleted file mode 100644 index fb062f3bf..000000000 --- a/front/src/modules/metadata/scopes/scope-internal-context/ObjectMetadataItemScopeInternalContext.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { ScopedStateKey } from '@/ui/utilities/recoil-scope/scopes-internal/types/ScopedStateKey'; -import { createScopeInternalContext } from '@/ui/utilities/recoil-scope/scopes-internal/utils/createScopeInternalContext'; - -type ObjectMetadataItemScopeInternalContextProps = ScopedStateKey & { - objectNamePlural: string; -}; - -export const ObjectMetadataItemScopeInternalContext = - createScopeInternalContext(); diff --git a/front/src/modules/people/hooks/usePersonTableContextMenuEntries.tsx b/front/src/modules/people/hooks/usePersonTableContextMenuEntries.tsx index adeed2128..fe0ef0de4 100644 --- a/front/src/modules/people/hooks/usePersonTableContextMenuEntries.tsx +++ b/front/src/modules/people/hooks/usePersonTableContextMenuEntries.tsx @@ -11,7 +11,7 @@ import { } from '@/ui/display/icon'; import { actionBarEntriesState } from '@/ui/navigation/action-bar/states/actionBarEntriesState'; import { contextMenuEntriesState } from '@/ui/navigation/context-menu/states/contextMenuEntriesState'; -import { useResetTableRowSelection } from '@/ui/object/record-table/hooks/useResetTableRowSelection'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { selectedRowIdsSelector } from '@/ui/object/record-table/states/selectors/selectedRowIdsSelector'; import { tableRowIdsState } from '@/ui/object/record-table/states/tableRowIdsState'; import { @@ -30,7 +30,9 @@ export const usePersonTableContextMenuEntries = () => { const createActivityForPeople = useCreateActivityForPeople(); const setTableRowIds = useSetRecoilState(tableRowIdsState); - const resetRowSelection = useResetTableRowSelection(); + const { resetTableRowSelection } = useRecordTable({ + recordTableScopeId: 'people', + }); const { data } = useGetFavoritesQuery(); const favorites = data?.findFavorites; @@ -48,7 +50,7 @@ export const usePersonTableContextMenuEntries = () => { !!selectedPersonId && !!favorites?.find((favorite) => favorite.person?.id === selectedPersonId); - resetRowSelection(); + resetTableRowSelection(); if (isFavorite) deletePersonFavorite(selectedPersonId); else insertPersonFavorite(selectedPersonId); }); @@ -62,7 +64,7 @@ export const usePersonTableContextMenuEntries = () => { .getLoadable(selectedRowIdsSelector) .getValue(); - resetRowSelection(); + resetTableRowSelection(); await deleteManyPerson({ variables: { diff --git a/front/src/modules/people/hooks/useSetPeopleRecordTable.ts b/front/src/modules/people/hooks/useSetPeopleRecordTable.ts index c63692422..578e9794c 100644 --- a/front/src/modules/people/hooks/useSetPeopleRecordTable.ts +++ b/front/src/modules/people/hooks/useSetPeopleRecordTable.ts @@ -1,7 +1,7 @@ import { useLocation } from 'react-router-dom'; import { useRecoilCallback } from 'recoil'; -import { useResetTableRowSelection } from '@/ui/object/record-table/hooks/useResetTableRowSelection'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { isFetchingRecordTableDataState } from '@/ui/object/record-table/states/isFetchingRecordTableDataState'; import { numberOfTableRowsState } from '@/ui/object/record-table/states/numberOfTableRowsState'; import { tableRowIdsState } from '@/ui/object/record-table/states/tableRowIdsState'; @@ -18,7 +18,7 @@ import { peopleNameCellFamilyState } from '../states/peopleNamesFamilyState'; import { peoplePhoneFamilyState } from '../states/peoplePhoneFamilyState'; export const useSetPeopleRecordTable = () => { - const resetTableRowSelection = useResetTableRowSelection(); + const { resetTableRowSelection } = useRecordTable(); const currentLocation = useLocation().pathname; diff --git a/front/src/modules/people/table/components/PersonTable.tsx b/front/src/modules/people/table/components/PersonTable.tsx index 46b35250e..7d10f3c67 100644 --- a/front/src/modules/people/table/components/PersonTable.tsx +++ b/front/src/modules/people/table/components/PersonTable.tsx @@ -1,5 +1,4 @@ import styled from '@emotion/styled'; -import { useSetRecoilState } from 'recoil'; import { peopleAvailableFieldDefinitions } from '@/people/constants/peopleAvailableFieldDefinitions'; import { getPeopleOptimisticEffectDefinition } from '@/people/graphql/optimistic-effect-definitions/getPeopleOptimisticEffectDefinition'; @@ -9,15 +8,13 @@ import { FieldMetadata } from '@/ui/object/field/types/FieldMetadata'; import { RecordTable } from '@/ui/object/record-table/components/RecordTable'; import { RecordTableEffect } from '@/ui/object/record-table/components/RecordTableEffect'; import { TableOptionsDropdownId } from '@/ui/object/record-table/constants/TableOptionsDropdownId'; -import { TableContext } from '@/ui/object/record-table/contexts/TableContext'; -import { useUpsertRecordTableItem } from '@/ui/object/record-table/hooks/useUpsertRecordTableItem'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { TableOptionsDropdown } from '@/ui/object/record-table/options/components/TableOptionsDropdown'; -import { tableColumnsScopedState } from '@/ui/object/record-table/states/tableColumnsScopedState'; -import { tableFiltersScopedState } from '@/ui/object/record-table/states/tableFiltersScopedState'; -import { tableSortsScopedState } from '@/ui/object/record-table/states/tableSortsScopedState'; +import { RecordTableScope } from '@/ui/object/record-table/scopes/RecordTableScope'; import { ColumnDefinition } from '@/ui/object/record-table/types/ColumnDefinition'; import { ViewBar } from '@/views/components/ViewBar'; import { useViewFields } from '@/views/hooks/internal/useViewFields'; +import { useView } from '@/views/hooks/useView'; import { ViewScope } from '@/views/scopes/ViewScope'; import { mapColumnDefinitionsToViewFields } from '@/views/utils/mapColumnDefinitionToViewField'; import { mapViewFieldsToColumnDefinitions } from '@/views/utils/mapViewFieldsToColumnDefinitions'; @@ -36,18 +33,17 @@ import PersonTableEffect from './PersonTableEffect'; export const PersonTable = () => { const viewScopeId = 'person-table-view'; const tableScopeId = 'people'; - const setTableColumns = useSetRecoilState( - tableColumnsScopedState(tableScopeId), - ); - const setTableFilters = useSetRecoilState( - tableFiltersScopedState(tableScopeId), - ); - - const setTableSorts = useSetRecoilState(tableSortsScopedState(tableScopeId)); + const { + setTableFilters, + setTableSorts, + setTableColumns, + upsertRecordTableItem, + } = useRecordTable({ + recordTableScopeId: tableScopeId, + }); const [updateEntityMutation] = useUpdateOnePersonMutation(); - const upsertRecordTableItem = useUpsertRecordTableItem(); const { persistViewFields } = useViewFields(viewScopeId); @@ -73,6 +69,8 @@ export const PersonTable = () => { const { openPersonSpreadsheetImport: onImport } = useSpreadsheetPersonImport(); + const { setEntityCountInCurrentView } = useView({ viewScopeId }); + const StyledContainer = styled.div` display: flex; flex-direction: column; @@ -98,9 +96,11 @@ export const PersonTable = () => { }} > - { + setEntityCountInCurrentView(entityCount); }} > { variables: UpdateOnePersonMutationVariables; }) => updatePerson(variables)} /> - + ); diff --git a/front/src/modules/people/table/components/PersonTableEffect.tsx b/front/src/modules/people/table/components/PersonTableEffect.tsx index ad7b69d3d..8b4d37901 100644 --- a/front/src/modules/people/table/components/PersonTableEffect.tsx +++ b/front/src/modules/people/table/components/PersonTableEffect.tsx @@ -1,10 +1,7 @@ import { useEffect } from 'react'; import { peopleAvailableFieldDefinitions } from '@/people/constants/peopleAvailableFieldDefinitions'; -import { availableTableColumnsScopedState } from '@/ui/object/record-table/states/availableTableColumnsScopedState'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { tableColumnsScopedState } from '@/ui/object/record-table/states/tableColumnsScopedState'; -import { useRecoilScopedState } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedState'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { useView } from '@/views/hooks/useView'; import { ViewType } from '@/views/types/ViewType'; import { personTableFilterDefinitions } from '~/pages/people/constants/personTableFilterDefinitions'; @@ -19,15 +16,7 @@ const PeopleTableEffect = () => { setViewObjectId, } = useView(); - const [, setTableColumns] = useRecoilScopedState( - tableColumnsScopedState, - TableRecoilScopeContext, - ); - - const [, setAvailableTableColumns] = useRecoilScopedState( - availableTableColumnsScopedState, - TableRecoilScopeContext, - ); + const { setAvailableTableColumns, setTableColumns } = useRecordTable(); useEffect(() => { setAvailableSortDefinitions?.(personTableSortDefinitions); diff --git a/front/src/modules/ui/layout/board/hooks/useBoardColumns.ts b/front/src/modules/ui/layout/board/hooks/useBoardColumns.ts index d5df4dca2..d82ba3cb2 100644 --- a/front/src/modules/ui/layout/board/hooks/useBoardColumns.ts +++ b/front/src/modules/ui/layout/board/hooks/useBoardColumns.ts @@ -1,6 +1,6 @@ import { useRecoilState } from 'recoil'; -import { useMoveViewColumns } from '@/ui/object/record-table/hooks/useMoveViewColumns'; +import { useMoveViewColumns } from '@/views/hooks/useMoveViewColumns'; import { useUpdatePipelineStageMutation } from '~/generated/graphql'; import { boardColumnsState } from '../states/boardColumnsState'; diff --git a/front/src/modules/ui/navigation/action-bar/components/__stories__/ActionBar.stories.tsx b/front/src/modules/ui/navigation/action-bar/components/__stories__/ActionBar.stories.tsx index 3a0b581d9..a63bbc14d 100644 --- a/front/src/modules/ui/navigation/action-bar/components/__stories__/ActionBar.stories.tsx +++ b/front/src/modules/ui/navigation/action-bar/components/__stories__/ActionBar.stories.tsx @@ -4,8 +4,7 @@ import { useSetRecoilState } from 'recoil'; import { useCompanyTableContextMenuEntries } from '@/companies/hooks/useCompanyTableContextMenuEntries'; import { CompanyTableMockMode } from '@/companies/table/components/CompanyTableMockMode'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope'; +import { RecordTableScope } from '@/ui/object/record-table/scopes/RecordTableScope'; import { ComponentDecorator } from '~/testing/decorators/ComponentDecorator'; import { actionBarOpenState } from '../../states/actionBarIsOpenState'; @@ -24,12 +23,16 @@ const meta: Meta = { component: FilledActionBar, decorators: [ (Story) => ( - + {}} + onEntityCountChange={() => {}} + > - + ), ComponentDecorator, ], diff --git a/front/src/modules/ui/navigation/context-menu/components/__stories__/ContextMenu.stories.tsx b/front/src/modules/ui/navigation/context-menu/components/__stories__/ContextMenu.stories.tsx index 35f2d24bd..9e64b94b7 100644 --- a/front/src/modules/ui/navigation/context-menu/components/__stories__/ContextMenu.stories.tsx +++ b/front/src/modules/ui/navigation/context-menu/components/__stories__/ContextMenu.stories.tsx @@ -4,8 +4,7 @@ import { useSetRecoilState } from 'recoil'; import { useCompanyTableContextMenuEntries } from '@/companies/hooks/useCompanyTableContextMenuEntries'; import { CompanyTableMockMode } from '@/companies/table/components/CompanyTableMockMode'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope'; +import { RecordTableScope } from '@/ui/object/record-table/scopes/RecordTableScope'; import { ComponentDecorator } from '~/testing/decorators/ComponentDecorator'; import { contextMenuIsOpenState } from '../../states/contextMenuIsOpenState'; @@ -30,12 +29,16 @@ const meta: Meta = { component: FilledContextMenu, decorators: [ (Story) => ( - + {}} + onEntityCountChange={() => {}} + > - + ), ComponentDecorator, ], diff --git a/front/src/modules/ui/object/record-table/components/CheckboxCell.tsx b/front/src/modules/ui/object/record-table/components/CheckboxCell.tsx index 340d53ff9..8d1c361a1 100644 --- a/front/src/modules/ui/object/record-table/components/CheckboxCell.tsx +++ b/front/src/modules/ui/object/record-table/components/CheckboxCell.tsx @@ -5,7 +5,7 @@ import { useSetRecoilState } from 'recoil'; import { Checkbox } from '@/ui/input/components/Checkbox'; import { actionBarOpenState } from '@/ui/navigation/action-bar/states/actionBarIsOpenState'; -import { useCurrentRowSelected } from '../hooks/useCurrentRowSelected'; +import { useCurrentRowSelected } from '../record-table-row/hooks/useCurrentRowSelected'; const StyledContainer = styled.div` align-items: center; diff --git a/front/src/modules/ui/object/record-table/components/RecordTable.tsx b/front/src/modules/ui/object/record-table/components/RecordTable.tsx index d6cf763a5..4b12edbf5 100644 --- a/front/src/modules/ui/object/record-table/components/RecordTable.tsx +++ b/front/src/modules/ui/object/record-table/components/RecordTable.tsx @@ -10,10 +10,7 @@ import { import { ScrollWrapper } from '@/ui/utilities/scroll/components/ScrollWrapper'; import { EntityUpdateMutationContext } from '../contexts/EntityUpdateMutationHookContext'; -import { useLeaveTableFocus } from '../hooks/useLeaveTableFocus'; -import { useMapKeyboardToSoftFocus } from '../hooks/useMapKeyboardToSoftFocus'; -import { useResetTableRowSelection } from '../hooks/useResetTableRowSelection'; -import { useSetRowSelectedState } from '../hooks/useSetRowSelectedState'; +import { useRecordTable } from '../hooks/useRecordTable'; import { TableHotkeyScope } from '../types/TableHotkeyScope'; import { RecordTableBody } from './RecordTableBody'; @@ -89,13 +86,15 @@ type RecordTableProps = { export const RecordTable = ({ updateEntityMutation }: RecordTableProps) => { const tableBodyRef = useRef(null); - const setRowSelectedState = useSetRowSelectedState(); - const resetTableRowSelection = useResetTableRowSelection(); + const { + leaveTableFocus, + setRowSelectedState, + resetTableRowSelection, + useMapKeyboardToSoftFocus, + } = useRecordTable(); useMapKeyboardToSoftFocus(); - const leaveTableFocus = useLeaveTableFocus(); - useListenClickOutside({ refs: [tableBodyRef], callback: () => { diff --git a/front/src/modules/ui/object/record-table/components/RecordTableCell.tsx b/front/src/modules/ui/object/record-table/components/RecordTableCell.tsx index 7643696a4..519050790 100644 --- a/front/src/modules/ui/object/record-table/components/RecordTableCell.tsx +++ b/front/src/modules/ui/object/record-table/components/RecordTableCell.tsx @@ -12,8 +12,8 @@ import { ColumnContext } from '../contexts/ColumnContext'; import { ColumnIndexContext } from '../contexts/ColumnIndexContext'; import { EntityUpdateMutationContext } from '../contexts/EntityUpdateMutationHookContext'; import { RowIdContext } from '../contexts/RowIdContext'; -import { useCurrentRowSelected } from '../hooks/useCurrentRowSelected'; -import { TableCell } from '../table-cell/components/TableCell'; +import { TableCell } from '../record-table-cell/components/RecordTableCell'; +import { useCurrentRowSelected } from '../record-table-row/hooks/useCurrentRowSelected'; import { TableHotkeyScope } from '../types/TableHotkeyScope'; export const RecordTableCell = ({ cellIndex }: { cellIndex: number }) => { diff --git a/front/src/modules/ui/object/record-table/components/RecordTableEffect.tsx b/front/src/modules/ui/object/record-table/components/RecordTableEffect.tsx index d9a715c72..03dbd208e 100644 --- a/front/src/modules/ui/object/record-table/components/RecordTableEffect.tsx +++ b/front/src/modules/ui/object/record-table/components/RecordTableEffect.tsx @@ -1,10 +1,10 @@ import { useEffect } from 'react'; import { useSearchParams } from 'react-router-dom'; import defaults from 'lodash/defaults'; +import { useRecoilValue } from 'recoil'; import { useOptimisticEffect } from '@/apollo/optimistic-effect/hooks/useOptimisticEffect'; import { OptimisticEffectDefinition } from '@/apollo/optimistic-effect/types/OptimisticEffectDefinition'; -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; import { SortOrder, useGetCompaniesQuery, @@ -13,10 +13,8 @@ import { import { FilterDefinition } from '../../object-filter-dropdown/types/FilterDefinition'; import { SortDefinition } from '../../object-sort-dropdown/types/SortDefinition'; -import { useSetRecordTableData } from '../hooks/useSetRecordTableData'; -import { TableRecoilScopeContext } from '../states/recoil-scope-contexts/TableRecoilScopeContext'; -import { tablefiltersWhereScopedSelector } from '../states/selectors/tablefiltersWhereScopedSelector'; -import { tableSortsOrderByScopedSelector } from '../states/selectors/tableSortsOrderByScopedSelector'; +import { useRecordTableScopedStates } from '../hooks/internal/useRecordTableScopedStates'; +import { useRecordTable } from '../hooks/useRecordTable'; export const RecordTableEffect = ({ useGetRequest, @@ -35,32 +33,28 @@ export const RecordTableEffect = ({ setActionBarEntries?: () => void; setContextMenuEntries?: () => void; }) => { - const setRecordTableData = useSetRecordTableData(); + const { setRecordTableData } = useRecordTable(); + const { tableSortsOrderBySelector, tableFiltersWhereSelector } = + useRecordTableScopedStates(); const { registerOptimisticEffect } = useOptimisticEffect(); - const tableSortsOrderBy = useRecoilScopedValue( - tableSortsOrderByScopedSelector, - TableRecoilScopeContext, - ); + const tableSortsOrderBy = useRecoilValue(tableSortsOrderBySelector); const sortsOrderBy = defaults(tableSortsOrderBy, [ { createdAt: SortOrder.Desc, }, ]); - const tablefiltersWhere = useRecoilScopedValue( - tablefiltersWhereScopedSelector, - TableRecoilScopeContext, - ); + const tableFiltersWhere = useRecoilValue(tableFiltersWhereSelector); useGetRequest({ - variables: { orderBy: sortsOrderBy, where: tablefiltersWhere }, + variables: { orderBy: sortsOrderBy, where: tableFiltersWhere }, onCompleted: (data: any) => { const entities = data[getRequestResultKey] ?? []; setRecordTableData(entities); registerOptimisticEffect({ - variables: { orderBy: sortsOrderBy, where: tablefiltersWhere }, + variables: { orderBy: sortsOrderBy, where: tableFiltersWhere }, definition: getRequestOptimisticEffectDefinition, }); }, diff --git a/front/src/modules/ui/object/record-table/components/RecordTableHeader.tsx b/front/src/modules/ui/object/record-table/components/RecordTableHeader.tsx index cacc7ffdb..0fbbae3a1 100644 --- a/front/src/modules/ui/object/record-table/components/RecordTableHeader.tsx +++ b/front/src/modules/ui/object/record-table/components/RecordTableHeader.tsx @@ -1,21 +1,16 @@ import { useCallback, useState } from 'react'; import { useTheme } from '@emotion/react'; import styled from '@emotion/styled'; -import { useRecoilCallback, useRecoilState } from 'recoil'; +import { useRecoilCallback, useRecoilState, useRecoilValue } from 'recoil'; import { IconPlus } from '@/ui/display/icon'; import { Dropdown } from '@/ui/layout/dropdown/components/Dropdown'; import { DropdownScope } from '@/ui/layout/dropdown/scopes/DropdownScope'; import { useTrackPointer } from '@/ui/utilities/pointer-event/hooks/useTrackPointer'; -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; +import { useRecordTableScopedStates } from '../hooks/internal/useRecordTableScopedStates'; import { useTableColumns } from '../hooks/useTableColumns'; -import { TableRecoilScopeContext } from '../states/recoil-scope-contexts/TableRecoilScopeContext'; import { resizeFieldOffsetState } from '../states/resizeFieldOffsetState'; -import { hiddenTableColumnsScopedSelector } from '../states/selectors/hiddenTableColumnsScopedSelector'; -import { tableColumnsByKeyScopedSelector } from '../states/selectors/tableColumnsByKeyScopedSelector'; -import { visibleTableColumnsScopedSelector } from '../states/selectors/visibleTableColumnsScopedSelector'; -import { tableColumnsScopedState } from '../states/tableColumnsScopedState'; import { ColumnHeadWithDropdown } from './ColumnHeadWithDropdown'; import { RecordTableHeaderPlusButtonContent } from './RecordTableHeaderPlusButtonContent'; @@ -110,22 +105,18 @@ export const RecordTableHeader = () => { const [resizeFieldOffset, setResizeFieldOffset] = useRecoilState( resizeFieldOffsetState, ); - const tableColumns = useRecoilScopedValue( - tableColumnsScopedState, - TableRecoilScopeContext, - ); - const tableColumnsByKey = useRecoilScopedValue( - tableColumnsByKeyScopedSelector, - TableRecoilScopeContext, - ); - const hiddenTableColumns = useRecoilScopedValue( - hiddenTableColumnsScopedSelector, - TableRecoilScopeContext, - ); - const visibleTableColumns = useRecoilScopedValue( - visibleTableColumnsScopedSelector, - TableRecoilScopeContext, - ); + + const { + tableColumnsState, + tableColumnsByKeySelector, + hiddenTableColumnsSelector, + visibleTableColumnsSelector, + } = useRecordTableScopedStates(); + + const tableColumns = useRecoilValue(tableColumnsState); + const tableColumnsByKey = useRecoilValue(tableColumnsByKeySelector); + const hiddenTableColumns = useRecoilValue(hiddenTableColumnsSelector); + const visibleTableColumns = useRecoilValue(visibleTableColumnsSelector); const [initialPointerPositionX, setInitialPointerPositionX] = useState< number | null diff --git a/front/src/modules/ui/object/record-table/components/RecordTableHeaderPlusButtonContent.tsx b/front/src/modules/ui/object/record-table/components/RecordTableHeaderPlusButtonContent.tsx index 40c99af59..cb9b1b791 100644 --- a/front/src/modules/ui/object/record-table/components/RecordTableHeaderPlusButtonContent.tsx +++ b/front/src/modules/ui/object/record-table/components/RecordTableHeaderPlusButtonContent.tsx @@ -1,24 +1,22 @@ import { useCallback } from 'react'; +import { useRecoilValue } from 'recoil'; import { IconPlus } from '@/ui/display/icon'; import { DropdownMenuItemsContainer } from '@/ui/layout/dropdown/components/DropdownMenuItemsContainer'; import { useDropdown } from '@/ui/layout/dropdown/hooks/useDropdown'; import { MenuItem } from '@/ui/navigation/menu-item/components/MenuItem'; -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; import { FieldMetadata } from '../../field/types/FieldMetadata'; +import { useRecordTableScopedStates } from '../hooks/internal/useRecordTableScopedStates'; import { useTableColumns } from '../hooks/useTableColumns'; -import { TableRecoilScopeContext } from '../states/recoil-scope-contexts/TableRecoilScopeContext'; -import { hiddenTableColumnsScopedSelector } from '../states/selectors/hiddenTableColumnsScopedSelector'; import { ColumnDefinition } from '../types/ColumnDefinition'; export const RecordTableHeaderPlusButtonContent = () => { const { closeDropdown } = useDropdown(); - const hiddenTableColumns = useRecoilScopedValue( - hiddenTableColumnsScopedSelector, - TableRecoilScopeContext, - ); + const { hiddenTableColumnsSelector } = useRecordTableScopedStates(); + + const hiddenTableColumns = useRecoilValue(hiddenTableColumnsSelector); const { handleColumnVisibilityChange } = useTableColumns(); diff --git a/front/src/modules/ui/object/record-table/components/RecordTableRow.tsx b/front/src/modules/ui/object/record-table/components/RecordTableRow.tsx index 0a06c13bb..907321fea 100644 --- a/front/src/modules/ui/object/record-table/components/RecordTableRow.tsx +++ b/front/src/modules/ui/object/record-table/components/RecordTableRow.tsx @@ -1,12 +1,10 @@ import { forwardRef } from 'react'; import styled from '@emotion/styled'; - -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; +import { useRecoilValue } from 'recoil'; import { ColumnContext } from '../contexts/ColumnContext'; -import { useCurrentRowSelected } from '../hooks/useCurrentRowSelected'; -import { TableRecoilScopeContext } from '../states/recoil-scope-contexts/TableRecoilScopeContext'; -import { visibleTableColumnsScopedSelector } from '../states/selectors/visibleTableColumnsScopedSelector'; +import { useRecordTableScopedStates } from '../hooks/internal/useRecordTableScopedStates'; +import { useCurrentRowSelected } from '../record-table-row/hooks/useCurrentRowSelected'; import { CheckboxCell } from './CheckboxCell'; import { RecordTableCell } from './RecordTableCell'; @@ -24,10 +22,10 @@ export const RecordTableRow = forwardRef< HTMLTableRowElement, RecordTableRowProps >(({ rowId }, ref) => { - const visibleTableColumns = useRecoilScopedValue( - visibleTableColumnsScopedSelector, - TableRecoilScopeContext, - ); + const { visibleTableColumnsSelector } = useRecordTableScopedStates(); + + const visibleTableColumns = useRecoilValue(visibleTableColumnsSelector); + const { currentRowSelected } = useCurrentRowSelected(); return ( diff --git a/front/src/modules/ui/object/record-table/components/SelectAllCheckbox.tsx b/front/src/modules/ui/object/record-table/components/SelectAllCheckbox.tsx index c7c3ab11c..359e590fd 100644 --- a/front/src/modules/ui/object/record-table/components/SelectAllCheckbox.tsx +++ b/front/src/modules/ui/object/record-table/components/SelectAllCheckbox.tsx @@ -1,8 +1,10 @@ import styled from '@emotion/styled'; +import { useRecoilValue } from 'recoil'; import { Checkbox } from '@/ui/input/components/Checkbox'; -import { useSelectAllRows } from '../hooks/useSelectAllRows'; +import { useRecordTable } from '../hooks/useRecordTable'; +import { allRowsSelectedStatusSelector } from '../states/selectors/allRowsSelectedStatusSelector'; const StyledContainer = styled.div` align-items: center; @@ -14,7 +16,8 @@ const StyledContainer = styled.div` `; export const SelectAllCheckbox = () => { - const { selectAllRows, allRowsSelectedStatus } = useSelectAllRows(); + const allRowsSelectedStatus = useRecoilValue(allRowsSelectedStatusSelector); + const { selectAllRows } = useRecordTable(); const checked = allRowsSelectedStatus === 'all'; const indeterminate = allRowsSelectedStatus === 'some'; diff --git a/front/src/modules/ui/object/record-table/contexts/TableContext.ts b/front/src/modules/ui/object/record-table/contexts/TableContext.ts deleted file mode 100644 index 2268eb621..000000000 --- a/front/src/modules/ui/object/record-table/contexts/TableContext.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { createContext } from 'react'; - -import { FieldMetadata } from '@/ui/object/field/types/FieldMetadata'; - -import { ColumnDefinition } from '../types/ColumnDefinition'; - -export const TableContext = createContext<{ - onColumnsChange?: ( - columns: ColumnDefinition[], - ) => void | Promise; -}>({}); diff --git a/front/src/modules/ui/object/record-table/hooks/useCloseCurrentTableCellInEditMode.ts b/front/src/modules/ui/object/record-table/hooks/internal/useCloseCurrentTableCellInEditMode.ts similarity index 68% rename from front/src/modules/ui/object/record-table/hooks/useCloseCurrentTableCellInEditMode.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useCloseCurrentTableCellInEditMode.ts index 80cb41fa9..cc667e1e8 100644 --- a/front/src/modules/ui/object/record-table/hooks/useCloseCurrentTableCellInEditMode.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useCloseCurrentTableCellInEditMode.ts @@ -1,7 +1,7 @@ import { useRecoilCallback } from 'recoil'; -import { currentTableCellInEditModePositionState } from '../states/currentTableCellInEditModePositionState'; -import { isTableCellInEditModeFamilyState } from '../states/isTableCellInEditModeFamilyState'; +import { currentTableCellInEditModePositionState } from '../../states/currentTableCellInEditModePositionState'; +import { isTableCellInEditModeFamilyState } from '../../states/isTableCellInEditModeFamilyState'; export const useCloseCurrentTableCellInEditMode = () => useRecoilCallback(({ set, snapshot }) => { diff --git a/front/src/modules/ui/object/record-table/hooks/useDisableSoftFocus.ts b/front/src/modules/ui/object/record-table/hooks/internal/useDisableSoftFocus.ts similarity index 60% rename from front/src/modules/ui/object/record-table/hooks/useDisableSoftFocus.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useDisableSoftFocus.ts index beef9378e..316e219d8 100644 --- a/front/src/modules/ui/object/record-table/hooks/useDisableSoftFocus.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useDisableSoftFocus.ts @@ -1,8 +1,8 @@ import { useRecoilCallback } from 'recoil'; -import { isSoftFocusActiveState } from '../states/isSoftFocusActiveState'; -import { isSoftFocusOnTableCellFamilyState } from '../states/isSoftFocusOnTableCellFamilyState'; -import { softFocusPositionState } from '../states/softFocusPositionState'; +import { isSoftFocusActiveState } from '../../states/isSoftFocusActiveState'; +import { isSoftFocusOnTableCellFamilyState } from '../../states/isSoftFocusOnTableCellFamilyState'; +import { softFocusPositionState } from '../../states/softFocusPositionState'; export const useDisableSoftFocus = () => useRecoilCallback(({ set, snapshot }) => { diff --git a/front/src/modules/ui/object/record-table/hooks/useGetIsSomeCellInEditMode.ts b/front/src/modules/ui/object/record-table/hooks/internal/useGetIsSomeCellInEditMode.ts similarity index 73% rename from front/src/modules/ui/object/record-table/hooks/useGetIsSomeCellInEditMode.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useGetIsSomeCellInEditMode.ts index 60ebb6f16..2bf00436b 100644 --- a/front/src/modules/ui/object/record-table/hooks/useGetIsSomeCellInEditMode.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useGetIsSomeCellInEditMode.ts @@ -1,7 +1,7 @@ import { useRecoilCallback } from 'recoil'; -import { currentTableCellInEditModePositionState } from '../states/currentTableCellInEditModePositionState'; -import { isTableCellInEditModeFamilyState } from '../states/isTableCellInEditModeFamilyState'; +import { currentTableCellInEditModePositionState } from '../../states/currentTableCellInEditModePositionState'; +import { isTableCellInEditModeFamilyState } from '../../states/isTableCellInEditModeFamilyState'; export const useGetIsSomeCellInEditMode = () => { return useRecoilCallback( diff --git a/front/src/modules/ui/object/record-table/hooks/useLeaveTableFocus.ts b/front/src/modules/ui/object/record-table/hooks/internal/useLeaveTableFocus.ts similarity index 88% rename from front/src/modules/ui/object/record-table/hooks/useLeaveTableFocus.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useLeaveTableFocus.ts index 8ba90fcca..87c1950ef 100644 --- a/front/src/modules/ui/object/record-table/hooks/useLeaveTableFocus.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useLeaveTableFocus.ts @@ -2,8 +2,8 @@ import { useRecoilCallback } from 'recoil'; import { currentHotkeyScopeState } from '@/ui/utilities/hotkey/states/internal/currentHotkeyScopeState'; -import { isSoftFocusActiveState } from '../states/isSoftFocusActiveState'; -import { TableHotkeyScope } from '../types/TableHotkeyScope'; +import { isSoftFocusActiveState } from '../../states/isSoftFocusActiveState'; +import { TableHotkeyScope } from '../../types/TableHotkeyScope'; import { useCloseCurrentTableCellInEditMode } from './useCloseCurrentTableCellInEditMode'; import { useDisableSoftFocus } from './useDisableSoftFocus'; diff --git a/front/src/modules/ui/object/record-table/hooks/useMoveEditModeToCellPosition.ts b/front/src/modules/ui/object/record-table/hooks/internal/useMoveEditModeToCellPosition.ts similarity index 68% rename from front/src/modules/ui/object/record-table/hooks/useMoveEditModeToCellPosition.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useMoveEditModeToCellPosition.ts index b39a6910c..2a24f1b71 100644 --- a/front/src/modules/ui/object/record-table/hooks/useMoveEditModeToCellPosition.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useMoveEditModeToCellPosition.ts @@ -1,8 +1,8 @@ import { useRecoilCallback } from 'recoil'; -import { currentTableCellInEditModePositionState } from '../states/currentTableCellInEditModePositionState'; -import { isTableCellInEditModeFamilyState } from '../states/isTableCellInEditModeFamilyState'; -import { TableCellPosition } from '../types/TableCellPosition'; +import { currentTableCellInEditModePositionState } from '../../states/currentTableCellInEditModePositionState'; +import { isTableCellInEditModeFamilyState } from '../../states/isTableCellInEditModeFamilyState'; +import { TableCellPosition } from '../../types/TableCellPosition'; export const useMoveEditModeToTableCellPosition = () => useRecoilCallback(({ set, snapshot }) => { diff --git a/front/src/modules/ui/object/record-table/hooks/internal/useRecordTableScopedStates.ts b/front/src/modules/ui/object/record-table/hooks/internal/useRecordTableScopedStates.ts new file mode 100644 index 000000000..965d4967c --- /dev/null +++ b/front/src/modules/ui/object/record-table/hooks/internal/useRecordTableScopedStates.ts @@ -0,0 +1,46 @@ +import { RecordTableScopeInternalContext } from '@/ui/object/record-table/scopes/scope-internal-context/RecordTableScopeInternalContext'; +import { useAvailableScopeIdOrThrow } from '@/ui/utilities/recoil-scope/scopes-internal/hooks/useAvailableScopeId'; + +import { getRecordTableScopedStates } from '../../utils/getRecordTableScopedStates'; + +export const useRecordTableScopedStates = (args?: { + customRecordTableScopeId?: string; +}) => { + const { customRecordTableScopeId } = args ?? {}; + + const scopeId = useAvailableScopeIdOrThrow( + RecordTableScopeInternalContext, + customRecordTableScopeId, + ); + + const { + availableTableColumnsState, + tableFiltersState, + tableSortsState, + tableSortsOrderBySelector, + tableFiltersWhereSelector, + tableColumnsState, + tableColumnsByKeySelector, + hiddenTableColumnsSelector, + visibleTableColumnsSelector, + onEntityCountChangeState, + onColumnsChangeState, + } = getRecordTableScopedStates({ + recordTableScopeId: scopeId, + }); + + return { + scopeId, + availableTableColumnsState, + tableFiltersState, + tableSortsState, + tableSortsOrderBySelector, + tableFiltersWhereSelector, + tableColumnsState, + tableColumnsByKeySelector, + hiddenTableColumnsSelector, + visibleTableColumnsSelector, + onEntityCountChangeState, + onColumnsChangeState, + }; +}; diff --git a/front/src/modules/ui/object/record-table/hooks/useResetTableRowSelection.ts b/front/src/modules/ui/object/record-table/hooks/internal/useResetTableRowSelection.ts similarity index 70% rename from front/src/modules/ui/object/record-table/hooks/useResetTableRowSelection.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useResetTableRowSelection.ts index ebc67da37..4584aefdd 100644 --- a/front/src/modules/ui/object/record-table/hooks/useResetTableRowSelection.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useResetTableRowSelection.ts @@ -1,7 +1,7 @@ import { useRecoilCallback } from 'recoil'; -import { isRowSelectedFamilyState } from '../states/isRowSelectedFamilyState'; -import { tableRowIdsState } from '../states/tableRowIdsState'; +import { isRowSelectedFamilyState } from '../../record-table-row/states/isRowSelectedFamilyState'; +import { tableRowIdsState } from '../../states/tableRowIdsState'; export const useResetTableRowSelection = () => useRecoilCallback( diff --git a/front/src/modules/ui/object/record-table/hooks/useSelectAllRows.ts b/front/src/modules/ui/object/record-table/hooks/internal/useSelectAllRows.ts similarity index 65% rename from front/src/modules/ui/object/record-table/hooks/useSelectAllRows.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useSelectAllRows.ts index 01f19e693..f1ade5ed4 100644 --- a/front/src/modules/ui/object/record-table/hooks/useSelectAllRows.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useSelectAllRows.ts @@ -1,12 +1,10 @@ -import { useRecoilCallback, useRecoilValue } from 'recoil'; +import { useRecoilCallback } from 'recoil'; -import { isRowSelectedFamilyState } from '../states/isRowSelectedFamilyState'; -import { allRowsSelectedStatusSelector } from '../states/selectors/allRowsSelectedStatusSelector'; -import { tableRowIdsState } from '../states/tableRowIdsState'; +import { isRowSelectedFamilyState } from '../../record-table-row/states/isRowSelectedFamilyState'; +import { allRowsSelectedStatusSelector } from '../../states/selectors/allRowsSelectedStatusSelector'; +import { tableRowIdsState } from '../../states/tableRowIdsState'; export const useSelectAllRows = () => { - const allRowsSelectedStatus = useRecoilValue(allRowsSelectedStatusSelector); - const selectAllRows = useRecoilCallback( ({ set, snapshot }) => () => { @@ -35,7 +33,6 @@ export const useSelectAllRows = () => { ); return { - allRowsSelectedStatus, selectAllRows, }; }; diff --git a/front/src/modules/ui/object/record-table/hooks/useSetRecordTableData.ts b/front/src/modules/ui/object/record-table/hooks/internal/useSetRecordTableData.ts similarity index 68% rename from front/src/modules/ui/object/record-table/hooks/useSetRecordTableData.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useSetRecordTableData.ts index aa8c6e608..c0bcbcbaa 100644 --- a/front/src/modules/ui/object/record-table/hooks/useSetRecordTableData.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useSetRecordTableData.ts @@ -1,17 +1,21 @@ import { useRecoilCallback } from 'recoil'; import { entityFieldsFamilyState } from '@/ui/object/field/states/entityFieldsFamilyState'; -import { useView } from '@/views/hooks/useView'; -import { isFetchingRecordTableDataState } from '../states/isFetchingRecordTableDataState'; -import { numberOfTableRowsState } from '../states/numberOfTableRowsState'; -import { tableRowIdsState } from '../states/tableRowIdsState'; +import { isFetchingRecordTableDataState } from '../../states/isFetchingRecordTableDataState'; +import { numberOfTableRowsState } from '../../states/numberOfTableRowsState'; +import { tableRowIdsState } from '../../states/tableRowIdsState'; import { useResetTableRowSelection } from './useResetTableRowSelection'; -export const useSetRecordTableData = () => { +type useSetRecordTableDataProps = { + onEntityCountChange: (entityCount: number) => void; +}; + +export const useSetRecordTableData = ({ + onEntityCountChange, +}: useSetRecordTableDataProps) => { const resetTableRowSelection = useResetTableRowSelection(); - const { setEntityCountInCurrentView } = useView(); return useRecoilCallback( ({ set, snapshot }) => @@ -39,9 +43,9 @@ export const useSetRecordTableData = () => { resetTableRowSelection(); set(numberOfTableRowsState, entityIds.length); - setEntityCountInCurrentView(entityIds.length); + onEntityCountChange(entityIds.length); set(isFetchingRecordTableDataState, false); }, - [resetTableRowSelection, setEntityCountInCurrentView], + [onEntityCountChange, resetTableRowSelection], ); }; diff --git a/front/src/modules/ui/object/record-table/hooks/useSetRowSelectedState.ts b/front/src/modules/ui/object/record-table/hooks/internal/useSetRowSelectedState.ts similarity index 69% rename from front/src/modules/ui/object/record-table/hooks/useSetRowSelectedState.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useSetRowSelectedState.ts index be8423438..aa0d6380c 100644 --- a/front/src/modules/ui/object/record-table/hooks/useSetRowSelectedState.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useSetRowSelectedState.ts @@ -1,6 +1,6 @@ import { useRecoilCallback } from 'recoil'; -import { isRowSelectedFamilyState } from '../states/isRowSelectedFamilyState'; +import { isRowSelectedFamilyState } from '../../record-table-row/states/isRowSelectedFamilyState'; export const useSetRowSelectedState = () => useRecoilCallback(({ set }) => (rowId: string, selected: boolean) => { diff --git a/front/src/modules/ui/object/record-table/hooks/useSetSoftFocusPosition.ts b/front/src/modules/ui/object/record-table/hooks/internal/useSetSoftFocusPosition.ts similarity index 62% rename from front/src/modules/ui/object/record-table/hooks/useSetSoftFocusPosition.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useSetSoftFocusPosition.ts index 72cea1f34..282e6c344 100644 --- a/front/src/modules/ui/object/record-table/hooks/useSetSoftFocusPosition.ts +++ b/front/src/modules/ui/object/record-table/hooks/internal/useSetSoftFocusPosition.ts @@ -1,9 +1,9 @@ import { useRecoilCallback } from 'recoil'; -import { isSoftFocusActiveState } from '../states/isSoftFocusActiveState'; -import { isSoftFocusOnTableCellFamilyState } from '../states/isSoftFocusOnTableCellFamilyState'; -import { softFocusPositionState } from '../states/softFocusPositionState'; -import { TableCellPosition } from '../types/TableCellPosition'; +import { isSoftFocusActiveState } from '../../states/isSoftFocusActiveState'; +import { isSoftFocusOnTableCellFamilyState } from '../../states/isSoftFocusOnTableCellFamilyState'; +import { softFocusPositionState } from '../../states/softFocusPositionState'; +import { TableCellPosition } from '../../types/TableCellPosition'; export const useSetSoftFocusPosition = () => useRecoilCallback(({ set, snapshot }) => { diff --git a/front/src/modules/ui/object/record-table/hooks/useUpsertRecordTableItem.ts b/front/src/modules/ui/object/record-table/hooks/internal/useUpsertRecordTableItem.ts similarity index 100% rename from front/src/modules/ui/object/record-table/hooks/useUpsertRecordTableItem.ts rename to front/src/modules/ui/object/record-table/hooks/internal/useUpsertRecordTableItem.ts diff --git a/front/src/modules/ui/object/record-table/hooks/useCellInputEventHandlers.ts b/front/src/modules/ui/object/record-table/hooks/useCellInputEventHandlers.ts deleted file mode 100644 index f733a357b..000000000 --- a/front/src/modules/ui/object/record-table/hooks/useCellInputEventHandlers.ts +++ /dev/null @@ -1,48 +0,0 @@ -import { useCurrentTableCellEditMode } from '../table-cell/hooks/useCurrentTableCellEditMode'; -import { useTableCell } from '../table-cell/hooks/useTableCell'; - -import { useMoveSoftFocus } from './useMoveSoftFocus'; - -export const useCellInputEventHandlers = ({ - onSubmit, - onCancel, -}: { - onSubmit?: (newValue: T) => void; - onCancel?: () => void; -}) => { - const { closeTableCell: closeEditableCell } = useTableCell(); - const { isCurrentTableCellInEditMode: isCurrentCellInEditMode } = - useCurrentTableCellEditMode(); - const { moveRight, moveLeft, moveDown } = useMoveSoftFocus(); - - return { - handleClickOutside: (event: MouseEvent | TouchEvent, newValue: T) => { - if (isCurrentCellInEditMode) { - event.stopImmediatePropagation(); - - onSubmit?.(newValue); - - closeEditableCell(); - } - }, - handleEscape: () => { - closeEditableCell(); - onCancel?.(); - }, - handleEnter: (newValue: T) => { - onSubmit?.(newValue); - closeEditableCell(); - moveDown(); - }, - handleTab: (newValue: T) => { - onSubmit?.(newValue); - closeEditableCell(); - moveRight(); - }, - handleShiftTab: (newValue: T) => { - onSubmit?.(newValue); - closeEditableCell(); - moveLeft(); - }, - }; -}; diff --git a/front/src/modules/ui/object/record-table/hooks/useCurrentEntityId.ts b/front/src/modules/ui/object/record-table/hooks/useCurrentEntityId.ts deleted file mode 100644 index dfa2031ee..000000000 --- a/front/src/modules/ui/object/record-table/hooks/useCurrentEntityId.ts +++ /dev/null @@ -1,9 +0,0 @@ -import { useContext } from 'react'; - -import { RowIdContext } from '../contexts/RowIdContext'; - -export const useCurrentRowEntityId = () => { - const currentEntityId = useContext(RowIdContext); - - return currentEntityId; -}; diff --git a/front/src/modules/ui/object/record-table/hooks/useMapKeyboardToSoftFocus.ts b/front/src/modules/ui/object/record-table/hooks/useMapKeyboardToSoftFocus.ts deleted file mode 100644 index 17c1a4e77..000000000 --- a/front/src/modules/ui/object/record-table/hooks/useMapKeyboardToSoftFocus.ts +++ /dev/null @@ -1,62 +0,0 @@ -import { Key } from 'ts-key-enum'; - -import { useScopedHotkeys } from '@/ui/utilities/hotkey/hooks/useScopedHotkeys'; -import { useSetHotkeyScope } from '@/ui/utilities/hotkey/hooks/useSetHotkeyScope'; - -import { TableHotkeyScope } from '../types/TableHotkeyScope'; - -import { useDisableSoftFocus } from './useDisableSoftFocus'; -import { useMoveSoftFocus } from './useMoveSoftFocus'; - -export const useMapKeyboardToSoftFocus = () => { - const { moveDown, moveLeft, moveRight, moveUp } = useMoveSoftFocus(); - - const disableSoftFocus = useDisableSoftFocus(); - const setHotkeyScope = useSetHotkeyScope(); - - useScopedHotkeys( - [Key.ArrowUp, `${Key.Shift}+${Key.Enter}`], - () => { - moveUp(); - }, - TableHotkeyScope.TableSoftFocus, - [moveUp], - ); - - useScopedHotkeys( - Key.ArrowDown, - () => { - moveDown(); - }, - TableHotkeyScope.TableSoftFocus, - [moveDown], - ); - - useScopedHotkeys( - [Key.ArrowLeft, `${Key.Shift}+${Key.Tab}`], - () => { - moveLeft(); - }, - TableHotkeyScope.TableSoftFocus, - [moveLeft], - ); - - useScopedHotkeys( - [Key.ArrowRight, Key.Tab], - () => { - moveRight(); - }, - TableHotkeyScope.TableSoftFocus, - [moveRight], - ); - - useScopedHotkeys( - [Key.Escape], - () => { - setHotkeyScope(TableHotkeyScope.Table, { goto: true }); - disableSoftFocus(); - }, - TableHotkeyScope.TableSoftFocus, - [disableSoftFocus], - ); -}; diff --git a/front/src/modules/ui/object/record-table/hooks/useMoveSoftFocus.ts b/front/src/modules/ui/object/record-table/hooks/useMoveSoftFocus.ts deleted file mode 100644 index 92cd01c80..000000000 --- a/front/src/modules/ui/object/record-table/hooks/useMoveSoftFocus.ts +++ /dev/null @@ -1,159 +0,0 @@ -import { useRecoilCallback } from 'recoil'; - -import { useRecoilScopeId } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopeId'; - -import { numberOfTableRowsState } from '../states/numberOfTableRowsState'; -import { TableRecoilScopeContext } from '../states/recoil-scope-contexts/TableRecoilScopeContext'; -import { numberOfTableColumnsScopedSelector } from '../states/selectors/numberOfTableColumnsScopedSelector'; -import { softFocusPositionState } from '../states/softFocusPositionState'; - -import { useSetSoftFocusPosition } from './useSetSoftFocusPosition'; - -// TODO: stories - -export const useMoveSoftFocus = () => { - const tableScopeId = useRecoilScopeId(TableRecoilScopeContext); - const setSoftFocusPosition = useSetSoftFocusPosition(); - - const moveUp = useRecoilCallback( - ({ snapshot }) => - () => { - const softFocusPosition = snapshot - .getLoadable(softFocusPositionState) - .valueOrThrow(); - - let newRowNumber = softFocusPosition.row - 1; - - if (newRowNumber < 0) { - newRowNumber = 0; - } - - setSoftFocusPosition({ - ...softFocusPosition, - row: newRowNumber, - }); - }, - [setSoftFocusPosition], - ); - - const moveDown = useRecoilCallback( - ({ snapshot }) => - () => { - const softFocusPosition = snapshot - .getLoadable(softFocusPositionState) - .valueOrThrow(); - - const numberOfTableRows = snapshot - .getLoadable(numberOfTableRowsState) - .valueOrThrow(); - - let newRowNumber = softFocusPosition.row + 1; - - if (newRowNumber >= numberOfTableRows) { - newRowNumber = numberOfTableRows - 1; - } - - setSoftFocusPosition({ - ...softFocusPosition, - row: newRowNumber, - }); - }, - [setSoftFocusPosition], - ); - - const moveRight = useRecoilCallback( - ({ snapshot }) => - () => { - const softFocusPosition = snapshot - .getLoadable(softFocusPositionState) - .valueOrThrow(); - - const numberOfTableColumns = snapshot - .getLoadable(numberOfTableColumnsScopedSelector(tableScopeId)) - .valueOrThrow(); - - const numberOfTableRows = snapshot - .getLoadable(numberOfTableRowsState) - .valueOrThrow(); - - const currentColumnNumber = softFocusPosition.column; - const currentRowNumber = softFocusPosition.row; - - const isLastRowAndLastColumn = - currentColumnNumber === numberOfTableColumns - 1 && - currentRowNumber === numberOfTableRows - 1; - - const isLastColumnButNotLastRow = - currentColumnNumber === numberOfTableColumns - 1 && - currentRowNumber !== numberOfTableRows - 1; - - const isNotLastColumn = - currentColumnNumber !== numberOfTableColumns - 1; - - if (isLastRowAndLastColumn) { - return; - } - - if (isNotLastColumn) { - setSoftFocusPosition({ - row: currentRowNumber, - column: currentColumnNumber + 1, - }); - } else if (isLastColumnButNotLastRow) { - setSoftFocusPosition({ - row: currentRowNumber + 1, - column: 0, - }); - } - }, - [setSoftFocusPosition, tableScopeId], - ); - - const moveLeft = useRecoilCallback( - ({ snapshot }) => - () => { - const softFocusPosition = snapshot - .getLoadable(softFocusPositionState) - .valueOrThrow(); - - const numberOfTableColumns = snapshot - .getLoadable(numberOfTableColumnsScopedSelector(tableScopeId)) - .valueOrThrow(); - - const currentColumnNumber = softFocusPosition.column; - const currentRowNumber = softFocusPosition.row; - - const isFirstRowAndFirstColumn = - currentColumnNumber === 0 && currentRowNumber === 0; - - const isFirstColumnButNotFirstRow = - currentColumnNumber === 0 && currentRowNumber > 0; - - const isNotFirstColumn = currentColumnNumber > 0; - - if (isFirstRowAndFirstColumn) { - return; - } - - if (isNotFirstColumn) { - setSoftFocusPosition({ - row: currentRowNumber, - column: currentColumnNumber - 1, - }); - } else if (isFirstColumnButNotFirstRow) { - setSoftFocusPosition({ - row: currentRowNumber - 1, - column: numberOfTableColumns - 1, - }); - } - }, - [setSoftFocusPosition, tableScopeId], - ); - - return { - moveDown, - moveLeft, - moveRight, - moveUp, - }; -}; diff --git a/front/src/modules/ui/object/record-table/hooks/useRecordTable.ts b/front/src/modules/ui/object/record-table/hooks/useRecordTable.ts new file mode 100644 index 000000000..af44c7128 --- /dev/null +++ b/front/src/modules/ui/object/record-table/hooks/useRecordTable.ts @@ -0,0 +1,316 @@ +import { useRecoilCallback, useSetRecoilState } from 'recoil'; +import { Key } from 'ts-key-enum'; + +import { RecordTableScopeInternalContext } from '@/ui/object/record-table/scopes/scope-internal-context/RecordTableScopeInternalContext'; +import { onColumnsChangeScopedState } from '@/ui/object/record-table/states/onColumnsChangeScopedState'; +import { useScopedHotkeys } from '@/ui/utilities/hotkey/hooks/useScopedHotkeys'; +import { useSetHotkeyScope } from '@/ui/utilities/hotkey/hooks/useSetHotkeyScope'; +import { useAvailableScopeIdOrThrow } from '@/ui/utilities/recoil-scope/scopes-internal/hooks/useAvailableScopeId'; +import { getScopedState } from '@/ui/utilities/recoil-scope/utils/getScopedState'; +import { getSnapshotValue } from '@/ui/utilities/recoil-scope/utils/getSnapshotValue'; + +import { FieldMetadata } from '../../field/types/FieldMetadata'; +import { numberOfTableRowsState } from '../states/numberOfTableRowsState'; +import { onEntityCountChangeScopedState } from '../states/onEntityCountChange'; +import { numberOfTableColumnsScopedSelector } from '../states/selectors/numberOfTableColumnsScopedSelector'; +import { softFocusPositionState } from '../states/softFocusPositionState'; +import { ColumnDefinition } from '../types/ColumnDefinition'; +import { TableHotkeyScope } from '../types/TableHotkeyScope'; + +import { useDisableSoftFocus } from './internal/useDisableSoftFocus'; +import { useGetIsSomeCellInEditMode } from './internal/useGetIsSomeCellInEditMode'; +import { useLeaveTableFocus } from './internal/useLeaveTableFocus'; +import { useRecordTableScopedStates } from './internal/useRecordTableScopedStates'; +import { useResetTableRowSelection } from './internal/useResetTableRowSelection'; +import { useSelectAllRows } from './internal/useSelectAllRows'; +import { useSetRecordTableData } from './internal/useSetRecordTableData'; +import { useSetRowSelectedState } from './internal/useSetRowSelectedState'; +import { useSetSoftFocusPosition } from './internal/useSetSoftFocusPosition'; +import { useUpsertRecordTableItem } from './internal/useUpsertRecordTableItem'; + +type useRecordTableProps = { + recordTableScopeId?: string; +}; + +export const useRecordTable = (props?: useRecordTableProps) => { + const scopeId = useAvailableScopeIdOrThrow( + RecordTableScopeInternalContext, + props?.recordTableScopeId, + ); + + const { + availableTableColumnsState, + tableFiltersState, + tableSortsState, + tableColumnsState, + } = useRecordTableScopedStates({ + customRecordTableScopeId: scopeId, + }); + + const setAvailableTableColumns = useSetRecoilState( + availableTableColumnsState, + ); + + const setTableFilters = useSetRecoilState(tableFiltersState); + + const setTableSorts = useSetRecoilState(tableSortsState); + + const setTableColumns = useSetRecoilState(tableColumnsState); + + const onColumnsChange = useRecoilCallback( + ({ snapshot }) => + (columns: ColumnDefinition[]) => { + const onColumnsChangeState = getScopedState( + onColumnsChangeScopedState, + scopeId, + ); + const onColumnsChange = getSnapshotValue( + snapshot, + onColumnsChangeState, + ); + + onColumnsChange?.(columns); + }, + [scopeId], + ); + + const onEntityCountChange = useRecoilCallback( + ({ snapshot }) => + (count: number) => { + const onEntityCountChangeState = getScopedState( + onEntityCountChangeScopedState, + scopeId, + ); + const onEntityCountChange = getSnapshotValue( + snapshot, + onEntityCountChangeState, + ); + + onEntityCountChange?.(count); + }, + [scopeId], + ); + + const setRecordTableData = useSetRecordTableData({ onEntityCountChange }); + + const leaveTableFocus = useLeaveTableFocus(); + + const getIsSomeCellInEditMode = useGetIsSomeCellInEditMode(); + + const setRowSelectedState = useSetRowSelectedState(); + + const resetTableRowSelection = useResetTableRowSelection(); + + const upsertRecordTableItem = useUpsertRecordTableItem(); + + const setSoftFocusPosition = useSetSoftFocusPosition(); + + const moveUp = useRecoilCallback( + ({ snapshot }) => + () => { + const softFocusPosition = snapshot + .getLoadable(softFocusPositionState) + .valueOrThrow(); + + let newRowNumber = softFocusPosition.row - 1; + + if (newRowNumber < 0) { + newRowNumber = 0; + } + + setSoftFocusPosition({ + ...softFocusPosition, + row: newRowNumber, + }); + }, + [setSoftFocusPosition], + ); + + const moveDown = useRecoilCallback( + ({ snapshot }) => + () => { + const softFocusPosition = snapshot + .getLoadable(softFocusPositionState) + .valueOrThrow(); + + const numberOfTableRows = snapshot + .getLoadable(numberOfTableRowsState) + .valueOrThrow(); + + let newRowNumber = softFocusPosition.row + 1; + + if (newRowNumber >= numberOfTableRows) { + newRowNumber = numberOfTableRows - 1; + } + + setSoftFocusPosition({ + ...softFocusPosition, + row: newRowNumber, + }); + }, + [setSoftFocusPosition], + ); + + const moveRight = useRecoilCallback( + ({ snapshot }) => + () => { + const softFocusPosition = snapshot + .getLoadable(softFocusPositionState) + .valueOrThrow(); + + const numberOfTableColumns = snapshot + .getLoadable(numberOfTableColumnsScopedSelector(scopeId)) + .valueOrThrow(); + + const numberOfTableRows = snapshot + .getLoadable(numberOfTableRowsState) + .valueOrThrow(); + + const currentColumnNumber = softFocusPosition.column; + const currentRowNumber = softFocusPosition.row; + + const isLastRowAndLastColumn = + currentColumnNumber === numberOfTableColumns - 1 && + currentRowNumber === numberOfTableRows - 1; + + const isLastColumnButNotLastRow = + currentColumnNumber === numberOfTableColumns - 1 && + currentRowNumber !== numberOfTableRows - 1; + + const isNotLastColumn = + currentColumnNumber !== numberOfTableColumns - 1; + + if (isLastRowAndLastColumn) { + return; + } + + if (isNotLastColumn) { + setSoftFocusPosition({ + row: currentRowNumber, + column: currentColumnNumber + 1, + }); + } else if (isLastColumnButNotLastRow) { + setSoftFocusPosition({ + row: currentRowNumber + 1, + column: 0, + }); + } + }, + [scopeId, setSoftFocusPosition], + ); + + const moveLeft = useRecoilCallback( + ({ snapshot }) => + () => { + const softFocusPosition = snapshot + .getLoadable(softFocusPositionState) + .valueOrThrow(); + + const numberOfTableColumns = snapshot + .getLoadable(numberOfTableColumnsScopedSelector(scopeId)) + .valueOrThrow(); + + const currentColumnNumber = softFocusPosition.column; + const currentRowNumber = softFocusPosition.row; + + const isFirstRowAndFirstColumn = + currentColumnNumber === 0 && currentRowNumber === 0; + + const isFirstColumnButNotFirstRow = + currentColumnNumber === 0 && currentRowNumber > 0; + + const isNotFirstColumn = currentColumnNumber > 0; + + if (isFirstRowAndFirstColumn) { + return; + } + + if (isNotFirstColumn) { + setSoftFocusPosition({ + row: currentRowNumber, + column: currentColumnNumber - 1, + }); + } else if (isFirstColumnButNotFirstRow) { + setSoftFocusPosition({ + row: currentRowNumber - 1, + column: numberOfTableColumns - 1, + }); + } + }, + [scopeId, setSoftFocusPosition], + ); + + const useMapKeyboardToSoftFocus = () => { + const disableSoftFocus = useDisableSoftFocus(); + const setHotkeyScope = useSetHotkeyScope(); + + useScopedHotkeys( + [Key.ArrowUp, `${Key.Shift}+${Key.Enter}`], + () => { + moveUp(); + }, + TableHotkeyScope.TableSoftFocus, + [moveUp], + ); + + useScopedHotkeys( + Key.ArrowDown, + () => { + moveDown(); + }, + TableHotkeyScope.TableSoftFocus, + [moveDown], + ); + + useScopedHotkeys( + [Key.ArrowLeft, `${Key.Shift}+${Key.Tab}`], + () => { + moveLeft(); + }, + TableHotkeyScope.TableSoftFocus, + [moveLeft], + ); + + useScopedHotkeys( + [Key.ArrowRight, Key.Tab], + () => { + moveRight(); + }, + TableHotkeyScope.TableSoftFocus, + [moveRight], + ); + + useScopedHotkeys( + [Key.Escape], + () => { + setHotkeyScope(TableHotkeyScope.Table, { goto: true }); + disableSoftFocus(); + }, + TableHotkeyScope.TableSoftFocus, + [disableSoftFocus], + ); + }; + + const { selectAllRows } = useSelectAllRows(); + + return { + scopeId, + onColumnsChange, + setAvailableTableColumns, + setTableFilters, + setTableSorts, + setRecordTableData, + setTableColumns, + leaveTableFocus, + getIsSomeCellInEditMode, + setRowSelectedState, + resetTableRowSelection, + upsertRecordTableItem, + moveDown, + moveLeft, + moveRight, + moveUp, + useMapKeyboardToSoftFocus, + selectAllRows, + }; +}; diff --git a/front/src/modules/ui/object/record-table/hooks/useTableColumns.ts b/front/src/modules/ui/object/record-table/hooks/useTableColumns.ts index d60b463f3..1e8f380de 100644 --- a/front/src/modules/ui/object/record-table/hooks/useTableColumns.ts +++ b/front/src/modules/ui/object/record-table/hooks/useTableColumns.ts @@ -1,42 +1,35 @@ -import { useCallback, useContext } from 'react'; -import { useSetRecoilState } from 'recoil'; +import { useCallback } from 'react'; +import { useRecoilValue, useSetRecoilState } from 'recoil'; import { FieldMetadata } from '@/ui/object/field/types/FieldMetadata'; -import { useMoveViewColumns } from '@/ui/object/record-table/hooks/useMoveViewColumns'; -import { useRecoilScopedState } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedState'; -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; +import { useMoveViewColumns } from '@/views/hooks/useMoveViewColumns'; import { useView } from '@/views/hooks/useView'; -import { TableContext } from '../contexts/TableContext'; -import { availableTableColumnsScopedState } from '../states/availableTableColumnsScopedState'; -import { TableRecoilScopeContext } from '../states/recoil-scope-contexts/TableRecoilScopeContext'; import { savedTableColumnsFamilyState } from '../states/savedTableColumnsFamilyState'; -import { visibleTableColumnsScopedSelector } from '../states/selectors/visibleTableColumnsScopedSelector'; -import { tableColumnsScopedState } from '../states/tableColumnsScopedState'; import { ColumnDefinition } from '../types/ColumnDefinition'; -export const useTableColumns = () => { - const { onColumnsChange } = useContext(TableContext); +import { useRecordTableScopedStates } from './internal/useRecordTableScopedStates'; - const [availableTableColumns] = useRecoilScopedState( - availableTableColumnsScopedState, - TableRecoilScopeContext, - ); +export const useTableColumns = () => { + const { onColumnsChange, setTableColumns } = useRecordTable(); + const { + availableTableColumnsState, + tableColumnsState, + visibleTableColumnsSelector, + } = useRecordTableScopedStates(); + + const availableTableColumns = useRecoilValue(availableTableColumnsState); const { currentViewId } = useView(); const setSavedTableColumns = useSetRecoilState( savedTableColumnsFamilyState(currentViewId), ); - const [tableColumns, setTableColumns] = useRecoilScopedState( - tableColumnsScopedState, - TableRecoilScopeContext, - ); - const visibleTableColumns = useRecoilScopedValue( - visibleTableColumnsScopedSelector, - TableRecoilScopeContext, - ); + const tableColumns = useRecoilValue(tableColumnsState); + const visibleTableColumns = useRecoilValue(visibleTableColumnsSelector); + const { handleColumnMove } = useMoveViewColumns(); const handleColumnsChange = useCallback( diff --git a/front/src/modules/ui/object/record-table/hooks/useUpsertRecordTableItems.ts b/front/src/modules/ui/object/record-table/hooks/useUpsertRecordTableItems.ts deleted file mode 100644 index d9e47e91d..000000000 --- a/front/src/modules/ui/object/record-table/hooks/useUpsertRecordTableItems.ts +++ /dev/null @@ -1,33 +0,0 @@ -import { useRecoilCallback } from 'recoil'; - -import { entityFieldsFamilyState } from '@/ui/object/field/states/entityFieldsFamilyState'; - -export const useUpsertRecordTableItems = () => - useRecoilCallback( - ({ set, snapshot }) => - (entities: T[]) => { - // Create a map of new entities for quick lookup. - const newEntityMap = new Map( - entities.map((entity) => [entity.id, entity]), - ); - - // Filter out entities that are already the same in the state. - const entitiesToUpdate = entities.filter((entity) => { - const currentEntity = snapshot - .getLoadable(entityFieldsFamilyState(entity.id)) - .valueMaybe(); - - return ( - !currentEntity || - JSON.stringify(currentEntity) !== - JSON.stringify(newEntityMap.get(entity.id)) - ); - }); - - // Batch set state for the filtered entities. - for (const entity of entitiesToUpdate) { - set(entityFieldsFamilyState(entity.id), entity); - } - }, - [], - ); diff --git a/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowId.ts b/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowId.ts index 5200823b5..540aea6a9 100644 --- a/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowId.ts +++ b/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowId.ts @@ -2,6 +2,9 @@ import { useRecoilCallback } from 'recoil'; import { tableRowIdsState } from '../states/tableRowIdsState'; +// Used only in company table and people table +// Remove after refactoring + export const useUpsertTableRowId = () => useRecoilCallback( ({ set, snapshot }) => diff --git a/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowIds.ts b/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowIds.ts deleted file mode 100644 index 4981be430..000000000 --- a/front/src/modules/ui/object/record-table/hooks/useUpsertTableRowIds.ts +++ /dev/null @@ -1,17 +0,0 @@ -import { useRecoilCallback } from 'recoil'; - -import { tableRowIdsState } from '../states/tableRowIdsState'; - -export const useUpsertTableRowIds = () => - useRecoilCallback( - ({ set, snapshot }) => - (rowIds: string[]) => { - const currentRowIds = snapshot - .getLoadable(tableRowIdsState) - .valueOrThrow(); - - const uniqueRowIds = Array.from(new Set([...rowIds, ...currentRowIds])); - set(tableRowIdsState, uniqueRowIds); - }, - [], - ); diff --git a/front/src/modules/ui/object/record-table/options/components/TableOptionsDropdownContent.tsx b/front/src/modules/ui/object/record-table/options/components/TableOptionsDropdownContent.tsx index 1b4861050..d9c560227 100644 --- a/front/src/modules/ui/object/record-table/options/components/TableOptionsDropdownContent.tsx +++ b/front/src/modules/ui/object/record-table/options/components/TableOptionsDropdownContent.tsx @@ -11,15 +11,12 @@ import { DropdownMenuSeparator } from '@/ui/layout/dropdown/components/DropdownM import { useDropdown } from '@/ui/layout/dropdown/hooks/useDropdown'; import { MenuItem } from '@/ui/navigation/menu-item/components/MenuItem'; import { useScopedHotkeys } from '@/ui/utilities/hotkey/hooks/useScopedHotkeys'; -import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue'; import { ViewFieldsVisibilityDropdownSection } from '@/views/components/ViewFieldsVisibilityDropdownSection'; import { useViewScopedStates } from '@/views/hooks/internal/useViewScopedStates'; import { useView } from '@/views/hooks/useView'; +import { useRecordTableScopedStates } from '../../hooks/internal/useRecordTableScopedStates'; import { useTableColumns } from '../../hooks/useTableColumns'; -import { TableRecoilScopeContext } from '../../states/recoil-scope-contexts/TableRecoilScopeContext'; -import { hiddenTableColumnsScopedSelector } from '../../states/selectors/hiddenTableColumnsScopedSelector'; -import { visibleTableColumnsScopedSelector } from '../../states/selectors/visibleTableColumnsScopedSelector'; import { TableOptionsHotkeyScope } from '../../types/TableOptionsHotkeyScope'; type TableOptionsMenu = 'fields'; @@ -43,14 +40,11 @@ export const TableOptionsDropdownContent = ({ const viewEditInputRef = useRef(null); - const visibleTableColumns = useRecoilScopedValue( - visibleTableColumnsScopedSelector, - TableRecoilScopeContext, - ); - const hiddenTableColumns = useRecoilScopedValue( - hiddenTableColumnsScopedSelector, - TableRecoilScopeContext, - ); + const { hiddenTableColumnsSelector, visibleTableColumnsSelector } = + useRecordTableScopedStates(); + + const hiddenTableColumns = useRecoilValue(hiddenTableColumnsSelector); + const visibleTableColumns = useRecoilValue(visibleTableColumnsSelector); const { handleColumnVisibilityChange, handleColumnReorder } = useTableColumns(); diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCell.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCell.tsx similarity index 89% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCell.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCell.tsx index 1b42ecb47..0dbc57078 100644 --- a/front/src/modules/ui/object/record-table/table-cell/components/TableCell.tsx +++ b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCell.tsx @@ -3,10 +3,10 @@ import { FieldInput } from '@/ui/object/field/components/FieldInput'; import { FieldInputEvent } from '@/ui/object/field/types/FieldInputEvent'; import { HotkeyScope } from '@/ui/utilities/hotkey/types/HotkeyScope'; -import { useMoveSoftFocus } from '../../hooks/useMoveSoftFocus'; +import { useRecordTable } from '../../hooks/useRecordTable'; import { useTableCell } from '../hooks/useTableCell'; -import { TableCellContainer } from './TableCellContainer'; +import { TableCellContainer } from './RecordTableCellContainer'; export const TableCell = ({ customHotkeyScope, @@ -15,7 +15,7 @@ export const TableCell = ({ }) => { const { closeTableCell } = useTableCell(); - const { moveLeft, moveRight, moveDown } = useMoveSoftFocus(); + const { moveLeft, moveRight, moveDown } = useRecordTable(); const handleEnter: FieldInputEvent = (persistField) => { persistField(); diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellButton.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellButton.tsx similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellButton.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellButton.tsx diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellContainer.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellContainer.tsx similarity index 89% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellContainer.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellContainer.tsx index f664f1b10..0d94a332a 100644 --- a/front/src/modules/ui/object/record-table/table-cell/components/TableCellContainer.tsx +++ b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellContainer.tsx @@ -9,18 +9,18 @@ import { HotkeyScope } from '@/ui/utilities/hotkey/types/HotkeyScope'; import { CellHotkeyScopeContext } from '../../contexts/CellHotkeyScopeContext'; import { ColumnIndexContext } from '../../contexts/ColumnIndexContext'; -import { useGetIsSomeCellInEditMode } from '../../hooks/useGetIsSomeCellInEditMode'; -import { useMoveSoftFocusToCurrentCellOnHover } from '../../hooks/useMoveSoftFocusToCurrentCellOnHover'; +import { useRecordTable } from '../../hooks/useRecordTable'; import { TableHotkeyScope } from '../../types/TableHotkeyScope'; import { useCurrentTableCellEditMode } from '../hooks/useCurrentTableCellEditMode'; import { useIsSoftFocusOnCurrentTableCell } from '../hooks/useIsSoftFocusOnCurrentTableCell'; +import { useMoveSoftFocusToCurrentCellOnHover } from '../hooks/useMoveSoftFocusToCurrentCellOnHover'; import { useSetSoftFocusOnCurrentTableCell } from '../hooks/useSetSoftFocusOnCurrentTableCell'; import { useTableCell } from '../hooks/useTableCell'; -import { TableCellButton } from './TableCellButton'; -import { TableCellDisplayMode } from './TableCellDisplayMode'; -import { TableCellEditMode } from './TableCellEditMode'; -import { TableCellSoftFocusMode } from './TableCellSoftFocusMode'; +import { TableCellButton } from './RecordTableCellButton'; +import { TableCellDisplayMode } from './RecordTableCellDisplayMode'; +import { TableCellEditMode } from './RecordTableCellEditMode'; +import { TableCellSoftFocusMode } from './RecordTableCellSoftFocusMode'; const StyledCellBaseContainer = styled.div` align-items: center; @@ -57,7 +57,7 @@ export const TableCellContainer = ({ }: TableCellContainerProps) => { const { isCurrentTableCellInEditMode } = useCurrentTableCellEditMode(); - const getIsSomeCellInEditMode = useGetIsSomeCellInEditMode(); + const { getIsSomeCellInEditMode } = useRecordTable(); const [isHovered, setIsHovered] = useState(false); diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellDisplayContainer.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellDisplayContainer.tsx similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellDisplayContainer.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellDisplayContainer.tsx diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellDisplayMode.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellDisplayMode.tsx similarity index 90% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellDisplayMode.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellDisplayMode.tsx index ad6898711..6e43fd755 100644 --- a/front/src/modules/ui/object/record-table/table-cell/components/TableCellDisplayMode.tsx +++ b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellDisplayMode.tsx @@ -3,7 +3,7 @@ import { useIsFieldInputOnly } from '@/ui/object/field/hooks/useIsFieldInputOnly import { useSetSoftFocusOnCurrentTableCell } from '../hooks/useSetSoftFocusOnCurrentTableCell'; import { useTableCell } from '../hooks/useTableCell'; -import { TableCellDisplayContainer } from './TableCellDisplayContainer'; +import { TableCellDisplayContainer } from './RecordTableCellDisplayContainer'; export const TableCellDisplayMode = ({ children, diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellEditButton.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellEditButton.tsx similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellEditButton.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellEditButton.tsx diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellEditMode.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellEditMode.tsx similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellEditMode.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellEditMode.tsx diff --git a/front/src/modules/ui/object/record-table/table-cell/components/TableCellSoftFocusMode.tsx b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellSoftFocusMode.tsx similarity index 96% rename from front/src/modules/ui/object/record-table/table-cell/components/TableCellSoftFocusMode.tsx rename to front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellSoftFocusMode.tsx index 9e5a91363..932f7291f 100644 --- a/front/src/modules/ui/object/record-table/table-cell/components/TableCellSoftFocusMode.tsx +++ b/front/src/modules/ui/object/record-table/record-table-cell/components/RecordTableCellSoftFocusMode.tsx @@ -9,7 +9,7 @@ import { isNonTextWritingKey } from '@/ui/utilities/hotkey/utils/isNonTextWritin import { TableHotkeyScope } from '../../types/TableHotkeyScope'; import { useTableCell } from '../hooks/useTableCell'; -import { TableCellDisplayContainer } from './TableCellDisplayContainer'; +import { TableCellDisplayContainer } from './RecordTableCellDisplayContainer'; type TableCellSoftFocusModeProps = PropsWithChildren; diff --git a/front/src/modules/ui/object/record-table/table-cell/hooks/useCurrentCellPosition.ts b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useCurrentCellPosition.ts similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/hooks/useCurrentCellPosition.ts rename to front/src/modules/ui/object/record-table/record-table-cell/hooks/useCurrentCellPosition.ts diff --git a/front/src/modules/ui/object/record-table/table-cell/hooks/useCurrentTableCellEditMode.ts b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useCurrentTableCellEditMode.ts similarity index 95% rename from front/src/modules/ui/object/record-table/table-cell/hooks/useCurrentTableCellEditMode.ts rename to front/src/modules/ui/object/record-table/record-table-cell/hooks/useCurrentTableCellEditMode.ts index 98759de86..f446d2f4f 100644 --- a/front/src/modules/ui/object/record-table/table-cell/hooks/useCurrentTableCellEditMode.ts +++ b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useCurrentTableCellEditMode.ts @@ -1,7 +1,7 @@ import { useCallback } from 'react'; import { useRecoilState } from 'recoil'; -import { useMoveEditModeToTableCellPosition } from '../../hooks/useMoveEditModeToCellPosition'; +import { useMoveEditModeToTableCellPosition } from '../../hooks/internal/useMoveEditModeToCellPosition'; import { isTableCellInEditModeFamilyState } from '../../states/isTableCellInEditModeFamilyState'; import { useCurrentTableCellPosition } from './useCurrentCellPosition'; diff --git a/front/src/modules/ui/object/record-table/table-cell/hooks/useIsSoftFocusOnCurrentTableCell.ts b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useIsSoftFocusOnCurrentTableCell.ts similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/hooks/useIsSoftFocusOnCurrentTableCell.ts rename to front/src/modules/ui/object/record-table/record-table-cell/hooks/useIsSoftFocusOnCurrentTableCell.ts diff --git a/front/src/modules/ui/object/record-table/hooks/useMoveSoftFocusToCurrentCellOnHover.ts b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useMoveSoftFocusToCurrentCellOnHover.ts similarity index 75% rename from front/src/modules/ui/object/record-table/hooks/useMoveSoftFocusToCurrentCellOnHover.ts rename to front/src/modules/ui/object/record-table/record-table-cell/hooks/useMoveSoftFocusToCurrentCellOnHover.ts index 8e406dc49..b358e3612 100644 --- a/front/src/modules/ui/object/record-table/hooks/useMoveSoftFocusToCurrentCellOnHover.ts +++ b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useMoveSoftFocusToCurrentCellOnHover.ts @@ -2,10 +2,11 @@ import { useRecoilCallback } from 'recoil'; import { currentHotkeyScopeState } from '@/ui/utilities/hotkey/states/internal/currentHotkeyScopeState'; -import { currentTableCellInEditModePositionState } from '../states/currentTableCellInEditModePositionState'; -import { isTableCellInEditModeFamilyState } from '../states/isTableCellInEditModeFamilyState'; -import { useSetSoftFocusOnCurrentTableCell } from '../table-cell/hooks/useSetSoftFocusOnCurrentTableCell'; -import { TableHotkeyScope } from '../types/TableHotkeyScope'; +import { currentTableCellInEditModePositionState } from '../../states/currentTableCellInEditModePositionState'; +import { isTableCellInEditModeFamilyState } from '../../states/isTableCellInEditModeFamilyState'; +import { TableHotkeyScope } from '../../types/TableHotkeyScope'; + +import { useSetSoftFocusOnCurrentTableCell } from './useSetSoftFocusOnCurrentTableCell'; export const useMoveSoftFocusToCurrentCellOnHover = () => { const setSoftFocusOnCurrentTableCell = useSetSoftFocusOnCurrentTableCell(); diff --git a/front/src/modules/ui/object/record-table/table-cell/hooks/useSetSoftFocusOnCurrentTableCell.ts b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useSetSoftFocusOnCurrentTableCell.ts similarity index 90% rename from front/src/modules/ui/object/record-table/table-cell/hooks/useSetSoftFocusOnCurrentTableCell.ts rename to front/src/modules/ui/object/record-table/record-table-cell/hooks/useSetSoftFocusOnCurrentTableCell.ts index e734d9f29..8c5fcd1d3 100644 --- a/front/src/modules/ui/object/record-table/table-cell/hooks/useSetSoftFocusOnCurrentTableCell.ts +++ b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useSetSoftFocusOnCurrentTableCell.ts @@ -2,7 +2,7 @@ import { useRecoilCallback } from 'recoil'; import { useSetHotkeyScope } from '@/ui/utilities/hotkey/hooks/useSetHotkeyScope'; -import { useSetSoftFocusPosition } from '../../hooks/useSetSoftFocusPosition'; +import { useSetSoftFocusPosition } from '../../hooks/internal/useSetSoftFocusPosition'; import { isSoftFocusActiveState } from '../../states/isSoftFocusActiveState'; import { TableHotkeyScope } from '../../types/TableHotkeyScope'; diff --git a/front/src/modules/ui/object/record-table/table-cell/hooks/useTableCell.ts b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useTableCell.ts similarity index 98% rename from front/src/modules/ui/object/record-table/table-cell/hooks/useTableCell.ts rename to front/src/modules/ui/object/record-table/record-table-cell/hooks/useTableCell.ts index d8423411d..9b7d357ac 100644 --- a/front/src/modules/ui/object/record-table/table-cell/hooks/useTableCell.ts +++ b/front/src/modules/ui/object/record-table/record-table-cell/hooks/useTableCell.ts @@ -12,7 +12,7 @@ import { HotkeyScope } from '@/ui/utilities/hotkey/types/HotkeyScope'; import { CellHotkeyScopeContext } from '../../contexts/CellHotkeyScopeContext'; import { ColumnIndexContext } from '../../contexts/ColumnIndexContext'; -import { useCloseCurrentTableCellInEditMode } from '../../hooks/useCloseCurrentTableCellInEditMode'; +import { useCloseCurrentTableCellInEditMode } from '../../hooks/internal/useCloseCurrentTableCellInEditMode'; import { TableHotkeyScope } from '../../types/TableHotkeyScope'; import { useCurrentTableCellEditMode } from './useCurrentTableCellEditMode'; diff --git a/front/src/modules/ui/object/record-table/table-cell/states/isCreateModeScopedState.ts b/front/src/modules/ui/object/record-table/record-table-cell/states/isCreateModeScopedState.ts similarity index 100% rename from front/src/modules/ui/object/record-table/table-cell/states/isCreateModeScopedState.ts rename to front/src/modules/ui/object/record-table/record-table-cell/states/isCreateModeScopedState.ts diff --git a/front/src/modules/ui/object/record-table/hooks/useCurrentRowSelected.ts b/front/src/modules/ui/object/record-table/record-table-row/hooks/useCurrentRowSelected.ts similarity index 94% rename from front/src/modules/ui/object/record-table/hooks/useCurrentRowSelected.ts rename to front/src/modules/ui/object/record-table/record-table-row/hooks/useCurrentRowSelected.ts index 4558b46d7..dddb5a464 100644 --- a/front/src/modules/ui/object/record-table/hooks/useCurrentRowSelected.ts +++ b/front/src/modules/ui/object/record-table/record-table-row/hooks/useCurrentRowSelected.ts @@ -1,7 +1,7 @@ import { useContext } from 'react'; import { useRecoilCallback, useRecoilState } from 'recoil'; -import { RowIdContext } from '../contexts/RowIdContext'; +import { RowIdContext } from '../../contexts/RowIdContext'; import { isRowSelectedFamilyState } from '../states/isRowSelectedFamilyState'; export const useCurrentRowSelected = () => { diff --git a/front/src/modules/ui/object/record-table/states/isRowSelectedFamilyState.ts b/front/src/modules/ui/object/record-table/record-table-row/states/isRowSelectedFamilyState.ts similarity index 100% rename from front/src/modules/ui/object/record-table/states/isRowSelectedFamilyState.ts rename to front/src/modules/ui/object/record-table/record-table-row/states/isRowSelectedFamilyState.ts diff --git a/front/src/modules/ui/object/record-table/scopes/RecordTableScope.tsx b/front/src/modules/ui/object/record-table/scopes/RecordTableScope.tsx new file mode 100644 index 000000000..e17592bea --- /dev/null +++ b/front/src/modules/ui/object/record-table/scopes/RecordTableScope.tsx @@ -0,0 +1,37 @@ +import { ReactNode } from 'react'; + +import { FieldMetadata } from '../../field/types/FieldMetadata'; +import { ColumnDefinition } from '../types/ColumnDefinition'; + +import { RecordTableScopeInternalContext } from './scope-internal-context/RecordTableScopeInternalContext'; +import { RecordTableScopeInitEffect } from './RecordTableScopeInitEffect'; + +type RecordTableScopeProps = { + children: ReactNode; + recordTableScopeId: string; + onColumnsChange: (columns: ColumnDefinition[]) => void; + onEntityCountChange: (entityCount: number) => void; +}; + +export const RecordTableScope = ({ + children, + recordTableScopeId, + onColumnsChange, + onEntityCountChange, +}: RecordTableScopeProps) => { + return ( + + + {children} + + ); +}; diff --git a/front/src/modules/ui/object/record-table/scopes/RecordTableScopeInitEffect.tsx b/front/src/modules/ui/object/record-table/scopes/RecordTableScopeInitEffect.tsx new file mode 100644 index 000000000..310691ff5 --- /dev/null +++ b/front/src/modules/ui/object/record-table/scopes/RecordTableScopeInitEffect.tsx @@ -0,0 +1,34 @@ +import { useEffect } from 'react'; +import { useSetRecoilState } from 'recoil'; + +import { FieldMetadata } from '../../field/types/FieldMetadata'; +import { useRecordTableScopedStates } from '../hooks/internal/useRecordTableScopedStates'; +import { ColumnDefinition } from '../types/ColumnDefinition'; + +type RecordTableScopeInitEffectProps = { + onColumnsChange: (columns: ColumnDefinition[]) => void; + onEntityCountChange?: (count: number) => void | Promise; +}; + +export const RecordTableScopeInitEffect = ({ + onColumnsChange, + onEntityCountChange, +}: RecordTableScopeInitEffectProps) => { + const { onColumnsChangeState, onEntityCountChangeState } = + useRecordTableScopedStates(); + + const setOnEntityCountChange = useSetRecoilState(onEntityCountChangeState); + const setOnColumnsChange = useSetRecoilState(onColumnsChangeState); + + useEffect(() => { + setOnEntityCountChange(() => onEntityCountChange); + setOnColumnsChange(() => onColumnsChange); + }, [ + onColumnsChange, + onEntityCountChange, + setOnColumnsChange, + setOnEntityCountChange, + ]); + + return <>; +}; diff --git a/front/src/modules/ui/object/record-table/scopes/scope-internal-context/RecordTableScopeInternalContext.ts b/front/src/modules/ui/object/record-table/scopes/scope-internal-context/RecordTableScopeInternalContext.ts new file mode 100644 index 000000000..1fab91ccf --- /dev/null +++ b/front/src/modules/ui/object/record-table/scopes/scope-internal-context/RecordTableScopeInternalContext.ts @@ -0,0 +1,13 @@ +import { FieldMetadata } from '@/ui/object/field/types/FieldMetadata'; +import { ScopedStateKey } from '@/ui/utilities/recoil-scope/scopes-internal/types/ScopedStateKey'; +import { createScopeInternalContext } from '@/ui/utilities/recoil-scope/scopes-internal/utils/createScopeInternalContext'; + +import { ColumnDefinition } from '../../types/ColumnDefinition'; + +type RecordTableScopeInternalContextProps = ScopedStateKey & { + onColumnsChange: (columns: ColumnDefinition[]) => void; + onEntityCountChange: (entityCount: number) => void; +}; + +export const RecordTableScopeInternalContext = + createScopeInternalContext(); diff --git a/front/src/modules/ui/object/record-table/states/availableTableColumnsScopedState.ts b/front/src/modules/ui/object/record-table/states/availableTableColumnsScopedState.ts index c5c283811..c3a06e985 100644 --- a/front/src/modules/ui/object/record-table/states/availableTableColumnsScopedState.ts +++ b/front/src/modules/ui/object/record-table/states/availableTableColumnsScopedState.ts @@ -1,13 +1,11 @@ -import { atomFamily } from 'recoil'; - import { FieldMetadata } from '@/ui/object/field/types/FieldMetadata'; +import { createScopedState } from '@/ui/utilities/recoil-scope/utils/createScopedState'; import { ColumnDefinition } from '../types/ColumnDefinition'; -export const availableTableColumnsScopedState = atomFamily< - ColumnDefinition[], - string +export const availableTableColumnsScopedState = createScopedState< + ColumnDefinition[] >({ key: 'availableTableColumnsScopedState', - default: [], + defaultValue: [], }); diff --git a/front/src/modules/ui/object/record-table/states/onColumnsChangeScopedState.ts b/front/src/modules/ui/object/record-table/states/onColumnsChangeScopedState.ts new file mode 100644 index 000000000..88c183a58 --- /dev/null +++ b/front/src/modules/ui/object/record-table/states/onColumnsChangeScopedState.ts @@ -0,0 +1,11 @@ +import { createScopedState } from '@/ui/utilities/recoil-scope/utils/createScopedState'; + +import { FieldMetadata } from '../../field/types/FieldMetadata'; +import { ColumnDefinition } from '../types/ColumnDefinition'; + +export const onColumnsChangeScopedState = createScopedState< + ((columns: ColumnDefinition[]) => void) | undefined +>({ + key: 'onColumnsChangeScopedState', + defaultValue: undefined, +}); diff --git a/front/src/modules/ui/object/record-table/states/onEntityCountChange.ts b/front/src/modules/ui/object/record-table/states/onEntityCountChange.ts new file mode 100644 index 000000000..b28896936 --- /dev/null +++ b/front/src/modules/ui/object/record-table/states/onEntityCountChange.ts @@ -0,0 +1,8 @@ +import { createScopedState } from '@/ui/utilities/recoil-scope/utils/createScopedState'; + +export const onEntityCountChangeScopedState = createScopedState< + ((entityCount: number) => void) | undefined +>({ + key: 'onEntityCountChangeScopedState', + defaultValue: undefined, +}); diff --git a/front/src/modules/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext.ts b/front/src/modules/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext.ts deleted file mode 100644 index e1305044f..000000000 --- a/front/src/modules/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext.ts +++ /dev/null @@ -1,3 +0,0 @@ -import { createContext } from 'react'; - -export const TableRecoilScopeContext = createContext(null); diff --git a/front/src/modules/ui/object/record-table/states/selectors/hiddenTableColumnsScopedSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/hiddenTableColumnsScopedSelector.ts index da895b8ef..d672233f8 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/hiddenTableColumnsScopedSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/hiddenTableColumnsScopedSelector.ts @@ -8,10 +8,10 @@ export const hiddenTableColumnsScopedSelector = selectorFamily({ get: (scopeId: string) => ({ get }) => { - const columns = get(tableColumnsScopedState(scopeId)); + const columns = get(tableColumnsScopedState({ scopeId })); const columnKeys = columns.map(({ fieldId }) => fieldId); const otherAvailableColumns = get( - availableTableColumnsScopedState(scopeId), + availableTableColumnsScopedState({ scopeId }), ).filter(({ fieldId }) => !columnKeys.includes(fieldId)); return [ diff --git a/front/src/modules/ui/object/record-table/states/selectors/numberOfTableColumnsScopedSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/numberOfTableColumnsScopedSelector.ts index 09a8533a6..e05138b88 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/numberOfTableColumnsScopedSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/numberOfTableColumnsScopedSelector.ts @@ -7,5 +7,5 @@ export const numberOfTableColumnsScopedSelector = selectorFamily({ get: (scopeId: string) => ({ get }) => - get(tableColumnsScopedState(scopeId)).length, + get(tableColumnsScopedState({ scopeId })).length, }); diff --git a/front/src/modules/ui/object/record-table/states/selectors/selectedRowIdsSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/selectedRowIdsSelector.ts index b64e0fbe4..de58b51c4 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/selectedRowIdsSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/selectedRowIdsSelector.ts @@ -1,6 +1,6 @@ import { selector } from 'recoil'; -import { isRowSelectedFamilyState } from '../isRowSelectedFamilyState'; +import { isRowSelectedFamilyState } from '../../record-table-row/states/isRowSelectedFamilyState'; import { tableRowIdsState } from '../tableRowIdsState'; export const selectedRowIdsSelector = selector({ diff --git a/front/src/modules/ui/object/record-table/states/selectors/tableColumnsByKeyScopedSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/tableColumnsByKeyScopedSelector.ts index c7de54f1c..419e32b55 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/tableColumnsByKeyScopedSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/tableColumnsByKeyScopedSelector.ts @@ -10,7 +10,7 @@ export const tableColumnsByKeyScopedSelector = selectorFamily({ get: (scopeId: string) => ({ get }) => - get(tableColumnsScopedState(scopeId)).reduce< + get(tableColumnsScopedState({ scopeId })).reduce< Record> >((result, column) => ({ ...result, [column.fieldId]: column }), {}), }); diff --git a/front/src/modules/ui/object/record-table/states/selectors/tableSortsOrderByScopedSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/tableSortsOrderByScopedSelector.ts index b57c2437c..3c866934b 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/tableSortsOrderByScopedSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/tableSortsOrderByScopedSelector.ts @@ -10,7 +10,9 @@ export const tableSortsOrderByScopedSelector = selectorFamily({ get: (scopeId: string) => ({ get }) => { - const orderBy = reduceSortsToOrderBy(get(tableSortsScopedState(scopeId))); + const orderBy = reduceSortsToOrderBy( + get(tableSortsScopedState({ scopeId })), + ); return orderBy.length ? orderBy : [{ createdAt: SortOrder.Desc }]; }, }); diff --git a/front/src/modules/ui/object/record-table/states/selectors/tablefiltersWhereScopedSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/tablefiltersWhereScopedSelector.ts index 0bdf3a711..f013cb59b 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/tablefiltersWhereScopedSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/tablefiltersWhereScopedSelector.ts @@ -3,11 +3,13 @@ import { selectorFamily } from 'recoil'; import { turnFilterIntoWhereClause } from '../../../object-filter-dropdown/utils/turnFilterIntoWhereClause'; import { tableFiltersScopedState } from '../tableFiltersScopedState'; -export const tablefiltersWhereScopedSelector = selectorFamily({ +export const tableFiltersWhereScopedSelector = selectorFamily({ key: 'tablefiltersWhereScopedSelector', get: (scopeId: string) => ({ get }) => ({ - AND: get(tableFiltersScopedState(scopeId)).map(turnFilterIntoWhereClause), + AND: get(tableFiltersScopedState({ scopeId })).map( + turnFilterIntoWhereClause, + ), }), }); diff --git a/front/src/modules/ui/object/record-table/states/selectors/visibleTableColumnsScopedSelector.ts b/front/src/modules/ui/object/record-table/states/selectors/visibleTableColumnsScopedSelector.ts index e5d879b70..476a1a1d3 100644 --- a/front/src/modules/ui/object/record-table/states/selectors/visibleTableColumnsScopedSelector.ts +++ b/front/src/modules/ui/object/record-table/states/selectors/visibleTableColumnsScopedSelector.ts @@ -8,9 +8,9 @@ export const visibleTableColumnsScopedSelector = selectorFamily({ get: (scopeId: string) => ({ get }) => { - const columns = get(tableColumnsScopedState(scopeId)); + const columns = get(tableColumnsScopedState({ scopeId })); const availableColumnKeys = get( - availableTableColumnsScopedState(scopeId), + availableTableColumnsScopedState({ scopeId }), ).map(({ fieldId }) => fieldId); return [...columns] diff --git a/front/src/modules/ui/object/record-table/states/tableColumnsScopedState.ts b/front/src/modules/ui/object/record-table/states/tableColumnsScopedState.ts index 23d406e78..412c9417d 100644 --- a/front/src/modules/ui/object/record-table/states/tableColumnsScopedState.ts +++ b/front/src/modules/ui/object/record-table/states/tableColumnsScopedState.ts @@ -1,13 +1,11 @@ -import { atomFamily } from 'recoil'; - import { FieldMetadata } from '@/ui/object/field/types/FieldMetadata'; +import { createScopedState } from '@/ui/utilities/recoil-scope/utils/createScopedState'; import { ColumnDefinition } from '../types/ColumnDefinition'; -export const tableColumnsScopedState = atomFamily< - ColumnDefinition[], - string +export const tableColumnsScopedState = createScopedState< + ColumnDefinition[] >({ key: 'tableColumnsScopedState', - default: [], + defaultValue: [], }); diff --git a/front/src/modules/ui/object/record-table/states/tableFiltersScopedState.ts b/front/src/modules/ui/object/record-table/states/tableFiltersScopedState.ts index 9a54bbce6..5206f3fd7 100644 --- a/front/src/modules/ui/object/record-table/states/tableFiltersScopedState.ts +++ b/front/src/modules/ui/object/record-table/states/tableFiltersScopedState.ts @@ -1,8 +1,8 @@ -import { atomFamily } from 'recoil'; +import { createScopedState } from '@/ui/utilities/recoil-scope/utils/createScopedState'; import { Filter } from '../../object-filter-dropdown/types/Filter'; -export const tableFiltersScopedState = atomFamily({ +export const tableFiltersScopedState = createScopedState({ key: 'tableFiltersScopedState', - default: [], + defaultValue: [], }); diff --git a/front/src/modules/ui/object/record-table/states/tableSortsScopedState.ts b/front/src/modules/ui/object/record-table/states/tableSortsScopedState.ts index 67c9a5e58..1d555cc9b 100644 --- a/front/src/modules/ui/object/record-table/states/tableSortsScopedState.ts +++ b/front/src/modules/ui/object/record-table/states/tableSortsScopedState.ts @@ -1,8 +1,8 @@ -import { atomFamily } from 'recoil'; +import { createScopedState } from '@/ui/utilities/recoil-scope/utils/createScopedState'; import { Sort } from '../../object-sort-dropdown/types/Sort'; -export const tableSortsScopedState = atomFamily({ +export const tableSortsScopedState = createScopedState({ key: 'tableSortsScopedState', - default: [], + defaultValue: [], }); diff --git a/front/src/modules/ui/object/record-table/utils/getRecordTableScopedStates.ts b/front/src/modules/ui/object/record-table/utils/getRecordTableScopedStates.ts new file mode 100644 index 000000000..c9b3cba6e --- /dev/null +++ b/front/src/modules/ui/object/record-table/utils/getRecordTableScopedStates.ts @@ -0,0 +1,79 @@ +import { getScopedState } from '@/ui/utilities/recoil-scope/utils/getScopedState'; + +import { availableTableColumnsScopedState } from '../states/availableTableColumnsScopedState'; +import { onColumnsChangeScopedState } from '../states/onColumnsChangeScopedState'; +import { hiddenTableColumnsScopedSelector } from '../states/selectors/hiddenTableColumnsScopedSelector'; +import { tableColumnsByKeyScopedSelector } from '../states/selectors/tableColumnsByKeyScopedSelector'; +import { tableFiltersWhereScopedSelector } from '../states/selectors/tablefiltersWhereScopedSelector'; +import { tableSortsOrderByScopedSelector } from '../states/selectors/tableSortsOrderByScopedSelector'; +import { visibleTableColumnsScopedSelector } from '../states/selectors/visibleTableColumnsScopedSelector'; +import { tableColumnsScopedState } from '../states/tableColumnsScopedState'; +import { tableFiltersScopedState } from '../states/tableFiltersScopedState'; +import { tableSortsScopedState } from '../states/tableSortsScopedState'; + +import { onEntityCountChangeScopedState } from './../states/onEntityCountChange'; + +export const getRecordTableScopedStates = ({ + recordTableScopeId, +}: { + recordTableScopeId: string; +}) => { + const availableTableColumnsState = getScopedState( + availableTableColumnsScopedState, + recordTableScopeId, + ); + + const tableFiltersState = getScopedState( + tableFiltersScopedState, + recordTableScopeId, + ); + + const tableSortsState = getScopedState( + tableSortsScopedState, + recordTableScopeId, + ); + + const tableSortsOrderBySelector = + tableSortsOrderByScopedSelector(recordTableScopeId); + + const tableFiltersWhereSelector = + tableFiltersWhereScopedSelector(recordTableScopeId); + + const tableColumnsState = getScopedState( + tableColumnsScopedState, + recordTableScopeId, + ); + + const tableColumnsByKeySelector = + tableColumnsByKeyScopedSelector(recordTableScopeId); + + const hiddenTableColumnsSelector = + hiddenTableColumnsScopedSelector(recordTableScopeId); + + const visibleTableColumnsSelector = + visibleTableColumnsScopedSelector(recordTableScopeId); + + const onColumnsChangeState = getScopedState( + onColumnsChangeScopedState, + recordTableScopeId, + ); + + const onEntityCountChangeState = getScopedState( + onEntityCountChangeScopedState, + recordTableScopeId, + ); + + return { + availableTableColumnsState, + tableFiltersState, + tableSortsState, + tableSortsOrderBySelector, + tableFiltersWhereSelector, + tableColumnsState, + tableColumnsByKeySelector, + hiddenTableColumnsSelector, + visibleTableColumnsSelector, + onColumnsChangeState, + onEntityCountChangeState, + }; +}; diff --git a/front/src/modules/views/hooks/internal/useViewFilters.ts b/front/src/modules/views/hooks/internal/useViewFilters.ts index 5e63ae5af..e1354347b 100644 --- a/front/src/modules/views/hooks/internal/useViewFilters.ts +++ b/front/src/modules/views/hooks/internal/useViewFilters.ts @@ -21,7 +21,9 @@ export const useViewFilters = (viewScopeId: string) => { }); const apolloClient = useApolloClient(); - const { currentViewFiltersState } = useViewScopedStates(); + const { currentViewFiltersState } = useViewScopedStates({ + customViewScopeId: viewScopeId, + }); const persistViewFilters = useRecoilCallback( ({ snapshot, set }) => diff --git a/front/src/modules/views/hooks/internal/useViewSorts.ts b/front/src/modules/views/hooks/internal/useViewSorts.ts index 95a30ef62..3b815764e 100644 --- a/front/src/modules/views/hooks/internal/useViewSorts.ts +++ b/front/src/modules/views/hooks/internal/useViewSorts.ts @@ -21,7 +21,9 @@ export const useViewSorts = (viewScopeId: string) => { }); const apolloClient = useApolloClient(); - const { currentViewSortsState } = useViewScopedStates(); + const { currentViewSortsState } = useViewScopedStates({ + customViewScopeId: viewScopeId, + }); const persistViewSorts = useRecoilCallback( ({ snapshot, set }) => diff --git a/front/src/modules/ui/object/record-table/hooks/useMoveViewColumns.ts b/front/src/modules/views/hooks/useMoveViewColumns.ts similarity index 100% rename from front/src/modules/ui/object/record-table/hooks/useMoveViewColumns.ts rename to front/src/modules/views/hooks/useMoveViewColumns.ts diff --git a/front/src/pages/companies/Companies.tsx b/front/src/pages/companies/Companies.tsx index 0f9b30046..1828dbe71 100644 --- a/front/src/pages/companies/Companies.tsx +++ b/front/src/pages/companies/Companies.tsx @@ -14,10 +14,8 @@ import { PageHeader } from '@/ui/layout/page/PageHeader'; import { PageHotkeysEffect } from '@/ui/layout/page/PageHotkeysEffect'; import { RecordTableActionBar } from '@/ui/object/record-table/action-bar/components/RecordTableActionBar'; import { RecordTableContextMenu } from '@/ui/object/record-table/context-menu/components/RecordTableContextMenu'; -import { useUpsertRecordTableItem } from '@/ui/object/record-table/hooks/useUpsertRecordTableItem'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { useUpsertTableRowId } from '@/ui/object/record-table/hooks/useUpsertTableRowId'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope'; import { useInsertOneCompanyMutation } from '~/generated/graphql'; const StyledTableContainer = styled.div` @@ -27,7 +25,9 @@ const StyledTableContainer = styled.div` export const Companies = () => { const [insertCompany] = useInsertOneCompanyMutation(); - const upsertRecordTableItem = useUpsertRecordTableItem(); + const { upsertRecordTableItem } = useRecordTable({ + recordTableScopeId: 'companies', + }); const upsertTableRowIds = useUpsertTableRowId(); const { triggerOptimisticEffects } = useOptimisticEffect(); @@ -61,16 +61,11 @@ export const Companies = () => { - - - - - - - + + + + + diff --git a/front/src/pages/companies/CompaniesMockMode.tsx b/front/src/pages/companies/CompaniesMockMode.tsx index 54e6e8108..9d8ad5921 100644 --- a/front/src/pages/companies/CompaniesMockMode.tsx +++ b/front/src/pages/companies/CompaniesMockMode.tsx @@ -5,8 +5,6 @@ import { IconBuildingSkyscraper } from '@/ui/display/icon'; import { PageBody } from '@/ui/layout/page/PageBody'; import { PageContainer } from '@/ui/layout/page/PageContainer'; import { PageHeader } from '@/ui/layout/page/PageHeader'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope'; const StyledTableContainer = styled.div` display: flex; @@ -18,11 +16,9 @@ export const CompaniesMockMode = () => { - - - - - + + + ); diff --git a/front/src/pages/people/People.tsx b/front/src/pages/people/People.tsx index cf3db26dd..56ba58336 100644 --- a/front/src/pages/people/People.tsx +++ b/front/src/pages/people/People.tsx @@ -12,10 +12,8 @@ import { PageHeader } from '@/ui/layout/page/PageHeader'; import { PageHotkeysEffect } from '@/ui/layout/page/PageHotkeysEffect'; import { RecordTableActionBar } from '@/ui/object/record-table/action-bar/components/RecordTableActionBar'; import { RecordTableContextMenu } from '@/ui/object/record-table/context-menu/components/RecordTableContextMenu'; -import { useUpsertRecordTableItem } from '@/ui/object/record-table/hooks/useUpsertRecordTableItem'; +import { useRecordTable } from '@/ui/object/record-table/hooks/useRecordTable'; import { useUpsertTableRowId } from '@/ui/object/record-table/hooks/useUpsertTableRowId'; -import { TableRecoilScopeContext } from '@/ui/object/record-table/states/recoil-scope-contexts/TableRecoilScopeContext'; -import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope'; import { useInsertOnePersonMutation } from '~/generated/graphql'; const StyledTableContainer = styled.div` @@ -25,7 +23,9 @@ const StyledTableContainer = styled.div` export const People = () => { const [insertOnePerson] = useInsertOnePersonMutation(); - const upsertRecordTableItem = useUpsertRecordTableItem(); + const { upsertRecordTableItem } = useRecordTable({ + recordTableScopeId: 'people', + }); const upsertTableRowIds = useUpsertTableRowId(); const { triggerOptimisticEffects } = useOptimisticEffect(); @@ -57,16 +57,11 @@ export const People = () => { - - - - - - - + + + + +