在添加 Material Table 的新行时编辑自定义列组件

Edit custom column component while adding new row of Material Table

使用 React Material Table 库,是否可以在添加新行时呈现自定义组件?对于“预期结果”列,我是 using a custom component(实际上是 Material UI select 框)。当我添加一个新行时,我只看到 Requirement 列的字段,而不是 Expected Result 列。是否也可以为新行的预期结果列添加输入?

另一种选择是完全不使用自定义组件,而是使用类似于 https://material-table.com/#/docs/features/editable 的 Cell Editable Example 之类的东西。但是,与直接使用 Select 字段相比,我不喜欢编辑预期结果所需的额外点击。

import MaterialTable from 'material-table'
import { MenuItem, Select } from '@material-ui/core'
import React, { useState } from 'react'
import update from 'immutability-helper'

type PassFailNA = 'Pass' | 'Fail' | 'N/A'

type RowData = {
    requirementId: number,
    requirementName: string,
    expectedResult: PassFailNA,
    expectedResultId?: number
}

export function ExpectedResultsTable(props: {
    scenarioId: number
}) {
    const [tableData, setTableData] = useState<RowData[]>([{ requirementId: 1, requirementName: 'hello', expectedResult: 'Pass' }])
    const { enqueueSnackbar } = useSnackbar()

    const handleSelect = (id: number) => (event: React.ChangeEvent<{ name?: string; value: any }>) => {
        setTableData((tableData: RowData[]) => {
            const rowNum = tableData.findIndex(x => x.requirementId === id)
            return update<RowData[]>(tableData, {
                [rowNum]: { expectedResult: { $set: event.target.value } }
            })
        })
    }

    return (
        <MaterialTable<RowData>
            title=""
            columns={[
                {
                    title: 'Requirement',
                    field: 'requirementName'
                },
                {
                    title: 'Expected Result',
                    field: 'expectedResult',
                    render: (rowData) => (
                        <Select value={rowData.expectedResult} onChange={handleSelect(rowData.requirementId)}>
                            <MenuItem value="Pass">Pass</MenuItem>
                            <MenuItem value="Fail">Fail</MenuItem>
                            <MenuItem value="N/A">N/A</MenuItem>
                        </Select>
                    )
                }
            ]}
            data={tableData}
            editable={{
                onRowAdd: newRow =>
                    new Promise((resolve, reject) => {
                        setTimeout(() => {
                            setTableData(tableData => update(tableData, { $push: [{ ...newRow, expectedResult: 'N/A'}] }))
                            resolve()
                        }, 1000)
                    })
            }}
        />
    )
}

为了达到您的要求,我认为您应该在定义列时指定 editComponent 属性(除 render 之外)。该道具具有一个功能,您可以在其中定义在编辑或创建阶段使用的组件。

这是我用布尔输入做的一个例子:

  const tableColumns = [
    { title: "Client", field: "id" },
    { title: "Name", field: "name" },

    {
      title: "booleanValue",
      field: "booleanValue",
      editComponent: (props) => {
        console.log(props);
        return (
          <input
            type="checkbox"
            checked={props.value}
            onChange={(e) => props.onChange(e.target.checked)}
          />
        );
      },
      render: (rowdata) => (
        <input type="checkbox" checked={rowdata.booleanValue} />
      )
    }
  ];

Link 开始工作 sandbox。希望对你有用!