How to write a mon function handleInputChange
that will take two or more arguments and update the states in the same way.
function X(param1 , param2 ,...){}
resultant state:
name: {value: param1 , error: param2}
Initial state declaration :
this.state = {
name: { value: "", error: "" },
city: { value: "", error: "" },
email: { value: "", error: "" },
contact_number: { value: "", error: "" },
otp_data: {}
};
My handleInputChange function:
handleInputChange = (name, value) => {
let label = "";
this.setState({
[label]: {
...this.state[label],
value: value,
error: validateFields(label, value)
}
});
};
How to write a mon function handleInputChange
that will take two or more arguments and update the states in the same way.
function X(param1 , param2 ,...){}
resultant state:
name: {value: param1 , error: param2}
Initial state declaration :
this.state = {
name: { value: "", error: "" },
city: { value: "", error: "" },
email: { value: "", error: "" },
contact_number: { value: "", error: "" },
otp_data: {}
};
My handleInputChange function:
handleInputChange = (name, value) => {
let label = "";
this.setState({
[label]: {
...this.state[label],
value: value,
error: validateFields(label, value)
}
});
};
Share
Improve this question
edited Apr 8, 2022 at 14:33
sidverma
asked Jul 24, 2020 at 4:37
sidvermasidverma
1,18512 silver badges25 bronze badges
1
- It would be helpful if you could include some code in the form of a minimal reproducible example. – Alexander Nied Commented Jul 24, 2020 at 4:40
4 Answers
Reset to default 2When using react hooks to manage state of the ponents it is more mon to separate properties if they do not affect each other like this:
const [name, setName] = React.useState(`default name, can be left empty`)
const [city, setCity] = React.useState(`default city, can be left empty`)
Now you can access state by accessing name
and city
and change them by using setCity('New York
)`.
If you need for whatever reason to group stage like it is done in Class based ponents you would do it like this:
const [obj, setObj] = React.useState({name: 'Milorad', city: 'Svrljig'})
Now to change only name you have to setObj(prev => ({...prev, name: 'Ilija'}))
or in your case where you have key value pairs:
const handleInputChange = (key, value) => {
setObj(prev => ({...prev,
[key]: {
...prev[key],
value: value,
error: validateFields(key, value)
})
});
};
It is always remended to create separate state for each variable. In functional ponent you can use useState as below
const [name, setName] = useState({ value: "", error: "" });
const [city, setCity] = useState({ value: "", error: "" });
const [email, setEmail] = useState({ value: "", error: "" });
const [contact_number, setContactNumber] = useState({ value: "", error: "" });
const [otp_data, setOtpData] = useState({ value: "", error: "" });
// Mapping of label with state changer
const labelStateMap = {
name: setName,
city: setCity,
email: setEmail,
contact_number: setContactNumber,
otp_data: setOtpData
}
handleInputChange = (label, value) => {
const stateChanger = labelStateMap[label];
if(stateChanger){
stateChanger({
value,
error: validateFields(label, value)
})
}
};
Instead of writing your own logic, you could consider using Formik which makes it a lot easier for you.
Using useState
hook you can do something like this
Make a state variable and initialize it to the initial form data
const [formData, setFormData] = useState({
name: { value: "", error: "" },
city: { value: "", error: "" },
email: { value: "", error: "" },
contact_number: { value: "", error: "" },
otp_data: {},
});
And to handle change,
handleInputChange = (event) => {
const { name, value } = event.target;
setFormData({
...formData,
[label]: {
value,
error: validateFields(label, value),
},
});
};
The input to handleChange
function calls the setFormData
function returned by the hook and overrides the form data for the changed input.