Add full name composite field (#9008)
- Add composite field - Add test - Fix search variable dropdown scroll <img width="548" alt="Capture d’écran 2024-12-10 à 16 52 43" src="https://github.com/user-attachments/assets/c337f0c3-8a70-401a-abd0-7206489ba73e">
This commit is contained in:
@ -1,11 +1,16 @@
|
||||
import { FormBooleanFieldInput } from '@/object-record/record-field/form-types/components/FormBooleanFieldInput';
|
||||
import { FormFullNameFieldInput } from '@/object-record/record-field/form-types/components/FormFullNameFieldInput';
|
||||
import { FormNumberFieldInput } from '@/object-record/record-field/form-types/components/FormNumberFieldInput';
|
||||
import { FormSelectFieldInput } from '@/object-record/record-field/form-types/components/FormSelectFieldInput';
|
||||
import { FormTextFieldInput } from '@/object-record/record-field/form-types/components/FormTextFieldInput';
|
||||
import { VariablePickerComponent } from '@/object-record/record-field/form-types/types/VariablePickerComponent';
|
||||
import { FieldDefinition } from '@/object-record/record-field/types/FieldDefinition';
|
||||
import { FieldMetadata } from '@/object-record/record-field/types/FieldMetadata';
|
||||
import {
|
||||
FieldFullNameValue,
|
||||
FieldMetadata,
|
||||
} from '@/object-record/record-field/types/FieldMetadata';
|
||||
import { isFieldBoolean } from '@/object-record/record-field/types/guards/isFieldBoolean';
|
||||
import { isFieldFullName } from '@/object-record/record-field/types/guards/isFieldFullName';
|
||||
import { isFieldNumber } from '@/object-record/record-field/types/guards/isFieldNumber';
|
||||
import { isFieldSelect } from '@/object-record/record-field/types/guards/isFieldSelect';
|
||||
import { isFieldText } from '@/object-record/record-field/types/guards/isFieldText';
|
||||
@ -55,5 +60,12 @@ export const FormFieldInput = ({
|
||||
field={field}
|
||||
VariablePicker={VariablePicker}
|
||||
/>
|
||||
) : isFieldFullName(field) ? (
|
||||
<FormFullNameFieldInput
|
||||
label={field.label}
|
||||
defaultValue={defaultValue as FieldFullNameValue | undefined}
|
||||
onPersist={onPersist}
|
||||
VariablePicker={VariablePicker}
|
||||
/>
|
||||
) : null;
|
||||
};
|
||||
|
||||
@ -0,0 +1,66 @@
|
||||
import { FormTextFieldInput } from '@/object-record/record-field/form-types/components/FormTextFieldInput';
|
||||
import { StyledFormCompositeFieldInputContainer } from '@/object-record/record-field/form-types/components/StyledFormCompositeFieldInputContainer';
|
||||
import { StyledFormFieldInputContainer } from '@/object-record/record-field/form-types/components/StyledFormFieldInputContainer';
|
||||
import { VariablePickerComponent } from '@/object-record/record-field/form-types/types/VariablePickerComponent';
|
||||
import { FIRST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS } from '@/object-record/record-field/meta-types/input/constants/FirstNamePlaceholder';
|
||||
import { LAST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS } from '@/object-record/record-field/meta-types/input/constants/LastNamePlaceholder';
|
||||
import { FieldFullNameValue } from '@/object-record/record-field/types/FieldMetadata';
|
||||
import { InputLabel } from '@/ui/input/components/InputLabel';
|
||||
|
||||
type FormFullNameFieldInputProps = {
|
||||
label?: string;
|
||||
defaultValue: FieldFullNameValue | undefined;
|
||||
onPersist: (value: FieldFullNameValue) => void;
|
||||
VariablePicker?: VariablePickerComponent;
|
||||
readonly?: boolean;
|
||||
};
|
||||
|
||||
export const FormFullNameFieldInput = ({
|
||||
label,
|
||||
defaultValue,
|
||||
onPersist,
|
||||
readonly,
|
||||
VariablePicker,
|
||||
}: FormFullNameFieldInputProps) => {
|
||||
const handleFirstNameChange = (newText: string) => {
|
||||
onPersist({
|
||||
lastName: defaultValue?.lastName ?? '',
|
||||
firstName: newText,
|
||||
});
|
||||
};
|
||||
|
||||
const handleLastNameChange = (newText: string) => {
|
||||
onPersist({
|
||||
firstName: defaultValue?.firstName ?? '',
|
||||
lastName: newText,
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<StyledFormFieldInputContainer>
|
||||
{label ? <InputLabel>{label}</InputLabel> : null}
|
||||
<StyledFormCompositeFieldInputContainer>
|
||||
<FormTextFieldInput
|
||||
label="First Name"
|
||||
defaultValue={defaultValue?.firstName}
|
||||
onPersist={handleFirstNameChange}
|
||||
placeholder={
|
||||
FIRST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS
|
||||
}
|
||||
readonly={readonly}
|
||||
VariablePicker={VariablePicker}
|
||||
/>
|
||||
<FormTextFieldInput
|
||||
label="Last Name"
|
||||
defaultValue={defaultValue?.lastName}
|
||||
onPersist={handleLastNameChange}
|
||||
placeholder={
|
||||
LAST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS
|
||||
}
|
||||
readonly={readonly}
|
||||
VariablePicker={VariablePicker}
|
||||
/>
|
||||
</StyledFormCompositeFieldInputContainer>
|
||||
</StyledFormFieldInputContainer>
|
||||
);
|
||||
};
|
||||
@ -0,0 +1,11 @@
|
||||
import styled from '@emotion/styled';
|
||||
|
||||
export const StyledFormCompositeFieldInputContainer = styled.div`
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
background: ${({ theme }) => theme.background.secondary};
|
||||
border: 1px solid ${({ theme }) => theme.border.color.medium};
|
||||
border-radius: ${({ theme }) => theme.border.radius.sm};
|
||||
gap: ${({ theme }) => theme.spacing(2)};
|
||||
padding: ${({ theme }) => theme.spacing(2)};
|
||||
`;
|
||||
@ -3,4 +3,5 @@ import styled from '@emotion/styled';
|
||||
export const StyledFormFieldInputContainer = styled.div`
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
`;
|
||||
|
||||
@ -0,0 +1,31 @@
|
||||
import { Meta, StoryObj } from '@storybook/react';
|
||||
import { within } from '@storybook/test';
|
||||
import { FormFullNameFieldInput } from '../FormFullNameFieldInput';
|
||||
|
||||
const meta: Meta<typeof FormFullNameFieldInput> = {
|
||||
title: 'UI/Data/Field/Form/Input/FormFullNameFieldInput',
|
||||
component: FormFullNameFieldInput,
|
||||
args: {},
|
||||
argTypes: {},
|
||||
};
|
||||
|
||||
export default meta;
|
||||
|
||||
type Story = StoryObj<typeof FormFullNameFieldInput>;
|
||||
|
||||
export const Default: Story = {
|
||||
args: {
|
||||
label: 'Name',
|
||||
defaultValue: {
|
||||
firstName: 'John',
|
||||
lastName: 'Doe',
|
||||
},
|
||||
},
|
||||
play: async ({ canvasElement }) => {
|
||||
const canvas = within(canvasElement);
|
||||
|
||||
await canvas.findByText('Name');
|
||||
await canvas.findByText('First Name');
|
||||
await canvas.findByText('Last Name');
|
||||
},
|
||||
};
|
||||
@ -3,18 +3,14 @@ import { FieldDoubleText } from '@/object-record/record-field/types/FieldDoubleT
|
||||
import { DoubleTextInput } from '@/ui/field/input/components/DoubleTextInput';
|
||||
import { FieldInputOverlay } from '@/ui/field/input/components/FieldInputOverlay';
|
||||
|
||||
import { FIRST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS } from '@/object-record/record-field/meta-types/input/constants/FirstNamePlaceholder';
|
||||
import { LAST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS } from '@/object-record/record-field/meta-types/input/constants/LastNamePlaceholder';
|
||||
import { isDoubleTextFieldEmpty } from '@/object-record/record-field/meta-types/input/utils/isDoubleTextFieldEmpty';
|
||||
import {
|
||||
FieldInputClickOutsideEvent,
|
||||
FieldInputEvent,
|
||||
} from './DateTimeFieldInput';
|
||||
|
||||
const FIRST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS =
|
||||
'First name';
|
||||
|
||||
const LAST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS =
|
||||
'Last name';
|
||||
|
||||
type FullNameFieldInputProps = {
|
||||
onClickOutside?: FieldInputClickOutsideEvent;
|
||||
onEnter?: FieldInputEvent;
|
||||
|
||||
@ -0,0 +1,2 @@
|
||||
export const FIRST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS =
|
||||
'First name';
|
||||
@ -0,0 +1,2 @@
|
||||
export const LAST_NAME_PLACEHOLDER_WITH_SPECIAL_CHARACTER_TO_AVOID_PASSWORD_MANAGERS =
|
||||
'Last name';
|
||||
Reference in New Issue
Block a user