We have a form we want to validate on change only after a user have submitted a form.
We try to fix this warning now: "Cannot update a component from inside the function body of a different component." Which is mentioned in this issue of react on Github https://github.com/facebook/react/issues/18178
With this error we had a solution with a local useState. Which basically looks like this:
const component = () => {
const [validateOnChange, setValidateOnChange] = useState(false);
return (
<Formik
initialValues={{ one: '', two: '' }}
validationSchema={validationSchema}
validateOnChange={validateOnChange}
validateOnBlur={false}
onSubmit={handleSubmit}
>
{(formikProps: FormikProps<SomeTypes>) => {
/** validate form on change after one submit count */
formikProps.submitCount > 0 && setValidateOnChange(true);
return <FormComponent formikProps={formikProps} />;
}}
</Formik>
);
};
To fix this we currently have a PR for this solution. But I'm not sure as usually props are not mutable. But it does change the prop validateOnChange value..
example here: https://codesandbox.io/s/formik-example-ovi1c
How should we set a value for validate on change on a dynamic way?
I think this looks like a good solution. In this solution you aren't mutating the props but passing a slice of state as the prop and updating that slice of state.
You could update your conditional to prevent unnecessary updates.
formikProps.submitCount > 0 && validateOnChange === false && setValidateOnChange(true);
One possible solution could be to allow validateOnChange to optionally accept a function that could use props to return if the form should validateOnChange.
It looks like it's not really working. It is changing the validateOnChange prop inside the
Ahh, I'd have to dig in the code to verify but I'm assuming that is because validateOnChange gets set on formikBag and can't be changed once initialized.
Maybe check out the onReset function? You could use that to reset the form to the current props plus the updated validateOnChangeProp https://jaredpalmer.com/formik/docs/api/formik#onreset-values-values-formikbag-formikbag--void
You may need to add enableReinitialize={true} in order to cause the validateOnChange prop to reinitialize formik.
I'm not certain if that will actually work, but it's a good next step. Please note that enableReinitialize will cause Formik to reinitialize if values change, meaning if you pass a dynamic initialValues obejct to Formik you'll need to make sure it's memoized to prevent meaningless initializations.
Edit: I checked out your sandbox, and you were on the right track with your first attempt. However, you should update the state in an event handler instead of during render, like this:
https://codesandbox.io/s/formik-example-luou6
Note the change to <form onSubmit={} />
Thanks @johnrom . I was updating the component during the rendering. thanks for your reply and fix! I appreciate it.
Most helpful comment
You may need to addenableReinitialize={true}in order to cause the validateOnChange prop to reinitialize formik.I'm not certain if that will actually work, but it's a good next step. Please note that enableReinitialize will cause Formik to reinitialize if values change, meaning if you pass a dynamic initialValues obejct to Formik you'll need to make sure it's memoized to prevent meaningless initializations.Edit: I checked out your sandbox, and you were on the right track with your first attempt. However, you should update the state in an event handler instead of during render, like this:
https://codesandbox.io/s/formik-example-luou6
Note the change to
<form onSubmit={} />