Form built using Chakra UI components
Below is the example how to integrate with Chakra UI.
There is a custom <ChakraFormInput />
component which accepts essential form
props, onChange
, onBlur
, error
and touched
and renders Chakra's input,
label and helper text under the input.
Alternative way is to use useConvert
hook to adopt form props to component.
Example ChakraAddressForm.tsx ChakraFormInput.tsx
"use client" ;
import { yupResolver } from "react-flexible-form-resolvers" ;
import { OnSubmit, useForm, Field } from "react-flexible-form" ;
import { useCallback } from "react" ;
import * as Yup from "yup" ;
import ChakraFormInput from "./ChakraFormInput" ;
import { Button, HStack, VStack } from "@chakra-ui/react" ;
type Values = {
country : string ;
state : string ;
city : string ;
zipCode : string ;
street1 : string ;
street2 ?: string | undefined ;
};
const resolver = yupResolver (
Yup. object ({
country: Yup. string (). required ( "Required" ),
state: Yup. string (). required ( "Required" ),
city: Yup. string (). required ( "Required" ),
zipCode: Yup. string (). required ( "Required" ),
street1: Yup. string (). required ( "Required" ),
street2: Yup. string (),
}),
);
const ChakraAddressForm = () => {
const onSubmit = useCallback < OnSubmit < Values >>(
async ({ formControl : { values , setIsSubmitting } }) => {
await new Promise (( resolve ) => setTimeout (resolve, 100 ));
alert ( `Form values: \n ${ JSON . stringify ( values ) }` );
setIsSubmitting ( false );
},
[],
);
const formControl = useForm ({
initialValues: {
country: "" ,
state: "" ,
city: "" ,
zipCode: "" ,
street1: "" ,
street2: undefined ,
},
onSubmit,
resolver,
});
return (
< VStack w = "full" alignItems = "flex-start" >
< HStack w = "full" >
< VStack w = "full" >
< Field
rffFormControl ={ formControl }
rffName = "country"
rffComponent ={ ChakraFormInput }
label = "Country"
/>
< Field
rffFormControl ={ formControl }
rffName = "state"
rffComponent ={ ChakraFormInput }
label = "State"
/>
< Field
rffFormControl ={ formControl }
rffName = "city"
rffComponent ={ ChakraFormInput }
label = "City"
/>
</ VStack >
< VStack w = "full" >
< Field
rffFormControl ={ formControl }
rffName = "zipCode"
rffComponent ={ ChakraFormInput }
label = "Zip Code"
/>
< Field
rffFormControl ={ formControl }
rffName = "street1"
rffComponent ={ ChakraFormInput }
label = "Street Address 1"
/>
< Field
rffFormControl ={ formControl }
rffName = "street2"
rffComponent ={ ChakraFormInput }
label = "Street Address 2"
/>
</ VStack >
</ HStack >
< Button
onClick ={ formControl.handleSubmit }
isLoading ={ formControl.isSubmitting }
>
Submit
</ Button >
</ VStack >
);
};
export default ChakraAddressForm;
"use client" ;
import {
FormControl,
FormHelperText,
FormLabel,
Input,
InputProps,
} from "@chakra-ui/react" ;
import { FC } from "react" ;
type Props = {
error : string | undefined ;
touched : boolean ;
label : string ;
value : string | number | undefined ;
onChange : ( arg : { target : { value : string | number } }) => void ;
onBlur : () => void ;
} & Omit < InputProps , "value" | "onChange" | "onBlur" >;
const ChakraFormInput : FC < Props > = ({ touched , error , label , ... rest }) => {
const isInvalid = !! (error && touched);
return (
< FormControl isInvalid ={ isInvalid } >
< FormLabel > { label } </ FormLabel >
< Input {... rest } />
{ isInvalid ? (
< FormHelperText color = "red" > { error } </ FormHelperText >
) : (
< FormHelperText whiteSpace = "pre" > </ FormHelperText >
) }
</ FormControl >
);
};
export default ChakraFormInput;