刘光辉
7 小时以前 0dfe84494048ce27ba8449831782128412d3eb13
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
import type { ComponentType } from '@jnpf/ui/form';
 
import { defineComponent, getCurrentInstance, h, nextTick, onMounted, ref, unref } from 'vue';
 
import { componentMap } from '@jnpf/ui/form';
 
import { cloneDeep, upperFirst } from 'lodash-es';
 
import { getRealProps } from './transform';
 
export default defineComponent({
  props: {
    conf: {
      type: Object,
      required: true,
    },
    formData: {
      type: Object,
      default: () => {},
    },
    size: {
      type: String,
      default: 'default',
    },
    relations: {
      type: Object,
      default: () => {},
    },
    onlineUtilsOpen: {
      type: Boolean,
      default: false,
    },
  },
  setup(props, { emit, expose }) {
    const tableRef = ref<any>(null);
 
    expose({ tableRef });
    function buildVModel(dataObject, defaultValue) {
      dataObject.value = defaultValue;
      const obj = dataObject.on ?? {};
      obj['update:value'] = (val) => {
        emit('update:value', val);
      };
      dataObject.on = obj;
    }
 
    function emitEvents(confClone) {
      ['on', 'nativeOn'].forEach((attr) => {
        const eventKeyList = Object.keys(confClone[attr] || {});
        eventKeyList.forEach((key) => {
          if (typeof key === 'string') {
            confClone[attr][key] = (...arg) => emit(key, arg);
          }
        });
      });
    }
 
    function buildDataObject(confClone, dataObject, formData) {
      const jnpfKey = confClone.__config__.jnpfKey;
      Object.keys(confClone).forEach((key) => {
        const val = confClone[key];
        if (key === '__vModel__') {
          buildVModel(dataObject, confClone.__config__.defaultValue);
        } else if (dataObject[key] === undefined) {
          dataObject[key] = val;
        } else {
          if (dataObject[key] === null || dataObject[key] instanceof RegExp || ['boolean', 'function', 'number', 'string'].includes(typeof dataObject[key])) {
            dataObject[key] = val;
          } else if (Array.isArray(dataObject[key])) {
            dataObject[key] = [...dataObject[key], ...val];
          } else {
            dataObject[key] = { ...dataObject[key], ...val };
          }
        }
      });
      if (['autoComplete', 'barcode', 'calculate', 'dateCalculate', 'popupSelect', 'popupTableSelect', 'qrcode', 'relationQuery', 'table'].includes(jnpfKey)) {
        dataObject.formData = formData;
      }
      if (['table'].includes(jnpfKey)) {
        dataObject.relations = props.relations;
        dataObject.vModel = confClone.__vModel__;
        dataObject.ref = 'tableRef';
      }
      if (['popupSelect', 'relationForm'].includes(jnpfKey)) {
        dataObject.field = confClone.__config__.tableName
          ? `${confClone.__vModel__}_jnpfTable_${confClone.__config__.tableName}${confClone.__config__.isSubTable ? '0' : '1'}`
          : confClone.__vModel__;
        if (confClone.__config__.isSubTable) delete dataObject.extraOptions;
      }
      if (jnpfKey === 'relationForm') dataObject.onlineUtilsOpen = props.onlineUtilsOpen;
      // 清理属性
      clearAttrs(dataObject);
    }
 
    function clearAttrs(dataObject) {
      delete dataObject.__config__;
      delete dataObject.__slot__;
      delete dataObject.__methods__;
      delete dataObject.on;
    }
 
    onMounted(() => {
      const instance = getCurrentInstance();
      nextTick(() => {
        tableRef.value = unref(instance?.refs?.tableRef);
      });
    });
 
    return () => {
      const dataObject = {};
      const confClone = cloneDeep(props.conf);
      // 将字符串类型的事件,发送为消息
      emitEvents(confClone);
      // 将json表单配置转化为vue render可以识别的数据对象(dataObject)
      buildDataObject(confClone, dataObject, props.formData);
      const jnpfKey =
        upperFirst(props.conf.__config__.jnpfKey) === 'Table'
          ? 'InputTable'
          : props.conf.__config__.tag == 'JnpfOcr'
            ? 'Ocr'
            : upperFirst(props.conf.__config__.jnpfKey);
      const Comp = componentMap.get(jnpfKey as ComponentType) as ReturnType<typeof defineComponent>;
      if (!Comp) return null;
      const realDataObject = getRealProps(dataObject, props.conf.__config__.jnpfKey);
      if (props.conf.__config__.isDisplayOnly) {
        if (Reflect.has(realDataObject, 'readonly')) realDataObject.readonly = true;
        else realDataObject.disabled = true;
      }
      return h(Comp, realDataObject as any);
    };
  },
});