Zmienne stanu instancji v w reag.js

121

Czy w respond.js lepiej jest przechowywać odwołanie do limitu czasu jako zmienną instancji (this.timeout) czy zmienną stanu (this.state.timeout)?

React.createClass({
     handleEnter: function () {
         // Open a new one after a delay
         var self = this;
         this.timeout = setTimeout(function () {
             self.openWidget();
         }, DELAY);
     },
     handleLeave: function () {
        // Clear the timeout for opening the widget
        clearTimeout(this.timeout); 
     }
    ...
})

lub

React.createClass({
     handleEnter: function () {
         // Open a new one after a delay
         var self = this;
         this.state.timeout = setTimeout(function () {
             self.openWidget();
         }, DELAY);
     },
     handleLeave: function () {
        // Clear the timeout for opening the widget
        clearTimeout(this.state.timeout); 
     }
    ...
})

oba te podejścia działają. Chcę tylko poznać powody używania jednego nad drugim.

brendangibson
źródło
13
Z dokumentacji : NIGDY nie mutuj this.statebezpośrednio, ponieważ setState()późniejsze wywołanie może zastąpić dokonaną przez Ciebie mutację. Traktuj this.statetak, jakby była niezmienna”.
Felix Kling
6
Wskazówka: użyj autobindingu Reacta:this.timeout = setTimeout(this.openWidget, DELAY);
David Hellsing
1
Na co należy ustawić DELAY?
justingordon

Odpowiedzi:

171

Sugeruję przechowywanie go w instancji, ale nie w jego state. Za każdym razem, gdy statejest aktualizowany (co powinno być zrobione tylko setStatezgodnie z sugestią w komentarzu), React wywołuje renderi wprowadza niezbędne zmiany w prawdziwym DOM.

Ponieważ wartość timeoutnie ma wpływu na renderowanie komponentu, nie powinna istnieć state. Umieszczenie go tam spowodowałoby niepotrzebne wezwania render.

Ross Allen
źródło
12

Oprócz tego, co powiedział @ssorallen, powinieneś również pamiętać o odmontowaniu komponentu przed wywołaniem twojego handleLeave.

React.createClass({
     handleEnter: function () {
         // Open a new one after a delay
         this._timeout = setTimeout(function () {
             this.openWidget();
         }.bind(this), DELAY);
     },
     handleLeave: function () {
        // Clear the timeout for opening the widget
        clearTimeout(this._timeout); 
     },
     componentWillUnmount: function(){
        // Clear the timeout when the component unmounts
        clearTimeout(this._timeout); 
     },
    ...
});
Bandyta
źródło