@gravity-ui/graph
Version:
Modern graph editor component
78 lines (77 loc) • 2.89 kB
JavaScript
import { HitBox } from "../../../services/HitTest";
import { getXY } from "../../../utils/functions";
import { dragListener } from "../../../utils/functions/dragListener";
import { EVENTS } from "../../../utils/types/events";
import { EventedComponent } from "../EventedComponent/EventedComponent";
export class GraphComponent extends EventedComponent {
constructor(props, parent) {
super(props, parent);
this.unsubscribe = [];
this.hitBox = new HitBox(this, this.context.graph.hitTest);
}
onDrag({ onDragStart, onDragUpdate, onDrop, isDraggable, }) {
let startDragCoords;
return this.addEventListener("mousedown", (event) => {
if (!isDraggable?.(event)) {
return;
}
event.stopPropagation();
dragListener(this.context.ownerDocument)
.on(EVENTS.DRAG_START, (event) => {
if (onDragStart?.(event) === false) {
return;
}
this.context.graph.getGraphLayer().captureEvents(this);
const xy = getXY(this.context.canvas, event);
startDragCoords = this.context.camera.applyToPoint(xy[0], xy[1]);
})
.on(EVENTS.DRAG_UPDATE, (event) => {
if (!startDragCoords.length)
return;
const [canvasX, canvasY] = getXY(this.context.canvas, event);
const currentCoords = this.context.camera.applyToPoint(canvasX, canvasY);
const diffX = (startDragCoords[0] - currentCoords[0]) | 0;
const diffY = (startDragCoords[1] - currentCoords[1]) | 0;
onDragUpdate?.({ prevCoords: startDragCoords, currentCoords, diffX, diffY }, event);
startDragCoords = currentCoords;
})
.on(EVENTS.DRAG_END, (_event) => {
this.context.graph.getGraphLayer().releaseCapture();
startDragCoords = undefined;
onDrop?.(_event);
});
});
}
subscribeSignal(signal, cb) {
this.unsubscribe.push(signal.subscribe(cb));
}
unmount() {
super.unmount();
this.unsubscribe.forEach((cb) => cb());
this.destroyHitBox();
}
setHitBox(minX, minY, maxX, maxY, force) {
this.hitBox.update(minX, minY, maxX, maxY, force);
}
willIterate() {
super.willIterate();
if (!this.firstIterate) {
this.shouldRender = this.isVisible();
}
}
isVisible() {
return this.context.camera.isRectVisible(...this.getHitBox());
}
getHitBox() {
return this.hitBox.getRect();
}
removeHitBox() {
this.hitBox.remove();
}
destroyHitBox() {
this.hitBox.destroy();
}
onHitBox(_) {
return this.isIterated();
}
}