Reputation: 1082
I'm trying to make the user profile editable in my component. Right now, when the user clicks "edit," the profile is replaced with a form that has the values they typed in as defaults. However, if they update only one field, the others get rewritten with blank values instead of passing the default value to the state.
Is there a way to pass the defaultValue to the state? I've tried value={} too but then the value doesn't change at all.
I'm trying to avoid having an "Edit" button for each input.
class AccountEditor extends Component {
constructor() {
super()
this.state = {
isEditing: false,
profile: {
firstName: '',
lastName: '',
city: '',
email: '',
bio: '',
}
}
}
toggleEdit(event) {
event.preventDefault()
this.setState({
isEditing: !this.state.isEditing
})
}
updateProfile(event) {
let updatedProfile = Object.assign({}, this.state.profile)
updatedProfile[event.target.id] = event.target.value
this.setState({
profile: updatedProfile
}
}
submitUpdate(event) {
event.preventDefault()
this.props.onUpdate(this.state.profile)
this.setState({
isEditing: !this.state.isEditing
})
}
render() {
let profile = this.props.profile
let content = null
if (this.state.isEditing == true) {
content = (
<div>
<input
id="firstName"
onChange={this.updateProfile.bind(this)}
defaultValue={profile.firstName} />
<br />
<input
id="lastName"
onChange={this.updateProfile.bind(this)}
defaultValue={profile.lastName} />
<br />
<input
id="city"
onChange={this.updateProfile.bind(this)}
defaultValue={profile.city} />
<br />
<input
id="email"
onChange={this.updateProfile.bind(this)}
defaultValue={profile.email} />
<br />
<textarea
id="bio"
onChange={this.updateProfile.bind(this)}
defaultValue={profile.bio} />
<br />
<button onClick={this.submitUpdate.bind(this)}>Done</button>
</div>
)
} else {
content = (
<div>
<h4>Name: </h4>
<span>{profile.firstName}</span>
<span>{profile.lastName}</span><br/>
<h4>City: </h4>
<span>{profile.city}</span><br/>
<h4>Bio :</h4>
<p>{profile.bio}</p><br />
<button onClick={this.toggleEdit.bind(this)}>Edit</button>
</div>
)
}
return (
<div>
{content}
</div>
)
}
}
export default AccountEditor
Upvotes: 4
Views: 12098
Reputation: 6507
You should replace defaultValue
with value = { this.state.someProp }
. So an example with your code would be
constructor(props) {
super(props)
this.state = {
isEditing: false,
profile: props.profile // Setting up the initial data from the passed prop
}
}
and
<input id="firstName"
onChange={ this.updateProfile.bind(this) }
value={ this.state.profile.firstName } />
More about using react with form elements in these docs.
Upvotes: 7