Fix phone input and link input (#2679)

* wip

* phone picker is appearing

* fixing picker placement

* set phone picker width

* fix link input
This commit is contained in:
bosiraphael
2023-11-23 16:38:13 +01:00
committed by GitHub
parent c795db33b2
commit 4f55243b30
9 changed files with 92 additions and 91 deletions

View File

@ -140,7 +140,8 @@ export const CountryPickerDropdownButton = ({
onChange={handleChange} onChange={handleChange}
/> />
} }
dropdownOffset={{ x: -60, y: -34 }} dropdownPlacement="bottom-start"
dropdownOffset={{ x: 0, y: 4 }}
/> />
</DropdownScope> </DropdownScope>
); );

View File

@ -27,13 +27,6 @@ const StyledIconContainer = styled.div`
} }
`; `;
const StyledDropdownMenuContainer = styled.ul`
left: 6px;
padding: 0;
position: absolute;
top: 26px;
`;
export const CountryPickerDropdownSelect = ({ export const CountryPickerDropdownSelect = ({
countries, countries,
selectedCountry, selectedCountry,
@ -56,54 +49,50 @@ export const CountryPickerDropdownSelect = ({
); );
return ( return (
<> <DropdownMenu width="200px" disableBlur>
<StyledDropdownMenuContainer data-select-disable> <DropdownMenuSearchInput
<DropdownMenu width="240px" disableBlur> value={searchFilter}
<DropdownMenuSearchInput onChange={(event) => setSearchFilter(event.currentTarget.value)}
value={searchFilter} autoFocus
onChange={(event) => setSearchFilter(event.currentTarget.value)} />
autoFocus <DropdownMenuSeparator />
/> <DropdownMenuItemsContainer hasMaxHeight>
<DropdownMenuSeparator /> {filteredCountries?.length === 0 ? (
<DropdownMenuItemsContainer hasMaxHeight> <MenuItem text="No result" />
{filteredCountries?.length === 0 ? ( ) : (
<MenuItem text="No result" /> <>
) : ( {selectedCountry && (
<> <MenuItemSelectAvatar
{selectedCountry && ( key={selectedCountry.countryCode}
selected={true}
onClick={() => onChange(selectedCountry.countryCode)}
text={`${selectedCountry.countryName} (+${selectedCountry.callingCode})`}
avatar={
<StyledIconContainer>
<selectedCountry.Flag />
</StyledIconContainer>
}
/>
)}
{filteredCountries.map(
({ countryCode, countryName, callingCode, Flag }) =>
selectedCountry?.countryCode === countryCode ? null : (
<MenuItemSelectAvatar <MenuItemSelectAvatar
key={selectedCountry.countryCode} key={countryCode}
selected={true} selected={selectedCountry?.countryCode === countryCode}
onClick={() => onChange(selectedCountry.countryCode)} onClick={() => onChange(countryCode)}
text={`${selectedCountry.countryName} (+${selectedCountry.callingCode})`} text={`${countryName} (+${callingCode})`}
avatar={ avatar={
<StyledIconContainer> <StyledIconContainer>
<selectedCountry.Flag /> <Flag />
</StyledIconContainer> </StyledIconContainer>
} }
/> />
)} ),
{filteredCountries.map(
({ countryCode, countryName, callingCode, Flag }) =>
selectedCountry?.countryCode === countryCode ? null : (
<MenuItemSelectAvatar
key={countryCode}
selected={selectedCountry?.countryCode === countryCode}
onClick={() => onChange(countryCode)}
text={`${countryName} (+${callingCode})`}
avatar={
<StyledIconContainer>
<Flag />
</StyledIconContainer>
}
/>
),
)}
</>
)} )}
</DropdownMenuItemsContainer> </>
</DropdownMenu> )}
</StyledDropdownMenuContainer> </DropdownMenuItemsContainer>
</> </DropdownMenu>
); );
}; };

View File

@ -6,18 +6,16 @@ const StyledDropdownMenu = styled.div<{
}>` }>`
backdrop-filter: ${({ disableBlur }) => backdrop-filter: ${({ disableBlur }) =>
disableBlur ? 'none' : 'blur(20px)'}; disableBlur ? 'none' : 'blur(20px)'};
background: ${({ theme }) => theme.background.secondary}; background: ${({ theme }) => theme.background.secondary};
border: 1px solid ${({ theme }) => theme.border.color.medium}; border: 1px solid ${({ theme }) => theme.border.color.medium};
border-radius: ${({ theme }) => theme.border.radius.md}; border-radius: ${({ theme }) => theme.border.radius.md};
box-shadow: ${({ theme }) => theme.boxShadow.strong}; box-shadow: ${({ theme }) => theme.boxShadow.strong};
display: flex; display: flex;
flex-direction: column; flex-direction: column;
overflow: hidden;
width: ${({ width }) => width: ${({ width }) =>
width ? `${typeof width === 'number' ? `${width}px` : width}` : '160px'}; width ? `${typeof width === 'number' ? `${width}px` : width}` : '160px'};
`; `;

View File

@ -48,12 +48,22 @@ export const FieldInput = ({
}: FieldInputProps) => { }: FieldInputProps) => {
const { fieldDefinition } = useContext(FieldContext); const { fieldDefinition } = useContext(FieldContext);
console.log(fieldDefinition);
return ( return (
<> <>
{isFieldRelation(fieldDefinition) ? ( {isFieldRelation(fieldDefinition) ? (
<RecoilScope> <RecoilScope>
<RelationFieldInput onSubmit={onSubmit} onCancel={onCancel} /> <RelationFieldInput onSubmit={onSubmit} onCancel={onCancel} />
</RecoilScope> </RecoilScope>
) : isFieldPhone(fieldDefinition) ? (
<PhoneFieldInput
onEnter={onEnter}
onEscape={onEscape}
onClickOutside={onClickOutside}
onTab={onTab}
onShiftTab={onShiftTab}
/>
) : isFieldText(fieldDefinition) ? ( ) : isFieldText(fieldDefinition) ? (
<TextFieldInput <TextFieldInput
onEnter={onEnter} onEnter={onEnter}
@ -110,14 +120,6 @@ export const FieldInput = ({
onTab={onTab} onTab={onTab}
onShiftTab={onShiftTab} onShiftTab={onShiftTab}
/> />
) : isFieldPhone(fieldDefinition) ? (
<PhoneFieldInput
onEnter={onEnter}
onEscape={onEscape}
onClickOutside={onClickOutside}
onTab={onTab}
onShiftTab={onShiftTab}
/>
) : isFieldBoolean(fieldDefinition) ? ( ) : isFieldBoolean(fieldDefinition) ? (
<BooleanFieldInput onSubmit={onSubmit} /> <BooleanFieldInput onSubmit={onSubmit} />
) : isFieldProbability(fieldDefinition) ? ( ) : isFieldProbability(fieldDefinition) ? (

View File

@ -12,7 +12,8 @@ import { isFieldPhone } from '../../types/guards/isFieldPhone';
export const usePhoneField = () => { export const usePhoneField = () => {
const { entityId, fieldDefinition, hotkeyScope } = useContext(FieldContext); const { entityId, fieldDefinition, hotkeyScope } = useContext(FieldContext);
assertFieldMetadata('PHONE', isFieldPhone, fieldDefinition); //assertFieldMetadata('PHONE', isFieldPhone, fieldDefinition);
assertFieldMetadata('TEXT', isFieldPhone, fieldDefinition);
const fieldName = fieldDefinition.metadata.fieldName; const fieldName = fieldDefinition.metadata.fieldName;

View File

@ -1,7 +1,7 @@
import { FieldDoubleText } from '../../../types/FieldDoubleText'; import { TextInput } from '@/ui/object/field/meta-types/input/components/internal/TextInput';
import { useLinkField } from '../../hooks/useLinkField'; import { useLinkField } from '../../hooks/useLinkField';
import { DoubleTextInput } from './internal/DoubleTextInput';
import { FieldInputOverlay } from './internal/FieldInputOverlay'; import { FieldInputOverlay } from './internal/FieldInputOverlay';
import { FieldInputEvent } from './DateFieldInput'; import { FieldInputEvent } from './DateFieldInput';
@ -22,61 +22,59 @@ export const LinkFieldInput = ({
}: LinkFieldInputProps) => { }: LinkFieldInputProps) => {
const { initialValue, hotkeyScope, persistLinkField } = useLinkField(); const { initialValue, hotkeyScope, persistLinkField } = useLinkField();
const handleEnter = (newURL: FieldDoubleText) => { const handleEnter = (newURL: string) => {
onEnter?.(() => onEnter?.(() =>
persistLinkField({ persistLinkField({
url: newURL.firstValue, url: newURL,
label: newURL.secondValue, label: newURL,
}), }),
); );
}; };
const handleEscape = (newURL: FieldDoubleText) => { const handleEscape = (newURL: string) => {
onEscape?.(() => onEscape?.(() =>
persistLinkField({ persistLinkField({
url: newURL.firstValue, url: newURL,
label: newURL.secondValue, label: newURL,
}), }),
); );
}; };
const handleClickOutside = ( const handleClickOutside = (
event: MouseEvent | TouchEvent, event: MouseEvent | TouchEvent,
newURL: FieldDoubleText, newURL: string,
) => { ) => {
onClickOutside?.(() => onClickOutside?.(() =>
persistLinkField({ persistLinkField({
url: newURL.firstValue, url: newURL,
label: newURL.secondValue, label: newURL,
}), }),
); );
}; };
const handleTab = (newURL: FieldDoubleText) => { const handleTab = (newURL: string) => {
onTab?.(() => onTab?.(() =>
persistLinkField({ persistLinkField({
url: newURL.firstValue, url: newURL,
label: newURL.secondValue, label: newURL,
}), }),
); );
}; };
const handleShiftTab = (newURL: FieldDoubleText) => { const handleShiftTab = (newURL: string) => {
onShiftTab?.(() => onShiftTab?.(() =>
persistLinkField({ persistLinkField({
url: newURL.firstValue, url: newURL,
label: newURL.secondValue, label: newURL,
}), }),
); );
}; };
return ( return (
<FieldInputOverlay> <FieldInputOverlay>
<DoubleTextInput <TextInput
firstValue={initialValue.url} value={initialValue.url}
secondValue={initialValue.label} placeholder="URL"
firstValuePlaceholder={'Url'}
secondValuePlaceholder={'Label'}
hotkeyScope={hotkeyScope} hotkeyScope={hotkeyScope}
onClickOutside={handleClickOutside} onClickOutside={handleClickOutside}
onEnter={handleEnter} onEnter={handleEnter}

View File

@ -15,7 +15,6 @@ import { isFieldEmail } from '../../types/guards/isFieldEmail';
import { isFieldLink } from '../../types/guards/isFieldLink'; import { isFieldLink } from '../../types/guards/isFieldLink';
import { isFieldLinkValue } from '../../types/guards/isFieldLinkValue'; import { isFieldLinkValue } from '../../types/guards/isFieldLinkValue';
import { isFieldNumber } from '../../types/guards/isFieldNumber'; import { isFieldNumber } from '../../types/guards/isFieldNumber';
import { isFieldPhone } from '../../types/guards/isFieldPhone';
import { isFieldProbability } from '../../types/guards/isFieldProbability'; import { isFieldProbability } from '../../types/guards/isFieldProbability';
import { isFieldRelation } from '../../types/guards/isFieldRelation'; import { isFieldRelation } from '../../types/guards/isFieldRelation';
import { isFieldRelationValue } from '../../types/guards/isFieldRelationValue'; import { isFieldRelationValue } from '../../types/guards/isFieldRelationValue';
@ -43,8 +42,8 @@ export const isEntityFieldEmptyFamilySelector = selectorFamily({
isFieldNumber(fieldDefinition) || isFieldNumber(fieldDefinition) ||
isFieldProbability(fieldDefinition) || isFieldProbability(fieldDefinition) ||
isFieldEmail(fieldDefinition) || isFieldEmail(fieldDefinition) ||
isFieldBoolean(fieldDefinition) || isFieldBoolean(fieldDefinition)
isFieldPhone(fieldDefinition) //|| isFieldPhone(fieldDefinition)
) { ) {
const fieldValue = get(entityFieldsFamilyState(entityId))?.[ const fieldValue = get(entityFieldsFamilyState(entityId))?.[
fieldName fieldName

View File

@ -1,58 +1,67 @@
import { EntityForSelect } from '@/ui/input/relation-picker/types/EntityForSelect'; import { EntityForSelect } from '@/ui/input/relation-picker/types/EntityForSelect';
export type FieldUuidMetadata = { export type FieldUuidMetadata = {
objectMetadataNameSingular?: string;
fieldName: string; fieldName: string;
}; };
export type FieldBooleanMetadata = { export type FieldBooleanMetadata = {
objectMetadataNameSingular?: string;
fieldName: string; fieldName: string;
}; };
export type FieldTextMetadata = { export type FieldTextMetadata = {
objectMetadataNameSingular: string; objectMetadataNameSingular?: string;
placeHolder: string; placeHolder: string;
fieldName: string; fieldName: string;
}; };
export type FieldDateTimeMetadata = { export type FieldDateTimeMetadata = {
objectMetadataNameSingular?: string;
placeHolder: string; placeHolder: string;
fieldName: string; fieldName: string;
}; };
export type FieldNumberMetadata = { export type FieldNumberMetadata = {
objectMetadataNameSingular?: string;
fieldName: string; fieldName: string;
placeHolder: string; placeHolder: string;
isPositive?: boolean; isPositive?: boolean;
}; };
export type FieldLinkMetadata = { export type FieldLinkMetadata = {
objectMetadataNameSingular?: string;
placeHolder: string; placeHolder: string;
fieldName: string; fieldName: string;
}; };
export type FieldCurrencyMetadata = { export type FieldCurrencyMetadata = {
objectMetadataNameSingular?: string;
fieldName: string; fieldName: string;
placeHolder: string; placeHolder: string;
isPositive?: boolean; isPositive?: boolean;
}; };
export type FieldFullNameMetadata = { export type FieldFullNameMetadata = {
objectMetadataNameSingular: string; objectMetadataNameSingular?: string;
placeHolder: string; placeHolder: string;
fieldName: string; fieldName: string;
}; };
export type FieldEmailMetadata = { export type FieldEmailMetadata = {
objectMetadataNameSingular?: string;
placeHolder: string; placeHolder: string;
fieldName: string; fieldName: string;
}; };
export type FieldPhoneMetadata = { export type FieldPhoneMetadata = {
objectMetadataNameSingular?: string;
placeHolder: string; placeHolder: string;
fieldName: string; fieldName: string;
}; };
export type FieldProbabilityMetadata = { export type FieldProbabilityMetadata = {
objectMetadataNameSingular?: string;
fieldName: string; fieldName: string;
}; };
@ -63,6 +72,7 @@ export type FieldDefinitionRelationType =
| 'TO_ONE_OBJECT'; | 'TO_ONE_OBJECT';
export type FieldRelationMetadata = { export type FieldRelationMetadata = {
objectMetadataNameSingular?: string;
fieldName: string; fieldName: string;
useEditButton?: boolean; useEditButton?: boolean;
relationType?: FieldDefinitionRelationType; relationType?: FieldDefinitionRelationType;

View File

@ -2,5 +2,8 @@ import { FieldDefinition } from '../FieldDefinition';
import { FieldMetadata, FieldPhoneMetadata } from '../FieldMetadata'; import { FieldMetadata, FieldPhoneMetadata } from '../FieldMetadata';
export const isFieldPhone = ( export const isFieldPhone = (
field: Pick<FieldDefinition<FieldMetadata>, 'type'>, field: Pick<FieldDefinition<FieldMetadata>, 'type' | 'metadata'>,
): field is FieldDefinition<FieldPhoneMetadata> => field.type === 'PHONE'; ): field is FieldDefinition<FieldPhoneMetadata> =>
field.metadata.objectMetadataNameSingular === 'person' &&
field.metadata.fieldName === 'phone' &&
field.type === 'TEXT';