@finos/legend-extension-dsl-diagram 1.0.26 → 1.0.29
Sign up to get free protection for your applications and to get access to all the features.
- package/lib/DiagramRenderer.d.ts +1 -1
- package/lib/DiagramRenderer.d.ts.map +1 -1
- package/lib/DiagramRenderer.js +56 -54
- package/lib/DiagramRenderer.js.map +1 -1
- package/lib/components/studio/ClassDiagramPreview.d.ts +1 -0
- package/lib/components/studio/ClassDiagramPreview.d.ts.map +1 -1
- package/lib/components/studio/DiagramEditor.d.ts +1 -0
- package/lib/components/studio/DiagramEditor.d.ts.map +1 -1
- package/lib/components/studio/DiagramEditor.js +10 -9
- package/lib/components/studio/DiagramEditor.js.map +1 -1
- package/lib/helpers/DiagramHelper.d.ts.map +1 -1
- package/lib/helpers/DiagramHelper.js +4 -3
- package/lib/helpers/DiagramHelper.js.map +1 -1
- package/lib/index.css +1 -1
- package/lib/index.d.ts +2 -1
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +2 -1
- package/lib/index.js.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView.d.ts +0 -3
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView.d.ts.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView.js +1 -13
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView.js.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassViewReference.d.ts +0 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassViewReference.d.ts.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassViewReference.js +2 -7
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassViewReference.js.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram.d.ts +0 -11
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram.d.ts.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram.js +2 -46
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram.js.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper.d.ts +35 -0
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper.d.ts.map +1 -0
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper.js +118 -0
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper.js.map +1 -0
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipEdgeView.d.ts +0 -2
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipEdgeView.d.ts.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipEdgeView.js +1 -9
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipEdgeView.js.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView.d.ts +0 -17
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView.d.ts.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView.js +6 -109
- package/lib/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView.js.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_PositionedRectangle.d.ts +0 -8
- package/lib/models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_PositionedRectangle.d.ts.map +1 -1
- package/lib/models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_PositionedRectangle.js +1 -16
- package/lib/models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_PositionedRectangle.js.map +1 -1
- package/lib/models/protocols/pure/v1/transformation/pureGraph/V1_DSLDiagram_GraphBuilderHelper.d.ts.map +1 -1
- package/lib/models/protocols/pure/v1/transformation/pureGraph/V1_DSLDiagram_GraphBuilderHelper.js +3 -2
- package/lib/models/protocols/pure/v1/transformation/pureGraph/V1_DSLDiagram_GraphBuilderHelper.js.map +1 -1
- package/lib/package.json +4 -4
- package/lib/stores/studio/DSLDiagram_ModifierHelper.d.ts +54 -0
- package/lib/stores/studio/DSLDiagram_ModifierHelper.d.ts.map +1 -0
- package/lib/stores/studio/DSLDiagram_ModifierHelper.js +87 -0
- package/lib/stores/studio/DSLDiagram_ModifierHelper.js.map +1 -0
- package/lib/stores/studio/DiagramEditorState.d.ts.map +1 -1
- package/lib/stores/studio/DiagramEditorState.js +3 -3
- package/lib/stores/studio/DiagramEditorState.js.map +1 -1
- package/package.json +10 -10
- package/src/DiagramRenderer.ts +125 -58
- package/src/components/studio/DiagramEditor.tsx +16 -11
- package/src/helpers/DiagramHelper.ts +4 -3
- package/src/index.ts +2 -4
- package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView.ts +1 -14
- package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassViewReference.ts +1 -8
- package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram.ts +2 -52
- package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper.ts +165 -0
- package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipEdgeView.ts +1 -10
- package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView.ts +6 -147
- package/src/models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_PositionedRectangle.ts +1 -17
- package/src/models/protocols/pure/v1/transformation/pureGraph/V1_DSLDiagram_GraphBuilderHelper.ts +3 -2
- package/src/stores/studio/DSLDiagram_ModifierHelper.ts +148 -0
- package/src/stores/studio/DiagramEditorState.ts +2 -2
- package/tsconfig.json +2 -0
@@ -84,10 +84,6 @@ import {
|
|
84
84
|
isValidFullPath,
|
85
85
|
isValidPathIdentifier,
|
86
86
|
resolvePackagePathAndElementName,
|
87
|
-
setPropertyName,
|
88
|
-
setPropertyGenericType,
|
89
|
-
setPropertyMultiplicity,
|
90
|
-
addPackageElement,
|
91
87
|
} from '@finos/legend-graph';
|
92
88
|
import {
|
93
89
|
guaranteeNonNullable,
|
@@ -104,10 +100,19 @@ import {
|
|
104
100
|
CORE_DND_TYPE,
|
105
101
|
ElementDragSource,
|
106
102
|
useEditorStore,
|
103
|
+
property_setName,
|
104
|
+
property_setGenericType,
|
105
|
+
property_setMultiplicity,
|
106
|
+
package_addElement,
|
107
107
|
} from '@finos/legend-studio';
|
108
108
|
import { cleanUpDeadReferencesInDiagram } from '../../helpers/DiagramHelper';
|
109
109
|
import { Point } from '../../models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_Point';
|
110
110
|
import type { DSLDiagram_LegendStudioPlugin_Extension } from './DSLDiagram_LegendStudioPlugin_Extension';
|
111
|
+
import {
|
112
|
+
classView_setHideProperties,
|
113
|
+
classView_setHideStereotypes,
|
114
|
+
classView_setHideTaggedValues,
|
115
|
+
} from '../../stores/studio/DSLDiagram_ModifierHelper';
|
111
116
|
|
112
117
|
const DiagramEditorContextMenu = observer(
|
113
118
|
forwardRef<
|
@@ -519,21 +524,21 @@ const DiagramEditorClassViewEditor = observer(
|
|
519
524
|
if (isReadOnly) {
|
520
525
|
return;
|
521
526
|
}
|
522
|
-
classView
|
527
|
+
classView_setHideProperties(classView, !classView.hideProperties);
|
523
528
|
diagramEditorState.renderer.render();
|
524
529
|
};
|
525
530
|
const toggleHideTaggedValues = (): void => {
|
526
531
|
if (isReadOnly) {
|
527
532
|
return;
|
528
533
|
}
|
529
|
-
classView
|
534
|
+
classView_setHideTaggedValues(classView, !classView.hideTaggedValues);
|
530
535
|
diagramEditorState.renderer.render();
|
531
536
|
};
|
532
537
|
const toggleHideStereotypes = (): void => {
|
533
538
|
if (isReadOnly) {
|
534
539
|
return;
|
535
540
|
}
|
536
|
-
classView
|
541
|
+
classView_setHideStereotypes(classView, !classView.hideStereotypes);
|
537
542
|
diagramEditorState.renderer.render();
|
538
543
|
};
|
539
544
|
|
@@ -857,7 +862,7 @@ const DiagramEditorInlineClassCreatorInner = observer(
|
|
857
862
|
diagramEditorState.setInlineClassCreatorState(undefined);
|
858
863
|
const [packagePath, name] = resolvePackagePathAndElementName(path);
|
859
864
|
const _class = new Class(name);
|
860
|
-
|
865
|
+
package_addElement(
|
861
866
|
editorStore.graphManagerState.graph.getOrCreatePackage(packagePath),
|
862
867
|
_class,
|
863
868
|
);
|
@@ -1032,14 +1037,14 @@ const DiagramEditorInlinePropertyEditorInner = observer(
|
|
1032
1037
|
event,
|
1033
1038
|
) => {
|
1034
1039
|
if (property instanceof DerivedProperty || property instanceof Property) {
|
1035
|
-
|
1040
|
+
property_setName(property, event.target.value);
|
1036
1041
|
diagramEditorState.renderer.render();
|
1037
1042
|
}
|
1038
1043
|
};
|
1039
1044
|
|
1040
1045
|
const changeMultiplicity = (val: Multiplicity): void => {
|
1041
1046
|
if (property instanceof DerivedProperty || property instanceof Property) {
|
1042
|
-
|
1047
|
+
property_setMultiplicity(property, val);
|
1043
1048
|
diagramEditorState.renderer.render();
|
1044
1049
|
}
|
1045
1050
|
};
|
@@ -1059,7 +1064,7 @@ const DiagramEditorInlinePropertyEditorInner = observer(
|
|
1059
1064
|
};
|
1060
1065
|
const changePropertyType = (val: PackageableElementOption<Type>): void => {
|
1061
1066
|
if (property instanceof Property || property instanceof DerivedProperty) {
|
1062
|
-
|
1067
|
+
property_setGenericType(property, new GenericType(val.value));
|
1063
1068
|
}
|
1064
1069
|
};
|
1065
1070
|
|
@@ -15,6 +15,7 @@
|
|
15
15
|
*/
|
16
16
|
|
17
17
|
import type { PureModel } from '@finos/legend-graph';
|
18
|
+
import { deleteEntry } from '@finos/legend-shared';
|
18
19
|
import type { ClassView } from '../models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView';
|
19
20
|
import type { Diagram } from '../models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram';
|
20
21
|
import { Point } from '../models/metamodels/pure/packageableElements/diagram/geometry/DSLDiagram_Point';
|
@@ -51,14 +52,14 @@ export const cleanUpDeadReferencesInDiagram = (
|
|
51
52
|
.includes(propertyView.property.value.name),
|
52
53
|
);
|
53
54
|
propertyViewsToRemove.forEach((propertyView) =>
|
54
|
-
diagram.
|
55
|
+
deleteEntry(diagram.propertyViews, propertyView),
|
55
56
|
);
|
56
57
|
|
57
58
|
// Fix orphan class views
|
58
59
|
const classViewsToRemove = diagram.classViews.filter(
|
59
60
|
(cv) => !graph.getNullableClass(cv.class.value.path),
|
60
61
|
);
|
61
|
-
classViewsToRemove.forEach((cw) => diagram.
|
62
|
+
classViewsToRemove.forEach((cw) => deleteEntry(diagram.classViews, cw));
|
62
63
|
|
63
64
|
// Fix orphan gneralization views
|
64
65
|
const generalizationViewsToRemove = diagram.generalizationViews.filter(
|
@@ -74,6 +75,6 @@ export const cleanUpDeadReferencesInDiagram = (
|
|
74
75
|
},
|
75
76
|
);
|
76
77
|
generalizationViewsToRemove.forEach((g) =>
|
77
|
-
diagram.
|
78
|
+
deleteEntry(diagram.generalizationViews, g),
|
78
79
|
);
|
79
80
|
};
|
package/src/index.ts
CHANGED
@@ -24,10 +24,8 @@ export { DiagramRenderer, DIAGRAM_INTERACTION_MODE } from './DiagramRenderer';
|
|
24
24
|
|
25
25
|
export { Diagram } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_Diagram';
|
26
26
|
export { ClassView } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassView';
|
27
|
-
export {
|
28
|
-
|
29
|
-
manageInsidePointsDynamically,
|
30
|
-
} from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView';
|
27
|
+
export { RelationshipView } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView';
|
28
|
+
export { _relationView_manageInsidePointsDynamically } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper';
|
31
29
|
export { PropertyHolderView } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_PropertyHolderView';
|
32
30
|
export { PropertyView } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_PropertyView';
|
33
31
|
export { AssociationView } from './models/metamodels/pure/packageableElements/diagram/DSLDiagram_AssociationView';
|
@@ -14,7 +14,7 @@
|
|
14
14
|
* limitations under the License.
|
15
15
|
*/
|
16
16
|
|
17
|
-
import { computed, observable,
|
17
|
+
import { computed, observable, makeObservable } from 'mobx';
|
18
18
|
import { hashArray, type Hashable } from '@finos/legend-shared';
|
19
19
|
import { PositionedRectangle } from './geometry/DSLDiagram_PositionedRectangle';
|
20
20
|
import { Rectangle } from './geometry/DSLDiagram_Rectangle';
|
@@ -43,9 +43,6 @@ export class ClassView extends PositionedRectangle implements Hashable {
|
|
43
43
|
hideProperties: observable,
|
44
44
|
hideTaggedValues: observable,
|
45
45
|
hideStereotypes: observable,
|
46
|
-
setHideProperties: action,
|
47
|
-
setHideStereotypes: action,
|
48
|
-
setHideTaggedValues: action,
|
49
46
|
hashCode: computed,
|
50
47
|
});
|
51
48
|
|
@@ -54,16 +51,6 @@ export class ClassView extends PositionedRectangle implements Hashable {
|
|
54
51
|
this.class = _class;
|
55
52
|
}
|
56
53
|
|
57
|
-
setHideProperties(val: boolean): void {
|
58
|
-
this.hideProperties = val;
|
59
|
-
}
|
60
|
-
setHideStereotypes(val: boolean): void {
|
61
|
-
this.hideStereotypes = val;
|
62
|
-
}
|
63
|
-
setHideTaggedValues(val: boolean): void {
|
64
|
-
this.hideTaggedValues = val;
|
65
|
-
}
|
66
|
-
|
67
54
|
override get hashCode(): string {
|
68
55
|
return hashArray([
|
69
56
|
DIAGRAM_HASH_STRUCTURE.CLASS_VIEW,
|
package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_ClassViewReference.ts
CHANGED
@@ -14,13 +14,12 @@
|
|
14
14
|
* limitations under the License.
|
15
15
|
*/
|
16
16
|
|
17
|
-
import { observable,
|
17
|
+
import { observable, makeObservable } from 'mobx';
|
18
18
|
import type { Diagram } from './DSLDiagram_Diagram';
|
19
19
|
import type { ClassView } from './DSLDiagram_ClassView';
|
20
20
|
import {
|
21
21
|
PackageableElementExplicitReference,
|
22
22
|
ReferenceWithOwner,
|
23
|
-
setPackageableElementReferenceValue,
|
24
23
|
type PackageableElementImplicitReference,
|
25
24
|
type PackageableElementReference,
|
26
25
|
} from '@finos/legend-graph';
|
@@ -37,17 +36,11 @@ export abstract class ClassViewReference extends ReferenceWithOwner {
|
|
37
36
|
|
38
37
|
makeObservable(this, {
|
39
38
|
value: observable,
|
40
|
-
setValue: action,
|
41
39
|
});
|
42
40
|
|
43
41
|
this.ownerReference = ownerReference;
|
44
42
|
this.value = value;
|
45
43
|
}
|
46
|
-
|
47
|
-
setValue(value: ClassView): void {
|
48
|
-
this.value = value;
|
49
|
-
setPackageableElementReferenceValue(this.ownerReference, value.owner);
|
50
|
-
}
|
51
44
|
}
|
52
45
|
|
53
46
|
export class ClassViewExplicitReference extends ClassViewReference {
|
@@ -14,13 +14,8 @@
|
|
14
14
|
* limitations under the License.
|
15
15
|
*/
|
16
16
|
|
17
|
-
import { observable,
|
18
|
-
import {
|
19
|
-
hashArray,
|
20
|
-
addUniqueEntry,
|
21
|
-
deleteEntry,
|
22
|
-
type Hashable,
|
23
|
-
} from '@finos/legend-shared';
|
17
|
+
import { observable, makeObservable, override } from 'mobx';
|
18
|
+
import { hashArray, type Hashable } from '@finos/legend-shared';
|
24
19
|
import type { ClassView } from './DSLDiagram_ClassView';
|
25
20
|
import type { PropertyView } from './DSLDiagram_PropertyView';
|
26
21
|
import type { GeneralizationView } from './DSLDiagram_GeneralizationView';
|
@@ -45,55 +40,10 @@ export class Diagram extends PackageableElement implements Hashable {
|
|
45
40
|
associationViews: observable,
|
46
41
|
generalizationViews: observable,
|
47
42
|
propertyViews: observable,
|
48
|
-
setClassViews: action,
|
49
|
-
addClassView: action,
|
50
|
-
deleteClassView: action,
|
51
|
-
setAssociationViews: action,
|
52
|
-
deleteAssociationView: action,
|
53
|
-
setGeneralizationViews: action,
|
54
|
-
addGeneralizationView: action,
|
55
|
-
deleteGeneralizationView: action,
|
56
|
-
setPropertyViews: action,
|
57
|
-
addPropertyView: action,
|
58
|
-
deletePropertyView: action,
|
59
43
|
_elementHashCode: override,
|
60
44
|
});
|
61
45
|
}
|
62
46
|
|
63
|
-
setClassViews(val: ClassView[]): void {
|
64
|
-
this.classViews = val;
|
65
|
-
}
|
66
|
-
addClassView(val: ClassView): void {
|
67
|
-
addUniqueEntry(this.classViews, val);
|
68
|
-
}
|
69
|
-
deleteClassView(val: ClassView): void {
|
70
|
-
deleteEntry(this.classViews, val);
|
71
|
-
}
|
72
|
-
setAssociationViews(val: AssociationView[]): void {
|
73
|
-
this.associationViews = val;
|
74
|
-
}
|
75
|
-
deleteAssociationView(val: AssociationView): void {
|
76
|
-
deleteEntry(this.associationViews, val);
|
77
|
-
}
|
78
|
-
setGeneralizationViews(val: GeneralizationView[]): void {
|
79
|
-
this.generalizationViews = val;
|
80
|
-
}
|
81
|
-
addGeneralizationView(val: GeneralizationView): void {
|
82
|
-
addUniqueEntry(this.generalizationViews, val);
|
83
|
-
}
|
84
|
-
deleteGeneralizationView(val: GeneralizationView): void {
|
85
|
-
deleteEntry(this.generalizationViews, val);
|
86
|
-
}
|
87
|
-
setPropertyViews(val: PropertyView[]): void {
|
88
|
-
this.propertyViews = val;
|
89
|
-
}
|
90
|
-
addPropertyView(val: PropertyView): void {
|
91
|
-
addUniqueEntry(this.propertyViews, val);
|
92
|
-
}
|
93
|
-
deletePropertyView(val: PropertyView): void {
|
94
|
-
deleteEntry(this.propertyViews, val);
|
95
|
-
}
|
96
|
-
|
97
47
|
protected override get _elementHashCode(): string {
|
98
48
|
return hashArray([
|
99
49
|
DIAGRAM_HASH_STRUCTURE.DIAGRAM,
|
package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_GraphModifierHelper.ts
ADDED
@@ -0,0 +1,165 @@
|
|
1
|
+
/**
|
2
|
+
* Copyright (c) 2020-present, Goldman Sachs
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
import type { ClassView } from './DSLDiagram_ClassView';
|
18
|
+
import type { RelationshipView } from './DSLDiagram_RelationshipView';
|
19
|
+
import { Point } from './geometry/DSLDiagram_Point';
|
20
|
+
import { Vector } from './geometry/DSLDiagram_Vector';
|
21
|
+
|
22
|
+
export const _relationView_setPath = (
|
23
|
+
relationView: RelationshipView,
|
24
|
+
val: Point[],
|
25
|
+
): void => {
|
26
|
+
relationView.path = val;
|
27
|
+
};
|
28
|
+
|
29
|
+
/**
|
30
|
+
* For a path, only counts the points which lie outside of the 2 class views
|
31
|
+
*/
|
32
|
+
export const _relationView_manageInsidePointsDynamically = (
|
33
|
+
path: Point[],
|
34
|
+
from: ClassView,
|
35
|
+
to: ClassView,
|
36
|
+
): Point[] => {
|
37
|
+
if (!path.length) {
|
38
|
+
return [];
|
39
|
+
}
|
40
|
+
|
41
|
+
let start = 0;
|
42
|
+
let startPoint = path[start] as Point;
|
43
|
+
|
44
|
+
while (start < path.length - 1 && from.contains(startPoint.x, startPoint.y)) {
|
45
|
+
start++;
|
46
|
+
startPoint = path[start] as Point;
|
47
|
+
}
|
48
|
+
|
49
|
+
let end = path.length - 1;
|
50
|
+
let endPoint = path[end] as Point;
|
51
|
+
|
52
|
+
while (end > 0 && to.contains(endPoint.x, endPoint.y)) {
|
53
|
+
end--;
|
54
|
+
endPoint = path[end] as Point;
|
55
|
+
}
|
56
|
+
|
57
|
+
return path.slice(start - 1, end + 2);
|
58
|
+
};
|
59
|
+
|
60
|
+
/**
|
61
|
+
* Flatten the path if the angle is wide enough
|
62
|
+
* Also `swallow` points in path which lie inside of the rectangle of a view
|
63
|
+
*/
|
64
|
+
export const _relationView_possiblyFlattenPath = (
|
65
|
+
relationView: RelationshipView,
|
66
|
+
): void => {
|
67
|
+
const fullPath = relationView.buildFullPath();
|
68
|
+
// NOTE: this method here will `swallow` up points inside of the boxes
|
69
|
+
const newPath = _relationView_manageInsidePointsDynamically(
|
70
|
+
fullPath,
|
71
|
+
relationView.from.classView.value,
|
72
|
+
relationView.to.classView.value,
|
73
|
+
);
|
74
|
+
|
75
|
+
// recompute the offset point from center inside of `from` and `to` classviews.
|
76
|
+
// for each, we first check if `manageInsidePointsDynamically` removes any points from the full path
|
77
|
+
// if it does we will update the offset
|
78
|
+
if (newPath[0] !== fullPath[0]) {
|
79
|
+
const center = relationView.from.classView.value.center();
|
80
|
+
|
81
|
+
relationView.from.offsetX = (newPath[0] as Point).x - center.x;
|
82
|
+
relationView.from.offsetY = (newPath[0] as Point).y - center.y;
|
83
|
+
}
|
84
|
+
|
85
|
+
if (newPath[newPath.length - 1] !== fullPath[fullPath.length - 1]) {
|
86
|
+
const center = relationView.to.classView.value.center();
|
87
|
+
relationView.to.offsetX =
|
88
|
+
(newPath[newPath.length - 1] as Point).x - center.x;
|
89
|
+
relationView.to.offsetY =
|
90
|
+
(newPath[newPath.length - 1] as Point).y - center.y;
|
91
|
+
}
|
92
|
+
|
93
|
+
// find the point which can be flattened due to its wide angle
|
94
|
+
const result = [];
|
95
|
+
for (let i = 0; i < newPath.length - 2; i++) {
|
96
|
+
const v1 = Vector.fromPoints(
|
97
|
+
newPath[i + 1] as Point,
|
98
|
+
newPath[i] as Point,
|
99
|
+
).norm();
|
100
|
+
const v2 = Vector.fromPoints(
|
101
|
+
newPath[i + 1] as Point,
|
102
|
+
newPath[i + 2] as Point,
|
103
|
+
).norm();
|
104
|
+
const dot = v1.dotProduct(v2);
|
105
|
+
const angle = (Math.acos(dot) * 180) / Math.PI;
|
106
|
+
if (Math.abs(angle - 180) > 5) {
|
107
|
+
result.push(newPath[i + 1] as Point);
|
108
|
+
}
|
109
|
+
}
|
110
|
+
// here's where we will modify the path, i.e. swallow inside points if we have to
|
111
|
+
_relationView_setPath(relationView, result);
|
112
|
+
};
|
113
|
+
|
114
|
+
/**
|
115
|
+
* Based on the location, find the point on the path that matches or create new point
|
116
|
+
* (within a threshold of proximity) from the coordinate and put this in the path array
|
117
|
+
* so it doesn't look too weird
|
118
|
+
*/
|
119
|
+
export const _findOrBuildPoint = (
|
120
|
+
relationView: RelationshipView,
|
121
|
+
x: number,
|
122
|
+
y: number,
|
123
|
+
zoom: number,
|
124
|
+
allowChange = true,
|
125
|
+
): Point | undefined => {
|
126
|
+
for (const pt of relationView.path) {
|
127
|
+
if (
|
128
|
+
Math.sqrt((x - pt.x) * (x - pt.x) + (y - pt.y) * (y - pt.y)) <
|
129
|
+
10 / zoom
|
130
|
+
) {
|
131
|
+
return pt;
|
132
|
+
}
|
133
|
+
}
|
134
|
+
|
135
|
+
const fullPath = relationView.buildFullPath(allowChange);
|
136
|
+
const newPath = [];
|
137
|
+
let point;
|
138
|
+
|
139
|
+
for (let i = 0; i < fullPath.length - 1; i++) {
|
140
|
+
const a = fullPath[i] as Point;
|
141
|
+
const b = fullPath[i + 1] as Point;
|
142
|
+
const n = new Vector(a.x, a.y).normal(new Vector(b.x, b.y)).norm();
|
143
|
+
const v = Vector.fromPoints(a, new Point(x, y));
|
144
|
+
|
145
|
+
if (Math.abs(n.dotProduct(v)) < 5 / zoom) {
|
146
|
+
const lx = (a.x < b.x ? a.x : b.x) - 5 / zoom;
|
147
|
+
const hx = (a.x < b.x ? b.x : a.x) + 5 / zoom;
|
148
|
+
const ly = (a.y < b.y ? a.y : b.y) - 5 / zoom;
|
149
|
+
const hy = (a.y < b.y ? b.y : a.y) + 5 / zoom;
|
150
|
+
|
151
|
+
if (lx <= x && x <= hx && ly <= y && y <= hy) {
|
152
|
+
point = new Point(x, y);
|
153
|
+
newPath.push(point);
|
154
|
+
}
|
155
|
+
}
|
156
|
+
|
157
|
+
if (i < fullPath.length - 2) {
|
158
|
+
newPath.push(fullPath[i + 1] as Point);
|
159
|
+
}
|
160
|
+
}
|
161
|
+
if (point && allowChange) {
|
162
|
+
_relationView_setPath(relationView, newPath);
|
163
|
+
}
|
164
|
+
return point;
|
165
|
+
};
|
package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipEdgeView.ts
CHANGED
@@ -14,7 +14,7 @@
|
|
14
14
|
* limitations under the License.
|
15
15
|
*/
|
16
16
|
|
17
|
-
import { observable,
|
17
|
+
import { observable, makeObservable } from 'mobx';
|
18
18
|
import type { ClassViewReference } from './DSLDiagram_ClassViewReference';
|
19
19
|
|
20
20
|
export class RelationShipEdgeView {
|
@@ -26,17 +26,8 @@ export class RelationShipEdgeView {
|
|
26
26
|
makeObservable(this, {
|
27
27
|
offsetX: observable,
|
28
28
|
offsetY: observable,
|
29
|
-
setOffsetX: action,
|
30
|
-
setOffsetY: action,
|
31
29
|
});
|
32
30
|
|
33
31
|
this.classView = classView;
|
34
32
|
}
|
35
|
-
|
36
|
-
setOffsetX(val: number): void {
|
37
|
-
this.offsetX = val;
|
38
|
-
}
|
39
|
-
setOffsetY(val: number): void {
|
40
|
-
this.offsetY = val;
|
41
|
-
}
|
42
33
|
}
|
package/src/models/metamodels/pure/packageableElements/diagram/DSLDiagram_RelationshipView.ts
CHANGED
@@ -14,46 +14,15 @@
|
|
14
14
|
* limitations under the License.
|
15
15
|
*/
|
16
16
|
|
17
|
-
import { observable,
|
18
|
-
import { hashArray,
|
17
|
+
import { observable, computed, makeObservable } from 'mobx';
|
18
|
+
import { hashArray, type Hashable } from '@finos/legend-shared';
|
19
19
|
import { RelationShipEdgeView as RelationshipEdgeView } from './DSLDiagram_RelationshipEdgeView';
|
20
20
|
import { Point } from './geometry/DSLDiagram_Point';
|
21
21
|
import type { ClassView } from './DSLDiagram_ClassView';
|
22
|
-
import { Vector } from './geometry/DSLDiagram_Vector';
|
23
22
|
import type { Diagram } from './DSLDiagram_Diagram';
|
24
23
|
import { ClassViewExplicitReference } from './DSLDiagram_ClassViewReference';
|
25
24
|
import { DIAGRAM_HASH_STRUCTURE } from '../../../../DSLDiagram_ModelUtils';
|
26
|
-
|
27
|
-
/**
|
28
|
-
* For a path, only counts the points which lie outside of the 2 class views
|
29
|
-
*/
|
30
|
-
export const manageInsidePointsDynamically = (
|
31
|
-
path: Point[],
|
32
|
-
from: ClassView,
|
33
|
-
to: ClassView,
|
34
|
-
): Point[] => {
|
35
|
-
if (!path.length) {
|
36
|
-
return [];
|
37
|
-
}
|
38
|
-
|
39
|
-
let start = 0;
|
40
|
-
let startPoint = path[start] as Point;
|
41
|
-
|
42
|
-
while (start < path.length - 1 && from.contains(startPoint.x, startPoint.y)) {
|
43
|
-
start++;
|
44
|
-
startPoint = path[start] as Point;
|
45
|
-
}
|
46
|
-
|
47
|
-
let end = path.length - 1;
|
48
|
-
let endPoint = path[end] as Point;
|
49
|
-
|
50
|
-
while (end > 0 && to.contains(endPoint.x, endPoint.y)) {
|
51
|
-
end--;
|
52
|
-
endPoint = path[end] as Point;
|
53
|
-
}
|
54
|
-
|
55
|
-
return path.slice(start - 1, end + 2);
|
56
|
-
};
|
25
|
+
import { _relationView_manageInsidePointsDynamically } from './DSLDiagram_GraphModifierHelper';
|
57
26
|
|
58
27
|
export class RelationshipView implements Hashable {
|
59
28
|
owner: Diagram;
|
@@ -66,8 +35,6 @@ export class RelationshipView implements Hashable {
|
|
66
35
|
constructor(owner: Diagram, from: ClassView, to: ClassView) {
|
67
36
|
makeObservable(this, {
|
68
37
|
path: observable,
|
69
|
-
setPath: action,
|
70
|
-
changePoint: action,
|
71
38
|
fullPath: computed,
|
72
39
|
});
|
73
40
|
|
@@ -78,13 +45,6 @@ export class RelationshipView implements Hashable {
|
|
78
45
|
this.to = new RelationshipEdgeView(ClassViewExplicitReference.create(to));
|
79
46
|
}
|
80
47
|
|
81
|
-
setPath(val: Point[]): void {
|
82
|
-
this.path = val;
|
83
|
-
}
|
84
|
-
changePoint(val: Point, newVal: Point): void {
|
85
|
-
changeEntry(this.path, val, newVal);
|
86
|
-
}
|
87
|
-
|
88
48
|
/**
|
89
49
|
* Compute the full path for an edge, but notice here that the end points are recomputed every time, as such
|
90
50
|
* `path` only stores point that matters to the edge but are not end points
|
@@ -101,114 +61,13 @@ export class RelationshipView implements Hashable {
|
|
101
61
|
* This method will compute the full path from the offset within class view for persistence purpose
|
102
62
|
*/
|
103
63
|
get fullPath(): Point[] {
|
104
|
-
return
|
64
|
+
return _relationView_manageInsidePointsDynamically(
|
105
65
|
this.buildFullPath(),
|
106
66
|
this.from.classView.value,
|
107
67
|
this.to.classView.value,
|
108
68
|
);
|
109
69
|
}
|
110
70
|
|
111
|
-
/**
|
112
|
-
* Flatten the path if the angle is wide enough
|
113
|
-
* Also `swallow` points in path which lie inside of the rectangle of a view
|
114
|
-
*/
|
115
|
-
possiblyFlattenPath(): void {
|
116
|
-
const fullPath = this.buildFullPath();
|
117
|
-
// NOTE: this method here will `swallow` up points inside of the boxes
|
118
|
-
const newPath = manageInsidePointsDynamically(
|
119
|
-
fullPath,
|
120
|
-
this.from.classView.value,
|
121
|
-
this.to.classView.value,
|
122
|
-
);
|
123
|
-
|
124
|
-
// recompute the offset point from center inside of `from` and `to` classviews.
|
125
|
-
// for each, we first check if `manageInsidePointsDynamically` removes any points from the full path
|
126
|
-
// if it does we will update the offset
|
127
|
-
if (newPath[0] !== fullPath[0]) {
|
128
|
-
const center = this.from.classView.value.center();
|
129
|
-
this.from.setOffsetX((newPath[0] as Point).x - center.x);
|
130
|
-
this.from.setOffsetY((newPath[0] as Point).y - center.y);
|
131
|
-
}
|
132
|
-
|
133
|
-
if (newPath[newPath.length - 1] !== fullPath[fullPath.length - 1]) {
|
134
|
-
const center = this.to.classView.value.center();
|
135
|
-
this.to.setOffsetX((newPath[newPath.length - 1] as Point).x - center.x);
|
136
|
-
this.to.setOffsetY((newPath[newPath.length - 1] as Point).y - center.y);
|
137
|
-
}
|
138
|
-
|
139
|
-
// find the point which can be flattened due to its wide angle
|
140
|
-
const result = [];
|
141
|
-
for (let i = 0; i < newPath.length - 2; i++) {
|
142
|
-
const v1 = Vector.fromPoints(
|
143
|
-
newPath[i + 1] as Point,
|
144
|
-
newPath[i] as Point,
|
145
|
-
).norm();
|
146
|
-
const v2 = Vector.fromPoints(
|
147
|
-
newPath[i + 1] as Point,
|
148
|
-
newPath[i + 2] as Point,
|
149
|
-
).norm();
|
150
|
-
const dot = v1.dotProduct(v2);
|
151
|
-
const angle = (Math.acos(dot) * 180) / Math.PI;
|
152
|
-
if (Math.abs(angle - 180) > 5) {
|
153
|
-
result.push(newPath[i + 1] as Point);
|
154
|
-
}
|
155
|
-
}
|
156
|
-
// here's where we will modify the path, i.e. swallow inside points if we have to
|
157
|
-
this.setPath(result);
|
158
|
-
}
|
159
|
-
|
160
|
-
/**
|
161
|
-
* Based on the location, find the point on the path that matches or create new point
|
162
|
-
* (within a threshold of proximity) from the coordinate and put this in the path array
|
163
|
-
* so it doesn't look too weird
|
164
|
-
*/
|
165
|
-
findOrBuildPoint(
|
166
|
-
x: number,
|
167
|
-
y: number,
|
168
|
-
zoom: number,
|
169
|
-
allowChange = true,
|
170
|
-
): Point | undefined {
|
171
|
-
for (const pt of this.path) {
|
172
|
-
if (
|
173
|
-
Math.sqrt((x - pt.x) * (x - pt.x) + (y - pt.y) * (y - pt.y)) <
|
174
|
-
10 / zoom
|
175
|
-
) {
|
176
|
-
return pt;
|
177
|
-
}
|
178
|
-
}
|
179
|
-
|
180
|
-
const fullPath = this.buildFullPath(allowChange);
|
181
|
-
const newPath = [];
|
182
|
-
let point;
|
183
|
-
|
184
|
-
for (let i = 0; i < fullPath.length - 1; i++) {
|
185
|
-
const a = fullPath[i] as Point;
|
186
|
-
const b = fullPath[i + 1] as Point;
|
187
|
-
const n = new Vector(a.x, a.y).normal(new Vector(b.x, b.y)).norm();
|
188
|
-
const v = Vector.fromPoints(a, new Point(x, y));
|
189
|
-
|
190
|
-
if (Math.abs(n.dotProduct(v)) < 5 / zoom) {
|
191
|
-
const lx = (a.x < b.x ? a.x : b.x) - 5 / zoom;
|
192
|
-
const hx = (a.x < b.x ? b.x : a.x) + 5 / zoom;
|
193
|
-
const ly = (a.y < b.y ? a.y : b.y) - 5 / zoom;
|
194
|
-
const hy = (a.y < b.y ? b.y : a.y) + 5 / zoom;
|
195
|
-
|
196
|
-
if (lx <= x && x <= hx && ly <= y && y <= hy) {
|
197
|
-
point = new Point(x, y);
|
198
|
-
newPath.push(point);
|
199
|
-
}
|
200
|
-
}
|
201
|
-
|
202
|
-
if (i < fullPath.length - 2) {
|
203
|
-
newPath.push(fullPath[i + 1] as Point);
|
204
|
-
}
|
205
|
-
}
|
206
|
-
if (point && allowChange) {
|
207
|
-
this.setPath(newPath);
|
208
|
-
}
|
209
|
-
return point;
|
210
|
-
}
|
211
|
-
|
212
71
|
/**
|
213
72
|
* Calculate the end points of the edge using offset, otherwise, use the center
|
214
73
|
*/
|
@@ -224,8 +83,8 @@ export class RelationshipView implements Hashable {
|
|
224
83
|
return new Point(newX, newY);
|
225
84
|
}
|
226
85
|
if (allowChange) {
|
227
|
-
edgeView.
|
228
|
-
edgeView.
|
86
|
+
edgeView.offsetX = 0;
|
87
|
+
edgeView.offsetY = 0;
|
229
88
|
}
|
230
89
|
return new Point(center.x, center.y);
|
231
90
|
}
|