Adding debounce to react hook form - reactjs

I have the following controlled component set up using react-hook-forms.
<Controller
control={control}
name={"test"}
render={({ field: { onChange, value, name } }) => (
<Dropdown
name={name}
value={value}
handleChange={onChange}
options={foodCategories()}
/>
)}
/>
I want to call a debounce and and I tried doing the following:
handleChange={debounce(onChange, 500)}
but I keep getting errors throw:
This synthetic event is reused for performance reasons, Objects are not valid as a React child (found: object with keys {dispatchConfig, _targetInst, nativeEvent, type, target, currentTarget, eventPhase, bubbles, cancelable,
How can I call debounce on a controlled react hook form component?

This could be achieved my the following implementation;
<Controller
name={fieldName}
rules={{ required: `errors.${fieldName}.required` }}
render={({ field, fieldState: { error } }) => (
<input
type="text"
error={error && t(`${error.message}`)}
onChange={debounce((e) => field.onChange(e), 50)}
defaultValue={field.value}
/>
)}
/>

Related

react select with form hook form submit

this works fine on form submit shows selected value when I add onChange event then on form submit it doesnot show selected value
<Controller name="CostCenterGrp" className="form-control" control={control} render={({ field, value}) => ( <ReactSelect {...field} isClearable options={costCenterHeads} value={value} /> )}`
You need to add field.onchange inside the component to manual edit the value
field.onChange(event);
<Controller
render={({ field }) => <input onChange={event=>{
handleSampleChange(event);
field.onChange(event);
}} />}
name="sample"
control={control}
/>

How to trigger re-render with `setValue` using react-hook-form?

I have a simple form with a select field, it's react-hook-form for validation and everything. There's a Controller which renders a Material UI Select. I would like to set the value of such select using setValue from outside the component (in the root of the form, where all controls reside).
This is the piece of code I'm using (slightly simplified not to waste too much of your time)
type Props = {
name: string;
control: Control<any>;
options: SelectOptions[];
};
const Select: FunctionComponent<Props> = ({
name,
control,
options,
}) => (
<Controller
control={control}
name={name}
render={({ field: { onChange, value } }) => {
return (
<FormControl>
<MuiSelect onChange={onChange}>
{options.map((o) => (
<MuiSelectItem key={o.key} value={o.value}>{o.label}</MuiSelectItem>
))}
</MuiSelect>
</FormControl>
)
}}
/>
);
As far as changing the value of the select, setValue works magically. When I feed a new value, it works as intended. The problem (I guess) is the component is not re-rendered, so the old value is still shown. I'm not sure how to fix this thing and docs did not help a lot. Any help is much appreciated, thanks!
As #knoefel said I tried setting the defaultValue="" but doesn't work for me(maybe because I am using FormProvider). So what I did is use watch instead of value
<Controller
name='name'
control={control}
render={({ field: { onChange } }) => (
<Select
dropdownValues={dropdownValues}
value={watch('name')}
onChange={onChange}
/>
)}
/>
I think you just forgot to set the value prop of <Controller /> to your <MuiSelect />. You also have to set a defaultValue for your <Controller /> field, either via the defaultValue prop or via useForm.
<Controller
control={control}
name={name}
defaultValue=""
render={({ field: { onChange, value } }) => {
return (
<FormControl>
<MuiSelect onChange={onChange} value={value}>
{options.map((o) => (
<MuiSelectItem key={o.key} value={o.value}>{o.label}</MuiSelectItem>
))}
</MuiSelect>
</FormControl>
)
}}
/>

How To implement ReactFlagsSelect with React Hook Form Controller

I tried to implement with React Hook From using <Controller />. While I am submitting the form country field return undefined.
<Controller
name="country"
control={control}
render={({ field: { onChange, value } }) => (
<ReactFlagsSelect
selected={selected}
onSelect={code => handleChange(code)}
value={value}
onChange={onChange}
/>
)}
/>
The problem is you pass RHF's onChange handler to the wrong prop. <ReactFlagsSelect /> doesn't have a onChange prop, instead you should pass it to the onSelect prop.
<Controller
name="country"
control={control}
render={({ field: { onChange, value } }) => (
<ReactFlagsSelect
selected={selected}
onSelect={onChange}
value={value}
/>
)}
/>
Side-note: RHF's will update value changes to your registered fields in it's internal form state, so there is no need to use extra state management for these values via useState or something similar. If you really need to call your handleChange callback, you can do both in the onSelect callback.
<Controller
name="country"
control={control}
render={({ field: { onChange, value } }) => (
<ReactFlagsSelect
selected={selected}
onSelect={code => {
onChange(code);
handleChange(code);
}}
value={value}
/>
)}
/>

React Hook Form and React Select Not Working as Expected

Im trying to wrap React Select inside of a React Hook Form with the Controller wrapper component as per the docs (https://react-hook-form.com/get-started#IntegratingControlledInputs)
<Controller
name="ShiftCaptain"
control={control}
render={({ field }) => (
<Select
{...field}
value={selectValue}
options={options}
placeholder={"Select Person"}
onChange={(e) => setSelectValue(e)}
/>
)}
/>
On form submission, the value captured inside the React Select isnt being populated into React Hook Forms:
Any ideas?
TIA
The field object of the render callback which you spread on your <ReactSelect /> component has a value and a onChange property, which RHF needs to link the value and also changes to the value to it's internal form state. Right now you overwriting this, so RHF can't update the value. Try this and it should work:
<Controller
name="ShiftCaptain"
control={control}
defaultValue={null}
render={({ field }) => (
<Select
{...field}
options={options}
placeholder={"Select Person"}
/>
)}
/>
If you want to set a default value for your select after page load you should use the <Controller /> defaultValue prop, which will pass the value to your <ReactSelect />.
Please check the this code sandbox.
https://codesandbox.io/s/react-hook-form-v7-controller-forked-40t3s?file=/src/index.js
const handleOnChange = (e) => {
setSelectedValue(e.value);
};
<label>React Select</label>
<Controller
name="ReactSelect"
control={control}
render={({ field }) => (
<ReactSelect
isClearable
{...field}
value={selectedValue}
onChange={handleOnChange}
options={[
{ value: "chocolate", label: "Chocolate" },
{ value: "strawberry", label: "Strawberry" },
{ value: "vanilla", label: "Vanilla" }
]}
/>
)}
/>

React Datepicker with redux-form

How to make the react-datepicker bind with redux-form?
I have this redux-form field:
<Field name="due_date" component={props =>
<DatePicker
{...props}
readOnly={true}
selected={this.state.due_date}
value={this.state.due_date}
onChange={this.handleDueDate}
/>
} />
Whenever i submit the redux form does return an empty object not binding the datepicker's value...
my onChange :
handleDueDate(date) {
this.setState({
due_date: moment(date).format('L')
}, () => {
// do I need to dispatch and action here to update the redux-form in state tree?
})
}
you have to make a custom component to validate and use datepicker with redux-form
Try this
const datePicker = ({ input, label, type, className, selected, meta: { touched, error } }) => (
<div>
<div>
<DatePicker {...input}
selected={selected} placeholder={label}
type={type} className={className}
peekNextMonth
showMonthDropdown
showYearDropdown
dropdownMode="select"
/>
{touched && error && <span className="error_field">{error}</span>}
</div>
</div>
)
and then pass props to that custom component
<Field
name="date_of_birth"
component={datePicker}
type="text"
selected={this.state.date_of_birth}
onChange={this.handleChange.bind(this)}
className="form-control"
/>
For future readers, just go to this link: DatePicker in Redux Form
first, I created the component like metioned in link above and just passed the selected prop in it. in my case:
<Field
name="due_date"
component={DatePickerComponent}
selected={this.state.date_of_briefing} />

Resources