From 42ad4630eae0ddccd1bdd149c1791e0861b17037 Mon Sep 17 00:00:00 2001 From: Abdul Rahman <81605929+abdulrahmancodes@users.noreply.github.com> Date: Tue, 23 Dec 2025 16:06:23 +0530 Subject: [PATCH] Auto-focus workflow title field when creating new workflow (#16765) Closes #14135 https://github.com/user-attachments/assets/4170c33d-4a2e-450a-98c0-20163d4b2382 --- .../effect-components/PageChangeEffect.tsx | 16 +++++++ .../hooks/useCreateNewIndexRecord.ts | 23 ++++++++-- .../hooks/useOpenNewRecordTitleCell.ts | 43 +++++++++++++++++++ 3 files changed, 78 insertions(+), 4 deletions(-) create mode 100644 packages/twenty-front/src/modules/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell.ts diff --git a/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx b/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx index 369b9c2990..77db3d456b 100644 --- a/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx +++ b/packages/twenty-front/src/modules/app/effect-components/PageChangeEffect.tsx @@ -29,6 +29,7 @@ import { useResetFocusStackToRecordIndex } from '@/object-record/record-index/ho import { useResetTableRowSelection } from '@/object-record/record-table/hooks/internal/useResetTableRowSelection'; import { useActiveRecordTableRow } from '@/object-record/record-table/hooks/useActiveRecordTableRow'; import { useFocusedRecordTableRow } from '@/object-record/record-table/hooks/useFocusedRecordTableRow'; +import { useOpenNewRecordTitleCell } from '@/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell'; import { getRecordIndexIdFromObjectNamePluralAndViewId } from '@/object-record/utils/getRecordIndexIdFromObjectNamePluralAndViewId'; import { PageFocusId } from '@/types/PageFocusId'; import { useResetFocusStackToFocusItem } from '@/ui/utilities/focus/hooks/useResetFocusStackToFocusItem'; @@ -100,6 +101,8 @@ export const PageChangeEffect = () => { const { resetFocusStackToRecordIndex } = useResetFocusStackToRecordIndex(); + const { openNewRecordTitleCell } = useOpenNewRecordTitleCell(); + useEffect(() => { closeCommandMenu(); }, [location.pathname, closeCommandMenu]); @@ -167,6 +170,18 @@ export const PageChangeEffect = () => { }, }, }); + + const isNewRecord = location.state?.isNewRecord === true; + + if ( + isNewRecord && + isDefined(location.state?.labelIdentifierFieldName) + ) { + openNewRecordTitleCell({ + recordId: location.state.objectRecordId, + fieldName: location.state.labelIdentifierFieldName, + }); + } break; } case isMatchingLocation(location, AppPath.SignInUp): { @@ -310,6 +325,7 @@ export const PageChangeEffect = () => { unfocusBoardCard, resetFocusStackToRecordIndex, resetFocusStackToFocusItem, + openNewRecordTitleCell, ]); useEffect(() => { diff --git a/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts b/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts index 7f5fd828ed..1563f6c0de 100644 --- a/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts +++ b/packages/twenty-front/src/modules/object-record/record-table/hooks/useCreateNewIndexRecord.ts @@ -101,10 +101,25 @@ export const useCreateNewIndexRecord = ({ }); } } else { - navigate(AppPath.RecordShowPage, { - objectNameSingular: objectMetadataItem.nameSingular, - objectRecordId: recordId, - }); + const labelIdentifierFieldMetadataItem = + getLabelIdentifierFieldMetadataItem(objectMetadataItem); + + navigate( + AppPath.RecordShowPage, + { + objectNameSingular: objectMetadataItem.nameSingular, + objectRecordId: recordId, + }, + undefined, + { + state: { + isNewRecord: true, + objectRecordId: recordId, + labelIdentifierFieldName: + labelIdentifierFieldMetadataItem?.name, + }, + }, + ); } if (isDefined(recordIndexGroupFieldMetadataItem)) { diff --git a/packages/twenty-front/src/modules/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell.ts b/packages/twenty-front/src/modules/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell.ts new file mode 100644 index 0000000000..98c3a92a95 --- /dev/null +++ b/packages/twenty-front/src/modules/object-record/record-title-cell/hooks/useOpenNewRecordTitleCell.ts @@ -0,0 +1,43 @@ +import { isTitleCellInEditModeComponentState } from '@/object-record/record-title-cell/states/isTitleCellInEditModeComponentState'; +import { RecordTitleCellContainerType } from '@/object-record/record-title-cell/types/RecordTitleCellContainerType'; +import { getRecordFieldInputInstanceId } from '@/object-record/utils/getRecordFieldInputId'; +import { usePushFocusItemToFocusStack } from '@/ui/utilities/focus/hooks/usePushFocusItemToFocusStack'; +import { FocusComponentType } from '@/ui/utilities/focus/types/FocusComponentType'; +import { useRecoilCallback } from 'recoil'; + +export const useOpenNewRecordTitleCell = () => { + const { pushFocusItemToFocusStack } = usePushFocusItemToFocusStack(); + + const openNewRecordTitleCell = useRecoilCallback( + ({ set }) => + ({ recordId, fieldName }: { recordId: string; fieldName: string }) => { + const instanceId = getRecordFieldInputInstanceId({ + recordId, + fieldName, + prefix: RecordTitleCellContainerType.PageHeader, + }); + + pushFocusItemToFocusStack({ + focusId: instanceId, + component: { + type: FocusComponentType.OPENED_FIELD_INPUT, + instanceId, + }, + globalHotkeysConfig: { + enableGlobalHotkeysConflictingWithKeyboard: false, + enableGlobalHotkeysWithModifiers: false, + }, + }); + + set( + isTitleCellInEditModeComponentState.atomFamily({ + instanceId, + }), + true, + ); + }, + [pushFocusItemToFocusStack], + ); + + return { openNewRecordTitleCell }; +};