@tmagic/editor 1.4.0-beta.2 → 1.4.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/dist/style.css +8 -20
- package/dist/tmagic-editor.js +829 -742
- package/dist/tmagic-editor.umd.cjs +832 -745
- package/package.json +11 -11
- package/src/components/CodeBlockEditor.vue +50 -73
- package/src/components/FloatingBox.vue +24 -9
- package/src/fields/DataSourceFieldSelect.vue +2 -1
- package/src/fields/DataSourceFields.vue +55 -30
- package/src/fields/DataSourceInput.vue +6 -2
- package/src/fields/DataSourceMocks.vue +35 -17
- package/src/hooks/use-editor-content-height.ts +1 -1
- package/src/hooks/use-float-box.ts +14 -8
- package/src/hooks/use-next-float-box-position.ts +29 -0
- package/src/layouts/CodeEditor.vue +3 -6
- package/src/layouts/PropsPanel.vue +4 -2
- package/src/layouts/sidebar/Sidebar.vue +7 -10
- package/src/layouts/sidebar/code-block/CodeBlockListPanel.vue +1 -3
- package/src/layouts/sidebar/data-source/DataSourceConfigPanel.vue +36 -22
- package/src/layouts/sidebar/data-source/DataSourceListPanel.vue +1 -6
- package/src/layouts/workspace/viewer/StageOverlay.vue +3 -1
- package/src/theme/code-block.scss +0 -14
- package/src/theme/component-list-panel.scss +0 -1
- package/src/theme/icon.scss +7 -1
- package/src/theme/layer-panel.scss +0 -1
- package/src/theme/sidebar.scss +0 -7
- package/src/type.ts +0 -6
- package/types/components/CodeBlockEditor.vue.d.ts +0 -7
- package/types/fields/DataSourceFields.vue.d.ts +84 -28
- package/types/fields/DataSourceMocks.vue.d.ts +80 -28
- package/types/hooks/use-code-block-edit.d.ts +0 -9
- package/types/hooks/use-data-source-method.d.ts +0 -9
- package/types/hooks/use-next-float-box-position.d.ts +9 -0
- package/types/layouts/sidebar/code-block/CodeBlockListPanel.vue.d.ts +1 -3
- package/types/layouts/sidebar/data-source/DataSourceConfigPanel.vue.d.ts +34 -22
- package/types/layouts/sidebar/data-source/DataSourceListPanel.vue.d.ts +2 -15
- package/types/type.d.ts +0 -5
package/package.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "1.4.0
|
|
2
|
+
"version": "1.4.0",
|
|
3
3
|
"name": "@tmagic/editor",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"sideEffects": [
|
|
@@ -42,14 +42,14 @@
|
|
|
42
42
|
"dependencies": {
|
|
43
43
|
"@babel/core": "^7.18.0",
|
|
44
44
|
"@element-plus/icons-vue": "^2.3.1",
|
|
45
|
-
"@tmagic/core": "1.4.0
|
|
46
|
-
"@tmagic/dep": "1.4.0
|
|
47
|
-
"@tmagic/design": "1.4.0
|
|
48
|
-
"@tmagic/form": "1.4.0
|
|
49
|
-
"@tmagic/schema": "1.4.0
|
|
50
|
-
"@tmagic/stage": "1.4.0
|
|
51
|
-
"@tmagic/table": "1.4.0
|
|
52
|
-
"@tmagic/utils": "1.4.0
|
|
45
|
+
"@tmagic/core": "1.4.0",
|
|
46
|
+
"@tmagic/dep": "1.4.0",
|
|
47
|
+
"@tmagic/design": "1.4.0",
|
|
48
|
+
"@tmagic/form": "1.4.0",
|
|
49
|
+
"@tmagic/schema": "1.4.0",
|
|
50
|
+
"@tmagic/stage": "1.4.0",
|
|
51
|
+
"@tmagic/table": "1.4.0",
|
|
52
|
+
"@tmagic/utils": "1.4.0",
|
|
53
53
|
"buffer": "^6.0.3",
|
|
54
54
|
"color": "^3.1.3",
|
|
55
55
|
"emmet-monaco-es": "^5.3.0",
|
|
@@ -63,8 +63,8 @@
|
|
|
63
63
|
"vue": "^3.4.21"
|
|
64
64
|
},
|
|
65
65
|
"peerDependencies": {
|
|
66
|
-
"@tmagic/design": "1.4.0
|
|
67
|
-
"@tmagic/form": "1.4.0
|
|
66
|
+
"@tmagic/design": "1.4.0",
|
|
67
|
+
"@tmagic/form": "1.4.0",
|
|
68
68
|
"monaco-editor": "^0.47.0",
|
|
69
69
|
"vue": "^3.4.21"
|
|
70
70
|
},
|
|
@@ -9,59 +9,57 @@
|
|
|
9
9
|
:before-close="beforeClose"
|
|
10
10
|
>
|
|
11
11
|
<template #body>
|
|
12
|
-
<
|
|
12
|
+
<MFormBox
|
|
13
|
+
class="m-editor-code-block-editor"
|
|
14
|
+
ref="formBox"
|
|
15
|
+
label-width="80px"
|
|
16
|
+
:close-on-press-escape="false"
|
|
17
|
+
:title="content.name"
|
|
18
|
+
:config="functionConfig"
|
|
19
|
+
:values="content"
|
|
20
|
+
:disabled="disabled"
|
|
21
|
+
style="height: 100%"
|
|
22
|
+
@change="changeHandler"
|
|
23
|
+
@submit="submitForm"
|
|
24
|
+
@error="errorHandler"
|
|
25
|
+
@closed="closedHandler"
|
|
26
|
+
>
|
|
27
|
+
<template #left>
|
|
28
|
+
<TMagicButton v-if="!disabled" type="primary" link @click="difVisible = true">查看修改</TMagicButton>
|
|
29
|
+
</template>
|
|
30
|
+
</MFormBox>
|
|
13
31
|
</template>
|
|
14
32
|
</FloatingBox>
|
|
15
33
|
|
|
16
|
-
<Teleport
|
|
17
|
-
<
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
+
<Teleport to="body">
|
|
35
|
+
<TMagicDialog title="查看修改" v-model="difVisible" fullscreen>
|
|
36
|
+
<div style="display: flex; margin-bottom: 10px">
|
|
37
|
+
<div style="flex: 1"><TMagicTag size="small" type="info">修改前</TMagicTag></div>
|
|
38
|
+
<div style="flex: 1"><TMagicTag size="small" type="success">修改后</TMagicTag></div>
|
|
39
|
+
</div>
|
|
40
|
+
|
|
41
|
+
<CodeEditor
|
|
42
|
+
v-if="difVisible"
|
|
43
|
+
ref="magicVsEditor"
|
|
44
|
+
type="diff"
|
|
45
|
+
language="json"
|
|
46
|
+
:initValues="content.content"
|
|
47
|
+
:modifiedValues="formBox?.form?.values.content"
|
|
48
|
+
:style="`height: ${windowRect.height - 150}px`"
|
|
49
|
+
></CodeEditor>
|
|
50
|
+
|
|
51
|
+
<template #footer>
|
|
52
|
+
<span class="dialog-footer">
|
|
53
|
+
<TMagicButton size="small" @click="difVisible = false">取消</TMagicButton>
|
|
54
|
+
<TMagicButton size="small" type="primary" @click="diffChange">确定</TMagicButton>
|
|
55
|
+
</span>
|
|
34
56
|
</template>
|
|
35
|
-
</
|
|
57
|
+
</TMagicDialog>
|
|
36
58
|
</Teleport>
|
|
37
|
-
|
|
38
|
-
<TMagicDialog v-model="difVisible" title="查看修改" fullscreen>
|
|
39
|
-
<div style="display: flex; margin-bottom: 10px">
|
|
40
|
-
<div style="flex: 1"><TMagicTag size="small" type="info">修改前</TMagicTag></div>
|
|
41
|
-
<div style="flex: 1"><TMagicTag size="small" type="success">修改后</TMagicTag></div>
|
|
42
|
-
</div>
|
|
43
|
-
|
|
44
|
-
<CodeEditor
|
|
45
|
-
v-if="difVisible"
|
|
46
|
-
ref="magicVsEditor"
|
|
47
|
-
type="diff"
|
|
48
|
-
language="json"
|
|
49
|
-
:initValues="content.content"
|
|
50
|
-
:modifiedValues="formBox?.form?.values.content"
|
|
51
|
-
:style="`height: ${windowRect.height - 150}px`"
|
|
52
|
-
></CodeEditor>
|
|
53
|
-
|
|
54
|
-
<template #footer>
|
|
55
|
-
<span class="dialog-footer">
|
|
56
|
-
<TMagicButton size="small" @click="difVisible = false">取消</TMagicButton>
|
|
57
|
-
<TMagicButton size="small" type="primary" @click="diffChange">确定</TMagicButton>
|
|
58
|
-
</span>
|
|
59
|
-
</template>
|
|
60
|
-
</TMagicDialog>
|
|
61
59
|
</template>
|
|
62
60
|
|
|
63
61
|
<script lang="ts" setup>
|
|
64
|
-
import { computed, inject,
|
|
62
|
+
import { computed, inject, Ref, ref } from 'vue';
|
|
65
63
|
|
|
66
64
|
import { TMagicButton, TMagicDialog, tMagicMessage, tMagicMessageBox, TMagicTag } from '@tmagic/design';
|
|
67
65
|
import { ColumnConfig, FormConfig, FormState, MFormBox } from '@tmagic/form';
|
|
@@ -69,9 +67,10 @@ import type { CodeBlockContent } from '@tmagic/schema';
|
|
|
69
67
|
|
|
70
68
|
import FloatingBox from '@editor/components/FloatingBox.vue';
|
|
71
69
|
import { useEditorContentHeight } from '@editor/hooks/use-editor-content-height';
|
|
70
|
+
import { useNextFloatBoxPosition } from '@editor/hooks/use-next-float-box-position';
|
|
72
71
|
import { useWindowRect } from '@editor/hooks/use-window-rect';
|
|
73
72
|
import CodeEditor from '@editor/layouts/CodeEditor.vue';
|
|
74
|
-
import type { Services
|
|
73
|
+
import type { Services } from '@editor/type';
|
|
75
74
|
import { getConfig } from '@editor/utils/config';
|
|
76
75
|
|
|
77
76
|
defineOptions({
|
|
@@ -86,7 +85,6 @@ const props = defineProps<{
|
|
|
86
85
|
disabled?: boolean;
|
|
87
86
|
isDataSource?: boolean;
|
|
88
87
|
dataSourceType?: string;
|
|
89
|
-
slideType?: SlideType;
|
|
90
88
|
}>();
|
|
91
89
|
|
|
92
90
|
const emit = defineEmits<{
|
|
@@ -229,7 +227,6 @@ const changeHandler = (values: CodeBlockContent) => {
|
|
|
229
227
|
|
|
230
228
|
const beforeClose = (done: (cancel?: boolean) => void) => {
|
|
231
229
|
if (!changedValue.value) {
|
|
232
|
-
editVisible.value = false;
|
|
233
230
|
done();
|
|
234
231
|
return;
|
|
235
232
|
}
|
|
@@ -242,12 +239,10 @@ const beforeClose = (done: (cancel?: boolean) => void) => {
|
|
|
242
239
|
})
|
|
243
240
|
.then(() => {
|
|
244
241
|
changedValue.value && submitForm(changedValue.value);
|
|
245
|
-
editVisible.value = false;
|
|
246
242
|
done();
|
|
247
243
|
})
|
|
248
244
|
.catch((action: string) => {
|
|
249
245
|
if (action === 'cancel') {
|
|
250
|
-
editVisible.value = false;
|
|
251
246
|
}
|
|
252
247
|
done(action === 'cancel');
|
|
253
248
|
});
|
|
@@ -257,35 +252,17 @@ const closedHandler = () => {
|
|
|
257
252
|
changedValue.value = undefined;
|
|
258
253
|
};
|
|
259
254
|
|
|
260
|
-
const
|
|
261
|
-
const
|
|
262
|
-
|
|
263
|
-
const boxPosition = computed(() => {
|
|
264
|
-
const columnWidth = services?.uiService?.get('columnWidth');
|
|
265
|
-
const navMenuRect = services?.uiService?.get('navMenuRect');
|
|
266
|
-
return {
|
|
267
|
-
left: columnWidth?.left ?? 0,
|
|
268
|
-
top: (navMenuRect?.top ?? 0) + (navMenuRect?.height ?? 0),
|
|
269
|
-
};
|
|
270
|
-
});
|
|
255
|
+
const parentFloating = inject<Ref<HTMLDivElement | null>>('parentFloating', ref(null));
|
|
256
|
+
const { boxPosition, calcBoxPosition } = useNextFloatBoxPosition(services?.uiService, parentFloating);
|
|
271
257
|
|
|
272
258
|
defineExpose({
|
|
273
259
|
async show() {
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
await nextTick();
|
|
277
|
-
}
|
|
278
|
-
|
|
279
|
-
editVisible.value = true;
|
|
260
|
+
calcBoxPosition();
|
|
261
|
+
boxVisible.value = true;
|
|
280
262
|
},
|
|
281
263
|
|
|
282
264
|
async hide() {
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
if (props.slideType !== 'box') {
|
|
286
|
-
await nextTick();
|
|
287
|
-
boxVisible.value = false;
|
|
288
|
-
}
|
|
265
|
+
boxVisible.value = false;
|
|
289
266
|
},
|
|
290
267
|
});
|
|
291
268
|
</script>
|
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
<span>{{ title }}</span>
|
|
7
7
|
</slot>
|
|
8
8
|
<div>
|
|
9
|
-
<TMagicButton link size="small"
|
|
9
|
+
<TMagicButton link size="small" @click="closeHandler"><MIcon :icon="Close"></MIcon></TMagicButton>
|
|
10
10
|
</div>
|
|
11
11
|
</div>
|
|
12
12
|
<div class="m-editor-float-box-body" :style="{ height: `${bodyHeight}px` }">
|
|
@@ -17,12 +17,15 @@
|
|
|
17
17
|
</template>
|
|
18
18
|
|
|
19
19
|
<script setup lang="ts">
|
|
20
|
-
import { computed, nextTick, onBeforeUnmount, ref, watch } from 'vue';
|
|
20
|
+
import { computed, inject, nextTick, onBeforeUnmount, provide, ref, watch } from 'vue';
|
|
21
21
|
import { Close } from '@element-plus/icons-vue';
|
|
22
22
|
import VanillaMoveable from 'moveable';
|
|
23
23
|
|
|
24
24
|
import { TMagicButton, useZIndex } from '@tmagic/design';
|
|
25
25
|
|
|
26
|
+
import MIcon from '@editor/components/Icon.vue';
|
|
27
|
+
import type { Services } from '@editor/type';
|
|
28
|
+
|
|
26
29
|
interface Position {
|
|
27
30
|
left: number;
|
|
28
31
|
top: number;
|
|
@@ -48,7 +51,7 @@ const target = ref<HTMLDivElement>();
|
|
|
48
51
|
const titleEl = ref<HTMLDivElement>();
|
|
49
52
|
|
|
50
53
|
const zIndex = useZIndex();
|
|
51
|
-
const curZIndex = ref<number>(
|
|
54
|
+
const curZIndex = ref<number>(0);
|
|
52
55
|
|
|
53
56
|
const titleHeight = ref(0);
|
|
54
57
|
const bodyHeight = computed(() => {
|
|
@@ -63,12 +66,21 @@ const bodyHeight = computed(() => {
|
|
|
63
66
|
return 'auto';
|
|
64
67
|
});
|
|
65
68
|
|
|
66
|
-
const
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
69
|
+
const services = inject<Services>('services');
|
|
70
|
+
const frameworkWidth = computed(() => services?.uiService.get('frameworkRect').width || 0);
|
|
71
|
+
const style = computed(() => {
|
|
72
|
+
let { left } = props.position;
|
|
73
|
+
if (width.value) {
|
|
74
|
+
left = left + width.value > frameworkWidth.value ? frameworkWidth.value - width.value : left;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
return {
|
|
78
|
+
left: `${left}px`,
|
|
79
|
+
top: `${props.position.top}px`,
|
|
80
|
+
width: width.value ? `${width.value}px` : 'auto',
|
|
81
|
+
height: height.value ? `${height.value}px` : 'auto',
|
|
82
|
+
};
|
|
83
|
+
});
|
|
72
84
|
|
|
73
85
|
let moveable: VanillaMoveable | null = null;
|
|
74
86
|
|
|
@@ -112,6 +124,7 @@ watch(
|
|
|
112
124
|
async (visible) => {
|
|
113
125
|
if (visible) {
|
|
114
126
|
await nextTick();
|
|
127
|
+
curZIndex.value = zIndex.nextZIndex();
|
|
115
128
|
|
|
116
129
|
const targetRect = target.value?.getBoundingClientRect();
|
|
117
130
|
if (targetRect) {
|
|
@@ -155,6 +168,8 @@ const nextZIndex = () => {
|
|
|
155
168
|
curZIndex.value = zIndex.nextZIndex();
|
|
156
169
|
};
|
|
157
170
|
|
|
171
|
+
provide('parentFloating', target);
|
|
172
|
+
|
|
158
173
|
defineExpose({
|
|
159
174
|
bodyHeight,
|
|
160
175
|
target,
|
|
@@ -19,9 +19,9 @@
|
|
|
19
19
|
style="margin-left: 5px"
|
|
20
20
|
link
|
|
21
21
|
:type="showDataSourceFieldSelect ? 'primary' : 'default'"
|
|
22
|
-
:icon="Coin"
|
|
23
22
|
:size="size"
|
|
24
23
|
@click="showDataSourceFieldSelect = !showDataSourceFieldSelect"
|
|
24
|
+
><MIcon :icon="Coin"></MIcon
|
|
25
25
|
></TMagicButton>
|
|
26
26
|
</div>
|
|
27
27
|
</template>
|
|
@@ -36,6 +36,7 @@ import { MCascader } from '@tmagic/form';
|
|
|
36
36
|
import type { DataSchema, DataSourceFieldType } from '@tmagic/schema';
|
|
37
37
|
import { DATA_SOURCE_FIELDS_SELECT_VALUE_PREFIX } from '@tmagic/utils';
|
|
38
38
|
|
|
39
|
+
import MIcon from '@editor/components/Icon.vue';
|
|
39
40
|
import type { DataSourceFieldSelectConfig, Services } from '@editor/type';
|
|
40
41
|
|
|
41
42
|
defineOptions({
|
|
@@ -7,39 +7,57 @@
|
|
|
7
7
|
<TMagicButton size="small" type="primary" :disabled="disabled" plain @click="newHandler()">添加</TMagicButton>
|
|
8
8
|
</div>
|
|
9
9
|
|
|
10
|
-
<
|
|
11
|
-
|
|
12
|
-
|
|
10
|
+
<FloatingBox
|
|
11
|
+
v-model:visible="addDialogVisible"
|
|
12
|
+
v-model:width="width"
|
|
13
|
+
v-model:height="editorHeight"
|
|
13
14
|
:title="fieldTitle"
|
|
14
|
-
:
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
15
|
+
:position="boxPosition"
|
|
16
|
+
>
|
|
17
|
+
<template #body>
|
|
18
|
+
<MFormBox
|
|
19
|
+
label-width="80px"
|
|
20
|
+
:title="fieldTitle"
|
|
21
|
+
:config="dataSourceFieldsConfig"
|
|
22
|
+
:values="fieldValues"
|
|
23
|
+
:parentValues="model[name]"
|
|
24
|
+
:disabled="disabled"
|
|
25
|
+
@submit="fieldChange"
|
|
26
|
+
></MFormBox>
|
|
27
|
+
</template>
|
|
28
|
+
</FloatingBox>
|
|
29
|
+
|
|
30
|
+
<FloatingBox
|
|
31
|
+
v-model:visible="addFromJsonDialogVisible"
|
|
32
|
+
v-model:width="width"
|
|
33
|
+
v-model:height="editorHeight"
|
|
24
34
|
title="快速添加数据定义"
|
|
25
|
-
:
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
35
|
+
:position="boxPosition"
|
|
36
|
+
>
|
|
37
|
+
<template #body>
|
|
38
|
+
<MFormBox
|
|
39
|
+
:config="jsonFromConfig"
|
|
40
|
+
:values="jsonFromValues"
|
|
41
|
+
:disabled="disabled"
|
|
42
|
+
@submit="addFromJsonFromChange"
|
|
43
|
+
></MFormBox>
|
|
44
|
+
</template>
|
|
45
|
+
</FloatingBox>
|
|
31
46
|
</div>
|
|
32
47
|
</template>
|
|
33
48
|
|
|
34
49
|
<script setup lang="ts">
|
|
35
|
-
import {
|
|
50
|
+
import { inject, Ref, ref } from 'vue';
|
|
36
51
|
|
|
37
52
|
import { TMagicButton, tMagicMessage, tMagicMessageBox } from '@tmagic/design';
|
|
38
|
-
import { type FieldProps, type FormConfig, type FormState,
|
|
53
|
+
import { type FieldProps, type FormConfig, type FormState, MFormBox } from '@tmagic/form';
|
|
39
54
|
import type { DataSchema } from '@tmagic/schema';
|
|
40
55
|
import { type ColumnConfig, MagicTable } from '@tmagic/table';
|
|
41
56
|
import { getDefaultValueFromFields } from '@tmagic/utils';
|
|
42
57
|
|
|
58
|
+
import FloatingBox from '@editor/components/FloatingBox.vue';
|
|
59
|
+
import { useEditorContentHeight } from '@editor/hooks';
|
|
60
|
+
import { useNextFloatBoxPosition } from '@editor/hooks/use-next-float-box-position';
|
|
43
61
|
import type { Services } from '@editor/type';
|
|
44
62
|
|
|
45
63
|
defineOptions({
|
|
@@ -61,17 +79,16 @@ const emit = defineEmits(['change']);
|
|
|
61
79
|
|
|
62
80
|
const services = inject<Services>('services');
|
|
63
81
|
|
|
64
|
-
const addDialog = ref<InstanceType<typeof MFormDrawer>>();
|
|
65
|
-
|
|
66
82
|
const fieldValues = ref<Record<string, any>>({});
|
|
67
83
|
const fieldTitle = ref('');
|
|
68
84
|
|
|
69
|
-
const width =
|
|
85
|
+
const width = defineModel<number>('width', { default: 670 });
|
|
70
86
|
|
|
71
87
|
const newHandler = () => {
|
|
72
88
|
fieldValues.value = {};
|
|
73
89
|
fieldTitle.value = '新增属性';
|
|
74
|
-
|
|
90
|
+
calcBoxPosition();
|
|
91
|
+
addDialogVisible.value = true;
|
|
75
92
|
};
|
|
76
93
|
|
|
77
94
|
const fieldChange = ({ index, ...value }: Record<string, any>) => {
|
|
@@ -81,7 +98,7 @@ const fieldChange = ({ index, ...value }: Record<string, any>) => {
|
|
|
81
98
|
props.model[props.name].push(value);
|
|
82
99
|
}
|
|
83
100
|
|
|
84
|
-
|
|
101
|
+
addDialogVisible.value = false;
|
|
85
102
|
|
|
86
103
|
emit('change', props.model[props.name]);
|
|
87
104
|
};
|
|
@@ -122,7 +139,8 @@ const fieldColumns: ColumnConfig[] = [
|
|
|
122
139
|
index,
|
|
123
140
|
};
|
|
124
141
|
fieldTitle.value = `编辑${row.title}`;
|
|
125
|
-
|
|
142
|
+
calcBoxPosition();
|
|
143
|
+
addDialogVisible.value = true;
|
|
126
144
|
},
|
|
127
145
|
},
|
|
128
146
|
{
|
|
@@ -220,7 +238,6 @@ const dataSourceFieldsConfig: FormConfig = [
|
|
|
220
238
|
},
|
|
221
239
|
];
|
|
222
240
|
|
|
223
|
-
const addFromJsonDialog = ref<InstanceType<typeof MFormDrawer>>();
|
|
224
241
|
const jsonFromConfig: FormConfig = [
|
|
225
242
|
{
|
|
226
243
|
name: 'data',
|
|
@@ -238,7 +255,8 @@ const jsonFromValues = ref({
|
|
|
238
255
|
|
|
239
256
|
const newFromJsonHandler = () => {
|
|
240
257
|
jsonFromValues.value.data = getDefaultValueFromFields(props.model[props.name]);
|
|
241
|
-
|
|
258
|
+
calcBoxPosition();
|
|
259
|
+
addFromJsonDialogVisible.value = true;
|
|
242
260
|
};
|
|
243
261
|
|
|
244
262
|
const getValueType = (value: any) => {
|
|
@@ -288,11 +306,18 @@ const addFromJsonFromChange = ({ data }: { data: string }) => {
|
|
|
288
306
|
|
|
289
307
|
props.model[props.name] = getFieldsConfig(value, props.model[props.name]);
|
|
290
308
|
|
|
291
|
-
|
|
309
|
+
addFromJsonDialogVisible.value = false;
|
|
292
310
|
|
|
293
311
|
emit('change', props.model[props.name]);
|
|
294
312
|
} catch (e: any) {
|
|
295
313
|
tMagicMessage.error(e.message);
|
|
296
314
|
}
|
|
297
315
|
};
|
|
316
|
+
|
|
317
|
+
const addDialogVisible = defineModel<boolean>('visible', { default: false });
|
|
318
|
+
const addFromJsonDialogVisible = defineModel<boolean>('visible1', { default: false });
|
|
319
|
+
const { height: editorHeight } = useEditorContentHeight();
|
|
320
|
+
|
|
321
|
+
const parentFloating = inject<Ref<HTMLDivElement | null>>('parentFloating', ref(null));
|
|
322
|
+
const { boxPosition, calcBoxPosition } = useNextFloatBoxPosition(services?.uiService, parentFloating);
|
|
298
323
|
</script>
|
|
@@ -29,9 +29,13 @@
|
|
|
29
29
|
</div>
|
|
30
30
|
</template>
|
|
31
31
|
</component>
|
|
32
|
-
<div
|
|
32
|
+
<div
|
|
33
|
+
:class="`tmagic-data-source-input-text el-input t-input t-size-${size?.[0]} el-input--${size}`"
|
|
34
|
+
@mouseup="mouseupHandler"
|
|
35
|
+
v-else
|
|
36
|
+
>
|
|
33
37
|
<div :class="`tmagic-data-source-input-text-wrapper el-input__wrapper ${isFocused ? ' is-focus' : ''}`">
|
|
34
|
-
<div class="el-input__inner">
|
|
38
|
+
<div class="el-input__inner t-input__inner">
|
|
35
39
|
<template v-for="(item, index) in displayState">
|
|
36
40
|
<span :key="index" v-if="item.type === 'text'" style="margin-right: 2px">{{ item.value }}</span>
|
|
37
41
|
<TMagicTag :key="index" :size="size" v-if="item.type === 'var'">{{ item.value }}</TMagicTag>
|
|
@@ -6,32 +6,44 @@
|
|
|
6
6
|
<TMagicButton size="small" type="primary" :disabled="disabled" plain @click="newHandler()">添加</TMagicButton>
|
|
7
7
|
</div>
|
|
8
8
|
|
|
9
|
-
<
|
|
10
|
-
|
|
11
|
-
|
|
9
|
+
<FloatingBox
|
|
10
|
+
v-model:visible="addDialogVisible"
|
|
11
|
+
v-model:width="width"
|
|
12
|
+
v-model:height="editorHeight"
|
|
12
13
|
:title="drawerTitle"
|
|
13
|
-
:
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
14
|
+
:position="boxPosition"
|
|
15
|
+
>
|
|
16
|
+
<template #body>
|
|
17
|
+
<MFormBox
|
|
18
|
+
ref="addDialog"
|
|
19
|
+
label-width="120px"
|
|
20
|
+
:config="formConfig"
|
|
21
|
+
:values="formValues"
|
|
22
|
+
:parentValues="model[name]"
|
|
23
|
+
:disabled="disabled"
|
|
24
|
+
@submit="formChangeHandler"
|
|
25
|
+
></MFormBox>
|
|
26
|
+
</template>
|
|
27
|
+
</FloatingBox>
|
|
20
28
|
</div>
|
|
21
29
|
</template>
|
|
22
30
|
|
|
23
31
|
<script setup lang="ts">
|
|
24
|
-
import {
|
|
32
|
+
import { inject, Ref, ref } from 'vue';
|
|
25
33
|
|
|
26
34
|
import { TMagicButton, tMagicMessageBox, TMagicSwitch } from '@tmagic/design';
|
|
27
|
-
import { type FieldProps, type FormConfig, type FormState,
|
|
35
|
+
import { type FieldProps, type FormConfig, type FormState, MFormBox } from '@tmagic/form';
|
|
28
36
|
import type { MockSchema } from '@tmagic/schema';
|
|
29
37
|
import { type ColumnConfig, MagicTable } from '@tmagic/table';
|
|
30
38
|
import { getDefaultValueFromFields } from '@tmagic/utils';
|
|
31
39
|
|
|
40
|
+
import FloatingBox from '@editor/components/FloatingBox.vue';
|
|
41
|
+
import { useNextFloatBoxPosition } from '@editor/hooks/use-next-float-box-position';
|
|
32
42
|
import CodeEditor from '@editor/layouts/CodeEditor.vue';
|
|
33
43
|
import { Services } from '@editor/type';
|
|
34
44
|
|
|
45
|
+
import { useEditorContentHeight } from '..';
|
|
46
|
+
|
|
35
47
|
defineOptions({
|
|
36
48
|
name: 'MFieldsDataSourceMocks',
|
|
37
49
|
});
|
|
@@ -50,9 +62,8 @@ const props = withDefaults(
|
|
|
50
62
|
const emit = defineEmits(['change']);
|
|
51
63
|
|
|
52
64
|
const services = inject<Services>('services');
|
|
53
|
-
const width =
|
|
65
|
+
const width = defineModel<number>('width', { default: 670 });
|
|
54
66
|
|
|
55
|
-
const addDialog = ref<InstanceType<typeof MFormDrawer>>();
|
|
56
67
|
const drawerTitle = ref('');
|
|
57
68
|
const formValues = ref<Record<string, any>>({});
|
|
58
69
|
|
|
@@ -182,7 +193,8 @@ const columns: ColumnConfig[] = [
|
|
|
182
193
|
index,
|
|
183
194
|
};
|
|
184
195
|
drawerTitle.value = `编辑${row.title}`;
|
|
185
|
-
|
|
196
|
+
calcBoxPosition();
|
|
197
|
+
addDialogVisible.value = true;
|
|
186
198
|
},
|
|
187
199
|
},
|
|
188
200
|
{
|
|
@@ -206,7 +218,8 @@ const newHandler = () => {
|
|
|
206
218
|
enable: isFirstRow,
|
|
207
219
|
};
|
|
208
220
|
drawerTitle.value = '新增Mock';
|
|
209
|
-
|
|
221
|
+
calcBoxPosition();
|
|
222
|
+
addDialogVisible.value = true;
|
|
210
223
|
};
|
|
211
224
|
|
|
212
225
|
const formChangeHandler = ({ index, ...value }: Record<string, any>) => {
|
|
@@ -216,7 +229,7 @@ const formChangeHandler = ({ index, ...value }: Record<string, any>) => {
|
|
|
216
229
|
props.model[props.name].push(value);
|
|
217
230
|
}
|
|
218
231
|
|
|
219
|
-
|
|
232
|
+
addDialogVisible.value = false;
|
|
220
233
|
|
|
221
234
|
emit('change', props.model[props.name]);
|
|
222
235
|
};
|
|
@@ -234,4 +247,9 @@ const toggleValue = (row: MockSchema, key: 'enable' | 'useInEditor', value: bool
|
|
|
234
247
|
index,
|
|
235
248
|
});
|
|
236
249
|
};
|
|
250
|
+
|
|
251
|
+
const addDialogVisible = defineModel<boolean>('visible', { default: false });
|
|
252
|
+
const { height: editorHeight } = useEditorContentHeight();
|
|
253
|
+
const parentFloating = inject<Ref<HTMLDivElement | null>>('parentFloating', ref(null));
|
|
254
|
+
const { boxPosition, calcBoxPosition } = useNextFloatBoxPosition(services?.uiService, parentFloating);
|
|
237
255
|
</script>
|
|
@@ -10,7 +10,7 @@ export const useEditorContentHeight = () => {
|
|
|
10
10
|
|
|
11
11
|
const height = ref(0);
|
|
12
12
|
watchEffect(() => {
|
|
13
|
-
if (height.value > 0) return;
|
|
13
|
+
if (height.value > 0 && height.value === editorContentHeight.value) return;
|
|
14
14
|
height.value = editorContentHeight.value;
|
|
15
15
|
});
|
|
16
16
|
|
|
@@ -1,4 +1,6 @@
|
|
|
1
|
-
import { computed, ComputedRef, ref, watch } from 'vue';
|
|
1
|
+
import { computed, ComputedRef, inject, ref, watch } from 'vue';
|
|
2
|
+
|
|
3
|
+
import type { Services } from '@editor/type';
|
|
2
4
|
|
|
3
5
|
interface State {
|
|
4
6
|
status: boolean;
|
|
@@ -7,6 +9,8 @@ interface State {
|
|
|
7
9
|
}
|
|
8
10
|
|
|
9
11
|
export const useFloatBox = (slideKeys: ComputedRef<string[]>) => {
|
|
12
|
+
const services = inject<Services>('services');
|
|
13
|
+
|
|
10
14
|
const floatBoxStates = ref<{
|
|
11
15
|
[key in (typeof slideKeys.value)[number]]: State;
|
|
12
16
|
}>(
|
|
@@ -30,9 +34,10 @@ export const useFloatBox = (slideKeys: ComputedRef<string[]>) => {
|
|
|
30
34
|
|
|
31
35
|
const dragstartHandler = () => (isDragging.value = true);
|
|
32
36
|
const dragendHandler = (key: string, e: DragEvent) => {
|
|
37
|
+
const navMenuRect = services?.uiService?.get('navMenuRect');
|
|
33
38
|
floatBoxStates.value[key] = {
|
|
34
39
|
left: e.clientX,
|
|
35
|
-
top:
|
|
40
|
+
top: (navMenuRect?.top ?? 0) + (navMenuRect?.height ?? 0),
|
|
36
41
|
status: true,
|
|
37
42
|
};
|
|
38
43
|
isDragging.value = false;
|
|
@@ -47,12 +52,13 @@ export const useFloatBox = (slideKeys: ComputedRef<string[]>) => {
|
|
|
47
52
|
() => slideKeys.value,
|
|
48
53
|
(slideKeys) => {
|
|
49
54
|
slideKeys.forEach((key) => {
|
|
50
|
-
if (floatBoxStates.value[key])
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
55
|
+
if (!floatBoxStates.value[key]) {
|
|
56
|
+
floatBoxStates.value[key] = {
|
|
57
|
+
status: false,
|
|
58
|
+
top: 0,
|
|
59
|
+
left: 0,
|
|
60
|
+
};
|
|
61
|
+
}
|
|
56
62
|
});
|
|
57
63
|
},
|
|
58
64
|
{
|