MUI X Data Grid Pro TreeData模式如何保存编辑后的单元格值
实现方案
树形模式下的MUI X Data Grid Pro 行数据本质还是平铺存储的数组,每一行(不管父/子节点)都有唯一id,编辑值保存逻辑和普通单层表格完全一致,不需要针对树形结构做特殊处理。你当前代码不生效是两个基础写法错误:
- 传给组件的
rows属性是写死的静态常量,没有绑定你自己维护的响应式状态,状态更新后无法触发表格重渲染 - 初始状态错误引用了MUI内部未公开的
applyInitialState工具方法,这个方法是框架内部处理列状态用的,和行数据存储无关
具体修改点
- 移除无用的
applyInitialState导入,直接用初始树形行数据作为useState的默认值 - 将组件接收的
rows属性替换为你自己维护的响应式行状态,不要传静态常量 - 推荐使用新编辑API配套的
processRowUpdate回调处理值更新,比onCellEditCommit兼容性更好,支持单元格/行编辑双场景,更新逻辑就是按id匹配到对应行,覆盖修改的字段即可,子节点和父节点的更新逻辑完全一致 - 如果需要把编辑后的值同步到后端,直接在更新回调里加接口请求逻辑即可
修正后可运行代码
import * as React from "react"; import { DataGridPro, GridColumns, GridRowsProp, DataGridProProps, GridRowModel } from "@mui/x-data-grid-pro"; import { GridCellEditStopParams, GridCellEditStopReasons, MuiEvent, } from "@mui/x-data-grid"; // 初始树形行数据,和普通表格行结构一致,仅多了hierarchy路径字段用来生成层级 const initialRows: GridRowsProp = [ { hierarchy: ["Documents"], rubrics: "Head of Human Resources", totalMarks: "", id: 0, }, { hierarchy: ["Scope"], rubrics: "Head of Sales", totalMarks: "15", id: 1, }, { hierarchy: ["Scope", "Rubric item 1"], rubrics: "Sales Person", totalMarks: "2", id: 2, }, { hierarchy: ["Scope", "Rubric item 2"], rubrics: "Sales Person", totalMarks: "5", id: 3, }, { hierarchy: ["Scope", "Rubric item 3"], rubrics: "Sales Person", totalMarks: "8", id: 4, }, ]; const columns: GridColumns = [ { field: "rubrics", headerName: "Rubric Type", width: 200, editable: true }, { field: "totalMarks", headerName: "Total Marks", width: 150, editable: true, }, ]; const getTreeDataPath: DataGridProProps["getTreeDataPath"] = (row) => row.hierarchy; export default function TreeDataSimple() { // 直接用初始行数据初始化状态,不要用内部未公开方法 const [rows, setRows] = React.useState<GridRowModel[]>(initialRows); // 新编辑API推荐的行更新处理方法,父/子节点编辑都会触发 const processRowUpdate = (newRow: GridRowModel) => { setRows(prev => prev.map(row => row.id === newRow.id ? newRow : row)); // 此处可加后端保存逻辑,比如调用接口提交newRow return newRow; }; return ( <div style={{ height: 400, width: "100%" }}> <DataGridPro treeData rows={rows} // 绑定响应式行数据,不要传静态常量 columns={columns} getTreeDataPath={getTreeDataPath} processRowUpdate={processRowUpdate} experimentalFeatures={{ newEditingApi: true }} onCellEditStop={(params: GridCellEditStopParams, event: MuiEvent) => { if (params.reason === GridCellEditStopReasons.cellFocusOut) { event.defaultMuiPrevented = true; } }} /> </div> ); }
补充说明:如果需要实现父节点值自动汇总子节点值的逻辑,只需要在
processRowUpdate里更新完当前行后,根据hierarchy路径找到对应父节点,重新计算父节点字段值同步更新即可,底层还是操作平铺的行数组,没有特殊API要求。
内容的提问来源于stack exchange,提问作者KawaiiPotato57
相关产品推荐
相关产品推荐

