I am developing a dynamic form in React JS, when the user clicks on the Add button, the Register form is added to screen. In the Register form I am using formik for validation.
The form is dynamically adding successfully but whenever I start entering any input in the input box, I am getting the following error in the console:
Warning: A component is changing an uncontrolled input of type text to be
controlled. Input elements should not switch from uncontrolled to controlled
(or vice versa). Decide between using a controlled or uncontrolled input element
for the lifetime of the component.
I am not sure where it is wrong. Below is my dynamic form rendering code -
Account.js
import React, { Component } from 'react';
import axios from 'axios';
import {
Card, CardBody, CardHeader,Button,Col, Row, Form, Container
} from 'reactstrap';
import { Formik, Field, ErrorMessage } from 'formik';
import WrapperForm from './WrapperForm'
class Account extends Component {
state = {
wrapperForm: [{}]
}
constructor(props) {
super(props);
}
addUser = () => {
this.setState((prevState) => ({
wrapperForm: [...prevState.wrapperForm, {}],
}));
}
render() {
let { wrapperForm } = this.state
return (
<Form>
<Container className="themed-container" fluid={true}>
<button type="button" onClick={this.addUser}>Add User</button>
<WrapperForm wrapperForm={wrapperForm} />
</Container>
</Form>
);
}
}
export default Account;
WrapperForm.js
const WrapperForm = (props) => {
return (
props.wrapperForm.map((val, idx)=> {
return (
<Formik
key={idx}
initialValues={{
email: props.wrapperForm[idx].email || '',
password: props.wrapperForm[idx].password || '',
firstName: props.wrapperForm[idx].firstName || '',
lastName: props.wrapperForm[idx].lastName || '',
zipCode: props.wrapperForm[idx].zipCode || ''
}}
>
{({ values }) => (
<Row style={{ marginBottom: "2em" }}>
<Card>
<CardHeader>Register</CardHeader>
<CardBody>
<Temp index={idx} />
</CardBody>
</Card>
</Row>
)}
</Formik>
)
})
)
}
Temp.js
const Temp = ({ index }) => {
let passwordId = 'password-'+ index;
let firstNameId = 'firstName-'+ index;
let lastNameId = 'lastName-'+ index;
let zipCodeId = 'zipCode-'+ index;
return (
<Card body outline color="primary">
<CardTitle>Create Profile</CardTitle>
<Row form>
<Col md={6}>
<Field
className="email"
component={customInputForm}
data-id={index}
id="email"
label="Email"
name="email"
placeholder="Email"
type="email"
/>
</Col>
</Row>
</Card>
)
}
It's the world's leading library for building forms in React. Formik is a complete solution that helps you to implement form validation, keep track of visited fields, and handle form submission in an efficient and robust manner. It is based on the concept of a controlled component.
The warning "A component is changing an uncontrolled input to be controlled" occurs when an input value is initialized to undefined but is later changed to a different value. To fix the warning, initialize the input value to an empty string, e.g. value={message || ''} . Here is an example of how the error occurs.
formikBag is an object that contains different methods and fields to act upon your formik form. I need access to formikBag.submitForm , and formikBag.isSubmitting inside the handleClick function. Eg: isSubmitting helps me with button styling while the form is submitting.
Using Formik's handleChange The handleChange method updates the form values based on the input's name attribute that was changed.
I found one solution, maybe it will help someone. You need to create dynamic initialValues
for formik as:
let passwordId = 'password-'+ idx ;
let firstNameId = 'firstName-'+ idx;
let lastNameId = 'lastName-'+ idx;
let zipCodeId = 'zipCode-'+ idx;
return (
<Formik
key={idx}
initialValues={{
email: props.wrapperForm[idx].email || '',
[passwordId]: props.wrapperForm[idx].password || '',
[firstNameId]: props.wrapperForm[idx].firstName || '',
[lastNameId]: props.wrapperForm[idx].lastName || '',
[zipCodeId]: props.wrapperForm[idx].zipCode || ''
}}
>
)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With