safety-eval-service-frontend/src/pages/Container/QualApplication/FilingForm/components/PersonnelStep.jsx

134 lines
4.5 KiB
React
Raw Normal View History

2026-06-30 17:32:29 +08:00
import { Button, Modal, Space, Table } from "antd";
2026-08-05 09:11:32 +08:00
import { useMemo, useState } from "react";
import { CAPABILITY_MAP, GENDER_MAP } from "~/enumerate/constant";
2026-07-09 09:23:22 +08:00
import StaffViewModal from "~/components/StaffViewModal";
2026-06-30 17:32:29 +08:00
import OrgPersonnelSelectModal from "./OrgPersonnelSelectModal";
2026-08-05 09:11:32 +08:00
function calcAge(birthDate) {
if (!birthDate) return "-";
const birth = new Date(birthDate);
if (isNaN(birth.getTime())) return "-";
const now = new Date();
let age = now.getFullYear() - birth.getFullYear();
const m = now.getMonth() - birth.getMonth();
if (m < 0 || (m === 0 && now.getDate() < birth.getDate())) age--;
return age >= 0 ? age : "-";
}
2026-07-10 14:38:17 +08:00
const PersonnelStep=({
2026-06-30 17:32:29 +08:00
personnelList = [],
disabled,
onAdd,
onRemove,
2026-07-10 14:38:17 +08:00
})=> {
2026-06-30 17:32:29 +08:00
const [selectOpen, setSelectOpen] = useState(false);
const [viewId, setViewId] = useState("");
2026-07-15 16:13:07 +08:00
const [selectedRowKeys, setSelectedRowKeys] = useState([]);
2026-06-30 17:32:29 +08:00
2026-08-05 09:11:32 +08:00
const tableData = useMemo(
() => personnelList.map((item) => ({ ...item, age: item.age ?? calcAge(item.birthDate) })),
[personnelList],
);
2026-07-07 18:07:59 +08:00
const existingIds = personnelList.map((item) => String(item.sourcePersonnelId || item.id || ""));
2026-06-30 17:32:29 +08:00
2026-07-15 16:13:07 +08:00
const handleBatchRemove = () => {
const records = selectedRowKeys
.map((key) => personnelList.find(
(item) => String(item.sourcePersonnelId || item.id) === key,
))
.filter(Boolean);
if (records.length > 0) {
onRemove?.(records);
}
};
2026-06-30 17:32:29 +08:00
return (
<>
<div style={{ display: "flex", justifyContent: "space-between", marginBottom: 12 }}>
<span style={{ fontWeight: 600 }}>
备案人员信息
<span style={{ marginLeft: 8, color: "rgba(0,0,0,0.45)", fontWeight: 400 }}>
当前 {personnelList.length}
</span>
</span>
{!disabled && (
2026-07-15 16:13:07 +08:00
<Space size="small">
<Button type="primary" size="small" onClick={() => setSelectOpen(true)}>添加人员信息</Button>
{selectedRowKeys.length > 0 && (
<Button danger size="small" onClick={handleBatchRemove}>批量删除</Button>
)}
</Space>
2026-06-30 17:32:29 +08:00
)}
</div>
<Table
size="small"
2026-07-15 16:13:07 +08:00
rowKey={(record) => String(record.sourcePersonnelId || record.id)}
2026-06-30 17:32:29 +08:00
pagination={false}
2026-08-05 09:11:32 +08:00
scroll={{ x: 1200, y: 400 }}
dataSource={tableData}
2026-07-15 16:13:07 +08:00
rowSelection={!disabled ? {
selectedRowKeys,
onChange: setSelectedRowKeys,
} : undefined}
2026-06-30 17:32:29 +08:00
columns={[
{ title: "序号", width: 60, render: (_, __, index) => index + 1 },
2026-08-05 09:11:32 +08:00
{ title: "人员姓名", dataIndex: "personName" },
{ title: "部门", dataIndex: "deptName", ellipsis: true },
{ title: "岗位", dataIndex: "positionName", ellipsis: true },
{ title: "性别", dataIndex: "genderCode", width: 70, render: (v) => GENDER_MAP[v] || "-" },
{ title: "年龄", dataIndex: "age", width: 70 },
{ title: "注册安全工程师", dataIndex: "registerEngineerFlag", width: 120, render: (v) => v === 1 ? "是" : "否" },
{ title: "评价师", dataIndex: "evaluatorCertNo", width: 80, render: (v) => v ? "是" : "否" },
{
2026-08-08 16:44:49 +08:00
title: "专业能力",
2026-08-05 09:11:32 +08:00
render: (_, record) => {
const codes = record.professionalCapabilityCodeList || [];
return codes.length
? codes.map((code) => CAPABILITY_MAP[code] || code).join("、")
: "-";
},
},
2026-06-30 17:32:29 +08:00
{
title: "操作",
width: 140,
2026-08-05 09:11:32 +08:00
fixed: "right",
2026-06-30 17:32:29 +08:00
render: (_, record) => (
<Space size="small">
<Button
type="link"
size="small"
onClick={() => setViewId(record.sourcePersonnelId || record.id)}
>
查看
</Button>
{!disabled && (
<Button type="link" size="small" danger onClick={() => onRemove?.(record)}>删除</Button>
)}
</Space>
),
},
]}
/>
<OrgPersonnelSelectModal
open={selectOpen}
existingIds={existingIds}
onCancel={() => setSelectOpen(false)}
onConfirm={(ids, rows) => {
onAdd?.(ids, rows);
setSelectOpen(false);
}}
/>
<StaffViewModal
open={!!viewId}
currentId={viewId}
2026-07-02 16:58:07 +08:00
2026-06-30 17:32:29 +08:00
onCancel={() => setViewId("")}
/>
</>
);
}
2026-07-10 14:38:17 +08:00
export default PersonnelStep;