@tmagic/editor 1.0.0-beta.11 → 1.0.0-beta.12
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 +1 -0
- package/dist/tmagic-editor.es.js +69 -14
- package/dist/tmagic-editor.es.js.map +1 -1
- package/dist/tmagic-editor.umd.js +72 -17
- package/dist/tmagic-editor.umd.js.map +1 -1
- package/dist/types/src/layouts/sidebar/ComponentListPanel.vue.d.ts +1 -1
- package/dist/types/src/layouts/workspace/Workspace.vue.d.ts +2 -1
- package/dist/types/src/services/props.d.ts +1 -1
- package/dist/types/src/type.d.ts +3 -1
- package/dist/types/src/utils/editor.d.ts +2 -1
- package/package.json +17 -7
- package/src/layouts/PropsPanel.vue +1 -1
- package/src/layouts/sidebar/ComponentListPanel.vue +2 -2
- package/src/layouts/sidebar/LayerMenu.vue +1 -0
- package/src/layouts/workspace/Workspace.vue +48 -3
- package/src/services/editor.ts +7 -2
- package/src/services/props.ts +2 -1
- package/src/type.ts +3 -1
- package/src/utils/editor.ts +25 -4
- package/src/utils/props.ts +1 -1
|
@@ -7,6 +7,6 @@ declare const _default: DefineComponent<{}, {
|
|
|
7
7
|
items: ComponentItem[];
|
|
8
8
|
title: string;
|
|
9
9
|
}[] | undefined>;
|
|
10
|
-
appendComponent({ text, type,
|
|
10
|
+
appendComponent({ text, type, data }: ComponentItem): void;
|
|
11
11
|
}, {}, {}, {}, ComponentOptionsMixin, ComponentOptionsMixin, EmitsOptions, string, VNodeProps & AllowedComponentProps & ComponentCustomProps, Readonly<ExtractPropTypes<{}>>, {}>;
|
|
12
12
|
export default _default;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { DefineComponent, ComputedRef, ComponentOptionsMixin, VNodeProps, AllowedComponentProps, ComponentCustomProps, ExtractPropTypes, PropType } from 'vue';
|
|
1
|
+
import type { DefineComponent, Ref, ComputedRef, ComponentOptionsMixin, VNodeProps, AllowedComponentProps, ComponentCustomProps, ExtractPropTypes, PropType } from 'vue';
|
|
2
2
|
import type { MPage } from '@tmagic/schema';
|
|
3
3
|
import type { MoveableOptions } from '@tmagic/stage';
|
|
4
4
|
import StageCore from '@tmagic/stage';
|
|
@@ -14,6 +14,7 @@ declare const _default: DefineComponent<{
|
|
|
14
14
|
type: PropType<(el: HTMLElement) => boolean | Promise<boolean>>;
|
|
15
15
|
};
|
|
16
16
|
}, {
|
|
17
|
+
workspace: Ref<HTMLDivElement | undefined>;
|
|
17
18
|
page: ComputedRef<MPage | undefined>;
|
|
18
19
|
}, unknown, {}, {}, ComponentOptionsMixin, ComponentOptionsMixin, Record<string, any>, string, VNodeProps & AllowedComponentProps & ComponentCustomProps, Readonly<ExtractPropTypes<{
|
|
19
20
|
runtimeUrl: StringConstructor;
|
|
@@ -29,7 +29,7 @@ declare class Props extends BaseService {
|
|
|
29
29
|
* @param type 组件类型
|
|
30
30
|
* @returns 组件初始值
|
|
31
31
|
*/
|
|
32
|
-
getPropsValue(type: string): Promise<MComponent>;
|
|
32
|
+
getPropsValue(type: string, defaultValue?: {}): Promise<MComponent>;
|
|
33
33
|
}
|
|
34
34
|
export declare type PropsService = Props;
|
|
35
35
|
declare const _default: Props;
|
package/dist/types/src/type.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import type { MApp, MContainer, MNode, MPage } from '@tmagic/schema';
|
|
2
|
+
import type StageCore from '@tmagic/stage';
|
|
2
3
|
import { Layout } from '../type';
|
|
3
4
|
export declare const COPY_STORAGE_KEY = "$MagicEditorCopyData";
|
|
4
5
|
export declare const generateId: (type: string | number) => string;
|
|
@@ -38,7 +39,7 @@ export declare const setNewItemId: (config: MNode, parent?: MPage | undefined) =
|
|
|
38
39
|
export declare const isFixed: (node: MNode) => boolean;
|
|
39
40
|
export declare const getNodeIndex: (node: MNode, parent: MContainer) => number;
|
|
40
41
|
export declare const toRelative: (node: MNode) => MNode;
|
|
41
|
-
export declare const initPosition: (node: MNode, layout: Layout) => MNode;
|
|
42
|
+
export declare const initPosition: (node: MNode, layout: Layout, parentNode: MNode, stage: StageCore) => MNode;
|
|
42
43
|
export declare const setLayout: (node: MNode, layout: Layout) => MNode;
|
|
43
44
|
export declare const change2Fixed: (node: MNode, root: MApp) => MNode;
|
|
44
45
|
export declare const Fixed2Other: (node: MNode, root: MApp, getLayout: (node: MNode) => Promise<Layout>) => Promise<MNode>;
|
package/package.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "1.0.0-beta.
|
|
2
|
+
"version": "1.0.0-beta.12",
|
|
3
3
|
"name": "@tmagic/editor",
|
|
4
4
|
"sideEffects": false,
|
|
5
5
|
"main": "dist/tmagic-editor.umd.js",
|
|
@@ -26,16 +26,26 @@
|
|
|
26
26
|
"type": "git",
|
|
27
27
|
"url": "https://github.com/Tencent/tmagic-editor.git"
|
|
28
28
|
},
|
|
29
|
+
"homepage": "https://tencent.github.io/tmagic-editor/docs/",
|
|
30
|
+
"keywords": [
|
|
31
|
+
"editor",
|
|
32
|
+
"drag",
|
|
33
|
+
"resize",
|
|
34
|
+
"vue",
|
|
35
|
+
"vue3",
|
|
36
|
+
"typescript"
|
|
37
|
+
],
|
|
29
38
|
"dependencies": {
|
|
30
39
|
"@element-plus/icons": "0.0.11",
|
|
31
|
-
"@tmagic/core": "^1.0.0-beta.
|
|
32
|
-
"@tmagic/form": "^1.0.0-beta.
|
|
33
|
-
"@tmagic/schema": "^1.0.0-beta.
|
|
34
|
-
"@tmagic/stage": "^1.0.0-beta.
|
|
35
|
-
"@tmagic/utils": "^1.0.0-beta.
|
|
40
|
+
"@tmagic/core": "^1.0.0-beta.12",
|
|
41
|
+
"@tmagic/form": "^1.0.0-beta.12",
|
|
42
|
+
"@tmagic/schema": "^1.0.0-beta.12",
|
|
43
|
+
"@tmagic/stage": "^1.0.0-beta.12",
|
|
44
|
+
"@tmagic/utils": "^1.0.0-beta.12",
|
|
36
45
|
"color": "^3.1.3",
|
|
37
46
|
"element-plus": "^2.1.7",
|
|
38
47
|
"events": "^3.3.0",
|
|
48
|
+
"keycon": "^1.1.2",
|
|
39
49
|
"lodash-es": "^4.17.21",
|
|
40
50
|
"monaco-editor": "^0.32.1",
|
|
41
51
|
"serialize-javascript": "^6.0.0",
|
|
@@ -56,5 +66,5 @@
|
|
|
56
66
|
"vite-plugin-dts": "^0.9.6",
|
|
57
67
|
"vue-tsc": "^0.0.24"
|
|
58
68
|
},
|
|
59
|
-
"gitHead": "
|
|
69
|
+
"gitHead": "ae00dd242d593ac8f57ffcd34e10e99399c7d00b"
|
|
60
70
|
}
|
|
@@ -39,9 +39,9 @@ export default defineComponent({
|
|
|
39
39
|
return;
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
-
values.value = node.value;
|
|
43
42
|
const type = node.value.type || (node.value.items ? 'container' : 'text');
|
|
44
43
|
curFormConfig.value = (await services?.propsService.getPropsConfig(type)) || [];
|
|
44
|
+
values.value = node.value;
|
|
45
45
|
};
|
|
46
46
|
|
|
47
47
|
watchEffect(init);
|
|
@@ -56,11 +56,11 @@ export default defineComponent({
|
|
|
56
56
|
collapseValue,
|
|
57
57
|
list,
|
|
58
58
|
|
|
59
|
-
appendComponent({ text, type,
|
|
59
|
+
appendComponent({ text, type, data = {} }: ComponentItem): void {
|
|
60
60
|
services?.editorService.add({
|
|
61
61
|
name: text,
|
|
62
62
|
type,
|
|
63
|
-
...
|
|
63
|
+
...data,
|
|
64
64
|
});
|
|
65
65
|
},
|
|
66
66
|
};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
<template>
|
|
2
|
-
<div class="m-editor-workspace">
|
|
2
|
+
<div class="m-editor-workspace" tabindex="1" ref="workspace">
|
|
3
3
|
<magic-stage
|
|
4
4
|
:key="page?.id"
|
|
5
5
|
:runtime-url="runtimeUrl"
|
|
@@ -18,9 +18,10 @@
|
|
|
18
18
|
</template>
|
|
19
19
|
|
|
20
20
|
<script lang="ts">
|
|
21
|
-
import { computed, defineComponent, inject, PropType } from 'vue';
|
|
21
|
+
import { computed, defineComponent, inject, onMounted, onUnmounted, PropType, ref } from 'vue';
|
|
22
|
+
import KeyController from 'keycon';
|
|
22
23
|
|
|
23
|
-
import type { MPage } from '@tmagic/schema';
|
|
24
|
+
import type { MNode, MPage } from '@tmagic/schema';
|
|
24
25
|
import type { MoveableOptions } from '@tmagic/stage';
|
|
25
26
|
import StageCore from '@tmagic/stage';
|
|
26
27
|
|
|
@@ -55,8 +56,52 @@ export default defineComponent({
|
|
|
55
56
|
|
|
56
57
|
setup() {
|
|
57
58
|
const services = inject<Services>('services');
|
|
59
|
+
const workspace = ref<HTMLDivElement>();
|
|
60
|
+
const node = computed(() => services?.editorService.get<MNode>('node'));
|
|
61
|
+
let keycon: KeyController;
|
|
62
|
+
|
|
63
|
+
const mouseenterHandler = () => {
|
|
64
|
+
workspace.value?.focus();
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
const mouseleaveHandler = () => {
|
|
68
|
+
workspace.value?.blur();
|
|
69
|
+
};
|
|
70
|
+
|
|
71
|
+
onMounted(() => {
|
|
72
|
+
workspace.value?.addEventListener('mouseenter', mouseenterHandler);
|
|
73
|
+
|
|
74
|
+
workspace.value?.addEventListener('mouseleave', mouseleaveHandler);
|
|
75
|
+
|
|
76
|
+
keycon = new KeyController(workspace.value);
|
|
77
|
+
|
|
78
|
+
keycon
|
|
79
|
+
.keyup('delete', () => {
|
|
80
|
+
node.value && services?.editorService.remove(node.value);
|
|
81
|
+
})
|
|
82
|
+
.keyup(['ctrl', 'c'], () => {
|
|
83
|
+
node.value && services?.editorService.copy(node.value);
|
|
84
|
+
})
|
|
85
|
+
.keyup(['ctrl', 'v'], () => {
|
|
86
|
+
node.value && services?.editorService.paste();
|
|
87
|
+
})
|
|
88
|
+
.keyup(['ctrl', 'x'], () => {
|
|
89
|
+
if (node.value && services) {
|
|
90
|
+
services.editorService.copy(node.value);
|
|
91
|
+
services.editorService.remove(node.value);
|
|
92
|
+
}
|
|
93
|
+
});
|
|
94
|
+
});
|
|
95
|
+
|
|
96
|
+
onUnmounted(() => {
|
|
97
|
+
workspace.value?.removeEventListener('mouseenter', mouseenterHandler);
|
|
98
|
+
workspace.value?.removeEventListener('mouseleave', mouseleaveHandler);
|
|
99
|
+
keycon.destroy();
|
|
100
|
+
});
|
|
58
101
|
|
|
59
102
|
return {
|
|
103
|
+
workspace,
|
|
104
|
+
|
|
60
105
|
page: computed(() => services?.editorService.get<MPage>('page')),
|
|
61
106
|
};
|
|
62
107
|
},
|
package/src/services/editor.ts
CHANGED
|
@@ -22,7 +22,7 @@ import serialize from 'serialize-javascript';
|
|
|
22
22
|
|
|
23
23
|
import type { Id, MApp, MComponent, MContainer, MNode, MPage } from '@tmagic/schema';
|
|
24
24
|
import { NodeType } from '@tmagic/schema';
|
|
25
|
-
import
|
|
25
|
+
import StageCore from '@tmagic/stage';
|
|
26
26
|
import { getNodePath, isPop } from '@tmagic/utils';
|
|
27
27
|
|
|
28
28
|
import historyService, { StepValue } from '@editor/services/history';
|
|
@@ -228,7 +228,12 @@ class Editor extends BaseService {
|
|
|
228
228
|
if (!parentNode) throw new Error('未找到父元素');
|
|
229
229
|
|
|
230
230
|
const layout = await this.getLayout(parentNode);
|
|
231
|
-
const newNode = initPosition(
|
|
231
|
+
const newNode = initPosition(
|
|
232
|
+
{ ...toRaw(await propsService.getPropsValue(type, config)) },
|
|
233
|
+
layout,
|
|
234
|
+
parentNode,
|
|
235
|
+
this.get<StageCore>('stage'),
|
|
236
|
+
);
|
|
232
237
|
|
|
233
238
|
if ((parentNode?.type === NodeType.ROOT || curNode.type === NodeType.ROOT) && newNode.type !== NodeType.PAGE) {
|
|
234
239
|
throw new Error('app下不能添加组件');
|
package/src/services/props.ts
CHANGED
|
@@ -87,7 +87,7 @@ class Props extends BaseService {
|
|
|
87
87
|
* @param type 组件类型
|
|
88
88
|
* @returns 组件初始值
|
|
89
89
|
*/
|
|
90
|
-
public async getPropsValue(type: string) {
|
|
90
|
+
public async getPropsValue(type: string, defaultValue = {}) {
|
|
91
91
|
if (type === 'area') {
|
|
92
92
|
const value = (await this.getPropsValue('button')) as MComponent;
|
|
93
93
|
value.className = 'action-area';
|
|
@@ -100,6 +100,7 @@ class Props extends BaseService {
|
|
|
100
100
|
|
|
101
101
|
return cloneDeep({
|
|
102
102
|
...getDefaultPropsValue(type),
|
|
103
|
+
...defaultValue,
|
|
103
104
|
...(this.state.propsValueMap[type] || {}),
|
|
104
105
|
});
|
|
105
106
|
}
|
package/src/type.ts
CHANGED
package/src/utils/editor.ts
CHANGED
|
@@ -20,7 +20,8 @@ import { random } from 'lodash-es';
|
|
|
20
20
|
|
|
21
21
|
import type { Id, MApp, MContainer, MNode, MPage } from '@tmagic/schema';
|
|
22
22
|
import { NodeType } from '@tmagic/schema';
|
|
23
|
-
import
|
|
23
|
+
import type StageCore from '@tmagic/stage';
|
|
24
|
+
import { getNodePath, isNumber, isPage, isPop } from '@tmagic/utils';
|
|
24
25
|
|
|
25
26
|
import { Layout } from '@editor/type';
|
|
26
27
|
|
|
@@ -105,7 +106,7 @@ const updatePopId = (oldId: Id, popId: Id, pageConfig: MPage) => {
|
|
|
105
106
|
export const setNewItemId = (config: MNode, parent?: MPage) => {
|
|
106
107
|
const oldId = config.id;
|
|
107
108
|
|
|
108
|
-
config.id = generateId(config.type);
|
|
109
|
+
config.id = generateId(config.type || 'component');
|
|
109
110
|
config.name = `${config.name?.replace(/_(\d+)$/, '')}_${config.id}`;
|
|
110
111
|
|
|
111
112
|
// 只有弹窗在页面下的一级子元素才有效
|
|
@@ -139,11 +140,29 @@ export const toRelative = (node: MNode) => {
|
|
|
139
140
|
return node;
|
|
140
141
|
};
|
|
141
142
|
|
|
142
|
-
|
|
143
|
+
const setTop2Middle = (node: MNode, parentNode: MNode, stage: StageCore) => {
|
|
144
|
+
const style = node.style || {};
|
|
145
|
+
const height = style.height || 0;
|
|
146
|
+
|
|
147
|
+
if (!stage || style.top || !parentNode.style || !isNumber(height)) return style;
|
|
148
|
+
|
|
149
|
+
const { height: parentHeight } = parentNode.style;
|
|
150
|
+
|
|
151
|
+
if (isPage(parentNode)) {
|
|
152
|
+
const { scrollTop = 0, wrapperHeight } = stage.mask;
|
|
153
|
+
style.top = (wrapperHeight - height) / 2 + scrollTop;
|
|
154
|
+
} else {
|
|
155
|
+
style.top = (parentHeight - height) / 2;
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
return style;
|
|
159
|
+
};
|
|
160
|
+
|
|
161
|
+
export const initPosition = (node: MNode, layout: Layout, parentNode: MNode, stage: StageCore) => {
|
|
143
162
|
if (layout === Layout.ABSOLUTE) {
|
|
144
163
|
node.style = {
|
|
145
164
|
position: 'absolute',
|
|
146
|
-
...(node
|
|
165
|
+
...setTop2Middle(node, parentNode, stage),
|
|
147
166
|
};
|
|
148
167
|
return node;
|
|
149
168
|
}
|
|
@@ -200,6 +219,8 @@ export const Fixed2Other = async (node: MNode, root: MApp, getLayout: (node: MNo
|
|
|
200
219
|
const offset = {
|
|
201
220
|
left: cur?.style?.left || 0,
|
|
202
221
|
top: cur?.style?.top || 0,
|
|
222
|
+
right: '',
|
|
223
|
+
bottom: '',
|
|
203
224
|
};
|
|
204
225
|
|
|
205
226
|
path.forEach((value) => {
|
package/src/utils/props.ts
CHANGED
|
@@ -174,7 +174,7 @@ export const fillConfig = (config: FormConfig = []) => [
|
|
|
174
174
|
type: 'select',
|
|
175
175
|
options: (mForm: FormState, { model }: any) => {
|
|
176
176
|
const node = editorService.getNodeById(model.to);
|
|
177
|
-
if (!node) return [];
|
|
177
|
+
if (!node?.type) return [];
|
|
178
178
|
|
|
179
179
|
return eventsService.getMethod(node.type).map((option) => ({
|
|
180
180
|
text: option.label,
|