react-cosmos-diagram 0.7.0 → 0.7.2
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/dist/esm/components/DragBox/index.d.ts +1 -1
- package/dist/esm/components/DragBox/index.d.ts.map +1 -1
- package/dist/esm/components/Edges/Anchor.d.ts +1 -1
- package/dist/esm/components/Edges/Anchor.d.ts.map +1 -1
- package/dist/esm/components/Edges/EdgeWrapper/type.d.ts +1 -1
- package/dist/esm/components/Edges/EdgeWrapper/type.d.ts.map +1 -1
- package/dist/esm/components/Edges/type.d.ts +1 -1
- package/dist/esm/components/Edges/type.d.ts.map +1 -1
- package/dist/esm/components/Node/NodeWrapper/index.d.ts +1 -1
- package/dist/esm/components/Node/NodeWrapper/index.d.ts.map +1 -1
- package/dist/esm/components/Node/NodeWrapper/type.d.ts +1 -1
- package/dist/esm/components/Node/NodeWrapper/type.d.ts.map +1 -1
- package/dist/esm/components/Node/type.d.ts +1 -1
- package/dist/esm/components/Node/type.d.ts.map +1 -1
- package/dist/esm/components/Port/index.d.ts +1 -1
- package/dist/esm/components/Port/index.d.ts.map +1 -1
- package/dist/esm/components/ReactDiagramProvider/type.d.ts +1 -1
- package/dist/esm/components/ReactDiagramProvider/type.d.ts.map +1 -1
- package/dist/esm/components/SelectionBox/index.d.ts +1 -1
- package/dist/esm/components/SelectionBox/index.d.ts.map +1 -1
- package/dist/esm/components/SelectionBox/type.d.ts +1 -1
- package/dist/esm/components/SelectionBox/type.d.ts.map +1 -1
- package/dist/esm/container/ConnectionLineRenderer/ConnectionPath.d.ts +1 -1
- package/dist/esm/container/ConnectionLineRenderer/ConnectionPath.d.ts.map +1 -1
- package/dist/esm/container/ConnectionLineRenderer/type.d.ts +1 -1
- package/dist/esm/container/ConnectionLineRenderer/type.d.ts.map +1 -1
- package/dist/esm/container/EdgeRenderer/MarkerSymbols.d.ts +1 -1
- package/dist/esm/container/EdgeRenderer/MarkerSymbols.d.ts.map +1 -1
- package/dist/esm/container/EdgeRenderer/utils.d.ts +2 -2
- package/dist/esm/container/EdgeRenderer/utils.d.ts.map +1 -1
- package/dist/esm/container/ReactDiagram/index.d.ts +10 -10
- package/dist/esm/container/ReactDiagram/index.d.ts.map +1 -1
- package/dist/esm/contexts/{RFStoreContext.d.ts → RCDStoreContext.d.ts} +1 -1
- package/dist/esm/contexts/RCDStoreContext.d.ts.map +1 -0
- package/dist/esm/hooks/useDrag.d.ts +1 -1
- package/dist/esm/hooks/useDrag.d.ts.map +1 -1
- package/dist/esm/hooks/useNodesEdgesState/type.d.ts +1 -1
- package/dist/esm/hooks/useNodesEdgesState/type.d.ts.map +1 -1
- package/dist/esm/index.d.ts +3 -3
- package/dist/esm/index.d.ts.map +1 -1
- package/dist/esm/index.js +7 -1182
- package/dist/esm/index.mjs +1811 -0
- package/dist/esm/store/index.d.ts +2 -2
- package/dist/esm/store/index.d.ts.map +1 -1
- package/dist/esm/store/initialState.d.ts +1 -1
- package/dist/esm/store/initialState.d.ts.map +1 -1
- package/dist/esm/store/utils.d.ts +1 -1
- package/dist/esm/store/utils.d.ts.map +1 -1
- package/dist/esm/types/core.d.ts +1 -1
- package/dist/esm/types/core.d.ts.map +1 -1
- package/dist/esm/types/general.d.ts +1 -1
- package/dist/esm/types/general.d.ts.map +1 -1
- package/dist/esm/utils/index.d.ts +1 -1
- package/dist/esm/utils/index.d.ts.map +1 -1
- package/dist/umd/components/DragBox/index.d.ts +1 -1
- package/dist/umd/components/DragBox/index.d.ts.map +1 -1
- package/dist/umd/components/Edges/Anchor.d.ts +1 -1
- package/dist/umd/components/Edges/Anchor.d.ts.map +1 -1
- package/dist/umd/components/Edges/EdgeWrapper/type.d.ts +1 -1
- package/dist/umd/components/Edges/EdgeWrapper/type.d.ts.map +1 -1
- package/dist/umd/components/Edges/type.d.ts +1 -1
- package/dist/umd/components/Edges/type.d.ts.map +1 -1
- package/dist/umd/components/Node/NodeWrapper/index.d.ts +1 -1
- package/dist/umd/components/Node/NodeWrapper/index.d.ts.map +1 -1
- package/dist/umd/components/Node/NodeWrapper/type.d.ts +1 -1
- package/dist/umd/components/Node/NodeWrapper/type.d.ts.map +1 -1
- package/dist/umd/components/Node/type.d.ts +1 -1
- package/dist/umd/components/Node/type.d.ts.map +1 -1
- package/dist/umd/components/Port/index.d.ts +1 -1
- package/dist/umd/components/Port/index.d.ts.map +1 -1
- package/dist/umd/components/ReactDiagramProvider/type.d.ts +1 -1
- package/dist/umd/components/ReactDiagramProvider/type.d.ts.map +1 -1
- package/dist/umd/components/SelectionBox/index.d.ts +1 -1
- package/dist/umd/components/SelectionBox/index.d.ts.map +1 -1
- package/dist/umd/components/SelectionBox/type.d.ts +1 -1
- package/dist/umd/components/SelectionBox/type.d.ts.map +1 -1
- package/dist/umd/container/ConnectionLineRenderer/ConnectionPath.d.ts +1 -1
- package/dist/umd/container/ConnectionLineRenderer/ConnectionPath.d.ts.map +1 -1
- package/dist/umd/container/ConnectionLineRenderer/type.d.ts +1 -1
- package/dist/umd/container/ConnectionLineRenderer/type.d.ts.map +1 -1
- package/dist/umd/container/EdgeRenderer/MarkerSymbols.d.ts +1 -1
- package/dist/umd/container/EdgeRenderer/MarkerSymbols.d.ts.map +1 -1
- package/dist/umd/container/EdgeRenderer/utils.d.ts +2 -2
- package/dist/umd/container/EdgeRenderer/utils.d.ts.map +1 -1
- package/dist/umd/container/ReactDiagram/index.d.ts +10 -10
- package/dist/umd/container/ReactDiagram/index.d.ts.map +1 -1
- package/dist/umd/contexts/{RFStoreContext.d.ts → RCDStoreContext.d.ts} +1 -1
- package/dist/umd/contexts/RCDStoreContext.d.ts.map +1 -0
- package/dist/umd/hooks/useDrag.d.ts +1 -1
- package/dist/umd/hooks/useDrag.d.ts.map +1 -1
- package/dist/umd/hooks/useNodesEdgesState/type.d.ts +1 -1
- package/dist/umd/hooks/useNodesEdgesState/type.d.ts.map +1 -1
- package/dist/umd/index.d.ts +3 -3
- package/dist/umd/index.d.ts.map +1 -1
- package/dist/umd/store/index.d.ts +2 -2
- package/dist/umd/store/index.d.ts.map +1 -1
- package/dist/umd/store/initialState.d.ts +1 -1
- package/dist/umd/store/initialState.d.ts.map +1 -1
- package/dist/umd/store/utils.d.ts +1 -1
- package/dist/umd/store/utils.d.ts.map +1 -1
- package/dist/umd/types/core.d.ts +1 -1
- package/dist/umd/types/core.d.ts.map +1 -1
- package/dist/umd/types/general.d.ts +1 -1
- package/dist/umd/types/general.d.ts.map +1 -1
- package/dist/umd/utils/index.d.ts +1 -1
- package/dist/umd/utils/index.d.ts.map +1 -1
- package/package.json +2 -6
- package/dist/esm/contexts/RFStoreContext.d.ts.map +0 -1
- package/dist/umd/contexts/RFStoreContext.d.ts.map +0 -1
package/dist/esm/index.js
CHANGED
|
@@ -1,1187 +1,12 @@
|
|
|
1
|
-
|
|
2
|
-
import {
|
|
3
|
-
|
|
1
|
+
"use client"
|
|
2
|
+
import { errorMessages, CosmosPanZoom, CosmosDrag, getRectOfNodes, getEventPosition, getNodesInside, Position, internalsSymbol as internalsSymbol$1, MarkerType, getMarkerId, isNumeric, getStraightPath, getStepPath, getBezierPath, CosmosPort, devWarn, isMouseEvent, clampPosition, getNodePositionWithOrigin, getDimensions, getPortBounds } from 'cosmos-diagram';
|
|
3
|
+
export { MarkerType, Position, addEdge, boxToRect, clamp, getBezierEdgeCenter, getBezierPath, getStepPath, getStraightPath, isCoreEdge, isCoreNode, rectToBox, updateEdge } from 'cosmos-diagram';
|
|
4
4
|
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
5
5
|
import { createContext, useContext, useMemo, useState, useEffect, useRef, memo, useCallback, forwardRef } from 'react';
|
|
6
6
|
import { useStore as useStore$1, createStore } from 'zustand';
|
|
7
7
|
import cc from 'classcat';
|
|
8
8
|
import { shallow } from 'zustand/shallow';
|
|
9
|
-
|
|
10
|
-
var Position;
|
|
11
|
-
(function (Position) {
|
|
12
|
-
Position["Left"] = "left";
|
|
13
|
-
Position["Top"] = "top";
|
|
14
|
-
Position["Right"] = "right";
|
|
15
|
-
Position["Bottom"] = "bottom";
|
|
16
|
-
})(Position || (Position = {}));
|
|
17
|
-
|
|
18
|
-
// export const internalsSymbol = Symbol.for('internals');
|
|
19
|
-
const internalsSymbol$1 = 'internals';
|
|
20
|
-
|
|
21
|
-
var MarkerType;
|
|
22
|
-
(function (MarkerType) {
|
|
23
|
-
MarkerType["Arrow"] = "arrow";
|
|
24
|
-
})(MarkerType || (MarkerType = {}));
|
|
25
|
-
|
|
26
|
-
const getDimensions = (node) => ({
|
|
27
|
-
width: node.offsetWidth,
|
|
28
|
-
height: node.offsetHeight,
|
|
29
|
-
});
|
|
30
|
-
const getPortBounds = (selector, nodeElement, zoom, nodeOrigin) => {
|
|
31
|
-
const ports = nodeElement.querySelectorAll(selector);
|
|
32
|
-
if (!ports || !ports.length) {
|
|
33
|
-
return null;
|
|
34
|
-
}
|
|
35
|
-
const portsArray = Array.from(ports);
|
|
36
|
-
const nodeBounds = nodeElement.getBoundingClientRect();
|
|
37
|
-
const nodeOffset = {
|
|
38
|
-
x: nodeBounds.width * nodeOrigin[0],
|
|
39
|
-
y: nodeBounds.height * nodeOrigin[1],
|
|
40
|
-
};
|
|
41
|
-
return portsArray.map((port) => {
|
|
42
|
-
const portBounds = port.getBoundingClientRect();
|
|
43
|
-
return {
|
|
44
|
-
id: port.getAttribute('data-portid'),
|
|
45
|
-
position: port.dataset.portPosition,
|
|
46
|
-
x: (portBounds.left - nodeBounds.left - nodeOffset.x) / zoom,
|
|
47
|
-
y: (portBounds.top - nodeBounds.top - nodeOffset.y) / zoom,
|
|
48
|
-
...getDimensions(port),
|
|
49
|
-
};
|
|
50
|
-
});
|
|
51
|
-
};
|
|
52
|
-
const getHostForElement = (element) => element.getRootNode?.() || window?.document;
|
|
53
|
-
const isMouseEvent = (event) => 'clientX' in event;
|
|
54
|
-
const getEventPosition = (event, bounds) => {
|
|
55
|
-
const isMouseTriggered = isMouseEvent(event);
|
|
56
|
-
const eventX = isMouseTriggered ? event.clientX : event.touches?.[0].clientX;
|
|
57
|
-
const eventY = isMouseTriggered ? event.clientY : event.touches?.[0].clientY;
|
|
58
|
-
return {
|
|
59
|
-
x: eventX - (bounds?.left ?? 0),
|
|
60
|
-
y: eventY - (bounds?.top ?? 0),
|
|
61
|
-
};
|
|
62
|
-
};
|
|
63
|
-
const pointToRendererPoint = ({ x, y }, [tx, ty, tScale]) => {
|
|
64
|
-
const position = {
|
|
65
|
-
x: (x - tx) / tScale,
|
|
66
|
-
y: (y - ty) / tScale,
|
|
67
|
-
};
|
|
68
|
-
return position;
|
|
69
|
-
};
|
|
70
|
-
const rendererPointToPoint = ({ x, y }, [tx, ty, tScale]) => {
|
|
71
|
-
return {
|
|
72
|
-
x: x * tScale + tx,
|
|
73
|
-
y: y * tScale + ty,
|
|
74
|
-
};
|
|
75
|
-
};
|
|
76
|
-
const getPointerPosition = (event, { transform, gridStep, centerStep }) => {
|
|
77
|
-
const { x, y } = getEventPosition(event);
|
|
78
|
-
const pointerPos = pointToRendererPoint({ x, y }, transform);
|
|
79
|
-
const getStepPosition = (params = {
|
|
80
|
-
position: pointerPos,
|
|
81
|
-
}) => {
|
|
82
|
-
const { position, nodeSize } = params;
|
|
83
|
-
if (!gridStep)
|
|
84
|
-
return position;
|
|
85
|
-
let x = gridStep[0] * Math.round(position.x / gridStep[0]), y = gridStep[1] * Math.round(position.y / gridStep[1]);
|
|
86
|
-
if (centerStep && nodeSize) {
|
|
87
|
-
const centerX = (gridStep[0] - nodeSize.width) / 2;
|
|
88
|
-
const centerY = (gridStep[1] - nodeSize.height) / 2;
|
|
89
|
-
const positionX = position.x - centerX;
|
|
90
|
-
const positionY = position.y - centerY;
|
|
91
|
-
x = gridStep[0] * Math.round(positionX / gridStep[0]) + centerX;
|
|
92
|
-
y = gridStep[1] * Math.round(positionY / gridStep[1]) + centerY;
|
|
93
|
-
}
|
|
94
|
-
return {
|
|
95
|
-
x,
|
|
96
|
-
y,
|
|
97
|
-
};
|
|
98
|
-
};
|
|
99
|
-
return {
|
|
100
|
-
getStepPosition,
|
|
101
|
-
...pointerPos,
|
|
102
|
-
};
|
|
103
|
-
};
|
|
104
|
-
|
|
105
|
-
const errorMessages = {
|
|
106
|
-
'001': () => 'Seems like you have not used zustand provider as an ancestor',
|
|
107
|
-
'002': () => 'It looks like you`ve created a new nodeTypes or edgeTypes object. If this wasn`t on purpose please define the nodeTypes/edgeTypes outside of the component or memoize them.',
|
|
108
|
-
'010': (nodeType) => `Node type "${nodeType}" not found. Using fallback type "default".`,
|
|
109
|
-
'011': () => 'Only child nodes can use a parent extent',
|
|
110
|
-
'020': () => 'Can`t create edge. An edge needs a source and a target.',
|
|
111
|
-
'021': (id) => `The old edge with id=${id} does not exist.`,
|
|
112
|
-
'022': (type) => `Marker type "${type}" doesn't exist.`,
|
|
113
|
-
};
|
|
114
|
-
|
|
115
|
-
const clamp = (val, min = 0, max = 1) => Math.min(Math.max(val, min), max);
|
|
116
|
-
const calcAutoPanVelocity = (value, bound, radius, velocity) => {
|
|
117
|
-
const maxRadius = bound - radius;
|
|
118
|
-
if (value < radius) {
|
|
119
|
-
return (clamp(Math.abs(value - radius), 1, 50) / 50) * velocity;
|
|
120
|
-
}
|
|
121
|
-
else if (value > maxRadius) {
|
|
122
|
-
return (-clamp(Math.abs(value - maxRadius), 1, 50) / 50) * velocity;
|
|
123
|
-
}
|
|
124
|
-
return 0;
|
|
125
|
-
};
|
|
126
|
-
const calcAutoPanPosition = (pos, bounds) => {
|
|
127
|
-
const xMovement = calcAutoPanVelocity(pos.x, bounds.width, 30, 10);
|
|
128
|
-
const yMovement = calcAutoPanVelocity(pos.y, bounds.height, 30, 10);
|
|
129
|
-
return [xMovement, yMovement];
|
|
130
|
-
};
|
|
131
|
-
const devWarn = (id, value = '') => {
|
|
132
|
-
if (process.env.NODE_ENV === 'development') {
|
|
133
|
-
console.warn(`[React Diagram]: ${id}-${errorMessages[id](value)}`);
|
|
134
|
-
}
|
|
135
|
-
};
|
|
136
|
-
const rectToBox = ({ x, y, width, height }) => ({
|
|
137
|
-
x,
|
|
138
|
-
y,
|
|
139
|
-
x2: x + width,
|
|
140
|
-
y2: y + height,
|
|
141
|
-
});
|
|
142
|
-
const boxToRect = ({ x, y, x2, y2 }) => ({
|
|
143
|
-
x,
|
|
144
|
-
y,
|
|
145
|
-
width: x2 - x,
|
|
146
|
-
height: y2 - y,
|
|
147
|
-
});
|
|
148
|
-
const getBoundsOfBoxes = (box1, box2) => ({
|
|
149
|
-
x: Math.min(box1.x, box2.x),
|
|
150
|
-
y: Math.min(box1.y, box2.y),
|
|
151
|
-
x2: Math.max(box1.x2, box2.x2),
|
|
152
|
-
y2: Math.max(box1.y2, box2.y2),
|
|
153
|
-
});
|
|
154
|
-
const isNumeric = (n) => !isNaN(n) && isFinite(n);
|
|
155
|
-
const getOverlappingArea = (rectA, rectB) => {
|
|
156
|
-
const xOverlap = Math.max(0, Math.min(rectA.x + rectA.width, rectB.x + rectB.width) -
|
|
157
|
-
Math.max(rectA.x, rectB.x));
|
|
158
|
-
const yOverlap = Math.max(0, Math.min(rectA.y + rectA.height, rectB.y + rectB.height) -
|
|
159
|
-
Math.max(rectA.y, rectB.y));
|
|
160
|
-
return Math.ceil(xOverlap * yOverlap);
|
|
161
|
-
};
|
|
162
|
-
const clampPosition = (position = { x: 0, y: 0 }, extent) => ({
|
|
163
|
-
x: clamp(position.x, extent[0][0], extent[1][0]),
|
|
164
|
-
y: clamp(position.y, extent[0][1], extent[1][1]),
|
|
165
|
-
});
|
|
166
|
-
|
|
167
|
-
const isCoreNode = (element) => 'id' in element && !('source' in element) && !('target' in element);
|
|
168
|
-
const isCoreEdge = (element) => 'source' in element && 'target' in element;
|
|
169
|
-
const getNodePositionWithOrigin = (node, nodeOrigin = [0, 0]) => {
|
|
170
|
-
if (!node) {
|
|
171
|
-
return {
|
|
172
|
-
x: 0,
|
|
173
|
-
y: 0,
|
|
174
|
-
positionAbsolute: {
|
|
175
|
-
x: 0,
|
|
176
|
-
y: 0,
|
|
177
|
-
},
|
|
178
|
-
};
|
|
179
|
-
}
|
|
180
|
-
const offsetX = (node.width ?? 0) * nodeOrigin[0];
|
|
181
|
-
const offsetY = (node.height ?? 0) * nodeOrigin[1];
|
|
182
|
-
const position = {
|
|
183
|
-
x: node.position.x - offsetX,
|
|
184
|
-
y: node.position.y - offsetY,
|
|
185
|
-
};
|
|
186
|
-
return {
|
|
187
|
-
...position,
|
|
188
|
-
positionAbsolute: node.positionAbsolute
|
|
189
|
-
? {
|
|
190
|
-
x: node.positionAbsolute.x - offsetX,
|
|
191
|
-
y: node.positionAbsolute.y - offsetY,
|
|
192
|
-
}
|
|
193
|
-
: position,
|
|
194
|
-
};
|
|
195
|
-
};
|
|
196
|
-
const getNodesInside = (nodeInternals, rect, [tx, ty, tScale] = [0, 0, 1], partially = false, excludeNonSelectableNodes = false, nodeOrigin = [0, 0]) => {
|
|
197
|
-
const paneRect = {
|
|
198
|
-
x: (rect.x - tx) / tScale,
|
|
199
|
-
y: (rect.y - ty) / tScale,
|
|
200
|
-
width: rect.width / tScale,
|
|
201
|
-
height: rect.height / tScale,
|
|
202
|
-
};
|
|
203
|
-
const visibleNodes = [];
|
|
204
|
-
nodeInternals.forEach((node) => {
|
|
205
|
-
const { width, height, selectable = true, hidden = false } = node;
|
|
206
|
-
if ((excludeNonSelectableNodes && !selectable) || hidden) {
|
|
207
|
-
return false;
|
|
208
|
-
}
|
|
209
|
-
const { positionAbsolute } = getNodePositionWithOrigin(node, nodeOrigin);
|
|
210
|
-
const nodeRect = {
|
|
211
|
-
x: positionAbsolute.x,
|
|
212
|
-
y: positionAbsolute.y,
|
|
213
|
-
width: width || 0,
|
|
214
|
-
height: height || 0,
|
|
215
|
-
};
|
|
216
|
-
const overlappingArea = getOverlappingArea(paneRect, nodeRect);
|
|
217
|
-
const notInitialized = typeof width === 'undefined' ||
|
|
218
|
-
typeof height === 'undefined' ||
|
|
219
|
-
width === null ||
|
|
220
|
-
height === null;
|
|
221
|
-
const partiallyVisible = partially && overlappingArea > 0;
|
|
222
|
-
const area = (width || 0) * (height || 0);
|
|
223
|
-
const isVisible = notInitialized || partiallyVisible || overlappingArea >= area;
|
|
224
|
-
if (isVisible || node.dragging) {
|
|
225
|
-
visibleNodes.push(node);
|
|
226
|
-
}
|
|
227
|
-
});
|
|
228
|
-
return visibleNodes;
|
|
229
|
-
};
|
|
230
|
-
const getRectOfNodes = (nodes, nodeOrigin = [0, 0]) => {
|
|
231
|
-
if (nodes.length === 0) {
|
|
232
|
-
return { x: 0, y: 0, width: 0, height: 0 };
|
|
233
|
-
}
|
|
234
|
-
const box = nodes.reduce((currentBox, node) => {
|
|
235
|
-
const { x, y } = getNodePositionWithOrigin(node, nodeOrigin).positionAbsolute;
|
|
236
|
-
const nextBox = rectToBox({
|
|
237
|
-
x,
|
|
238
|
-
y,
|
|
239
|
-
width: node.width || 0,
|
|
240
|
-
height: node.height || 0,
|
|
241
|
-
});
|
|
242
|
-
return getBoundsOfBoxes(currentBox, nextBox);
|
|
243
|
-
}, { x: Infinity, y: Infinity, x2: -Infinity, y2: -Infinity });
|
|
244
|
-
return boxToRect(box);
|
|
245
|
-
};
|
|
246
|
-
const calcNextPosition = (node, nextPosition, nodeInternals, nodeExtent, nodeOrigin = [0, 0]) => {
|
|
247
|
-
let currentExtent = node.extent || nodeExtent;
|
|
248
|
-
if (node.extent && node.parentNode) {
|
|
249
|
-
const parent = nodeInternals.get(node.parentNode);
|
|
250
|
-
const { x: parentX, y: parentY } = getNodePositionWithOrigin(parent, nodeOrigin).positionAbsolute;
|
|
251
|
-
currentExtent = [
|
|
252
|
-
[node.extent[0][0] + parentX, node.extent[0][1] + parentY],
|
|
253
|
-
[node.extent[1][0] + parentX, node.extent[1][1] + parentY],
|
|
254
|
-
];
|
|
255
|
-
}
|
|
256
|
-
let parentPosition = { x: 0, y: 0 };
|
|
257
|
-
if (node.parentNode) {
|
|
258
|
-
const parentNode = nodeInternals.get(node.parentNode);
|
|
259
|
-
parentPosition = getNodePositionWithOrigin(parentNode, nodeOrigin).positionAbsolute;
|
|
260
|
-
}
|
|
261
|
-
const positionAbsolute = currentExtent
|
|
262
|
-
? clampPosition(nextPosition, currentExtent)
|
|
263
|
-
: nextPosition;
|
|
264
|
-
return {
|
|
265
|
-
position: {
|
|
266
|
-
x: positionAbsolute.x - parentPosition.x,
|
|
267
|
-
y: positionAbsolute.y - parentPosition.y,
|
|
268
|
-
},
|
|
269
|
-
positionAbsolute,
|
|
270
|
-
};
|
|
271
|
-
};
|
|
272
|
-
|
|
273
|
-
const getMarkerId = (marker, id) => {
|
|
274
|
-
if (typeof marker === 'undefined')
|
|
275
|
-
return '';
|
|
276
|
-
if (typeof marker === 'string')
|
|
277
|
-
return marker;
|
|
278
|
-
const idPrefix = id ? `${id}__` : '';
|
|
279
|
-
const markerKeys = Object.keys(marker);
|
|
280
|
-
return `${idPrefix}${markerKeys
|
|
281
|
-
.sort()
|
|
282
|
-
.map((key) => `${key}=${marker[key]}`)
|
|
283
|
-
.join('&')}`;
|
|
284
|
-
};
|
|
285
|
-
// export function createMarkerIds(
|
|
286
|
-
// edges: EdgeBase[],
|
|
287
|
-
// {
|
|
288
|
-
// id,
|
|
289
|
-
// defaultColor,
|
|
290
|
-
// defaultMarkerStart,
|
|
291
|
-
// defaultMarkerEnd,
|
|
292
|
-
// }: {
|
|
293
|
-
// id?: string | null;
|
|
294
|
-
// defaultColor?: string;
|
|
295
|
-
// defaultMarkerStart?: EdgeMarker;
|
|
296
|
-
// defaultMarkerEnd?: EdgeMarker;
|
|
297
|
-
// },
|
|
298
|
-
// ) {
|
|
299
|
-
// const ids = new Set<string>();
|
|
300
|
-
// return edges
|
|
301
|
-
// .reduce<(EdgeMarker & { id: string })[]>((markers, edge) => {
|
|
302
|
-
// [
|
|
303
|
-
// edge.markerStart || defaultMarkerStart,
|
|
304
|
-
// edge.markerEnd || defaultMarkerEnd,
|
|
305
|
-
// ].forEach((marker) => {
|
|
306
|
-
// if (marker && typeof marker === 'object') {
|
|
307
|
-
// const markerId = getMarkerId(marker, id);
|
|
308
|
-
// if (!ids.has(markerId)) {
|
|
309
|
-
// markers.push({
|
|
310
|
-
// id: markerId,
|
|
311
|
-
// color: marker.color || defaultColor,
|
|
312
|
-
// ...marker,
|
|
313
|
-
// });
|
|
314
|
-
// ids.add(markerId);
|
|
315
|
-
// }
|
|
316
|
-
// }
|
|
317
|
-
// });
|
|
318
|
-
// return markers;
|
|
319
|
-
// }, [])
|
|
320
|
-
// .sort((a, b) => a.id.localeCompare(b.id));
|
|
321
|
-
// }
|
|
322
|
-
|
|
323
|
-
const getEdgeCenter = ({ sourceX, sourceY, targetX, targetY, }) => {
|
|
324
|
-
const xOffset = Math.abs(targetX - sourceX) / 2;
|
|
325
|
-
const centerX = targetX < sourceX ? targetX + xOffset : targetX - xOffset;
|
|
326
|
-
const yOffset = Math.abs(targetY - sourceY) / 2;
|
|
327
|
-
const centerY = targetY < sourceY ? targetY + yOffset : targetY - yOffset;
|
|
328
|
-
return [centerX, centerY, xOffset, yOffset];
|
|
329
|
-
};
|
|
330
|
-
const getEdgeId = ({ source, sourcePort, target, targetPort, }) => `react-diagram__edge-${source}${sourcePort}-${target}${targetPort}`;
|
|
331
|
-
const isExistsConnection = (edge, edges) => edges.some((el) => el.source === edge.source &&
|
|
332
|
-
el.target === edge.target &&
|
|
333
|
-
(el.sourcePort === edge.sourcePort ||
|
|
334
|
-
(!el.sourcePort && !edge.sourcePort)) &&
|
|
335
|
-
(el.targetPort === edge.targetPort ||
|
|
336
|
-
(!el.targetPort && !edge.targetPort)));
|
|
337
|
-
const addEdge = (edgeParams, edges) => {
|
|
338
|
-
if (!isCoreEdge(edgeParams)) {
|
|
339
|
-
devWarn('020');
|
|
340
|
-
return edges;
|
|
341
|
-
}
|
|
342
|
-
if (isExistsConnection(edgeParams, edges)) {
|
|
343
|
-
return edges;
|
|
344
|
-
}
|
|
345
|
-
let edge;
|
|
346
|
-
if (edgeParams.sourcePort === null) {
|
|
347
|
-
delete edgeParams.sourcePort;
|
|
348
|
-
}
|
|
349
|
-
if (edgeParams.targetPort === null) {
|
|
350
|
-
delete edgeParams.targetPort;
|
|
351
|
-
}
|
|
352
|
-
if (edgeParams.id)
|
|
353
|
-
edge = { ...edgeParams };
|
|
354
|
-
else
|
|
355
|
-
edge = {
|
|
356
|
-
...edgeParams,
|
|
357
|
-
id: getEdgeId(edgeParams),
|
|
358
|
-
};
|
|
359
|
-
return edges.concat(edge);
|
|
360
|
-
};
|
|
361
|
-
const updateEdge = (originEdge, newConnection, edges, options = { shouldReplaceId: true }) => {
|
|
362
|
-
const { id: oldEdgeId, ...rest } = originEdge;
|
|
363
|
-
if (!newConnection.source || !newConnection.target)
|
|
364
|
-
devWarn('020');
|
|
365
|
-
const foundEdge = edges.find((e) => e.id === oldEdgeId);
|
|
366
|
-
if (!foundEdge)
|
|
367
|
-
devWarn('021', oldEdgeId);
|
|
368
|
-
const edge = {
|
|
369
|
-
...rest,
|
|
370
|
-
id: options.shouldReplaceId ? getEdgeId(newConnection) : oldEdgeId,
|
|
371
|
-
source: newConnection.source,
|
|
372
|
-
target: newConnection.target,
|
|
373
|
-
};
|
|
374
|
-
return edges.filter((e) => e.id !== oldEdgeId).concat(edge);
|
|
375
|
-
};
|
|
376
|
-
|
|
377
|
-
const HANDLE_DIRECTIONS = {
|
|
378
|
-
[Position.Left]: { x: -1, y: 0 },
|
|
379
|
-
[Position.Right]: { x: 1, y: 0 },
|
|
380
|
-
[Position.Top]: { x: 0, y: -1 },
|
|
381
|
-
[Position.Bottom]: { x: 0, y: 1 },
|
|
382
|
-
};
|
|
383
|
-
const getDirection = ({ source, sourcePosition = Position.Bottom, target, }) => {
|
|
384
|
-
if (sourcePosition === Position.Left || sourcePosition === Position.Right) {
|
|
385
|
-
// when source Node position is on the left side of a Port of target Node => x = 1
|
|
386
|
-
return source.x < target.x ? { x: 1, y: 0 } : { x: -1, y: 0 };
|
|
387
|
-
}
|
|
388
|
-
//when source Node position is above of a Port of target Node => y = 1
|
|
389
|
-
return source.y < target.y ? { x: 0, y: 1 } : { x: 0, y: -1 };
|
|
390
|
-
};
|
|
391
|
-
const distance = (a, b) => Math.sqrt(Math.pow(b.x - a.x, 2) + Math.pow(b.y - a.y, 2));
|
|
392
|
-
const getPoints = ({ source, sourcePosition = Position.Bottom, target, targetPosition = Position.Top, center, offset, }) => {
|
|
393
|
-
const sourceDir = HANDLE_DIRECTIONS[sourcePosition];
|
|
394
|
-
const targetDir = HANDLE_DIRECTIONS[targetPosition];
|
|
395
|
-
const sourceGapped = {
|
|
396
|
-
x: source.x + sourceDir.x * offset,
|
|
397
|
-
y: source.y + sourceDir.y * offset,
|
|
398
|
-
};
|
|
399
|
-
const targetGapped = {
|
|
400
|
-
x: target.x + targetDir.x * offset,
|
|
401
|
-
y: target.y + targetDir.y * offset,
|
|
402
|
-
};
|
|
403
|
-
const direction = getDirection({
|
|
404
|
-
source: sourceGapped,
|
|
405
|
-
sourcePosition,
|
|
406
|
-
target: targetGapped,
|
|
407
|
-
});
|
|
408
|
-
const dirAccessor = direction.x !== 0 ? 'x' : 'y';
|
|
409
|
-
const currentDirection = direction[dirAccessor];
|
|
410
|
-
let points = [];
|
|
411
|
-
let centerX = 0, centerY = 0;
|
|
412
|
-
const [defaultCenterX, defaultCenterY, defaultOffsetX, defaultOffsetY] = getEdgeCenter({
|
|
413
|
-
sourceX: source.x,
|
|
414
|
-
sourceY: source.y,
|
|
415
|
-
targetX: target.x,
|
|
416
|
-
targetY: target.y,
|
|
417
|
-
});
|
|
418
|
-
const isSourceAndTargetPositionsParallel = sourceDir[dirAccessor] * targetDir[dirAccessor] === -1;
|
|
419
|
-
if (isSourceAndTargetPositionsParallel) {
|
|
420
|
-
centerX = center.x || defaultCenterX;
|
|
421
|
-
centerY = center.y || defaultCenterY;
|
|
422
|
-
const verticalSplit = [
|
|
423
|
-
{ x: centerX, y: sourceGapped.y },
|
|
424
|
-
{ x: centerX, y: targetGapped.y },
|
|
425
|
-
];
|
|
426
|
-
const horizontalSplit = [
|
|
427
|
-
{ x: sourceGapped.x, y: centerY },
|
|
428
|
-
{ x: targetGapped.x, y: centerY },
|
|
429
|
-
];
|
|
430
|
-
const centerLineIsBent = sourceDir[dirAccessor] !== currentDirection;
|
|
431
|
-
if (centerLineIsBent) {
|
|
432
|
-
points = dirAccessor === 'x' ? horizontalSplit : verticalSplit;
|
|
433
|
-
}
|
|
434
|
-
else {
|
|
435
|
-
points = dirAccessor === 'x' ? verticalSplit : horizontalSplit;
|
|
436
|
-
}
|
|
437
|
-
}
|
|
438
|
-
const pathPoints = [source, sourceGapped, ...points, targetGapped, target];
|
|
439
|
-
return [pathPoints, centerX, centerY, defaultOffsetX, defaultOffsetY];
|
|
440
|
-
};
|
|
441
|
-
const getBend = (a, b, c, size) => {
|
|
442
|
-
const bendSize = Math.min(distance(a, b) / 2, distance(b, c) / 2, size);
|
|
443
|
-
const { x, y } = b;
|
|
444
|
-
// no bend
|
|
445
|
-
if ((a.x === x && x === c.x) || (a.y === y && y === c.y)) {
|
|
446
|
-
return `L${x} ${y}`;
|
|
447
|
-
}
|
|
448
|
-
// first segment is horizontal
|
|
449
|
-
if (a.y === y) {
|
|
450
|
-
const xDir = a.x < c.x ? -1 : 1;
|
|
451
|
-
const yDir = a.y < c.y ? 1 : -1;
|
|
452
|
-
return `L ${x + bendSize * xDir},${y}Q ${x},${y} ${x},${y + bendSize * yDir}`;
|
|
453
|
-
}
|
|
454
|
-
const xDir = a.x < c.x ? 1 : -1;
|
|
455
|
-
const yDir = a.y < c.y ? -1 : 1;
|
|
456
|
-
return `L ${x},${y + bendSize * yDir}Q ${x},${y} ${x + bendSize * xDir},${y}`;
|
|
457
|
-
};
|
|
458
|
-
const getStepPath = ({ sourceX, sourceY, sourcePosition = Position.Bottom, targetX, targetY, targetPosition = Position.Top, borderRadius = 5, centerX, centerY, offset = 20, }) => {
|
|
459
|
-
const [points, labelX, labelY, offsetX, offsetY] = getPoints({
|
|
460
|
-
source: { x: sourceX, y: sourceY },
|
|
461
|
-
sourcePosition,
|
|
462
|
-
target: { x: targetX, y: targetY },
|
|
463
|
-
targetPosition,
|
|
464
|
-
center: { x: centerX, y: centerY },
|
|
465
|
-
offset,
|
|
466
|
-
});
|
|
467
|
-
const path = points.reduce((res, p, i) => {
|
|
468
|
-
let segment = '';
|
|
469
|
-
if (i > 0 && i < points.length - 1) {
|
|
470
|
-
segment = getBend(points[i - 1], p, points[i + 1], borderRadius);
|
|
471
|
-
}
|
|
472
|
-
else {
|
|
473
|
-
segment = `${i === 0 ? 'M' : 'L'}${p.x} ${p.y}`;
|
|
474
|
-
}
|
|
475
|
-
res += segment;
|
|
476
|
-
return res;
|
|
477
|
-
}, '');
|
|
478
|
-
return [path, labelX, labelY, offsetX, offsetY];
|
|
479
|
-
};
|
|
480
|
-
|
|
481
|
-
/**
|
|
482
|
-
* Get a straight path from source to target port
|
|
483
|
-
* @param params.sourceX - The x position of the source port
|
|
484
|
-
* @param params.sourceY - The y position of the source port
|
|
485
|
-
* @param params.targetX - The x position of the target port
|
|
486
|
-
* @param params.targetY - The y position of the target port
|
|
487
|
-
* @returns A path string you can use in an SVG, the labelX and labelY position (center of path) and offsetX, offsetY between source port and label
|
|
488
|
-
* @example
|
|
489
|
-
* const source = { x: 0, y: 20 };
|
|
490
|
-
const target = { x: 150, y: 100 };
|
|
491
|
-
|
|
492
|
-
const [path, labelX, labelY, offsetX, offsetY] = getStraightPath({
|
|
493
|
-
sourceX: source.x,
|
|
494
|
-
sourceY: source.y,
|
|
495
|
-
sourcePosition: Position.Right,
|
|
496
|
-
targetX: target.x,
|
|
497
|
-
targetY: target.y,
|
|
498
|
-
targetPosition: Position.Left,
|
|
499
|
-
});
|
|
500
|
-
*/
|
|
501
|
-
const getStraightPath = ({ sourceX, sourceY, targetX, targetY, }) => {
|
|
502
|
-
const [labelX, labelY, offsetX, offsetY] = getEdgeCenter({
|
|
503
|
-
sourceX,
|
|
504
|
-
sourceY,
|
|
505
|
-
targetX,
|
|
506
|
-
targetY,
|
|
507
|
-
});
|
|
508
|
-
return [
|
|
509
|
-
`M ${sourceX},${sourceY}L ${targetX},${targetY}`,
|
|
510
|
-
labelX,
|
|
511
|
-
labelY,
|
|
512
|
-
offsetX,
|
|
513
|
-
offsetY,
|
|
514
|
-
];
|
|
515
|
-
};
|
|
516
|
-
|
|
517
|
-
const getBezierEdgeCenter = ({ sourceX, sourceY, targetX, targetY, sourceControlX, sourceControlY, targetControlX, targetControlY, }) => {
|
|
518
|
-
// cubic bezier t=0.5 mid point, not the actual mid point, but easy to calculate
|
|
519
|
-
// https://stackoverflow.com/questions/67516101/how-to-find-distance-mid-point-of-bezier-curve
|
|
520
|
-
const midPoint = 0.5;
|
|
521
|
-
const point = 0.125;
|
|
522
|
-
const controlPoint = midPoint - point;
|
|
523
|
-
const centerX = sourceX * point +
|
|
524
|
-
sourceControlX * controlPoint +
|
|
525
|
-
targetControlX * controlPoint +
|
|
526
|
-
targetX * point;
|
|
527
|
-
const centerY = sourceY * point +
|
|
528
|
-
sourceControlY * controlPoint +
|
|
529
|
-
targetControlY * controlPoint +
|
|
530
|
-
targetY * point;
|
|
531
|
-
const offsetX = Math.abs(centerX - sourceX);
|
|
532
|
-
const offsetY = Math.abs(centerY - sourceY);
|
|
533
|
-
return [centerX, centerY, offsetX, offsetY];
|
|
534
|
-
};
|
|
535
|
-
const calculateControlOffset = (distance, curvature) => {
|
|
536
|
-
if (distance >= 0) {
|
|
537
|
-
return 0.5 * distance;
|
|
538
|
-
}
|
|
539
|
-
return curvature * 25 * Math.sqrt(-distance);
|
|
540
|
-
};
|
|
541
|
-
const getControlWithCurvature = ({ pos, x1, y1, x2, y2, c, }) => {
|
|
542
|
-
switch (pos) {
|
|
543
|
-
case Position.Left:
|
|
544
|
-
return [x1 - calculateControlOffset(x1 - x2, c), y1];
|
|
545
|
-
case Position.Right:
|
|
546
|
-
return [x1 + calculateControlOffset(x2 - x1, c), y1];
|
|
547
|
-
case Position.Top:
|
|
548
|
-
return [x1, y1 - calculateControlOffset(y1 - y2, c)];
|
|
549
|
-
case Position.Bottom:
|
|
550
|
-
return [x1, y1 + calculateControlOffset(y2 - y1, c)];
|
|
551
|
-
}
|
|
552
|
-
};
|
|
553
|
-
/**
|
|
554
|
-
* Get a bezier path from source to target port
|
|
555
|
-
* @param params.sourceX - The x position of the source port
|
|
556
|
-
* @param params.sourceY - The y position of the source port
|
|
557
|
-
* @param params.sourcePosition - The position of the source port (default: Position.Bottom)
|
|
558
|
-
* @param params.targetX - The x position of the target port
|
|
559
|
-
* @param params.targetY - The y position of the target port
|
|
560
|
-
* @param params.targetPosition - The position of the target port (default: Position.Top)
|
|
561
|
-
* @param params.curvature - The curvature of the bezier edge
|
|
562
|
-
* @returns A path string you can use in an SVG, the labelX and labelY position (center of path) and offsetX, offsetY between source port and label
|
|
563
|
-
* @example
|
|
564
|
-
* const source = { x: 0, y: 20 };
|
|
565
|
-
const target = { x: 150, y: 100 };
|
|
566
|
-
|
|
567
|
-
const [path, labelX, labelY, offsetX, offsetY] = getBezierPath({
|
|
568
|
-
sourceX: source.x,
|
|
569
|
-
sourceY: source.y,
|
|
570
|
-
sourcePosition: Position.Right,
|
|
571
|
-
targetX: target.x,
|
|
572
|
-
targetY: target.y,
|
|
573
|
-
targetPosition: Position.Left,
|
|
574
|
-
});
|
|
575
|
-
*/
|
|
576
|
-
const getBezierPath = ({ sourceX, sourceY, sourcePosition = Position.Bottom, targetX, targetY, targetPosition = Position.Top, curvature = 0.25, }) => {
|
|
577
|
-
const [sourceControlX, sourceControlY] = getControlWithCurvature({
|
|
578
|
-
pos: sourcePosition,
|
|
579
|
-
x1: sourceX,
|
|
580
|
-
y1: sourceY,
|
|
581
|
-
x2: targetX,
|
|
582
|
-
y2: targetY,
|
|
583
|
-
c: curvature,
|
|
584
|
-
});
|
|
585
|
-
const [targetControlX, targetControlY] = getControlWithCurvature({
|
|
586
|
-
pos: targetPosition,
|
|
587
|
-
x1: targetX,
|
|
588
|
-
y1: targetY,
|
|
589
|
-
x2: sourceX,
|
|
590
|
-
y2: sourceY,
|
|
591
|
-
c: curvature,
|
|
592
|
-
});
|
|
593
|
-
const [labelX, labelY, offsetX, offsetY] = getBezierEdgeCenter({
|
|
594
|
-
sourceX,
|
|
595
|
-
sourceY,
|
|
596
|
-
targetX,
|
|
597
|
-
targetY,
|
|
598
|
-
sourceControlX,
|
|
599
|
-
sourceControlY,
|
|
600
|
-
targetControlX,
|
|
601
|
-
targetControlY,
|
|
602
|
-
});
|
|
603
|
-
return [
|
|
604
|
-
`M${sourceX},${sourceY} C${sourceControlX},${sourceControlY} ${targetControlX},${targetControlY} ${targetX},${targetY}`,
|
|
605
|
-
labelX,
|
|
606
|
-
labelY,
|
|
607
|
-
offsetX,
|
|
608
|
-
offsetY,
|
|
609
|
-
];
|
|
610
|
-
};
|
|
611
|
-
|
|
612
|
-
const getPorts = (node, portBounds, type, currentPort) => (portBounds[type] || []).reduce((res, h) => {
|
|
613
|
-
if (`${node.id}-${h.id}-${type}` !== currentPort) {
|
|
614
|
-
res.push({
|
|
615
|
-
portId: h.id || null,
|
|
616
|
-
portType: type,
|
|
617
|
-
nodeId: node.id,
|
|
618
|
-
x: (node.positionAbsolute?.x ?? 0) + h.x + h.width / 2,
|
|
619
|
-
y: (node.positionAbsolute?.y ?? 0) + h.y + h.height / 2,
|
|
620
|
-
});
|
|
621
|
-
}
|
|
622
|
-
return res;
|
|
623
|
-
}, []);
|
|
624
|
-
const getPortType = (PortDomNode) => {
|
|
625
|
-
if (PortDomNode?.classList.contains('target')) {
|
|
626
|
-
return 'target';
|
|
627
|
-
}
|
|
628
|
-
else if (PortDomNode?.classList.contains('source')) {
|
|
629
|
-
return 'source';
|
|
630
|
-
}
|
|
631
|
-
return null;
|
|
632
|
-
};
|
|
633
|
-
const getAllPort = ({ nodes, nodeId, portId, portType, }) => nodes.reduce((res, node) => {
|
|
634
|
-
if (node[internalsSymbol$1]) {
|
|
635
|
-
const { portBounds } = node[internalsSymbol$1];
|
|
636
|
-
let sourcePorts = [];
|
|
637
|
-
let targetPorts = [];
|
|
638
|
-
if (portBounds) {
|
|
639
|
-
sourcePorts = getPorts(node, portBounds, 'source', `${nodeId}-${portId}-${portType}`);
|
|
640
|
-
targetPorts = getPorts(node, portBounds, 'target', `${nodeId}-${portId}-${portType}`);
|
|
641
|
-
}
|
|
642
|
-
res.push(...sourcePorts, ...targetPorts);
|
|
643
|
-
}
|
|
644
|
-
return res;
|
|
645
|
-
}, []);
|
|
646
|
-
const getClosestPort = (pos, connectionRadius, ports) => {
|
|
647
|
-
let closestPort = null;
|
|
648
|
-
let minDistance = Infinity;
|
|
649
|
-
ports.forEach((port) => {
|
|
650
|
-
const distance = Math.sqrt(Math.pow(port.x - pos.x, 2) + Math.pow(port.y - pos.y, 2));
|
|
651
|
-
if (distance <= connectionRadius && distance < minDistance) {
|
|
652
|
-
minDistance = distance;
|
|
653
|
-
closestPort = port;
|
|
654
|
-
}
|
|
655
|
-
});
|
|
656
|
-
return closestPort;
|
|
657
|
-
};
|
|
658
|
-
const getConnection = (event, port, fromNodeId, fromPortId, fromType, doc) => {
|
|
659
|
-
const isTarget = fromType === 'target';
|
|
660
|
-
const result = {
|
|
661
|
-
isValid: false,
|
|
662
|
-
connection: null,
|
|
663
|
-
endPort: null,
|
|
664
|
-
};
|
|
665
|
-
const PortDomNode = doc.querySelector(`.react-diagram__port[data-id="${port?.nodeId}-${port?.portId}-${port?.portType}"]`);
|
|
666
|
-
const { x, y } = getEventPosition(event);
|
|
667
|
-
const ElementFromPoint = doc.elementFromPoint(x, y);
|
|
668
|
-
const Port = ElementFromPoint?.classList.contains('react-diagram__port')
|
|
669
|
-
? ElementFromPoint
|
|
670
|
-
: PortDomNode;
|
|
671
|
-
if (Port) {
|
|
672
|
-
const portType = getPortType(Port);
|
|
673
|
-
const toNodeId = Port.getAttribute('data-nodeid');
|
|
674
|
-
const toPortId = Port.getAttribute('data-portid');
|
|
675
|
-
const connection = {
|
|
676
|
-
source: isTarget ? toNodeId : fromNodeId,
|
|
677
|
-
target: isTarget ? fromNodeId : toNodeId,
|
|
678
|
-
sourcePort: isTarget ? port?.portId || null : fromPortId,
|
|
679
|
-
targetPort: isTarget ? fromPortId : port?.portId || null,
|
|
680
|
-
};
|
|
681
|
-
result.connection = connection;
|
|
682
|
-
const isValid = (isTarget && portType === 'source') ||
|
|
683
|
-
(!isTarget && portType === 'target');
|
|
684
|
-
if (isValid) {
|
|
685
|
-
result.isValid = true;
|
|
686
|
-
result.endPort = {
|
|
687
|
-
nodeId: toNodeId,
|
|
688
|
-
portId: toPortId,
|
|
689
|
-
portType,
|
|
690
|
-
};
|
|
691
|
-
}
|
|
692
|
-
}
|
|
693
|
-
return result;
|
|
694
|
-
};
|
|
695
|
-
|
|
696
|
-
let connectionStartPort = null;
|
|
697
|
-
const onPointerDown = ({ isAnchor = false, event, nodeId, portId, portType, domNode, autoPanOnConnect, connectionRadius, nodes, getTransform, cancelConnection, onConnectStart, onConnect, onConnectEnd, onEdgeUpdateEnd, panBy, updateConnection, }) => {
|
|
698
|
-
const doc = getHostForElement(event.target);
|
|
699
|
-
const containerBounds = domNode?.getBoundingClientRect();
|
|
700
|
-
const { x, y } = getEventPosition(event);
|
|
701
|
-
const clickedPort = doc?.elementFromPoint(x, y);
|
|
702
|
-
const clickedPortType = isAnchor ? portType : getPortType(clickedPort);
|
|
703
|
-
const allPort = getAllPort({
|
|
704
|
-
nodes,
|
|
705
|
-
nodeId,
|
|
706
|
-
portId,
|
|
707
|
-
portType,
|
|
708
|
-
});
|
|
709
|
-
let connectionPosition = getEventPosition(event, containerBounds);
|
|
710
|
-
let closestPort = null;
|
|
711
|
-
let isValid = false;
|
|
712
|
-
let connection = null;
|
|
713
|
-
let autoPanId = 0;
|
|
714
|
-
let autoPanStarted = false;
|
|
715
|
-
if (!containerBounds || !portType) {
|
|
716
|
-
return;
|
|
717
|
-
}
|
|
718
|
-
const autoPan = () => {
|
|
719
|
-
if (!autoPanOnConnect) {
|
|
720
|
-
return;
|
|
721
|
-
}
|
|
722
|
-
const [xMovement, yMovement] = calcAutoPanPosition(connectionPosition, containerBounds);
|
|
723
|
-
panBy({ x: xMovement, y: yMovement });
|
|
724
|
-
autoPanId = requestAnimationFrame(autoPan);
|
|
725
|
-
};
|
|
726
|
-
connectionStartPort = {
|
|
727
|
-
nodeId,
|
|
728
|
-
portId,
|
|
729
|
-
portType: clickedPortType,
|
|
730
|
-
};
|
|
731
|
-
updateConnection({
|
|
732
|
-
connectionPosition,
|
|
733
|
-
connectionStartPort,
|
|
734
|
-
connectionEndPort: null,
|
|
735
|
-
});
|
|
736
|
-
onConnectStart?.(event, { nodeId, portId, portType });
|
|
737
|
-
const onPointerMove = (event) => {
|
|
738
|
-
const transform = getTransform();
|
|
739
|
-
connectionPosition = getEventPosition(event, containerBounds);
|
|
740
|
-
closestPort = getClosestPort(pointToRendererPoint(connectionPosition, transform), connectionRadius, allPort);
|
|
741
|
-
if (!autoPanStarted) {
|
|
742
|
-
autoPan();
|
|
743
|
-
autoPanStarted = true;
|
|
744
|
-
}
|
|
745
|
-
const result = getConnection(event, closestPort, nodeId, portId, portType, doc);
|
|
746
|
-
isValid = result.isValid;
|
|
747
|
-
connection = result.connection;
|
|
748
|
-
updateConnection({
|
|
749
|
-
connectionPosition: closestPort && isValid
|
|
750
|
-
? rendererPointToPoint(closestPort, transform)
|
|
751
|
-
: connectionPosition,
|
|
752
|
-
connectionStartPort,
|
|
753
|
-
connectionEndPort: result.endPort,
|
|
754
|
-
});
|
|
755
|
-
};
|
|
756
|
-
const onPointerUp = (event) => {
|
|
757
|
-
if (isValid && connection)
|
|
758
|
-
onConnect?.(connection);
|
|
759
|
-
onConnectEnd?.(event);
|
|
760
|
-
if (portType) {
|
|
761
|
-
onEdgeUpdateEnd?.(event);
|
|
762
|
-
}
|
|
763
|
-
cancelConnection();
|
|
764
|
-
cancelAnimationFrame(autoPanId);
|
|
765
|
-
isValid = false;
|
|
766
|
-
connection = null;
|
|
767
|
-
autoPanStarted = false;
|
|
768
|
-
doc.removeEventListener('mousemove', onPointerMove);
|
|
769
|
-
doc.removeEventListener('mouseup', onPointerUp);
|
|
770
|
-
doc.removeEventListener('touchmove', onPointerMove);
|
|
771
|
-
doc.removeEventListener('touchend', onPointerUp);
|
|
772
|
-
};
|
|
773
|
-
doc.addEventListener('mousemove', onPointerMove);
|
|
774
|
-
doc.addEventListener('mouseup', onPointerUp);
|
|
775
|
-
doc.addEventListener('touchmove', onPointerMove);
|
|
776
|
-
doc.addEventListener('touchend', onPointerUp);
|
|
777
|
-
};
|
|
778
|
-
const CosmosPort = {
|
|
779
|
-
onPointerDown,
|
|
780
|
-
};
|
|
781
|
-
|
|
782
|
-
const isParentSelected = (node, nodeInternals) => {
|
|
783
|
-
if (!node.parentNode) {
|
|
784
|
-
return false;
|
|
785
|
-
}
|
|
786
|
-
const parentNode = nodeInternals.get(node.parentNode);
|
|
787
|
-
if (!parentNode) {
|
|
788
|
-
return false;
|
|
789
|
-
}
|
|
790
|
-
if (parentNode.selected) {
|
|
791
|
-
return true;
|
|
792
|
-
}
|
|
793
|
-
return isParentSelected(parentNode, nodeInternals);
|
|
794
|
-
};
|
|
795
|
-
const hasSelector = (target, selector, domNode) => {
|
|
796
|
-
let current = target;
|
|
797
|
-
do {
|
|
798
|
-
if (current?.matches(selector))
|
|
799
|
-
return true;
|
|
800
|
-
if (current === domNode)
|
|
801
|
-
return false;
|
|
802
|
-
current = current.parentElement;
|
|
803
|
-
} while (current);
|
|
804
|
-
return false;
|
|
805
|
-
};
|
|
806
|
-
const hasChangedPosition = (beforePositions, currentPosition) => beforePositions.x !== currentPosition.x ||
|
|
807
|
-
beforePositions.y !== currentPosition.y;
|
|
808
|
-
const getDragItems = (nodeInternals, nodesDraggable, mousePosition, nodeId) => {
|
|
809
|
-
const filteredNode = Array.from(nodeInternals.values()).filter((n) => {
|
|
810
|
-
const hasSize = n.width && n.height;
|
|
811
|
-
const isSelected = n.selected || n.id === nodeId;
|
|
812
|
-
const hasNoParent = !n.parentNode || !isParentSelected(n, nodeInternals);
|
|
813
|
-
const isDraggable = n.draggable || (nodesDraggable && typeof n.draggable === 'undefined');
|
|
814
|
-
return hasSize && isSelected && hasNoParent && isDraggable;
|
|
815
|
-
});
|
|
816
|
-
return filteredNode.map((n) => ({
|
|
817
|
-
id: n.id,
|
|
818
|
-
position: n.position || { x: 0, y: 0 },
|
|
819
|
-
positionAbsolute: n.positionAbsolute || { x: 0, y: 0 },
|
|
820
|
-
distance: {
|
|
821
|
-
x: mousePosition.x - (n.positionAbsolute?.x ?? 0),
|
|
822
|
-
y: mousePosition.y - (n.positionAbsolute?.y ?? 0),
|
|
823
|
-
},
|
|
824
|
-
extent: n.extent,
|
|
825
|
-
parentNode: n.parentNode,
|
|
826
|
-
width: n.width || 0,
|
|
827
|
-
height: n.height || 0,
|
|
828
|
-
}));
|
|
829
|
-
};
|
|
830
|
-
const getEventHandlerParams = ({ nodeId, dragItems, nodeInternals, }) => {
|
|
831
|
-
const extentedDragItems = dragItems.map((n) => {
|
|
832
|
-
const node = nodeInternals.get(n.id);
|
|
833
|
-
return {
|
|
834
|
-
...node,
|
|
835
|
-
position: n.position,
|
|
836
|
-
positionAbsolute: n.positionAbsolute,
|
|
837
|
-
};
|
|
838
|
-
});
|
|
839
|
-
return [
|
|
840
|
-
nodeId
|
|
841
|
-
? extentedDragItems.find((n) => n.id === nodeId)
|
|
842
|
-
: extentedDragItems[0],
|
|
843
|
-
extentedDragItems,
|
|
844
|
-
];
|
|
845
|
-
};
|
|
846
|
-
|
|
847
|
-
const isDragItem = (node) => 'distance' in node;
|
|
848
|
-
const CosmosDrag = ({ getStore, onNodeMouseDown, onDragStart, onDrag, onDragEnd, }) => {
|
|
849
|
-
let dragItems = [];
|
|
850
|
-
let containerBounds = null;
|
|
851
|
-
let mousePosition = { x: 0, y: 0 };
|
|
852
|
-
let lastPosition = { x: 0, y: 0 };
|
|
853
|
-
let dragEvent = null;
|
|
854
|
-
let autoPanStarted = false;
|
|
855
|
-
let autoPanId = 0;
|
|
856
|
-
let d3Selection = null;
|
|
857
|
-
const update = ({ domNode, nodeId, noDragClassName }) => {
|
|
858
|
-
const updateNodePosition = (pointerPositions, dragEnd = false) => (dragItem) => {
|
|
859
|
-
if (!isDragItem(dragItem))
|
|
860
|
-
return;
|
|
861
|
-
const { nodeInternals, nodeExtent, nodeOrigin, smoothStep, gridStep, } = getStore();
|
|
862
|
-
const { distance, width, height } = dragItem;
|
|
863
|
-
const { x, y, getStepPosition } = pointerPositions;
|
|
864
|
-
let nextPosition = {
|
|
865
|
-
x: x - distance.x,
|
|
866
|
-
y: y - distance.y,
|
|
867
|
-
};
|
|
868
|
-
if (gridStep && getStepPosition) {
|
|
869
|
-
const nodeSize = { width, height };
|
|
870
|
-
const stepPosition = getStepPosition({
|
|
871
|
-
position: nextPosition,
|
|
872
|
-
nodeSize,
|
|
873
|
-
});
|
|
874
|
-
if (!smoothStep || (smoothStep && dragEnd)) {
|
|
875
|
-
nextPosition = stepPosition;
|
|
876
|
-
}
|
|
877
|
-
}
|
|
878
|
-
const updatedPosition = calcNextPosition(dragItem, nextPosition, nodeInternals, nodeExtent, nodeOrigin);
|
|
879
|
-
const hasChange = hasChangedPosition(dragItem.position, updatedPosition.position);
|
|
880
|
-
if (!hasChange)
|
|
881
|
-
return;
|
|
882
|
-
dragItem.position = updatedPosition.position;
|
|
883
|
-
dragItem.positionAbsolute = updatedPosition.positionAbsolute;
|
|
884
|
-
};
|
|
885
|
-
d3Selection = select(domNode);
|
|
886
|
-
const updateNodes = (pointerPosition) => {
|
|
887
|
-
const { nodeInternals, updateNodesPosition } = getStore();
|
|
888
|
-
const { x, y } = pointerPosition;
|
|
889
|
-
lastPosition = { x, y };
|
|
890
|
-
updateNodesPosition(dragItems, true, updateNodePosition(pointerPosition));
|
|
891
|
-
if (onDrag && dragEvent) {
|
|
892
|
-
const [currentNode, nodes] = getEventHandlerParams({
|
|
893
|
-
nodeId,
|
|
894
|
-
dragItems: dragItems,
|
|
895
|
-
nodeInternals,
|
|
896
|
-
});
|
|
897
|
-
onDrag(dragEvent, dragItems, currentNode, nodes);
|
|
898
|
-
}
|
|
899
|
-
};
|
|
900
|
-
const autoPan = () => {
|
|
901
|
-
if (!containerBounds) {
|
|
902
|
-
return;
|
|
903
|
-
}
|
|
904
|
-
const [xMovement, yMovement] = calcAutoPanPosition(mousePosition, containerBounds);
|
|
905
|
-
if (xMovement !== 0 || yMovement !== 0) {
|
|
906
|
-
const { transform, panBy } = getStore();
|
|
907
|
-
lastPosition.x -= xMovement / transform[2];
|
|
908
|
-
lastPosition.y -= yMovement / transform[2];
|
|
909
|
-
updateNodes(lastPosition);
|
|
910
|
-
panBy({ x: xMovement, y: yMovement });
|
|
911
|
-
}
|
|
912
|
-
autoPanId = requestAnimationFrame(autoPan);
|
|
913
|
-
};
|
|
914
|
-
const startDrag = (event) => {
|
|
915
|
-
const { nodeInternals, nodesDraggable, domNode, transform, gridStep, centerStep, } = getStore();
|
|
916
|
-
if (nodeId) {
|
|
917
|
-
onNodeMouseDown?.(nodeId);
|
|
918
|
-
}
|
|
919
|
-
const pointerPosition = getPointerPosition(event.sourceEvent, {
|
|
920
|
-
transform,
|
|
921
|
-
gridStep,
|
|
922
|
-
centerStep,
|
|
923
|
-
});
|
|
924
|
-
dragItems = getDragItems(nodeInternals, nodesDraggable, pointerPosition, nodeId);
|
|
925
|
-
if (onDragStart && dragItems) {
|
|
926
|
-
const [currentNode, nodes] = getEventHandlerParams({
|
|
927
|
-
nodeId,
|
|
928
|
-
dragItems: dragItems,
|
|
929
|
-
nodeInternals,
|
|
930
|
-
});
|
|
931
|
-
onDragStart?.(event.sourceEvent, dragItems, currentNode, nodes);
|
|
932
|
-
}
|
|
933
|
-
containerBounds = domNode?.getBoundingClientRect() || null;
|
|
934
|
-
mousePosition = getEventPosition(event.sourceEvent, containerBounds);
|
|
935
|
-
};
|
|
936
|
-
const dragHandle = drag()
|
|
937
|
-
.on('start', (event) => {
|
|
938
|
-
startDrag(event);
|
|
939
|
-
})
|
|
940
|
-
.on('drag', (event) => {
|
|
941
|
-
const { transform, gridStep, centerStep, autoPanOnNodeDrag, updateNodesIntersection, } = getStore();
|
|
942
|
-
const pointerPosition = getPointerPosition(event.sourceEvent, {
|
|
943
|
-
transform,
|
|
944
|
-
gridStep,
|
|
945
|
-
centerStep,
|
|
946
|
-
});
|
|
947
|
-
if (!autoPanStarted && autoPanOnNodeDrag) {
|
|
948
|
-
autoPanStarted = true;
|
|
949
|
-
autoPan();
|
|
950
|
-
}
|
|
951
|
-
const isChanged = hasChangedPosition(lastPosition, pointerPosition.getStepPosition());
|
|
952
|
-
if (isChanged && dragItems) {
|
|
953
|
-
dragEvent = event.sourceEvent;
|
|
954
|
-
mousePosition = getEventPosition(event.sourceEvent, containerBounds);
|
|
955
|
-
updateNodes(pointerPosition);
|
|
956
|
-
updateNodesIntersection();
|
|
957
|
-
}
|
|
958
|
-
})
|
|
959
|
-
.on('end', (event) => {
|
|
960
|
-
autoPanStarted = false;
|
|
961
|
-
cancelAnimationFrame(autoPanId);
|
|
962
|
-
if (dragItems) {
|
|
963
|
-
const { nodeInternals, transform, gridStep, centerStep, smoothStep, updateNodesPosition, updateNodesIntersection, } = getStore();
|
|
964
|
-
const isSmoothStep = !!gridStep && smoothStep;
|
|
965
|
-
if (isSmoothStep) {
|
|
966
|
-
const pointerPosition = getPointerPosition(event.sourceEvent, {
|
|
967
|
-
transform,
|
|
968
|
-
gridStep,
|
|
969
|
-
centerStep,
|
|
970
|
-
});
|
|
971
|
-
updateNodesPosition(dragItems, false, updateNodePosition(pointerPosition, true));
|
|
972
|
-
updateNodesIntersection();
|
|
973
|
-
}
|
|
974
|
-
else {
|
|
975
|
-
updateNodesPosition(dragItems, false);
|
|
976
|
-
}
|
|
977
|
-
if (onDragEnd) {
|
|
978
|
-
const [currentNode, nodes] = getEventHandlerParams({
|
|
979
|
-
nodeId,
|
|
980
|
-
dragItems: dragItems,
|
|
981
|
-
nodeInternals,
|
|
982
|
-
});
|
|
983
|
-
onDragEnd(event.sourceEvent, dragItems, currentNode, nodes);
|
|
984
|
-
}
|
|
985
|
-
}
|
|
986
|
-
})
|
|
987
|
-
.filter((event) => {
|
|
988
|
-
const target = event.target;
|
|
989
|
-
if (!domNode)
|
|
990
|
-
return false;
|
|
991
|
-
const isDraggable = !event.button &&
|
|
992
|
-
(!noDragClassName ||
|
|
993
|
-
!hasSelector(target, `.${noDragClassName}`, domNode));
|
|
994
|
-
return isDraggable;
|
|
995
|
-
});
|
|
996
|
-
d3Selection.call(dragHandle);
|
|
997
|
-
};
|
|
998
|
-
const destroy = () => {
|
|
999
|
-
d3Selection?.on('.drag', null);
|
|
1000
|
-
};
|
|
1001
|
-
return {
|
|
1002
|
-
update,
|
|
1003
|
-
destroy,
|
|
1004
|
-
};
|
|
1005
|
-
};
|
|
1006
|
-
|
|
1007
|
-
const transformToViewport = (transform) => {
|
|
1008
|
-
const { x, y, k } = transform;
|
|
1009
|
-
return {
|
|
1010
|
-
x,
|
|
1011
|
-
y,
|
|
1012
|
-
zoom: k,
|
|
1013
|
-
};
|
|
1014
|
-
};
|
|
1015
|
-
const viewportToTransform = ({ x, y, zoom }) => zoomIdentity.translate(x, y).scale(zoom);
|
|
1016
|
-
const isWrappedWithClass = (event, className) => event.target.closest(`.${className}`);
|
|
1017
|
-
const isViewChanged = (prevViewport, eventViewport) => {
|
|
1018
|
-
const { x: prevX, y: prevY, zoom: prevZoom } = prevViewport;
|
|
1019
|
-
const { x, y, k } = eventViewport;
|
|
1020
|
-
return prevX !== x || prevY !== y || prevZoom !== k;
|
|
1021
|
-
};
|
|
1022
|
-
const getD3Transition = (selection, duration = 0) => typeof duration === 'number' && duration > 0
|
|
1023
|
-
? selection.transition().duration(duration)
|
|
1024
|
-
: selection;
|
|
1025
|
-
|
|
1026
|
-
const createPanZoomStartHandler = ({ zoomPanValues, onPanningChange, onPanZoomStart, }) => {
|
|
1027
|
-
return (event) => {
|
|
1028
|
-
if (event.sourceEvent?.internal) {
|
|
1029
|
-
return;
|
|
1030
|
-
}
|
|
1031
|
-
const viewport = transformToViewport(event.transform);
|
|
1032
|
-
// we need to remember it here, because it's always 0 in the "zoom" event
|
|
1033
|
-
zoomPanValues.mouseButton = event.sourceEvent?.button || 0;
|
|
1034
|
-
zoomPanValues.isZoomingOrPanning = true;
|
|
1035
|
-
zoomPanValues.prevViewport = viewport;
|
|
1036
|
-
if (event.sourceEvent?.type === 'mousedown') {
|
|
1037
|
-
onPanningChange(true);
|
|
1038
|
-
}
|
|
1039
|
-
if (onPanZoomStart) {
|
|
1040
|
-
onPanZoomStart?.(event.sourceEvent, viewport);
|
|
1041
|
-
}
|
|
1042
|
-
};
|
|
1043
|
-
};
|
|
1044
|
-
const createPanZoomHandler = ({ onPanZoom, onTransformChange, }) => {
|
|
1045
|
-
return (event) => {
|
|
1046
|
-
if (!event.sourceEvent?.sync) {
|
|
1047
|
-
onTransformChange([
|
|
1048
|
-
event.transform.x,
|
|
1049
|
-
event.transform.y,
|
|
1050
|
-
event.transform.k,
|
|
1051
|
-
]);
|
|
1052
|
-
}
|
|
1053
|
-
if (onPanZoom && !event.sourceEvent?.internal) {
|
|
1054
|
-
onPanZoom?.(event.sourceEvent, transformToViewport(event.transform));
|
|
1055
|
-
}
|
|
1056
|
-
};
|
|
1057
|
-
};
|
|
1058
|
-
const createPanZoomEndHandler = ({ zoomPanValues, onPanningChange, onPanZoomEnd, }) => {
|
|
1059
|
-
return (event) => {
|
|
1060
|
-
if (event.sourceEvent?.internal) {
|
|
1061
|
-
return;
|
|
1062
|
-
}
|
|
1063
|
-
zoomPanValues.isZoomingOrPanning = false;
|
|
1064
|
-
onPanningChange(false);
|
|
1065
|
-
if (onPanZoomEnd &&
|
|
1066
|
-
isViewChanged(zoomPanValues.prevViewport, event.transform)) {
|
|
1067
|
-
const viewport = transformToViewport(event.transform);
|
|
1068
|
-
zoomPanValues.prevViewport = viewport;
|
|
1069
|
-
clearTimeout(zoomPanValues.timerId);
|
|
1070
|
-
zoomPanValues.timerId = setTimeout(() => {
|
|
1071
|
-
onPanZoomEnd?.(event.sourceEvent, viewport);
|
|
1072
|
-
}, 0);
|
|
1073
|
-
}
|
|
1074
|
-
};
|
|
1075
|
-
};
|
|
1076
|
-
function createZoomOnScrollHandler({ d3ZoomHandler, }) {
|
|
1077
|
-
return function (event, d) {
|
|
1078
|
-
event.preventDefault();
|
|
1079
|
-
d3ZoomHandler.call(this, event, d);
|
|
1080
|
-
};
|
|
1081
|
-
}
|
|
1082
|
-
|
|
1083
|
-
const CosmosPanZoom = ({ domNode, panning,
|
|
1084
|
-
// selection,
|
|
1085
|
-
minZoom, maxZoom, viewport, translateExtent,
|
|
1086
|
-
// children,
|
|
1087
|
-
onTransformChange, onPanningChange, onPanZoom, onPanZoomStart, onPanZoomEnd, }) => {
|
|
1088
|
-
const zoomPanValues = {
|
|
1089
|
-
isZoomingOrPanning: false,
|
|
1090
|
-
timerId: undefined,
|
|
1091
|
-
prevViewport: { x: 0, y: 0, zoom: 0 },
|
|
1092
|
-
// usedRightMouseButton: false,
|
|
1093
|
-
mouseButton: 0,
|
|
1094
|
-
// panScrollTimeout: undefined,
|
|
1095
|
-
isPanScrolling: false,
|
|
1096
|
-
};
|
|
1097
|
-
const bbox = domNode.getBoundingClientRect();
|
|
1098
|
-
const d3ZoomInstance = zoom()
|
|
1099
|
-
.scaleExtent([minZoom, maxZoom])
|
|
1100
|
-
.translateExtent(translateExtent);
|
|
1101
|
-
const d3Selection = select(domNode).call(d3ZoomInstance);
|
|
1102
|
-
const d3ZoomHandler = d3Selection.on('wheel.zoom');
|
|
1103
|
-
const setTransform = (transform, options) => {
|
|
1104
|
-
if (d3Selection) {
|
|
1105
|
-
d3ZoomInstance?.transform(getD3Transition(d3Selection, options?.duration), transform);
|
|
1106
|
-
}
|
|
1107
|
-
};
|
|
1108
|
-
const setViewportConstrained = (viewport, extent, translateExtent) => {
|
|
1109
|
-
const updatedTransform = viewportToTransform(viewport);
|
|
1110
|
-
const constrainedTransform = d3ZoomInstance.constrain()(updatedTransform, extent, translateExtent);
|
|
1111
|
-
if (constrainedTransform) {
|
|
1112
|
-
setTransform(constrainedTransform);
|
|
1113
|
-
}
|
|
1114
|
-
return constrainedTransform;
|
|
1115
|
-
};
|
|
1116
|
-
setViewportConstrained({
|
|
1117
|
-
x: viewport.x,
|
|
1118
|
-
y: viewport.y,
|
|
1119
|
-
zoom: clamp(viewport.zoom, minZoom, maxZoom),
|
|
1120
|
-
}, [
|
|
1121
|
-
[0, 0],
|
|
1122
|
-
[bbox.width, bbox.height],
|
|
1123
|
-
], translateExtent);
|
|
1124
|
-
const destroy = () => {
|
|
1125
|
-
d3ZoomInstance.on('zoom', null);
|
|
1126
|
-
// d3ZoomInstance.on('start', null);
|
|
1127
|
-
// d3ZoomInstance.on('end', null);
|
|
1128
|
-
// d3Selection.on('wheel.zoom', null);
|
|
1129
|
-
};
|
|
1130
|
-
const update = ({ noPanClassName, selection }) => {
|
|
1131
|
-
if (selection && !zoomPanValues.isZoomingOrPanning) {
|
|
1132
|
-
destroy();
|
|
1133
|
-
}
|
|
1134
|
-
const filter = (event) => {
|
|
1135
|
-
if (selection) {
|
|
1136
|
-
return false;
|
|
1137
|
-
}
|
|
1138
|
-
if (isWrappedWithClass(event, noPanClassName) &&
|
|
1139
|
-
event.type !== 'wheel') {
|
|
1140
|
-
return false;
|
|
1141
|
-
}
|
|
1142
|
-
if (!panning)
|
|
1143
|
-
return false;
|
|
1144
|
-
const buttonAllowed = !event.button || event.button <= 1;
|
|
1145
|
-
if (!buttonAllowed)
|
|
1146
|
-
return false;
|
|
1147
|
-
return true;
|
|
1148
|
-
};
|
|
1149
|
-
const wheelZoomHandler = createZoomOnScrollHandler({ d3ZoomHandler });
|
|
1150
|
-
d3Selection.on('wheel.zoom', wheelZoomHandler, { passive: false });
|
|
1151
|
-
if (!selection) {
|
|
1152
|
-
const panZoomStartHandler = createPanZoomStartHandler({
|
|
1153
|
-
zoomPanValues,
|
|
1154
|
-
onPanningChange,
|
|
1155
|
-
onPanZoomStart,
|
|
1156
|
-
});
|
|
1157
|
-
const panZoomHandler = createPanZoomHandler({
|
|
1158
|
-
onPanZoom,
|
|
1159
|
-
onTransformChange,
|
|
1160
|
-
});
|
|
1161
|
-
const panZoomEndHandler = createPanZoomEndHandler({
|
|
1162
|
-
zoomPanValues,
|
|
1163
|
-
onPanningChange,
|
|
1164
|
-
onPanZoomEnd,
|
|
1165
|
-
});
|
|
1166
|
-
d3ZoomInstance.on('start', panZoomStartHandler);
|
|
1167
|
-
d3ZoomInstance.on('zoom', panZoomHandler);
|
|
1168
|
-
d3ZoomInstance.on('end', panZoomEndHandler);
|
|
1169
|
-
}
|
|
1170
|
-
d3ZoomInstance.filter(filter);
|
|
1171
|
-
};
|
|
1172
|
-
const getViewport = () => {
|
|
1173
|
-
const transform = d3Selection
|
|
1174
|
-
? zoomTransform(d3Selection.node())
|
|
1175
|
-
: { x: 0, y: 0, k: 1 };
|
|
1176
|
-
return { x: transform.x, y: transform.y, zoom: transform.k };
|
|
1177
|
-
};
|
|
1178
|
-
return {
|
|
1179
|
-
update,
|
|
1180
|
-
destroy,
|
|
1181
|
-
getViewport,
|
|
1182
|
-
setViewportConstrained,
|
|
1183
|
-
};
|
|
1184
|
-
};
|
|
9
|
+
import { zoomIdentity } from 'd3-zoom';
|
|
1185
10
|
|
|
1186
11
|
const StoreContext = createContext(null);
|
|
1187
12
|
const Provider$1 = StoreContext.Provider;
|
|
@@ -2709,7 +1534,7 @@ const initialState = {
|
|
|
2709
1534
|
onError: devWarn,
|
|
2710
1535
|
};
|
|
2711
1536
|
|
|
2712
|
-
const
|
|
1537
|
+
const createRCDStore = () => createStore((set, get) => ({
|
|
2713
1538
|
...initialState,
|
|
2714
1539
|
setNodes: (nodes) => {
|
|
2715
1540
|
const { nodeInternals, nodeOrigin, elevateNodesOnSelect } = get();
|
|
@@ -2907,7 +1732,7 @@ const createRFStore = () => createStore((set, get) => ({
|
|
|
2907
1732
|
const ReactDiagramProvider = ({ children }) => {
|
|
2908
1733
|
const storeRef = useRef(null);
|
|
2909
1734
|
if (!storeRef.current) {
|
|
2910
|
-
storeRef.current =
|
|
1735
|
+
storeRef.current = createRCDStore();
|
|
2911
1736
|
}
|
|
2912
1737
|
return jsx(Provider$1, { value: storeRef.current, children: children });
|
|
2913
1738
|
};
|
|
@@ -2983,4 +1808,4 @@ function Background({ gap, lineWidth = 1, color = '#000000', }) {
|
|
|
2983
1808
|
Background.displayName = 'Background';
|
|
2984
1809
|
var index = memo(Background);
|
|
2985
1810
|
|
|
2986
|
-
export { index as Background, BaseEdge, BezierEdge,
|
|
1811
|
+
export { index as Background, BaseEdge, BezierEdge, Port$1 as Port, ReactDiagramProvider, StepEdge, ReactDiagram as default, internalsSymbol, useEdgesState, useNodesState };
|