将事件发送到同一容器中的另一个组件的最佳做法?

问题描述 投票:1回答:2

所以我有一个按钮,它位于一个容器中并使用回调on onClick事件来更新容器中的状态,相当基本的东西。但是现在我希望那个容器让不同的孩子知道按钮被点击,这样它就可以触发相应的响应。 (并且它应该只让孩子知道一次,因此响应不会被触发一百万次)

我解决这个问题的方式看起来和感觉就像代码味道一样嘎嘎叫,所以我想我会问你们有没有更好的办法。这是我做的:

class myContainer extend Component {
   constructor(){
   super()
   state= { triggered: false }
   }
   componentWillUpdate(nextProps, nextState){
      this.hasTriggered = this.state.triggered !== nextState.triggered
   }

   triggerResponse = () => this.setState({...this.state, !this.state.triggered})

   render(){
      return (
         <myButton onClick={triggerResponse}/>
         <myComponent hasTriggered={this.hasTriggered}/>
      )
   }
}

现在这似乎工作得很好,也许这就是我应该做的,但它只是觉得必须有一种更简洁的方式将“我被点击”的简单信息发送到同一容器中的组件。对我来说,一个主要的红旗是“触发”是一个布尔值,但无论它是真还是假都无关紧要,所以如果触发为假,则没有任何意义,如果它是上一轮的另一个布尔值那么重要。这似乎违反了对我的良好做法。

*总结:我正在寻找的是一种快速的方式,只为一个更新周期赋予状态值,然后返回null或false,而不必再次更新它。或者以不同的方式获得相同的结果。

javascript reactjs
2个回答
0
投票

我提出了两个不同但不满意的答案:

class myContainer extend Component {
   constructor(){
   super()
   state= { hasTriggered: false }
   }
   shouldComponentUpdate(nextProps, nextState){
      return (!nextState.hasTriggered && this.state.hasTriggered)
   }

   componentDidUpdate(nextProps, nextState){
      if(nextState.hasTriggered)this.setState({hasTriggered: false})
   }

   triggerResponse = () => this.setState({hasTriggered: true})

   render(){
      return (
         <myButton onClick={triggerResponse}/>
         <myComponent hasTriggered={this.state.hasTriggered}/>
      )
   }
}

这是令人不满意的,因为它是一个非常简单的按钮点击的很多代码。我正在设置状态,将其发送,重置状态,然后忽略下一个渲染调用全部以容纳糟糕的按钮单击。好消息是我不再滥用布尔值,但这绝对是太多的代码。

class myContainer extend Component {
   componentDidUpdate(){
      this.hasTriggered = false
   }

   triggerResponse = () => {
      this.hasTriggered = true
      this.forceUpdate()
}

   render(){
      return (
         <myButton onClick={triggerResponse}/>
         <myComponent hasTriggered={this.hasTriggered}/>
      )
   }
}

我发现这种方法不能令人满意,因为我不再拥有状态中的共享状态。在我通过比较新旧状态并使变量将结果传递给我的组件之前也这样做之前,但至少那时我可以查看我的状态并看到有一个与该按钮有关的状态变量。现在我的组件中存在一个与实际状态无关的本地状态,这使得跟踪变得更加困难。


0
投票

在考虑了这一整天后,我得出的结论是@ShubhamKhatri在他的评论中走在正确的轨道上,我以为我是通过使用回调和传递状态将状态提升到我的容器,但显然有太多如果正在处理点击事件,则在我的组件中执行逻辑。因此,我的新规则是,在这种情况下,您应该提取在容器内执行onClick所需的任何状态。如果您的哑组件正在执行除回调之外的任何操作,那么这是一个错误。

我想在我的演示组件中执行onClick逻辑的原因是因为我使用第三方库(d3)来处理图形,所以我没有考虑到我没有拔出的状态是d3状态,如果我向上移动,在单击按钮时更改它,然后将其传递给我的组件,它可以很好地工作。

现在这意味着我需要在两个地方导入d3,我确实需要编写比以前更多的代码,但我认为关注点的分离和代码的整体清洁度非常值得。此外,它使我的儿童组件更容易维护,所以这很好。

© www.soinside.com 2019 - 2024. All rights reserved.