@gravity-ui/graph
Version:
Modern graph editor component
124 lines (123 loc) • 4.93 kB
TypeScript
import { GraphMouseEvent } from "../../../../graphEvents";
import { Layer, LayerContext, LayerProps } from "../../../../services/Layer";
import { AnchorState } from "../../../../store/anchor/Anchor";
import { BlockState, TBlockId } from "../../../../store/block/Block";
import { Point, TPoint } from "../../../../utils/types/shapes";
import { Anchor } from "../../../canvas/anchors";
import { Block } from "../../../canvas/blocks/Block";
type TIcon = {
path: string;
fill?: string;
stroke?: string;
width: number;
height: number;
viewWidth: number;
viewHeight: number;
};
type LineStyle = {
color: string;
dash: number[];
};
type DrawLineFunction = (start: TPoint, end: TPoint) => {
path: Path2D;
style: LineStyle;
};
type ConnectionLayerProps = LayerProps & {
createIcon?: TIcon;
point?: TIcon;
drawLine?: DrawLineFunction;
isConnectionAllowed?: (sourceComponent: BlockState | AnchorState) => boolean;
};
declare module "../../../../graphEvents" {
interface GraphEventsDefinitions {
/**
* Fired when a user initiates a connection from a block or anchor.
* This happens when dragging starts from a block (with Shift key) or an anchor.
* Preventing this event will prevent the selection of the source component.
*/
"connection-create-start": (event: CustomEvent<{
blockId: TBlockId;
anchorId: string | undefined;
}>) => void;
/**
* Fired when the dragged connection endpoint hovers over a potential target block or anchor.
* Preventing this event will prevent the selection of the target component.
*/
"connection-create-hover": (event: CustomEvent<{
sourceBlockId: TBlockId;
sourceAnchorId: string | undefined;
targetBlockId: TBlockId | undefined;
targetAnchorId: string | undefined;
}>) => void;
/**
* Fired when a connection is successfully created between two elements.
* By default, this adds the connection to the connectionsList in the store.
* Preventing this event will prevent the connection from being added to the store.
*/
"connection-created": (event: CustomEvent<{
sourceBlockId: TBlockId;
sourceAnchorId?: string;
targetBlockId: TBlockId;
targetAnchorId?: string;
}>) => void;
/**
* Fired when the user releases the mouse button to complete the connection process.
* This event fires regardless of whether a valid connection was established.
* Can be used for cleanup or to handle custom connection drop behavior.
*/
"connection-create-drop": (event: CustomEvent<{
sourceBlockId: TBlockId;
sourceAnchorId: string;
targetBlockId?: TBlockId;
targetAnchorId?: string;
point: Point;
}>) => void;
}
}
/**
* ConnectionLayer manages the creation process of connections between blocks and anchors in the graph.
* It handles the temporary visualization during connection creation but does not render existing connections.
*
* Features:
* - Interactive connection creation through drag and drop
* - Temporary visualization during connection creation with configurable icons and line styles
* - Automatic selection handling of source and target elements
* - Comprehensive event system for the connection creation lifecycle
* - Optional connection validation through isConnectionAllowed prop
*
* Connection types:
* - Block-to-Block: Hold Shift key and drag from one block to another
* - Anchor-to-Anchor: Drag from one anchor to another (must be on different blocks)
*
* The layer renders on a separate canvas with a higher z-index and handles
* all mouse interactions for connection creation.
*/
export declare class ConnectionLayer extends Layer<ConnectionLayerProps, LayerContext & {
canvas: HTMLCanvasElement;
ctx: CanvasRenderingContext2D;
}> {
private startState;
private endState;
protected target?: Block | Anchor;
protected sourceComponent?: BlockState | AnchorState;
protected enabled: boolean;
private eventAborter;
constructor(props: ConnectionLayerProps);
/**
* Called after initialization and when the layer is reattached.
* This is where we set up event subscriptions to ensure they work properly
* after the layer is unmounted and reattached.
*/
protected afterInit(): void;
enable: () => void;
disable: () => void;
protected handleMouseDown: (nativeEvent: GraphMouseEvent) => void;
protected renderEndpoint(ctx: CanvasRenderingContext2D): void;
protected render(): void;
private getBlockId;
private getAnchorId;
private onStartConnection;
private onMoveNewConnection;
private onEndNewConnection;
}
export {};