如何点击切换React状态中sections数组元素的expanded属性?
实现方案
要完成sections数组中对应项的expanded属性切换,核心要遵循Reactstate不可变的原则,不能直接修改原数组或对象,以下是具体实现:
完整代码示例
import { useState } from 'react'; function SectionToggle() { const [sections, setSections] = useState([ { title: "section one", expanded: false }, { title: "section two", expanded: false }, ]); const toggleSection = (targetTitle) => { // 使用函数式更新获取最新state,避免闭包问题 setSections(prevSections => prevSections.map(section => // 匹配目标section,切换expanded状态 section.title === targetTitle ? { ...section, expanded: !section.expanded } : section ) ); }; return ( <div> {sections.map((section) => ( <div key={section.title} onClick={() => toggleSection(section.title)} style={{ cursor: 'pointer', padding: '8px', margin: '4px 0', border: '1px solid #ddd' }} > {section.title} {/* 可选:添加展开状态可视化标识 */} <span style={{ marginLeft: '8px' }}>{section.expanded ? '▼' : '▶'}</span> </div> ))} </div> ); } export default SectionToggle;
关键细节说明
- 不可变更新:通过
{ ...section }创建新对象,修改expanded属性,原state对象不会被直接修改,符合React的state更新规则。 - 函数式setState:使用
prevSections参数获取最新的state值,避免因闭包导致的旧state引用问题。 - 唯一标识匹配:通过
title作为匹配依据(如果title可能重复,建议给每个section添加唯一id字段),比直接传递section对象更可靠。 - 列表key:给每个列表项添加
key={section.title},帮助React高效识别列表项变化,提升渲染性能。
备选实现(使用索引)
如果你的sections不会出现顺序调整,也可以通过索引来切换状态:
const toggleSection = (index) => { setSections(prevSections => { const newSections = [...prevSections]; newSections[index] = { ...newSections[index], expanded: !newSections[index].expanded }; return newSections; }); }; // 渲染时传递索引 {sections.map((section, index) => ( <div key={index} onClick={() => toggleSection(index)} // ...其他属性 > {/* ...内容 */} </div> ))}
内容的提问来源于stack exchange,提问作者Onyx
相关产品推荐
相关产品推荐

