2016-06-30 34 views
0

我是新來的ReactJS,我有一個錯誤「this.setState不是一個函數」。ReactJS:this.setState不是函數嗎?

constructor() { 
    super(); 

    this.state = { 
     visible: false, 
     navLinesShow: true 
    }; 

    this.navOpen = this.navOpen.bind(this) 

} 

navOpen() { 
    this.setState({ 
     navStatus: "navShow", 
     navLinesShow: false 
    }); 

    if (this.state.visible === false) { 

     setTimeout(function(){ 

      this.setState({ 
       visible: true 
      }); 

     }, 3000); 

    } 

我已將this.navOpen = this.navOpen.bind(this)添加到構造函數中。所以我想問題是用setTimeout函數。

什麼是可能的修復?

謝謝。

回答

5

是問題的setTimeout函數裏面的setTimeout的「本」是指本身的功能:這樣的解決方案是典型的var that = this

navOpen() { 
this.setState({ 
    navStatus: "navShow", 
    navLinesShow: false 
}); 
if (this.state.visible === false) { 
var that = this; 
    setTimeout(function(){ 
     that.setState({ 
      visible: true 
     }); 
    }, 3000); 
} 
+1

你好Pinturic。是的,這是完美的。也許你可以解釋這個以幫助我更好地理解? – xoomer

+2

你也可以使用箭頭函數:'setTimeout(_ => {this.setState(...)},3000)''讓'this'按預期工作 – pawel

+0

我更新瞭解決方案,如果它不清楚我會詳細介紹它。如果你的瀏覽器/轉發器支持它,你可以使用胖箭頭語法 – pinturic

3

這是因爲this不具備應有正確的值到運行時綁定。你需要使用詞法綁定。最好的解決方案是使用ES6箭頭函數() => {},它提供了該值的詞彙綁定。即使是setTimeout()這個詞彙的結合會修正這個錯誤,你得到

constructor() { 
    super(); 

    this.state = { 
     visible: false, 
     navLinesShow: true 
    }; 
} 

navOpen =() => { 
    this.setState({ 
     navStatus: "navShow", 
     navLinesShow: false 
    }); 

    if (this.state.visible === false) { 
     setTimeout(() => { 
      this.setState({ 
       visible: true 
      }); 
     }, 3000); 
    } 
} 
2

除了另一種解決方案,以@ pinturic的解決方案是使用ES6箭頭功能。如果您使用的是ES6/Babel等,則可以使用箭頭函數綁定到詞彙this

navOpen() { 
    this.setState({ 
     navStatus: "navShow", 
     navLinesShow: false 
    }); 
    if (!this.state.visible) { 
     setTimeout(() => this.setState({visible: true}), 3000); 
    } 
}