美文网首页
React基础组件的事件绑定

React基础组件的事件绑定

作者: Oo晨晨oO | 来源:发表于2017-09-25 11:31 被阅读95次

    在React中, 对于组件事件的绑定是有很大的坑的.
    比如经常会报如下这种错误: Warning: setState(...): Cannot update during an existing state transition (such as within `render` or another component's constructor). Render methods should be a pure function of props and state; constructor side-effects are an anti-pattern, but can be moved to `componentWillMount`.
    这种错误引起的原因是在事件绑定的位置直接使用了方法, 而不是调用的匿名函数.

    比如如下这样就会报错:

     <button className="btn btn-default"
         disabled={submitting} onClick={
           editStop(form)
          } >
     <i className="fa fa-ban"/> 取消
      </button>
    

    解决方法:

     <button className="btn btn-default"
         disabled={submitting} onClick={()=>{
             editStop(form)
        }} >
      <i className="fa fa-ban"/> 取消
    </button>
    

    注意, 在onclick的地方, 我们把直接放上去的函数onClick={editStop(form)}改为了使用匿名函数来调用onClick={()=>{editStop(form)}
    也就是说使用一个函数将我们的onclick函数句柄包裹起来.

    还可以看一下下面的例子:

    class ErrorSimulation extends React.Component {
      constructor(props) {
        super(props);
        this.state = {
          x : 1
        };
      }
      sayHello(){
        console.log("sayHello");
      }
      _changeValue(newValue){
        console.log("_changeValue invoke!");
        //你会发现虽然我们没有点击下面的超链接,但是这里会无限打印log,所以说react会自动执行下面的onClick表达式,从而得到真正的onclick函数句柄,
     //进而导致无限修改state与reRender,直到内存溢出。因此可以是onClick={this._changeValue.bind(2)}或者onClick={()=>{this._changeValue(2)}},
     //后者当react执行onClick表达式的时候得到的是一个函数
        this.setState({newValue});
      }
      render() {
        return (
        <div>
         <a onClick={this._changeValue.bind(2)}>Change Value</a>
         <a onClick={this.sayHello()}>sayHello</a>
        </div>
        )
      }
    }
    ReactDOM.render(
      <ErrorSimulation name="World" />,
      document.getElementById('container')
    );
    

    参考资料最重要的一篇 Why does this error exist: “Invariant Violation: Cannot update during an existing state transition” setState(...): Cannot update during an existing state transition
    总结: 你可以看到,我们的第二个a标签我们onClick是直接调用了函数,所以会导致无限渲染元素,导致内存溢出。而第一个a标签,我们使用了bind,所以必须点击才能触发,这才是我们想要的结果。

    相关文章

      网友评论

          本文标题:React基础组件的事件绑定

          本文链接:https://www.haomeiwen.com/subject/kmbrextx.html