Ant-Design-Pro-Components: EditableProTable、ProTable组件数据联动。

时间:2025-04-08 14:09:43
import React, { useRef, useState, Fragment, useEffect } from 'react'; import { Modal, Button, Table, Form, Collapse, Spin, message, Tooltip } from 'antd'; import { EditableProTable, ProForm, ProTable } from '@ant-design/pro-components'; import { CaretRightOutlined, ExportOutlined } from '@ant-design/icons'; import BasicInfo from '../basicInfo'; import { getCourseListByClassCode, getTeacherInfoByStaffCode, updateClassSchedule, courseTeacherExportExcel, } from '@/services/train/train'; const { Panel } = Collapse; export default function Teacher({ current, setCurrent, handleModalVisible, currentRow, yesOrNo, orgList, idtypeArray, sexArray, teacherTypeArray, yesOrNoObj, }) { const [form] = Form.useForm(); // 创建表单 const [saveLoading, setSaveLoading] = useState(false); // 保存讲师按钮 const [teacherListVisible, handleTeacherListVisible] = useState(false); // 讲师姓名列表 的弹窗 const [teacherList, setTeacherList] = useState([]); // 讲师列表 const [curConfigAndForm, setCurConfigAndForm] = useState({}); // 讲师姓名失去焦点时当前行信息 const [curTeacherInfo, setTeacherInfo] = useState({}); // 讲师弹窗列表点击确定时讲师个人信息 const [spinLoading, setSpinLoading] = useState(false); // loading const [courseData, setCourseData] = useState([]); // 课表讲师列表数据 const [editableKeys, setEditableRowKeys] = useState([]); // 课程讲师信息列表编辑 const [downloadParams, setDownloadParams] = useState(''); //导出参数 useEffect(() => { setSpinLoading(true); if (currentRow && currentRow.classCode) { setDownloadParams(currentRow.classCode); getCourseList(currentRow.classCode); } else { setSpinLoading(false); } }, []); const getCourseList = (classCode) => { getCourseListByClassCode(classCode).then((res) => { if (res && res.success && res.data) { const { data } = res; form.setFieldsValue({ teacherDetails: data, }); setSpinLoading(false); } }); setSpinLoading(false); }; // 导出讲师信息 const genExtra = () => ( <Tooltip placement="topLeft" title="点击导出讲师课表信息"> <Button type="default" key="export" loading={spinLoading} onClick={() => { courseTeacherExportExcel({ downloadParams, setSpinLoading, yesOrNoObj, }); }} > <ExportOutlined /> 导出数据 </Button> </Tooltip> ); // 保存课表讲师信息 const handleSubmit = (value) => { const { teacherDetails } = value; setSaveLoading(true); let flag = teacherDetails.every((item, index) => { if (!item.staffCode) { message.error(`${index + 1}行, 讲师编码或者讲师姓名不能为空!`); return false; } return item.staffCode != null || item.staffCode != ''; }); if (flag) { updateClassSchedule(teacherDetails).then((res) => { if (res && res.success && res?.data?.code == '200') { setSaveLoading(false); message.success('保存讲师信息成功!'); } else { message.error(res?.data?.message); } setSaveLoading(false); }); } else { setSaveLoading(false); } }; // 讲师列表点击选择讲师信息 const rowSelectOnChange = (selectedRowKeys, selectedRows) => { if (selectedRows && selectedRows.length > 0) { console.log('selectedRows', selectedRows); console.log('curConfigAndForm', curConfigAndForm); setTeacherInfo(selectedRows[0]); } }; //确定使用该讲师 const confirmCurTeacher = () => { // 联动数据赋值助教姓名 curConfigAndForm.form.setFieldValue( ['teacherDetails', curConfigAndForm.config.rowIndex, 'staffCode'], curTeacherInfo.staffCode, ); handleTeacherListVisible(false); }; // 课程列表 const columns2 = [ { title: '课程名称', dataIndex: 'courseName', editable: false, }, { title: '授课日期', dataIndex: 'lectureDate', valueType: 'date', editable: false, }, { title: '课时', dataIndex: 'courseHours', editable: false, }, { title: '开始时间', dataIndex: 'beginTime', editable: false, }, { title: '结束时间', dataIndex: 'endTime', editable: false, }, { title: '是否计入讲师课时', dataIndex: 'isTakeIntoHours', editable: false, valueType: 'select', fieldProps: { options: yesOrNo, fieldNames: { // 树属性重命名 label: 'codeName', value: 'code', }, }, }, { title: '是否支付课时津贴', dataIndex: 'isPayAllowance', editable: false, valueType: 'select', fieldProps: { options: yesOrNo, fieldNames: { // 树属性重命名 label: 'codeName', value: 'code', }, }, }, { title: '讲师编码', dataIndex: 'staffCode', formItemProps: { rules: [ { required: true, message: '此项为必填项', }, ], }, fieldProps: (form, config) => ({ onBlur: (changeValue) => { // 可以直接拿到当前行数据 const staffCode = form.getFieldValue(['teacherDetails', config.rowIndex, 'staffCode']); if (staffCode) { getTeacherInfoByStaffCode({ staffCode: staffCode }).then((res) => { if (res && res.success && res?.data?.code == '200') { // 联动数据赋值姓名 form.setFieldValue( ['teacherDetails', config.rowIndex, 'teacherName'], res?.data?.data[0].name, ); } }); } else { form.setFieldValue(['teacherDetails', config.rowIndex, 'teacherName'], ''); } }, }), }, { title: '讲师姓名', dataIndex: 'teacherName', formItemProps: { rules: [ { required: false, message: '此项为必填项', }, ], }, fieldProps: (form, config) => ({ onBlur: (changeValue) => { // 可以直接拿到当前行数据 const teacherName = form.getFieldValue([ 'teacherDetails', config.rowIndex, 'teacherName', ]); if (teacherName) { getTeacherInfoByStaffCode({ name: teacherName }).then((res) => { if (res && res.success && res?.data?.code == '200') { if (res?.data?.data.length > 0) { res?.data?.data.map((item, index) => { item.listKey = index + 1; }); } setCurConfigAndForm({ form, config, }); setTeacherList(res?.data?.data); // 联动数据赋值助教姓名 // ( // ['teacherDetails', , 'staffCode'], // res?.data?.data?.name, // ); } }); handleTeacherListVisible(true); } else { form.setFieldValue(['teacherDetails', config.rowIndex, 'staffCode'], ''); } }, }), }, { title: '操作', key: 'action', valueType: 'option', render: (_, record, index, action) => { return [ <a key="editable" onClick={() => { action?.startEditable(record.seriesNo); }} > 编辑 </a>, ]; }, }, ]; // 讲师列表 const columns3 = [ { title: '管理机构', dataIndex: 'manageCom', width: 180, valueType: 'select', fieldProps: { options: orgList, fieldNames: { label: 'name', value: 'comCode', }, }, }, { title: '营销员编码(工号)', dataIndex: 'staffCode', width: 150, }, { title: '姓名', dataIndex: 'name', width: 180, }, { title: '性别', dataIndex: 'sex', width: 150, valueType: 'select', fieldProps: { options: sexArray, fieldNames: { // 树属性重命名 label: 'codeName', value: 'code', }, }, }, { title: '证件类型', dataIndex: 'idNoType', width: 150, valueType: 'select', fieldProps: { options: idtypeArray, fieldNames: { // 树属性重命名 label: 'codeName', value: 'code', }, }, }, { title: '证件号码', dataIndex: 'idNo', width: 180, }, { title: '讲师类型', dataIndex: 'teacherType', width: 150, valueType: 'select', fieldProps: { options: teacherTypeArray, fieldNames: { // 树属性重命名 label: 'codeName', value: 'code', }, }, }, ]; return ( <Spin spinning={spinLoading}> <BasicInfo basicInfo={currentRow} /> <Collapse defaultActiveKey={['12']} bordered={false} ghost collapsible="header" expandIcon={({ isActive }) => <CaretRightOutlined rotate={isActive ? 90 : 0} />} > <Panel header="课程讲师信息" key="12" style={{ fontWeight: 700, width: '90%' }} extra={genExtra()} > <ProForm // layout="horizontal" form={form} style={{ fontWeight: 500 }} submitter={{ // 完全自定义整个区域 render: (props, doms) => { return [ <Button type="primary" key="save" loading={saveLoading} onClick={() => { // ?.resetFields(); props.form?.submit?.(); }} > 保存讲师信息 </Button>, ]; }, }} // initialValues={{ teacherDetails: tableData }} onFinish={handleSubmit} > <ProForm.Item> <EditableProTable name="teacherDetails" columns={columns2} recordCreatorProps={{ style: { display: 'none', }, // 隐藏添加一行 }} rowKey="seriesNo" editable={{ type: 'single', actionRender: (row, config, defaultDom) => [defaultDom?.save], editableKeys, onChange: setEditableRowKeys, }} /> {/* <EditableProTable recordCreatorProps={{ record: () => { return { key: `0${()}`, }; }, }} columns={columns2} rowKey="seriesNo" /> */} </ProForm.Item> </ProForm> </Panel> </Collapse> <div style={{ position: 'fixed', bottom: '30px' }}> <Button type="primary" key="back2" onClick={() => { // handleModalVisible(false); setCurrent(current - 1); }} style={{ marginRight: 10 }} > 上一步 </Button> <Button type="primary" key="next2" onClick={() => { setCurrent(current + 1); }} > 下一步 </Button> </div> {teacherListVisible ? ( <Modal title="讲师列表" visible={teacherListVisible} destroyOnClose width="60%" onCancel={() => handleTeacherListVisible(false)} footer={[ <Button key="confirm" type="primary" onClick={() => confirmCurTeacher()}> 确定使用该讲师 </Button>, <Button key="close" onClick={() => handleTeacherListVisible(false)}> 关闭 </Button>, ]} maskClosable={false} > <ProTable style={{ marginLeft: '-20px' }} headerTitle="" rowKey="listKey" options={false} search={false} pagination={false} dataSource={teacherList} revalidateOnFocus={false} columns={columns3} rowSelection={{ selections: [Table.SELECTION_ALL, Table.SELECTION_INVERT], defaultSelectedRowKeys: [], type: 'radio', onChange: rowSelectOnChange, }} tableAlertOptionRender={false} tableAlertRender={false} /> </Modal> ) : null} </Spin> ); }