@longhongguo/form-create-ant-design-vue 3.3.6 → 3.3.8
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/auto-import.js +5 -1
- package/dist/form-create.css +104 -7
- package/dist/form-create.esm.css +104 -7
- package/dist/form-create.esm.js +2 -2
- package/dist/form-create.esm.js.map +1 -1
- package/dist/form-create.js +2 -2
- package/dist/form-create.js.map +1 -1
- package/package.json +2 -2
- package/src/components/FcEditorWrapper.vue +618 -2
- package/src/core/alias.js +6 -0
- package/src/core/manager.js +23 -2
- package/src/parsers/alert.js +17 -0
- package/src/parsers/card.js +38 -0
- package/src/parsers/index.js +4 -0
- package/src/parsers/input.js +61 -0
- package/src/style/index.css +104 -7
package/src/core/manager.js
CHANGED
|
@@ -84,13 +84,34 @@ export default {
|
|
|
84
84
|
)
|
|
85
85
|
})
|
|
86
86
|
|
|
87
|
-
// 预览模式下:对 upload
|
|
87
|
+
// 预览模式下:对 upload 组件设置 disabled
|
|
88
|
+
// wangEditor 组件使用只读模式(readOnly),允许复制和点击链接
|
|
89
|
+
// textarea 组件使用只读模式(readOnly),允许复制和自适应高度
|
|
88
90
|
// CusSelect 相关组件使用预览模式(通过 CSS 阻止交互,不置灰)
|
|
89
91
|
if (this.$handle.preview === true) {
|
|
90
|
-
if (ctx.rule.type === 'upload'
|
|
92
|
+
if (ctx.rule.type === 'upload') {
|
|
91
93
|
if (ctx.prop.props) {
|
|
92
94
|
ctx.prop.props.disabled = true
|
|
93
95
|
}
|
|
96
|
+
} else if (ctx.rule.type === 'fcEditor') {
|
|
97
|
+
// wangEditor 使用只读模式,不设置 disabled
|
|
98
|
+
// 只读模式允许复制和点击链接,但禁止编辑
|
|
99
|
+
if (ctx.prop.props) {
|
|
100
|
+
ctx.prop.props.readOnly = true
|
|
101
|
+
}
|
|
102
|
+
} else if (
|
|
103
|
+
ctx.rule.type === 'input' &&
|
|
104
|
+
ctx.prop.props?.type === 'textarea'
|
|
105
|
+
) {
|
|
106
|
+
// textarea 使用只读模式,不设置 disabled
|
|
107
|
+
// 只读模式允许复制,但禁止编辑
|
|
108
|
+
if (ctx.prop.props) {
|
|
109
|
+
ctx.prop.props.readOnly = true
|
|
110
|
+
// 完全自适应高度,不限制最大高度
|
|
111
|
+
ctx.prop.props.autoSize = true
|
|
112
|
+
// 移除 rows 属性,让 autoSize 完全控制高度
|
|
113
|
+
delete ctx.prop.props.rows
|
|
114
|
+
}
|
|
94
115
|
}
|
|
95
116
|
}
|
|
96
117
|
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export default {
|
|
2
|
+
name: 'aAlert',
|
|
3
|
+
// Alert 是非输入组件,不需要 modelField
|
|
4
|
+
mergeProp(ctx) {
|
|
5
|
+
const props = ctx.prop.props || {}
|
|
6
|
+
// 如果没有 message 但有 description,将 description 作为 message
|
|
7
|
+
// 这样 Alert 会显示为小的样式(只有 message,没有 description)
|
|
8
|
+
if ((!props.message || props.message === '') && props.description) {
|
|
9
|
+
props.message = props.description
|
|
10
|
+
delete props.description
|
|
11
|
+
}
|
|
12
|
+
},
|
|
13
|
+
render(children, ctx) {
|
|
14
|
+
// 使用默认渲染,通过 alias 映射到 aAlert 组件
|
|
15
|
+
return ctx.$render.defaultRender(ctx, children)
|
|
16
|
+
}
|
|
17
|
+
}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
export default {
|
|
2
|
+
name: 'aCard',
|
|
3
|
+
mergeProp(ctx) {
|
|
4
|
+
// 确保 children 存在
|
|
5
|
+
if (!ctx.rule.children) {
|
|
6
|
+
ctx.rule.children = []
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
// 为 Card 容器的所有子组件设置 col: false,避免被 a-col 包装
|
|
10
|
+
// 这样子组件可以直接作为 Card 的子元素
|
|
11
|
+
if (ctx.rule.children && Array.isArray(ctx.rule.children)) {
|
|
12
|
+
ctx.rule.children.forEach((child) => {
|
|
13
|
+
if (
|
|
14
|
+
child &&
|
|
15
|
+
typeof child === 'object' &&
|
|
16
|
+
child.type !== 'DragTool' &&
|
|
17
|
+
child.type !== 'DragBox'
|
|
18
|
+
) {
|
|
19
|
+
// 只有当 col 未设置或为默认值时才设置
|
|
20
|
+
if (child.col === undefined || child.col === null) {
|
|
21
|
+
child.col = false
|
|
22
|
+
} else if (
|
|
23
|
+
child.col &&
|
|
24
|
+
typeof child.col === 'object' &&
|
|
25
|
+
child.col.show !== false
|
|
26
|
+
) {
|
|
27
|
+
child.col.show = false
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
})
|
|
31
|
+
}
|
|
32
|
+
},
|
|
33
|
+
render(children, ctx) {
|
|
34
|
+
// 使用默认渲染,通过 alias 映射到 aCard 组件
|
|
35
|
+
return ctx.$render.defaultRender(ctx, children)
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
package/src/parsers/index.js
CHANGED
|
@@ -17,6 +17,8 @@ import flex from './flex'
|
|
|
17
17
|
import space from './space'
|
|
18
18
|
import spin from './spin'
|
|
19
19
|
import div from './div'
|
|
20
|
+
import alert from './alert'
|
|
21
|
+
import card from './card'
|
|
20
22
|
import accTable from './accTable'
|
|
21
23
|
|
|
22
24
|
export default [
|
|
@@ -39,5 +41,7 @@ export default [
|
|
|
39
41
|
space,
|
|
40
42
|
spin,
|
|
41
43
|
div,
|
|
44
|
+
alert,
|
|
45
|
+
card,
|
|
42
46
|
accTable
|
|
43
47
|
]
|
package/src/parsers/input.js
CHANGED
|
@@ -26,5 +26,66 @@ export default {
|
|
|
26
26
|
password: 'aInputPassword'
|
|
27
27
|
}[type] || 'aInput'
|
|
28
28
|
return ctx.$render.vNode.make(type, ctx.prop, children)
|
|
29
|
+
},
|
|
30
|
+
mounted(ctx) {
|
|
31
|
+
// 预览模式下,为 textarea 设置自适应高度
|
|
32
|
+
if (
|
|
33
|
+
ctx.prop.props?.type === 'textarea' &&
|
|
34
|
+
ctx.prop.props?.readOnly &&
|
|
35
|
+
ctx.$handle?.preview === true
|
|
36
|
+
) {
|
|
37
|
+
const adjustTextareaHeight = (textareaEl) => {
|
|
38
|
+
if (!textareaEl) return
|
|
39
|
+
// 重置高度,然后设置为 scrollHeight
|
|
40
|
+
textareaEl.style.height = 'auto'
|
|
41
|
+
const scrollHeight = textareaEl.scrollHeight
|
|
42
|
+
if (scrollHeight > 0) {
|
|
43
|
+
textareaEl.style.height = scrollHeight + 'px'
|
|
44
|
+
}
|
|
45
|
+
textareaEl.style.overflow = 'hidden'
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
// 延迟执行,确保 DOM 已完全渲染
|
|
49
|
+
setTimeout(() => {
|
|
50
|
+
const el = ctx.el
|
|
51
|
+
if (!el) return
|
|
52
|
+
|
|
53
|
+
// 查找 textarea 元素
|
|
54
|
+
const textarea =
|
|
55
|
+
el.querySelector('textarea.ant-input') || el.querySelector('textarea')
|
|
56
|
+
if (!textarea) return
|
|
57
|
+
|
|
58
|
+
// 首次调整高度
|
|
59
|
+
adjustTextareaHeight(textarea)
|
|
60
|
+
|
|
61
|
+
// 使用 MutationObserver 监听内容变化
|
|
62
|
+
if (typeof MutationObserver !== 'undefined') {
|
|
63
|
+
const observer = new MutationObserver(() => {
|
|
64
|
+
adjustTextareaHeight(textarea)
|
|
65
|
+
})
|
|
66
|
+
|
|
67
|
+
observer.observe(textarea, {
|
|
68
|
+
attributes: true,
|
|
69
|
+
attributeFilter: ['value'],
|
|
70
|
+
childList: true,
|
|
71
|
+
subtree: true,
|
|
72
|
+
characterData: true
|
|
73
|
+
})
|
|
74
|
+
|
|
75
|
+
// 定期检查并调整(备用方案)
|
|
76
|
+
const intervalId = setInterval(() => {
|
|
77
|
+
adjustTextareaHeight(textarea)
|
|
78
|
+
}, 200)
|
|
79
|
+
|
|
80
|
+
// 在组件销毁时清理
|
|
81
|
+
if (ctx.$handle && ctx.$handle.vm) {
|
|
82
|
+
ctx.$handle.vm.$once('hook:beforeUnmount', () => {
|
|
83
|
+
observer.disconnect()
|
|
84
|
+
clearInterval(intervalId)
|
|
85
|
+
})
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
}, 100)
|
|
89
|
+
}
|
|
29
90
|
}
|
|
30
91
|
}
|
package/src/style/index.css
CHANGED
|
@@ -57,7 +57,11 @@
|
|
|
57
57
|
.form-create.is-preview .ant-textarea,
|
|
58
58
|
.form-create.is-preview .ant-upload,
|
|
59
59
|
.form-create.is-preview .ant-upload-list,
|
|
60
|
-
.form-create.is-preview .ant-upload-list-item
|
|
60
|
+
.form-create.is-preview .ant-upload-list-item,
|
|
61
|
+
.form-create.is-preview .ant-input-wrapper,
|
|
62
|
+
.form-create.is-preview .ant-input-affix-wrapper,
|
|
63
|
+
.form-create.is-preview .ant-input-group-wrapper,
|
|
64
|
+
.form-create.is-preview .ant-input-group {
|
|
61
65
|
border: none !important;
|
|
62
66
|
box-shadow: none !important;
|
|
63
67
|
background: transparent !important;
|
|
@@ -69,7 +73,10 @@
|
|
|
69
73
|
.form-create.is-preview .ant-picker:focus,
|
|
70
74
|
.form-create.is-preview .ant-cascader-picker:focus,
|
|
71
75
|
.form-create.is-preview .ant-input-password:focus,
|
|
72
|
-
.form-create.is-preview .ant-textarea:focus
|
|
76
|
+
.form-create.is-preview .ant-textarea:focus,
|
|
77
|
+
.form-create.is-preview .ant-input-wrapper:focus,
|
|
78
|
+
.form-create.is-preview .ant-input-affix-wrapper:focus,
|
|
79
|
+
.form-create.is-preview .ant-input-affix-wrapper-focused {
|
|
73
80
|
border: none !important;
|
|
74
81
|
box-shadow: none !important;
|
|
75
82
|
outline: none !important;
|
|
@@ -81,11 +88,30 @@
|
|
|
81
88
|
.form-create.is-preview .ant-picker:hover,
|
|
82
89
|
.form-create.is-preview .ant-cascader-picker:hover,
|
|
83
90
|
.form-create.is-preview .ant-input-password:hover,
|
|
84
|
-
.form-create.is-preview .ant-textarea:hover
|
|
91
|
+
.form-create.is-preview .ant-textarea:hover,
|
|
92
|
+
.form-create.is-preview .ant-input-wrapper:hover,
|
|
93
|
+
.form-create.is-preview .ant-input-affix-wrapper:hover {
|
|
85
94
|
border: none !important;
|
|
86
95
|
box-shadow: none !important;
|
|
87
96
|
}
|
|
88
97
|
|
|
98
|
+
/* 预览模式:移除所有 input 相关元素的边框(更全面的覆盖) */
|
|
99
|
+
.form-create.is-preview .ant-input-affix-wrapper,
|
|
100
|
+
.form-create.is-preview .ant-input-affix-wrapper:hover,
|
|
101
|
+
.form-create.is-preview .ant-input-affix-wrapper-focused,
|
|
102
|
+
.form-create.is-preview .ant-input-affix-wrapper-disabled,
|
|
103
|
+
.form-create.is-preview .ant-input-wrapper .ant-input,
|
|
104
|
+
.form-create.is-preview .ant-input-group-addon,
|
|
105
|
+
.form-create.is-preview .ant-input-group .ant-input,
|
|
106
|
+
.form-create.is-preview input.ant-input,
|
|
107
|
+
.form-create.is-preview textarea.ant-input {
|
|
108
|
+
border: none !important;
|
|
109
|
+
border-width: 0 !important;
|
|
110
|
+
box-shadow: none !important;
|
|
111
|
+
outline: none !important;
|
|
112
|
+
background: transparent !important;
|
|
113
|
+
}
|
|
114
|
+
|
|
89
115
|
/* 隐藏字数限制等提示信息 */
|
|
90
116
|
.form-create.is-preview .ant-input-character-count,
|
|
91
117
|
.form-create.is-preview .ant-textarea-character-count,
|
|
@@ -117,6 +143,16 @@
|
|
|
117
143
|
pointer-events: none !important;
|
|
118
144
|
}
|
|
119
145
|
|
|
146
|
+
/* 预览模式:允许 textarea 交互(用于复制文本) */
|
|
147
|
+
.form-create.is-preview textarea.ant-input {
|
|
148
|
+
pointer-events: auto !important;
|
|
149
|
+
user-select: text !important;
|
|
150
|
+
-webkit-user-select: text !important;
|
|
151
|
+
-moz-user-select: text !important;
|
|
152
|
+
-ms-user-select: text !important;
|
|
153
|
+
cursor: text !important;
|
|
154
|
+
}
|
|
155
|
+
|
|
120
156
|
/* 预览模式:允许富文本编辑器容器滚动 */
|
|
121
157
|
.form-create.is-preview .w-e-text-container {
|
|
122
158
|
pointer-events: auto !important;
|
|
@@ -273,6 +309,39 @@
|
|
|
273
309
|
cursor: default !important;
|
|
274
310
|
}
|
|
275
311
|
|
|
312
|
+
/* 预览模式:textarea 自适应高度且只读可复制 */
|
|
313
|
+
.form-create.is-preview textarea.ant-input,
|
|
314
|
+
.form-create.is-preview .ant-textarea {
|
|
315
|
+
/* 允许文本选择,用于复制 */
|
|
316
|
+
user-select: text !important;
|
|
317
|
+
-webkit-user-select: text !important;
|
|
318
|
+
-moz-user-select: text !important;
|
|
319
|
+
-ms-user-select: text !important;
|
|
320
|
+
/* 允许交互,用于复制 */
|
|
321
|
+
pointer-events: auto !important;
|
|
322
|
+
cursor: text !important;
|
|
323
|
+
/* 移除滚动条(因为内容会自适应显示) */
|
|
324
|
+
overflow: hidden !important;
|
|
325
|
+
overflow-y: hidden !important;
|
|
326
|
+
overflow-x: hidden !important;
|
|
327
|
+
/* 确保只读状态下仍可正常显示和选择 */
|
|
328
|
+
resize: none !important;
|
|
329
|
+
/* 确保 textarea 能够根据内容自动调整高度 */
|
|
330
|
+
box-sizing: border-box !important;
|
|
331
|
+
/* 移除固定高度限制,让 JavaScript 动态设置 */
|
|
332
|
+
min-height: auto !important;
|
|
333
|
+
max-height: none !important;
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
/* 预览模式:textarea 只读状态样式 */
|
|
337
|
+
.form-create.is-preview textarea.ant-input[readonly],
|
|
338
|
+
.form-create.is-preview .ant-textarea[readonly] {
|
|
339
|
+
opacity: 1 !important;
|
|
340
|
+
color: inherit !important;
|
|
341
|
+
background-color: transparent !important;
|
|
342
|
+
cursor: text !important;
|
|
343
|
+
}
|
|
344
|
+
|
|
276
345
|
/* 预览模式:防止选择器显示为禁用状态 */
|
|
277
346
|
.form-create.is-preview .ant-select-disabled .ant-select-selector {
|
|
278
347
|
opacity: 1 !important;
|
|
@@ -314,7 +383,7 @@
|
|
|
314
383
|
max-height: none !important;
|
|
315
384
|
}
|
|
316
385
|
|
|
317
|
-
/*
|
|
386
|
+
/* 富文本内容只读:允许选择文本和点击链接,但禁止编辑 */
|
|
318
387
|
.form-create.is-preview .w-e-text p,
|
|
319
388
|
.form-create.is-preview .w-e-text div,
|
|
320
389
|
.form-create.is-preview .w-e-text span,
|
|
@@ -327,19 +396,47 @@
|
|
|
327
396
|
.form-create.is-preview .w-e-text h4,
|
|
328
397
|
.form-create.is-preview .w-e-text h5,
|
|
329
398
|
.form-create.is-preview .w-e-text h6,
|
|
330
|
-
.form-create.is-preview .w-e-text a,
|
|
331
|
-
.form-create.is-preview .w-e-text img,
|
|
332
399
|
.form-create.is-preview .w-e-text table,
|
|
333
400
|
.form-create.is-preview .w-e-text tr,
|
|
334
401
|
.form-create.is-preview .w-e-text td,
|
|
335
402
|
.form-create.is-preview .w-e-text th {
|
|
336
|
-
|
|
403
|
+
/* 允许文本选择,用于复制 */
|
|
404
|
+
user-select: text !important;
|
|
405
|
+
-webkit-user-select: text !important;
|
|
406
|
+
-moz-user-select: text !important;
|
|
407
|
+
-ms-user-select: text !important;
|
|
408
|
+
/* 阻止编辑,但不阻止交互 */
|
|
409
|
+
pointer-events: auto !important;
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
/* 允许链接可以点击 */
|
|
413
|
+
.form-create.is-preview .w-e-text a {
|
|
414
|
+
pointer-events: auto !important;
|
|
415
|
+
cursor: pointer !important;
|
|
416
|
+
user-select: text !important;
|
|
417
|
+
-webkit-user-select: text !important;
|
|
418
|
+
-moz-user-select: text !important;
|
|
419
|
+
-ms-user-select: text !important;
|
|
420
|
+
text-decoration: underline !important;
|
|
421
|
+
}
|
|
422
|
+
|
|
423
|
+
/* 允许图片可以查看 */
|
|
424
|
+
.form-create.is-preview .w-e-text img {
|
|
425
|
+
pointer-events: auto !important;
|
|
337
426
|
user-select: none !important;
|
|
338
427
|
-webkit-user-select: none !important;
|
|
339
428
|
-moz-user-select: none !important;
|
|
340
429
|
-ms-user-select: none !important;
|
|
341
430
|
}
|
|
342
431
|
|
|
432
|
+
/* 禁止编辑:通过 contenteditable 属性控制 */
|
|
433
|
+
.form-create.is-preview .w-e-text {
|
|
434
|
+
user-select: text !important;
|
|
435
|
+
-webkit-user-select: text !important;
|
|
436
|
+
-moz-user-select: text !important;
|
|
437
|
+
-ms-user-select: text !important;
|
|
438
|
+
}
|
|
439
|
+
|
|
343
440
|
/* 预览模式:禁用按钮点击 */
|
|
344
441
|
.form-create.is-preview .ant-btn {
|
|
345
442
|
pointer-events: none !important;
|