I am writing a game and when the game is over, I want it to reset to the initial state. I haven't found any meaningful information in the docs for this, so I've been playing around with adding a reset method to my Game class. First, I attempted doing the follow in hopes of creating a base class I could extend later, but using a variable for the component name fails:
class Game extends React.Component {
constructor(props) {
super(props);
this.state = {
...
};
}
reset() {
var node = ReactDOM.findDOMNode(this),
ComponentName = this.constructor.name;
if (node) {
ReactDOM.unmountComponentAtNode(node);
ReactDOM.render(<ComponentName />, node);
}
}
...
}
I moved on, and tried to hardcode the component name as follows:
class Game extends React.Component {
constructor(props) {
super(props);
this.state = {
...
};
}
reset() {
var node = ReactDOM.findDOMNode(this);
if (node) {
ReactDOM.unmountComponentAtNode(node);
ReactDOM.render(<Game />, node);
}
}
...
}
This works really well, but I am wondering if there is a built-in way that is better, or a more generic way.
Update Please disregard the previous answer, replaceState is obviously not available in the ES2015 class pattern. Anyway, another solution is to keep an instance of the game in a wrapper component's state.
Working fiddle: https://jsfiddle.net/dannyjolie/upktozt1/1/
This will just remove the old game from App's state when you reset to a new game, and a new game will take its place.
class App extends React.Component {
constructor(props) {
super(props);
this.newGame = this.newGame.bind(this);
this.state = {
game: ()=><Game />
};
}
newGame () {
this.setState({
game: () => <Game />
});
}
render () {
const ActiveGame = this.state.game;
return (
<div>
<ActiveGame />
<button onClick={this.newGame}>RESET GAME</button>
</div>
);
}
}
class Game extends React.Component {
constructor(props) {
super(props);
this.state = {
foo: 'Bar'
};
this.onButtonClick = this.onButtonClick.bind(this);
}
onButtonClick () {
this.setState({
somethingElse: 'Hello',
foo: 'Changed foo'
});
}
render () {
return (
<div>
<button onClick={this.onButtonClick}>Set state.somethingElse</button>
<p>state.foo: {this.state.foo}</p>
<p>state.somethingElse: {this.state.somethingElse || '(not defined yet)'}</p>
</div>
);
}
}
If you need only reset state
then you can move default state into some function or variable and when you need reset state only call setState
with value from this function or variable.
Example:
class Game extends React.Component {
constructor(props) {
super(props);
this.state = this.getState(); // set state from getState result
this.onButtonClick = this.onButtonClick.bind(this);
this.onReset = this.onReset.bind(this);
}
getState() {
return {
number: 0
}
}
onReset() {
this.setState(this.getState()) // set state from getState result
}
onButtonClick () {
this.setState({
number: this.state.number + 1
});
}
render () {
return (
<div>
<button onClick={this.onButtonClick}>
Increment
</button>
<p>{this.state.number}</p>
<button onClick={this.onReset}>
Reset
</button>
</div>
);
}
}
Example on JSFiddle
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