@flowgram-vue/core 0.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/LICENSE +22 -0
- package/dist/index.cjs +0 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +0 -0
- package/dist/index.js.map +1 -0
- package/package.json +63 -0
- package/src/common/config-entity.ts +80 -0
- package/src/common/entity-data.ts +171 -0
- package/src/common/entity-manager-contribution.ts +12 -0
- package/src/common/entity-manager.ts +475 -0
- package/src/common/entity.ts +482 -0
- package/src/common/index.ts +22 -0
- package/src/common/playground-context.ts +35 -0
- package/src/common/playground-decorator-helper.ts +113 -0
- package/src/common/playground-decorators.ts +85 -0
- package/src/common/playground-schedule.ts +30 -0
- package/src/common/protect-wheel-area.ts +11 -0
- package/src/common/schema/index.ts +14 -0
- package/src/common/schema/node.ts +15 -0
- package/src/common/schema/opacity-schema.ts +19 -0
- package/src/common/schema/origin-schema.ts +35 -0
- package/src/common/schema/position-schema.ts +35 -0
- package/src/common/schema/rotation-schema.ts +19 -0
- package/src/common/schema/scale-schema.ts +35 -0
- package/src/common/schema/size-schema.ts +42 -0
- package/src/common/schema/skew-schema.ts +35 -0
- package/src/common/schema/transform-schema.ts +613 -0
- package/src/common/utils/bounds.spec.ts +229 -0
- package/src/common/utils/bounds.ts +176 -0
- package/src/common/utils/index.ts +6 -0
- package/src/composables/index.ts +16 -0
- package/src/composables/use-config-entity.ts +31 -0
- package/src/composables/use-entities.ts +26 -0
- package/src/composables/use-entity-data-from-context.ts +34 -0
- package/src/composables/use-entity-from-context.ts +31 -0
- package/src/composables/use-listen-events.ts +22 -0
- package/src/composables/use-playground-container.ts +16 -0
- package/src/composables/use-playground-context.ts +15 -0
- package/src/composables/use-playground-drag.ts +31 -0
- package/src/composables/use-playground.ts +16 -0
- package/src/composables/use-refresh.ts +6 -0
- package/src/composables/use-service.ts +17 -0
- package/src/core/index.ts +8 -0
- package/src/core/layer/config/editor-state-config-entity.ts +180 -0
- package/src/core/layer/config/index.ts +7 -0
- package/src/core/layer/config/playground-config-entity.ts +604 -0
- package/src/core/layer/index.ts +8 -0
- package/src/core/layer/layer.ts +248 -0
- package/src/core/layer/playground-layer.ts +547 -0
- package/src/core/pipeline/index.ts +10 -0
- package/src/core/pipeline/pipeline-entities-selector.ts +200 -0
- package/src/core/pipeline/pipeline-entities.ts +230 -0
- package/src/core/pipeline/pipeline-registry.ts +344 -0
- package/src/core/pipeline/pipeline-renderer.ts +248 -0
- package/src/core/pipeline/pipeline-vue-utils.ts +96 -0
- package/src/core/pipeline/pipeline.ts +28 -0
- package/src/core/utils/index.ts +12 -0
- package/src/core/utils/inject-provider-decorators.ts +27 -0
- package/src/core/utils/lazy-inject-decorators.ts +38 -0
- package/src/core/utils/mouse-touch-event.ts +120 -0
- package/src/core/utils/playground-drag.ts +511 -0
- package/src/core/utils/playground-gesture.spec.ts +135 -0
- package/src/core/utils/playground-gesture.ts +118 -0
- package/src/core/utils/tween.ts +156 -0
- package/src/core/utils/use-gesture/core/Controller.ts +212 -0
- package/src/core/utils/use-gesture/core/EventStore.ts +46 -0
- package/src/core/utils/use-gesture/core/TimeoutStore.ts +28 -0
- package/src/core/utils/use-gesture/core/actions.ts +63 -0
- package/src/core/utils/use-gesture/core/config/commonConfigResolver.ts +86 -0
- package/src/core/utils/use-gesture/core/config/coordinatesConfigResolver.ts +48 -0
- package/src/core/utils/use-gesture/core/config/dragConfigResolver.ts +140 -0
- package/src/core/utils/use-gesture/core/config/hoverConfigResolver.ts +11 -0
- package/src/core/utils/use-gesture/core/config/moveConfigResolver.ts +11 -0
- package/src/core/utils/use-gesture/core/config/pinchConfigResolver.ts +59 -0
- package/src/core/utils/use-gesture/core/config/resolver.ts +70 -0
- package/src/core/utils/use-gesture/core/config/scrollConfigResolver.ts +8 -0
- package/src/core/utils/use-gesture/core/config/sharedConfigResolver.ts +28 -0
- package/src/core/utils/use-gesture/core/config/support.ts +52 -0
- package/src/core/utils/use-gesture/core/config/wheelConfigResolver.ts +8 -0
- package/src/core/utils/use-gesture/core/engines/CoordinatesEngine.ts +78 -0
- package/src/core/utils/use-gesture/core/engines/DragEngine.ts +403 -0
- package/src/core/utils/use-gesture/core/engines/Engine.ts +406 -0
- package/src/core/utils/use-gesture/core/engines/HoverEngine.ts +43 -0
- package/src/core/utils/use-gesture/core/engines/MoveEngine.ts +52 -0
- package/src/core/utils/use-gesture/core/engines/PinchEngine.ts +345 -0
- package/src/core/utils/use-gesture/core/engines/ScrollEngine.ts +42 -0
- package/src/core/utils/use-gesture/core/engines/WheelEngine.ts +48 -0
- package/src/core/utils/use-gesture/core/index.ts +7 -0
- package/src/core/utils/use-gesture/core/parser.ts +92 -0
- package/src/core/utils/use-gesture/core/types/action.ts +19 -0
- package/src/core/utils/use-gesture/core/types/config.ts +255 -0
- package/src/core/utils/use-gesture/core/types/handlers.ts +73 -0
- package/src/core/utils/use-gesture/core/types/index.ts +11 -0
- package/src/core/utils/use-gesture/core/types/internalConfig.ts +80 -0
- package/src/core/utils/use-gesture/core/types/state.ts +275 -0
- package/src/core/utils/use-gesture/core/types/utils.ts +204 -0
- package/src/core/utils/use-gesture/core/types.ts +8 -0
- package/src/core/utils/use-gesture/core/utils/events.ts +158 -0
- package/src/core/utils/use-gesture/core/utils/fn.ts +32 -0
- package/src/core/utils/use-gesture/core/utils/maths.ts +63 -0
- package/src/core/utils/use-gesture/core/utils/state.ts +24 -0
- package/src/core/utils/use-gesture/core/utils.ts +8 -0
- package/src/core/utils/use-gesture/index.ts +6 -0
- package/src/core/utils/use-gesture/vanilla/DragGesture.ts +27 -0
- package/src/core/utils/use-gesture/vanilla/Gesture.ts +45 -0
- package/src/core/utils/use-gesture/vanilla/HoverGesture.ts +27 -0
- package/src/core/utils/use-gesture/vanilla/MoveGesture.ts +27 -0
- package/src/core/utils/use-gesture/vanilla/PinchGesture.ts +27 -0
- package/src/core/utils/use-gesture/vanilla/Recognizer.ts +43 -0
- package/src/core/utils/use-gesture/vanilla/ScrollGesture.ts +27 -0
- package/src/core/utils/use-gesture/vanilla/WheelGesture.ts +27 -0
- package/src/core/utils/use-gesture/vanilla/createGesture.ts +18 -0
- package/src/core/utils/use-gesture/vanilla/index.ts +18 -0
- package/src/env.d.ts +10 -0
- package/src/index.ts +17 -0
- package/src/playground-config.ts +70 -0
- package/src/playground-container.ts +129 -0
- package/src/playground-contribution.ts +81 -0
- package/src/playground-mock-tools.ts +143 -0
- package/src/playground.ts +401 -0
- package/src/plugin/index.ts +6 -0
- package/src/plugin/plugin.ts +226 -0
- package/src/services/clipboard-service.ts +40 -0
- package/src/services/context-menu-service.ts +25 -0
- package/src/services/index.ts +10 -0
- package/src/services/logger-service.ts +49 -0
- package/src/services/selection-service.ts +54 -0
- package/src/services/storage-service.ts +65 -0
- package/src/vue/index.ts +8 -0
- package/src/vue/playground-vue-context.ts +22 -0
- package/src/vue/playground-vue-provider.ts +115 -0
- package/src/vue/playground-vue-renderer.vue +44 -0
|
@@ -0,0 +1,482 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2025 Bytedance Ltd. and/or its affiliates
|
|
3
|
+
* SPDX-License-Identifier: MIT
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { nanoid } from 'nanoid';
|
|
7
|
+
import { interfaces } from 'inversify';
|
|
8
|
+
import { Compare, Disposable, DisposableCollection, Emitter, type Event } from '@flowgram-vue/utils';
|
|
9
|
+
|
|
10
|
+
import { type PlaygroundContext } from './playground-context';
|
|
11
|
+
import type { EntityManager } from './entity-manager';
|
|
12
|
+
import type { EntityData, EntityDataProps, EntityDataRegistry } from './entity-data';
|
|
13
|
+
// import type { AbleChangedEvent, EntityAbles } from './entity-ables';
|
|
14
|
+
// import type { AbleManager } from './able-manager';
|
|
15
|
+
// import type { Able, AbleRegistry } from './able';
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* 注册类
|
|
19
|
+
*/
|
|
20
|
+
export interface EntityRegistry<E extends Entity = Entity> {
|
|
21
|
+
new (opts: any): E;
|
|
22
|
+
|
|
23
|
+
readonly type: E['type'];
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* 持久化数据
|
|
28
|
+
*/
|
|
29
|
+
export interface EntityJSON {
|
|
30
|
+
type: string;
|
|
31
|
+
id: string;
|
|
32
|
+
// ableList?: string[];
|
|
33
|
+
dataList: object[];
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
// eslint-disable-next-line no-proto
|
|
37
|
+
const ObjectProto = (Object as any).__proto__;
|
|
38
|
+
|
|
39
|
+
export interface EntityDataChangedEvent<T extends Entity = Entity> {
|
|
40
|
+
type: 'add' | 'delete' | 'update';
|
|
41
|
+
data: EntityData;
|
|
42
|
+
entity: T;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export interface EntityOpts {
|
|
46
|
+
entityManager: EntityManager;
|
|
47
|
+
id?: string;
|
|
48
|
+
// ables?: AbleRegistry[]; // 添加的 able
|
|
49
|
+
datas?: { registry: EntityDataRegistry; data?: EntityDataProps<any> }[];
|
|
50
|
+
savedInManager?: boolean; // 是否存储到 manager 上,默认 true
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
let _version = 0;
|
|
54
|
+
|
|
55
|
+
export class Entity<OPTS extends EntityOpts = EntityOpts> implements Disposable {
|
|
56
|
+
static type = 'Entity';
|
|
57
|
+
|
|
58
|
+
private readonly onEntityChangeEmitter = new Emitter<Entity>();
|
|
59
|
+
|
|
60
|
+
private readonly onDataChangeEmitter = new Emitter<EntityDataChangedEvent>();
|
|
61
|
+
|
|
62
|
+
private readonly initializeDataKeys: string[] = []; // 初始化的
|
|
63
|
+
|
|
64
|
+
protected readonly dataManager: Map<string, EntityData> = new Map(); // 存储的数据
|
|
65
|
+
|
|
66
|
+
// readonly onBeforeAbleDispatchedEmitter = new Emitter<Able>();
|
|
67
|
+
//
|
|
68
|
+
// readonly onAfterAbleDispatchedEmitter = new Emitter<Able>();
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* 销毁事件管理
|
|
72
|
+
*/
|
|
73
|
+
readonly toDispose = new DisposableCollection();
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* 销毁前事件管理
|
|
77
|
+
*/
|
|
78
|
+
readonly preDispose = new DisposableCollection();
|
|
79
|
+
|
|
80
|
+
// /**
|
|
81
|
+
// * able 管理
|
|
82
|
+
// */
|
|
83
|
+
// readonly ables: EntityAbles;
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* 修改会触发
|
|
87
|
+
*/
|
|
88
|
+
readonly onEntityChange = this.onEntityChangeEmitter.event;
|
|
89
|
+
|
|
90
|
+
// /**
|
|
91
|
+
// * able 触发之前
|
|
92
|
+
// */
|
|
93
|
+
// readonly onBeforeAbleDispatched = this.onBeforeAbleDispatchedEmitter.event;
|
|
94
|
+
|
|
95
|
+
// /**
|
|
96
|
+
// * able 触发之后
|
|
97
|
+
// */
|
|
98
|
+
// readonly onAfterAbleDispatched = this.onAfterAbleDispatchedEmitter.event;
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* 数据更改事件
|
|
102
|
+
*/
|
|
103
|
+
readonly onDataChange = this.onDataChangeEmitter.event;
|
|
104
|
+
|
|
105
|
+
// /**
|
|
106
|
+
// * able 数据更改
|
|
107
|
+
// */
|
|
108
|
+
// readonly onAbleChange: Event<AbleChangedEvent>;
|
|
109
|
+
|
|
110
|
+
// /**
|
|
111
|
+
// * 默认初始化的 Able
|
|
112
|
+
// */
|
|
113
|
+
// getDefaultAbleRegistries(): AbleRegistry[] {
|
|
114
|
+
// return [];
|
|
115
|
+
// }
|
|
116
|
+
|
|
117
|
+
/**
|
|
118
|
+
* 默认初始化的 Data
|
|
119
|
+
*/
|
|
120
|
+
getDefaultDataRegistries(): EntityDataRegistry[] {
|
|
121
|
+
return [];
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
private _changeLockedTimes = 0;
|
|
125
|
+
|
|
126
|
+
protected isInitialized = true;
|
|
127
|
+
|
|
128
|
+
private _id: string;
|
|
129
|
+
|
|
130
|
+
private _version: number = _version++; // 每次创建都有一个新 version,避免 id 相同的 entity 频繁创建销毁导致碰撞
|
|
131
|
+
|
|
132
|
+
private _savedInManager = true;
|
|
133
|
+
|
|
134
|
+
// readonly ableManager: AbleManager;
|
|
135
|
+
|
|
136
|
+
/**
|
|
137
|
+
* 暂停更新开关
|
|
138
|
+
* @protected
|
|
139
|
+
*/
|
|
140
|
+
protected get changeLocked(): boolean {
|
|
141
|
+
return this._changeLockedTimes > 0;
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
protected set changeLocked(changeLocked) {
|
|
145
|
+
this._changeLockedTimes = changeLocked
|
|
146
|
+
? this._changeLockedTimes + 1
|
|
147
|
+
: this._changeLockedTimes - 1;
|
|
148
|
+
|
|
149
|
+
/* istanbul ignore next */
|
|
150
|
+
if (this._changeLockedTimes < 0) this._changeLockedTimes = 0;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* 实体类型
|
|
155
|
+
*/
|
|
156
|
+
get type(): string {
|
|
157
|
+
if (!(this.constructor as any).type) {
|
|
158
|
+
throw new Error(`Entity Registry need a type: ${this.constructor.name}`);
|
|
159
|
+
}
|
|
160
|
+
return (this.constructor as any).type;
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
/**
|
|
164
|
+
* 全局的entity管理器
|
|
165
|
+
*/
|
|
166
|
+
readonly entityManager: EntityManager;
|
|
167
|
+
|
|
168
|
+
get context(): PlaygroundContext {
|
|
169
|
+
return this.entityManager.context;
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
constructor(opts: OPTS) {
|
|
173
|
+
this.entityManager = opts.entityManager;
|
|
174
|
+
this._id = opts.id || nanoid();
|
|
175
|
+
this._savedInManager = opts.savedInManager === undefined ? true : opts.savedInManager;
|
|
176
|
+
// this.ableManager = this.entityManager.ableManager;
|
|
177
|
+
// this.context = this.entityManager.context;
|
|
178
|
+
this.isInitialized = true;
|
|
179
|
+
// this.ables = this.entityManager.ableManager.createAbleMap(this);
|
|
180
|
+
// this.ables.onAbleChange(event => {
|
|
181
|
+
// // 只需要监听删除,add 和 update 都由 entityData 去监听
|
|
182
|
+
// if (event.type === 'delete') {
|
|
183
|
+
// this.fireChange();
|
|
184
|
+
// }
|
|
185
|
+
// });
|
|
186
|
+
this.toDispose.push(this.onEntityChangeEmitter);
|
|
187
|
+
// this.toDispose.push(this.onBeforeAbleDispatchedEmitter);
|
|
188
|
+
// this.toDispose.push(this.onAfterAbleDispatchedEmitter);
|
|
189
|
+
this.toDispose.push(this.onDataChangeEmitter);
|
|
190
|
+
// this.toDispose.push(this.ables);
|
|
191
|
+
// this.onAbleChange = this.ables.onAbleChange;
|
|
192
|
+
this.register();
|
|
193
|
+
// if (opts.ables) {
|
|
194
|
+
// opts.ables.forEach(able => this.ables.add(able));
|
|
195
|
+
// }
|
|
196
|
+
if (opts.datas) {
|
|
197
|
+
opts.datas.forEach((data) => this.addData(data.registry, data.data));
|
|
198
|
+
}
|
|
199
|
+
this.isInitialized = false;
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
addInitializeData(datas: EntityDataRegistry[], dataConfig?: any) {
|
|
203
|
+
this.isInitialized = true;
|
|
204
|
+
datas.forEach((data) => this.addData(data, dataConfig));
|
|
205
|
+
this.isInitialized = false;
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
/**
|
|
209
|
+
* 实体的版本
|
|
210
|
+
*/
|
|
211
|
+
get version(): number {
|
|
212
|
+
return this._version;
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
/**
|
|
216
|
+
* 存储数据,用于持久化存储
|
|
217
|
+
*/
|
|
218
|
+
toJSON(): EntityJSON | any {
|
|
219
|
+
const dataList: object[] = [];
|
|
220
|
+
for (const data of this.dataManager.values()) {
|
|
221
|
+
dataList.push({
|
|
222
|
+
type: data.type,
|
|
223
|
+
data: data.toJSON(),
|
|
224
|
+
});
|
|
225
|
+
}
|
|
226
|
+
return {
|
|
227
|
+
type: this.type,
|
|
228
|
+
id: this.id,
|
|
229
|
+
// ableList: this.ables.toJSON(),
|
|
230
|
+
dataList,
|
|
231
|
+
};
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
/**
|
|
235
|
+
* 还原数据
|
|
236
|
+
*/
|
|
237
|
+
fromJSON(data?: EntityJSON | any): void {
|
|
238
|
+
if (!data || !data.id || !data.type) return;
|
|
239
|
+
this.changeLocked = true;
|
|
240
|
+
this.reset();
|
|
241
|
+
if (data.dataList) {
|
|
242
|
+
data.dataList.forEach((d: any) => {
|
|
243
|
+
const registry = this.entityManager.getDataRegistryByType(d.type);
|
|
244
|
+
if (registry) {
|
|
245
|
+
const dataEntity = this.addData(registry);
|
|
246
|
+
dataEntity.update(d.data);
|
|
247
|
+
}
|
|
248
|
+
});
|
|
249
|
+
}
|
|
250
|
+
this.changeLocked = false;
|
|
251
|
+
this.fireChange();
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
/**
|
|
255
|
+
* 实体 id
|
|
256
|
+
*/
|
|
257
|
+
get id(): string {
|
|
258
|
+
return this._id;
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
/**
|
|
262
|
+
* 销毁实体
|
|
263
|
+
*/
|
|
264
|
+
dispose(): void {
|
|
265
|
+
this.preDispose.dispose();
|
|
266
|
+
this.toDispose.dispose();
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
get disposed(): boolean {
|
|
270
|
+
return this.toDispose.disposed;
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
/**
|
|
274
|
+
* 重制为初始化状态
|
|
275
|
+
*/
|
|
276
|
+
reset(): void {
|
|
277
|
+
this.changeLocked = true;
|
|
278
|
+
for (const data of this.dataManager.values()) {
|
|
279
|
+
if (!this.initializeDataKeys.includes(data.type)) {
|
|
280
|
+
data.dispose();
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
// this.ables.reset();
|
|
284
|
+
this.register();
|
|
285
|
+
this.changeLocked = false;
|
|
286
|
+
this.fireChange();
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
/**
|
|
290
|
+
* 销毁事件
|
|
291
|
+
*/
|
|
292
|
+
get onDispose(): Event<void> {
|
|
293
|
+
return this.toDispose.onDispose;
|
|
294
|
+
}
|
|
295
|
+
|
|
296
|
+
/**
|
|
297
|
+
* 触发实体更新
|
|
298
|
+
* @protected
|
|
299
|
+
*/
|
|
300
|
+
protected fireChange(): void {
|
|
301
|
+
if (this.changeLocked || this.isInitialized || this.disposed) return;
|
|
302
|
+
this._version++;
|
|
303
|
+
/* istanbul ignore next */
|
|
304
|
+
if (this._version >= Number.MAX_SAFE_INTEGER) {
|
|
305
|
+
this._version = 0;
|
|
306
|
+
}
|
|
307
|
+
this.onEntityChangeEmitter.fire(this);
|
|
308
|
+
}
|
|
309
|
+
|
|
310
|
+
/**
|
|
311
|
+
* 添加数据
|
|
312
|
+
*/
|
|
313
|
+
addData<D extends EntityData>(
|
|
314
|
+
Registry: EntityDataRegistry,
|
|
315
|
+
defaultProps?: EntityDataProps<D>
|
|
316
|
+
): D {
|
|
317
|
+
this.entityManager.registerEntityData(Registry);
|
|
318
|
+
let entityData = this.dataManager.get(Registry.type) as D;
|
|
319
|
+
|
|
320
|
+
if (entityData) {
|
|
321
|
+
if (defaultProps) this.updateData(Registry, defaultProps);
|
|
322
|
+
return entityData;
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
// 是否存在EntityData依赖注入器
|
|
326
|
+
const injector = this.entityManager.getDataInjector(Registry);
|
|
327
|
+
entityData = new Registry(this, injector?.()) as D;
|
|
328
|
+
|
|
329
|
+
if (this.isInitialized) this.initializeDataKeys.push(entityData.type);
|
|
330
|
+
this.dataManager.set(Registry.type, entityData);
|
|
331
|
+
this.toDispose.push(entityData);
|
|
332
|
+
entityData.onDataChange(() => {
|
|
333
|
+
const event: EntityDataChangedEvent = {
|
|
334
|
+
type: 'update',
|
|
335
|
+
data: entityData,
|
|
336
|
+
entity: this,
|
|
337
|
+
};
|
|
338
|
+
this.onDataChangeEmitter.fire(event);
|
|
339
|
+
this.fireChange();
|
|
340
|
+
});
|
|
341
|
+
entityData.toDispose.push(
|
|
342
|
+
Disposable.create(() => {
|
|
343
|
+
// 初始化的 data 数据无法被删除
|
|
344
|
+
if (!this.initializeDataKeys.includes(Registry.type)) {
|
|
345
|
+
this.dataManager.delete(Registry.type);
|
|
346
|
+
}
|
|
347
|
+
const event: EntityDataChangedEvent = {
|
|
348
|
+
type: 'delete',
|
|
349
|
+
data: entityData,
|
|
350
|
+
entity: this,
|
|
351
|
+
};
|
|
352
|
+
this.onDataChangeEmitter.fire(event);
|
|
353
|
+
this.fireChange();
|
|
354
|
+
})
|
|
355
|
+
);
|
|
356
|
+
entityData.changeLocked = true;
|
|
357
|
+
this.updateData(Registry, defaultProps || entityData.getDefaultData());
|
|
358
|
+
entityData.changeLocked = false;
|
|
359
|
+
const event: EntityDataChangedEvent = {
|
|
360
|
+
type: 'add',
|
|
361
|
+
data: entityData,
|
|
362
|
+
entity: this,
|
|
363
|
+
};
|
|
364
|
+
this.onDataChangeEmitter.fire(event);
|
|
365
|
+
return entityData;
|
|
366
|
+
}
|
|
367
|
+
|
|
368
|
+
/**
|
|
369
|
+
* 是否存到全局 manager,默认 true
|
|
370
|
+
*/
|
|
371
|
+
get savedInManager(): boolean {
|
|
372
|
+
return this._savedInManager;
|
|
373
|
+
}
|
|
374
|
+
|
|
375
|
+
/**
|
|
376
|
+
* 更新实体的数据
|
|
377
|
+
*/
|
|
378
|
+
updateData<D extends EntityData>(
|
|
379
|
+
Registry: EntityDataRegistry<D>,
|
|
380
|
+
props: EntityDataProps<D>
|
|
381
|
+
): void {
|
|
382
|
+
const entityData = this.dataManager.get(Registry.type);
|
|
383
|
+
if (entityData) {
|
|
384
|
+
entityData.update(props);
|
|
385
|
+
}
|
|
386
|
+
}
|
|
387
|
+
|
|
388
|
+
/**
|
|
389
|
+
* 获取 data 数据
|
|
390
|
+
*/
|
|
391
|
+
getData<D extends EntityData>(Registry: EntityDataRegistry<D>): D {
|
|
392
|
+
return this.dataManager.get(Registry.type) as D;
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
/**
|
|
396
|
+
* 是否有指定数据
|
|
397
|
+
*/
|
|
398
|
+
hasData(Registry: EntityDataRegistry): boolean {
|
|
399
|
+
return this.dataManager.has(Registry.type);
|
|
400
|
+
}
|
|
401
|
+
|
|
402
|
+
/**
|
|
403
|
+
* 删除数据,初始化状态注入的数据无法被删除
|
|
404
|
+
*/
|
|
405
|
+
removeData<D extends EntityData>(Registry: EntityDataRegistry<D>): void {
|
|
406
|
+
// 初始化的数据无法被删除
|
|
407
|
+
if (this.initializeDataKeys.includes(Registry.type)) return;
|
|
408
|
+
const entityData = this.dataManager.get(Registry.type);
|
|
409
|
+
if (entityData) {
|
|
410
|
+
entityData.dispose();
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
|
|
414
|
+
/**
|
|
415
|
+
* 获取 IOC 服务
|
|
416
|
+
* @param identifier
|
|
417
|
+
*/
|
|
418
|
+
getService<T>(identifier: interfaces.ServiceIdentifier<T>): T {
|
|
419
|
+
return this.entityManager.getService<T>(identifier);
|
|
420
|
+
}
|
|
421
|
+
// /**
|
|
422
|
+
// * 添加 able
|
|
423
|
+
// */
|
|
424
|
+
// addAbles(...ables: AbleRegistry[]): void {
|
|
425
|
+
// ables.forEach(able => this.ables.add(able));
|
|
426
|
+
// }
|
|
427
|
+
//
|
|
428
|
+
// /**
|
|
429
|
+
// * 删除 able
|
|
430
|
+
// */
|
|
431
|
+
// removeAbles(...ables: AbleRegistry[]): void {
|
|
432
|
+
// ables.forEach(able => this.ables.remove(able));
|
|
433
|
+
// }
|
|
434
|
+
//
|
|
435
|
+
// /**
|
|
436
|
+
// * 是否有 able
|
|
437
|
+
// */
|
|
438
|
+
// hasAble(able: AbleRegistry): boolean {
|
|
439
|
+
// return this.ables.has(able);
|
|
440
|
+
// }
|
|
441
|
+
//
|
|
442
|
+
// hasAbles(...ables: AbleRegistry[]): boolean {
|
|
443
|
+
// for (const able of ables) {
|
|
444
|
+
// if (!this.ables.has(able)) return false;
|
|
445
|
+
// }
|
|
446
|
+
// return true;
|
|
447
|
+
// }
|
|
448
|
+
|
|
449
|
+
protected register(): void {
|
|
450
|
+
// 注册默认 able
|
|
451
|
+
// this.getDefaultAbleRegistries().forEach(Registry => this.ables.add(Registry));
|
|
452
|
+
// 注册默认 data
|
|
453
|
+
this.getDefaultDataRegistries().forEach((Registry) => this.addData(Registry));
|
|
454
|
+
}
|
|
455
|
+
|
|
456
|
+
declare __opts_type__: OPTS;
|
|
457
|
+
}
|
|
458
|
+
|
|
459
|
+
export namespace Entity {
|
|
460
|
+
export function getType(registry: EntityRegistry): string {
|
|
461
|
+
return registry.type;
|
|
462
|
+
}
|
|
463
|
+
|
|
464
|
+
/**
|
|
465
|
+
* 默认数据比较,采用浅比较
|
|
466
|
+
*/
|
|
467
|
+
export function checkDataChanged(oldProps: any, newProps: any): boolean {
|
|
468
|
+
return Compare.isChanged(oldProps, newProps);
|
|
469
|
+
}
|
|
470
|
+
|
|
471
|
+
export function isRegistryOf(target: any, Registry: any): boolean {
|
|
472
|
+
if (target === Registry) return true;
|
|
473
|
+
// eslint-disable-next-line no-proto
|
|
474
|
+
let proto = target.__proto__;
|
|
475
|
+
while (proto && proto !== ObjectProto) {
|
|
476
|
+
if (proto.prototype === Registry.prototype) return true;
|
|
477
|
+
// eslint-disable-next-line no-proto
|
|
478
|
+
proto = proto.__proto__;
|
|
479
|
+
}
|
|
480
|
+
return false;
|
|
481
|
+
}
|
|
482
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2025 Bytedance Ltd. and/or its affiliates
|
|
3
|
+
* SPDX-License-Identifier: MIT
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
export * from './schema';
|
|
7
|
+
export * from './utils';
|
|
8
|
+
// export * from './able';
|
|
9
|
+
// export * from './able-manager';
|
|
10
|
+
export * from './entity-manager';
|
|
11
|
+
export * from './config-entity';
|
|
12
|
+
export * from './entity';
|
|
13
|
+
// export * from './entity-tree';
|
|
14
|
+
// export * from './entity-ables';
|
|
15
|
+
export * from './entity-data';
|
|
16
|
+
export * from './entity-manager-contribution';
|
|
17
|
+
export * from './playground-context';
|
|
18
|
+
export * from './playground-decorator-helper';
|
|
19
|
+
export * from './playground-decorators';
|
|
20
|
+
export * from './playground-schedule';
|
|
21
|
+
export * from './protect-wheel-area';
|
|
22
|
+
export { bindContributions, ContributionProvider, bindContributionProvider } from '@flowgram-vue/utils';
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2025 Bytedance Ltd. and/or its affiliates
|
|
3
|
+
* SPDX-License-Identifier: MIT
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { interfaces } from 'inversify';
|
|
7
|
+
|
|
8
|
+
import { injectByProvider } from '../core/utils';
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* 会被注入到 layer 层,可以在使用的时候替换它
|
|
12
|
+
*/
|
|
13
|
+
export const PlaygroundContext = Symbol('PlaygroundContext');
|
|
14
|
+
|
|
15
|
+
export type PlaygroundContext = any;
|
|
16
|
+
|
|
17
|
+
export const PlaygroundContextProvider = Symbol('PlaygroundContextProvider');
|
|
18
|
+
export type PlaygroundContextProvider = () => any;
|
|
19
|
+
export const injectPlaygroundContext = () => injectByProvider(PlaygroundContextProvider);
|
|
20
|
+
export const bindPlaygroundContextProvider = (bind: interfaces.Bind) => {
|
|
21
|
+
bind(PlaygroundContextProvider).toDynamicValue(ctx => () => {
|
|
22
|
+
if (ctx.container.isBound(PlaygroundContext)) {
|
|
23
|
+
return ctx.container.get(PlaygroundContext);
|
|
24
|
+
}
|
|
25
|
+
return undefined;
|
|
26
|
+
});
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
export const PlaygroundContainerFactory = Symbol('PlaygroundContainerFactory');
|
|
30
|
+
|
|
31
|
+
export interface PlaygroundContainerFactory {
|
|
32
|
+
createChild: interfaces.Container['createChild'];
|
|
33
|
+
get: interfaces.Container['get'];
|
|
34
|
+
getAll: interfaces.Container['getAll'];
|
|
35
|
+
}
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) 2025 Bytedance Ltd. and/or its affiliates
|
|
3
|
+
* SPDX-License-Identifier: MIT
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
// import type { AbleRegistry } from './able';
|
|
7
|
+
import type { EntityDataRegistry, EntityRegistry } from '.';
|
|
8
|
+
|
|
9
|
+
declare namespace Reflect {
|
|
10
|
+
export function getMetadata(key: string | symbol, target: any): any;
|
|
11
|
+
export function defineMetadata(key: string | symbol, value: any, target: any): any;
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
// export const ABLES_DECO_KEY = Symbol('AblesDecorator');
|
|
15
|
+
export const ENTITIES_DECO_KEY = Symbol('EntitiesDecorator');
|
|
16
|
+
// export const PAYLOAD_DECO_KEY = Symbol('PayloadDecorator');
|
|
17
|
+
// export const HANDLE_DECO_KEY = Symbol('HandleDecorator');
|
|
18
|
+
export const ENTITIES_BY_DATA_DECO_KEY = Symbol('EntitiesByDataDecorator');
|
|
19
|
+
|
|
20
|
+
const PROPERTEIS_INJECTED = Symbol('PropertiesInjected');
|
|
21
|
+
|
|
22
|
+
export interface RegistryValueGetter<T> {
|
|
23
|
+
(target: any, method: string | symbol): T;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export interface RegistryInit {
|
|
27
|
+
(target: any, method: string | symbol): void;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export function getRegistryMetadata(target: any, key: symbol): any[] {
|
|
31
|
+
return Reflect.getMetadata(key, target.prototype) || [];
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
function getRegistryInjectedProperties(target: any): string[] {
|
|
35
|
+
return Reflect.getMetadata(PROPERTEIS_INJECTED, target) || [];
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
function definePropertiesMetadata(target: any, property: string): void {
|
|
39
|
+
const properties = getRegistryInjectedProperties(target);
|
|
40
|
+
properties.push(property);
|
|
41
|
+
Reflect.defineMetadata(PROPERTEIS_INJECTED, properties, target);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
/**
|
|
45
|
+
* 在 rspack 场景编译ts文件时候
|
|
46
|
+
* decorator 注入的 property 会被当成 this 的属性, 导致 Reflect.metadata 失效
|
|
47
|
+
*/
|
|
48
|
+
export function removeInjectedProperties(instance: any): void {
|
|
49
|
+
if (typeof instance === 'object') {
|
|
50
|
+
const propertiesInjected = getRegistryInjectedProperties(instance.constructor.prototype);
|
|
51
|
+
propertiesInjected.forEach(propertyKey => {
|
|
52
|
+
// eslint-disable-next-line no-prototype-builtins
|
|
53
|
+
if (instance.hasOwnProperty(propertyKey) && instance[propertyKey] === undefined) {
|
|
54
|
+
delete instance[propertyKey];
|
|
55
|
+
}
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
export function createRegistryDecorator(
|
|
61
|
+
key: symbol,
|
|
62
|
+
data: any,
|
|
63
|
+
getValue?: RegistryValueGetter<any>,
|
|
64
|
+
init?: RegistryInit,
|
|
65
|
+
): any {
|
|
66
|
+
return (target: any, property: string): any => {
|
|
67
|
+
let registries = Reflect.getMetadata(key, target);
|
|
68
|
+
if (!registries) {
|
|
69
|
+
registries = [];
|
|
70
|
+
Reflect.defineMetadata(key, registries, target);
|
|
71
|
+
}
|
|
72
|
+
if (!Array.isArray(data)) {
|
|
73
|
+
data = [data];
|
|
74
|
+
}
|
|
75
|
+
data.forEach((registry: any) => {
|
|
76
|
+
if (!registries.includes(registry)) {
|
|
77
|
+
registries.push(registry);
|
|
78
|
+
}
|
|
79
|
+
});
|
|
80
|
+
if (init) init(target, property);
|
|
81
|
+
if (property && getValue) {
|
|
82
|
+
definePropertiesMetadata(target, property);
|
|
83
|
+
return {
|
|
84
|
+
enumerable: false,
|
|
85
|
+
configurable: false,
|
|
86
|
+
get(): any {
|
|
87
|
+
return getValue(this, property);
|
|
88
|
+
},
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
// export function getAbleMetadata(layer: any): AbleRegistry[] {
|
|
95
|
+
// return getRegistryMetadata(layer, ABLES_DECO_KEY);
|
|
96
|
+
// }
|
|
97
|
+
|
|
98
|
+
export function getEntityMetadata(layer: any): EntityRegistry[] {
|
|
99
|
+
return getRegistryMetadata(layer, ENTITIES_DECO_KEY);
|
|
100
|
+
}
|
|
101
|
+
export function getEntityDatasMetadata(
|
|
102
|
+
layer: any,
|
|
103
|
+
): { entity: EntityRegistry; data: EntityDataRegistry }[] {
|
|
104
|
+
return getRegistryMetadata(layer, ENTITIES_BY_DATA_DECO_KEY);
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
// export function getPayloadMetadata(able: AbleRegistry): string | symbol {
|
|
108
|
+
// return getRegistryMetadata(able, PAYLOAD_DECO_KEY)[0];
|
|
109
|
+
// }
|
|
110
|
+
|
|
111
|
+
// export function getHandleParams(able: AbleRegistry): EntityDataRegistry[] {
|
|
112
|
+
// return getRegistryMetadata(able, HANDLE_DECO_KEY);
|
|
113
|
+
// }
|