전략편집기 수정

This commit is contained in:
Macbook
2026-05-24 12:25:17 +09:00
parent ea39f7df27
commit 1465cb2255
10 changed files with 714 additions and 83 deletions
+62 -8
View File
@@ -301,7 +301,13 @@ export function buildConnectionFromPositions(
export type EdgeHandleBinding = {
sourceHandle?: string | null;
targetHandle?: string | null;
/** smooth-step 경로 굽힘 중심 (중간 영역 드래그) */
centerX?: number | null;
centerY?: number | null;
manual?: boolean;
manualSource?: boolean;
manualTarget?: boolean;
manualCenter?: boolean;
};
export const FLOW_NODE_W = 200;
@@ -340,21 +346,69 @@ export function pickHandleSides(
: { sourceHandle: 's-top', targetHandle: 't-bottom' };
}
/** 경로 굽힘 중심 기준 — 양쪽 노드에 가장 자연스러운 핸들 */
export function pickHandlesFromCenter(
sourceId: string,
targetId: string,
center: { x: number; y: number },
positions: Map<string, { x: number; y: number }>,
): { sourceHandle: string; targetHandle: string } {
const sourcePos = positions.get(sourceId) ?? { x: 0, y: 0 };
const targetPos = positions.get(targetId) ?? { x: 0, y: 0 };
const sourceDim = getNodeDimensions(sourceId);
const targetDim = getNodeDimensions(targetId);
const sourceSide = pickSideFromPoint(center, sourcePos, sourceDim);
const targetSide = pickSideFromPoint(center, targetPos, targetDim);
return {
sourceHandle: `s-${sourceSide}`,
targetHandle: `t-${targetSide}`,
};
}
export function applyEdgeHandles(
edges: Edge[],
positions: Map<string, { x: number; y: number }>,
saved: Map<string, EdgeHandleBinding>,
): Edge[] {
return edges.map(edge => {
const binding = saved.get(edge.id);
if (binding?.manual && binding.sourceHandle && binding.targetHandle) {
return { ...edge, sourceHandle: binding.sourceHandle, targetHandle: binding.targetHandle };
}
const binding = saved.get(edge.id) ?? {};
const picked = pickHandleSides(edge.source, edge.target, positions);
const sourceHandle = binding?.sourceHandle ?? picked.sourceHandle;
const targetHandle = binding?.targetHandle ?? picked.targetHandle;
saved.set(edge.id, { sourceHandle, targetHandle, manual: binding?.manual });
return { ...edge, sourceHandle, targetHandle };
let sourceHandle = picked.sourceHandle;
let targetHandle = picked.targetHandle;
if (
binding.manualCenter
&& binding.centerX != null
&& binding.centerY != null
) {
const natural = pickHandlesFromCenter(
edge.source,
edge.target,
{ x: binding.centerX, y: binding.centerY },
positions,
);
if (!binding.manualSource) sourceHandle = natural.sourceHandle;
else sourceHandle = binding.sourceHandle ?? picked.sourceHandle;
if (!binding.manualTarget) targetHandle = natural.targetHandle;
else targetHandle = binding.targetHandle ?? picked.targetHandle;
} else {
if (binding.manualSource) sourceHandle = binding.sourceHandle ?? picked.sourceHandle;
if (binding.manualTarget) targetHandle = binding.targetHandle ?? picked.targetHandle;
}
const nextBinding: EdgeHandleBinding = {
...binding,
sourceHandle,
targetHandle,
};
saved.set(edge.id, nextBinding);
return {
...edge,
sourceHandle,
targetHandle,
data: { ...(edge.data as object), binding: nextBinding },
};
});
}