feat: persist board card fields (#1566)

Closes #1538
This commit is contained in:
Thaïs
2023-09-15 00:06:15 +02:00
committed by GitHub
parent 6462505a86
commit 2461a387ce
27 changed files with 541 additions and 342 deletions

View File

@ -1,46 +1,101 @@
import type { ComponentProps } from 'react';
import { useContext } from 'react';
import { useRecoilCallback, useRecoilState, useRecoilValue } from 'recoil';
import { DropdownRecoilScopeContext } from '@/ui/dropdown/states/recoil-scope-contexts/DropdownRecoilScopeContext';
import { RecoilScope } from '@/ui/utilities/recoil-scope/components/RecoilScope';
import { useContextScopeId } from '@/ui/utilities/recoil-scope/hooks/useContextScopeId';
import { useRecoilScopedState } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedState';
import { useRecoilScopedValue } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedValue';
import { ViewBar, type ViewBarProps } from '@/ui/view-bar/components/ViewBar';
import { ViewBarContext } from '@/ui/view-bar/contexts/ViewBarContext';
import { currentViewIdScopedState } from '@/ui/view-bar/states/currentViewIdScopedState';
import { boardCardFieldsScopedState } from '../states/boardCardFieldsScopedState';
import { savedBoardCardFieldsFamilyState } from '../states/savedBoardCardFieldsFamilyState';
import { canPersistBoardCardFieldsScopedFamilySelector } from '../states/selectors/canPersistBoardCardFieldsScopedFamilySelector';
import type { BoardColumnDefinition } from '../types/BoardColumnDefinition';
import { BoardOptionsDropdownKey } from '../types/BoardOptionsDropdownKey';
import { BoardOptionsHotkeyScope } from '../types/BoardOptionsHotkeyScope';
import { BoardOptionsDropdown } from './BoardOptionsDropdown';
export type BoardHeaderProps = ComponentProps<'div'> & {
export type BoardHeaderProps = {
className?: string;
onStageAdd?: (boardColumn: BoardColumnDefinition) => void;
} & Pick<
ViewBarProps,
'defaultViewName' | 'onViewsChange' | 'onViewSubmit' | 'scopeContext'
>;
} & Pick<ViewBarProps, 'scopeContext'>;
export function BoardHeader({
className,
onStageAdd,
onViewsChange,
onViewSubmit,
scopeContext,
defaultViewName,
}: BoardHeaderProps) {
const { onCurrentViewSubmit, ...viewBarContextProps } =
useContext(ViewBarContext);
const tableScopeId = useContextScopeId(scopeContext);
const currentViewId = useRecoilScopedValue(
currentViewIdScopedState,
scopeContext,
);
const canPersistBoardCardFields = useRecoilValue(
canPersistBoardCardFieldsScopedFamilySelector([
tableScopeId,
currentViewId,
]),
);
const [boardCardFields, setBoardCardFields] = useRecoilScopedState(
boardCardFieldsScopedState,
scopeContext,
);
const [savedBoardCardFields, setSavedBoardCardFields] = useRecoilState(
savedBoardCardFieldsFamilyState(currentViewId),
);
const handleViewBarReset = () => setBoardCardFields(savedBoardCardFields);
const handleViewSelect = useRecoilCallback(
({ set, snapshot }) =>
async (viewId: string) => {
const savedBoardCardFields = await snapshot.getPromise(
savedBoardCardFieldsFamilyState(viewId),
);
set(boardCardFieldsScopedState(tableScopeId), savedBoardCardFields);
},
[tableScopeId],
);
const handleCurrentViewSubmit = async () => {
if (canPersistBoardCardFields) {
setSavedBoardCardFields(boardCardFields);
}
await onCurrentViewSubmit?.();
};
return (
<RecoilScope SpecificContext={DropdownRecoilScopeContext}>
<ViewBar
defaultViewName={defaultViewName}
onViewsChange={onViewsChange}
onViewSubmit={onViewSubmit}
optionsDropdownButton={
<BoardOptionsDropdown
customHotkeyScope={{ scope: BoardOptionsHotkeyScope.Dropdown }}
onStageAdd={onStageAdd}
onViewsChange={onViewsChange}
scopeContext={scopeContext}
/>
}
optionsDropdownKey={BoardOptionsDropdownKey}
scopeContext={scopeContext}
/>
<ViewBarContext.Provider
value={{
...viewBarContextProps,
canPersistViewFields: canPersistBoardCardFields,
onCurrentViewSubmit: handleCurrentViewSubmit,
onViewBarReset: handleViewBarReset,
onViewSelect: handleViewSelect,
}}
>
<ViewBar
className={className}
optionsDropdownButton={
<BoardOptionsDropdown
customHotkeyScope={{ scope: BoardOptionsHotkeyScope.Dropdown }}
onStageAdd={onStageAdd}
scopeContext={scopeContext}
/>
}
optionsDropdownKey={BoardOptionsDropdownKey}
scopeContext={scopeContext}
/>
</ViewBarContext.Provider>
</RecoilScope>
);
}