react-table GlobalFilter输入异常:仅能输入单个字符且失焦
解决react-table GlobalFilter输入框单次输入后失焦的问题
问题根源
你遇到的输入框每次输入一个字符就失焦的问题,核心原因是**GlobalFilter组件被重复销毁并重新挂载**。如果你的GlobalFilter是定义在父组件(比如App)的内部,或者每次父组件渲染时都会生成新的组件引用,React会把它当成全新的组件处理——旧的输入框被卸载,新的输入框被创建,自然就丢失了焦点。
具体修复步骤
将
GlobalFilter组件移到父组件外部定义
把过滤组件抽离到父组件的作用域之外,确保它的引用在每次渲染时保持稳定,不会被React判定为新组件。修复后的代码示例:
// 把GlobalFilter放在App组件外部,作为独立组件 const GlobalFilter = ({ filter, setFilter }) => { return ( <input value={filter || ""} onChange={(e) => setFilter(e.target.value)} placeholder="全局搜索..." /> ); }; function App() { const columns = useMemo(() => [...], []); const data = useMemo(() => [...], []); const { getTableProps, getTableBodyProps, headerGroups, rows, prepareRow, state: { globalFilter }, setGlobalFilter, } = useTable( { columns, data }, useGlobalFilter ); return ( <div> <GlobalFilter filter={globalFilter} setFilter={setGlobalFilter} /> <table {...getTableProps()}> {/* 表格内容渲染 */} </table> </div> ); }缓存动态生成的props(如果有)
如果需要给GlobalFilter传递自定义的处理函数,一定要用useCallback缓存函数引用,避免每次渲染生成新函数导致组件重新挂载:function App() { // ... 其他逻辑 const handleFilterChange = useCallback((e) => { setGlobalFilter(e.target.value.trim()); }, [setGlobalFilter]); return ( <div> <GlobalFilter filter={globalFilter} setFilter={handleFilterChange} /> {/* ... */} </div> ); }
为什么autoFocus不是解决方案
autoFocus只是在组件挂载时自动聚焦,但你的问题是组件一直在重复挂载——每次输入字符后,旧组件被销毁、新组件挂载并自动聚焦,这只是掩盖了根本问题,并没有解决组件重复渲染的核心矛盾。
内容的提问来源于stack exchange,提问作者José Fayard
相关产品推荐
相关产品推荐

