@verifiedinc-public/shared-ui-elements 1.3.2 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (117) hide show
  1. package/README.md +4 -24
  2. package/dist/components/index.mjs +1 -0
  3. package/dist/hooks/index.d.ts +1 -0
  4. package/dist/hooks/index.mjs +1 -0
  5. package/dist/hooks/useSearchParams.d.ts +5 -0
  6. package/dist/index.mjs +1 -0
  7. package/dist/shared/index-CTvz4BbG.mjs +105 -0
  8. package/dist/shared/phone.schema-XBbyizhq.mjs +1 -0
  9. package/dist/shared/shadows-fgmuXym6.mjs +1 -0
  10. package/dist/shared/unix.schema-CMYTtXco.mjs +1 -0
  11. package/dist/shared/useQRCode-DXiPIj-D.mjs +1 -0
  12. package/dist/shared/useSearchParams-CW9y02Ym.mjs +1 -0
  13. package/dist/styles/index.mjs +1 -0
  14. package/dist/utils/masks/index.mjs +1 -0
  15. package/dist/utils/string/index.mjs +1 -0
  16. package/dist/validations/index.mjs +1 -0
  17. package/package.json +29 -8
  18. package/dist/shared-ui-elements.mjs +0 -105
  19. package/src/components/Alert/Alert.tsx +0 -8
  20. package/src/components/Alert/FullWidthAlert.tsx +0 -27
  21. package/src/components/Alert/index.ts +0 -2
  22. package/src/components/Backdrop/index.tsx +0 -34
  23. package/src/components/Banners/Banner.tsx +0 -42
  24. package/src/components/Banners/ExactBirthdayBanner.tsx +0 -18
  25. package/src/components/Banners/ResendPhoneBanner.tsx +0 -55
  26. package/src/components/Banners/TestPhoneNumbersBanner.tsx +0 -25
  27. package/src/components/Banners/index.tsx +0 -4
  28. package/src/components/Button/index.tsx +0 -8
  29. package/src/components/CredentialRequestsEditor/CredentialRequestsEditor.context.tsx +0 -98
  30. package/src/components/CredentialRequestsEditor/components/CredentialRequestsField.tsx +0 -103
  31. package/src/components/CredentialRequestsEditor/components/DataFieldAccordion.tsx +0 -337
  32. package/src/components/CredentialRequestsEditor/components/DataFieldDeleteModal.tsx +0 -64
  33. package/src/components/CredentialRequestsEditor/components/DataFieldDescription.tsx +0 -68
  34. package/src/components/CredentialRequestsEditor/components/DataFieldMandatory.tsx +0 -84
  35. package/src/components/CredentialRequestsEditor/components/DataFieldMulti.tsx +0 -74
  36. package/src/components/CredentialRequestsEditor/components/DataFieldOptionType.tsx +0 -84
  37. package/src/components/CredentialRequestsEditor/components/DataFieldSection.tsx +0 -48
  38. package/src/components/CredentialRequestsEditor/components/DataFieldUserInput.tsx +0 -71
  39. package/src/components/CredentialRequestsEditor/components/RadioOption.tsx +0 -89
  40. package/src/components/CredentialRequestsEditor/contexts/CredentialRequestFieldContext.tsx +0 -36
  41. package/src/components/CredentialRequestsEditor/index.tsx +0 -15
  42. package/src/components/CredentialRequestsEditor/types/compositeCredentialSchema.ts +0 -1
  43. package/src/components/CredentialRequestsEditor/types/credentialSchemasDto.ts +0 -3
  44. package/src/components/CredentialRequestsEditor/types/form.ts +0 -28
  45. package/src/components/CredentialRequestsEditor/types/mandatoryEnum.ts +0 -5
  46. package/src/components/CredentialRequestsEditor/utils/buildDataFieldValue.ts +0 -65
  47. package/src/components/CredentialRequestsEditor/utils/prettyField.ts +0 -16
  48. package/src/components/Image.tsx +0 -10
  49. package/src/components/QRCodeDisplay/index.tsx +0 -50
  50. package/src/components/RequiredLabel/index.tsx +0 -15
  51. package/src/components/Snackbar/index.tsx +0 -156
  52. package/src/components/TextField/index.tsx +0 -8
  53. package/src/components/Tip/index.tsx +0 -18
  54. package/src/components/Typography/index.tsx +0 -8
  55. package/src/components/When.tsx +0 -28
  56. package/src/components/form/CountrySelector.tsx +0 -96
  57. package/src/components/form/DataFieldClearAdornment.tsx +0 -28
  58. package/src/components/form/DateInput.tsx +0 -78
  59. package/src/components/form/DefaultInput.tsx +0 -26
  60. package/src/components/form/InputMask.tsx +0 -41
  61. package/src/components/form/OTPInput.tsx +0 -254
  62. package/src/components/form/PhoneInput.tsx +0 -152
  63. package/src/components/form/SSNInput.tsx +0 -99
  64. package/src/components/form/SelectInput.tsx +0 -101
  65. package/src/components/form/TextMaskCustom.tsx +0 -48
  66. package/src/components/form/index.ts +0 -5
  67. package/src/components/index.ts +0 -13
  68. package/src/components/terms/AcceptTermsNotice.tsx +0 -27
  69. package/src/components/terms/LegalLink.tsx +0 -22
  70. package/src/components/verified/VerifiedImage.tsx +0 -272
  71. package/src/components/verified/VerifiedIncLogo.tsx +0 -11
  72. package/src/components/verified/index.ts +0 -2
  73. package/src/hooks/index.ts +0 -5
  74. package/src/hooks/useCallbackRef.ts +0 -22
  75. package/src/hooks/useCopyToClipboard.ts +0 -76
  76. package/src/hooks/useDisclosure.ts +0 -96
  77. package/src/hooks/useLocalStorage.ts +0 -24
  78. package/src/hooks/usePrevious.ts +0 -17
  79. package/src/hooks/useQRCode.ts +0 -62
  80. package/src/index.ts +0 -13
  81. package/src/stories/components/Alert.stories.tsx +0 -41
  82. package/src/stories/components/Button.stories.ts +0 -49
  83. package/src/stories/components/CredentialRequestsEditor.stories.tsx +0 -98
  84. package/src/stories/components/QRCodeDisplay.stories.tsx +0 -60
  85. package/src/stories/components/TextField.stories.ts +0 -59
  86. package/src/stories/components/Typography.stories.ts +0 -140
  87. package/src/stories/components/VerifiedImage.stories.tsx +0 -32
  88. package/src/stories/components/form/DateInput.stories.ts +0 -36
  89. package/src/stories/components/form/OTPInput.stories.tsx +0 -90
  90. package/src/stories/components/form/PhoneInput.stories.tsx +0 -34
  91. package/src/stories/components/form/SSNInput.stories.ts +0 -30
  92. package/src/stories/components/form/SelectInput.stories.ts +0 -39
  93. package/src/stories/hooks/useCopyToClipboard.stories.tsx +0 -45
  94. package/src/styles/colors.ts +0 -60
  95. package/src/styles/index.ts +0 -3
  96. package/src/styles/shadows.ts +0 -6
  97. package/src/styles/theme.ts +0 -257
  98. package/src/styles/typography.ts +0 -86
  99. package/src/utils/date.ts +0 -32
  100. package/src/utils/index.ts +0 -6
  101. package/src/utils/masks/index.ts +0 -6
  102. package/src/utils/omitProperty.ts +0 -19
  103. package/src/utils/phone.ts +0 -76
  104. package/src/utils/ssn.ts +0 -8
  105. package/src/utils/string/index.ts +0 -2
  106. package/src/utils/string/toCapitalize.ts +0 -13
  107. package/src/utils/string/toSentenceCase.ts +0 -7
  108. package/src/utils/wrapPromise.ts +0 -19
  109. package/src/validations/date.schema.ts +0 -18
  110. package/src/validations/description.schema.ts +0 -5
  111. package/src/validations/email.schema.ts +0 -3
  112. package/src/validations/field.schema.ts +0 -3
  113. package/src/validations/index.ts +0 -8
  114. package/src/validations/phone.schema.ts +0 -6
  115. package/src/validations/ssn.schema.ts +0 -24
  116. package/src/validations/state.schema.ts +0 -3
  117. package/src/validations/unix.schema.ts +0 -11
@@ -1,254 +0,0 @@
1
- import {
2
- type ChangeEvent,
3
- type ForwardedRef,
4
- forwardRef,
5
- type KeyboardEvent,
6
- useCallback,
7
- useEffect,
8
- useImperativeHandle,
9
- useMemo,
10
- useRef,
11
- useState,
12
- } from 'react';
13
- import {
14
- Box,
15
- Stack,
16
- type StackProps,
17
- type SxProps,
18
- TextField,
19
- InputBase,
20
- type InputBaseProps,
21
- Typography,
22
- useTheme,
23
- FormControl,
24
- } from '@mui/material';
25
- import { v4 as uuid } from 'uuid';
26
-
27
- interface OTPInputProps {
28
- name?: string;
29
- onChange?: (event: { target: { value: string } }) => void;
30
- disabled?: boolean;
31
- sx?: SxProps;
32
- }
33
-
34
- export type OTPInputInstance = Readonly<{
35
- focus: () => void;
36
- blur: () => void;
37
- clear: () => void;
38
- }> & { get value(): string; set value(newValue: string) };
39
-
40
- /**
41
- * OTP input component that displays individual field for each value.
42
- * @param props
43
- * @param ref
44
- * @constructor
45
- */
46
- function OTPInputComponent(
47
- props: OTPInputProps,
48
- ref: ForwardedRef<OTPInputInstance> | null,
49
- ): React.JSX.Element {
50
- const theme = useTheme();
51
- // Generate unique ids for each input.
52
- const ids = useRef(Array.from({ length: 6 }, () => uuid()));
53
- const [values, setValues] = useState<string[]>([]);
54
- const inputRef = useRef<HTMLInputElement | null>(null);
55
- const inputsRef = useRef<Array<HTMLInputElement | null>>([]);
56
-
57
- const [isFocused, setIsFocused] = useState(false);
58
-
59
- // Control inputs from outside via ref.
60
- useImperativeHandle(
61
- ref,
62
- () => ({
63
- get value() {
64
- return values.join('');
65
- },
66
- set value(newValue: string) {
67
- setValues(newValue.split(''));
68
- // Trigger onChange when the value is set from outside.
69
- props.onChange?.({ target: { value: newValue } });
70
- },
71
- focus() {
72
- inputsRef.current[0]?.click();
73
- inputsRef.current[0]?.focus();
74
- },
75
- blur() {
76
- inputsRef.current.forEach((input) => input?.blur());
77
- },
78
- clear() {
79
- setValues([]);
80
- },
81
- }),
82
- [props, values],
83
- );
84
-
85
- const inputContainerProps: StackProps = {
86
- boxSizing: 'content-box',
87
- direction: 'row',
88
- alignItems: 'center',
89
- spacing: 1.25,
90
- sx: {
91
- '& input': {
92
- textAlign: 'center',
93
- fontWeight: 500,
94
- height: 30,
95
- [theme.breakpoints.down('xs')]: {
96
- height: 16,
97
- fontSize: 16,
98
- pt: 1,
99
- pb: 1,
100
- px: 1,
101
- },
102
- [theme.breakpoints.up('xs')]: {
103
- fontSize: 28,
104
- px: 1,
105
- },
106
- fontSize: 32,
107
- py: 1.75,
108
- },
109
- },
110
- };
111
- const inputProps: InputBaseProps = useMemo(
112
- () => ({
113
- inputProps: {
114
- inputMode: 'numeric',
115
- pattern: '[0-9]*',
116
- autoCorrect: 'off',
117
- autoCapitalize: 'off',
118
- },
119
- sx: {
120
- '& input': {
121
- borderRadius: 1,
122
- borderStyle: 'solid',
123
- borderColor: 'rgba(0, 0, 0, 0.23)',
124
- borderWidth: 1,
125
- },
126
- ...(isFocused && {
127
- '& input': {
128
- borderRadius: 1,
129
- borderStyle: 'solid',
130
- borderWidth: 1,
131
- borderColor: theme.palette.primary.main,
132
- boxShadow: `inset 0 0 0 1px ${theme.palette.primary.main}`,
133
- },
134
- }),
135
- },
136
- }),
137
- [isFocused, theme.palette.primary.main],
138
- );
139
-
140
- const focusFirstEmptyInput = useCallback(() => {
141
- const valuesString = values.join('');
142
- const firstEmptyInput = inputsRef.current[valuesString.length];
143
-
144
- firstEmptyInput?.focus();
145
- firstEmptyInput?.select();
146
- }, [values]);
147
-
148
- const handleChange = useCallback(
149
- (event: ChangeEvent<HTMLInputElement>) => {
150
- const value = event.target.value;
151
-
152
- // Allow up to 6 digits only.
153
- if (!value.length || !/^[0-9]{1,6}$/.test(value)) return;
154
-
155
- setValues((prev) => {
156
- const newValue = value.length === 6 ? [...value] : [...prev, ...value];
157
- const newValueString = newValue.join('');
158
-
159
- if (inputRef.current) {
160
- inputRef.current.value = newValue.join('');
161
- }
162
-
163
- // Calls onChange when all OTP fields are filled.
164
- if (newValueString.length === 6) {
165
- inputsRef.current.forEach((input) => input?.blur());
166
- props.onChange?.({ target: { value: newValueString } });
167
- }
168
-
169
- return newValue;
170
- });
171
- },
172
- [props],
173
- );
174
-
175
- const handleKeyUp = useCallback((event: KeyboardEvent<HTMLInputElement>) => {
176
- if (event.key === 'Backspace') {
177
- setValues((prev) => {
178
- const newValue = [...prev.slice(0, -1)];
179
- if (inputRef.current) {
180
- inputRef.current.value = newValue.join('');
181
- }
182
- return newValue;
183
- });
184
- }
185
- }, []);
186
-
187
- const handleFocus = useCallback(() => {
188
- focusFirstEmptyInput();
189
- setIsFocused(true);
190
- }, [focusFirstEmptyInput]);
191
-
192
- const renderInputGroup = useCallback(
193
- (startIndex: number) => {
194
- return new Array(3).fill(undefined).map((_, index) => {
195
- return (
196
- // FormControl is required for InputBase to avoid bad setState in handleBlur event, and it is one per input.
197
- <FormControl key={ids.current[index + startIndex]}>
198
- <InputBase
199
- inputRef={(input) =>
200
- ((inputsRef.current[index + startIndex] as any) = input)
201
- }
202
- autoComplete='one-time-code'
203
- autoFocus={index + startIndex === 0}
204
- value={values[index + startIndex] || ''}
205
- disabled={props.disabled}
206
- onChange={handleChange}
207
- onKeyUp={handleKeyUp}
208
- onFocus={handleFocus}
209
- onBlur={() => setIsFocused(false)}
210
- {...inputProps}
211
- data-testid={`otp-input-${index + startIndex}`}
212
- />
213
- </FormControl>
214
- );
215
- });
216
- },
217
- [
218
- handleChange,
219
- handleFocus,
220
- handleKeyUp,
221
- inputProps,
222
- props.disabled,
223
- values,
224
- ],
225
- );
226
-
227
- // Focus the first empty input when the value changes.
228
- useEffect(() => {
229
- focusFirstEmptyInput();
230
- }, [focusFirstEmptyInput]);
231
-
232
- return (
233
- <Box width='100%' sx={props.sx}>
234
- {/* Use input facade to update the value and listen to changes */}
235
- <div style={{ display: 'none!important', pointerEvents: 'none' }}>
236
- <TextField
237
- inputRef={inputRef}
238
- name={props.name}
239
- type='text'
240
- value={values.join('') || ''}
241
- sx={{ pointerEvents: 'none', display: 'none' }}
242
- inputProps={{ hidden: true }}
243
- />
244
- </div>
245
- <Stack {...inputContainerProps} onClick={focusFirstEmptyInput}>
246
- {renderInputGroup(0)}
247
- <Typography sx={{ fontWeight: '700', fontSize: 32 }}>-</Typography>
248
- {renderInputGroup(3)}
249
- </Stack>
250
- </Box>
251
- );
252
- }
253
-
254
- export const OTPInput = forwardRef(OTPInputComponent);
@@ -1,152 +0,0 @@
1
- import { Box, InputAdornment, type InputProps } from '@mui/material';
2
- import { type TextFieldProps } from '../TextField';
3
- import { useEffect, useMemo, useRef, useState } from 'react';
4
-
5
- import { getPhoneDataByFieldName } from '../../utils/phone';
6
- import { phoneSchema } from '../../validations/phone.schema';
7
-
8
- import { TextMaskCustom } from './TextMaskCustom';
9
- import CountrySelector from './CountrySelector';
10
- import DefaultInput from './DefaultInput';
11
- import { DataFieldClearAdornment } from './DataFieldClearAdornment';
12
-
13
- export interface PhoneInputProps {
14
- label?: string;
15
- name?: string;
16
- helperText?: string;
17
- initialValue?: string;
18
- onChange?: (value: string) => void;
19
- onValidPhone?: (value: string) => void;
20
- error?: boolean;
21
- handleChangeCountry?: (newCountry: string) => void;
22
- value?: string;
23
- shouldShowOnlyNorthAmericanCountries?: boolean;
24
- shouldHaveClearButton?: boolean;
25
- variant?: TextFieldProps['variant'];
26
- InputProps?: InputProps;
27
- }
28
-
29
- /**
30
- * Renders a phone input component with country selector and masking.
31
- *
32
- * @param label - The label for the phone input. Defaults to 'Phone'.
33
- * @param name - The name of the phone input. Defaults to 'phone'.
34
- * @param helperText - The helper text for the phone input.
35
- * @param onChange - The callback function to handle the change event of the phone input.
36
- * @param initialValue - The initial value for the phone input. Defaults to ''.
37
- * @param error - Whether the phone input has an error. Defaults to false.
38
- * @param handleChangeCountry - The callback function to handle the change event of the country selector.
39
- * @param value - The value of the phone input. If passed, it will be used instead of the value from component state.
40
- */
41
- export function PhoneInput({
42
- label = 'Phone',
43
- name = 'phone',
44
- helperText,
45
- onChange,
46
- onValidPhone,
47
- initialValue = '',
48
- error = false,
49
- handleChangeCountry,
50
- value: valueProp,
51
- InputProps,
52
- shouldHaveClearButton = false,
53
- }: Readonly<PhoneInputProps>): React.JSX.Element {
54
- const inputRef = useRef<HTMLInputElement | null>(null);
55
-
56
- /**
57
- * Represents the country selected for the phone input. Defaults to US.
58
- */
59
- const [country, setCountry] = useState<string>('US');
60
-
61
- /**
62
- * Represents the value of the phone input. Initially set to the initialValue passed in the props.
63
- */
64
- const [value, setValue] = useState<string>(initialValue);
65
-
66
- const phoneData = useMemo(
67
- () => getPhoneDataByFieldName('countryCode', country),
68
- [country],
69
- );
70
-
71
- /**
72
- * Handles the change of the selected country in the phone input.
73
- * @param newCountry - The selected country.
74
- */
75
- const _handleChangeCountry = (newCountry: string): void => {
76
- setCountry(newCountry);
77
-
78
- if (handleChangeCountry) {
79
- handleChangeCountry(newCountry);
80
- }
81
-
82
- // HACK alert:
83
- // Wait a while so focus can take effect.
84
- setTimeout(() => {
85
- inputRef.current?.focus();
86
- }, 10);
87
- };
88
-
89
- const checkIsValidPhone = (phone: string): void => {
90
- const validation = phoneSchema.safeParse(value);
91
- if (validation.success) {
92
- onValidPhone?.(phone);
93
- }
94
- };
95
-
96
- const handleChange = (value: string): void => {
97
- setValue(value);
98
- onChange?.(value);
99
- };
100
-
101
- useEffect(() => {
102
- checkIsValidPhone(value);
103
- }, [value]);
104
-
105
- const inputProps: TextFieldProps = {
106
- inputRef,
107
- label,
108
- name: `_${name}`,
109
- helperText,
110
- // if the value prop is passed, use it, otherwise use the value from component state
111
- // this allows the parent component to control the value of the input field
112
- value: valueProp ?? value,
113
- error,
114
- onChange: (e) => {
115
- handleChange(e.target.value);
116
- },
117
- inputProps: {
118
- // Receive unmasked value on change.
119
- unmask: true,
120
- // Make placeholder always visible
121
- lazy: false,
122
- mask: phoneData?.mask,
123
- placeholderChar: '_',
124
- // Tab index for each block.
125
- tabIndex: 0,
126
- },
127
- InputProps: {
128
- ...InputProps,
129
- inputComponent: TextMaskCustom as any,
130
- startAdornment: (
131
- <InputAdornment position='start'>
132
- <CountrySelector value={country} onChange={_handleChangeCountry} />
133
- </InputAdornment>
134
- ),
135
- endAdornment: shouldHaveClearButton && (
136
- <DataFieldClearAdornment
137
- handleClear={() => {
138
- handleChange('');
139
- }}
140
- />
141
- ),
142
- },
143
- fullWidth: true,
144
- };
145
-
146
- return (
147
- <Box width='100%'>
148
- <input name={name} value={value} readOnly type='hidden' hidden />
149
- <DefaultInput {...inputProps} />
150
- </Box>
151
- );
152
- }
@@ -1,99 +0,0 @@
1
- import { useState } from 'react';
2
- import { Box, TextField, type TextFieldProps } from '@mui/material';
3
-
4
- import { usePrevious } from '../../hooks/usePrevious';
5
- import { DataFieldClearAdornment } from './DataFieldClearAdornment';
6
- import { TextMaskCustom } from './TextMaskCustom';
7
-
8
- type TextStyles = Omit<TextFieldProps, 'onChange'> & { onChange: any };
9
-
10
- export interface SSNInputProps {
11
- onChange?: (event: { target: { value: string } }) => void;
12
- name?: string;
13
- value?: string;
14
- label?: string;
15
- error?: boolean;
16
- helperText?: string;
17
- shouldHaveCloseAdornment?: boolean;
18
- }
19
-
20
- /**
21
- * This component manages the input of type SSN.
22
- * @constructor
23
- */
24
- export function SSNInput({
25
- onChange,
26
- label = 'Social Security number',
27
- shouldHaveCloseAdornment = false,
28
- ...rest
29
- }: SSNInputProps): React.JSX.Element {
30
- // Arbitrary states to allow to empty input field.
31
- const [value, setValue] = useState<string | undefined>('');
32
- const previousValue = usePrevious(value);
33
-
34
- const handleChange = (value: string): void => {
35
- setValue(value);
36
- onChange?.({ target: { value } });
37
- };
38
-
39
- const handleClear = (): void => {
40
- handleChange('');
41
- onChange?.({ target: { value: '' } });
42
- };
43
-
44
- const textFieldStyle: TextStyles = {
45
- value,
46
- onChange: (e: any, nativeEvent: any) => {
47
- if (!nativeEvent) return;
48
- handleChange(e.target.value);
49
- },
50
- inputProps: {
51
- onFocus: () => {
52
- handleChange('');
53
- },
54
- onBlur: () => {
55
- if (value?.length) return;
56
- handleChange(previousValue ?? '');
57
- },
58
-
59
- // Use onChange event.
60
- useOnComplete: false,
61
- // Use unmasked value.
62
- unmask: true,
63
- // Mask in the pattern of SSN.
64
- mask: 'XXX-XX-0000',
65
-
66
- definitions: {
67
- X: {
68
- mask: /[0-9•]/,
69
- displayChar: '•',
70
- },
71
- },
72
-
73
- // Set input mode to numeric, so mobile virtual keyboards just show numeric keys.
74
- inputMode: 'numeric',
75
-
76
- overwrite: false,
77
- // Tab index for each block.
78
- tabIndex: 0,
79
- },
80
- InputProps: {
81
- inputComponent: TextMaskCustom as any,
82
-
83
- endAdornment: !!shouldHaveCloseAdornment && (
84
- <DataFieldClearAdornment
85
- onClick={handleClear}
86
- handleClear={handleClear}
87
- />
88
- ),
89
- },
90
- fullWidth: true,
91
- label,
92
- };
93
-
94
- return (
95
- <Box width='100%'>
96
- <TextField {...textFieldStyle} {...rest} />
97
- </Box>
98
- );
99
- }
@@ -1,101 +0,0 @@
1
- import {
2
- Autocomplete,
3
- TextField,
4
- type TextFieldProps as InternalFieldProps,
5
- } from '@mui/material';
6
- import { useState } from 'react';
7
-
8
- interface TextFieldProps extends Omit<InternalFieldProps, 'onChange'> {}
9
-
10
- interface Option {
11
- label: string;
12
- id: string;
13
- }
14
-
15
- interface SelectInputProps {
16
- name?: string;
17
- onChange?: (value: Option | null) => void;
18
- onClear?: () => void;
19
- options: Option[];
20
- value?: Option | null; // Controlled value
21
- defaultOption?: Option;
22
- InputProps?: TextFieldProps;
23
- disableClearable?: boolean;
24
- }
25
-
26
- /**
27
- * This component manages the input of type Select.
28
- * @constructor
29
- */
30
- export function SelectInput({
31
- options,
32
- defaultOption,
33
- value: controlledValue,
34
- onChange,
35
- onClear,
36
- disableClearable,
37
- ...props
38
- }: SelectInputProps): React.JSX.Element {
39
- const [internalValue, setInternalValue] = useState<Option | null>(
40
- defaultOption ?? null,
41
- );
42
-
43
- // Determine the value to display
44
- const isControlled = controlledValue !== undefined;
45
- const value = isControlled ? controlledValue : internalValue;
46
-
47
- const handleChange = (option: Option | null): void => {
48
- if (!isControlled) {
49
- setInternalValue(option); // Update internal state only if uncontrolled
50
- }
51
- if (onChange) {
52
- onChange(option);
53
- }
54
- };
55
-
56
- const handleClear = (): void => {
57
- handleChange(null);
58
- if (onClear) {
59
- onClear();
60
- }
61
- };
62
-
63
- const textFieldStyle: TextFieldProps = {
64
- inputProps: {
65
- tabIndex: 0,
66
- },
67
- fullWidth: true,
68
- ...props.InputProps,
69
- };
70
-
71
- return (
72
- <Autocomplete
73
- disablePortal
74
- autoHighlight
75
- defaultValue={defaultOption}
76
- options={options}
77
- disableClearable={disableClearable}
78
- isOptionEqualToValue={(option, value) => option?.id === value?.id}
79
- value={value}
80
- onChange={(_event, newInputValue) => {
81
- // User clicked on clear button.
82
- if (!newInputValue) {
83
- handleClear();
84
- return;
85
- }
86
-
87
- handleChange(newInputValue);
88
- }}
89
- renderInput={(params) => (
90
- <TextField
91
- {...params}
92
- {...textFieldStyle}
93
- inputProps={{
94
- ...params.inputProps,
95
- ...textFieldStyle.inputProps,
96
- }}
97
- />
98
- )}
99
- />
100
- );
101
- }
@@ -1,48 +0,0 @@
1
- import { forwardRef, type Ref } from 'react';
2
- import { IMaskInput } from 'react-imask';
3
-
4
- export type ChangeEvent = (
5
- event: { target: { name: string; value: string } },
6
- nativeEvent?: InputEvent,
7
- ) => void;
8
-
9
- interface TextMaskCustomProps {
10
- onChange: ChangeEvent;
11
- name: string;
12
- mask: string;
13
- definitions?: Record<string, RegExp>;
14
- // Value to define which event to handle onAccept(default) or onComplete.
15
- useOnComplete?: boolean;
16
- }
17
-
18
- /**
19
- * Component that mask the input with the given mask pattern.
20
- * @param props {TextMaskCustomProps}
21
- * @param ref {Ref<HTMLInputElement>}
22
- * @constructor
23
- */
24
- function TextMaskCustomComponent(
25
- props: TextMaskCustomProps,
26
- ref: Ref<HTMLInputElement>,
27
- ): React.JSX.Element {
28
- const { onChange, useOnComplete, ...other } = props;
29
- return (
30
- <IMaskInput
31
- {...other}
32
- inputRef={ref}
33
- onAccept={(value, _, event) => {
34
- if (useOnComplete) return;
35
- onChange({ target: { name: props.name, value } }, event);
36
- }}
37
- onComplete={(value, _, event) => {
38
- if (!useOnComplete) return;
39
- onChange({ target: { name: props.name, value } }, event);
40
- }}
41
- overwrite
42
- />
43
- );
44
- }
45
-
46
- export const TextMaskCustom = forwardRef<HTMLInputElement, TextMaskCustomProps>(
47
- TextMaskCustomComponent,
48
- );
@@ -1,5 +0,0 @@
1
- export * from './DateInput';
2
- export * from './SSNInput';
3
- export * from './SelectInput';
4
- export * from './PhoneInput';
5
- export * from './OTPInput';
@@ -1,13 +0,0 @@
1
- export * from './Button';
2
- export * from './Typography';
3
- export * from './CredentialRequestsEditor';
4
- export * from './terms/AcceptTermsNotice';
5
- export * from './When';
6
- export * from './Alert';
7
- export * from './Image';
8
- export * from './form/';
9
- export * from './verified';
10
- export * from './QRCodeDisplay';
11
- export * from './Snackbar';
12
- export * from './Banners';
13
- export * from './Backdrop';
@@ -1,27 +0,0 @@
1
- import { Box, type Theme, Typography, useTheme } from '@mui/material';
2
-
3
- import LegalLink from './LegalLink';
4
- interface AcceptTermsNoticeProps {
5
- legalLinkUrl?: string;
6
- }
7
- export const AcceptTermsNotice = ({
8
- legalLinkUrl = 'https://www.verified.inc/legal#terms-of-use',
9
- }: AcceptTermsNoticeProps): React.JSX.Element => {
10
- const theme: Theme = useTheme();
11
- return (
12
- <Box display='inline-block'>
13
- <Typography
14
- align='center'
15
- sx={{
16
- fontSize: '.75rem',
17
- fontWeight: 400,
18
- color: theme.palette.neutral.main,
19
- lineHeight: 1.25,
20
- }}
21
- >
22
- By continuing, you agree to Verified’s{' '}
23
- <LegalLink href={legalLinkUrl}>Terms of Use</LegalLink>.
24
- </Typography>
25
- </Box>
26
- );
27
- };