Reputation: 21
I'm creating a form that will have three input fields and I want to change the state to what has been input. Instead of having to write three separate functions to handle all three inputs is there a way to set the state depending on the field the user has chosen to fill in?
Thanks in advance.
handleChange = e => {
this.setState({
//Can this be changed to target the right field in the state// : e.target.value
})
}
render() {
return (
<div>
<div>
<label htmlFor="name">Name:</label>
<input
type="text"
value={this.state.name}
onChange={this.handleChange}
/>
</div>
<div>
<label htmlFor="county">County:</label>
<input
type="text"
value={this.state.county}
onChange={this.handleChange}
/>
</div>
<div>
<label htmlFor="position">Position:</label>
<input
type="text"
value={this.state.position}
onChange={this.handleChange}
/>
</div>
<button>Submit Player</button>
</div>
)
}
Upvotes: 0
Views: 180
Reputation: 468
Here is the code
handleChange = e => {
this.setState({
[e.target.name]: e.target.value
});
}
render() {
return (
<div>
<div>
<label htmlFor="name">Name:</label>
<input
type="text"
name="name"
value={this.state.name}
onChange={this.handleChange}
/>
</div>
<div>
<label htmlFor="county">County:</label>
<input
type="text"
name="county"
value={this.state.county}
onChange={this.handleChange}
/>
</div>
<div>
<label htmlFor="position">Position:</label>
<input
type="text"
name="position"
value={this.state.position}
onChange={this.handleChange}
/>
</div>
<button>Submit Player</button>
</div>
)
}
Upvotes: 3
Reputation: 11571
Rather than relying on anything in the DOM to identify the elements you want to update - which is not exactly best practice for React, because it confuses where the source of truth of state and model lie - you should abstract the form away entirely into a data structure:
state = {
formInputs: [
{
name: 'Name',
type: 'text',
value: '',
},
{
name: 'Country',
type: 'text',
value: '',
},
{
name: 'Position',
type: 'text',
value: '',
},
]
};
handleChange = (evt, n) => {
this.setState((state) => {
const arr = state.formInputs.slice();
arr[n] = {value: evt.target.value, ...arr[n]};
return {formInputs: arr};
});
}
render() {
return (
<div>
{this.state.formInputs.map((ea, i) => {
return (
<div key={ea.name} >
<label htmlFor={ea.name}>{`${ea.name}:`}</label>
<input {...ea} onChange={(e) => {this.handleChange(e, i)}} />
</div>
);
})}
<button>Submit Player</button>
</div>
);
}
Storing the data/inputs and their value in abstract component state -- and then using Array.map()
to transform them into rendered UI -- is a very common and useful pattern in React.
Advantages:
Upvotes: 1