在 cellRender 中使用复选框时如何更改 MUI 数据网格的状态?
How do I change state of MUI Data Grid when using a checkbox in cellRender?
所以我有一个相当简单的场景,我正在处理我需要 MUI 数据网格中的复选框,但不使用 checkboxSelection。我很容易在一列中呈现我的复选框,但是一旦我选中该框,我就无法真正弄清楚如何更改该网格行的状态。该函数接收事件对象,您可以访问目标元素,但我试图实际更改行上已确认 属性 的值。
这是该组件的示例代码。
import React, { useState, useEffect } from 'react'
import { Checkbox } from '@mui/material';
import { DataGrid } from '@mui/x-data-grid'
const DataTable = () => {
const [tableData, setTableData] = useState([])
function handleConfirmChange() {
console.log('How do I change row state here????');
}
const columns = [
{ field: 'title', headerName: 'Title', width: 200 },
{ field: 'body', headerName: 'Body', width: 600 },
{
field: 'confirmed',
headerName: 'Confirmed',
renderCell: (params) => (
<Checkbox
checked={params.confirmed===1}
onChange={handleConfirmChange}
/>
),
}
]
useEffect(() => {
fetch("https://jsonplaceholder.typicode.com/posts")
.then((data) => data.json())
.then((data) => {
for (var i=0; i<data.length; i++) {
data[i].confirmed = false;
}
setTableData(data);
})
}, [])
return (
<div style={{ height: 700, width: '100%' }}>
<DataGrid
rows={tableData}
columns={columns}
pageSize={12}
/>
</div>
)
}
export default DataTable
在 checked={params.confirmed===1}
语句中,params
属性 中的 confirmed
不是 tableData
中的 属性。它是列的字段名称。
要获取点击的行,我们必须为每一行设置Id,将rowId
作为checkbox
的参数传递,然后我们可以识别点击的行。
因此,在 useEffect
钩子中,我们必须根据索引设置 rowId
。
useEffect(() => {
fetch("https://jsonplaceholder.typicode.com/posts")
.then((data) => data.json())
.then((data) => {
setTableData(
data.map((x, index) => ({
...x,
rowId: index,
confirmed: false
}))
);
});
}, []);
然后在复选框单击事件中将 row
作为参数传递。另外,将 checked
属性 设置为 params.rows?.confirmed
。 params.rows
给出了实际的行数据。这些行在初始化期间可能为空,因此我们必须将 Optional chaining (?.) 设置为 confirmed
属性.
<Checkbox
checked={params.rows?.confirmed}
onChange={() => handleConfirmChange(params.row)}
/>
在handleConfirmChange
函数中,获取点击的行并更新confirmed
属性。遍历 tableData
数组并获取点击的行,然后设置 confirmed
并更新网格。
function handleConfirmChange(clickedRow) {
const updatedData = tableData.map((x) => {
if (x.rowId === clickedRow.rowId) {
return {
...x,
confirmed: !clickedRow.confirmed
};
}
return x;
});
setTableData(updatedData);
}
这是更新后的工作代码和codesandbox。
import React, { useState, useEffect } from "react";
import { Checkbox } from "@mui/material";
import { DataGrid } from "@mui/x-data-grid";
export default function DataTable() {
const [tableData, setTableData] = useState([]);
function handleConfirmChange(clickedRow) {
const updatedData = tableData.map((x) => {
if (x.rowId === clickedRow) {
return {
...x,
confirmed: true
};
}
return x;
});
setTableData(updatedData);
}
const columns = [
{ field: "title", headerName: "Title", width: 200 },
{ field: "body", headerName: "Body", width: 400 },
{
field: "confirmed",
headerName: "Confirmed",
renderCell: (params) => (
<Checkbox
checked={params.rows?.confirmed}
onChange={() => handleConfirmChange(params.row.rowId)}
/>
)
}
];
useEffect(() => {
fetch("https://jsonplaceholder.typicode.com/posts")
.then((data) => data.json())
.then((data) => {
setTableData(
data.map((x, index) => ({
...x,
rowId: index,
confirmed: false
}))
);
});
}, []);
return (
<div style={{ height: 400, width: "100%" }}>
<DataGrid
rows={tableData}
columns={columns}
pageSize={12}
rowsPerPageOptions={[12]}
/>
</div>
);
}
所以我有一个相当简单的场景,我正在处理我需要 MUI 数据网格中的复选框,但不使用 checkboxSelection。我很容易在一列中呈现我的复选框,但是一旦我选中该框,我就无法真正弄清楚如何更改该网格行的状态。该函数接收事件对象,您可以访问目标元素,但我试图实际更改行上已确认 属性 的值。
这是该组件的示例代码。
import React, { useState, useEffect } from 'react'
import { Checkbox } from '@mui/material';
import { DataGrid } from '@mui/x-data-grid'
const DataTable = () => {
const [tableData, setTableData] = useState([])
function handleConfirmChange() {
console.log('How do I change row state here????');
}
const columns = [
{ field: 'title', headerName: 'Title', width: 200 },
{ field: 'body', headerName: 'Body', width: 600 },
{
field: 'confirmed',
headerName: 'Confirmed',
renderCell: (params) => (
<Checkbox
checked={params.confirmed===1}
onChange={handleConfirmChange}
/>
),
}
]
useEffect(() => {
fetch("https://jsonplaceholder.typicode.com/posts")
.then((data) => data.json())
.then((data) => {
for (var i=0; i<data.length; i++) {
data[i].confirmed = false;
}
setTableData(data);
})
}, [])
return (
<div style={{ height: 700, width: '100%' }}>
<DataGrid
rows={tableData}
columns={columns}
pageSize={12}
/>
</div>
)
}
export default DataTable
在 checked={params.confirmed===1}
语句中,params
属性 中的 confirmed
不是 tableData
中的 属性。它是列的字段名称。
要获取点击的行,我们必须为每一行设置Id,将rowId
作为checkbox
的参数传递,然后我们可以识别点击的行。
因此,在 useEffect
钩子中,我们必须根据索引设置 rowId
。
useEffect(() => {
fetch("https://jsonplaceholder.typicode.com/posts")
.then((data) => data.json())
.then((data) => {
setTableData(
data.map((x, index) => ({
...x,
rowId: index,
confirmed: false
}))
);
});
}, []);
然后在复选框单击事件中将 row
作为参数传递。另外,将 checked
属性 设置为 params.rows?.confirmed
。 params.rows
给出了实际的行数据。这些行在初始化期间可能为空,因此我们必须将 Optional chaining (?.) 设置为 confirmed
属性.
<Checkbox
checked={params.rows?.confirmed}
onChange={() => handleConfirmChange(params.row)}
/>
在handleConfirmChange
函数中,获取点击的行并更新confirmed
属性。遍历 tableData
数组并获取点击的行,然后设置 confirmed
并更新网格。
function handleConfirmChange(clickedRow) {
const updatedData = tableData.map((x) => {
if (x.rowId === clickedRow.rowId) {
return {
...x,
confirmed: !clickedRow.confirmed
};
}
return x;
});
setTableData(updatedData);
}
这是更新后的工作代码和codesandbox。
import React, { useState, useEffect } from "react";
import { Checkbox } from "@mui/material";
import { DataGrid } from "@mui/x-data-grid";
export default function DataTable() {
const [tableData, setTableData] = useState([]);
function handleConfirmChange(clickedRow) {
const updatedData = tableData.map((x) => {
if (x.rowId === clickedRow) {
return {
...x,
confirmed: true
};
}
return x;
});
setTableData(updatedData);
}
const columns = [
{ field: "title", headerName: "Title", width: 200 },
{ field: "body", headerName: "Body", width: 400 },
{
field: "confirmed",
headerName: "Confirmed",
renderCell: (params) => (
<Checkbox
checked={params.rows?.confirmed}
onChange={() => handleConfirmChange(params.row.rowId)}
/>
)
}
];
useEffect(() => {
fetch("https://jsonplaceholder.typicode.com/posts")
.then((data) => data.json())
.then((data) => {
setTableData(
data.map((x, index) => ({
...x,
rowId: index,
confirmed: false
}))
);
});
}, []);
return (
<div style={{ height: 400, width: "100%" }}>
<DataGrid
rows={tableData}
columns={columns}
pageSize={12}
rowsPerPageOptions={[12]}
/>
</div>
);
}