Ant Design V5.18 Table鼠标hover触发冗余渲染问题求助
解决Table悬停操作按钮导致的冗余渲染问题
你的问题核心是每次hover状态变化时,整个Table组件及所有行都会触发重渲染,根源在于:
columns和data每次组件渲染都会重新创建新对象,导致Table判定props发生变化onRow返回的事件函数每次都是新实例,同样会触发Table重渲染- 操作列的render依赖
hoveredRowKey,状态变化时会让所有行的操作列重新计算
优化方案:通过缓存减少不必要的重渲染
直接上修改后的代码,关键优化点已标注:
import { useState, useMemo, useCallback } from 'react'; import { Table, Button } from 'antd'; const YourTableComponent = () => { const [hoveredRowKey, setHoveredRowKey] = useState(null); // 1. 用useMemo缓存静态数据,避免每次渲染创建新数组 const data = useMemo(() => [ { key: '1', name: 'John Brown', age: 32, address: 'New York No. 1 Lake Park' }, { key: '2', name: 'Jim Green', age: 42, address: 'London No. 1 Lake Park' }, { key: '3', name: 'Joe Black', age: 32, address: 'Sidney No. 1 Lake Park' }, ], []); // 2. 用useMemo缓存columns,仅当hoveredRowKey变化时才重新生成 const columns = useMemo(() => [ { title: 'Name', dataIndex: 'name', key: 'name', }, { title: 'Age', dataIndex: 'age', key: 'age', }, { title: 'Address', dataIndex: 'address', key: 'address', }, { title: 'Action', key: 'action', render: (_, record) => ( hoveredRowKey === record.key ? ( <span> <Button type="link">Edit</Button> <Button type="link">Delete</Button> </span> ) : null ), }, ], [hoveredRowKey]); // 3. 用useCallback缓存onRow的事件函数,避免每次渲染创建新函数 const rowEvents = useCallback((record) => ({ onMouseEnter: () => setHoveredRowKey(record.key), onMouseLeave: () => setHoveredRowKey(null), }), []); return ( <Table dataSource={data} columns={columns} onRow={rowEvents} /> ); }; export default YourTableComponent;
进阶优化:让操作列仅渲染当前hover行的按钮
如果上述优化后仍有轻微卡顿,可以把操作按钮拆成独立组件并用memo包裹,确保只有当前hover的行才会重新渲染操作按钮:
import { memo } from 'react'; // 独立的操作按钮组件,用memo包裹减少重渲染 const ActionButtons = memo(({ visible }) => { if (!visible) return null; return ( <span> <Button type="link">Edit</Button> <Button type="link">Delete</Button> </span> ); }); // 在columns的render中替换为该组件 render: (_, record) => ( <ActionButtons visible={hoveredRowKey === record.key} /> )
这样只有visible属性变化的行才会更新操作按钮,其他行的操作列不会触发重渲染。
内容的提问来源于stack exchange,提问作者Lisan Li
相关产品推荐
相关产品推荐

