React中多个Ant Design Collapse面板共享状态无法独立修改如何解决?
问题根源
4个面板共享了父组件中同一份followed和show状态,只要修改就会同步作用到所有面板上,要实现状态独立,需要将这两个状态改成按面板唯一标识(你代码里的keys属性)分类存储的结构。
改造步骤
1. 改造父组件状态定义
将原来的单个布尔值状态,替换为以面板keys为键的对象结构,存储每个面板独立的状态:
// 父组件原来的状态定义(删除) // const [followed, setFollowed] = useState(false); // const [show, setShow] = useState(false); // 替换为以下代码,key对应你4个面板的keys属性值 const [followedMap, setFollowedMap] = useState({ "1": false, "2": false, "3": false, "4": false }); const [showMap, setShowMap] = useState({ "1": false, "2": false, "3": false, "4": false });
2. 新增父组件按面板修改状态的方法
给状态修改方法增加面板key参数,实现仅修改指定面板的状态:
// 切换单个面板的展开/收起状态 const handleSetShow = (panelKey) => { setShowMap(prev => ({ ...prev, [panelKey]: !prev[panelKey] })); }; // 修改单个面板的followed状态 const handleFollow = (panelKey) => { setFollowedMap(prev => ({ ...prev, [panelKey]: true })); };
3. 修改每个面板的传参和事件绑定
给每个AntCollapse传入对应key的独立状态,以及绑定了当前面板key的方法:
// 第一个面板示例,其他3个面板替换对应key值即可 <AntCollapse isFollowed={followedMap["1"]} show={showMap["1"]} keys="1" setShow={() => handleSetShow("1")} id={styles.telegramHeader1} header="Follow XXX on Telegram" > <Row type='flex' align='middle' justify='center'> <Button href={links} target="_blank" style={buttonStyle1} onClick={() => setClicked(false)}> <Icon type="link" style={{ color: '#fff' }} theme="outlined" /> Subscribe </Button> </Row> <span className={styles.greyLine}> </span> <Row type='flex' align='middle' justify='center'> {/* 仅修改这一行的点击事件,传入当前面板key */} <Button onClick={() => {handleFollow("1"); handleSetShow("1"); }} style={buttonStyle2} disabled={clicked}>Continue</Button> </Row> </AntCollapse>
可选优化
如果没有跨面板读取followed状态的需求,你可以直接把followed状态完全放到CustomCollapse内部管理,不需要从父组件传参,每个组件天然维护自己的独立状态,代码会更简洁。
内容的提问来源于stack exchange,提问作者Trey
相关产品推荐
相关产品推荐

