fix: prevent default object re-selection in relation field form (#17313)
Fixes #17111 ### Problem When creating a Relation field, after deselecting the pre-selected default object (e.g., Company) and selecting a different object (e.g., Opportunity), both objects would end up being selected, showing "2 Objects" instead of just the newly selected one. ### Root Cause The `initialMorphRelationsObjectMetadataIds` array was being recreated on every component render, causing react-hook-form's `Controller` to treat the `defaultValue` prop as a new value and re-apply it after user changes. ### Solution 1. **Memoized the initial value**: Used `useMemo` to ensure `initialMorphRelationsObjectMetadataIds` has a stable reference across renders 2. **Added initialization guard**: Used `useEffect` with a `useRef` flag to ensure the default value is only set once during component mount 3. **Maintained Controller defaultValue**: Kept the `defaultValue` prop on the Controller, which now works correctly with the stable memoized value ### Changes - `SettingsDataModelFieldRelationForm.tsx`: Added memoization and initialization guard to prevent default value re-application --------- Co-authored-by: Etienne <45695613+etiennejouan@users.noreply.github.com>
This commit is contained in:
@@ -20,6 +20,7 @@ type MultiSelectControlProps = Omit<SelectControlProps, 'selectedOption'> & {
|
||||
fixedIcon?: IconComponent;
|
||||
fixedText?: string;
|
||||
selectedOptions: MultiSelectOptionType[];
|
||||
placeholderText?: string;
|
||||
};
|
||||
|
||||
export const MultiSelectControl = ({
|
||||
@@ -30,16 +31,22 @@ export const MultiSelectControl = ({
|
||||
selectSizeVariant,
|
||||
textAccent = 'default',
|
||||
hasRightElement,
|
||||
placeholderText,
|
||||
}: MultiSelectControlProps) => {
|
||||
const theme = useTheme();
|
||||
|
||||
const firstSelectedOption = selectedOptions?.[0];
|
||||
const firstSelectedOption = selectedOptions[0];
|
||||
const hasSelection = selectedOptions.length > 0;
|
||||
|
||||
return (
|
||||
<StyledControlContainer
|
||||
disabled={isDisabled}
|
||||
hasIcon={isDefined(fixedIcon) || isDefined(firstSelectedOption?.Icon)}
|
||||
hasIcon={
|
||||
isDefined(fixedIcon) ||
|
||||
(hasSelection && isDefined(firstSelectedOption?.Icon))
|
||||
}
|
||||
selectSizeVariant={selectSizeVariant}
|
||||
textAccent={textAccent}
|
||||
textAccent={hasSelection ? textAccent : 'placeholder'}
|
||||
hasRightElement={hasRightElement}
|
||||
>
|
||||
{isDefined(fixedIcon) ? (
|
||||
@@ -48,7 +55,7 @@ export const MultiSelectControl = ({
|
||||
size: theme.icon.size.md,
|
||||
stroke: theme.icon.stroke.sm,
|
||||
})
|
||||
) : isDefined(firstSelectedOption?.Icon) ? (
|
||||
) : hasSelection && isDefined(firstSelectedOption.Icon) ? (
|
||||
<firstSelectedOption.Icon
|
||||
color={isDisabled ? theme.font.color.light : theme.font.color.primary}
|
||||
size={theme.icon.size.md}
|
||||
@@ -57,9 +64,11 @@ export const MultiSelectControl = ({
|
||||
) : null}
|
||||
{isDefined(fixedText) ? (
|
||||
<OverflowingTextWithTooltip text={fixedText} />
|
||||
) : (
|
||||
<OverflowingTextWithTooltip text={firstSelectedOption?.label ?? ''} />
|
||||
)}
|
||||
) : hasSelection ? (
|
||||
<OverflowingTextWithTooltip text={firstSelectedOption.label} />
|
||||
) : isDefined(placeholderText) ? (
|
||||
<OverflowingTextWithTooltip text={placeholderText} />
|
||||
) : null}
|
||||
|
||||
<StyledSelectControlIconChevronDown
|
||||
disabled={isDisabled}
|
||||
|
||||
Reference in New Issue
Block a user