I am creating a form in a React app using Formik and Yup for validation. The page component has a section for shipping address and billing address. I have a checkbox in the form that will hide the billing address section if the details are identical. My problem is that if the checkbox is checked, and the user hits submit
, the billing details are not copied over from the shipping details and thus I get an error.
My first thought was to add an onChange
hook to the checkbox which copies the shipping details to the billing details. The 2 problems I found with this are 1) what if the user clicks the checkbox before filling out any shipping details and 2) Formik already has a default onChange
hook. I then tried to add some code inside of the onSubmit
hook to update the values, but this hook is not called if the billing details are invalid or empty.
How would I go about copying over all shipping details to billing details only if the checkbox is checked? I am new to Formik, React, and Yup so I suspect I will probably need to restructure the code? Below is my very simplified form component with only a name for each section and the checkbox:
const DetailsPage = () => {
return (
<Formik
initialValues={{
name_s: "",
name_b: "",
same_address_box: false,
}}
validationSchema={yup.object({
name_s: yup.string().required("Required"),
name_b: yup.string().required("Required"),
})}
onSubmit={(values, { setSubmitting }) => {
setTimeout(() => {
updateOrderInfo("name_s", values.name_s); // Context hook that updates my order data once form is validated and submitted
updateOrderInfo("name_b", values.name_b);
setSubmitting(false);
}, 500);
}}
>
{({ values }) => (
<Form>
<section id="shipping-details-container"> // Shipping section
<MyTextInput
name="name_s"
type="text"
placeholder="Shipping name..."
/>
</section>
<section id="billing-details-container"> // Billing section
<MyCheckbox name={"same_address_box"}>Same Address</MyCheckbox> // Checkbox
{`${values.same_address_box}` !== "true" ? (
<div id="hide-address-container">
<MyTextInput
name="name_b"
type="text"
placeholder="Billing name..."
/>
</div>
) : (
<h1>SHOW NOTHING</h1>
)}
</section>
<button type="submit">Submit</button>
</Form>
)}
</Formik>
);
};
CodePudding user response:
Try
setTimeout(() => {
updateOrderInfo("name_s", values.name_s); // Context hook that updates my order data once form is validated and submitted
if (values.same_address_box) {
updateOrderInfo("name_b", values.name_s);
}
setSubmitting(false);
}, 500);
And in Yup schema make change:
name_b: yup.string(). when("same_address_box", {
is: true,
then: yup.string().required("Required")
})