From 3c0c1722ff4b63662f709c17591692b49dfa9f16 Mon Sep 17 00:00:00 2001 From: Weiko Date: Tue, 17 Dec 2024 16:01:22 +0100 Subject: [PATCH] Replace block editor on page change --- .../activities/components/RichTextEditor.tsx | 33 +++++++---------- .../hooks/useReplaceBlockEditorContent.tsx | 36 +++++++++++++++++++ 2 files changed, 49 insertions(+), 20 deletions(-) create mode 100644 packages/twenty-front/src/modules/ui/input/hooks/useReplaceBlockEditorContent.tsx diff --git a/packages/twenty-front/src/modules/activities/components/RichTextEditor.tsx b/packages/twenty-front/src/modules/activities/components/RichTextEditor.tsx index bff2bef3cb..312aec9e56 100644 --- a/packages/twenty-front/src/modules/activities/components/RichTextEditor.tsx +++ b/packages/twenty-front/src/modules/activities/components/RichTextEditor.tsx @@ -1,14 +1,13 @@ import { useApolloClient } from '@apollo/client'; import { useCreateBlockNote } from '@blocknote/react'; import { isArray, isNonEmptyString } from '@sniptt/guards'; -import { useCallback, useMemo } from 'react'; +import { useCallback, useEffect, useMemo } from 'react'; import { useRecoilCallback, useRecoilState } from 'recoil'; import { Key } from 'ts-key-enum'; import { useDebouncedCallback } from 'use-debounce'; import { v4 } from 'uuid'; import { useUpsertActivity } from '@/activities/hooks/useUpsertActivity'; -import { activityBodyFamilyState } from '@/activities/states/activityBodyFamilyState'; import { activityTitleHasBeenSetFamilyState } from '@/activities/states/activityTitleHasBeenSetFamilyState'; import { canCreateActivityState } from '@/activities/states/canCreateActivityState'; import { ActivityEditorHotkeyScope } from '@/activities/types/ActivityEditorHotkeyScope'; @@ -27,6 +26,7 @@ import { useUploadAttachmentFile } from '@/activities/files/hooks/useUploadAttac import { Note } from '@/activities/types/Note'; import { Task } from '@/activities/types/Task'; import { CoreObjectNameSingular } from '@/object-metadata/types/CoreObjectNameSingular'; +import { useReplaceBlockEditorContent } from '@/ui/input/hooks/useReplaceBlockEditorContent'; import '@blocknote/core/fonts/inter.css'; import '@blocknote/mantine/style.css'; import '@blocknote/react/style.css'; @@ -55,12 +55,6 @@ export const RichTextEditor = ({ }), ); - const [activityBody, setActivityBody] = useRecoilState( - activityBodyFamilyState({ - activityId: activityId, - }), - ); - const { objectMetadataItem: objectMetadataItemActivity } = useObjectMetadataItem({ objectNameSingular: activityObjectNameSingular, @@ -241,24 +235,14 @@ export const RichTextEditor = ({ const handleBodyChangeDebounced = useDebouncedCallback(handleBodyChange, 500); - // See https://github.com/twentyhq/twenty/issues/6724 for explanation - const setActivityBodyDebouncedToAvoidDragBug = useDebouncedCallback( - setActivityBody, - 100, - ); - const handleEditorChange = () => { const newStringifiedBody = JSON.stringify(editor.document) ?? ''; - setActivityBodyDebouncedToAvoidDragBug(newStringifiedBody); - handleBodyChangeDebounced(newStringifiedBody); }; const initialBody = useMemo(() => { - if (isNonEmptyString(activityBody) && activityBody !== '{}') { - return JSON.parse(activityBody); - } else if ( + if ( isDefined(activity) && isNonEmptyString(activity.body) && activity?.body !== '{}' @@ -267,7 +251,7 @@ export const RichTextEditor = ({ } else { return undefined; } - }, [activity, activityBody]); + }, [activity]); const handleEditorBuiltInUploadFile = async (file: File) => { const { attachementAbsoluteURL } = await handleUploadAttachment(file); @@ -282,6 +266,15 @@ export const RichTextEditor = ({ uploadFile: handleEditorBuiltInUploadFile, }); + const { replaceBlockEditorContent } = useReplaceBlockEditorContent( + activityId, + editor, + ); + + useEffect(() => { + replaceBlockEditorContent(); + }, [replaceBlockEditorContent, activityId, editor]); + useScopedHotkeys( Key.Escape, () => { diff --git a/packages/twenty-front/src/modules/ui/input/hooks/useReplaceBlockEditorContent.tsx b/packages/twenty-front/src/modules/ui/input/hooks/useReplaceBlockEditorContent.tsx new file mode 100644 index 0000000000..8237fca892 --- /dev/null +++ b/packages/twenty-front/src/modules/ui/input/hooks/useReplaceBlockEditorContent.tsx @@ -0,0 +1,36 @@ +import { recordStoreFamilyState } from '@/object-record/record-store/states/recordStoreFamilyState'; +import { isNonEmptyString } from '@sniptt/guards'; +import { useRecoilCallback } from 'recoil'; +import { isDefined } from 'twenty-ui'; +import { isDeeplyEqual } from '~/utils/isDeeplyEqual'; + +export const useReplaceBlockEditorContent = ( + activityId: string, + editor: any, +) => { + const replaceBlockEditorContent = useRecoilCallback( + ({ snapshot }) => + () => { + if (isDefined(editor)) { + const activityInStore = snapshot + .getLoadable(recordStoreFamilyState(activityId)) + .getValue(); + + const content = isNonEmptyString(activityInStore?.body) + ? JSON.parse(activityInStore?.body) + : [{ type: 'paragraph', content: '' }]; + + console.log(editor.document, content); + if (!isDeeplyEqual(editor.document, content)) { + console.log('replacing'); + editor.replaceBlocks(editor.document, content); + } + } + }, + [activityId, editor], + ); + + return { + replaceBlockEditorContent, + }; +};