Browse Source

修复点位管理相关内容

pm 3 months ago
parent
commit
bca9e1ffa3

+ 52 - 24
src/components/SegregationPointForm.tsx

@@ -2,9 +2,9 @@ import React, { useState, useImperativeHandle, forwardRef, useEffect } from 'rea
 import { Modal, Form, Input, Select, Row, Col, message } from 'antd';
 import { segregationPointApi, SegregationPointVO } from '../api/spm/index';
 import { postApi, PostVO } from '../api/Post';
-import { lotoStationApi } from '../api/lotoStation/index';
+import { dictDataApi } from '../api/DictData';
 import { loginApi } from '../api/Login';
-import { getStrDictOptions, DICT_TYPE } from '../utils/dict';
+import { getStrDictOptions, getDictOptions, setDictOptions, DICT_TYPE } from '../utils/dict';
 import { toast } from 'sonner';
 import { useTranslation } from 'react-i18next';
 import UploadImg from './lockCabinet/UploadImg';
@@ -32,8 +32,8 @@ const SegregationPointForm = forwardRef<SegregationPointFormRef, SegregationPoin
 
     // 下拉选项数据
     const [postOptions, setPostOptions] = useState<Array<{ label: string; value: number }>>([]);
-    const [lotoOptions, setLotoOptions] = useState<Array<{ label: string; value: number }>>([]);
-    const powerTypeOptions = getStrDictOptions(DICT_TYPE.POWER_TYPE);
+    const [pointGroupOptions, setPointGroupOptions] = useState<Array<{ label: string; value: number }>>([]);
+    const [powerSourceOptions, setPowerSourceOptions] = useState<Array<{ label: string; value: string }>>([]);
 
     // 打开弹窗
     const open = async (type: string, id?: number) => {
@@ -128,19 +128,44 @@ const SegregationPointForm = forwardRef<SegregationPointFormRef, SegregationPoin
           }));
         setPostOptions(options);
 
-        // 获取锁定站数据
+        // 获取点位分组数据(从字典 point_group)
         try {
-          const lotoRes = await lotoStationApi.listLoto({ pageNo: 1, pageSize: -1 });
-          const data = (lotoRes as any)?.data || lotoRes;
-          const lotoList = data?.list || [];
-          setLotoOptions(lotoList.map((item: any) => ({
-            value: item.id!,
-            label: item.lotoName,
+          const dictRes = await dictDataApi.getDictDataPage({ pageNo: 1, pageSize: -1, dictType: DICT_TYPE.POINT_GROUP });
+          const data = (dictRes as any)?.list ?? (dictRes as any)?.data?.list ?? (Array.isArray(dictRes) ? dictRes : []);
+          const list = Array.isArray(data) ? data : [];
+          setDictOptions(DICT_TYPE.POINT_GROUP, list.map((item: any) => ({
+            dictType: DICT_TYPE.POINT_GROUP,
+            label: item.label,
+            value: item.value,
+            colorType: item.colorType || '',
+            cssClass: item.cssClass || '',
+          })));
+          const options = getDictOptions(DICT_TYPE.POINT_GROUP).map((item) => ({
+            label: item.label,
+            value: Number(item.value),
+          }));
+          setPointGroupOptions(options);
+        } catch (dictError) {
+          console.error('获取点位分组字典失败:', dictError);
+          setPointGroupOptions([]);
+        }
+
+        // 获取能量源数据(从字典 power_source)
+        try {
+          const powerRes = await dictDataApi.getDictDataPage({ pageNo: 1, pageSize: -1, dictType: DICT_TYPE.POWER_SOURCE });
+          const powerData = (powerRes as any)?.list ?? (powerRes as any)?.data?.list ?? (Array.isArray(powerRes) ? powerRes : []);
+          const powerList = Array.isArray(powerData) ? powerData : [];
+          setDictOptions(DICT_TYPE.POWER_SOURCE, powerList.map((item: any) => ({
+            dictType: DICT_TYPE.POWER_SOURCE,
+            label: item.label,
+            value: item.value,
+            colorType: item.colorType || '',
+            cssClass: item.cssClass || '',
           })));
-        } catch (lotoError) {
-          console.error('获取锁定站数据失败:', lotoError);
-          // 锁定站是非必填的,如果接口不存在或失败,设置为空数组即可
-          setLotoOptions([]);
+          setPowerSourceOptions(getStrDictOptions(DICT_TYPE.POWER_SOURCE));
+        } catch (powerError) {
+          console.error('获取能量源字典失败:', powerError);
+          setPowerSourceOptions([]);
         }
       } catch (error) {
         console.error('加载选项数据失败:', error);
@@ -214,8 +239,8 @@ const SegregationPointForm = forwardRef<SegregationPointFormRef, SegregationPoin
               // pointNfc: 如果为空字符串或 undefined,设置为 null;否则使用填入的值
               pointNfc: values.pointNfc && values.pointNfc.trim() !== '' ? values.pointNfc : null as any,
               workstationId: values.workstationId,
-              lotoId: values.lotoId,
-              powerType: values.powerType,
+              lotoId: values.lotoId != null && values.lotoId !== '' ? Number(values.lotoId) : null,
+              powerType: values.powerType != null && values.powerType !== '' ? Number(values.powerType) : undefined,
               // pointSerialNumber: 如果为空字符串或 undefined,设置为 null;否则使用填入的值
               pointSerialNumber: values.pointSerialNumber && values.pointSerialNumber.trim() !== '' ? values.pointSerialNumber : null as any,
               remark: values.remark,
@@ -246,10 +271,13 @@ const SegregationPointForm = forwardRef<SegregationPointFormRef, SegregationPoin
                 ? (values.pointNfc && values.pointNfc.trim() !== '' ? values.pointNfc : null)
                 : detailData.pointNfc,
               workstationId: values.workstationId !== undefined ? values.workstationId : detailData.workstationId,
-              // lotoId 处理:如果表单中有值(包括 null),使用表单值;否则使用详情数据中的原值(可能是 null)
-              // 注意:表单 Select 清空时返回 undefined,此时应该保留详情数据中的 null
-              lotoId: values.lotoId !== undefined ? values.lotoId : detailData.lotoId,
-              powerType: values.powerType !== undefined ? values.powerType : detailData.powerType,
+              // lotoId 处理:接口要求数字类型;表单中有值时转为 Number,清空时为 null
+              lotoId: values.lotoId !== undefined
+                ? (values.lotoId != null && values.lotoId !== '' ? Number(values.lotoId) : null)
+                : detailData.lotoId,
+              powerType: values.powerType !== undefined
+                ? (values.powerType != null && values.powerType !== '' ? Number(values.powerType) : undefined)
+                : detailData.powerType,
               // pointSerialNumber: 如果表单中有值且不为空字符串,使用表单值;如果为空字符串,设置为 null;如果为 undefined,使用详情数据中的原值(可能是 null)
               pointSerialNumber: values.pointSerialNumber !== undefined 
                 ? (values.pointSerialNumber && values.pointSerialNumber.trim() !== '' ? values.pointSerialNumber : null)
@@ -325,10 +353,10 @@ const SegregationPointForm = forwardRef<SegregationPointFormRef, SegregationPoin
           <Row gutter={16}>
             <Col span={12}>
               <Form.Item
-                label={t('form.lotoStation')}
+                label={t('form.pointGroup')}
                 name="lotoId"
               >
-                <Select placeholder={t('form.lotoStationPlaceholder')} options={lotoOptions} />
+                <Select placeholder={t('form.pointGroupPlaceholder')} options={pointGroupOptions} allowClear />
               </Form.Item>
             </Col>
             <Col span={12}>
@@ -353,7 +381,7 @@ const SegregationPointForm = forwardRef<SegregationPointFormRef, SegregationPoin
                 label={t('form.energySource')}
                 name="powerType"
               >
-                <Select placeholder={t('form.energySourcePlaceholder')} options={powerTypeOptions} />
+                <Select placeholder={t('form.energySourcePlaceholder')} options={powerSourceOptions} allowClear />
               </Form.Item>
             </Col>
             <Col span={12}>

+ 22 - 9
src/components/SegregationPointManagement.tsx

@@ -3,12 +3,13 @@ import { Plus, Search, RefreshCw, Edit2, Trash2 } from 'lucide-react';
 import { segregationPointApi, SegregationPointVO, PageParam } from '../api/spm/index';
 import { lotoStationApi, LotoStationVO } from '../api/lotoStation/index';
 import { technologyApi, TechnologyVO } from '../api/technology/index';
+import { dictDataApi } from '../api/DictData';
 import { toast } from 'sonner';
 import { Modal, Table, Input, Button, Select, TreeSelect, Space, Image, Switch } from 'antd';
 import { ExclamationCircleOutlined } from '@ant-design/icons';
 import type { ColumnsType } from 'antd/es/table';
 import { handleTree } from '../utils/tree';
-import { getStrDictOptions, DICT_TYPE } from '../utils/dict';
+import { getStrDictOptions, setDictOptions, DICT_TYPE } from '../utils/dict';
 import SegregationPointForm, { SegregationPointFormRef } from './SegregationPointForm';
 import { Button as UIButton } from './ui/button';
 import PermissionWrapper from './PermissionWrapper';
@@ -40,7 +41,7 @@ export default function SegregationPointManagement({ subMenu }: SegregationPoint
   const [deptOptions, setDeptOptions] = useState<any[]>([]);
   const [machineryOptions, setMachineryOptions] = useState<any[]>([]);
   const [lotoOptions, setLotoOptions] = useState<Array<{ label: string; value: number }>>([]);
-  const powerTypeOptions = getStrDictOptions(DICT_TYPE.POWER_TYPE);
+  const [powerTypeOptions, setPowerTypeOptions] = useState<Array<{ label: string; value: string }>>([]);
 
   const formRef = useRef<SegregationPointFormRef>(null);
 
@@ -111,6 +112,24 @@ export default function SegregationPointManagement({ subMenu }: SegregationPoint
         const techData = techRes.list.filter(item => item.machineryType === '工艺');
         const techTreeData = handleTree(techData, 'id', 'parentId');
         setMachineryOptions(convertToTreeSelectData(techTreeData, 'machineryName'));
+
+        // 获取能量源数据(从字典 power_source)
+        try {
+          const powerRes = await dictDataApi.getDictDataPage({ pageNo: 1, pageSize: -1, dictType: DICT_TYPE.POWER_SOURCE });
+          const powerData = (powerRes as any)?.list ?? (powerRes as any)?.data?.list ?? (Array.isArray(powerRes) ? powerRes : []);
+          const powerList = Array.isArray(powerData) ? powerData : [];
+          setDictOptions(DICT_TYPE.POWER_SOURCE, powerList.map((item: any) => ({
+            dictType: DICT_TYPE.POWER_SOURCE,
+            label: item.label,
+            value: item.value,
+            colorType: item.colorType || '',
+            cssClass: item.cssClass || '',
+          })));
+          setPowerTypeOptions(getStrDictOptions(DICT_TYPE.POWER_SOURCE));
+        } catch (powerError) {
+          console.error('获取能量源字典失败:', powerError);
+          setPowerTypeOptions([]);
+        }
       } catch (error) {
         console.error('初始化数据失败:', error);
       }
@@ -250,13 +269,7 @@ export default function SegregationPointManagement({ subMenu }: SegregationPoint
       align: 'center',
     },
     {
-      title: t('table.deviceProcess'),
-      dataIndex: 'machineryName',
-      width: 180,
-      align: 'center',
-    },
-    {
-      title: t('table.lotoStation'),
+      title: t('form.pointGroup'),
       dataIndex: 'lotoName',
       width: 120,
       align: 'center',

+ 2 - 0
src/locales/en.json

@@ -722,6 +722,8 @@
     "deviceProcessPlaceholder": "Select equipment/process",
     "lotoStation": "Lockout Station",
     "lotoStationPlaceholder": "Please select lockout station",
+    "pointGroup": "Point Group",
+    "pointGroupPlaceholder": "Please select point group",
     "energySource": "Energy Source",
     "energySourcePlaceholder": "Please select energy source",
     "templateName": "Template Name",

+ 2 - 0
src/locales/zh.json

@@ -724,6 +724,8 @@
     "deviceProcessPlaceholder": "选择设备/工艺",
     "lotoStation": "锁定站",
     "lotoStationPlaceholder": "请选择锁定站",
+    "pointGroup": "点位分组",
+    "pointGroupPlaceholder": "请选择点位分组",
     "energySource": "能量源",
     "energySourcePlaceholder": "请选择能量源",
     "templateName": "模板名称",

+ 3 - 1
src/utils/dict.ts

@@ -234,7 +234,9 @@ export enum DICT_TYPE {
   ISOCCUPIED_STATUS = 'isoccupied_status', // 是否被占用
   
   // ========== ISCS 模块 ==========
-  POWER_TYPE = 'power_type', // 能量源
+  POWER_TYPE = 'power_type', // 能量源(旧)
+  POWER_SOURCE = 'power_source', // 能量源
   KEY_STATUS = 'key_status', // 钥匙状态
+  POINT_GROUP = 'point_group', // 点位分组
 }