import { Form, Input, Popconfirm, Typography, Table } from "antd" import { useState } from "react"; const EditableCell = ({ editing, record, dataIndex, input, isRequired, title, formItemClass, formItemRules, children, }) => { const inputNode = input ?? const rules = formItemRules ?? [{ required: isRequired, message: `Please Input ${title}!`, }] const editor = {inputNode} return ( {editing ? editor: children} ) } export const EditableTable = ({columns, dataSource, onUpdateData: onChange, ...otherTableProps}) => { const [form] = Form.useForm() const [editingKey, setEditingKey] = useState('') const isEditing = (record) => record.key === editingKey const edit = (record) => { form.setFieldsValue({...record}) setEditingKey(record.key) } const cancel = () => { setEditingKey('') } const save = async (key) => { try { const row = await form.validateFields() const newData = [...dataSource] const index = newData.findIndex((item) => key === item.key) if (index > -1) { const item = newData[index] newData.splice(index, 1, { ...item, ...row }) } else { newData.push(row) } setEditingKey('') if(onChange) onChange(newData) else console.error(`EditableTable.onChange doesn't connected`) } catch (errInfo) { console.log('Validate Failed:', errInfo) } } const operationColumn = { title: '', dataIndex: 'operation', render: (_, record) => { const editable = isEditing(record) return editable ? ( save(record.key)} style={{ marginRight: 8, }} > Save Cancel ) : ( edit(record)}> Edit ) }, } const handleColumn = (col) => { if (col.children) col.children = col.children.map(handleColumn) if (!col.editable) return col return { ...col, onCell: (record) => ({ editing: isEditing(record), record, dataIndex: col.dataIndex ?? col.key, input: col.input, isRequired: col.isRequired, title: col.title, dataType: col.dataType, formItemClass: col.formItemClass, formItemRules: col.formItemRules, }), } } const mergedColumns = [...columns.map(handleColumn), operationColumn] return (
) }