el-form-renderer-vue3 1.0.5 → 1.0.7
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/README.md +409 -0
- package/el-form-renderer-vue3.es.js +949 -953
- package/el-form-renderer-vue3.umd.js +4 -4
- package/femessage/components/render-form-group.vue +19 -21
- package/femessage/components/render-form-item.vue +108 -97
- package/femessage/el-form-renderer.vue +43 -31
- package/femessage/util/keys.js +3 -0
- package/package.json +10 -4
|
@@ -1,98 +1,100 @@
|
|
|
1
1
|
<template>
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
<
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
<
|
|
18
|
-
|
|
19
|
-
v-if="data.type === 'input'"
|
|
20
|
-
v-bind="componentProps"
|
|
21
|
-
:modelValue="itemValue"
|
|
22
|
-
readonly
|
|
23
|
-
v-on="listeners"
|
|
24
|
-
/>
|
|
25
|
-
|
|
26
|
-
<div v-else-if="data.type === 'select'">
|
|
27
|
-
{{ multipleValue }}
|
|
28
|
-
</div>
|
|
29
|
-
</template>
|
|
30
|
-
<!-- 处理 date-picker,cascader,动态渲染不显示文字 bug-->
|
|
31
|
-
<component
|
|
32
|
-
v-else-if="data.type === 'date-picker' || data.type === 'cascader'"
|
|
33
|
-
ref="customComponent"
|
|
34
|
-
v-bind:is="data.component || `el-${data.type || 'input'}`"
|
|
35
|
-
v-bind="componentProps"
|
|
36
|
-
:modelValue="itemValue"
|
|
37
|
-
:disabled="disabled || componentProps.disabled || readonly"
|
|
38
|
-
v-on="listeners"
|
|
39
|
-
:loading="loading"
|
|
40
|
-
:remote-method="data.remoteMethod || componentProps.remoteMethod || remoteMethod"
|
|
41
|
-
>
|
|
42
|
-
</component>
|
|
43
|
-
<!-- 绑定 模板引用 动态组件 props value值 是否禁用 事件 lodding 远端搜索方法 -->
|
|
44
|
-
<component
|
|
45
|
-
v-else
|
|
46
|
-
ref="customComponent"
|
|
47
|
-
v-bind:is="data.component || `el-${data.type || 'input'}`"
|
|
2
|
+
<!-- 绑定显示,校验匹配规则字段,label,rules校验规则,attrs(原生属性), -->
|
|
3
|
+
<el-form-item
|
|
4
|
+
v-if="_show"
|
|
5
|
+
:prop="prop"
|
|
6
|
+
:label="typeof data.label === 'string' ? data.label : ''"
|
|
7
|
+
:rules="!readonly && Array.isArray(data.rules) ? data.rules : undefined"
|
|
8
|
+
v-bind="data.attrs"
|
|
9
|
+
class="render-form-item"
|
|
10
|
+
>
|
|
11
|
+
<!-- label插槽 -->
|
|
12
|
+
<template #label>
|
|
13
|
+
<v-node v-if="data.label !== 'string'" :content="data.label" />
|
|
14
|
+
</template>
|
|
15
|
+
<!-- 处理之只读input select -->
|
|
16
|
+
<template v-if="readonly && hasReadonlyContent">
|
|
17
|
+
<el-input
|
|
18
|
+
v-if="data.type === 'input'"
|
|
48
19
|
v-bind="componentProps"
|
|
49
20
|
:modelValue="itemValue"
|
|
50
|
-
|
|
21
|
+
readonly
|
|
51
22
|
v-on="listeners"
|
|
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
|
-
|
|
23
|
+
/>
|
|
24
|
+
|
|
25
|
+
<div v-else-if="data.type === 'select'">
|
|
26
|
+
{{ multipleValue }}
|
|
27
|
+
</div>
|
|
28
|
+
</template>
|
|
29
|
+
<!-- 处理 date-picker,cascader,动态渲染不显示文字 bug-->
|
|
30
|
+
<component
|
|
31
|
+
v-else-if="data.type === 'date-picker' || data.type === 'cascader'"
|
|
32
|
+
ref="customComponent"
|
|
33
|
+
v-bind:is="data.component || `el-${data.type || 'input'}`"
|
|
34
|
+
v-bind="componentProps"
|
|
35
|
+
:modelValue="itemValue"
|
|
36
|
+
:disabled="disabled || componentProps.disabled || readonly"
|
|
37
|
+
v-on="listeners"
|
|
38
|
+
:loading="loading"
|
|
39
|
+
:remote-method="
|
|
40
|
+
data.remoteMethod || componentProps.remoteMethod || remoteMethod
|
|
41
|
+
"
|
|
42
|
+
>
|
|
43
|
+
</component>
|
|
44
|
+
<!-- 绑定 模板引用 动态组件 props value值 是否禁用 事件 lodding 远端搜索方法 -->
|
|
45
|
+
<component
|
|
46
|
+
v-else
|
|
47
|
+
ref="customComponent"
|
|
48
|
+
v-bind:is="data.component || `el-${data.type || 'input'}`"
|
|
49
|
+
v-bind="componentProps"
|
|
50
|
+
:modelValue="itemValue"
|
|
51
|
+
:disabled="disabled || componentProps.disabled || readonly"
|
|
52
|
+
v-on="listeners"
|
|
53
|
+
:loading="loading"
|
|
54
|
+
:remote-method="
|
|
55
|
+
data.remoteMethod || componentProps.remoteMethod || remoteMethod
|
|
56
|
+
"
|
|
57
|
+
>
|
|
58
|
+
<!-- 插槽处理 选项-->
|
|
59
|
+
<template v-for="(opt, index) in options">
|
|
60
|
+
<el-option
|
|
61
|
+
v-if="data.type === 'select'"
|
|
62
|
+
:key="optionKey(opt) || index"
|
|
63
|
+
v-bind="opt"
|
|
64
|
+
/>
|
|
65
|
+
<el-checkbox-button
|
|
66
|
+
v-if="data.type === 'checkbox-group' && data.style === 'button'"
|
|
67
|
+
:key="opt.value"
|
|
68
|
+
v-bind="opt"
|
|
69
|
+
:label="'value' in opt ? opt.value : opt.label"
|
|
70
|
+
>
|
|
71
|
+
{{ opt.label }}
|
|
72
|
+
</el-checkbox-button>
|
|
73
|
+
<el-checkbox
|
|
74
|
+
v-else-if="data.type === 'checkbox-group' && data.style !== 'button'"
|
|
75
|
+
:key="opt.value"
|
|
76
|
+
v-bind="opt"
|
|
77
|
+
:label="'value' in opt ? opt.value : opt.label"
|
|
78
|
+
>
|
|
79
|
+
{{ opt.label }}
|
|
80
|
+
</el-checkbox>
|
|
81
|
+
<el-radio-button
|
|
82
|
+
v-else-if="data.type === 'radio-group' && data.style === 'button'"
|
|
83
|
+
:key="opt.label"
|
|
84
|
+
v-bind="opt"
|
|
85
|
+
:label="'value' in opt ? opt.value : opt.label"
|
|
86
|
+
>{{ opt.label }}</el-radio-button
|
|
87
|
+
>
|
|
88
|
+
<el-radio
|
|
89
|
+
v-else-if="data.type === 'radio-group' && data.style !== 'button'"
|
|
90
|
+
:key="opt.label"
|
|
91
|
+
v-bind="opt"
|
|
92
|
+
:label="'value' in opt ? opt.value : opt.label"
|
|
93
|
+
>{{ opt.label }}</el-radio
|
|
94
|
+
>
|
|
95
|
+
</template>
|
|
96
|
+
</component>
|
|
97
|
+
</el-form-item>
|
|
96
98
|
</template>
|
|
97
99
|
|
|
98
100
|
<script setup>
|
|
@@ -107,6 +109,11 @@ import _get from "lodash.get";
|
|
|
107
109
|
// import CustomComponent from "../util/CustomComponent";
|
|
108
110
|
import VNode from "../util/VNode";
|
|
109
111
|
import axios from "axios";
|
|
112
|
+
import {
|
|
113
|
+
methodsSymbol,
|
|
114
|
+
updateFormsSymbol,
|
|
115
|
+
setOptionsSymbol,
|
|
116
|
+
} from "../util/keys";
|
|
110
117
|
let customComponent = ref();
|
|
111
118
|
|
|
112
119
|
let props = defineProps({
|
|
@@ -134,9 +141,9 @@ const loading = ref(false);
|
|
|
134
141
|
let dataRef = ref(props.data);
|
|
135
142
|
// 注入一个由祖先组件或整个应用 (通过 app.provide()) 提供的值。
|
|
136
143
|
// 父组件提供 element ui的方法
|
|
137
|
-
let methods = inject(
|
|
144
|
+
let methods = inject(methodsSymbol);
|
|
138
145
|
// 父组件提供的 更新 options的方法
|
|
139
|
-
let setOptions = inject(
|
|
146
|
+
let setOptions = inject(setOptionsSymbol);
|
|
140
147
|
// 是否校验
|
|
141
148
|
const isBlurTrigger =
|
|
142
149
|
props.data.rules &&
|
|
@@ -147,7 +154,9 @@ const isBlurTrigger =
|
|
|
147
154
|
// 计算props
|
|
148
155
|
const componentProps = computed(() => ({ ...props.data.el, ...propsInner }));
|
|
149
156
|
// 计算是否为只读 input select
|
|
150
|
-
const hasReadonlyContent = computed(() =>
|
|
157
|
+
const hasReadonlyContent = computed(() =>
|
|
158
|
+
["input", "select"].includes(props.data.type)
|
|
159
|
+
);
|
|
151
160
|
//执行传入的hidden
|
|
152
161
|
const hiddenStatus = computed(() => {
|
|
153
162
|
const hidden = props.data.hidden || (() => false);
|
|
@@ -169,7 +178,7 @@ const listeners = computed(() => {
|
|
|
169
178
|
const originOnChange = on.change || noop;
|
|
170
179
|
const trim = data.trim !== undefined ? data.trim : true;
|
|
171
180
|
|
|
172
|
-
let updateForm = inject(
|
|
181
|
+
let updateForm = inject(updateFormsSymbol);
|
|
173
182
|
return {
|
|
174
183
|
..._frompairs(
|
|
175
184
|
_topairs(on).map(([eName, handler]) => [
|
|
@@ -266,7 +275,8 @@ watch(
|
|
|
266
275
|
// 现改写成:分开处理 remote.request,remote.url
|
|
267
276
|
// 至于为什么判断新旧值相同则返回,是因为 form 的 content 是响应式的,防止用户直接修改 content 其他内容时,导致 remote.request 重新发请求
|
|
268
277
|
|
|
269
|
-
if (!newValue || typeof newValue !== "function" || newValue === oldValue)
|
|
278
|
+
if (!newValue || typeof newValue !== "function" || newValue === oldValue)
|
|
279
|
+
return;
|
|
270
280
|
|
|
271
281
|
makingRequest(props.data.remote);
|
|
272
282
|
},
|
|
@@ -279,7 +289,8 @@ watch(
|
|
|
279
289
|
// 第三个判断条件:防止 url 与 request 同时存在时,发送两次请求
|
|
280
290
|
if (!url || url === oldV || (!oldV && props.data.remote.request)) return;
|
|
281
291
|
const request =
|
|
282
|
-
props.data.remote.request ||
|
|
292
|
+
props.data.remote.request ||
|
|
293
|
+
(() => axios.get(url).then((resp) => resp.data));
|
|
283
294
|
makingRequest(Object.assign({}, props.data.remote, { request }));
|
|
284
295
|
},
|
|
285
296
|
{ immediate: true }
|
|
@@ -1,32 +1,37 @@
|
|
|
1
1
|
<template>
|
|
2
|
-
<
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
2
|
+
<el-form
|
|
3
|
+
ref="myelForm"
|
|
4
|
+
v-bind="$attrs"
|
|
5
|
+
:model="value"
|
|
6
|
+
class="el-form-renderer"
|
|
7
|
+
>
|
|
8
|
+
<template v-for="item in innerContent" :key="item.id">
|
|
9
|
+
<slot :name="`id:${item.id}`" />
|
|
10
|
+
<slot :name="`$id:${item.id}`" />
|
|
7
11
|
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
</
|
|
29
|
-
|
|
12
|
+
<component
|
|
13
|
+
:is="item.type === GROUP ? RenderFormGroup : RenderFormItem"
|
|
14
|
+
:ref="
|
|
15
|
+
(el) => {
|
|
16
|
+
customComponent[item.id] = el;
|
|
17
|
+
}
|
|
18
|
+
"
|
|
19
|
+
:data="item"
|
|
20
|
+
:value="value"
|
|
21
|
+
:item-value="value[item.id]"
|
|
22
|
+
:disabled="
|
|
23
|
+
disabled ||
|
|
24
|
+
(typeof item.disabled === 'function'
|
|
25
|
+
? item.disabled(value)
|
|
26
|
+
: item.disabled)
|
|
27
|
+
"
|
|
28
|
+
:readonly="readonly || item.readonly"
|
|
29
|
+
:options="options[item.id]"
|
|
30
|
+
@updateValue="updateValue"
|
|
31
|
+
/>
|
|
32
|
+
</template>
|
|
33
|
+
<slot />
|
|
34
|
+
</el-form>
|
|
30
35
|
</template>
|
|
31
36
|
|
|
32
37
|
<script setup>
|
|
@@ -49,6 +54,12 @@ import transformContent from "./util/transform-content";
|
|
|
49
54
|
import _set from "lodash.set";
|
|
50
55
|
import _isequal from "lodash.isequal";
|
|
51
56
|
import _clonedeep from "lodash.clonedeep";
|
|
57
|
+
|
|
58
|
+
import {
|
|
59
|
+
methodsSymbol,
|
|
60
|
+
updateFormsSymbol,
|
|
61
|
+
setOptionsSymbol,
|
|
62
|
+
} from "./util/keys";
|
|
52
63
|
import {
|
|
53
64
|
collect,
|
|
54
65
|
mergeValue,
|
|
@@ -263,13 +274,14 @@ const getComponentById = (id) => {
|
|
|
263
274
|
if (!itemContent.groupId) {
|
|
264
275
|
return customComponent.value[id].customComponent;
|
|
265
276
|
} else {
|
|
266
|
-
const componentRef =
|
|
277
|
+
const componentRef =
|
|
278
|
+
customComponent.value[itemContent.groupId].customComponent;
|
|
267
279
|
return componentRef[`formItem-${id}`].customComponent;
|
|
268
280
|
}
|
|
269
281
|
};
|
|
270
|
-
provide(
|
|
271
|
-
provide(
|
|
272
|
-
provide(
|
|
282
|
+
provide(methodsSymbol, methods);
|
|
283
|
+
provide(updateFormsSymbol, updateForm);
|
|
284
|
+
provide(setOptionsSymbol, setOptions);
|
|
273
285
|
defineExpose({
|
|
274
286
|
updateValue,
|
|
275
287
|
resetFields,
|
package/package.json
CHANGED
|
@@ -1,12 +1,18 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "el-form-renderer-vue3",
|
|
3
|
-
"version": "1.0.
|
|
4
|
-
"description": "",
|
|
3
|
+
"version": "1.0.7",
|
|
4
|
+
"description": "JSON-Rendering-FROM",
|
|
5
5
|
"main": "el-form-renderer-vue3.es.js",
|
|
6
6
|
"scripts": {
|
|
7
7
|
"test": "echo \"Error: no test specified\" && exit 1"
|
|
8
8
|
},
|
|
9
|
-
"keywords": [
|
|
10
|
-
|
|
9
|
+
"keywords": [
|
|
10
|
+
"vue",
|
|
11
|
+
"element",
|
|
12
|
+
"render",
|
|
13
|
+
"form",
|
|
14
|
+
"component"
|
|
15
|
+
],
|
|
16
|
+
"author": "https://gitee.com/childe-jia",
|
|
11
17
|
"license": "ISC"
|
|
12
18
|
}
|