@jetlinks-web/components 3.1.14 → 3.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/es/EditTable/CellRender.js +69 -3
- package/es/EditTable/EditTable.js +108 -165
- package/es/EditTable/FormItem.js +234 -96
- package/es/EditTable/consts.js +13 -13
- package/es/EditTable/context.js +3 -2
- package/es/EditTable/fieldPool.js +166 -0
- package/es/EditTable/hooks/index.js +4 -2
- package/es/EditTable/hooks/useValidate.js +121 -51
- package/es/EditTable/hooks/useVirtualTreeTable.js +111 -0
- package/es/EditTable/index.js +0 -4
- package/es/EditTable/style/body.js +15 -2
- package/es/EditTable/style/form.js +2 -2
- package/es/EditTable/style/header.js +2 -2
- package/es/EditTable/style/table.js +2 -1
- package/es/Icon/icon.js +3 -3
- package/es/ProTable/Content.js +3 -4
- package/es/ProTable/ProTable.js +5 -0
- package/es/ProTable/setting.js +1 -1
- package/es/Search/Advanced/index.js +2 -1
- package/es/Search/Search.js +2 -1
- package/es/VirtualTable/Table.js +367 -0
- package/es/VirtualTable/VirtualBody.js +94 -0
- package/es/VirtualTable/data.js +43 -1
- package/es/VirtualTable/index.js +1 -1
- package/es/VirtualTable/style/index.js +6 -0
- package/es/VirtualTable/useTreeData.js +243 -0
- package/es/VirtualTable/useVirtualScroll.js +159 -0
- package/lib/EditTable/CellRender.js +69 -3
- package/lib/EditTable/EditTable.js +108 -165
- package/lib/EditTable/FormItem.js +234 -96
- package/lib/EditTable/consts.js +13 -13
- package/lib/EditTable/context.js +3 -2
- package/lib/EditTable/fieldPool.js +173 -0
- package/lib/EditTable/hooks/index.js +15 -2
- package/lib/EditTable/hooks/useValidate.js +120 -50
- package/lib/EditTable/hooks/useVirtualTreeTable.js +117 -0
- package/lib/EditTable/index.js +0 -4
- package/lib/EditTable/style/body.js +15 -2
- package/lib/EditTable/style/form.js +2 -2
- package/lib/EditTable/style/header.js +2 -2
- package/lib/EditTable/style/table.js +2 -1
- package/lib/Icon/icon.js +3 -3
- package/lib/ProTable/Content.js +3 -4
- package/lib/ProTable/ProTable.js +5 -0
- package/lib/ProTable/setting.js +1 -1
- package/lib/Search/Advanced/index.js +2 -1
- package/lib/Search/Search.js +2 -1
- package/lib/VirtualTable/Table.js +374 -0
- package/lib/VirtualTable/VirtualBody.js +100 -0
- package/lib/VirtualTable/data.js +44 -2
- package/lib/VirtualTable/index.js +4 -4
- package/lib/VirtualTable/style/index.js +6 -0
- package/lib/VirtualTable/useTreeData.js +250 -0
- package/lib/VirtualTable/useVirtualScroll.js +165 -0
- package/package.json +3 -3
- package/es/EditTable/Body.js +0 -312
- package/es/EditTable/Header.js +0 -164
- package/es/EditTable/HeaderRender.js +0 -12
- package/es/VirtualTable/VirtualTable.js +0 -407
- package/lib/EditTable/Body.js +0 -312
- package/lib/EditTable/Header.js +0 -164
- package/lib/EditTable/HeaderRender.js +0 -12
- package/lib/VirtualTable/VirtualTable.js +0 -407
|
@@ -15,21 +15,26 @@ function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]
|
|
|
15
15
|
}
|
|
16
16
|
} return value; }
|
|
17
17
|
/* Analyzed bindings: {
|
|
18
|
-
"name": "props",
|
|
19
|
-
"required": "props",
|
|
20
18
|
"onBeforeUnmount": "setup-const",
|
|
21
19
|
"computed": "setup-const",
|
|
22
20
|
"reactive": "setup-const",
|
|
23
21
|
"watch": "setup-const",
|
|
24
22
|
"provide": "setup-const",
|
|
23
|
+
"toRaw": "setup-const",
|
|
24
|
+
"nextTick": "setup-const",
|
|
25
|
+
"onMounted": "setup-const",
|
|
25
26
|
"get": "setup-maybe-ref",
|
|
26
27
|
"isArray": "setup-maybe-ref",
|
|
28
|
+
"set": "setup-maybe-ref",
|
|
29
|
+
"cloneDeep": "setup-maybe-ref",
|
|
27
30
|
"useProvideFormItemContext": "setup-maybe-ref",
|
|
31
|
+
"Schema": "setup-maybe-ref",
|
|
28
32
|
"useInjectError": "setup-maybe-ref",
|
|
29
33
|
"useInjectForm": "setup-maybe-ref",
|
|
30
34
|
"TABLE_FORM_ITEM_ERROR": "setup-maybe-ref",
|
|
31
35
|
"genEditTableStyle": "setup-maybe-ref",
|
|
32
|
-
"
|
|
36
|
+
"fieldPool": "setup-maybe-ref",
|
|
37
|
+
"props": "setup-const",
|
|
33
38
|
"emit": "setup-const",
|
|
34
39
|
"prefixCls": "setup-ref",
|
|
35
40
|
"wrapSSR": "setup-maybe-ref",
|
|
@@ -37,70 +42,119 @@ function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]
|
|
|
37
42
|
"context": "setup-maybe-ref",
|
|
38
43
|
"globalErrorMessage": "setup-maybe-ref",
|
|
39
44
|
"hideTimer": "setup-let",
|
|
45
|
+
"cachedFieldPath": "setup-let",
|
|
46
|
+
"cachedName": "setup-let",
|
|
47
|
+
"fieldPath": "setup-ref",
|
|
40
48
|
"eventKey": "setup-ref",
|
|
49
|
+
"fieldId": "setup-ref",
|
|
50
|
+
"fieldName": "setup-ref",
|
|
51
|
+
"rowIndex": "setup-ref",
|
|
52
|
+
"fieldValue": "setup-ref",
|
|
41
53
|
"errorMap": "setup-reactive-const",
|
|
42
|
-
"filedId": "setup-ref",
|
|
43
|
-
"filedName": "setup-ref",
|
|
44
|
-
"filedValue": "setup-ref",
|
|
45
54
|
"popContainer": "setup-const",
|
|
46
55
|
"removeTimer": "setup-const",
|
|
47
56
|
"showErrorTip": "setup-const",
|
|
48
57
|
"hideErrorTip": "setup-const",
|
|
58
|
+
"getFieldRules": "setup-const",
|
|
59
|
+
"validateField": "setup-const",
|
|
49
60
|
"validateRules": "setup-const",
|
|
50
61
|
"onFieldBlur": "setup-const",
|
|
51
|
-
"onFieldChange": "setup-const"
|
|
62
|
+
"onFieldChange": "setup-const",
|
|
63
|
+
"isRegistered": "setup-let",
|
|
64
|
+
"registerField": "setup-const",
|
|
65
|
+
"name": "props",
|
|
66
|
+
"required": "props",
|
|
67
|
+
"rules": "props"
|
|
52
68
|
} */
|
|
53
|
-
import {
|
|
69
|
+
import { defineComponent as _defineComponent } from 'vue';
|
|
70
|
+
import { toDisplayString as _toDisplayString, createElementVNode as _createElementVNode, unref as _unref, normalizeClass as _normalizeClass, openBlock as _openBlock, createElementBlock as _createElementBlock, createCommentVNode as _createCommentVNode, resolveComponent as _resolveComponent, withCtx as _withCtx, createBlock as _createBlock, renderSlot as _renderSlot, Fragment as _Fragment } from "vue";
|
|
54
71
|
const _hoisted_1 = { style: { "color": "#1d2129" } };
|
|
55
72
|
const _hoisted_2 = ["id"];
|
|
56
|
-
import { onBeforeUnmount, computed, reactive, watch, provide } from "vue";
|
|
57
|
-
import { get, isArray } from 'lodash-es';
|
|
73
|
+
import { onBeforeUnmount, computed, reactive, watch, provide, toRaw, nextTick, onMounted } from "vue";
|
|
74
|
+
import { get, isArray, } from 'lodash-es';
|
|
58
75
|
import { useProvideFormItemContext } from 'ant-design-vue/lib/form/FormItemContext';
|
|
76
|
+
import Schema from 'async-validator';
|
|
59
77
|
import { useInjectError, useInjectForm } from "./hooks";
|
|
60
78
|
import { TABLE_FORM_ITEM_ERROR } from "./consts";
|
|
61
79
|
import genEditTableStyle from './style';
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
80
|
+
import { fieldPool } from './fieldPool';
|
|
81
|
+
const __sfc_main__ = _defineComponent({
|
|
82
|
+
...{
|
|
83
|
+
name: 'JEditTableFormItem'
|
|
84
|
+
},
|
|
65
85
|
props: {
|
|
66
|
-
name: {
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
},
|
|
70
|
-
required: {
|
|
71
|
-
type: Boolean,
|
|
72
|
-
default: false
|
|
73
|
-
}
|
|
86
|
+
name: { type: [String, Array], required: false, default: undefined },
|
|
87
|
+
required: { type: Boolean, required: false, default: false },
|
|
88
|
+
rules: { type: Array, required: false, default: () => [] }
|
|
74
89
|
},
|
|
75
|
-
emits: [
|
|
76
|
-
setup(__props, { emit: __emit }) {
|
|
90
|
+
emits: ["change"],
|
|
91
|
+
setup(__props, { expose: __expose, emit: __emit }) {
|
|
77
92
|
const props = __props;
|
|
78
93
|
const emit = __emit;
|
|
79
94
|
const prefixCls = computed(() => 'jetlinks-edit-table');
|
|
80
95
|
const [wrapSSR, hashId] = genEditTableStyle(prefixCls);
|
|
81
96
|
const context = useInjectForm();
|
|
82
97
|
const globalErrorMessage = useInjectError();
|
|
83
|
-
let hideTimer;
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
const
|
|
89
|
-
|
|
90
|
-
|
|
98
|
+
let hideTimer = null;
|
|
99
|
+
// 缓存字段路径,避免频繁的数组操作
|
|
100
|
+
let cachedFieldPath = null;
|
|
101
|
+
let cachedName = undefined;
|
|
102
|
+
// 计算字段路径
|
|
103
|
+
const fieldPath = computed(() => {
|
|
104
|
+
if (!props.name)
|
|
105
|
+
return [];
|
|
106
|
+
// 如果 name 没变,返回缓存
|
|
107
|
+
if (cachedName === props.name && cachedFieldPath) {
|
|
108
|
+
return cachedFieldPath;
|
|
109
|
+
}
|
|
110
|
+
cachedName = props.name;
|
|
111
|
+
cachedFieldPath = isArray(props.name) ? props.name : [props.name];
|
|
112
|
+
return cachedFieldPath;
|
|
91
113
|
});
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
114
|
+
// 事件key,用于标识字段 - 使用简单字符串拼接
|
|
115
|
+
const eventKey = computed(() => fieldPath.value.join('-'));
|
|
116
|
+
// 字段ID
|
|
117
|
+
const fieldId = computed(() => {
|
|
118
|
+
const path = fieldPath.value;
|
|
119
|
+
if (path.length === 0)
|
|
120
|
+
return '';
|
|
121
|
+
const [index, ...extra] = path;
|
|
95
122
|
return `${index}-${extra.join('.')}`;
|
|
96
123
|
});
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
124
|
+
// 字段名(最后一个路径部分)
|
|
125
|
+
const fieldName = computed(() => {
|
|
126
|
+
const path = fieldPath.value;
|
|
127
|
+
return path.length > 0 ? path[path.length - 1] : undefined;
|
|
100
128
|
});
|
|
101
|
-
|
|
102
|
-
|
|
129
|
+
// 行索引
|
|
130
|
+
const rowIndex = computed(() => {
|
|
131
|
+
const path = fieldPath.value;
|
|
132
|
+
return path.length > 0 ? Number(path[0]) : 0;
|
|
103
133
|
});
|
|
134
|
+
// 字段值 - 优化:避免不必要的 get 调用
|
|
135
|
+
const fieldValue = computed(() => {
|
|
136
|
+
if (!_optionalChain([context, 'access', _2 => _2.dataSource, 'optionalAccess', _3 => _3.value]) || !props.name)
|
|
137
|
+
return undefined;
|
|
138
|
+
const dataSource = context.dataSource.value;
|
|
139
|
+
const path = fieldPath.value;
|
|
140
|
+
// 快速路径:单层访问
|
|
141
|
+
if (path.length === 1) {
|
|
142
|
+
return dataSource[path[0]];
|
|
143
|
+
}
|
|
144
|
+
// 快速路径:双层访问(最常见的情况:dataSource[index][field])
|
|
145
|
+
if (path.length === 2) {
|
|
146
|
+
const item = dataSource[path[0]];
|
|
147
|
+
return item ? item[path[1]] : undefined;
|
|
148
|
+
}
|
|
149
|
+
// 深层路径:使用 lodash.get
|
|
150
|
+
return get(dataSource, props.name);
|
|
151
|
+
});
|
|
152
|
+
// 错误状态
|
|
153
|
+
const errorMap = reactive({
|
|
154
|
+
message: '',
|
|
155
|
+
visible: false
|
|
156
|
+
});
|
|
157
|
+
// 向下提供错误状态
|
|
104
158
|
provide(TABLE_FORM_ITEM_ERROR, errorMap);
|
|
105
159
|
const popContainer = (e) => {
|
|
106
160
|
return e;
|
|
@@ -123,88 +177,172 @@ const __sfc_main__ = Object.assign({
|
|
|
123
177
|
errorMap.message = '';
|
|
124
178
|
}, 300);
|
|
125
179
|
};
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
180
|
+
// 获取当前字段的校验规则
|
|
181
|
+
const getFieldRules = () => {
|
|
182
|
+
// 优先使用 props.rules
|
|
183
|
+
if (props.rules && props.rules.length > 0) {
|
|
184
|
+
return props.rules;
|
|
130
185
|
}
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
const error = _optionalChain([res, 'optionalAccess', _2 => _2.filter, 'call', _3 => _3(item => item.field === filedName.value)]) || [];
|
|
137
|
-
if (error.length === 0) {
|
|
138
|
-
hideErrorTip();
|
|
139
|
-
context.removeFieldError(eventKey.value);
|
|
186
|
+
// 从 context 中获取规则
|
|
187
|
+
if (_optionalChain([context, 'access', _4 => _4.rules, 'optionalAccess', _5 => _5.value]) && fieldName.value) {
|
|
188
|
+
const rules = context.rules.value[fieldName.value];
|
|
189
|
+
if (Array.isArray(rules)) {
|
|
190
|
+
return rules;
|
|
140
191
|
}
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
192
|
+
}
|
|
193
|
+
// 如果 required 但没有规则,创建默认必填规则
|
|
194
|
+
if (props.required) {
|
|
195
|
+
return [{ required: true, message: `${fieldName.value} 不能为空` }];
|
|
196
|
+
}
|
|
197
|
+
return [];
|
|
198
|
+
};
|
|
199
|
+
// 使用 async-validator 执行校验
|
|
200
|
+
const validateField = () => {
|
|
201
|
+
return new Promise((resolve, reject) => {
|
|
202
|
+
const rules = getFieldRules();
|
|
203
|
+
if (!rules || rules.length === 0) {
|
|
204
|
+
hideErrorTip();
|
|
205
|
+
_optionalChain([context, 'access', _6 => _6.removeFieldError, 'optionalCall', _7 => _7(eventKey.value)]);
|
|
206
|
+
resolve();
|
|
207
|
+
return;
|
|
146
208
|
}
|
|
147
|
-
|
|
209
|
+
const descriptor = {
|
|
210
|
+
[fieldName.value]: rules
|
|
211
|
+
};
|
|
212
|
+
const validator = new Schema(descriptor);
|
|
213
|
+
const data = {
|
|
214
|
+
[fieldName.value]: toRaw(fieldValue.value)
|
|
215
|
+
};
|
|
216
|
+
validator.validate(data, { firstFields: true }, (errors) => {
|
|
217
|
+
if (errors && errors.length > 0) {
|
|
218
|
+
const errorMsg = errors[0].message || '校验失败';
|
|
219
|
+
showErrorTip(errorMsg);
|
|
220
|
+
_optionalChain([context, 'access', _8 => _8.addFieldError, 'optionalCall', _9 => _9(eventKey.value, errorMsg)]);
|
|
221
|
+
reject(errors);
|
|
222
|
+
}
|
|
223
|
+
else {
|
|
224
|
+
hideErrorTip();
|
|
225
|
+
_optionalChain([context, 'access', _10 => _10.removeFieldError, 'optionalCall', _11 => _11(eventKey.value)]);
|
|
226
|
+
resolve();
|
|
227
|
+
}
|
|
228
|
+
});
|
|
148
229
|
});
|
|
149
|
-
|
|
230
|
+
};
|
|
231
|
+
// 兼容旧API的校验方法
|
|
232
|
+
const validateRules = () => {
|
|
233
|
+
// 如果 context 提供了 validateItem,使用它来保持兼容性
|
|
234
|
+
if (context.validateItem) {
|
|
235
|
+
const promise = context.validateItem({ [fieldName.value]: fieldValue.value }, rowIndex.value);
|
|
236
|
+
promise.then(() => {
|
|
237
|
+
hideErrorTip();
|
|
238
|
+
_optionalChain([context, 'access', _12 => _12.removeFieldError, 'optionalCall', _13 => _13(eventKey.value)]);
|
|
239
|
+
}).catch((res) => {
|
|
240
|
+
const error = _optionalChain([res, 'optionalAccess', _14 => _14.filter, 'call', _15 => _15((item) => item.field === fieldName.value)]) || [];
|
|
241
|
+
if (error.length === 0) {
|
|
242
|
+
hideErrorTip();
|
|
243
|
+
_optionalChain([context, 'access', _16 => _16.removeFieldError, 'optionalCall', _17 => _17(eventKey.value)]);
|
|
244
|
+
}
|
|
245
|
+
else {
|
|
246
|
+
removeTimer();
|
|
247
|
+
errorMap.message = _optionalChain([error, 'access', _18 => _18[0], 'optionalAccess', _19 => _19.message]) || errorMap.message;
|
|
248
|
+
errorMap.visible = !!error.length;
|
|
249
|
+
_optionalChain([context, 'access', _20 => _20.addFieldError, 'optionalCall', _21 => _21(eventKey.value, errorMap.message)]);
|
|
250
|
+
}
|
|
251
|
+
});
|
|
252
|
+
return promise;
|
|
253
|
+
}
|
|
254
|
+
// 使用本地校验
|
|
255
|
+
return validateField();
|
|
150
256
|
};
|
|
151
257
|
const onFieldBlur = () => {
|
|
152
|
-
//
|
|
258
|
+
// 改为失焦时校验,减少实时校验的性能开销
|
|
259
|
+
validateRules();
|
|
153
260
|
};
|
|
154
261
|
const onFieldChange = () => {
|
|
155
|
-
|
|
156
|
-
validateRules()
|
|
262
|
+
// 只触发 change 事件,不进行校验
|
|
263
|
+
// validateRules() // 移到 onBlur
|
|
157
264
|
emit('change');
|
|
158
265
|
};
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
266
|
+
// 监听全局错误变化 - 精确监听单个字段,避免深度遍历
|
|
267
|
+
watch(() => _optionalChain([globalErrorMessage, 'optionalAccess', _22 => _22.value, 'optionalAccess', _23 => _23[eventKey.value]]), (errorMsg) => {
|
|
268
|
+
if (errorMsg) {
|
|
269
|
+
showErrorTip(errorMsg);
|
|
162
270
|
}
|
|
163
271
|
else {
|
|
164
272
|
hideErrorTip();
|
|
165
273
|
}
|
|
166
|
-
}, { immediate: true
|
|
274
|
+
}, { immediate: true });
|
|
275
|
+
// 注册到 ant-design-vue form context
|
|
167
276
|
useProvideFormItemContext({
|
|
168
|
-
id:
|
|
277
|
+
id: fieldId,
|
|
169
278
|
onFieldChange,
|
|
170
279
|
onFieldBlur,
|
|
171
280
|
}, computed(() => {
|
|
172
|
-
|
|
173
|
-
return get(context.dataSource.value, props.name);
|
|
281
|
+
return get(_optionalChain([context, 'access', _24 => _24.dataSource, 'optionalAccess', _25 => _25.value]), props.name);
|
|
174
282
|
}));
|
|
283
|
+
// 注册字段到父组件 - 使用字段池复用,减少创建/销毁开销
|
|
284
|
+
let isRegistered = false;
|
|
285
|
+
const registerField = () => {
|
|
286
|
+
if (props.name && !isRegistered) {
|
|
287
|
+
// 使用字段池获取或创建字段信息
|
|
288
|
+
const fieldInfo = fieldPool.acquire(eventKey.value, {
|
|
289
|
+
fieldName: fieldName.value,
|
|
290
|
+
eventKey: eventKey.value,
|
|
291
|
+
names: props.name,
|
|
292
|
+
validateRules,
|
|
293
|
+
showErrorTip
|
|
294
|
+
});
|
|
295
|
+
_optionalChain([context, 'access', _26 => _26.addField, 'optionalCall', _27 => _27(eventKey.value, fieldInfo)]);
|
|
296
|
+
isRegistered = true;
|
|
297
|
+
}
|
|
298
|
+
};
|
|
299
|
+
// 延迟注册,避免虚拟滚动时的同步阻塞
|
|
300
|
+
onMounted(() => {
|
|
301
|
+
nextTick(() => {
|
|
302
|
+
registerField();
|
|
303
|
+
});
|
|
304
|
+
});
|
|
175
305
|
onBeforeUnmount(() => {
|
|
176
306
|
hideErrorTip();
|
|
307
|
+
if (isRegistered) {
|
|
308
|
+
_optionalChain([context, 'access', _28 => _28.removeField, 'optionalCall', _29 => _29(eventKey.value)]);
|
|
309
|
+
// 释放字段到池中,而不是销毁
|
|
310
|
+
fieldPool.release(eventKey.value);
|
|
311
|
+
isRegistered = false;
|
|
312
|
+
}
|
|
313
|
+
});
|
|
314
|
+
// 暴露方法
|
|
315
|
+
__expose({
|
|
316
|
+
validate: validateField,
|
|
317
|
+
validateRules,
|
|
318
|
+
showErrorTip,
|
|
319
|
+
hideErrorTip
|
|
177
320
|
});
|
|
178
|
-
watch(() => [filedName.value, props.name], () => {
|
|
179
|
-
context.addField(eventKey.value, {
|
|
180
|
-
filedName: filedName.value,
|
|
181
|
-
eventKey: eventKey.value,
|
|
182
|
-
names: props.name,
|
|
183
|
-
validateRules,
|
|
184
|
-
showErrorTip
|
|
185
|
-
});
|
|
186
|
-
}, { immediate: true });
|
|
187
321
|
return (_ctx, _cache) => {
|
|
188
322
|
const _component_a_tooltip = _resolveComponent("a-tooltip");
|
|
189
323
|
return (_openBlock(), _createElementBlock(_Fragment, null, [
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
324
|
+
(errorMap.visible)
|
|
325
|
+
? (_openBlock(), _createBlock(_component_a_tooltip, {
|
|
326
|
+
key: 0,
|
|
327
|
+
color: "#ffffff",
|
|
328
|
+
"get-popup-container": popContainer,
|
|
329
|
+
arrowPointAtCenter: true,
|
|
330
|
+
open: ""
|
|
331
|
+
}, {
|
|
332
|
+
title: _withCtx(() => [
|
|
333
|
+
_createElementVNode("span", _hoisted_1, _toDisplayString(errorMap.message), 1 /* TEXT */)
|
|
334
|
+
]),
|
|
335
|
+
default: _withCtx(() => [
|
|
336
|
+
(errorMap.visible)
|
|
337
|
+
? (_openBlock(), _createElementBlock("div", {
|
|
338
|
+
key: 0,
|
|
339
|
+
class: _normalizeClass(['jetlinks-table-form-error-target', _unref(hashId), 'hashId'])
|
|
340
|
+
}, null, 2 /* CLASS */))
|
|
341
|
+
: _createCommentVNode("v-if", true)
|
|
342
|
+
]),
|
|
343
|
+
_: 1 /* STABLE */
|
|
344
|
+
}))
|
|
345
|
+
: _createCommentVNode("v-if", true),
|
|
208
346
|
_createElementVNode("div", {
|
|
209
347
|
id: eventKey.value,
|
|
210
348
|
style: { "position": "relative" },
|
package/lib/EditTable/consts.js
CHANGED
|
@@ -4,16 +4,16 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
6
|
exports.TABLE_WRAPPER = exports.TABLE_TOOL = exports.TABLE_OPEN_GROUP = exports.TABLE_H_SCROLL = exports.TABLE_GROUP_OPTIONS = exports.TABLE_GROUP_ERROR = exports.TABLE_GROUP_ACTIVE = exports.TABLE_FORM_ITEM_ERROR = exports.TABLE_ERROR = exports.TABLE_DATA_SOURCE = exports.RIGHT_MENU = exports.METADATA_GROUP_OPTIONS = exports.FULL_SCREEN = void 0;
|
|
7
|
-
var METADATA_GROUP_OPTIONS = exports.METADATA_GROUP_OPTIONS =
|
|
8
|
-
var TABLE_WRAPPER = exports.TABLE_WRAPPER =
|
|
9
|
-
var FULL_SCREEN = exports.FULL_SCREEN =
|
|
10
|
-
var RIGHT_MENU = exports.RIGHT_MENU =
|
|
11
|
-
var TABLE_ERROR = exports.TABLE_ERROR =
|
|
12
|
-
var TABLE_GROUP_ERROR = exports.TABLE_GROUP_ERROR =
|
|
13
|
-
var TABLE_GROUP_OPTIONS = exports.TABLE_GROUP_OPTIONS =
|
|
14
|
-
var TABLE_DATA_SOURCE = exports.TABLE_DATA_SOURCE =
|
|
15
|
-
var TABLE_OPEN_GROUP = exports.TABLE_OPEN_GROUP =
|
|
16
|
-
var TABLE_TOOL = exports.TABLE_TOOL =
|
|
17
|
-
var TABLE_FORM_ITEM_ERROR = exports.TABLE_FORM_ITEM_ERROR =
|
|
18
|
-
var TABLE_GROUP_ACTIVE = exports.TABLE_GROUP_ACTIVE =
|
|
19
|
-
var TABLE_H_SCROLL = exports.TABLE_H_SCROLL =
|
|
7
|
+
var METADATA_GROUP_OPTIONS = exports.METADATA_GROUP_OPTIONS = 'metadata-group-options';
|
|
8
|
+
var TABLE_WRAPPER = exports.TABLE_WRAPPER = 'table-wrapper';
|
|
9
|
+
var FULL_SCREEN = exports.FULL_SCREEN = 'full';
|
|
10
|
+
var RIGHT_MENU = exports.RIGHT_MENU = 'right-menu';
|
|
11
|
+
var TABLE_ERROR = exports.TABLE_ERROR = 'table-error';
|
|
12
|
+
var TABLE_GROUP_ERROR = exports.TABLE_GROUP_ERROR = 'table-group-error';
|
|
13
|
+
var TABLE_GROUP_OPTIONS = exports.TABLE_GROUP_OPTIONS = 'table-group-options';
|
|
14
|
+
var TABLE_DATA_SOURCE = exports.TABLE_DATA_SOURCE = 'table-data-source';
|
|
15
|
+
var TABLE_OPEN_GROUP = exports.TABLE_OPEN_GROUP = 'table-open-group';
|
|
16
|
+
var TABLE_TOOL = exports.TABLE_TOOL = 'table-tool';
|
|
17
|
+
var TABLE_FORM_ITEM_ERROR = exports.TABLE_FORM_ITEM_ERROR = 'table-form-item-error';
|
|
18
|
+
var TABLE_GROUP_ACTIVE = exports.TABLE_GROUP_ACTIVE = 'table-group-active';
|
|
19
|
+
var TABLE_H_SCROLL = exports.TABLE_H_SCROLL = 'table-h-scroll';
|
package/lib/EditTable/context.js
CHANGED
|
@@ -12,7 +12,8 @@ var useFormContext = exports.useFormContext = function useFormContext(options) {
|
|
|
12
12
|
};
|
|
13
13
|
var useInjectForm = exports.useInjectForm = function useInjectForm() {
|
|
14
14
|
return (0, _vue.inject)(FormContextKey, {
|
|
15
|
-
addField: function addField(
|
|
15
|
+
addField: function addField() {},
|
|
16
|
+
removeField: function removeField() {},
|
|
16
17
|
dataSource: (0, _vue.computed)(function () {
|
|
17
18
|
return [];
|
|
18
19
|
}),
|
|
@@ -40,7 +41,7 @@ var useTableOpenGroup = exports.useTableOpenGroup = function useTableOpenGroup()
|
|
|
40
41
|
return (0, _vue.inject)(_consts.TABLE_OPEN_GROUP, false);
|
|
41
42
|
};
|
|
42
43
|
var useTableTool = exports.useTableTool = function useTableTool() {
|
|
43
|
-
return (0, _vue.inject)(_consts.TABLE_TOOL,
|
|
44
|
+
return (0, _vue.inject)(_consts.TABLE_TOOL, {});
|
|
44
45
|
};
|
|
45
46
|
var useGroupOptions = exports.useGroupOptions = function useGroupOptions() {
|
|
46
47
|
return (0, _vue.inject)(_consts.TABLE_GROUP_OPTIONS, []);
|
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
4
|
+
Object.defineProperty(exports, "__esModule", {
|
|
5
|
+
value: true
|
|
6
|
+
});
|
|
7
|
+
exports.fieldPool = void 0;
|
|
8
|
+
var _slicedToArray2 = _interopRequireDefault(require("@babel/runtime/helpers/slicedToArray"));
|
|
9
|
+
var _createForOfIteratorHelper2 = _interopRequireDefault(require("@babel/runtime/helpers/createForOfIteratorHelper"));
|
|
10
|
+
var _classCallCheck2 = _interopRequireDefault(require("@babel/runtime/helpers/classCallCheck"));
|
|
11
|
+
var _createClass2 = _interopRequireDefault(require("@babel/runtime/helpers/createClass"));
|
|
12
|
+
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
|
|
13
|
+
/**
|
|
14
|
+
* 字段注册池 - 复用字段注册对象,避免频繁创建/销毁
|
|
15
|
+
*/
|
|
16
|
+
var FieldPool = /*#__PURE__*/function () {
|
|
17
|
+
function FieldPool() {
|
|
18
|
+
(0, _classCallCheck2.default)(this, FieldPool);
|
|
19
|
+
(0, _defineProperty2.default)(this, "pool", new Map());
|
|
20
|
+
(0, _defineProperty2.default)(this, "maxSize", 200);
|
|
21
|
+
// 池的最大大小
|
|
22
|
+
(0, _defineProperty2.default)(this, "cleanupThreshold", 150);
|
|
23
|
+
// 清理阈值
|
|
24
|
+
(0, _defineProperty2.default)(this, "cleanupInterval", null);
|
|
25
|
+
// 每 5 秒清理一次不活跃的字段
|
|
26
|
+
this.startCleanup();
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* 获取或创建字段
|
|
30
|
+
*/
|
|
31
|
+
return (0, _createClass2.default)(FieldPool, [{
|
|
32
|
+
key: "acquire",
|
|
33
|
+
value: function acquire(eventKey, fieldInfo) {
|
|
34
|
+
var pooled = this.pool.get(eventKey);
|
|
35
|
+
if (pooled) {
|
|
36
|
+
// 复用现有字段
|
|
37
|
+
pooled.isActive = true;
|
|
38
|
+
pooled.lastUsed = Date.now();
|
|
39
|
+
// 更新字段信息(可能数据变了)
|
|
40
|
+
pooled.field = fieldInfo;
|
|
41
|
+
return pooled.field;
|
|
42
|
+
}
|
|
43
|
+
// 创建新字段
|
|
44
|
+
var newPooled = {
|
|
45
|
+
field: fieldInfo,
|
|
46
|
+
isActive: true,
|
|
47
|
+
lastUsed: Date.now()
|
|
48
|
+
};
|
|
49
|
+
this.pool.set(eventKey, newPooled);
|
|
50
|
+
// 如果池太大,触发清理
|
|
51
|
+
if (this.pool.size > this.maxSize) {
|
|
52
|
+
this.cleanup();
|
|
53
|
+
}
|
|
54
|
+
return fieldInfo;
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* 释放字段(标记为不活跃,但不删除)
|
|
58
|
+
*/
|
|
59
|
+
}, {
|
|
60
|
+
key: "release",
|
|
61
|
+
value: function release(eventKey) {
|
|
62
|
+
var pooled = this.pool.get(eventKey);
|
|
63
|
+
if (pooled) {
|
|
64
|
+
pooled.isActive = false;
|
|
65
|
+
pooled.lastUsed = Date.now();
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* 清理不活跃的字段
|
|
70
|
+
*/
|
|
71
|
+
}, {
|
|
72
|
+
key: "cleanup",
|
|
73
|
+
value: function cleanup() {
|
|
74
|
+
var _this = this;
|
|
75
|
+
var now = Date.now();
|
|
76
|
+
var maxAge = 30000; // 30秒未使用的字段会被清理
|
|
77
|
+
// 如果池大小超过阈值,开始清理
|
|
78
|
+
if (this.pool.size < this.cleanupThreshold) {
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
var toDelete = [];
|
|
82
|
+
var _iterator = (0, _createForOfIteratorHelper2.default)(this.pool.entries()),
|
|
83
|
+
_step;
|
|
84
|
+
try {
|
|
85
|
+
for (_iterator.s(); !(_step = _iterator.n()).done;) {
|
|
86
|
+
var _step$value = (0, _slicedToArray2.default)(_step.value, 2),
|
|
87
|
+
key = _step$value[0],
|
|
88
|
+
pooled = _step$value[1];
|
|
89
|
+
// 清理不活跃且长时间未使用的字段
|
|
90
|
+
if (!pooled.isActive && now - pooled.lastUsed > maxAge) {
|
|
91
|
+
toDelete.push(key);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
} catch (err) {
|
|
95
|
+
_iterator.e(err);
|
|
96
|
+
} finally {
|
|
97
|
+
_iterator.f();
|
|
98
|
+
}
|
|
99
|
+
toDelete.forEach(function (key) {
|
|
100
|
+
return _this.pool.delete(key);
|
|
101
|
+
});
|
|
102
|
+
if (toDelete.length > 0) {
|
|
103
|
+
console.debug("[FieldPool] Cleaned up ".concat(toDelete.length, " inactive fields"));
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* 启动定时清理
|
|
108
|
+
*/
|
|
109
|
+
}, {
|
|
110
|
+
key: "startCleanup",
|
|
111
|
+
value: function startCleanup() {
|
|
112
|
+
var _this2 = this;
|
|
113
|
+
if (this.cleanupInterval) return;
|
|
114
|
+
this.cleanupInterval = setInterval(function () {
|
|
115
|
+
_this2.cleanup();
|
|
116
|
+
}, 5000);
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* 停止定时清理
|
|
120
|
+
*/
|
|
121
|
+
}, {
|
|
122
|
+
key: "stopCleanup",
|
|
123
|
+
value: function stopCleanup() {
|
|
124
|
+
if (this.cleanupInterval) {
|
|
125
|
+
clearInterval(this.cleanupInterval);
|
|
126
|
+
this.cleanupInterval = null;
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* 清空池
|
|
131
|
+
*/
|
|
132
|
+
}, {
|
|
133
|
+
key: "clear",
|
|
134
|
+
value: function clear() {
|
|
135
|
+
this.pool.clear();
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* 获取池的统计信息
|
|
139
|
+
*/
|
|
140
|
+
}, {
|
|
141
|
+
key: "getStats",
|
|
142
|
+
value: function getStats() {
|
|
143
|
+
var activeCount = 0;
|
|
144
|
+
var inactiveCount = 0;
|
|
145
|
+
var _iterator2 = (0, _createForOfIteratorHelper2.default)(this.pool.values()),
|
|
146
|
+
_step2;
|
|
147
|
+
try {
|
|
148
|
+
for (_iterator2.s(); !(_step2 = _iterator2.n()).done;) {
|
|
149
|
+
var pooled = _step2.value;
|
|
150
|
+
if (pooled.isActive) {
|
|
151
|
+
activeCount++;
|
|
152
|
+
} else {
|
|
153
|
+
inactiveCount++;
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
} catch (err) {
|
|
157
|
+
_iterator2.e(err);
|
|
158
|
+
} finally {
|
|
159
|
+
_iterator2.f();
|
|
160
|
+
}
|
|
161
|
+
return {
|
|
162
|
+
total: this.pool.size,
|
|
163
|
+
active: activeCount,
|
|
164
|
+
inactive: inactiveCount
|
|
165
|
+
};
|
|
166
|
+
}
|
|
167
|
+
}]);
|
|
168
|
+
}(); // 创建全局单例
|
|
169
|
+
var fieldPool = exports.fieldPool = new FieldPool();
|
|
170
|
+
// 开发环境下暴露到 window,方便调试
|
|
171
|
+
if (import.meta.env.DEV) {
|
|
172
|
+
window.__fieldPool__ = fieldPool;
|
|
173
|
+
}
|