Reputation: 81
I ran into a use case where I have to reset the current state to initial state. I tried preserving in an instance variable but forgot that it works through reference and when the state updates the instance variable will also update. When the user hits reset button the state should refer to initial state which is stored in this.reset
. But I couldn't find a workaround.
class MyApp extends {Component} {
constructor(props){
super(props);
this.state = {
data: null
}
this.reset = null;
this.resetData = this.resetData.bind(this);
}
componentWillReceiveProps(nextProps) {
const {data} = nextProps;
this.reset = data;
this.setState({
data
});
}
resetData(){
this.setState({
data: this.reset
});
}
render() {
return(
<button onClick={this.resetData}> {this.state.data}</button>
);
}
}
Upvotes: 2
Views: 2653
Reputation: 30390
Are you able to use a third party library?
Lodash provides the deepClone()
method that would be useful to you for this, and would allow you to reset your component's state, regardless of the shape of data
that is passed in.
You'll also want to make sure you use deepClone()
each time you invoke resetData()
to ensure that the data
reference passed to .setState()
is to a copy (clone) of your this.reset
data, rather than a direct reference to the this.reset
data:
import _ from 'loadash'
class MyApp extends Component {
...
componentWillReceiveProps(nextProps) {
const {data} = nextProps;
// Invoke cloneDeep to get a clone of data that is also a unique
// reference
this.reset = _.cloneDeep(data);
this.setState({
data
});
}
resetData(){
// Remember to clone reset data each time you reset data, so that
// data is a reference to a new copy of this.reset, rather than
// the reset data you stored when componentWillReceiveProps was
// called
this.setState({
data: _.cloneDeep(this.reset)
});
}
...
}
Upvotes: 3