diff --git a/packages/core/src/hooks/useDrag/utils.ts b/packages/core/src/hooks/useDrag/utils.ts index 1e6d7693..6dcbe833 100644 --- a/packages/core/src/hooks/useDrag/utils.ts +++ b/packages/core/src/hooks/useDrag/utils.ts @@ -89,14 +89,16 @@ export function calcNextPosition( if (node.parentNode && node.width && node.height) { const parent = nodeInternals.get(node.parentNode); const parentOrigin = parent?.origin || nodeOrigin; + const currNodeOrigin = node.origin || nodeOrigin; + const { x: parentX, y: parentY } = getNodePositionWithOrigin(parent, parentOrigin).positionAbsolute; currentExtent = parent && isNumeric(parentX) && isNumeric(parentY) && isNumeric(parent.width) && isNumeric(parent.height) ? [ - [parentX + node.width * parentOrigin[0], parentY + node.height * parentOrigin[1]], + [parentX + node.width * currNodeOrigin[0], parentY + node.height * currNodeOrigin[1]], [ - parentX + parent.width - node.width + node.width * parentOrigin[0], - parentY + parent.height - node.height + node.height * parentOrigin[1], + parentX + parent.width - node.width + node.width * currNodeOrigin[0], + parentY + parent.height - node.height + node.height * currNodeOrigin[1], ], ] : currentExtent; diff --git a/packages/svelte/src/example-components/Header/Header.svelte b/packages/svelte/src/example-components/Header/Header.svelte index e6ada667..901aa1ed 100644 --- a/packages/svelte/src/example-components/Header/Header.svelte +++ b/packages/svelte/src/example-components/Header/Header.svelte @@ -5,6 +5,7 @@ 'drag-n-drop', 'overview', 'stress', + 'subflows', 'usesvelteflow', 'validation' ]; diff --git a/packages/svelte/src/lib/actions/drag/index.ts b/packages/svelte/src/lib/actions/drag/index.ts index c96777c2..85155753 100644 --- a/packages/svelte/src/lib/actions/drag/index.ts +++ b/packages/svelte/src/lib/actions/drag/index.ts @@ -1,10 +1,9 @@ -import { get, type Writable } from 'svelte/store'; +import { get } from 'svelte/store'; import { drag as d3Drag, type D3DragEvent, type SubjectPosition } from 'd3-drag'; import { select } from 'd3-selection'; -import type { XYPosition, CoordinateExtent, Transform } from '@reactflow/system'; +import type { XYPosition, CoordinateExtent } from '@reactflow/system'; import { getDragItems, hasSelector, calcNextPosition } from './utils'; -import type { Node } from '$lib/types'; import type { SvelteFlowStore } from '$lib/store/types'; export type UseDragData = { dx: number; dy: number }; diff --git a/packages/svelte/src/lib/actions/drag/utils.ts b/packages/svelte/src/lib/actions/drag/utils.ts index c7a78848..c470fb71 100644 --- a/packages/svelte/src/lib/actions/drag/utils.ts +++ b/packages/svelte/src/lib/actions/drag/utils.ts @@ -1,5 +1,11 @@ -import type { CoordinateExtent, NodeDragItem, NodeOrigin, XYPosition } from '@reactflow/system'; -import { clampPosition, isNumeric } from '@reactflow/utils'; +import { + errorMessages, + type CoordinateExtent, + type NodeDragItem, + type NodeOrigin, + type XYPosition +} from '@reactflow/system'; +import { clampPosition, devWarn, getNodePositionWithOrigin, isNumeric } from '@reactflow/utils'; import type { Node } from '$lib/types'; @@ -65,16 +71,28 @@ export function calcNextPosition( node: NodeDragItem | Node, nextPosition: XYPosition, nodes: Node[], - nodeExtent?: CoordinateExtent, - nodeOrigin: NodeOrigin = [0, 0] + nodeExtent?: CoordinateExtent ): { position: XYPosition; positionAbsolute: XYPosition } { let currentExtent = node.extent || nodeExtent; if (node.extent === 'parent') { if (node.parentNode && node.width && node.height) { - const parent = nodes.find((n) => n.id === node.parentNode)!; - const parentOrigin = parent.origin || nodeOrigin; - const { x: parentX, y: parentY } = parent.positionAbsolute!; + const parent = nodes.find((n) => n.id === node.parentNode); + const parentOrigin = parent?.origin || [0, 0]; + const nodeOrigin = node.origin || [0, 0]; + const { x: parentX, y: parentY } = getNodePositionWithOrigin( + parent, + parentOrigin + ).positionAbsolute; + console.log({ + parentX, + parentY, + parentW: parent?.width, + parentH: parent?.height, + nodeW: node.width, + nodeH: node.height, + parentOrigin: parentOrigin[0] + }); currentExtent = parent && isNumeric(parentX) && @@ -82,19 +100,23 @@ export function calcNextPosition( isNumeric(parent.width) && isNumeric(parent.height) ? [ - [parentX + node.width * parentOrigin[0], parentY + node.height * parentOrigin[1]], + [parentX + node.width * nodeOrigin[0], parentY + node.height * nodeOrigin[1]], [ - parentX + parent.width! - node.width + node.width * parentOrigin[0], - parentY + parent.height! - node.height + node.height * parentOrigin[1] + parentX + parent.width - node.width + node.width * nodeOrigin[0], + parentY + parent.height - node.height + node.height * nodeOrigin[1] ] ] : currentExtent; } else { + devWarn('005', errorMessages['005']()); currentExtent = nodeExtent; } } else if (node.extent && node.parentNode) { - const parent = nodes.find((n) => n.id === node.parentNode)!; - const { x: parentX, y: parentY } = parent.positionAbsolute!; + const parent = nodes.find((n) => n.id === node.parentNode); + const { x: parentX, y: parentY } = getNodePositionWithOrigin( + parent, + parent?.origin || [0, 0] + ).positionAbsolute; currentExtent = [ [node.extent[0][0] + parentX, node.extent[0][1] + parentY], [node.extent[1][0] + parentX, node.extent[1][1] + parentY] @@ -104,8 +126,8 @@ export function calcNextPosition( let parentPosition = { x: 0, y: 0 }; if (node.parentNode) { - const parent = nodes.find((n) => n.id === node.parentNode)!; - parentPosition = parent.positionAbsolute!; + const parent = nodes.find((n) => n.id === node.parentNode); + parentPosition = getNodePositionWithOrigin(parent, parent?.origin || [0, 0]).positionAbsolute; } const positionAbsolute = currentExtent diff --git a/packages/svelte/src/lib/components/NodeWrapper/NodeWrapper.svelte b/packages/svelte/src/lib/components/NodeWrapper/NodeWrapper.svelte index b9671cb0..d05be824 100644 --- a/packages/svelte/src/lib/components/NodeWrapper/NodeWrapper.svelte +++ b/packages/svelte/src/lib/components/NodeWrapper/NodeWrapper.svelte @@ -22,11 +22,11 @@ export let width: NodeWrapperProps['width'] = undefined; export let height: NodeWrapperProps['height'] = undefined; export let type: NodeWrapperProps['type'] = 'default'; + export let isParent: NodeWrapperProps['isParent'] = false; export let positionAbsolute: NodeWrapperProps['positionAbsolute'] = undefined; export let positionOrigin: NodeWrapperProps['positionOrigin'] = undefined; export let sourcePosition: NodeWrapperProps['sourcePosition'] = undefined; export let targetPosition: NodeWrapperProps['targetPosition'] = undefined; - let className: string = ''; export { className as class }; @@ -77,12 +77,13 @@ use:drag={{ nodeId: id, nodes, snapGrid, transform, updateNodePositions }} bind:this={nodeRef} data-id={id} - class={cc(['svelte-flow__node', `svelte-flow__node-${type}`, className])} + class={cc(['svelte-flow__node', `svelte-flow__node-${type || 'default'}`, className])} class:initializing={!width && !height} class:dragging class:selected class:draggable class:connectable + class:parent={isParent} style:transform={`translate(${positionOrigin?.x ?? 0}px, ${positionOrigin?.y ?? 0}px)`} {style} on:click={onSelectNodeHandler} diff --git a/packages/svelte/src/lib/components/NodeWrapper/types.ts b/packages/svelte/src/lib/components/NodeWrapper/types.ts index 564aaa41..acd26836 100644 --- a/packages/svelte/src/lib/components/NodeWrapper/types.ts +++ b/packages/svelte/src/lib/components/NodeWrapper/types.ts @@ -21,4 +21,5 @@ export type NodeWrapperProps = Pick< positionOrigin?: XYPosition; 'on:nodeclick'?: (event: MouseEvent) => void; resizeObserver?: ResizeObserver | null; + isParent?: boolean; }; diff --git a/packages/svelte/src/lib/container/NodeRenderer/NodeRenderer.svelte b/packages/svelte/src/lib/container/NodeRenderer/NodeRenderer.svelte index 6b99962a..270247b8 100644 --- a/packages/svelte/src/lib/container/NodeRenderer/NodeRenderer.svelte +++ b/packages/svelte/src/lib/container/NodeRenderer/NodeRenderer.svelte @@ -1,5 +1,6 @@ + + + + + + + + + + diff --git a/packages/svelte/src/routes/subflows/DebugNode/DebugNode.svelte b/packages/svelte/src/routes/subflows/DebugNode/DebugNode.svelte new file mode 100644 index 00000000..1f208219 --- /dev/null +++ b/packages/svelte/src/routes/subflows/DebugNode/DebugNode.svelte @@ -0,0 +1,23 @@ + + + +
{id}
+
+ x:{Math.round(xPos || 0)} y:{Math.round(yPos || 0)} z:{zIndex} +
+ + + + diff --git a/packages/svelte/src/routes/subflows/DebugNode/index.ts b/packages/svelte/src/routes/subflows/DebugNode/index.ts new file mode 100644 index 00000000..124af6ca --- /dev/null +++ b/packages/svelte/src/routes/subflows/DebugNode/index.ts @@ -0,0 +1 @@ +export { default as DebugNode } from './DebugNode.svelte'; diff --git a/packages/system/src/types/nodes.ts b/packages/system/src/types/nodes.ts index 8cb6d803..ce096014 100644 --- a/packages/system/src/types/nodes.ts +++ b/packages/system/src/types/nodes.ts @@ -80,6 +80,7 @@ export type NodeDragItem = { extent?: 'parent' | CoordinateExtent; parentNode?: string; dragging?: boolean; + origin?: NodeOrigin; }; export type NodeOrigin = [number, number];