【问题标题】:React checkbox in stateless component is not updating immediately无状态组件中的反应复选框不会立即更新
【发布时间】:2017-09-07 15:26:05
【问题描述】:

我使用复选框创建了一个基本界面,该界面使用了一种反应设计模式,这种模式在我之前很受用,并且我认为效果很好 - 即提升状态并将道具传递给 UI 组件。我的复选框组件传递了一个值(一个指标)、一个状态更改方法和一个用于检查的布尔值。问题是复选框不会立即更新,即使您可以在 React 开发工具中看到它们正在更新。它们仅在下次单击时更新,例如选中另一个复选框时。这是代码:

class App extends React.Component {
 constructor(props) {
  super(props);
  this.state = {
   metricsSelected: []
  }
  this.selectMetric = this.selectMetric.bind(this)
 }

selectMetric(metric) {
 const metricsSelected = this.state.metricsSelected
 const index = metricsSelected.indexOf(metric)
 if (index !== -1){
  metricsSelected.splice(index, 1)
 }
 else {
  metricsSelected.push(metric)
 }
 this.setState({
  metricsSelected,
 });
}

render() {
 return (
  <div>
    <Sidebar
      metricsSelected={this.state.metricsSelected}
      selectMetric={this.selectMetric}/>
    <SomethingElse/>
   </div>
  )
 }
}

const SomethingElse = () => (<div><h2>Something Else </h2></div>)

const Sidebar = ({ metricsSelected, selectMetric }) => {
 const metrics = ['first thing', 'second thing', 'third thing']
 return (
  <div>
   <h3>Select Metrics</h3>
   { metrics.map( (metric, i) =>
    <Checkbox
      key={i}
      metric={metric}
      selectMetric={selectMetric}
      checked={metricsSelected.includes(metric)}/>
    )}
   </div>
  )
 }

const Checkbox = ({ metric, selectMetric, checked }) => {

const onChange = e => {
 e.preventDefault()
 selectMetric(e.target.value)
}
return (
  <ul>
   <li>{metric}</li>
   <li><input
   type='checkbox'
   value={metric}
   checked={checked}
   onChange={onChange} /></li>
  </ul>
 )
}

我已经阅读了几乎所有关于反应复选框的信息,并且复选框的大多数应用程序都在做与我想做的不同的事情。我尝试向 Checkbox 组件添加状态,但这似乎没有帮助,因为选中的值仍然需要从其他地方进入。我认为当道具改变时反应组件会重新渲染。是什么赋予了?

这是一个代码笔:https://codepen.io/matsad/pen/QpexdM

【问题讨论】:

标签: reactjs checkbox


【解决方案1】:

这是一个工作版本:http://codepen.io/TLadd/pen/oWvOad?editors=1111

class App extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      metricsSelected: {}
    }
    this.selectMetric = this.selectMetric.bind(this)
  }

  selectMetric(metric) {
    this.setState(({ metricsSelected }) => ({
      metricsSelected: {
        ...metricsSelected,
        [metric]: !metricsSelected[metric]
      }
    }))
  }

  render() {
    return (
      <div>
        <Sidebar
          metricsSelected={this.state.metricsSelected}
          selectMetric={this.selectMetric}/>
        <SomethingElse/>
      </div>
    )
  }
}

const SomethingElse = () => (<div><h2>Something Else </h2></div>)

const Sidebar = ({ metricsSelected, selectMetric }) => {
  const metrics = ['first thing', 'second thing', 'third thing']
  return (
    <div>
      <h3>Select Metrics</h3>
      { metrics.map( (metric, i) =>
        <Checkbox
          key={i}
          metric={metric}
          selectMetric={selectMetric}
          checked={Boolean(metricsSelected[metric])}/>
        )}
    </div>
  )
}

const Checkbox = ({ metric, selectMetric, checked }) => {
  return (
  <ul>
    <li>{metric}</li>
    <li>
      <input
        type='checkbox'
        name={metric}
        checked={checked}
        onChange={() => selectMetric(metric)} 
       />
     </li>
   </ul>
  )
}


ReactDOM.render(
  <App />,
  document.getElementById('root')
);

导致问题的两件事是您在 selectMetric 中改变了状态,并且您的复选框输入的 onChange 函数使用的是 e.target.value 而不是 e.target.checked。

我将 metricsSelected 状态更改为一个对象,因为我认为它使管理它变得相当容易。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-11-06
    • 2021-02-18
    • 1970-01-01
    • 2018-08-12
    • 2018-11-03
    • 1970-01-01
    • 1970-01-01
    • 2021-11-07
    相关资源
    最近更新 更多