我正在研究用 React.JS 制作的过滤器组件。
其中一些过滤组件嵌入在面板中 ( div
)。面板的包裹部分如下所示:
Initiative <a onClick={() => {this.setState({ showInitiatives: true })}} className="milestone-list-link" href="#initiative">
{this.state.selectedInitiative}
<InitiativeSelector
initiatives={initiatives || {}}
show={this.state.showInitiatives}
selector={
() => {
console.log('called selector state:', this.state)
this.setState({ showInitiatives: false })
}
}
/>
<FilterIcon />
</a>
我的<InitiativeSelector />
如下所示:
const InitiativeSelector = ({initiatives, show, selector}) => {
return (show) ? (
<div className="list-filter">
<div>
<input placeholder="Search..." />
</div>
<ul>
{
Object.values(initiatives).map((initiative, i) => <li onClick={() => {selector()}} key={i}>{initiative.name}</li> )
}
</ul>
</div>
) : null
}
当我运行这个时,我的 selector
确实被叫了。因此,我看到状态打印到控制台。然而,this.setState({ showInitiatives: false })
似乎什么也没做。我的模式没有隐藏,第二次(等等)我点击<li>
, showInitiatives
仍设置为true
.
最佳答案
这是因为点击事件在 DOM 树中冒泡,并结合了 setState
第一个li.onClick
触发调用selector
,它调用setState({ showInitiatives: false})
然后a.onClick
触发调用setState({ showInitiatives: true })
。您可以通过添加日志语句来检查它是否正确。
现在您有 2 个待处理的更新
{ showInitiatives: false}
{ showInitiatives: true}
合并后是 noop。
您需要通过调用 e.stopPropagation()
来停止 li.onClick
内的事件传播,或者重新考虑 a.onClick
处理程序是什么正在做。
关于javascript - React 调用函数调用 setState 并传入无状态组件的 props,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48563859/