From b643fbe425b81b652a4494e3832b842fcd19c79e Mon Sep 17 00:00:00 2001 From: nitin <142569587+ehconitin@users.noreply.github.com> Date: Mon, 2 Feb 2026 18:44:27 +0530 Subject: [PATCH] [Dashboards] Auto focus effect on standalone widget (#17623) closes https://discord.com/channels/1130383047699738754/1467809255771078719 before - https://github.com/user-attachments/assets/3af6dbfd-358c-44fd-9419-338791fd5cfc after - https://github.com/user-attachments/assets/2e8f89f8-5989-4e62-9bc0-6ddd47c0d421 --- .../hooks/useEditPageLayoutWidget.ts | 5 +++ .../components/StandaloneRichTextWidget.tsx | 6 ++++ ...tandaloneRichTextWidgetAutoFocusEffect.tsx | 34 +++++++++++++++++++ 3 files changed, 45 insertions(+) create mode 100644 packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidgetAutoFocusEffect.tsx diff --git a/packages/twenty-front/src/modules/page-layout/hooks/useEditPageLayoutWidget.ts b/packages/twenty-front/src/modules/page-layout/hooks/useEditPageLayoutWidget.ts index 1ac39506dc..2656da741c 100644 --- a/packages/twenty-front/src/modules/page-layout/hooks/useEditPageLayoutWidget.ts +++ b/packages/twenty-front/src/modules/page-layout/hooks/useEditPageLayoutWidget.ts @@ -1,6 +1,8 @@ import { useCallback } from 'react'; +import { useSetRecoilState } from 'recoil'; import { useCommandMenu } from '@/command-menu/hooks/useCommandMenu'; +import { commandMenuPageState } from '@/command-menu/states/commandMenuPageState'; import { CommandMenuPages } from '@/command-menu/types/CommandMenuPages'; import { useSetRecoilComponentState } from '@/ui/utilities/state/component-state/hooks/useSetRecoilComponentState'; @@ -24,6 +26,7 @@ export const useEditPageLayoutWidget = (pageLayoutIdFromProps?: string) => { const { navigatePageLayoutCommandMenu } = useNavigatePageLayoutCommandMenu(); const { closeCommandMenu } = useCommandMenu(); + const setCommandMenuPage = useSetRecoilState(commandMenuPageState); const handleEditWidget = useCallback( ({ @@ -53,12 +56,14 @@ export const useEditPageLayoutWidget = (pageLayoutIdFromProps?: string) => { return; } + setCommandMenuPage(CommandMenuPages.Root); closeCommandMenu(); }, [ setPageLayoutEditingWidgetId, navigatePageLayoutCommandMenu, closeCommandMenu, + setCommandMenuPage, ], ); diff --git a/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidget.tsx b/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidget.tsx index 308b4b2d04..215163a4ba 100644 --- a/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidget.tsx +++ b/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidget.tsx @@ -11,6 +11,7 @@ import { isPageLayoutInEditModeComponentState } from '@/page-layout/states/isPag import { pageLayoutEditingWidgetIdComponentState } from '@/page-layout/states/pageLayoutEditingWidgetIdComponentState'; import { type PageLayoutWidget } from '@/page-layout/types/PageLayoutWidget'; import { DashboardsBlockEditor } from '@/page-layout/widgets/standalone-rich-text/components/DashboardsBlockEditor'; +import { StandaloneRichTextWidgetAutoFocusEffect } from '@/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidgetAutoFocusEffect'; import { BLOCK_EDITOR_GLOBAL_HOTKEYS_CONFIG } from '@/ui/input/editor/constants/BlockEditorGlobalHotkeysConfig'; import { useAttachmentSync } from '@/ui/input/editor/hooks/useAttachmentSync'; import { parseInitialBlocknote } from '@/ui/input/editor/utils/parseInitialBlocknote'; @@ -182,6 +183,11 @@ export const StandaloneRichTextWidget = ({ ref={containerElementRef} isPageLayoutInEditMode={isPageLayoutInEditMode} > + diff --git a/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidgetAutoFocusEffect.tsx b/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidgetAutoFocusEffect.tsx new file mode 100644 index 0000000000..748f870b02 --- /dev/null +++ b/packages/twenty-front/src/modules/page-layout/widgets/standalone-rich-text/components/StandaloneRichTextWidgetAutoFocusEffect.tsx @@ -0,0 +1,34 @@ +import { useEffect } from 'react'; + +import { type BLOCK_SCHEMA } from '@/activities/blocks/constants/Schema'; + +type StandaloneRichTextWidgetAutoFocusEffectProps = { + shouldFocus: boolean; + editor: typeof BLOCK_SCHEMA.BlockNoteEditor; + containerElement?: HTMLElement | null; +}; + +export const StandaloneRichTextWidgetAutoFocusEffect = ({ + shouldFocus, + editor, + containerElement, +}: StandaloneRichTextWidgetAutoFocusEffectProps) => { + useEffect(() => { + if (shouldFocus) { + const alreadyFocused = + containerElement?.contains(document.activeElement) ?? false; + + if (!alreadyFocused) { + const rafId = requestAnimationFrame(() => { + editor.focus(); + }); + + return () => { + cancelAnimationFrame(rafId); + }; + } + } + }, [shouldFocus, editor, containerElement]); + + return null; +};