Next.js带Checkbox的搜索筛选组件问题:搜索后Checkbox失效
问题分析与修复方案
核心错误点
- 选中状态未持久化:
checkedMember是组件内部普通数组,每次组件渲染(如搜索触发重渲染)都会被重置为空,导致选中状态丢失。 - 搜索过滤数据源错误:搜索时直接基于状态
getMemberList过滤,多次搜索后会截断原始数据,无法还原完整列表。 - Checkbox语法错误:
type="checked"是无效属性,正确应为type="checkbox"。 - Checkbox未绑定选中状态:搜索后重新渲染的Checkbox无法读取之前的选中状态,导致显示与实际选中情况不符。
修复后的完整代码
const MemberSearchFilter = () => { const memberList = [ { "member_id": "133", "name": "Deepak Ramnani", "checked": "false" }, { "member_id": "116", "name": "Yash Chandhok", "checked": "false" }, { "member_id": "115", "name": "Tonia Sehan", "checked": "false" }, { "member_id": "101", "name": "Akanksha Garg", "checked": "false" }, ]; const [filteredMemberList, setFilteredMemberList] = useState(memberList); const [searchName, setSearchName] = useState(""); // 用状态持久化选中的成员ID const [checkedMemberIds, setCheckedMemberIds] = useState([]); // 始终基于原始成员列表过滤,避免数据截断 const onTypeFilterNonMemberHandler = (e) => { const textValue = e.target.value.toLowerCase(); setSearchName(textValue); const results = memberList.filter(customer => customer.name.toLowerCase().startsWith(textValue) ); setFilteredMemberList(results); }; // 通过状态更新函数处理选中/取消选中逻辑 const onClickCheckboxHandler = (e) => { const memberId = e.target.value; setCheckedMemberIds(prevIds => { if (e.target.checked) { return [...prevIds, memberId]; } else { return prevIds.filter(id => id !== memberId); } }); }; return ( <> <div className="col-md-9"> <input type="text" className="form-control w-3/6" style={{ width: "300px" }} placeholder="search by name" onChange={onTypeFilterNonMemberHandler} /> </div> <div className="row"> {filteredMemberList.map((list, index) => ( <div className="col-md-12" key={list.member_id}> {/* 用唯一的member_id作为key,避免索引key的问题 */} <div className="border my-[5px] rounded-lg px-[10px] py-[5px] relative"> <div className="flex align-center justify-center"> <div className="specialist-infos w-100"> <div> <h4 className="xs:text-[13px] text-[15px]" style={{ color: "#702963" }} > {list.name} </h4> {/* 原始数据无current_organisation字段,暂时注释或补充数据 */} {/* <p className="mb-0 text-[12px]">{list.current_organisation}</p> */} </div> </div> <input type="checkbox" {/* 修复type属性 */} name={`sendToMember`} className="radio_input" id={list.member_id} {/* 用member_id作为id,避免重名问题 */} value={list.member_id} checked={checkedMemberIds.includes(list.member_id)} {/* 绑定选中状态 */} onChange={onClickCheckboxHandler} /> </div> </div> </div> ))} </div> </> ); };
额外优化点
- 将状态变量
getMemberList重命名为filteredMemberList,语义更清晰。 - 使用
member_id作为列表项的key,而非索引,避免列表项顺序变化时的渲染问题。 - 简化
onChange事件的写法,直接传递函数引用。
内容的提问来源于stack exchange,提问作者utkarsh tiwari
相关产品推荐
相关产品推荐

