最近在使用List组件的时候,发现组件没有重新渲染,导致状态发送错误。首先,我复现下代码。
function Other() {
const [data, setData] = useState([6, 7, 8, 3, 4, 5])
function handleData() {
setData([6, 7, 8, 9])
}
function handleData1() {
setData([6,7,8])
}
return (
<>
<Button onClick={handleData}>12</Button>
<Button onClick={handleData1}>12</Button>
<List dataSource={data} renderItem={(item)=><ListData list={item}/>}>
</List>
</>
)
}
function ListData(props) {
const [check, setCheck] = useState(false)
console.log(check)
return <div onClick={() => setCheck(!check)}>{props.list}{check?" true":" false"}</div>
}
export default Other
这里我们使用了List组件,这是一个很常用的组件。
但是当我们点击按钮的时候,发现6,7,8三个组件 都没有重新渲染。
我们很容易 就会想到 map key唯一性的问题。 但是如果我们这样改
<List dataSource={data} renderItem={(item,index)=><ListData list={item} key={index}/>}>
</List>
//or
<List dataSource={data} renderItem={(item,index)=><ListData list={item} key={item}/>}>
</List>
我们会发现 依然没有用 。组件还是没有被重复渲染
当我们查看 antd文档的时候,也没有关于该解决方案的 props。
所以我们得去查看源码
renderItem = (item: any, index: number) => {
const { renderItem, rowKey } = this.props;
let key;
if (typeof rowKey === 'function') {
key = rowKey(item);
} else if (typeof rowKey === 'string') {
key = item[rowKey];
} else {
key = item.key;
}
if (!key) {
key = `list-item-${index}`;
}
this.keys[index] = key;
return renderItem(item, index);
};
so, 看到这段代码,看名字我们也可以猜出 rowKey这个属性,就是我们需要使用的方法了。
所以我们将代码修改
<List dataSource={data} rowKey={()=>uuid()} renderItem={(item,index)=><ListData list={item} key={index}/>}>
</List>
这样就可以解决,组件没有被重新渲染的问题了