Skip to content
This repository was archived by the owner on Mar 25, 2025. It is now read-only.

Commit 050067a

Browse files
committed
feat(formik): add FormikSearchSelect component
1 parent 4c7d85b commit 050067a

File tree

3 files changed

+130
-0
lines changed

3 files changed

+130
-0
lines changed
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
export const meta = {
2+
name: 'FormikSearchSelect',
3+
route: '/formik/FormikSearchSelect',
4+
menu: 'Formik',
5+
}
6+
7+
# FormikSearchSelect
8+
9+
A formik component that wraps a SearchSelect component.
10+
11+
## Demo
12+
13+
```typescript type=demo
14+
<FormikDemo initialValues={{ fruits: 'cherry' }}>
15+
<FormikSearchSelectField
16+
label="Select favorite fruits"
17+
name="fruits"
18+
noOptionsLabel="No options"
19+
options={[
20+
{ label: 'Apple', value: 'apple' },
21+
{ label: 'Banana', value: 'banana' },
22+
{ label: 'Cherry', value: 'cherry' },
23+
{ label: 'Dragon fruit', value: 'dragon_fruit' },
24+
{ label: 'Elderberry', value: 'elderberry' },
25+
]}
26+
/>
27+
</FormikDemo>
28+
```
29+
30+
## Usage in code
31+
32+
```typescript
33+
import React, { useMemo, useCallback } from 'react'
34+
import { useFormik, FormikProvider } from 'formik'
35+
import { FormikSearchSelectField } from 'practical-react-components-formik'
36+
import * as yup from 'yup'
37+
38+
const MyComponent = ({ enabled }) => {
39+
const validationSchema = useMemo(
40+
() =>
41+
yup.object().shape({
42+
selected: yup.string().required(),
43+
}),
44+
[]
45+
)
46+
47+
const initialValues = useMemo(
48+
() => ({
49+
selected,
50+
}),
51+
// Initial values that should not change during
52+
// re-renders as formik handles state by itself
53+
// eslint-disable-next-line react-hooks/exhaustive-deps
54+
[]
55+
)
56+
57+
const onSubmit = useCallback((values: FormikValues) => {
58+
/* Save data here */
59+
}, [])
60+
61+
const formik = useFormik({
62+
initialValues,
63+
validationSchema,
64+
onSubmit,
65+
})
66+
67+
const options = [
68+
{ label: 'Apple', value: 'apple' },
69+
{ label: 'Banana', value: 'banana' },
70+
{ label: 'Cherry', value: 'cherry' },
71+
{ label: 'Dragon fruit', value: 'dragon_fruit' },
72+
{ label: 'Elderberry', value: 'elderberry' },
73+
]
74+
75+
return (
76+
<FormikProvider value={formik}>
77+
<FormikSearchSelectField
78+
label="Selected"
79+
name="selected"
80+
noOptionsLabel="No options"
81+
options={options}
82+
/>
83+
</FormikProvider>
84+
)
85+
}
86+
```
87+
88+
## Props
89+
90+
<Props of="FormikSearchSelect" />
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
import React, { useCallback } from 'react'
2+
import { useField, FieldConfig } from 'formik'
3+
import {
4+
SearchSelect,
5+
SelectProps,
6+
FieldProps,
7+
withField,
8+
} from 'practical-react-components-core'
9+
10+
export interface FormikSearchSelectProps<V extends string = string>
11+
extends Omit<SelectProps<V>, 'name' | 'value'>,
12+
Partial<Pick<SelectProps<V>, 'value'>>,
13+
Pick<FieldConfig, 'name' | 'validate'> {}
14+
15+
export function FormikSearchSelect<V extends string = string>({
16+
name,
17+
validate,
18+
...props
19+
}: FormikSearchSelectProps<V>): JSX.Element {
20+
const [field, meta, { setValue, setTouched }] = useField<V>({
21+
name,
22+
validate,
23+
})
24+
const onBlur = useCallback(() => setTouched(true), [setTouched])
25+
26+
return (
27+
<SearchSelect<V>
28+
{...field}
29+
onChange={setValue}
30+
onBlur={onBlur}
31+
error={meta.touched ? meta.error : undefined}
32+
{...props}
33+
/>
34+
)
35+
}
36+
37+
export const FormikSearchSelectField = <V extends string = string>(
38+
props: FieldProps & FormikSearchSelectProps<V>
39+
) => withField<FormikSearchSelectProps<V>>(FormikSearchSelect)(props)

packages/formik/src/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ export * from './FormikMultiSelect'
55
export * from './FormikNumberInput'
66
export * from './FormikNumberSelect'
77
export * from './FormikRadioButtonGroup'
8+
export * from './FormikSearchSelect'
89
export * from './FormikSelect'
910
export * from './FormikTextArea'
1011
export * from './FormikTextInput'

0 commit comments

Comments
 (0)