Ag-Grid下拉列修改值后自动恢复初始状态的问题求助
Ag-Grid下拉列修改值后自动恢复初始状态的问题求助
你好!我看了你的代码,问题的核心原因是Ag-Grid不会自动修改你通过useState维护的rowData状态。当你在下拉框里选择新值后,Ag-Grid虽然拿到了编辑器返回的新值,但没有同步到你的数据源rowData中,所以一旦失去焦点,表格会重新从原始的rowData读取旧值,导致看起来像是“恢复到初始状态”。
下面是具体的解决步骤和修改后的完整代码:
解决步骤
添加单元格值变更回调,同步更新
rowData
给AgGridReact组件加上onCellValueChanged事件处理函数,在编辑完成后手动更新对应的行数据,让你的rowData状态和表格的单元格值保持一致。完善自定义编辑器的状态同步(可选但推荐)
给自定义编辑器添加useEffect监听props.value的变化,确保编辑器初始化时能正确获取最新的单元格值,避免编辑器状态和单元格值不一致的情况。
修改后的完整代码
import React, { useState, useCallback, forwardRef, useImperativeHandle, useEffect } from 'react'; import { AgGridReact } from 'ag-grid-react'; import 'ag-grid-community/styles/ag-grid.css'; import 'ag-grid-community/styles/ag-theme-alpine.css'; import { ICellEditorComp } from 'ag-grid-community'; interface DropdownEditorProps { value: string; values: string[]; } const DropdownEditor = forwardRef<ICellEditorComp, DropdownEditorProps>( (props, ref) => { const [selectedValue, setSelectedValue] = useState(props.value); // 监听外部值变化,同步编辑器选中状态 useEffect(() => { setSelectedValue(props.value); }, [props.value]); useImperativeHandle(ref, () => { return { getValue() { return selectedValue; }, isPopup() { return true; }, // 可选:编辑器初始化后自动获取焦点,提升体验 afterGuiAttached() { const selectEl = document.querySelector('select'); selectEl?.focus(); } }; }); const handleChange = (event: React.ChangeEvent<HTMLSelectElement>) => { setSelectedValue(event.target.value); }; return ( <select value={selectedValue} onChange={handleChange} style={{ width: '100%' }} > {props.values.map((option) => ( <option key={option} value={option}> {option} </option> ))} </select> ); } ); const testapp: React.FC = () => { const [rowData, setRowData] = useState([ { Color: 'Green', make: 'Tesla', model: 'Model Y', price: 64950 }, { Color: 'Blue', make: 'Ford', model: 'F-Series', price: 33850 }, { Color: '', make: 'BMW', model: 'BMW Series', price: 5000 }, ]); const [colDefs] = useState([ { field: 'Color', editable: true, cellEditor: DropdownEditor, cellEditorParams: { values: ['Normal', 'Green', 'Red', 'Blue'], }, }, { field: 'make' }, { field: 'model' }, { field: 'price' }, ]); // 处理单元格值变更,同步到rowData状态 const handleCellValueChanged = useCallback((params: any) => { setRowData(prevRows => { return prevRows.map(row => { // 定位到被修改的行,更新对应字段 if (row === params.data) { return { ...row, [params.colDef.field]: params.newValue }; } return row; }); }); }, []); return ( <div className="ag-theme-alpine" style={{ width: 800, height: 400 }}> <AgGridReact rowData={rowData} columnDefs={colDefs} singleClickEdit={true} // 新增单元格值变更回调 onCellValueChanged={handleCellValueChanged} gridOptions={{ stopEditingWhenCellsLoseFocus: true, rowSelection: { mode: 'singleRow', checkboxes: false }, }} /> </div> ); }; export default testapp;
关键修改点说明
onCellValueChanged回调:这是解决问题的核心,它在编辑完成后将新值同步到你的rowData状态中,确保表格下次渲染时使用更新后的数据源。- 编辑器中的
useEffect:监听props.value的变化,避免当重新编辑同一行时,编辑器仍显示旧值的问题。 - 补充
afterGuiAttached方法:可选操作,让编辑器初始化后自动获取焦点,优化编辑的流畅度。
这样修改后,你修改下拉框的值并失去焦点后,表格就会保持你选择的新值,不会再自动恢复到初始状态了。
内容来源于stack exchange




