简体   繁体   English

如何在React中基于多个状态禁用按钮?

[英]How do I disable a button based on multiple states in React?

I'm building a form with React and I wanted to disable a button when the form is not 'valid', ie when one of the states is blank. 我正在用React构建一个表单,并且我想在表单“无效”(即状态之一为空白)时禁用按钮。 The button looks at a state called disable_button . 该按钮查看一个称为disable_button的状态。 Here's what I have so far: 这是我到目前为止的内容:

var MyForm = React.createClass({
  getInitialState: function() {
    return {
      group_id: '',
      ls_type_id: '',
      disable_button: false
    };
  },
  handleGroupChange: function(e) {
    this.setState({group_id: e.target.value});
  },
  handleTypeChange: function(e) {
    this.setState({ls_type_id: e.target.value});
  },
  handleClick: function() {
    console.log('Button clicked');
  },
  componentDidUpdate: function() {
    this.isFormValid();
  },
  isFormValid: function(){
    if (this.state.group_id == '' || this.state.ls_type_id == '') {
      this.setState({disable_button: true});
    } else {
      this.setState({disable_button: false});
    }
  },
  render: function() {
    return (
      <div>
        <select className='form-control' value={this.state.group_id} onChange={this.handleGroupChange}>
          <option value=''>Select group...</option>
          <option value='10'>Some group</option>
        </select>
        <br /> 
        <select className='form-control' value={this.state.ls_type_id} onChange={this.handleTypeChange}>
          <option value=''>Select type...</option>
          <option value='11'>Some type</option>
        </select>
        <br />
        <button className="btn btn-primary" onClick={this.handleClick} disabled={this.state.disable_button}>Save</button>
      </div>
    );
  }
});

ReactDOM.render(<MyForm />, document.getElementById('content'));

Running this code results in an Uncaught RangeError: Maximum call stack size exceeded and I realize why: it's because after the component updates, it calls my componentDidUpdate , which then updates a state, which then updates the component, and the loop occurs. 运行此代码会导致Uncaught RangeError: Maximum call stack size exceeded ,我意识到了原因:这是因为在组件更新之后,它调用了我的componentDidUpdate ,该componentDidUpdate随后更新了状态,然后更新了组件,并发生了循环。 So I don't really know how can I make the button disable when one of those states is blank. 因此,我真的不知道在其中一种状态为空白时如何禁用按钮。 I might add more form fields so I didn't want to hardcode it to only look at these two selects. 我可能会添加更多的表单字段,所以我不想对其进行硬编码以仅查看这两个选择。

Try this instead: 尝试以下方法:

isFormValid: function(){
  return this.state.group_id == '' || this.state.ls_type_id == '';
}

... ...

<button disabled={this.isFormValid()} ...>

componentDidUpdate has two props passed in to it, prevProps and prevState as documented . componentDidUpdate传递了两个props,分别是prevPropsprevState (已记录) You could use this fact in componentUpdate to only call isFormValid if either the type_id or ls_type_id has changed. 如果type_idls_type_id已更改,则可以在componentUpdate使用此事实以仅调用isFormValid

However, the cascading setState calls are a little inefficient. 但是,级联的setState调用效率较低。 It might make more sense to determine disable_button in your render function, since you don't appear to be consuming it anywhere else. 在渲染函数中确定disable_button可能更有意义,因为您似乎没有在其他任何地方使用它。 So, delete isFormValid and all calls to it, and put this in the beginning of render: 因此,删除isFormValid及其所有调用,并将其放在render的开头:

render: function () {
  var disable_button = false;
  if (this.state.group_id == '' || this.state.ls_type_id == '') {
    disable_button = true;
  }
  return ( <div> ...content </div>
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM