Просмотр исходного кода

feat (1.64.0 -> 1.65.0): 优化患者注册功能,支持从身份证自动提取出生日期并自动生成登记号显示在表单中

- 在qrCodeDataProcessor.ts中添加从身份证号提取出生日期的功能
- 在register.form.tsx中实现表单值自动同步到Redux store并自动生成登记号显示在表单中
- 在formSlice.ts中优化setFormData为对象合并更新逻辑

改动文件:
- src/domain/qrcode/qrCodeDataProcessor.ts
- src/pages/patient/components/register.form.tsx
- src/states/patient/register/formSlice.ts
dengdx 5 дней назад
Родитель
Сommit
813bb90482

+ 16 - 0
CHANGELOG.md

@@ -3,6 +3,22 @@
 本项目的所有重要变更都将记录在此文件中.
 
 
+## [1.65.0] - 2026-01-12 19:15
+
+### 新增 (Added)
+
+- **优化患者注册功能,支持从身份证自动提取出生日期并自动生成登记号显示在表单中** - 增强二维码扫描数据处理和表单管理
+  - 在qrCodeDataProcessor.ts中添加从身份证号提取出生日期的功能
+  - 在register.form.tsx中实现表单值自动同步到Redux store并自动生成登记号显示在表单中
+  - 在formSlice.ts中优化setFormData为对象合并更新逻辑
+
+**改动文件:**
+
+- src/domain/qrcode/qrCodeDataProcessor.ts
+- src/pages/patient/components/register.form.tsx
+- src/states/patient/register/formSlice.ts
+
+
 ## [1.64.0] - 2026-01-12 14:58
 
 ### 新增 (Added)

+ 3 - 1
config/dev.ts

@@ -83,6 +83,7 @@ export default {
         '/dr': {
           target: 'http://192.168.110.13', // 你的后端服务地址
           // target: 'http://192.168.110.133',
+          // target: 'http://192.168.110.239',
           changeOrigin: true, // 允许跨域
           // pathRewrite: {
           //   '^/dr/api': '' // 可选,用于重写路径
@@ -91,6 +92,7 @@ export default {
         '/mqtt': {
           target: 'ws://192.168.110.13:8083', // MQTT WebSocket 服务地址
           // target: 'ws://192.168.110.133:8083',
+          // target: 'ws://192.168.110.239:8083',
           changeOrigin: true,
           ws: true, // 启用 WebSocket 代理
           // pathRewrite: {
@@ -98,7 +100,7 @@ export default {
           // }
         },
       },
-      // server: 'https', // 启用 HTTPS ,为了开发环境测试打开摄像头功能
+      server: 'https', // 启用 HTTPS ,为了开发环境测试打开摄像头功能
       host: '0.0.0.0', // 监听所有网络接口
       open: false, // 可选:是否自动打开浏览器
       port: 10086, // 可选:指定端口号

+ 1 - 1
package.json

@@ -1,6 +1,6 @@
 {
   "name": "zsis",
-  "version": "1.64.0",
+  "version": "1.65.0",
   "private": true,
   "description": "医学成像系统",
   "main": "main.js",

+ 12 - 5
src/domain/qrcode/qrCodeDataProcessor.ts

@@ -17,15 +17,15 @@ const extractGenderFromIdNumber = (idNumber: string): 'M' | 'F' | undefined => {
   if (!idNumber || idNumber.length !== 18) {
     return undefined;
   }
-  
+
   // 获取第17位(索引16)- 性别标识位
   const genderDigit = parseInt(idNumber[16]);
-  
+
   // 验证是否为有效数字
   if (isNaN(genderDigit)) {
     return undefined;
   }
-  
+
   // 奇数为男性,偶数为女性
   return genderDigit % 2 === 1 ? 'M' : 'F';
 };
@@ -72,6 +72,13 @@ const parseTabSeparatedText = (text: string) => {
     const gender = extractGenderFromIdNumber(idNumber);
     const patient_sex = gender || 'O'; // 如果无法判断,使用 'O' (Other)
 
+
+    // 从身份证提取出生日期
+    const birthYear = parseInt(idNumber.substring(6, 10));
+    const birthMonth = parseInt(idNumber.substring(10, 12));
+    const birthDay = parseInt(idNumber.substring(12, 14));
+    const patient_dob = dayjs().year(birthYear).month(birthMonth - 1).date(birthDay);
+
     const result = {
       patient_name: name,
       patient_age: {
@@ -79,9 +86,9 @@ const parseTabSeparatedText = (text: string) => {
         unit: ageUnit
       },
       patient_id: idNumber,
-      patient_sex: patient_sex
+      patient_sex: patient_sex,
+      patient_dob: patient_dob.isValid() ? patient_dob.toISOString() : undefined
     };
-
     console.log('[QRCodeParse] 解析结果:', result);
     console.log('[QRCodeParse] 性别判断:', gender ? `从身份证号提取: ${gender}` : '无法判断性别,使用默认值 O');
     return result;

+ 23 - 0
src/pages/patient/components/register.form.tsx

@@ -40,9 +40,32 @@ const BasicInfoForm: React.FC<BasicInfoFormProps> = ({
   const productName = useSelector(
     (state: RootState) => state.product.productName
   );
+  const formData = useSelector((state: RootState) => state.form.formData);
   const dispatch = useDispatch();
   const [pregnancyStatusFieldVisible, setPregnancyStatusFieldVisible] =
     useState(false);
+  const initializedRef = useRef(false);
+
+  // 同步初始表单值到 Redux store,并生成登记号
+  useEffect(() => {
+    if (!initializedRef.current) {
+      // 生成登记号(如果不存在)
+      let updatedFormData = { ...formData };
+      if (!updatedFormData.accession_number) {
+        const now = dayjs();
+        updatedFormData.accession_number = now.format('YYYYMMDDHHmmSS');
+      }
+
+      const allValues = form?.getFieldsValue();
+      if (allValues && Object.keys(allValues).length > 0) {
+        const merged = { ...allValues ,...updatedFormData};
+        dispatch(setFormData(merged));
+        form?.setFieldsValue(merged)
+      }
+
+      initializedRef.current = true;
+    }
+  }, [form, dispatch, formData]);
 
   const intl = useIntl();
 

+ 1 - 1
src/states/patient/register/formSlice.ts

@@ -15,7 +15,7 @@ const formSlice = createSlice({
   reducers: {
     // eslint-disable-next-line @typescript-eslint/no-explicit-any
     setFormData: (state, action: PayloadAction<Record<string, any>>) => {
-      state.formData = action.payload;
+      state.formData = { ...state.formData, ...action.payload };
     },
     getFormData: (state) => state, //其实这里用不到
     // 清空表单数据