ngx-vflow 0.5.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.
@@ -0,0 +1,51 @@
1
+ import { DestroyRef, Directive, EventEmitter, Input, inject, signal } from "@angular/core";
2
+ import { ComponentEventBusService } from "../services/component-event-bus.service";
3
+ import { merge, tap } from "rxjs";
4
+ import { takeUntilDestroyed } from "@angular/core/rxjs-interop";
5
+ import * as i0 from "@angular/core";
6
+ export class CustomNodeComponent {
7
+ constructor() {
8
+ this.eventBus = inject(ComponentEventBusService);
9
+ this.destroyRef = inject(DestroyRef);
10
+ /**
11
+ * Signal with selected state of node
12
+ */
13
+ this.selected = signal(false);
14
+ }
15
+ set _selected(value) {
16
+ this.selected.set(value);
17
+ }
18
+ ngOnInit() {
19
+ this.trackEvents();
20
+ }
21
+ trackEvents() {
22
+ const props = Object.getOwnPropertyNames(this);
23
+ const emitters = new Map();
24
+ for (const prop of props) {
25
+ const field = this[prop];
26
+ if (field instanceof EventEmitter) {
27
+ emitters.set(field, prop);
28
+ }
29
+ }
30
+ merge(...Array.from(emitters.keys()).map(emitter => emitter.pipe(tap((event) => {
31
+ this.eventBus.pushEvent({
32
+ nodeId: this.node.id,
33
+ eventName: emitters.get(emitter),
34
+ eventPayload: event
35
+ });
36
+ }))))
37
+ .pipe(takeUntilDestroyed(this.destroyRef))
38
+ .subscribe();
39
+ }
40
+ ;
41
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: CustomNodeComponent, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
42
+ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "16.2.12", type: CustomNodeComponent, inputs: { node: "node", _selected: "_selected" }, ngImport: i0 }); }
43
+ }
44
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: CustomNodeComponent, decorators: [{
45
+ type: Directive
46
+ }], propDecorators: { node: [{
47
+ type: Input
48
+ }], _selected: [{
49
+ type: Input
50
+ }] } });
51
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY3VzdG9tLW5vZGUuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvbmd4LXZmbG93LWxpYi9zcmMvbGliL3ZmbG93L3B1YmxpYy1jb21wb25lbnRzL2N1c3RvbS1ub2RlLmNvbXBvbmVudC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsVUFBVSxFQUFFLFNBQVMsRUFBRSxZQUFZLEVBQUUsS0FBSyxFQUFVLE1BQU0sRUFBRSxNQUFNLEVBQUUsTUFBTSxlQUFlLENBQUE7QUFFbEcsT0FBTyxFQUFFLHdCQUF3QixFQUFFLE1BQU0seUNBQXlDLENBQUM7QUFDbkYsT0FBTyxFQUFFLEtBQUssRUFBRSxHQUFHLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFDbEMsT0FBTyxFQUFFLGtCQUFrQixFQUFFLE1BQU0sNEJBQTRCLENBQUM7O0FBR2hFLE1BQU0sT0FBZ0IsbUJBQW1CO0lBRHpDO1FBRVUsYUFBUSxHQUFHLE1BQU0sQ0FBQyx3QkFBd0IsQ0FBQyxDQUFBO1FBRXpDLGVBQVUsR0FBRyxNQUFNLENBQUMsVUFBVSxDQUFDLENBQUE7UUFhekM7O1dBRUc7UUFDSSxhQUFRLEdBQUcsTUFBTSxDQUFDLEtBQUssQ0FBQyxDQUFBO0tBbUNoQztJQTNDQyxJQUNXLFNBQVMsQ0FBQyxLQUFjO1FBQ2pDLElBQUksQ0FBQyxRQUFRLENBQUMsR0FBRyxDQUFDLEtBQUssQ0FBQyxDQUFBO0lBQzFCLENBQUM7SUFPTSxRQUFRO1FBQ2IsSUFBSSxDQUFDLFdBQVcsRUFBRSxDQUFBO0lBQ3BCLENBQUM7SUFFTyxXQUFXO1FBQ2pCLE1BQU0sS0FBSyxHQUFHLE1BQU0sQ0FBQyxtQkFBbUIsQ0FBQyxJQUFJLENBQUMsQ0FBQTtRQUU5QyxNQUFNLFFBQVEsR0FBRyxJQUFJLEdBQUcsRUFBaUMsQ0FBQTtRQUN6RCxLQUFLLE1BQU0sSUFBSSxJQUFJLEtBQUssRUFBRTtZQUN4QixNQUFNLEtBQUssR0FBSSxJQUFnQyxDQUFDLElBQUksQ0FBQyxDQUFBO1lBRXJELElBQUksS0FBSyxZQUFZLFlBQVksRUFBRTtnQkFDakMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxLQUFLLEVBQUUsSUFBSSxDQUFDLENBQUE7YUFDMUI7U0FDRjtRQUVELEtBQUssQ0FDSCxHQUFHLEtBQUssQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLElBQUksRUFBRSxDQUFDLENBQUMsR0FBRyxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQzNDLE9BQU8sQ0FBQyxJQUFJLENBQ1YsR0FBRyxDQUFDLENBQUMsS0FBSyxFQUFFLEVBQUU7WUFDWixJQUFJLENBQUMsUUFBUSxDQUFDLFNBQVMsQ0FBQztnQkFDdEIsTUFBTSxFQUFFLElBQUksQ0FBQyxJQUFJLENBQUMsRUFBRTtnQkFDcEIsU0FBUyxFQUFFLFFBQVEsQ0FBQyxHQUFHLENBQUMsT0FBTyxDQUFFO2dCQUNqQyxZQUFZLEVBQUUsS0FBSzthQUNwQixDQUFDLENBQUE7UUFDSixDQUFDLENBQUMsQ0FBQyxDQUNOLENBQ0Y7YUFDRSxJQUFJLENBQ0gsa0JBQWtCLENBQUMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxDQUNwQzthQUNBLFNBQVMsRUFBRSxDQUFBO0lBQ2hCLENBQUM7SUFBQSxDQUFDOytHQXJEa0IsbUJBQW1CO21HQUFuQixtQkFBbUI7OzRGQUFuQixtQkFBbUI7a0JBRHhDLFNBQVM7OEJBVUQsSUFBSTtzQkFEVixLQUFLO2dCQUlLLFNBQVM7c0JBRG5CLEtBQUsiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBEZXN0cm95UmVmLCBEaXJlY3RpdmUsIEV2ZW50RW1pdHRlciwgSW5wdXQsIE9uSW5pdCwgaW5qZWN0LCBzaWduYWwgfSBmcm9tIFwiQGFuZ3VsYXIvY29yZVwiXG5pbXBvcnQgeyBDb21wb25lbnROb2RlLCBTaGFyZWROb2RlIH0gZnJvbSAnLi4vaW50ZXJmYWNlcy9ub2RlLmludGVyZmFjZSc7XG5pbXBvcnQgeyBDb21wb25lbnRFdmVudEJ1c1NlcnZpY2UgfSBmcm9tIFwiLi4vc2VydmljZXMvY29tcG9uZW50LWV2ZW50LWJ1cy5zZXJ2aWNlXCI7XG5pbXBvcnQgeyBtZXJnZSwgdGFwIH0gZnJvbSBcInJ4anNcIjtcbmltcG9ydCB7IHRha2VVbnRpbERlc3Ryb3llZCB9IGZyb20gXCJAYW5ndWxhci9jb3JlL3J4anMtaW50ZXJvcFwiO1xuXG5ARGlyZWN0aXZlKClcbmV4cG9ydCBhYnN0cmFjdCBjbGFzcyBDdXN0b21Ob2RlQ29tcG9uZW50PFQgPSB1bmtub3duPiBpbXBsZW1lbnRzIE9uSW5pdCB7XG4gIHByaXZhdGUgZXZlbnRCdXMgPSBpbmplY3QoQ29tcG9uZW50RXZlbnRCdXNTZXJ2aWNlKVxuXG4gIHByb3RlY3RlZCBkZXN0cm95UmVmID0gaW5qZWN0KERlc3Ryb3lSZWYpXG5cbiAgLyoqXG4gICAqIFJlZmVyZW5jZSB0byBub2RlIGJvdW5kIHRvIHRoaXMgY29tcG9uZW50XG4gICAqL1xuICBASW5wdXQoKVxuICBwdWJsaWMgbm9kZSE6IFNoYXJlZE5vZGUgJiBDb21wb25lbnROb2RlPFQ+XG5cbiAgQElucHV0KClcbiAgcHVibGljIHNldCBfc2VsZWN0ZWQodmFsdWU6IGJvb2xlYW4pIHtcbiAgICB0aGlzLnNlbGVjdGVkLnNldCh2YWx1ZSlcbiAgfVxuXG4gIC8qKlxuICAgKiBTaWduYWwgd2l0aCBzZWxlY3RlZCBzdGF0ZSBvZiBub2RlXG4gICAqL1xuICBwdWJsaWMgc2VsZWN0ZWQgPSBzaWduYWwoZmFsc2UpXG5cbiAgcHVibGljIG5nT25Jbml0KCk6IHZvaWQge1xuICAgIHRoaXMudHJhY2tFdmVudHMoKVxuICB9XG5cbiAgcHJpdmF0ZSB0cmFja0V2ZW50cygpIHtcbiAgICBjb25zdCBwcm9wcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKHRoaXMpXG5cbiAgICBjb25zdCBlbWl0dGVycyA9IG5ldyBNYXA8RXZlbnRFbWl0dGVyPHVua25vd24+LCBzdHJpbmc+KClcbiAgICBmb3IgKGNvbnN0IHByb3Agb2YgcHJvcHMpIHtcbiAgICAgIGNvbnN0IGZpZWxkID0gKHRoaXMgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj4pW3Byb3BdXG5cbiAgICAgIGlmIChmaWVsZCBpbnN0YW5jZW9mIEV2ZW50RW1pdHRlcikge1xuICAgICAgICBlbWl0dGVycy5zZXQoZmllbGQsIHByb3ApXG4gICAgICB9XG4gICAgfVxuXG4gICAgbWVyZ2UoXG4gICAgICAuLi5BcnJheS5mcm9tKGVtaXR0ZXJzLmtleXMoKSkubWFwKGVtaXR0ZXIgPT5cbiAgICAgICAgZW1pdHRlci5waXBlKFxuICAgICAgICAgIHRhcCgoZXZlbnQpID0+IHtcbiAgICAgICAgICAgIHRoaXMuZXZlbnRCdXMucHVzaEV2ZW50KHtcbiAgICAgICAgICAgICAgbm9kZUlkOiB0aGlzLm5vZGUuaWQsXG4gICAgICAgICAgICAgIGV2ZW50TmFtZTogZW1pdHRlcnMuZ2V0KGVtaXR0ZXIpISxcbiAgICAgICAgICAgICAgZXZlbnRQYXlsb2FkOiBldmVudFxuICAgICAgICAgICAgfSlcbiAgICAgICAgICB9KSlcbiAgICAgIClcbiAgICApXG4gICAgICAucGlwZShcbiAgICAgICAgdGFrZVVudGlsRGVzdHJveWVkKHRoaXMuZGVzdHJveVJlZilcbiAgICAgIClcbiAgICAgIC5zdWJzY3JpYmUoKVxuICB9O1xufVxuXG4iXX0=
@@ -0,0 +1,18 @@
1
+ import { Injectable } from '@angular/core';
2
+ import { Subject } from 'rxjs';
3
+ import * as i0 from "@angular/core";
4
+ export class ComponentEventBusService {
5
+ constructor() {
6
+ this._event$ = new Subject();
7
+ this.event$ = this._event$.asObservable();
8
+ }
9
+ pushEvent(event) {
10
+ this._event$.next(event);
11
+ }
12
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ComponentEventBusService, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
13
+ static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ComponentEventBusService }); }
14
+ }
15
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: ComponentEventBusService, decorators: [{
16
+ type: Injectable
17
+ }] });
18
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY29tcG9uZW50LWV2ZW50LWJ1cy5zZXJ2aWNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvbmd4LXZmbG93LWxpYi9zcmMvbGliL3ZmbG93L3NlcnZpY2VzL2NvbXBvbmVudC1ldmVudC1idXMuc2VydmljZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQzNDLE9BQU8sRUFBRSxPQUFPLEVBQUUsTUFBTSxNQUFNLENBQUM7O0FBSy9CLE1BQU0sT0FBTyx3QkFBd0I7SUFEckM7UUFFVSxZQUFPLEdBQUcsSUFBSSxPQUFPLEVBQXlCLENBQUE7UUFFL0MsV0FBTSxHQUFHLElBQUksQ0FBQyxPQUFPLENBQUMsWUFBWSxFQUFFLENBQUE7S0FLNUM7SUFIUSxTQUFTLENBQUMsS0FBNEI7UUFDM0MsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUE7SUFDMUIsQ0FBQzsrR0FQVSx3QkFBd0I7bUhBQXhCLHdCQUF3Qjs7NEZBQXhCLHdCQUF3QjtrQkFEcEMsVUFBVSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IEluamVjdGFibGUgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IFN1YmplY3QgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IEFueUNvbXBvbmVudE5vZGVFdmVudCwgQ29tcG9uZW50Tm9kZUV2ZW50IH0gZnJvbSAnLi4vaW50ZXJmYWNlcy9jb21wb25lbnQtbm9kZS1ldmVudC5pbnRlcmZhY2UnO1xuaW1wb3J0IHsgQ3VzdG9tTm9kZUNvbXBvbmVudCB9IGZyb20gJy4uL3B1YmxpYy1jb21wb25lbnRzL2N1c3RvbS1ub2RlLmNvbXBvbmVudCc7XG5cbkBJbmplY3RhYmxlKClcbmV4cG9ydCBjbGFzcyBDb21wb25lbnRFdmVudEJ1c1NlcnZpY2Uge1xuICBwcml2YXRlIF9ldmVudCQgPSBuZXcgU3ViamVjdDxBbnlDb21wb25lbnROb2RlRXZlbnQ+KClcblxuICBwdWJsaWMgZXZlbnQkID0gdGhpcy5fZXZlbnQkLmFzT2JzZXJ2YWJsZSgpXG5cbiAgcHVibGljIHB1c2hFdmVudChldmVudDogQW55Q29tcG9uZW50Tm9kZUV2ZW50KSB7XG4gICAgdGhpcy5fZXZlbnQkLm5leHQoZXZlbnQpXG4gIH1cbn1cbiJdfQ==
@@ -41,7 +41,7 @@ export class DraggableService {
41
41
  deltaY = model.point().y - event.y;
42
42
  })
43
43
  .on('drag', (event) => {
44
- model.point.set({
44
+ model.setPoint({
45
45
  x: round(event.x + deltaX),
46
46
  y: round(event.y + deltaY)
47
47
  });
@@ -63,4 +63,4 @@ export class DraggableService {
63
63
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: DraggableService, decorators: [{
64
64
  type: Injectable
65
65
  }] });
66
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZHJhZ2dhYmxlLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtdmZsb3ctbGliL3NyYy9saWIvdmZsb3cvc2VydmljZXMvZHJhZ2dhYmxlLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUMzQyxPQUFPLEVBQUUsTUFBTSxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBQ3RDLE9BQU8sRUFBZSxJQUFJLEVBQUUsTUFBTSxTQUFTLENBQUM7QUFFNUMsT0FBTyxFQUFFLEtBQUssRUFBRSxNQUFNLGdCQUFnQixDQUFDOztBQUt2QyxNQUFNLE9BQU8sZ0JBQWdCO0lBQzNCOzs7Ozs7T0FNRztJQUNJLGVBQWUsQ0FBQyxPQUFnQixFQUFFLEtBQWdCO1FBQ3ZELE1BQU0sU0FBUyxHQUFHLE1BQU0sQ0FBQyxPQUFPLENBQUMsQ0FBQTtRQUVqQyxNQUFNLFFBQVEsR0FBRyxLQUFLLENBQUMsU0FBUztZQUM5QixDQUFDLENBQUMsSUFBSSxDQUFDLGVBQWUsQ0FBQyxLQUFLLENBQUM7WUFDN0IsQ0FBQyxDQUFDLElBQUksQ0FBQyxxQkFBcUIsRUFBRSxDQUFBO1FBRWhDLFNBQVMsQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLENBQUE7SUFDMUIsQ0FBQztJQUVEOzs7O09BSUc7SUFDSSxPQUFPLENBQUMsT0FBZ0I7UUFDN0IsTUFBTSxDQUFDLE9BQU8sQ0FBQyxDQUFDLEVBQUUsQ0FBQyxPQUFPLEVBQUUsSUFBSSxDQUFDLENBQUE7SUFDbkMsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0ssZUFBZSxDQUFDLEtBQWdCO1FBQ3RDLElBQUksTUFBYyxDQUFBO1FBQ2xCLElBQUksTUFBYyxDQUFBO1FBRWxCLE9BQU8sSUFBSSxFQUFFO2FBQ1YsRUFBRSxDQUFDLE9BQU8sRUFBRSxDQUFDLEtBQWdCLEVBQUUsRUFBRTtZQUNoQyxNQUFNLEdBQUcsS0FBSyxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUMsR0FBRyxLQUFLLENBQUMsQ0FBQyxDQUFBO1lBQ2xDLE1BQU0sR0FBRyxLQUFLLENBQUMsS0FBSyxFQUFFLENBQUMsQ0FBQyxHQUFHLEtBQUssQ0FBQyxDQUFDLENBQUE7UUFDcEMsQ0FBQyxDQUFDO2FBRUQsRUFBRSxDQUFDLE1BQU0sRUFBRSxDQUFDLEtBQWdCLEVBQUUsRUFBRTtZQUMvQixLQUFLLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FDYjtnQkFDRSxDQUFDLEVBQUUsS0FBSyxDQUFDLEtBQUssQ0FBQyxDQUFDLEdBQUcsTUFBTSxDQUFDO2dCQUMxQixDQUFDLEVBQUUsS0FBSyxDQUFDLEtBQUssQ0FBQyxDQUFDLEdBQUcsTUFBTSxDQUFDO2FBQzNCLENBQ0YsQ0FBQTtRQUNILENBQUMsQ0FBQyxDQUFBO0lBQ04sQ0FBQztJQUVEOzs7T0FHRztJQUNLLHFCQUFxQjtRQUMzQixPQUFPLElBQUksRUFBRTthQUNWLEVBQUUsQ0FBQyxNQUFNLEVBQUUsQ0FBQyxLQUFnQixFQUFFLEVBQUU7WUFDOUIsS0FBSyxDQUFDLFdBQXFCLENBQUMsZUFBZSxFQUFFLENBQUE7UUFDaEQsQ0FBQyxDQUFDLENBQUE7SUFDTixDQUFDOytHQTlEVSxnQkFBZ0I7bUhBQWhCLGdCQUFnQjs7NEZBQWhCLGdCQUFnQjtrQkFENUIsVUFBVSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IEluamVjdGFibGUgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IHNlbGVjdCB9IGZyb20gJ2QzLXNlbGVjdGlvbic7XG5pbXBvcnQgeyBEM0RyYWdFdmVudCwgZHJhZyB9IGZyb20gJ2QzLWRyYWcnO1xuaW1wb3J0IHsgTm9kZU1vZGVsIH0gZnJvbSAnLi4vbW9kZWxzL25vZGUubW9kZWwnO1xuaW1wb3J0IHsgcm91bmQgfSBmcm9tICcuLi91dGlscy9yb3VuZCc7XG5cbnR5cGUgRHJhZ0V2ZW50ID0gRDNEcmFnRXZlbnQ8RWxlbWVudCwgdW5rbm93biwgdW5rbm93bj5cblxuQEluamVjdGFibGUoKVxuZXhwb3J0IGNsYXNzIERyYWdnYWJsZVNlcnZpY2Uge1xuICAvKipcbiAgICogRW5hYmxlIG9yIGRpc2FibGUgZHJhZ2dhYmxlIGJlaGF2aW9yIGZvciBlbGVtZW50LlxuICAgKiBtb2RlbCBjb250YWlucyBkcmFnZ2FibGUgZmxhZyB3aGljaCBkZWNsYXJlcyBpZiBkcmFnZ2FibGUgc2hvdWxkIGJlIGVuYWJsZWQgb3Igbm90XG4gICAqXG4gICAqIEBwYXJhbSBlbGVtZW50IHRhcmdldCBlbGVtZW50IGZvciB0b2dnbGluZyBkcmFnZ2FibGVcbiAgICogQHBhcmFtIG1vZGVsIG1vZGVsIHdpdGggZGF0YSBmb3IgdGhpcyBlbGVtZW50XG4gICAqL1xuICBwdWJsaWMgdG9nZ2xlRHJhZ2dhYmxlKGVsZW1lbnQ6IEVsZW1lbnQsIG1vZGVsOiBOb2RlTW9kZWwpIHtcbiAgICBjb25zdCBkM0VsZW1lbnQgPSBzZWxlY3QoZWxlbWVudClcblxuICAgIGNvbnN0IGJlaGF2aW9yID0gbW9kZWwuZHJhZ2dhYmxlXG4gICAgICA/IHRoaXMuZ2V0RHJhZ0JlaGF2aW9yKG1vZGVsKVxuICAgICAgOiB0aGlzLmdldElnbm9yZURyYWdCZWhhdmlvcigpXG5cbiAgICBkM0VsZW1lbnQuY2FsbChiZWhhdmlvcilcbiAgfVxuXG4gIC8qKlxuICAgKiBUT0RPOiBub3Qgc2h1cmUgaWYgdGhpcyB3b3JrLCBuZWVkIHRvIGNoZWNrXG4gICAqXG4gICAqIEBwYXJhbSBlbGVtZW50XG4gICAqL1xuICBwdWJsaWMgZGVzdHJveShlbGVtZW50OiBFbGVtZW50KSB7XG4gICAgc2VsZWN0KGVsZW1lbnQpLm9uKCcuZHJhZycsIG51bGwpXG4gIH1cblxuICAvKipcbiAgICogTm9kZSBkcmFnIGJlaGF2aW9yLiBVcGRhdGVkIG5vZGUncyBjb29yZGluYXRlIGFjY29yZGluZyB0byBkcmFnZ2luZ1xuICAgKlxuICAgKiBAcGFyYW0gbW9kZWxcbiAgICogQHJldHVybnNcbiAgICovXG4gIHByaXZhdGUgZ2V0RHJhZ0JlaGF2aW9yKG1vZGVsOiBOb2RlTW9kZWwpIHtcbiAgICBsZXQgZGVsdGFYOiBudW1iZXJcbiAgICBsZXQgZGVsdGFZOiBudW1iZXJcblxuICAgIHJldHVybiBkcmFnKClcbiAgICAgIC5vbignc3RhcnQnLCAoZXZlbnQ6IERyYWdFdmVudCkgPT4ge1xuICAgICAgICBkZWx0YVggPSBtb2RlbC5wb2ludCgpLnggLSBldmVudC54XG4gICAgICAgIGRlbHRhWSA9IG1vZGVsLnBvaW50KCkueSAtIGV2ZW50LnlcbiAgICAgIH0pXG5cbiAgICAgIC5vbignZHJhZycsIChldmVudDogRHJhZ0V2ZW50KSA9PiB7XG4gICAgICAgIG1vZGVsLnBvaW50LnNldChcbiAgICAgICAgICB7XG4gICAgICAgICAgICB4OiByb3VuZChldmVudC54ICsgZGVsdGFYKSxcbiAgICAgICAgICAgIHk6IHJvdW5kKGV2ZW50LnkgKyBkZWx0YVkpXG4gICAgICAgICAgfVxuICAgICAgICApXG4gICAgICB9KVxuICB9XG5cbiAgLyoqXG4gICAqIFNwZWNpZnkgaWdub3JpbmcgZHJhZyBiZWhhdmlvci4gSXQncyByZXNwb25zaWJsZSBmb3Igbm90IG1vdmluZyB0aGUgbWFwIHdoZW4gdXNlciB0cmllcyB0byBkcmFnIG5vZGVcbiAgICogd2l0aCBkaXNhYmxlZCBkcmFnIGJlaGF2aW9yXG4gICAqL1xuICBwcml2YXRlIGdldElnbm9yZURyYWdCZWhhdmlvcigpIHtcbiAgICByZXR1cm4gZHJhZygpXG4gICAgICAub24oJ2RyYWcnLCAoZXZlbnQ6IERyYWdFdmVudCkgPT4ge1xuICAgICAgICAoZXZlbnQuc291cmNlRXZlbnQgYXMgRXZlbnQpLnN0b3BQcm9wYWdhdGlvbigpXG4gICAgICB9KVxuICB9XG59XG4iXX0=
66
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZHJhZ2dhYmxlLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtdmZsb3ctbGliL3NyYy9saWIvdmZsb3cvc2VydmljZXMvZHJhZ2dhYmxlLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUMzQyxPQUFPLEVBQUUsTUFBTSxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBQ3RDLE9BQU8sRUFBZSxJQUFJLEVBQUUsTUFBTSxTQUFTLENBQUM7QUFFNUMsT0FBTyxFQUFFLEtBQUssRUFBRSxNQUFNLGdCQUFnQixDQUFDOztBQUt2QyxNQUFNLE9BQU8sZ0JBQWdCO0lBQzNCOzs7Ozs7T0FNRztJQUNJLGVBQWUsQ0FBQyxPQUFnQixFQUFFLEtBQWdCO1FBQ3ZELE1BQU0sU0FBUyxHQUFHLE1BQU0sQ0FBQyxPQUFPLENBQUMsQ0FBQTtRQUVqQyxNQUFNLFFBQVEsR0FBRyxLQUFLLENBQUMsU0FBUztZQUM5QixDQUFDLENBQUMsSUFBSSxDQUFDLGVBQWUsQ0FBQyxLQUFLLENBQUM7WUFDN0IsQ0FBQyxDQUFDLElBQUksQ0FBQyxxQkFBcUIsRUFBRSxDQUFBO1FBRWhDLFNBQVMsQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLENBQUE7SUFDMUIsQ0FBQztJQUVEOzs7O09BSUc7SUFDSSxPQUFPLENBQUMsT0FBZ0I7UUFDN0IsTUFBTSxDQUFDLE9BQU8sQ0FBQyxDQUFDLEVBQUUsQ0FBQyxPQUFPLEVBQUUsSUFBSSxDQUFDLENBQUE7SUFDbkMsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0ssZUFBZSxDQUFDLEtBQWdCO1FBQ3RDLElBQUksTUFBYyxDQUFBO1FBQ2xCLElBQUksTUFBYyxDQUFBO1FBRWxCLE9BQU8sSUFBSSxFQUFFO2FBQ1YsRUFBRSxDQUFDLE9BQU8sRUFBRSxDQUFDLEtBQWdCLEVBQUUsRUFBRTtZQUNoQyxNQUFNLEdBQUcsS0FBSyxDQUFDLEtBQUssRUFBRSxDQUFDLENBQUMsR0FBRyxLQUFLLENBQUMsQ0FBQyxDQUFBO1lBQ2xDLE1BQU0sR0FBRyxLQUFLLENBQUMsS0FBSyxFQUFFLENBQUMsQ0FBQyxHQUFHLEtBQUssQ0FBQyxDQUFDLENBQUE7UUFDcEMsQ0FBQyxDQUFDO2FBRUQsRUFBRSxDQUFDLE1BQU0sRUFBRSxDQUFDLEtBQWdCLEVBQUUsRUFBRTtZQUMvQixLQUFLLENBQUMsUUFBUSxDQUNaO2dCQUNFLENBQUMsRUFBRSxLQUFLLENBQUMsS0FBSyxDQUFDLENBQUMsR0FBRyxNQUFNLENBQUM7Z0JBQzFCLENBQUMsRUFBRSxLQUFLLENBQUMsS0FBSyxDQUFDLENBQUMsR0FBRyxNQUFNLENBQUM7YUFDM0IsQ0FDRixDQUFBO1FBQ0gsQ0FBQyxDQUFDLENBQUE7SUFDTixDQUFDO0lBRUQ7OztPQUdHO0lBQ0sscUJBQXFCO1FBQzNCLE9BQU8sSUFBSSxFQUFFO2FBQ1YsRUFBRSxDQUFDLE1BQU0sRUFBRSxDQUFDLEtBQWdCLEVBQUUsRUFBRTtZQUM5QixLQUFLLENBQUMsV0FBcUIsQ0FBQyxlQUFlLEVBQUUsQ0FBQTtRQUNoRCxDQUFDLENBQUMsQ0FBQTtJQUNOLENBQUM7K0dBOURVLGdCQUFnQjttSEFBaEIsZ0JBQWdCOzs0RkFBaEIsZ0JBQWdCO2tCQUQ1QixVQUFVIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgc2VsZWN0IH0gZnJvbSAnZDMtc2VsZWN0aW9uJztcbmltcG9ydCB7IEQzRHJhZ0V2ZW50LCBkcmFnIH0gZnJvbSAnZDMtZHJhZyc7XG5pbXBvcnQgeyBOb2RlTW9kZWwgfSBmcm9tICcuLi9tb2RlbHMvbm9kZS5tb2RlbCc7XG5pbXBvcnQgeyByb3VuZCB9IGZyb20gJy4uL3V0aWxzL3JvdW5kJztcblxudHlwZSBEcmFnRXZlbnQgPSBEM0RyYWdFdmVudDxFbGVtZW50LCB1bmtub3duLCB1bmtub3duPlxuXG5ASW5qZWN0YWJsZSgpXG5leHBvcnQgY2xhc3MgRHJhZ2dhYmxlU2VydmljZSB7XG4gIC8qKlxuICAgKiBFbmFibGUgb3IgZGlzYWJsZSBkcmFnZ2FibGUgYmVoYXZpb3IgZm9yIGVsZW1lbnQuXG4gICAqIG1vZGVsIGNvbnRhaW5zIGRyYWdnYWJsZSBmbGFnIHdoaWNoIGRlY2xhcmVzIGlmIGRyYWdnYWJsZSBzaG91bGQgYmUgZW5hYmxlZCBvciBub3RcbiAgICpcbiAgICogQHBhcmFtIGVsZW1lbnQgdGFyZ2V0IGVsZW1lbnQgZm9yIHRvZ2dsaW5nIGRyYWdnYWJsZVxuICAgKiBAcGFyYW0gbW9kZWwgbW9kZWwgd2l0aCBkYXRhIGZvciB0aGlzIGVsZW1lbnRcbiAgICovXG4gIHB1YmxpYyB0b2dnbGVEcmFnZ2FibGUoZWxlbWVudDogRWxlbWVudCwgbW9kZWw6IE5vZGVNb2RlbCkge1xuICAgIGNvbnN0IGQzRWxlbWVudCA9IHNlbGVjdChlbGVtZW50KVxuXG4gICAgY29uc3QgYmVoYXZpb3IgPSBtb2RlbC5kcmFnZ2FibGVcbiAgICAgID8gdGhpcy5nZXREcmFnQmVoYXZpb3IobW9kZWwpXG4gICAgICA6IHRoaXMuZ2V0SWdub3JlRHJhZ0JlaGF2aW9yKClcblxuICAgIGQzRWxlbWVudC5jYWxsKGJlaGF2aW9yKVxuICB9XG5cbiAgLyoqXG4gICAqIFRPRE86IG5vdCBzaHVyZSBpZiB0aGlzIHdvcmssIG5lZWQgdG8gY2hlY2tcbiAgICpcbiAgICogQHBhcmFtIGVsZW1lbnRcbiAgICovXG4gIHB1YmxpYyBkZXN0cm95KGVsZW1lbnQ6IEVsZW1lbnQpIHtcbiAgICBzZWxlY3QoZWxlbWVudCkub24oJy5kcmFnJywgbnVsbClcbiAgfVxuXG4gIC8qKlxuICAgKiBOb2RlIGRyYWcgYmVoYXZpb3IuIFVwZGF0ZWQgbm9kZSdzIGNvb3JkaW5hdGUgYWNjb3JkaW5nIHRvIGRyYWdnaW5nXG4gICAqXG4gICAqIEBwYXJhbSBtb2RlbFxuICAgKiBAcmV0dXJuc1xuICAgKi9cbiAgcHJpdmF0ZSBnZXREcmFnQmVoYXZpb3IobW9kZWw6IE5vZGVNb2RlbCkge1xuICAgIGxldCBkZWx0YVg6IG51bWJlclxuICAgIGxldCBkZWx0YVk6IG51bWJlclxuXG4gICAgcmV0dXJuIGRyYWcoKVxuICAgICAgLm9uKCdzdGFydCcsIChldmVudDogRHJhZ0V2ZW50KSA9PiB7XG4gICAgICAgIGRlbHRhWCA9IG1vZGVsLnBvaW50KCkueCAtIGV2ZW50LnhcbiAgICAgICAgZGVsdGFZID0gbW9kZWwucG9pbnQoKS55IC0gZXZlbnQueVxuICAgICAgfSlcblxuICAgICAgLm9uKCdkcmFnJywgKGV2ZW50OiBEcmFnRXZlbnQpID0+IHtcbiAgICAgICAgbW9kZWwuc2V0UG9pbnQoXG4gICAgICAgICAge1xuICAgICAgICAgICAgeDogcm91bmQoZXZlbnQueCArIGRlbHRhWCksXG4gICAgICAgICAgICB5OiByb3VuZChldmVudC55ICsgZGVsdGFZKVxuICAgICAgICAgIH1cbiAgICAgICAgKVxuICAgICAgfSlcbiAgfVxuXG4gIC8qKlxuICAgKiBTcGVjaWZ5IGlnbm9yaW5nIGRyYWcgYmVoYXZpb3IuIEl0J3MgcmVzcG9uc2libGUgZm9yIG5vdCBtb3ZpbmcgdGhlIG1hcCB3aGVuIHVzZXIgdHJpZXMgdG8gZHJhZyBub2RlXG4gICAqIHdpdGggZGlzYWJsZWQgZHJhZyBiZWhhdmlvclxuICAgKi9cbiAgcHJpdmF0ZSBnZXRJZ25vcmVEcmFnQmVoYXZpb3IoKSB7XG4gICAgcmV0dXJuIGRyYWcoKVxuICAgICAgLm9uKCdkcmFnJywgKGV2ZW50OiBEcmFnRXZlbnQpID0+IHtcbiAgICAgICAgKGV2ZW50LnNvdXJjZUV2ZW50IGFzIEV2ZW50KS5zdG9wUHJvcGFnYXRpb24oKVxuICAgICAgfSlcbiAgfVxufVxuIl19
@@ -8,7 +8,7 @@ export class SelectionService {
8
8
  this.flowEntitiesService = inject(FlowEntitiesService);
9
9
  this.viewport$ = new Subject();
10
10
  this.resetSelection = this.viewport$.pipe(tap(({ start, end, target }) => {
11
- if (start && end) {
11
+ if (start && end && target) {
12
12
  const delta = SelectionService.delta;
13
13
  const diffX = Math.abs(end.x - start.x);
14
14
  const diffY = Math.abs(end.y - start.y);
@@ -42,4 +42,4 @@ export class SelectionService {
42
42
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: SelectionService, decorators: [{
43
43
  type: Injectable
44
44
  }] });
45
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2VsZWN0aW9uLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtdmZsb3ctbGliL3NyYy9saWIvdmZsb3cvc2VydmljZXMvc2VsZWN0aW9uLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBVSxNQUFNLEVBQXFCLE1BQU0sZUFBZSxDQUFDO0FBRzlFLE9BQU8sRUFBRSxtQkFBbUIsRUFBRSxNQUFNLHlCQUF5QixDQUFDO0FBRTlELE9BQU8sRUFBRSxPQUFPLEVBQUUsR0FBRyxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBQ3BDLE9BQU8sRUFBRSxrQkFBa0IsRUFBRSxNQUFNLDRCQUE0QixDQUFDOztBQVNoRSxNQUFNLE9BQU8sZ0JBQWdCO0lBRDdCO1FBSVUsd0JBQW1CLEdBQUcsTUFBTSxDQUFDLG1CQUFtQixDQUFDLENBQUE7UUFFL0MsY0FBUyxHQUFHLElBQUksT0FBTyxFQUF3QixDQUFBO1FBRS9DLG1CQUFjLEdBQUcsSUFBSSxDQUFDLFNBQVMsQ0FBQyxJQUFJLENBQzVDLEdBQUcsQ0FBQyxDQUFDLEVBQUUsS0FBSyxFQUFFLEdBQUcsRUFBRSxNQUFNLEVBQUUsRUFBRSxFQUFFO1lBQzdCLElBQUksS0FBSyxJQUFJLEdBQUcsRUFBRTtnQkFDaEIsTUFBTSxLQUFLLEdBQUcsZ0JBQWdCLENBQUMsS0FBSyxDQUFBO2dCQUVwQyxNQUFNLEtBQUssR0FBRyxJQUFJLENBQUMsR0FBRyxDQUFDLEdBQUcsQ0FBQyxDQUFDLEdBQUcsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFBO2dCQUN2QyxNQUFNLEtBQUssR0FBRyxJQUFJLENBQUMsR0FBRyxDQUFDLEdBQUcsQ0FBQyxDQUFDLEdBQUcsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFBO2dCQUV2QyxtQkFBbUI7Z0JBQ25CLE1BQU0sT0FBTyxHQUFHLEtBQUssR0FBRyxLQUFLLElBQUksS0FBSyxHQUFHLEtBQUssQ0FBQTtnQkFDOUMsd0RBQXdEO2dCQUN4RCxNQUFNLGVBQWUsR0FBRyxDQUFDLE1BQU0sQ0FBQyxPQUFPLENBQUMsYUFBYSxDQUFDLENBQUE7Z0JBRXRELElBQUksT0FBTyxJQUFJLGVBQWUsRUFBRTtvQkFDOUIsSUFBSSxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsQ0FBQTtpQkFDbEI7YUFDRjtRQUNILENBQUMsQ0FBQyxFQUNGLGtCQUFrQixFQUFFLENBQ3JCLENBQUMsU0FBUyxFQUFFLENBQUE7S0FrQmQ7YUEzQ2dCLFVBQUssR0FBRyxDQUFDLEFBQUosQ0FBSTtJQTRCakIsV0FBVyxDQUFDLFFBQThCO1FBQy9DLElBQUksQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFBO0lBQy9CLENBQUM7SUFFTSxNQUFNLENBQUMsTUFBeUI7UUFDckMsNENBQTRDO1FBQzVDLElBQUksQ0FBQyxtQkFBbUIsQ0FBQyxRQUFRLEVBQUU7YUFDaEMsTUFBTSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLFFBQVEsQ0FBQzthQUN2QixPQUFPLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQyxDQUFBO1FBRXRDLElBQUksTUFBTSxFQUFFO1lBQ1YsdUJBQXVCO1lBQ3ZCLE1BQU0sQ0FBQyxRQUFRLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxDQUFBO1NBQzFCO0lBQ0gsQ0FBQzsrR0EzQ1UsZ0JBQWdCO21IQUFoQixnQkFBZ0I7OzRGQUFoQixnQkFBZ0I7a0JBRDVCLFVBQVUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBJbmplY3RhYmxlLCBlZmZlY3QsIGluamVjdCwgc2lnbmFsLCB1bnRyYWNrZWQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IFZpZXdwb3J0U3RhdGUgfSBmcm9tICcuLi9pbnRlcmZhY2VzL3ZpZXdwb3J0LmludGVyZmFjZSc7XG5pbXBvcnQgeyBWaWV3cG9ydFNlcnZpY2UgfSBmcm9tICcuL3ZpZXdwb3J0LnNlcnZpY2UnO1xuaW1wb3J0IHsgRmxvd0VudGl0aWVzU2VydmljZSB9IGZyb20gJy4vZmxvdy1lbnRpdGllcy5zZXJ2aWNlJztcbmltcG9ydCB7IEZsb3dFbnRpdHkgfSBmcm9tICcuLi9pbnRlcmZhY2VzL2Zsb3ctZW50aXR5LmludGVyZmFjZSc7XG5pbXBvcnQgeyBTdWJqZWN0LCB0YXAgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IHRha2VVbnRpbERlc3Ryb3llZCB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUvcnhqcy1pbnRlcm9wJztcblxuZXhwb3J0IGludGVyZmFjZSBWaWV3cG9ydEZvclNlbGVjdGlvbiB7XG4gIHN0YXJ0OiBWaWV3cG9ydFN0YXRlXG4gIGVuZDogVmlld3BvcnRTdGF0ZVxuICB0YXJnZXQ6IEVsZW1lbnRcbn1cblxuQEluamVjdGFibGUoKVxuZXhwb3J0IGNsYXNzIFNlbGVjdGlvblNlcnZpY2Uge1xuICBwcml2YXRlIHN0YXRpYyBkZWx0YSA9IDZcblxuICBwcml2YXRlIGZsb3dFbnRpdGllc1NlcnZpY2UgPSBpbmplY3QoRmxvd0VudGl0aWVzU2VydmljZSlcblxuICBwcm90ZWN0ZWQgdmlld3BvcnQkID0gbmV3IFN1YmplY3Q8Vmlld3BvcnRGb3JTZWxlY3Rpb24+KClcblxuICBwcm90ZWN0ZWQgcmVzZXRTZWxlY3Rpb24gPSB0aGlzLnZpZXdwb3J0JC5waXBlKFxuICAgIHRhcCgoeyBzdGFydCwgZW5kLCB0YXJnZXQgfSkgPT4ge1xuICAgICAgaWYgKHN0YXJ0ICYmIGVuZCkge1xuICAgICAgICBjb25zdCBkZWx0YSA9IFNlbGVjdGlvblNlcnZpY2UuZGVsdGFcblxuICAgICAgICBjb25zdCBkaWZmWCA9IE1hdGguYWJzKGVuZC54IC0gc3RhcnQueClcbiAgICAgICAgY29uc3QgZGlmZlkgPSBNYXRoLmFicyhlbmQueSAtIHN0YXJ0LnkpXG5cbiAgICAgICAgLy8gY2xpY2sgKG5vdCBkcmFnKVxuICAgICAgICBjb25zdCBpc0NsaWNrID0gZGlmZlggPCBkZWx0YSAmJiBkaWZmWSA8IGRlbHRhXG4gICAgICAgIC8vIGRvIG5vdCByZXNldCBpZiBldmVudCBjaGFpbiBjb250YWlucyBzZWxlY3RhYmxlIGVsZW1zXG4gICAgICAgIGNvbnN0IGlzTm90U2VsZWN0YWJsZSA9ICF0YXJnZXQuY2xvc2VzdCgnLnNlbGVjdGFibGUnKVxuXG4gICAgICAgIGlmIChpc0NsaWNrICYmIGlzTm90U2VsZWN0YWJsZSkge1xuICAgICAgICAgIHRoaXMuc2VsZWN0KG51bGwpXG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9KSxcbiAgICB0YWtlVW50aWxEZXN0cm95ZWQoKVxuICApLnN1YnNjcmliZSgpXG5cblxuICBwdWJsaWMgc2V0Vmlld3BvcnQodmlld3BvcnQ6IFZpZXdwb3J0Rm9yU2VsZWN0aW9uKSB7XG4gICAgdGhpcy52aWV3cG9ydCQubmV4dCh2aWV3cG9ydClcbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3QoZW50aXR5OiBGbG93RW50aXR5IHwgbnVsbCkge1xuICAgIC8vIHVuZG8gc2VsZWN0IGZvciBwcmV2aW91c2x5IHNlbGVjdGVkIG5vZGVzXG4gICAgdGhpcy5mbG93RW50aXRpZXNTZXJ2aWNlLmVudGl0aWVzKClcbiAgICAgIC5maWx0ZXIobiA9PiBuLnNlbGVjdGVkKVxuICAgICAgLmZvckVhY2gobiA9PiBuLnNlbGVjdGVkLnNldChmYWxzZSkpXG5cbiAgICBpZiAoZW50aXR5KSB7XG4gICAgICAvLyBzZWxlY3QgcGFzc2VkIGVudGl0eVxuICAgICAgZW50aXR5LnNlbGVjdGVkLnNldCh0cnVlKVxuICAgIH1cbiAgfVxufVxuIl19
45
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2VsZWN0aW9uLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9uZ3gtdmZsb3ctbGliL3NyYy9saWIvdmZsb3cvc2VydmljZXMvc2VsZWN0aW9uLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBVSxNQUFNLEVBQXFCLE1BQU0sZUFBZSxDQUFDO0FBRTlFLE9BQU8sRUFBRSxtQkFBbUIsRUFBRSxNQUFNLHlCQUF5QixDQUFDO0FBRTlELE9BQU8sRUFBRSxPQUFPLEVBQUUsR0FBRyxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBQ3BDLE9BQU8sRUFBRSxrQkFBa0IsRUFBRSxNQUFNLDRCQUE0QixDQUFDOztBQVloRSxNQUFNLE9BQU8sZ0JBQWdCO0lBRDdCO1FBSVUsd0JBQW1CLEdBQUcsTUFBTSxDQUFDLG1CQUFtQixDQUFDLENBQUE7UUFFL0MsY0FBUyxHQUFHLElBQUksT0FBTyxFQUF3QixDQUFBO1FBRS9DLG1CQUFjLEdBQUcsSUFBSSxDQUFDLFNBQVMsQ0FBQyxJQUFJLENBQzVDLEdBQUcsQ0FBQyxDQUFDLEVBQUUsS0FBSyxFQUFFLEdBQUcsRUFBRSxNQUFNLEVBQUUsRUFBRSxFQUFFO1lBQzdCLElBQUksS0FBSyxJQUFJLEdBQUcsSUFBSSxNQUFNLEVBQUU7Z0JBQzFCLE1BQU0sS0FBSyxHQUFHLGdCQUFnQixDQUFDLEtBQUssQ0FBQTtnQkFFcEMsTUFBTSxLQUFLLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxHQUFHLENBQUMsQ0FBQyxHQUFHLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQTtnQkFDdkMsTUFBTSxLQUFLLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxHQUFHLENBQUMsQ0FBQyxHQUFHLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQTtnQkFFdkMsbUJBQW1CO2dCQUNuQixNQUFNLE9BQU8sR0FBRyxLQUFLLEdBQUcsS0FBSyxJQUFJLEtBQUssR0FBRyxLQUFLLENBQUE7Z0JBQzlDLHdEQUF3RDtnQkFDeEQsTUFBTSxlQUFlLEdBQUcsQ0FBQyxNQUFNLENBQUMsT0FBTyxDQUFDLGFBQWEsQ0FBQyxDQUFBO2dCQUV0RCxJQUFJLE9BQU8sSUFBSSxlQUFlLEVBQUU7b0JBQzlCLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLENBQUE7aUJBQ2xCO2FBQ0Y7UUFDSCxDQUFDLENBQUMsRUFDRixrQkFBa0IsRUFBRSxDQUNyQixDQUFDLFNBQVMsRUFBRSxDQUFBO0tBa0JkO2FBM0NnQixVQUFLLEdBQUcsQ0FBQyxBQUFKLENBQUk7SUE0QmpCLFdBQVcsQ0FBQyxRQUE4QjtRQUMvQyxJQUFJLENBQUMsU0FBUyxDQUFDLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQTtJQUMvQixDQUFDO0lBRU0sTUFBTSxDQUFDLE1BQXlCO1FBQ3JDLDRDQUE0QztRQUM1QyxJQUFJLENBQUMsbUJBQW1CLENBQUMsUUFBUSxFQUFFO2FBQ2hDLE1BQU0sQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxRQUFRLENBQUM7YUFDdkIsT0FBTyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLFFBQVEsQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQTtRQUV0QyxJQUFJLE1BQU0sRUFBRTtZQUNWLHVCQUF1QjtZQUN2QixNQUFNLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsQ0FBQTtTQUMxQjtJQUNILENBQUM7K0dBM0NVLGdCQUFnQjttSEFBaEIsZ0JBQWdCOzs0RkFBaEIsZ0JBQWdCO2tCQUQ1QixVQUFVIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSwgZWZmZWN0LCBpbmplY3QsIHNpZ25hbCwgdW50cmFja2VkIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBWaWV3cG9ydFN0YXRlIH0gZnJvbSAnLi4vaW50ZXJmYWNlcy92aWV3cG9ydC5pbnRlcmZhY2UnO1xuaW1wb3J0IHsgRmxvd0VudGl0aWVzU2VydmljZSB9IGZyb20gJy4vZmxvdy1lbnRpdGllcy5zZXJ2aWNlJztcbmltcG9ydCB7IEZsb3dFbnRpdHkgfSBmcm9tICcuLi9pbnRlcmZhY2VzL2Zsb3ctZW50aXR5LmludGVyZmFjZSc7XG5pbXBvcnQgeyBTdWJqZWN0LCB0YXAgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IHRha2VVbnRpbERlc3Ryb3llZCB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUvcnhqcy1pbnRlcm9wJztcblxuZXhwb3J0IGludGVyZmFjZSBWaWV3cG9ydEZvclNlbGVjdGlvbiB7XG4gIHN0YXJ0OiBWaWV3cG9ydFN0YXRlXG4gIGVuZDogVmlld3BvcnRTdGF0ZVxuICAvKipcbiAgICogVGFyZ2V0IG1heSBub3QgZXhpc3QgaWYgdmlld3BvcnQgY2hhbmdlIG1hZGUgcHJvZ3JhbW1hdGljYWxseVxuICAgKi9cbiAgdGFyZ2V0PzogRWxlbWVudFxufVxuXG5ASW5qZWN0YWJsZSgpXG5leHBvcnQgY2xhc3MgU2VsZWN0aW9uU2VydmljZSB7XG4gIHByaXZhdGUgc3RhdGljIGRlbHRhID0gNlxuXG4gIHByaXZhdGUgZmxvd0VudGl0aWVzU2VydmljZSA9IGluamVjdChGbG93RW50aXRpZXNTZXJ2aWNlKVxuXG4gIHByb3RlY3RlZCB2aWV3cG9ydCQgPSBuZXcgU3ViamVjdDxWaWV3cG9ydEZvclNlbGVjdGlvbj4oKVxuXG4gIHByb3RlY3RlZCByZXNldFNlbGVjdGlvbiA9IHRoaXMudmlld3BvcnQkLnBpcGUoXG4gICAgdGFwKCh7IHN0YXJ0LCBlbmQsIHRhcmdldCB9KSA9PiB7XG4gICAgICBpZiAoc3RhcnQgJiYgZW5kICYmIHRhcmdldCkge1xuICAgICAgICBjb25zdCBkZWx0YSA9IFNlbGVjdGlvblNlcnZpY2UuZGVsdGFcblxuICAgICAgICBjb25zdCBkaWZmWCA9IE1hdGguYWJzKGVuZC54IC0gc3RhcnQueClcbiAgICAgICAgY29uc3QgZGlmZlkgPSBNYXRoLmFicyhlbmQueSAtIHN0YXJ0LnkpXG5cbiAgICAgICAgLy8gY2xpY2sgKG5vdCBkcmFnKVxuICAgICAgICBjb25zdCBpc0NsaWNrID0gZGlmZlggPCBkZWx0YSAmJiBkaWZmWSA8IGRlbHRhXG4gICAgICAgIC8vIGRvIG5vdCByZXNldCBpZiBldmVudCBjaGFpbiBjb250YWlucyBzZWxlY3RhYmxlIGVsZW1zXG4gICAgICAgIGNvbnN0IGlzTm90U2VsZWN0YWJsZSA9ICF0YXJnZXQuY2xvc2VzdCgnLnNlbGVjdGFibGUnKVxuXG4gICAgICAgIGlmIChpc0NsaWNrICYmIGlzTm90U2VsZWN0YWJsZSkge1xuICAgICAgICAgIHRoaXMuc2VsZWN0KG51bGwpXG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9KSxcbiAgICB0YWtlVW50aWxEZXN0cm95ZWQoKVxuICApLnN1YnNjcmliZSgpXG5cblxuICBwdWJsaWMgc2V0Vmlld3BvcnQodmlld3BvcnQ6IFZpZXdwb3J0Rm9yU2VsZWN0aW9uKSB7XG4gICAgdGhpcy52aWV3cG9ydCQubmV4dCh2aWV3cG9ydClcbiAgfVxuXG4gIHB1YmxpYyBzZWxlY3QoZW50aXR5OiBGbG93RW50aXR5IHwgbnVsbCkge1xuICAgIC8vIHVuZG8gc2VsZWN0IGZvciBwcmV2aW91c2x5IHNlbGVjdGVkIG5vZGVzXG4gICAgdGhpcy5mbG93RW50aXRpZXNTZXJ2aWNlLmVudGl0aWVzKClcbiAgICAgIC5maWx0ZXIobiA9PiBuLnNlbGVjdGVkKVxuICAgICAgLmZvckVhY2gobiA9PiBuLnNlbGVjdGVkLnNldChmYWxzZSkpXG5cbiAgICBpZiAoZW50aXR5KSB7XG4gICAgICAvLyBzZWxlY3QgcGFzc2VkIGVudGl0eVxuICAgICAgZW50aXR5LnNlbGVjdGVkLnNldCh0cnVlKVxuICAgIH1cbiAgfVxufVxuIl19
@@ -10,6 +10,7 @@ export * from './lib/vflow/interfaces/connection.interface';
10
10
  export * from './lib/vflow/interfaces/connection-settings.interface';
11
11
  export * from './lib/vflow/interfaces/handle-positions.interface';
12
12
  export * from './lib/vflow/interfaces/marker.interface';
13
+ export * from './lib/vflow/interfaces/component-node-event.interface';
13
14
  // Types
14
15
  export * from './lib/vflow/types/node-change.type';
15
16
  export * from './lib/vflow/types/edge-change.type';
@@ -17,9 +18,10 @@ export * from './lib/vflow/types/position.type';
17
18
  // Components
18
19
  export * from './lib/vflow/components/vflow/vflow.component';
19
20
  export * from './lib/vflow/components/handle/handle.component';
21
+ export * from './lib/vflow/public-components/custom-node.component';
20
22
  // Directives
21
23
  export * from './lib/vflow/directives/template.directive';
22
24
  export * from './lib/vflow/directives/connection-controller.directive';
23
25
  export * from './lib/vflow/directives/changes-controller.directive';
24
26
  export * from './lib/vflow/directives/selectable.directive';
25
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicHVibGljLWFwaS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3Byb2plY3RzL25neC12Zmxvdy1saWIvc3JjL3B1YmxpYy1hcGkudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsVUFBVTtBQUNWLGNBQWMsMEJBQTBCLENBQUM7QUFFekMsYUFBYTtBQUNiLGNBQWMsdUNBQXVDLENBQUM7QUFDdEQsY0FBYyx3Q0FBd0MsQ0FBQztBQUN2RCxjQUFjLHVDQUF1QyxDQUFDO0FBQ3RELGNBQWMsNkNBQTZDLENBQUM7QUFDNUQsY0FBYyw2Q0FBNkMsQ0FBQztBQUM1RCxjQUFjLDZDQUE2QyxDQUFDO0FBQzVELGNBQWMsc0RBQXNELENBQUM7QUFDckUsY0FBYyxtREFBbUQsQ0FBQztBQUNsRSxjQUFjLHlDQUF5QyxDQUFDO0FBR3hELFFBQVE7QUFDUixjQUFjLG9DQUFvQyxDQUFDO0FBQ25ELGNBQWMsb0NBQW9DLENBQUM7QUFDbkQsY0FBYyxpQ0FBaUMsQ0FBQztBQUVoRCxhQUFhO0FBQ2IsY0FBYyw4Q0FBOEMsQ0FBQztBQUM3RCxjQUFjLGdEQUFnRCxDQUFDO0FBRS9ELGFBQWE7QUFDYixjQUFjLDJDQUEyQyxDQUFDO0FBQzFELGNBQWMsd0RBQXdELENBQUM7QUFDdkUsY0FBYyxxREFBcUQsQ0FBQztBQUNwRSxjQUFjLDZDQUE2QyxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiLy8gTW9kdWxlc1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvdmZsb3cubW9kdWxlJztcblxuLy8gSW50ZXJmYWNlc1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9ub2RlLmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL3BvaW50LmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL2VkZ2UuaW50ZXJmYWNlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2ludGVyZmFjZXMvZWRnZS1sYWJlbC5pbnRlcmZhY2UnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9jb25uZWN0aW9uLmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL2Nvbm5lY3Rpb24uaW50ZXJmYWNlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2ludGVyZmFjZXMvY29ubmVjdGlvbi1zZXR0aW5ncy5pbnRlcmZhY2UnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9oYW5kbGUtcG9zaXRpb25zLmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL21hcmtlci5pbnRlcmZhY2UnO1xuZXhwb3J0IHsgVmlld3BvcnRTdGF0ZSB9IGZyb20gJy4vbGliL3ZmbG93L2ludGVyZmFjZXMvdmlld3BvcnQuaW50ZXJmYWNlJztcblxuLy8gVHlwZXNcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L3R5cGVzL25vZGUtY2hhbmdlLnR5cGUnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvdHlwZXMvZWRnZS1jaGFuZ2UudHlwZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy90eXBlcy9wb3NpdGlvbi50eXBlJztcblxuLy8gQ29tcG9uZW50c1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvY29tcG9uZW50cy92Zmxvdy92Zmxvdy5jb21wb25lbnQnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvY29tcG9uZW50cy9oYW5kbGUvaGFuZGxlLmNvbXBvbmVudCc7XG5cbi8vIERpcmVjdGl2ZXNcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2RpcmVjdGl2ZXMvdGVtcGxhdGUuZGlyZWN0aXZlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2RpcmVjdGl2ZXMvY29ubmVjdGlvbi1jb250cm9sbGVyLmRpcmVjdGl2ZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9kaXJlY3RpdmVzL2NoYW5nZXMtY29udHJvbGxlci5kaXJlY3RpdmUnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvZGlyZWN0aXZlcy9zZWxlY3RhYmxlLmRpcmVjdGl2ZSc7XG4iXX0=
27
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicHVibGljLWFwaS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uL3Byb2plY3RzL25neC12Zmxvdy1saWIvc3JjL3B1YmxpYy1hcGkudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsVUFBVTtBQUNWLGNBQWMsMEJBQTBCLENBQUM7QUFFekMsYUFBYTtBQUNiLGNBQWMsdUNBQXVDLENBQUM7QUFDdEQsY0FBYyx3Q0FBd0MsQ0FBQztBQUN2RCxjQUFjLHVDQUF1QyxDQUFDO0FBQ3RELGNBQWMsNkNBQTZDLENBQUM7QUFDNUQsY0FBYyw2Q0FBNkMsQ0FBQztBQUM1RCxjQUFjLDZDQUE2QyxDQUFDO0FBQzVELGNBQWMsc0RBQXNELENBQUM7QUFDckUsY0FBYyxtREFBbUQsQ0FBQztBQUNsRSxjQUFjLHlDQUF5QyxDQUFDO0FBRXhELGNBQWMsdURBQXVELENBQUM7QUFFdEUsUUFBUTtBQUNSLGNBQWMsb0NBQW9DLENBQUM7QUFDbkQsY0FBYyxvQ0FBb0MsQ0FBQztBQUNuRCxjQUFjLGlDQUFpQyxDQUFDO0FBRWhELGFBQWE7QUFDYixjQUFjLDhDQUE4QyxDQUFDO0FBQzdELGNBQWMsZ0RBQWdELENBQUM7QUFDL0QsY0FBYyxxREFBcUQsQ0FBQztBQUVwRSxhQUFhO0FBQ2IsY0FBYywyQ0FBMkMsQ0FBQztBQUMxRCxjQUFjLHdEQUF3RCxDQUFDO0FBQ3ZFLGNBQWMscURBQXFELENBQUM7QUFDcEUsY0FBYyw2Q0FBNkMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8vIE1vZHVsZXNcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L3ZmbG93Lm1vZHVsZSc7XG5cbi8vIEludGVyZmFjZXNcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2ludGVyZmFjZXMvbm9kZS5pbnRlcmZhY2UnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9wb2ludC5pbnRlcmZhY2UnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9lZGdlLmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL2VkZ2UtbGFiZWwuaW50ZXJmYWNlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2ludGVyZmFjZXMvY29ubmVjdGlvbi5pbnRlcmZhY2UnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9jb25uZWN0aW9uLmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL2Nvbm5lY3Rpb24tc2V0dGluZ3MuaW50ZXJmYWNlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2ludGVyZmFjZXMvaGFuZGxlLXBvc2l0aW9ucy5pbnRlcmZhY2UnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvaW50ZXJmYWNlcy9tYXJrZXIuaW50ZXJmYWNlJztcbmV4cG9ydCB7IFZpZXdwb3J0U3RhdGUgfSBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL3ZpZXdwb3J0LmludGVyZmFjZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9pbnRlcmZhY2VzL2NvbXBvbmVudC1ub2RlLWV2ZW50LmludGVyZmFjZSc7XG5cbi8vIFR5cGVzXG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy90eXBlcy9ub2RlLWNoYW5nZS50eXBlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L3R5cGVzL2VkZ2UtY2hhbmdlLnR5cGUnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvdHlwZXMvcG9zaXRpb24udHlwZSc7XG5cbi8vIENvbXBvbmVudHNcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2NvbXBvbmVudHMvdmZsb3cvdmZsb3cuY29tcG9uZW50JztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2NvbXBvbmVudHMvaGFuZGxlL2hhbmRsZS5jb21wb25lbnQnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvcHVibGljLWNvbXBvbmVudHMvY3VzdG9tLW5vZGUuY29tcG9uZW50JztcblxuLy8gRGlyZWN0aXZlc1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvZGlyZWN0aXZlcy90ZW1wbGF0ZS5kaXJlY3RpdmUnO1xuZXhwb3J0ICogZnJvbSAnLi9saWIvdmZsb3cvZGlyZWN0aXZlcy9jb25uZWN0aW9uLWNvbnRyb2xsZXIuZGlyZWN0aXZlJztcbmV4cG9ydCAqIGZyb20gJy4vbGliL3ZmbG93L2RpcmVjdGl2ZXMvY2hhbmdlcy1jb250cm9sbGVyLmRpcmVjdGl2ZSc7XG5leHBvcnQgKiBmcm9tICcuL2xpYi92Zmxvdy9kaXJlY3RpdmVzL3NlbGVjdGFibGUuZGlyZWN0aXZlJztcbiJdfQ==
@@ -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, untracked, runInInjectionContext, HostListener, Injector, NgZone, Component, ChangeDetectionStrategy, ViewChild, ContentChild, NgModule } from '@angular/core';
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, switchMap, merge, skip, map, pairwise, filter, distinctUntilChanged, observeOn, asyncScheduler, zip, Observable, fromEvent, animationFrameScheduler, share, Subscription, startWith } from 'rxjs';
8
- import { takeUntilDestroyed, toObservable, toSignal } from '@angular/core/rxjs-interop';
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
- // TODO: hack with timer fixes wrong node scaling (handle positions not matched with content size)
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
- this.rootSvgSelection.call(this.zoomBehavior.translateTo, state.x, state.y);
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
- }), { allowSignalWrites: true });
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.point.set({
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.point = signal({ x: 0, y: 0 });
487
- this.point$ = toObservable(this.point);
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.point.set(node.point);
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 {
@@ -1264,6 +1344,8 @@ class NodeComponent {
1264
1344
  this.hostRef = inject(ElementRef);
1265
1345
  this.showMagnet = computed(() => this.flowStatusService.status().state === 'connection-start' ||
1266
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`);
1267
1349
  this.subscription = new Subscription();
1268
1350
  }
1269
1351
  ngOnInit() {
@@ -1278,10 +1360,12 @@ class NodeComponent {
1278
1360
  ngAfterViewInit() {
1279
1361
  this.setInitialHandles();
1280
1362
  if (this.nodeModel.node.type === 'default') {
1281
- const { width, height } = this.nodeContentRef.nativeElement.getBBox();
1282
- this.nodeModel.size.set({ width, height });
1363
+ this.nodeModel.size.set({
1364
+ width: this.nodeModel.node.width ?? NodeModel.defaultTypeSize.width,
1365
+ height: this.nodeModel.node.height ?? NodeModel.defaultTypeSize.height
1366
+ });
1283
1367
  }
1284
- if (this.nodeModel.node.type === 'html-template') {
1368
+ if (this.nodeModel.node.type === 'html-template' || this.nodeModel.isComponentType) {
1285
1369
  const sub = resizable([this.htmlWrapperRef.nativeElement], this.zone)
1286
1370
  .pipe(startWith(null), tap(() => {
1287
1371
  const width = this.htmlWrapperRef.nativeElement.clientWidth;
@@ -1369,7 +1453,7 @@ class NodeComponent {
1369
1453
  }
1370
1454
  }
1371
1455
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: NodeComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
1372
- 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=\"100\"\n height=\"50\"\n (mousedown)=\"pullNode(); selectNode()\"\n>\n <div\n #htmlWrapper\n class=\"default-node\"\n [class.default-node_selected]=\"nodeModel.selected()\"\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<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\n", styles: [".wrapper{width:max-content}.magnet{opacity:0}.default-node{max-width:100px;max-height:100px;width:100px;height:50px;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.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 }); }
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 }); }
1373
1457
  }
1374
1458
  __decorate([
1375
1459
  Microtask
@@ -1379,7 +1463,7 @@ __decorate([
1379
1463
  ], NodeComponent.prototype, "setInitialHandles", null);
1380
1464
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: NodeComponent, decorators: [{
1381
1465
  type: Component,
1382
- 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=\"100\"\n height=\"50\"\n (mousedown)=\"pullNode(); selectNode()\"\n>\n <div\n #htmlWrapper\n class=\"default-node\"\n [class.default-node_selected]=\"nodeModel.selected()\"\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<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\n", styles: [".wrapper{width:max-content}.magnet{opacity:0}.default-node{max-width:100px;max-height:100px;width:100px;height:50px;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"] }]
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"] }]
1383
1467
  }], propDecorators: { nodeModel: [{
1384
1468
  type: Input
1385
1469
  }], nodeHtmlTemplate: [{
@@ -1721,6 +1805,7 @@ class VflowComponent {
1721
1805
  this.edgesChangeService = inject(EdgeChangesService);
1722
1806
  this.nodeRenderingService = inject(NodeRenderingService);
1723
1807
  this.flowSettingsService = inject(FlowSettingsService);
1808
+ this.componentEventBusService = inject(ComponentEventBusService);
1724
1809
  this.injector = inject(Injector);
1725
1810
  /**
1726
1811
  * Minimum zoom value
@@ -1737,6 +1822,14 @@ class VflowComponent {
1737
1822
  this.nodeModels = computed(() => this.nodeRenderingService.nodes());
1738
1823
  this.edgeModels = computed(() => this.flowEntitiesService.validEdges());
1739
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
1740
1833
  // #region SIGNAL_API
1741
1834
  /**
1742
1835
  * Signal for reading viewport change
@@ -1873,7 +1966,7 @@ class VflowComponent {
1873
1966
  return edge;
1874
1967
  }
1875
1968
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: VflowComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
1876
- 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: [
1877
1970
  DraggableService,
1878
1971
  ViewportService,
1879
1972
  FlowStatusService,
@@ -1882,7 +1975,8 @@ class VflowComponent {
1882
1975
  EdgeChangesService,
1883
1976
  NodeRenderingService,
1884
1977
  SelectionService,
1885
- FlowSettingsService
1978
+ FlowSettingsService,
1979
+ ComponentEventBusService
1886
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 }); }
1887
1981
  }
1888
1982
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImport: i0, type: VflowComponent, decorators: [{
@@ -1896,7 +1990,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
1896
1990
  EdgeChangesService,
1897
1991
  NodeRenderingService,
1898
1992
  SelectionService,
1899
- FlowSettingsService
1993
+ FlowSettingsService,
1994
+ ComponentEventBusService
1900
1995
  ], hostDirectives: [
1901
1996
  connectionControllerHostDirective,
1902
1997
  changesControllerHostDirective
@@ -1921,6 +2016,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
1921
2016
  args: [{ required: true }]
1922
2017
  }], edges: [{
1923
2018
  type: Input
2019
+ }], onComponentNodeEvent: [{
2020
+ type: Output
1924
2021
  }], nodeHtmlDirective: [{
1925
2022
  type: ContentChild,
1926
2023
  args: [NodeHtmlTemplateDirective]
@@ -2086,5 +2183,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "16.2.12", ngImpo
2086
2183
  * Generated bundle index. Do not edit.
2087
2184
  */
2088
2185
 
2089
- 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 };
2090
2187
  //# sourceMappingURL=ngx-vflow.mjs.map