ngx-vflow 0.4.0 → 0.6.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/esm2022/lib/vflow/components/node/node.component.mjs +12 -6
- package/esm2022/lib/vflow/components/vflow/vflow.component.mjs +51 -9
- package/esm2022/lib/vflow/directives/changes-controller.directive.mjs +115 -14
- package/esm2022/lib/vflow/directives/map-context.directive.mjs +7 -6
- package/esm2022/lib/vflow/directives/pointer.directive.mjs +84 -0
- package/esm2022/lib/vflow/directives/root-pointer.directive.mjs +42 -0
- package/esm2022/lib/vflow/directives/root-svg-context.directive.mjs +5 -2
- package/esm2022/lib/vflow/directives/selectable.directive.mjs +1 -1
- package/esm2022/lib/vflow/directives/space-point-context.directive.mjs +10 -6
- package/esm2022/lib/vflow/interfaces/component-node-event.interface.mjs +2 -0
- package/esm2022/lib/vflow/interfaces/node.interface.mjs +1 -1
- package/esm2022/lib/vflow/models/node.model.mjs +25 -5
- package/esm2022/lib/vflow/public-components/custom-node.component.mjs +51 -0
- package/esm2022/lib/vflow/services/component-event-bus.service.mjs +18 -0
- package/esm2022/lib/vflow/services/draggable.service.mjs +2 -2
- package/esm2022/lib/vflow/services/selection.service.mjs +2 -2
- package/esm2022/lib/vflow/vflow.module.mjs +9 -3
- package/esm2022/public-api.mjs +3 -1
- package/fesm2022/ngx-vflow.mjs +397 -42
- package/fesm2022/ngx-vflow.mjs.map +1 -1
- package/lib/vflow/components/node/node.component.d.ts +10 -9
- package/lib/vflow/components/vflow/vflow.component.d.ts +9 -2
- package/lib/vflow/directives/changes-controller.directive.d.ts +35 -9
- package/lib/vflow/directives/pointer.directive.d.ts +21 -0
- package/lib/vflow/directives/root-pointer.directive.d.ts +40 -0
- package/lib/vflow/directives/space-point-context.directive.d.ts +13 -3
- package/lib/vflow/interfaces/component-node-event.interface.d.ts +32 -0
- package/lib/vflow/interfaces/node.interface.d.ts +9 -1
- package/lib/vflow/models/node.model.d.ts +14 -1
- package/lib/vflow/public-components/custom-node.component.d.ts +20 -0
- package/lib/vflow/services/component-event-bus.service.d.ts +9 -0
- package/lib/vflow/services/selection.service.d.ts +4 -1
- package/lib/vflow/vflow.module.d.ts +5 -3
- package/package.json +1 -1
- package/public-api.d.ts +2 -0
package/fesm2022/ngx-vflow.mjs
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import * as i1 from '@angular/common';
|
|
2
2
|
import { CommonModule } from '@angular/common';
|
|
3
3
|
import * as i0 from '@angular/core';
|
|
4
|
-
import { signal, Injectable, inject, ElementRef, Directive, computed, effect, Input, TemplateRef, EventEmitter, Output,
|
|
4
|
+
import { signal, Injectable, inject, ElementRef, Directive, computed, effect, untracked, Input, TemplateRef, EventEmitter, Output, DestroyRef, runInInjectionContext, HostListener, Injector, NgZone, Component, ChangeDetectionStrategy, ViewChild, ContentChild, NgModule } from '@angular/core';
|
|
5
5
|
import { select } from 'd3-selection';
|
|
6
6
|
import { zoomIdentity, zoom } from 'd3-zoom';
|
|
7
|
-
import { Subject, tap,
|
|
8
|
-
import { takeUntilDestroyed,
|
|
7
|
+
import { Subject, tap, merge, BehaviorSubject, observeOn, animationFrameScheduler, switchMap, skip, map, pairwise, filter, distinctUntilChanged, asyncScheduler, zip, Observable, fromEvent, share, Subscription, startWith } from 'rxjs';
|
|
8
|
+
import { takeUntilDestroyed, toSignal, toObservable } from '@angular/core/rxjs-interop';
|
|
9
9
|
import { drag } from 'd3-drag';
|
|
10
10
|
import { path } from 'd3-path';
|
|
11
11
|
import { __decorate } from 'tslib';
|
|
@@ -131,7 +131,7 @@ class SelectionService {
|
|
|
131
131
|
this.flowEntitiesService = inject(FlowEntitiesService);
|
|
132
132
|
this.viewport$ = new Subject();
|
|
133
133
|
this.resetSelection = this.viewport$.pipe(tap(({ start, end, target }) => {
|
|
134
|
-
if (start && end) {
|
|
134
|
+
if (start && end && target) {
|
|
135
135
|
const delta = SelectionService.delta;
|
|
136
136
|
const diffX = Math.abs(end.x - start.x);
|
|
137
137
|
const diffY = Math.abs(end.y - start.y);
|
|
@@ -176,8 +176,7 @@ class MapContextDirective {
|
|
|
176
176
|
this.zoomableSelection = select(this.host);
|
|
177
177
|
this.viewportForSelection = {};
|
|
178
178
|
// under the hood this effect triggers handleZoom, so error throws without this flag
|
|
179
|
-
|
|
180
|
-
this.manualViewportChangeEffect = effect(() => setTimeout(() => {
|
|
179
|
+
this.manualViewportChangeEffect = effect(() => {
|
|
181
180
|
const viewport = this.viewportService.writableViewport();
|
|
182
181
|
const state = viewport.state;
|
|
183
182
|
if (viewport.changeType === 'initial') {
|
|
@@ -190,7 +189,9 @@ class MapContextDirective {
|
|
|
190
189
|
}
|
|
191
190
|
// If only pan provided
|
|
192
191
|
if ((isDefined(state.x) && isDefined(state.y)) && !isDefined(state.zoom)) {
|
|
193
|
-
|
|
192
|
+
// remain same zoom value
|
|
193
|
+
const zoom = untracked(this.viewportService.readableViewport).zoom;
|
|
194
|
+
this.rootSvgSelection.call(this.zoomBehavior.transform, zoomIdentity.translate(state.x, state.y).scale(zoom));
|
|
194
195
|
return;
|
|
195
196
|
}
|
|
196
197
|
// If whole viewort state provided
|
|
@@ -198,7 +199,7 @@ class MapContextDirective {
|
|
|
198
199
|
this.rootSvgSelection.call(this.zoomBehavior.transform, zoomIdentity.translate(state.x, state.y).scale(state.zoom));
|
|
199
200
|
return;
|
|
200
201
|
}
|
|
201
|
-
}
|
|
202
|
+
}, { allowSignalWrites: true });
|
|
202
203
|
this.handleZoom = ({ transform }) => {
|
|
203
204
|
// update public signal for user to read
|
|
204
205
|
this.viewportService.readableViewport.set(mapTransformToViewportState(transform));
|
|
@@ -287,7 +288,7 @@ class DraggableService {
|
|
|
287
288
|
deltaY = model.point().y - event.y;
|
|
288
289
|
})
|
|
289
290
|
.on('drag', (event) => {
|
|
290
|
-
model.
|
|
291
|
+
model.setPoint({
|
|
291
292
|
x: round(event.x + deltaX),
|
|
292
293
|
y: round(event.y + deltaY)
|
|
293
294
|
});
|
|
@@ -479,12 +480,81 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
479
480
|
type: Injectable
|
|
480
481
|
}] });
|
|
481
482
|
|
|
483
|
+
class ComponentEventBusService {
|
|
484
|
+
constructor() {
|
|
485
|
+
this._event$ = new Subject();
|
|
486
|
+
this.event$ = this._event$.asObservable();
|
|
487
|
+
}
|
|
488
|
+
pushEvent(event) {
|
|
489
|
+
this._event$.next(event);
|
|
490
|
+
}
|
|
491
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ComponentEventBusService, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
492
|
+
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ComponentEventBusService }); }
|
|
493
|
+
}
|
|
494
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ComponentEventBusService, decorators: [{
|
|
495
|
+
type: Injectable
|
|
496
|
+
}] });
|
|
497
|
+
|
|
498
|
+
class CustomNodeComponent {
|
|
499
|
+
constructor() {
|
|
500
|
+
this.eventBus = inject(ComponentEventBusService);
|
|
501
|
+
this.destroyRef = inject(DestroyRef);
|
|
502
|
+
/**
|
|
503
|
+
* Signal with selected state of node
|
|
504
|
+
*/
|
|
505
|
+
this.selected = signal(false);
|
|
506
|
+
}
|
|
507
|
+
set _selected(value) {
|
|
508
|
+
this.selected.set(value);
|
|
509
|
+
}
|
|
510
|
+
ngOnInit() {
|
|
511
|
+
this.trackEvents();
|
|
512
|
+
}
|
|
513
|
+
trackEvents() {
|
|
514
|
+
const props = Object.getOwnPropertyNames(this);
|
|
515
|
+
const emitters = new Map();
|
|
516
|
+
for (const prop of props) {
|
|
517
|
+
const field = this[prop];
|
|
518
|
+
if (field instanceof EventEmitter) {
|
|
519
|
+
emitters.set(field, prop);
|
|
520
|
+
}
|
|
521
|
+
}
|
|
522
|
+
merge(...Array.from(emitters.keys()).map(emitter => emitter.pipe(tap((event) => {
|
|
523
|
+
this.eventBus.pushEvent({
|
|
524
|
+
nodeId: this.node.id,
|
|
525
|
+
eventName: emitters.get(emitter),
|
|
526
|
+
eventPayload: event
|
|
527
|
+
});
|
|
528
|
+
}))))
|
|
529
|
+
.pipe(takeUntilDestroyed(this.destroyRef))
|
|
530
|
+
.subscribe();
|
|
531
|
+
}
|
|
532
|
+
;
|
|
533
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: CustomNodeComponent, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
534
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: CustomNodeComponent, inputs: { node: "node", _selected: "_selected" }, ngImport: i0 }); }
|
|
535
|
+
}
|
|
536
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: CustomNodeComponent, decorators: [{
|
|
537
|
+
type: Directive
|
|
538
|
+
}], propDecorators: { node: [{
|
|
539
|
+
type: Input
|
|
540
|
+
}], _selected: [{
|
|
541
|
+
type: Input
|
|
542
|
+
}] } });
|
|
543
|
+
|
|
482
544
|
class NodeModel {
|
|
545
|
+
static { this.defaultTypeSize = {
|
|
546
|
+
width: 100,
|
|
547
|
+
height: 50
|
|
548
|
+
}; }
|
|
483
549
|
constructor(node) {
|
|
484
550
|
this.node = node;
|
|
485
551
|
this.flowSettingsService = inject(FlowSettingsService);
|
|
486
|
-
this.
|
|
487
|
-
this.
|
|
552
|
+
this.internalPoint$ = new BehaviorSubject({ x: 0, y: 0 });
|
|
553
|
+
this.throttledPoint$ = this.internalPoint$.pipe(observeOn(animationFrameScheduler));
|
|
554
|
+
this.point = toSignal(this.throttledPoint$, {
|
|
555
|
+
initialValue: this.internalPoint$.getValue()
|
|
556
|
+
});
|
|
557
|
+
this.point$ = this.throttledPoint$;
|
|
488
558
|
this.size = signal({ width: 0, height: 0 });
|
|
489
559
|
this.renderOrder = signal(0);
|
|
490
560
|
this.selected = signal(false);
|
|
@@ -498,10 +568,20 @@ class NodeModel {
|
|
|
498
568
|
this.draggable = true;
|
|
499
569
|
// disabled for configuration for now
|
|
500
570
|
this.magnetRadius = 20;
|
|
501
|
-
this.
|
|
571
|
+
this.isComponentType = CustomNodeComponent.isPrototypeOf(this.node.type);
|
|
572
|
+
this.componentTypeInputs = computed(() => {
|
|
573
|
+
return {
|
|
574
|
+
node: this.node,
|
|
575
|
+
_selected: this.selected()
|
|
576
|
+
};
|
|
577
|
+
});
|
|
578
|
+
this.setPoint(node.point);
|
|
502
579
|
if (isDefined(node.draggable))
|
|
503
580
|
this.draggable = node.draggable;
|
|
504
581
|
}
|
|
582
|
+
setPoint(point) {
|
|
583
|
+
this.internalPoint$.next(point);
|
|
584
|
+
}
|
|
505
585
|
}
|
|
506
586
|
|
|
507
587
|
class EdgeLabelModel {
|
|
@@ -812,20 +892,50 @@ class ChangesControllerDirective {
|
|
|
812
892
|
/**
|
|
813
893
|
* Watch nodes change
|
|
814
894
|
*/
|
|
815
|
-
this.onNodesChange =
|
|
895
|
+
this.onNodesChange = this.nodesChangeService.changes$;
|
|
896
|
+
this.onNodesChangePosition = this.nodeChangesOfType('position');
|
|
897
|
+
this.onNodesChangePositionSignle = this.singleChange(this.nodeChangesOfType('position'));
|
|
898
|
+
this.onNodesChangePositionMany = this.manyChanges(this.nodeChangesOfType('position'));
|
|
899
|
+
this.onNodesChangeAdd = this.nodeChangesOfType('add');
|
|
900
|
+
this.onNodesChangeAddSingle = this.singleChange(this.nodeChangesOfType('add'));
|
|
901
|
+
this.onNodesChangeAddMany = this.manyChanges(this.nodeChangesOfType('add'));
|
|
902
|
+
this.onNodesChangeRemove = this.nodeChangesOfType('remove');
|
|
903
|
+
this.onNodesChangeRemoveSingle = this.singleChange(this.nodeChangesOfType('remove'));
|
|
904
|
+
this.onNodesChangeRemoveMany = this.manyChanges(this.nodeChangesOfType('remove'));
|
|
905
|
+
this.onNodesChangeSelect = this.nodeChangesOfType('select');
|
|
906
|
+
this.onNodesChangeSelectSingle = this.singleChange(this.nodeChangesOfType('select'));
|
|
907
|
+
this.onNodesChangeSelectMany = this.manyChanges(this.nodeChangesOfType('select'));
|
|
816
908
|
/**
|
|
817
|
-
* Watch
|
|
909
|
+
* Watch edges change
|
|
818
910
|
*/
|
|
819
|
-
this.onEdgesChange =
|
|
820
|
-
this.
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
this.
|
|
824
|
-
|
|
825
|
-
|
|
911
|
+
this.onEdgesChange = this.edgesChangeService.changes$;
|
|
912
|
+
this.onNodesChangeDetached = this.edgeChangesOfType('detached');
|
|
913
|
+
this.onNodesChangeDetachedSingle = this.singleChange(this.edgeChangesOfType('detached'));
|
|
914
|
+
this.onNodesChangeDetachedMany = this.manyChanges(this.edgeChangesOfType('detached'));
|
|
915
|
+
this.onEdgesChangeAdd = this.edgeChangesOfType('add');
|
|
916
|
+
this.onEdgeChangeAddSingle = this.singleChange(this.edgeChangesOfType('add'));
|
|
917
|
+
this.onEdgeChangeAddMany = this.manyChanges(this.edgeChangesOfType('add'));
|
|
918
|
+
this.onEdgeChangeRemove = this.edgeChangesOfType('remove');
|
|
919
|
+
this.onEdgeChangeRemoveSingle = this.singleChange(this.edgeChangesOfType('remove'));
|
|
920
|
+
this.onEdgeChangeRemoveMany = this.manyChanges(this.edgeChangesOfType('remove'));
|
|
921
|
+
this.onEdgeChangeSelect = this.edgeChangesOfType('select');
|
|
922
|
+
this.onEdgeChangeSelectSingle = this.singleChange(this.edgeChangesOfType('select'));
|
|
923
|
+
this.onEdgeChangeSelectMany = this.manyChanges(this.edgeChangesOfType('select'));
|
|
924
|
+
}
|
|
925
|
+
nodeChangesOfType(type) {
|
|
926
|
+
return this.nodesChangeService.changes$.pipe(map(changes => changes.filter((c) => c.type === type)), filter(changes => !!changes.length));
|
|
927
|
+
}
|
|
928
|
+
edgeChangesOfType(type) {
|
|
929
|
+
return this.edgesChangeService.changes$.pipe(map(changes => changes.filter((c) => c.type === type)), filter(changes => !!changes.length));
|
|
930
|
+
}
|
|
931
|
+
singleChange(changes$) {
|
|
932
|
+
return changes$.pipe(filter(changes => changes.length === 1), map(([first]) => first));
|
|
933
|
+
}
|
|
934
|
+
manyChanges(changes$) {
|
|
935
|
+
return changes$.pipe(filter(changes => changes.length > 1));
|
|
826
936
|
}
|
|
827
937
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ChangesControllerDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
828
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: ChangesControllerDirective, isStandalone: true, selector: "[changesController]", outputs: { onNodesChange: "onNodesChange", onEdgesChange: "onEdgesChange" }, ngImport: i0 }); }
|
|
938
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: ChangesControllerDirective, isStandalone: true, selector: "[changesController]", outputs: { onNodesChange: "onNodesChange", onNodesChangePosition: "onNodesChange.position", onNodesChangePositionSignle: "onNodesChange.position.single", onNodesChangePositionMany: "onNodesChange.position.many", onNodesChangeAdd: "onNodesChange.add", onNodesChangeAddSingle: "onNodesChange.add.single", onNodesChangeAddMany: "onNodesChange.add.many", onNodesChangeRemove: "onNodesChange.remove", onNodesChangeRemoveSingle: "onNodesChange.remove.single", onNodesChangeRemoveMany: "onNodesChange.remove.many", onNodesChangeSelect: "onNodesChange.select", onNodesChangeSelectSingle: "onNodesChange.select.single", onNodesChangeSelectMany: "onNodesChange.select.many", onEdgesChange: "onEdgesChange", onNodesChangeDetached: "onEdgesChange.detached", onNodesChangeDetachedSingle: "onEdgesChange.detached.single", onNodesChangeDetachedMany: "onEdgesChange.detached.many", onEdgesChangeAdd: "onEdgesChange.add", onEdgeChangeAddSingle: "onEdgesChange.add.single", onEdgeChangeAddMany: "onEdgesChange.add.many", onEdgeChangeRemove: "onEdgesChange.remove", onEdgeChangeRemoveSingle: "onEdgesChange.remove.single", onEdgeChangeRemoveMany: "onEdgesChange.remove.many", onEdgeChangeSelect: "onEdgesChange.select", onEdgeChangeSelectSingle: "onEdgesChange.select.single", onEdgeChangeSelectMany: "onEdgesChange.select.many" }, ngImport: i0 }); }
|
|
829
939
|
}
|
|
830
940
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ChangesControllerDirective, decorators: [{
|
|
831
941
|
type: Directive,
|
|
@@ -835,8 +945,80 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
835
945
|
}]
|
|
836
946
|
}], propDecorators: { onNodesChange: [{
|
|
837
947
|
type: Output
|
|
948
|
+
}], onNodesChangePosition: [{
|
|
949
|
+
type: Output,
|
|
950
|
+
args: ['onNodesChange.position']
|
|
951
|
+
}], onNodesChangePositionSignle: [{
|
|
952
|
+
type: Output,
|
|
953
|
+
args: ['onNodesChange.position.single']
|
|
954
|
+
}], onNodesChangePositionMany: [{
|
|
955
|
+
type: Output,
|
|
956
|
+
args: ['onNodesChange.position.many']
|
|
957
|
+
}], onNodesChangeAdd: [{
|
|
958
|
+
type: Output,
|
|
959
|
+
args: ['onNodesChange.add']
|
|
960
|
+
}], onNodesChangeAddSingle: [{
|
|
961
|
+
type: Output,
|
|
962
|
+
args: ['onNodesChange.add.single']
|
|
963
|
+
}], onNodesChangeAddMany: [{
|
|
964
|
+
type: Output,
|
|
965
|
+
args: ['onNodesChange.add.many']
|
|
966
|
+
}], onNodesChangeRemove: [{
|
|
967
|
+
type: Output,
|
|
968
|
+
args: ['onNodesChange.remove']
|
|
969
|
+
}], onNodesChangeRemoveSingle: [{
|
|
970
|
+
type: Output,
|
|
971
|
+
args: ['onNodesChange.remove.single']
|
|
972
|
+
}], onNodesChangeRemoveMany: [{
|
|
973
|
+
type: Output,
|
|
974
|
+
args: ['onNodesChange.remove.many']
|
|
975
|
+
}], onNodesChangeSelect: [{
|
|
976
|
+
type: Output,
|
|
977
|
+
args: ['onNodesChange.select']
|
|
978
|
+
}], onNodesChangeSelectSingle: [{
|
|
979
|
+
type: Output,
|
|
980
|
+
args: ['onNodesChange.select.single']
|
|
981
|
+
}], onNodesChangeSelectMany: [{
|
|
982
|
+
type: Output,
|
|
983
|
+
args: ['onNodesChange.select.many']
|
|
838
984
|
}], onEdgesChange: [{
|
|
839
985
|
type: Output
|
|
986
|
+
}], onNodesChangeDetached: [{
|
|
987
|
+
type: Output,
|
|
988
|
+
args: ['onEdgesChange.detached']
|
|
989
|
+
}], onNodesChangeDetachedSingle: [{
|
|
990
|
+
type: Output,
|
|
991
|
+
args: ['onEdgesChange.detached.single']
|
|
992
|
+
}], onNodesChangeDetachedMany: [{
|
|
993
|
+
type: Output,
|
|
994
|
+
args: ['onEdgesChange.detached.many']
|
|
995
|
+
}], onEdgesChangeAdd: [{
|
|
996
|
+
type: Output,
|
|
997
|
+
args: ['onEdgesChange.add']
|
|
998
|
+
}], onEdgeChangeAddSingle: [{
|
|
999
|
+
type: Output,
|
|
1000
|
+
args: ['onEdgesChange.add.single']
|
|
1001
|
+
}], onEdgeChangeAddMany: [{
|
|
1002
|
+
type: Output,
|
|
1003
|
+
args: ['onEdgesChange.add.many']
|
|
1004
|
+
}], onEdgeChangeRemove: [{
|
|
1005
|
+
type: Output,
|
|
1006
|
+
args: ['onEdgesChange.remove']
|
|
1007
|
+
}], onEdgeChangeRemoveSingle: [{
|
|
1008
|
+
type: Output,
|
|
1009
|
+
args: ['onEdgesChange.remove.single']
|
|
1010
|
+
}], onEdgeChangeRemoveMany: [{
|
|
1011
|
+
type: Output,
|
|
1012
|
+
args: ['onEdgesChange.remove.many']
|
|
1013
|
+
}], onEdgeChangeSelect: [{
|
|
1014
|
+
type: Output,
|
|
1015
|
+
args: ['onEdgesChange.select']
|
|
1016
|
+
}], onEdgeChangeSelectSingle: [{
|
|
1017
|
+
type: Output,
|
|
1018
|
+
args: ['onEdgesChange.select.single']
|
|
1019
|
+
}], onEdgeChangeSelectMany: [{
|
|
1020
|
+
type: Output,
|
|
1021
|
+
args: ['onEdgesChange.select.many']
|
|
840
1022
|
}] } });
|
|
841
1023
|
|
|
842
1024
|
class NodeRenderingService {
|
|
@@ -1030,6 +1212,124 @@ function getChildStrokeWidth(element) {
|
|
|
1030
1212
|
return 0;
|
|
1031
1213
|
}
|
|
1032
1214
|
|
|
1215
|
+
class RootPointerDirective {
|
|
1216
|
+
constructor() {
|
|
1217
|
+
this.host = inject(ElementRef).nativeElement;
|
|
1218
|
+
this.initialTouch$ = new Subject();
|
|
1219
|
+
// TODO: do not emit if mouse not down
|
|
1220
|
+
this.mouseMovement$ = fromEvent(this.host, 'mousemove').pipe(map(event => ({
|
|
1221
|
+
x: event.clientX,
|
|
1222
|
+
y: event.clientY,
|
|
1223
|
+
originalEvent: event
|
|
1224
|
+
})), observeOn(animationFrameScheduler), share());
|
|
1225
|
+
this.touchMovement$ = merge(this.initialTouch$, fromEvent(this.host, 'touchmove')).pipe(tap((event) => event.preventDefault()), map((originalEvent) => {
|
|
1226
|
+
const x = originalEvent.touches[0]?.clientX ?? 0;
|
|
1227
|
+
const y = originalEvent.touches[0]?.clientY ?? 0;
|
|
1228
|
+
const target = document.elementFromPoint(x, y);
|
|
1229
|
+
return { x, y, target, originalEvent };
|
|
1230
|
+
}), observeOn(animationFrameScheduler), share());
|
|
1231
|
+
this.touchEnd$ = fromEvent(this.host, 'touchend').pipe(map((originalEvent) => {
|
|
1232
|
+
const x = originalEvent.changedTouches[0]?.clientX ?? 0;
|
|
1233
|
+
const y = originalEvent.changedTouches[0]?.clientY ?? 0;
|
|
1234
|
+
const target = document.elementFromPoint(x, y);
|
|
1235
|
+
return { x, y, target, originalEvent };
|
|
1236
|
+
}), share());
|
|
1237
|
+
this.pointerMovement$ = merge(this.mouseMovement$, this.touchMovement$);
|
|
1238
|
+
}
|
|
1239
|
+
/**
|
|
1240
|
+
* We should know when user started a touch in order to not
|
|
1241
|
+
* show old touch position when connection creation is started
|
|
1242
|
+
*/
|
|
1243
|
+
setInitialTouch(event) {
|
|
1244
|
+
this.initialTouch$.next(event);
|
|
1245
|
+
}
|
|
1246
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: RootPointerDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
1247
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: RootPointerDirective, selector: "svg[rootPointer]", ngImport: i0 }); }
|
|
1248
|
+
}
|
|
1249
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: RootPointerDirective, decorators: [{
|
|
1250
|
+
type: Directive,
|
|
1251
|
+
args: [{ selector: 'svg[rootPointer]' }]
|
|
1252
|
+
}] });
|
|
1253
|
+
|
|
1254
|
+
class PointerDirective {
|
|
1255
|
+
constructor() {
|
|
1256
|
+
this.hostElement = inject(ElementRef).nativeElement;
|
|
1257
|
+
this.pointerMovementDirective = inject(RootPointerDirective);
|
|
1258
|
+
this.pointerOver = new EventEmitter();
|
|
1259
|
+
this.pointerOut = new EventEmitter();
|
|
1260
|
+
this.pointerStart = new EventEmitter();
|
|
1261
|
+
this.pointerEnd = new EventEmitter();
|
|
1262
|
+
this.wasPointerOver = false;
|
|
1263
|
+
// TODO check if i could avoid global touch end
|
|
1264
|
+
this.touchEnd = this.pointerMovementDirective.touchEnd$
|
|
1265
|
+
.pipe(filter(({ target }) => target === this.hostElement), tap(({ originalEvent }) => this.pointerEnd.emit(originalEvent)), takeUntilDestroyed())
|
|
1266
|
+
.subscribe();
|
|
1267
|
+
this.touchOverOut = this.pointerMovementDirective.touchMovement$
|
|
1268
|
+
.pipe(tap(({ target, originalEvent }) => {
|
|
1269
|
+
this.handleTouchOverAndOut(target, originalEvent);
|
|
1270
|
+
}), takeUntilDestroyed())
|
|
1271
|
+
.subscribe();
|
|
1272
|
+
}
|
|
1273
|
+
onPointerStart(event) {
|
|
1274
|
+
this.pointerStart.emit(event);
|
|
1275
|
+
if (event instanceof TouchEvent) {
|
|
1276
|
+
this.pointerMovementDirective.setInitialTouch(event);
|
|
1277
|
+
}
|
|
1278
|
+
}
|
|
1279
|
+
onPointerEnd(event) {
|
|
1280
|
+
this.pointerEnd.emit(event);
|
|
1281
|
+
}
|
|
1282
|
+
onMouseOver(event) {
|
|
1283
|
+
this.pointerOver.emit(event);
|
|
1284
|
+
}
|
|
1285
|
+
onMouseOut(event) {
|
|
1286
|
+
this.pointerOut.emit(event);
|
|
1287
|
+
}
|
|
1288
|
+
// TODO: dirty imperative implementation
|
|
1289
|
+
handleTouchOverAndOut(target, event) {
|
|
1290
|
+
if (target === this.hostElement) {
|
|
1291
|
+
this.pointerOver.emit(event);
|
|
1292
|
+
this.wasPointerOver = true;
|
|
1293
|
+
}
|
|
1294
|
+
else {
|
|
1295
|
+
// should not emit before pointerOver
|
|
1296
|
+
if (this.wasPointerOver) {
|
|
1297
|
+
this.pointerOut.emit(event);
|
|
1298
|
+
}
|
|
1299
|
+
this.wasPointerOver = false;
|
|
1300
|
+
}
|
|
1301
|
+
}
|
|
1302
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: PointerDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
1303
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: PointerDirective, selector: "[pointerStart], [pointerEnd], [pointerOver], [pointerOut]", outputs: { pointerOver: "pointerOver", pointerOut: "pointerOut", pointerStart: "pointerStart", pointerEnd: "pointerEnd" }, host: { listeners: { "mousedown": "onPointerStart($event)", "touchstart": "onPointerStart($event)", "mouseup": "onPointerEnd($event)", "mouseover": "onMouseOver($event)", "mouseout": "onMouseOut($event)" } }, ngImport: i0 }); }
|
|
1304
|
+
}
|
|
1305
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: PointerDirective, decorators: [{
|
|
1306
|
+
type: Directive,
|
|
1307
|
+
args: [{ selector: '[pointerStart], [pointerEnd], [pointerOver], [pointerOut]' }]
|
|
1308
|
+
}], propDecorators: { pointerOver: [{
|
|
1309
|
+
type: Output
|
|
1310
|
+
}], pointerOut: [{
|
|
1311
|
+
type: Output
|
|
1312
|
+
}], pointerStart: [{
|
|
1313
|
+
type: Output
|
|
1314
|
+
}], pointerEnd: [{
|
|
1315
|
+
type: Output
|
|
1316
|
+
}], onPointerStart: [{
|
|
1317
|
+
type: HostListener,
|
|
1318
|
+
args: ['mousedown', ['$event']]
|
|
1319
|
+
}, {
|
|
1320
|
+
type: HostListener,
|
|
1321
|
+
args: ['touchstart', ['$event']]
|
|
1322
|
+
}], onPointerEnd: [{
|
|
1323
|
+
type: HostListener,
|
|
1324
|
+
args: ['mouseup', ['$event']]
|
|
1325
|
+
}], onMouseOver: [{
|
|
1326
|
+
type: HostListener,
|
|
1327
|
+
args: ['mouseover', ['$event']]
|
|
1328
|
+
}], onMouseOut: [{
|
|
1329
|
+
type: HostListener,
|
|
1330
|
+
args: ['mouseout', ['$event']]
|
|
1331
|
+
}] } });
|
|
1332
|
+
|
|
1033
1333
|
class NodeComponent {
|
|
1034
1334
|
constructor() {
|
|
1035
1335
|
this.injector = inject(Injector);
|
|
@@ -1044,6 +1344,8 @@ class NodeComponent {
|
|
|
1044
1344
|
this.hostRef = inject(ElementRef);
|
|
1045
1345
|
this.showMagnet = computed(() => this.flowStatusService.status().state === 'connection-start' ||
|
|
1046
1346
|
this.flowStatusService.status().state === 'connection-validation');
|
|
1347
|
+
this.styleWidth = computed(() => `${this.nodeModel.size().width}px`);
|
|
1348
|
+
this.styleHeight = computed(() => `${this.nodeModel.size().height}px`);
|
|
1047
1349
|
this.subscription = new Subscription();
|
|
1048
1350
|
}
|
|
1049
1351
|
ngOnInit() {
|
|
@@ -1058,10 +1360,12 @@ class NodeComponent {
|
|
|
1058
1360
|
ngAfterViewInit() {
|
|
1059
1361
|
this.setInitialHandles();
|
|
1060
1362
|
if (this.nodeModel.node.type === 'default') {
|
|
1061
|
-
|
|
1062
|
-
|
|
1363
|
+
this.nodeModel.size.set({
|
|
1364
|
+
width: this.nodeModel.node.width ?? NodeModel.defaultTypeSize.width,
|
|
1365
|
+
height: this.nodeModel.node.height ?? NodeModel.defaultTypeSize.height
|
|
1366
|
+
});
|
|
1063
1367
|
}
|
|
1064
|
-
if (this.nodeModel.node.type === 'html-template') {
|
|
1368
|
+
if (this.nodeModel.node.type === 'html-template' || this.nodeModel.isComponentType) {
|
|
1065
1369
|
const sub = resizable([this.htmlWrapperRef.nativeElement], this.zone)
|
|
1066
1370
|
.pipe(startWith(null), tap(() => {
|
|
1067
1371
|
const width = this.htmlWrapperRef.nativeElement.clientWidth;
|
|
@@ -1149,7 +1453,7 @@ class NodeComponent {
|
|
|
1149
1453
|
}
|
|
1150
1454
|
}
|
|
1151
1455
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: NodeComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
1152
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "16.2.12", type: NodeComponent, selector: "g[node]", inputs: { nodeModel: "nodeModel", nodeHtmlTemplate: "nodeHtmlTemplate" }, providers: [HandleService], viewQueries: [{ propertyName: "nodeContentRef", first: true, predicate: ["nodeContent"], descendants: true }, { propertyName: "htmlWrapperRef", first: true, predicate: ["htmlWrapper"], descendants: true }], ngImport: i0, template: "<svg:foreignObject\n *ngIf=\"nodeModel.node.type === 'default'\"\n class=\"selectable\"\n #nodeContent\n width=\"
|
|
1456
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "16.2.12", type: NodeComponent, selector: "g[node]", inputs: { nodeModel: "nodeModel", nodeHtmlTemplate: "nodeHtmlTemplate" }, providers: [HandleService], viewQueries: [{ propertyName: "nodeContentRef", first: true, predicate: ["nodeContent"], descendants: true }, { propertyName: "htmlWrapperRef", first: true, predicate: ["htmlWrapper"], descendants: true }], ngImport: i0, template: "<svg:foreignObject\n *ngIf=\"nodeModel.node.type === 'default'\"\n class=\"selectable\"\n #nodeContent\n [attr.width]=\"nodeModel.size().width\"\n [attr.height]=\"nodeModel.size().height\"\n (mousedown)=\"pullNode(); selectNode()\"\n>\n <div\n #htmlWrapper\n class=\"default-node\"\n [class.default-node_selected]=\"nodeModel.selected()\"\n [style.width]=\"styleWidth()\"\n [style.height]=\"styleHeight()\"\n [style.max-width]=\"styleWidth()\"\n [style.max-height]=\"styleHeight()\"\n [innerHTML]=\"nodeModel.node.text ?? ''\"\n ></div>\n</svg:foreignObject>\n\n<svg:foreignObject\n *ngIf=\"nodeModel.node.type === 'html-template' && nodeHtmlTemplate\"\n class=\"selectable\"\n [attr.width]=\"nodeModel.size().width\"\n [attr.height]=\"nodeModel.size().height\"\n (mousedown)=\"pullNode()\"\n>\n <div #htmlWrapper class=\"wrapper\">\n <ng-container\n [ngTemplateOutlet]=\"nodeHtmlTemplate\"\n [ngTemplateOutletContext]=\"{ $implicit: { node: nodeModel.node, selected: nodeModel.selected } }\"\n [ngTemplateOutletInjector]=\"injector\"\n />\n </div>\n</svg:foreignObject>\n\n<svg:foreignObject\n *ngIf=\"nodeModel.isComponentType\"\n class=\"selectable\"\n [attr.width]=\"nodeModel.size().width\"\n [attr.height]=\"nodeModel.size().height\"\n (mousedown)=\"pullNode()\"\n>\n <div #htmlWrapper class=\"wrapper\">\n <ng-container\n [ngComponentOutlet]=\"$any(nodeModel.node.type)\"\n [ngComponentOutletInputs]=\"nodeModel.componentTypeInputs()\"\n [ngComponentOutletInjector]=\"injector\"\n />\n </div>\n</svg:foreignObject>\n\n<ng-container *ngFor=\"let handle of nodeModel.handles()\">\n <svg:circle\n *ngIf=\"!handle.template\"\n class=\"default-handle\"\n [attr.cx]=\"handle.offset().x\"\n [attr.cy]=\"handle.offset().y\"\n [attr.stroke-width]=\"handle.strokeWidth\"\n r=\"5\"\n (pointerStart)=\"handle.rawHandle.type === 'source' ? startConnection($event, handle) : null\"\n (pointerEnd)=\"handle.rawHandle.type === 'target' ? endConnection() : null\"\n />\n\n <svg:g\n *ngIf=\"handle.template\"\n [handleSizeController]=\"handle\"\n (pointerStart)=\"handle.rawHandle.type === 'source' ? startConnection($event, handle) : null\"\n (pointerEnd)=\"handle.rawHandle.type === 'target' ? endConnection() : null\"\n >\n <ng-container *ngTemplateOutlet=\"handle.template; context: handle.templateContext\" />\n </svg:g>\n\n <svg:circle\n *ngIf=\"handle.rawHandle.type === 'target' && showMagnet()\"\n class=\"magnet\"\n [attr.r]=\"nodeModel.magnetRadius\"\n [attr.cx]=\"handle.offset().x\"\n [attr.cy]=\"handle.offset().y\"\n (pointerEnd)=\"endConnection(); resetValidateTargetHandle(handle)\"\n (pointerOver)=\"validateTargetHandle(handle)\"\n (pointerOut)=\"resetValidateTargetHandle(handle)\"\n />\n</ng-container>\n", styles: [".wrapper{width:max-content}.magnet{opacity:0}.default-node{border:1.5px solid #1b262c;border-radius:5px;display:flex;align-items:center;justify-content:center;color:#000;background-color:#fff}.default-node_selected{border-width:2px}.default-handle{stroke:#fff;fill:#1b262c}\n"], dependencies: [{ kind: "directive", type: i1.NgComponentOutlet, selector: "[ngComponentOutlet]", inputs: ["ngComponentOutlet", "ngComponentOutletInputs", "ngComponentOutletInjector", "ngComponentOutletContent", "ngComponentOutletNgModule", "ngComponentOutletNgModuleFactory"] }, { kind: "directive", type: i1.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: HandleSizeControllerDirective, selector: "[handleSizeController]", inputs: ["handleSizeController"] }, { kind: "directive", type: PointerDirective, selector: "[pointerStart], [pointerEnd], [pointerOver], [pointerOut]", outputs: ["pointerOver", "pointerOut", "pointerStart", "pointerEnd"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
1153
1457
|
}
|
|
1154
1458
|
__decorate([
|
|
1155
1459
|
Microtask
|
|
@@ -1159,7 +1463,7 @@ __decorate([
|
|
|
1159
1463
|
], NodeComponent.prototype, "setInitialHandles", null);
|
|
1160
1464
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: NodeComponent, decorators: [{
|
|
1161
1465
|
type: Component,
|
|
1162
|
-
args: [{ selector: 'g[node]', changeDetection: ChangeDetectionStrategy.OnPush, providers: [HandleService], template: "<svg:foreignObject\n *ngIf=\"nodeModel.node.type === 'default'\"\n class=\"selectable\"\n #nodeContent\n width=\"
|
|
1466
|
+
args: [{ selector: 'g[node]', changeDetection: ChangeDetectionStrategy.OnPush, providers: [HandleService], template: "<svg:foreignObject\n *ngIf=\"nodeModel.node.type === 'default'\"\n class=\"selectable\"\n #nodeContent\n [attr.width]=\"nodeModel.size().width\"\n [attr.height]=\"nodeModel.size().height\"\n (mousedown)=\"pullNode(); selectNode()\"\n>\n <div\n #htmlWrapper\n class=\"default-node\"\n [class.default-node_selected]=\"nodeModel.selected()\"\n [style.width]=\"styleWidth()\"\n [style.height]=\"styleHeight()\"\n [style.max-width]=\"styleWidth()\"\n [style.max-height]=\"styleHeight()\"\n [innerHTML]=\"nodeModel.node.text ?? ''\"\n ></div>\n</svg:foreignObject>\n\n<svg:foreignObject\n *ngIf=\"nodeModel.node.type === 'html-template' && nodeHtmlTemplate\"\n class=\"selectable\"\n [attr.width]=\"nodeModel.size().width\"\n [attr.height]=\"nodeModel.size().height\"\n (mousedown)=\"pullNode()\"\n>\n <div #htmlWrapper class=\"wrapper\">\n <ng-container\n [ngTemplateOutlet]=\"nodeHtmlTemplate\"\n [ngTemplateOutletContext]=\"{ $implicit: { node: nodeModel.node, selected: nodeModel.selected } }\"\n [ngTemplateOutletInjector]=\"injector\"\n />\n </div>\n</svg:foreignObject>\n\n<svg:foreignObject\n *ngIf=\"nodeModel.isComponentType\"\n class=\"selectable\"\n [attr.width]=\"nodeModel.size().width\"\n [attr.height]=\"nodeModel.size().height\"\n (mousedown)=\"pullNode()\"\n>\n <div #htmlWrapper class=\"wrapper\">\n <ng-container\n [ngComponentOutlet]=\"$any(nodeModel.node.type)\"\n [ngComponentOutletInputs]=\"nodeModel.componentTypeInputs()\"\n [ngComponentOutletInjector]=\"injector\"\n />\n </div>\n</svg:foreignObject>\n\n<ng-container *ngFor=\"let handle of nodeModel.handles()\">\n <svg:circle\n *ngIf=\"!handle.template\"\n class=\"default-handle\"\n [attr.cx]=\"handle.offset().x\"\n [attr.cy]=\"handle.offset().y\"\n [attr.stroke-width]=\"handle.strokeWidth\"\n r=\"5\"\n (pointerStart)=\"handle.rawHandle.type === 'source' ? startConnection($event, handle) : null\"\n (pointerEnd)=\"handle.rawHandle.type === 'target' ? endConnection() : null\"\n />\n\n <svg:g\n *ngIf=\"handle.template\"\n [handleSizeController]=\"handle\"\n (pointerStart)=\"handle.rawHandle.type === 'source' ? startConnection($event, handle) : null\"\n (pointerEnd)=\"handle.rawHandle.type === 'target' ? endConnection() : null\"\n >\n <ng-container *ngTemplateOutlet=\"handle.template; context: handle.templateContext\" />\n </svg:g>\n\n <svg:circle\n *ngIf=\"handle.rawHandle.type === 'target' && showMagnet()\"\n class=\"magnet\"\n [attr.r]=\"nodeModel.magnetRadius\"\n [attr.cx]=\"handle.offset().x\"\n [attr.cy]=\"handle.offset().y\"\n (pointerEnd)=\"endConnection(); resetValidateTargetHandle(handle)\"\n (pointerOver)=\"validateTargetHandle(handle)\"\n (pointerOut)=\"resetValidateTargetHandle(handle)\"\n />\n</ng-container>\n", styles: [".wrapper{width:max-content}.magnet{opacity:0}.default-node{border:1.5px solid #1b262c;border-radius:5px;display:flex;align-items:center;justify-content:center;color:#000;background-color:#fff}.default-node_selected{border-width:2px}.default-handle{stroke:#fff;fill:#1b262c}\n"] }]
|
|
1163
1467
|
}], propDecorators: { nodeModel: [{
|
|
1164
1468
|
type: Input
|
|
1165
1469
|
}], nodeHtmlTemplate: [{
|
|
@@ -1277,19 +1581,23 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
1277
1581
|
|
|
1278
1582
|
class SpacePointContextDirective {
|
|
1279
1583
|
constructor() {
|
|
1584
|
+
this.pointerMovementDirective = inject(RootPointerDirective);
|
|
1585
|
+
this.rootSvg = inject(RootSvgReferenceDirective).element;
|
|
1586
|
+
this.host = inject(ElementRef).nativeElement;
|
|
1280
1587
|
/**
|
|
1281
1588
|
* Signal with current mouse position in svg space
|
|
1282
1589
|
*/
|
|
1283
1590
|
this.svgCurrentSpacePoint = computed(() => {
|
|
1284
|
-
const movement = this.
|
|
1591
|
+
const movement = this.pointerMovement();
|
|
1592
|
+
if (!movement) {
|
|
1593
|
+
return { x: 0, y: 0 };
|
|
1594
|
+
}
|
|
1285
1595
|
const point = this.rootSvg.createSVGPoint();
|
|
1286
1596
|
point.x = movement.x;
|
|
1287
1597
|
point.y = movement.y;
|
|
1288
1598
|
return point.matrixTransform(this.host.getScreenCTM().inverse());
|
|
1289
1599
|
});
|
|
1290
|
-
this.
|
|
1291
|
-
this.host = inject(ElementRef).nativeElement;
|
|
1292
|
-
this.mouseMovement = toSignal(fromEvent(this.rootSvg, 'mousemove').pipe(map(event => ({ x: event.clientX, y: event.clientY }))), { initialValue: { x: 0, y: 0 } });
|
|
1600
|
+
this.pointerMovement = toSignal(this.pointerMovementDirective.pointerMovement$);
|
|
1293
1601
|
}
|
|
1294
1602
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: SpacePointContextDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
1295
1603
|
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: SpacePointContextDirective, selector: "g[spacePointContext]", ngImport: i0 }); }
|
|
@@ -1440,7 +1748,7 @@ class RootSvgContextDirective {
|
|
|
1440
1748
|
}
|
|
1441
1749
|
}
|
|
1442
1750
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: RootSvgContextDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
1443
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: RootSvgContextDirective, selector: "svg[rootSvgContext]", host: { listeners: { "document:mouseup": "resetConnection()" } }, ngImport: i0 }); }
|
|
1751
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: RootSvgContextDirective, selector: "svg[rootSvgContext]", host: { listeners: { "document:mouseup": "resetConnection()", "document:touchend": "resetConnection()" } }, ngImport: i0 }); }
|
|
1444
1752
|
}
|
|
1445
1753
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: RootSvgContextDirective, decorators: [{
|
|
1446
1754
|
type: Directive,
|
|
@@ -1448,6 +1756,9 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
1448
1756
|
}], propDecorators: { resetConnection: [{
|
|
1449
1757
|
type: HostListener,
|
|
1450
1758
|
args: ['document:mouseup']
|
|
1759
|
+
}, {
|
|
1760
|
+
type: HostListener,
|
|
1761
|
+
args: ['document:touchend']
|
|
1451
1762
|
}] } });
|
|
1452
1763
|
|
|
1453
1764
|
const connectionControllerHostDirective = {
|
|
@@ -1456,7 +1767,34 @@ const connectionControllerHostDirective = {
|
|
|
1456
1767
|
};
|
|
1457
1768
|
const changesControllerHostDirective = {
|
|
1458
1769
|
directive: ChangesControllerDirective,
|
|
1459
|
-
outputs: [
|
|
1770
|
+
outputs: [
|
|
1771
|
+
'onNodesChange',
|
|
1772
|
+
'onNodesChange.position',
|
|
1773
|
+
'onNodesChange.position.single',
|
|
1774
|
+
'onNodesChange.position.many',
|
|
1775
|
+
'onNodesChange.add',
|
|
1776
|
+
'onNodesChange.add.single',
|
|
1777
|
+
'onNodesChange.add.many',
|
|
1778
|
+
'onNodesChange.remove',
|
|
1779
|
+
'onNodesChange.remove.single',
|
|
1780
|
+
'onNodesChange.remove.many',
|
|
1781
|
+
'onNodesChange.select',
|
|
1782
|
+
'onNodesChange.select.single',
|
|
1783
|
+
'onNodesChange.select.many',
|
|
1784
|
+
'onEdgesChange',
|
|
1785
|
+
'onEdgesChange.detached',
|
|
1786
|
+
'onEdgesChange.detached.single',
|
|
1787
|
+
'onEdgesChange.detached.many',
|
|
1788
|
+
'onEdgesChange.add',
|
|
1789
|
+
'onEdgesChange.add.single',
|
|
1790
|
+
'onEdgesChange.add.many',
|
|
1791
|
+
'onEdgesChange.remove',
|
|
1792
|
+
'onEdgesChange.remove.single',
|
|
1793
|
+
'onEdgesChange.remove.many',
|
|
1794
|
+
'onEdgesChange.select',
|
|
1795
|
+
'onEdgesChange.select.single',
|
|
1796
|
+
'onEdgesChange.select.many',
|
|
1797
|
+
]
|
|
1460
1798
|
};
|
|
1461
1799
|
class VflowComponent {
|
|
1462
1800
|
constructor() {
|
|
@@ -1467,6 +1805,7 @@ class VflowComponent {
|
|
|
1467
1805
|
this.edgesChangeService = inject(EdgeChangesService);
|
|
1468
1806
|
this.nodeRenderingService = inject(NodeRenderingService);
|
|
1469
1807
|
this.flowSettingsService = inject(FlowSettingsService);
|
|
1808
|
+
this.componentEventBusService = inject(ComponentEventBusService);
|
|
1470
1809
|
this.injector = inject(Injector);
|
|
1471
1810
|
/**
|
|
1472
1811
|
* Minimum zoom value
|
|
@@ -1483,6 +1822,14 @@ class VflowComponent {
|
|
|
1483
1822
|
this.nodeModels = computed(() => this.nodeRenderingService.nodes());
|
|
1484
1823
|
this.edgeModels = computed(() => this.flowEntitiesService.validEdges());
|
|
1485
1824
|
// #endregion
|
|
1825
|
+
// #region OUTPUTS
|
|
1826
|
+
/**
|
|
1827
|
+
* Event that accumulates all custom node events
|
|
1828
|
+
*
|
|
1829
|
+
* @experimental
|
|
1830
|
+
*/
|
|
1831
|
+
this.onComponentNodeEvent = this.componentEventBusService.event$; // TODO: research how to remove as any
|
|
1832
|
+
// #endregion
|
|
1486
1833
|
// #region SIGNAL_API
|
|
1487
1834
|
/**
|
|
1488
1835
|
* Signal for reading viewport change
|
|
@@ -1508,7 +1855,7 @@ class VflowComponent {
|
|
|
1508
1855
|
*/
|
|
1509
1856
|
this.nodesChange$ = this.nodesChangeService.changes$;
|
|
1510
1857
|
/**
|
|
1511
|
-
* Observable with
|
|
1858
|
+
* Observable with edges change
|
|
1512
1859
|
*/
|
|
1513
1860
|
this.edgesChange$ = this.edgesChangeService.changes$;
|
|
1514
1861
|
// #endregion
|
|
@@ -1619,7 +1966,7 @@ class VflowComponent {
|
|
|
1619
1966
|
return edge;
|
|
1620
1967
|
}
|
|
1621
1968
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: VflowComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
1622
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "16.1.0", version: "16.2.12", type: VflowComponent, selector: "vflow", inputs: { view: "view", minZoom: "minZoom", maxZoom: "maxZoom", handlePositions: "handlePositions", background: "background", entitiesSelectable: "entitiesSelectable", connection: ["connection", "connection", (settings) => new ConnectionModel(settings)], nodes: "nodes", edges: "edges" }, providers: [
|
|
1969
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "16.1.0", version: "16.2.12", type: VflowComponent, selector: "vflow", inputs: { view: "view", minZoom: "minZoom", maxZoom: "maxZoom", handlePositions: "handlePositions", background: "background", entitiesSelectable: "entitiesSelectable", connection: ["connection", "connection", (settings) => new ConnectionModel(settings)], nodes: "nodes", edges: "edges" }, outputs: { onComponentNodeEvent: "onComponentNodeEvent" }, providers: [
|
|
1623
1970
|
DraggableService,
|
|
1624
1971
|
ViewportService,
|
|
1625
1972
|
FlowStatusService,
|
|
@@ -1628,8 +1975,9 @@ class VflowComponent {
|
|
|
1628
1975
|
EdgeChangesService,
|
|
1629
1976
|
NodeRenderingService,
|
|
1630
1977
|
SelectionService,
|
|
1631
|
-
FlowSettingsService
|
|
1632
|
-
|
|
1978
|
+
FlowSettingsService,
|
|
1979
|
+
ComponentEventBusService
|
|
1980
|
+
], queries: [{ propertyName: "nodeHtmlDirective", first: true, predicate: NodeHtmlTemplateDirective, descendants: true }, { propertyName: "edgeTemplateDirective", first: true, predicate: EdgeTemplateDirective, descendants: true }, { propertyName: "edgeLabelHtmlDirective", first: true, predicate: EdgeLabelHtmlTemplateDirective, descendants: true }, { propertyName: "connectionTemplateDirective", first: true, predicate: ConnectionTemplateDirective, descendants: true }], viewQueries: [{ propertyName: "mapContext", first: true, predicate: MapContextDirective, descendants: true }], hostDirectives: [{ directive: ConnectionControllerDirective, outputs: ["onConnect", "onConnect"] }, { directive: ChangesControllerDirective, outputs: ["onNodesChange", "onNodesChange", "onNodesChange.position", "onNodesChange.position", "onNodesChange.position.single", "onNodesChange.position.single", "onNodesChange.position.many", "onNodesChange.position.many", "onNodesChange.add", "onNodesChange.add", "onNodesChange.add.single", "onNodesChange.add.single", "onNodesChange.add.many", "onNodesChange.add.many", "onNodesChange.remove", "onNodesChange.remove", "onNodesChange.remove.single", "onNodesChange.remove.single", "onNodesChange.remove.many", "onNodesChange.remove.many", "onNodesChange.select", "onNodesChange.select", "onNodesChange.select.single", "onNodesChange.select.single", "onNodesChange.select.many", "onNodesChange.select.many", "onEdgesChange", "onEdgesChange", "onEdgesChange.detached", "onEdgesChange.detached", "onEdgesChange.detached.single", "onEdgesChange.detached.single", "onEdgesChange.detached.many", "onEdgesChange.detached.many", "onEdgesChange.add", "onEdgesChange.add", "onEdgesChange.add.single", "onEdgesChange.add.single", "onEdgesChange.add.many", "onEdgesChange.add.many", "onEdgesChange.remove", "onEdgesChange.remove", "onEdgesChange.remove.single", "onEdgesChange.remove.single", "onEdgesChange.remove.many", "onEdgesChange.remove.many", "onEdgesChange.select", "onEdgesChange.select", "onEdgesChange.select.single", "onEdgesChange.select.single", "onEdgesChange.select.many", "onEdgesChange.select.many"] }], ngImport: i0, template: "<svg:svg\n rootSvgRef\n rootSvgContext\n rootPointer\n class=\"root-svg\"\n #flow\n [style.backgroundColor]=\"background\"\n [attr.width]=\"flowWidth()\"\n [attr.height]=\"flowHeight()\"\n>\n <defs [markers]=\"markers()\" flowDefs />\n\n <svg:g\n mapContext\n spacePointContext\n [minZoom]=\"minZoom\"\n [maxZoom]=\"maxZoom\"\n >\n <!-- Connection -->\n <svg:g\n connection\n [model]=\"connection\"\n [template]=\"connectionTemplateDirective?.templateRef\"\n />\n\n <!-- Edges -->\n <svg:g\n *ngFor=\"let model of edgeModels(); trackBy: trackEdges\"\n edge\n [model]=\"model\"\n [edgeTemplate]=\"edgeTemplateDirective?.templateRef\"\n [edgeLabelHtmlTemplate]=\"edgeLabelHtmlDirective?.templateRef\"\n />\n\n <!-- Nodes -->\n <svg:g\n *ngFor=\"let model of nodeModels(); trackBy: trackNodes\"\n node\n [nodeModel]=\"model\"\n [nodeHtmlTemplate]=\"nodeHtmlDirective?.templateRef\"\n [attr.transform]=\"model.pointTransform()\"\n />\n </svg:g>\n\n</svg:svg>\n", styles: [":host{display:block;width:100%;height:100%;-webkit-user-select:none;user-select:none}:host ::ng-deep *{box-sizing:border-box}\n"], dependencies: [{ kind: "directive", type: i1.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "component", type: NodeComponent, selector: "g[node]", inputs: ["nodeModel", "nodeHtmlTemplate"] }, { kind: "component", type: EdgeComponent, selector: "g[edge]", inputs: ["model", "edgeTemplate", "edgeLabelHtmlTemplate"] }, { kind: "component", type: ConnectionComponent, selector: "g[connection]", inputs: ["model", "template"] }, { kind: "component", type: DefsComponent, selector: "defs[flowDefs]", inputs: ["markers"] }, { kind: "directive", type: SpacePointContextDirective, selector: "g[spacePointContext]" }, { kind: "directive", type: MapContextDirective, selector: "g[mapContext]", inputs: ["minZoom", "maxZoom"] }, { kind: "directive", type: RootSvgReferenceDirective, selector: "svg[rootSvgRef]" }, { kind: "directive", type: RootSvgContextDirective, selector: "svg[rootSvgContext]" }, { kind: "directive", type: RootPointerDirective, selector: "svg[rootPointer]" }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
1633
1981
|
}
|
|
1634
1982
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: VflowComponent, decorators: [{
|
|
1635
1983
|
type: Component,
|
|
@@ -1642,11 +1990,12 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
1642
1990
|
EdgeChangesService,
|
|
1643
1991
|
NodeRenderingService,
|
|
1644
1992
|
SelectionService,
|
|
1645
|
-
FlowSettingsService
|
|
1993
|
+
FlowSettingsService,
|
|
1994
|
+
ComponentEventBusService
|
|
1646
1995
|
], hostDirectives: [
|
|
1647
1996
|
connectionControllerHostDirective,
|
|
1648
1997
|
changesControllerHostDirective
|
|
1649
|
-
], template: "<svg:svg\n rootSvgRef\n rootSvgContext\n class=\"root-svg\"\n #flow\n [style.backgroundColor]=\"background\"\n [attr.width]=\"flowWidth()\"\n [attr.height]=\"flowHeight()\"\n>\n <defs [markers]=\"markers()\" flowDefs />\n\n <svg:g\n mapContext\n spacePointContext\n [minZoom]=\"minZoom\"\n [maxZoom]=\"maxZoom\"\n >\n <!-- Connection -->\n <svg:g\n connection\n [model]=\"connection\"\n [template]=\"connectionTemplateDirective?.templateRef\"\n />\n\n <!-- Edges -->\n <svg:g\n *ngFor=\"let model of edgeModels(); trackBy: trackEdges\"\n edge\n [model]=\"model\"\n [edgeTemplate]=\"edgeTemplateDirective?.templateRef\"\n [edgeLabelHtmlTemplate]=\"edgeLabelHtmlDirective?.templateRef\"\n />\n\n <!-- Nodes -->\n <svg:g\n *ngFor=\"let model of nodeModels(); trackBy: trackNodes\"\n node\n [nodeModel]=\"model\"\n [nodeHtmlTemplate]=\"nodeHtmlDirective?.templateRef\"\n [attr.transform]=\"model.pointTransform()\"\n />\n </svg:g>\n\n</svg:svg>\n", styles: [":host{display:block;width:100%;height:100%;-webkit-user-select:none;user-select:none}:host ::ng-deep *{box-sizing:border-box}\n"] }]
|
|
1998
|
+
], template: "<svg:svg\n rootSvgRef\n rootSvgContext\n rootPointer\n class=\"root-svg\"\n #flow\n [style.backgroundColor]=\"background\"\n [attr.width]=\"flowWidth()\"\n [attr.height]=\"flowHeight()\"\n>\n <defs [markers]=\"markers()\" flowDefs />\n\n <svg:g\n mapContext\n spacePointContext\n [minZoom]=\"minZoom\"\n [maxZoom]=\"maxZoom\"\n >\n <!-- Connection -->\n <svg:g\n connection\n [model]=\"connection\"\n [template]=\"connectionTemplateDirective?.templateRef\"\n />\n\n <!-- Edges -->\n <svg:g\n *ngFor=\"let model of edgeModels(); trackBy: trackEdges\"\n edge\n [model]=\"model\"\n [edgeTemplate]=\"edgeTemplateDirective?.templateRef\"\n [edgeLabelHtmlTemplate]=\"edgeLabelHtmlDirective?.templateRef\"\n />\n\n <!-- Nodes -->\n <svg:g\n *ngFor=\"let model of nodeModels(); trackBy: trackNodes\"\n node\n [nodeModel]=\"model\"\n [nodeHtmlTemplate]=\"nodeHtmlDirective?.templateRef\"\n [attr.transform]=\"model.pointTransform()\"\n />\n </svg:g>\n\n</svg:svg>\n", styles: [":host{display:block;width:100%;height:100%;-webkit-user-select:none;user-select:none}:host ::ng-deep *{box-sizing:border-box}\n"] }]
|
|
1650
1999
|
}], propDecorators: { view: [{
|
|
1651
2000
|
type: Input
|
|
1652
2001
|
}], minZoom: [{
|
|
@@ -1667,6 +2016,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
1667
2016
|
args: [{ required: true }]
|
|
1668
2017
|
}], edges: [{
|
|
1669
2018
|
type: Input
|
|
2019
|
+
}], onComponentNodeEvent: [{
|
|
2020
|
+
type: Output
|
|
1670
2021
|
}], nodeHtmlDirective: [{
|
|
1671
2022
|
type: ContentChild,
|
|
1672
2023
|
args: [NodeHtmlTemplateDirective]
|
|
@@ -1773,7 +2124,9 @@ const directives = [
|
|
|
1773
2124
|
RootSvgReferenceDirective,
|
|
1774
2125
|
RootSvgContextDirective,
|
|
1775
2126
|
HandleSizeControllerDirective,
|
|
1776
|
-
SelectableDirective
|
|
2127
|
+
SelectableDirective,
|
|
2128
|
+
PointerDirective,
|
|
2129
|
+
RootPointerDirective
|
|
1777
2130
|
];
|
|
1778
2131
|
const templateDirectives = [
|
|
1779
2132
|
NodeHtmlTemplateDirective,
|
|
@@ -1795,7 +2148,9 @@ class VflowModule {
|
|
|
1795
2148
|
RootSvgReferenceDirective,
|
|
1796
2149
|
RootSvgContextDirective,
|
|
1797
2150
|
HandleSizeControllerDirective,
|
|
1798
|
-
SelectableDirective,
|
|
2151
|
+
SelectableDirective,
|
|
2152
|
+
PointerDirective,
|
|
2153
|
+
RootPointerDirective, NodeHtmlTemplateDirective,
|
|
1799
2154
|
EdgeLabelHtmlTemplateDirective,
|
|
1800
2155
|
EdgeTemplateDirective,
|
|
1801
2156
|
ConnectionTemplateDirective,
|
|
@@ -1828,5 +2183,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
|
|
|
1828
2183
|
* Generated bundle index. Do not edit.
|
|
1829
2184
|
*/
|
|
1830
2185
|
|
|
1831
|
-
export { ChangesControllerDirective, ConnectionControllerDirective, ConnectionTemplateDirective, EdgeLabelHtmlTemplateDirective, EdgeTemplateDirective, HandleComponent, HandleTemplateDirective, NodeHtmlTemplateDirective, SelectableDirective, VflowComponent, VflowModule };
|
|
2186
|
+
export { ChangesControllerDirective, ConnectionControllerDirective, ConnectionTemplateDirective, CustomNodeComponent, EdgeLabelHtmlTemplateDirective, EdgeTemplateDirective, HandleComponent, HandleTemplateDirective, NodeHtmlTemplateDirective, SelectableDirective, VflowComponent, VflowModule };
|
|
1832
2187
|
//# sourceMappingURL=ngx-vflow.mjs.map
|