@flowgram.ai/free-lines-plugin 0.4.0 → 0.4.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/index.js +4 -8
- package/dist/esm/index.js.map +1 -1
- package/dist/index.js +4 -8
- package/dist/index.js.map +1 -1
- package/package.json +8 -8
package/dist/esm/index.js
CHANGED
|
@@ -295,9 +295,7 @@ import { WorkflowLineRenderData } from "@flowgram.ai/free-layout-core";
|
|
|
295
295
|
|
|
296
296
|
// src/components/workflow-line-render/index.style.ts
|
|
297
297
|
import styled2 from "styled-components";
|
|
298
|
-
var LineStyle = styled2.div
|
|
299
|
-
className: "gedit-flow-activity-edge"
|
|
300
|
-
})`
|
|
298
|
+
var LineStyle = styled2.div`
|
|
301
299
|
position: absolute;
|
|
302
300
|
|
|
303
301
|
@keyframes flowingDash {
|
|
@@ -367,17 +365,15 @@ var LineSVG = (props) => {
|
|
|
367
365
|
fill: "none",
|
|
368
366
|
stroke: `url(#${strokeID})`,
|
|
369
367
|
strokeWidth,
|
|
370
|
-
|
|
371
|
-
className: clsx(
|
|
372
|
-
line.className,
|
|
373
|
-
line.processing || line.flowing ? "dashed-line flowing-line" : ""
|
|
374
|
-
)
|
|
368
|
+
className: line.processing || line.flowing ? "dashed-line flowing-line" : ""
|
|
375
369
|
}
|
|
376
370
|
);
|
|
377
371
|
return /* @__PURE__ */ React4.createElement(
|
|
378
372
|
LineStyle,
|
|
379
373
|
{
|
|
374
|
+
className: clsx("gedit-flow-activity-edge", line.className),
|
|
380
375
|
style: {
|
|
376
|
+
...line.uiState.style,
|
|
381
377
|
left: bounds.x - PADDING,
|
|
382
378
|
top: bounds.y - PADDING,
|
|
383
379
|
position: "absolute"
|
package/dist/esm/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/components/workflow-port-render/index.tsx","../../src/constants/points.ts","../../src/components/workflow-port-render/style.ts","../../src/components/workflow-port-render/cross-hair.tsx","../../src/constants/lines.ts","../../src/create-free-lines-plugin.ts","../../src/layer/workflow-lines-layer.tsx","../../src/components/workflow-line-render/index.tsx","../../src/components/workflow-line-render/line-svg.tsx","../../src/components/workflow-line-render/index.style.ts","../../src/components/workflow-line-render/arrow.tsx","../../src/contributions/bezier/index.ts","../../src/contributions/bezier/bezier-controls.ts","../../src/contributions/fold/index.ts","../../src/contributions/fold/fold-line.ts","../../src/contributions/straight/index.ts","../../src/contributions/straight/point-on-line.ts","../../src/contributions/arc/index.ts"],"sourcesContent":["/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { useEffect, useState } from 'react';\n\nimport classNames from 'clsx';\nimport {\n WorkflowHoverService,\n type WorkflowPortEntity,\n usePlaygroundReadonlyState,\n WorkflowLinesManager,\n} from '@flowgram.ai/free-layout-core';\nimport { MouseTouchEvent, useService } from '@flowgram.ai/core';\n\nimport { PORT_BG_CLASS_NAME } from '../../constants/points';\nimport { WorkflowPointStyle } from './style';\nimport CrossHair from './cross-hair';\n\nexport interface WorkflowPortRenderProps {\n entity: WorkflowPortEntity;\n className?: string;\n style?: React.CSSProperties;\n onClick?: (e: React.MouseEvent<HTMLDivElement>, port: WorkflowPortEntity) => void;\n /** 激活状态颜色 (linked/hovered) */\n primaryColor?: string;\n /** 默认状态颜色 */\n secondaryColor?: string;\n /** 错误状态颜色 */\n errorColor?: string;\n /** 背景颜色 */\n backgroundColor?: string;\n}\n\nexport const WorkflowPortRender: React.FC<WorkflowPortRenderProps> =\n // eslint-disable-next-line react/display-name\n React.memo<WorkflowPortRenderProps>((props: WorkflowPortRenderProps) => {\n const hoverService = useService<WorkflowHoverService>(WorkflowHoverService);\n const linesManager = useService<WorkflowLinesManager>(WorkflowLinesManager);\n const { entity, onClick } = props;\n const { portType, relativePosition, disabled } = entity;\n const [targetElement, setTargetElement] = useState(entity.targetElement);\n const [posX, updatePosX] = useState(relativePosition.x);\n const [posY, updatePosY] = useState(relativePosition.y);\n const [hovered, setHovered] = useState(false);\n const [linked, setLinked] = useState(Boolean(entity?.lines?.length));\n const [hasError, setHasError] = useState(props.entity.hasError);\n const readonly = usePlaygroundReadonlyState();\n\n useEffect(() => {\n // useEffect 时序问题可能导致 port.hasError 非最新,需重新触发一次 validate\n entity.validate();\n setHasError(entity.hasError);\n const dispose = entity.onEntityChange(() => {\n // 如果有挂载的节点,不需要更新位置信息\n if (entity.targetElement) {\n if (entity.targetElement !== targetElement) {\n setTargetElement(entity.targetElement);\n }\n return;\n }\n const newPos = entity.relativePosition;\n // 加上 round 避免点位抖动\n updatePosX(Math.round(newPos.x));\n updatePosY(Math.round(newPos.y));\n });\n const dispose2 = hoverService.onHoveredChange((id) => {\n setHovered(hoverService.isHovered(entity.id));\n });\n const dispose3 = entity.onErrorChanged(() => {\n setHasError(entity.hasError);\n });\n const dispose4 = linesManager.onAvailableLinesChange(() => {\n setTimeout(() => {\n if (linesManager.disposed || entity.disposed) return;\n setLinked(Boolean(entity.lines.length));\n }, 0);\n });\n return () => {\n dispose.dispose();\n dispose2.dispose();\n dispose3.dispose();\n dispose4.dispose();\n };\n }, [hoverService, entity, targetElement]);\n\n // 监听变化\n const className = classNames('workflow-port-render', props.className || '', {\n hovered: !readonly && hovered && !disabled && portType !== 'input',\n // 有线条链接的时候深蓝色小圆点\n linked,\n });\n\n // 构建 CSS 自定义属性用于颜色覆盖\n const colorStyles: Record<string, string> = {};\n if (props.primaryColor) {\n colorStyles['--g-workflow-port-color-primary'] = props.primaryColor;\n }\n if (props.secondaryColor) {\n colorStyles['--g-workflow-port-color-secondary'] = props.secondaryColor;\n }\n if (props.errorColor) {\n colorStyles['--g-workflow-port-color-error'] = props.errorColor;\n }\n if (props.backgroundColor) {\n colorStyles['--g-workflow-port-color-background'] = props.backgroundColor;\n }\n\n const combinedStyle = targetElement\n ? { ...props.style, ...colorStyles }\n : { ...props.style, ...colorStyles, left: posX, top: posY };\n\n const content = (\n <WorkflowPointStyle\n className={className}\n style={combinedStyle}\n onClick={(e) => onClick?.(e, entity)}\n onTouchStart={(e) => {\n if (!onClick) {\n return;\n }\n MouseTouchEvent.onTouched(e, (mouseEvent) => {\n onClick(mouseEvent as unknown as React.MouseEvent<HTMLDivElement>, entity);\n });\n }}\n data-port-entity-id={entity.id}\n data-port-entity-type={entity.portType}\n data-testid=\"sdk.workflow.canvas.node.port\"\n >\n <div className={classNames('bg-circle', 'workflow-bg-circle')}></div>\n <div\n className={classNames({\n bg: true,\n [PORT_BG_CLASS_NAME]: true,\n 'workflow-point-bg': true,\n hasError,\n })}\n >\n <CrossHair />\n </div>\n <div className=\"focus-circle\" />\n </WorkflowPointStyle>\n );\n if (targetElement) {\n return ReactDOM.createPortal(content, targetElement);\n }\n return content;\n });\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 连接点半径\n\nexport const STROKE_WIDTH_SLECTED = 3;\n\nexport const STROKE_WIDTH = 2;\n\nexport const PORT_BG_CLASS_NAME = 'workflow-port-bg';\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\nexport const WorkflowPointStyle = styled.div`\n width: 20px;\n height: 20px;\n border-radius: 50%;\n margin-top: -10px;\n margin-left: -10px;\n left: 50%;\n top: 50%;\n position: absolute;\n // 非 hover 状态下的样式\n border: none;\n\n & > .symbol {\n opacity: 0;\n }\n\n .bg-circle {\n display: flex;\n align-items: center;\n justify-content: center;\n position: absolute;\n border-radius: 50%;\n width: 20px;\n height: 20px;\n background-color: var(--g-workflow-port-color-background, #fff);\n transform: scale(0.5);\n transition: all 0.2s linear 0s;\n }\n\n .bg {\n display: flex;\n align-items: center;\n justify-content: center;\n position: relative;\n width: 100%;\n height: 100%;\n border-radius: 50%;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n transform: scale(0.4, 0.4);\n transition: all 0.2s linear 0s;\n\n &.hasError {\n background: var(--g-workflow-port-color-error, red);\n }\n\n .symbol {\n position: absolute;\n width: 14px;\n height: 14px;\n opacity: 0;\n pointer-events: none;\n color: var(--g-workflow-port-color-background, #fff);\n transition: opacity 0.2s linear 0s;\n\n & > svg {\n width: 14px;\n height: 14px;\n }\n }\n\n .focus-circle {\n position: absolute;\n display: flex;\n justify-content: center;\n align-items: center;\n width: 8px;\n height: 8px;\n opacity: 0;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n border-radius: 50%;\n transition: opacity 0.2s linear 0s;\n }\n }\n\n &.linked .bg:not(.hasError) {\n background: var(--g-workflow-port-color-primary, #4d53e8);\n }\n\n &.hovered .bg:not(.hasError) {\n border: none;\n cursor: crosshair;\n transform: scale(1, 1);\n background: var(--g-workflow-port-color-primary, #4d53e8);\n\n & > .symbol {\n opacity: 1;\n }\n }\n\n .cross-hair {\n position: relative;\n left: 2px;\n top: 2px;\n\n &::after,\n &::before {\n content: '';\n background: var(--g-workflow-port-color-background, #fff);\n border-radius: 2px;\n position: absolute;\n }\n\n &::after {\n left: 4px;\n width: 2px;\n height: 6px;\n box-shadow: 0 4px var(--g-workflow-port-color-background, #fff);\n }\n\n &::before {\n top: 4px;\n width: 6px;\n height: 2px;\n box-shadow: 4px 0 var(--g-workflow-port-color-background, #fff);\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\n// demo 环境自绘 cross-hair,正式环境使用 IconAdd\nexport default function CrossHair(): JSX.Element {\n return (\n <div className=\"symbol\">\n <div className=\"cross-hair\" />\n </div>\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 箭头宽度\nexport const LINE_OFFSET = 6;\n\nexport const LINE_PADDING = 12;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { WorkflowLinesManager } from '@flowgram.ai/free-layout-core';\nimport { definePluginCreator, PluginContext } from '@flowgram.ai/core';\n\nimport { FreeLinesPluginOptions } from './type';\nimport { WorkflowLinesLayer } from './layer';\nimport { WorkflowBezierLineContribution, WorkflowFoldLineContribution } from './contributions';\n\nexport const createFreeLinesPlugin = definePluginCreator({\n singleton: true,\n onInit: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n ctx.playground.registerLayer(WorkflowLinesLayer, {\n ...opts,\n });\n },\n onReady: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n const linesManager = ctx.container.get(WorkflowLinesManager);\n linesManager\n .registerContribution(WorkflowBezierLineContribution)\n .registerContribution(WorkflowFoldLineContribution);\n\n if (opts.contributions) {\n opts.contributions.forEach((contribution) => {\n linesManager.registerContribution(contribution);\n });\n }\n\n if (opts.defaultLineType) {\n linesManager.switchLineType(opts.defaultLineType);\n }\n },\n});\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { ReactNode, useLayoutEffect, useState } from 'react';\n\nimport { inject, injectable } from 'inversify';\nimport { domUtils } from '@flowgram.ai/utils';\nimport { FlowRendererRegistry } from '@flowgram.ai/renderer';\nimport { StackingContextManager } from '@flowgram.ai/free-stack-plugin';\nimport {\n nanoid,\n WorkflowDocument,\n WorkflowHoverService,\n WorkflowLineEntity,\n WorkflowLineRenderData,\n WorkflowNodeEntity,\n WorkflowPortEntity,\n WorkflowSelectService,\n} from '@flowgram.ai/free-layout-core';\nimport { Layer, observeEntities, observeEntityDatas, TransformData } from '@flowgram.ai/core';\n\nimport { LineRenderProps, LinesLayerOptions } from '../type';\nimport { WorkflowLineRender } from '../components';\n\n@injectable()\nexport class WorkflowLinesLayer extends Layer<LinesLayerOptions> {\n static type = 'WorkflowLinesLayer';\n\n @inject(WorkflowHoverService) hoverService: WorkflowHoverService;\n\n @inject(WorkflowSelectService) selectService: WorkflowSelectService;\n\n @inject(StackingContextManager) stackContext: StackingContextManager;\n\n @inject(FlowRendererRegistry) rendererRegistry: FlowRendererRegistry;\n\n @observeEntities(WorkflowLineEntity) readonly lines: WorkflowLineEntity[];\n\n @observeEntities(WorkflowPortEntity) readonly ports: WorkflowPortEntity[];\n\n @observeEntityDatas(WorkflowNodeEntity, TransformData)\n readonly trans: TransformData[];\n\n @inject(WorkflowDocument) protected workflowDocument: WorkflowDocument;\n\n private layerID = nanoid();\n\n private mountedLines: Map<\n string,\n {\n line: WorkflowLineEntity;\n portal: ReactNode;\n version: string;\n }\n > = new Map();\n\n private _version = 0;\n\n /**\n * 节点线条\n */\n public node = domUtils.createDivWithClass('gedit-playground-layer gedit-flow-lines-layer');\n\n public onZoom(scale: number): void {\n this.node.style.transform = `scale(${scale})`;\n }\n\n public onReady() {\n this.pipelineNode.appendChild(this.node);\n this.toDispose.pushAll([\n this.selectService.onSelectionChanged(() => this.render()),\n this.hoverService.onHoveredChange(() => this.render()),\n this.workflowDocument.linesManager.onForceUpdate(() => {\n this.mountedLines.clear();\n this.bumpVersion();\n this.render();\n }),\n ]);\n }\n\n public dispose() {\n this.mountedLines.clear();\n }\n\n public render(): JSX.Element {\n const [, forceUpdate] = useState({});\n\n useLayoutEffect(() => {\n const updateLines = (): void => {\n let needsUpdate = false;\n\n // 批量处理所有线条的更新\n this.lines.forEach((line) => {\n const renderData = line.getData(WorkflowLineRenderData);\n const oldVersion = renderData.renderVersion;\n renderData.update();\n // 如果有任何一条线发生变化,标记需要更新\n if (renderData.renderVersion !== oldVersion) {\n needsUpdate = true;\n }\n });\n\n // 只在确实需要更新时触发重渲染\n if (needsUpdate) {\n forceUpdate({});\n }\n };\n\n const rafId = requestAnimationFrame(updateLines);\n return () => cancelAnimationFrame(rafId);\n }, [this.lines]); // 依赖项包含 lines\n\n const lines = this.lines.map((line) => this.renderLine(line));\n return <>{lines}</>;\n }\n\n // 用来绕过 memo\n private bumpVersion() {\n this._version = this._version + 1;\n if (this._version === Number.MAX_SAFE_INTEGER) {\n this._version = 0;\n }\n }\n\n private lineProps(line: WorkflowLineEntity): LineRenderProps {\n const { lineType } = this.workflowDocument.linesManager;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const version = this.lineVersion(line);\n\n return {\n key: line.id,\n color: line.color,\n selected,\n hovered,\n line,\n lineType,\n version,\n strokePrefix: this.layerID,\n rendererRegistry: this.rendererRegistry,\n };\n }\n\n private lineVersion(line: WorkflowLineEntity): string {\n const renderData = line.getData(WorkflowLineRenderData);\n const { renderVersion } = renderData;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const { version: lineVersion, color } = line;\n\n const version = `v:${this._version},lv:${lineVersion},rv:${renderVersion},c:${color},s:${\n selected ? 'T' : 'F'\n },h:${hovered ? 'T' : 'F'}`;\n\n return version;\n }\n\n private lineComponent(props: LineRenderProps): ReactNode {\n const RenderInsideLine = this.options.renderInsideLine ?? (() => <></>);\n return (\n <WorkflowLineRender {...props}>\n <RenderInsideLine {...props} />\n </WorkflowLineRender>\n );\n }\n\n private renderLine(line: WorkflowLineEntity): ReactNode {\n const lineProps = this.lineProps(line);\n const cache = this.mountedLines.get(line.id);\n const isCached = cache !== undefined;\n const { portal: cachedPortal, version: cachedVersion } = cache ?? {};\n if (isCached && cachedVersion === lineProps.version) {\n // 如果已有缓存且版本相同,则直接返回缓存的 portal\n return cachedPortal;\n }\n if (!isCached) {\n // 如果缓存不存在,则将 line 挂载到 renderElement 上\n this.renderElement.appendChild(line.node);\n line.onDispose(() => {\n this.mountedLines.delete(line.id);\n line.node.remove();\n });\n }\n // 刷新缓存\n const portal = ReactDOM.createPortal(this.lineComponent(lineProps), line.node);\n this.mountedLines.set(line.id, { line, portal, version: lineProps.version });\n return portal;\n }\n\n private get renderElement(): HTMLElement {\n return this.stackContext.node;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { memo } from 'react';\n\nimport { LineSVG } from './line-svg';\n\nexport const WorkflowLineRender = memo(\n LineSVG,\n (prevProps, nextProps) => prevProps.version === nextProps.version\n);\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport clsx from 'clsx';\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { POINT_RADIUS } from '@flowgram.ai/free-layout-core';\nimport { WorkflowLineRenderData } from '@flowgram.ai/free-layout-core';\n\nimport { type ArrowRendererComponent } from '../../types/arrow-renderer';\nimport { LineRenderProps } from '../../type';\nimport { STROKE_WIDTH_SLECTED, STROKE_WIDTH } from '../../constants/points';\nimport { LINE_OFFSET } from '../../constants/lines';\nimport { LineStyle } from './index.style';\nimport { ArrowRenderer } from './arrow';\n\nconst PADDING = 12;\n\nexport const LineSVG = (props: LineRenderProps) => {\n const { line, color, selected, children, strokePrefix, rendererRegistry } = props;\n const { position, reverse, hideArrow, vertical } = line;\n\n const renderData = line.getData(WorkflowLineRenderData);\n const { bounds, path: bezierPath } = renderData;\n\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bounds.x + PADDING,\n y: p.y - bounds.y + PADDING,\n });\n\n const fromPos = toRelative(position.from);\n const toPos = toRelative(position.to);\n\n // 箭头位置计算\n const arrowToPos: IPoint =\n position.to.location === 'top'\n ? { x: toPos.x, y: toPos.y - POINT_RADIUS }\n : { x: toPos.x - POINT_RADIUS, y: toPos.y };\n const arrowFromPos: IPoint =\n position.from.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + POINT_RADIUS + LINE_OFFSET }\n : { x: fromPos.x + POINT_RADIUS + LINE_OFFSET, y: fromPos.y };\n\n const strokeWidth = selected\n ? line.uiState.strokeWidthSelected ?? STROKE_WIDTH_SLECTED\n : line.uiState.strokeWidth ?? STROKE_WIDTH;\n\n const strokeID = strokePrefix ? `${strokePrefix}-${line.id}` : line.id;\n\n // 获取自定义箭头渲染器,如果没有则使用默认的\n const CustomArrowRenderer = rendererRegistry?.tryToGetRendererComponent('arrow-renderer')\n ?.renderer as ArrowRendererComponent;\n const ArrowComponent = CustomArrowRenderer || ArrowRenderer;\n\n const path = (\n <path\n d={bezierPath}\n fill=\"none\"\n stroke={`url(#${strokeID})`}\n strokeWidth={strokeWidth}\n style={line.uiState.style}\n className={clsx(\n line.className,\n line.processing || line.flowing ? 'dashed-line flowing-line' : ''\n )}\n />\n );\n\n return (\n <LineStyle\n style={{\n left: bounds.x - PADDING,\n top: bounds.y - PADDING,\n position: 'absolute',\n }}\n >\n {children}\n <svg width={bounds.width + PADDING * 2} height={bounds.height + PADDING * 2}>\n <defs>\n <linearGradient\n x1={vertical ? '100%' : '0%'}\n y1={vertical ? '0%' : '100%'}\n x2=\"100%\"\n y2=\"100%\"\n id={strokeID}\n gradientUnits=\"userSpaceOnUse\"\n >\n <stop stopColor={color} offset=\"0%\" />\n <stop stopColor={color} offset=\"100%\" />\n </linearGradient>\n </defs>\n <g>\n {path}\n <ArrowComponent\n id={strokeID}\n reverseArrow={reverse}\n pos={reverse ? arrowFromPos : arrowToPos}\n strokeWidth={strokeWidth}\n vertical={vertical}\n hide={hideArrow}\n line={line}\n />\n </g>\n </svg>\n </LineStyle>\n );\n};\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\n// 添加一个固定类名,用于选中该节点\n\nexport const LineStyle = styled.div.attrs({\n className: 'gedit-flow-activity-edge',\n})`\n position: absolute;\n\n @keyframes flowingDash {\n to {\n stroke-dashoffset: -13;\n }\n }\n\n .dashed-line {\n stroke-dasharray: 8, 5;\n }\n\n .flowing-line {\n animation: flowingDash 0.5s linear infinite;\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport { type ArrowRendererProps } from '../../types/arrow-renderer';\nimport { LINE_OFFSET } from '../../constants/lines';\n\nexport function ArrowRenderer({\n id,\n pos,\n reverseArrow,\n strokeWidth,\n vertical,\n hide,\n}: ArrowRendererProps) {\n if (hide) {\n return null;\n }\n const arrowPath = vertical\n ? reverseArrow\n ? `M ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${pos.y - LINE_OFFSET} L ${\n pos.x + LINE_OFFSET\n },${pos.y}`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x + LINE_OFFSET\n },${pos.y - LINE_OFFSET}`\n : reverseArrow\n ? `M ${pos.x},${pos.y + LINE_OFFSET} L ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${\n pos.y - LINE_OFFSET\n }`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x - LINE_OFFSET\n },${pos.y + LINE_OFFSET}`;\n\n return (\n <path\n d={arrowPath}\n strokeLinecap=\"round\"\n stroke={`url(#${id})`}\n fill=\"none\"\n strokeWidth={strokeWidth}\n />\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { Bezier } from 'bezier-js';\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { getBezierControlPoints } from './bezier-controls';\n\nexport interface BezierData {\n fromPos: IPoint;\n toPos: IPoint;\n bbox: Rectangle; // 外围矩形\n controls: IPoint[]; // 控制点\n bezier: Bezier;\n path: string;\n}\n\nexport class WorkflowBezierLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.BEZIER;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: BezierData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return Point.getDistance(pos, this.data.bezier.project(pos));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n this.data = this.calcBezier(params.fromPos, params.toPos);\n }\n\n private calcBezier(fromPos: LinePoint, toPos: LinePoint): BezierData {\n const controls = getBezierControlPoints(fromPos, toPos, this.entity.uiState.curvature);\n const bezier = new Bezier([fromPos, ...controls, toPos]);\n const bbox = bezier.bbox();\n const bboxBounds = new Rectangle(\n bbox.x.min,\n bbox.y.min,\n bbox.x.max - bbox.x.min,\n bbox.y.max - bbox.y.min\n );\n\n const path = this.getPath({ bbox: bboxBounds, fromPos, toPos, controls });\n\n this.data = {\n fromPos,\n toPos,\n bezier,\n bbox: bboxBounds,\n controls,\n path,\n };\n return this.data;\n }\n\n private getPath(params: {\n bbox: Rectangle;\n fromPos: LinePoint;\n toPos: LinePoint;\n controls: IPoint[];\n }): string {\n const { bbox } = params;\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n });\n const fromPos = toRelative(params.fromPos);\n const toPos = toRelative(params.toPos);\n\n const controls = params.controls.map((c) => toRelative(c));\n const shrink = this.entity.uiState.shrink;\n\n const renderFromPos: IPoint =\n params.fromPos.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + shrink }\n : { x: fromPos.x + shrink, y: fromPos.y };\n\n const renderToPos: IPoint =\n params.toPos.location === 'top'\n ? { x: toPos.x, y: toPos.y - shrink }\n : { x: toPos.x - shrink, y: toPos.y };\n\n const controlPoints = controls.map((s) => `${s.x} ${s.y}`).join(',');\n return `M${renderFromPos.x} ${renderFromPos.y} C ${controlPoints}, ${renderToPos.x} ${renderToPos.y}`;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { LinePoint, LinePointLocation } from '@flowgram.ai/free-layout-core';\n\nfunction getControlOffset(distance: number, curvature: number): number {\n if (distance >= 0) {\n return 0.5 * distance;\n }\n\n return curvature * 25 * Math.sqrt(-distance);\n}\n\nfunction getControlWithCurvature({\n location,\n x1,\n y1,\n x2,\n y2,\n curvature,\n}: {\n location: LinePointLocation;\n curvature: number;\n x1: number;\n x2: number;\n y1: number;\n y2: number;\n}): IPoint {\n switch (location) {\n case 'left':\n return {\n x: x1 - getControlOffset(x1 - x2, curvature),\n y: y1,\n };\n case 'right':\n return {\n x: x1 + getControlOffset(x2 - x1, curvature),\n y: y1,\n };\n case 'top':\n return {\n x: x1,\n y: y1 - getControlOffset(y1 - y2, curvature),\n };\n case 'bottom':\n return {\n x: x1,\n y: y1 + getControlOffset(y2 - y1, curvature),\n };\n }\n}\n\nexport function getBezierControlPoints(\n fromPos: LinePoint,\n toPos: LinePoint,\n curvature = 0.25\n): IPoint[] {\n const fromControl = getControlWithCurvature({\n location: fromPos.location,\n x1: fromPos.x,\n y1: fromPos.y,\n x2: toPos.x,\n y2: toPos.y,\n curvature,\n });\n const toControl = getControlWithCurvature({\n location: toPos.location,\n x1: toPos.x,\n y1: toPos.y,\n x2: fromPos.x,\n y2: fromPos.y,\n curvature,\n });\n return [fromControl, toControl];\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { FoldLine } from './fold-line';\n\nexport interface FoldData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowFoldLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.LINE_CHART;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: FoldData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return FoldLine.getFoldLineToPointDistance(this.data.points, pos);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = FoldLine.getPoints({\n source: {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n location: fromPos.location,\n },\n target: {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n location: toPos.location,\n },\n });\n\n const bbox = FoldLine.getBounds(points);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n const path = FoldLine.getSmoothStepPath(adjustedPoints);\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport { LinePoint } from '@flowgram.ai/free-layout-core';\n\n/**\n * 计算点到线段的距离\n * @param point 待测试点\n * @param segStart 线段起点\n * @param segEnd 线段终点\n */\nconst getPointToSegmentDistance = (point: IPoint, segStart: IPoint, segEnd: IPoint): number => {\n const { x: px, y: py } = point;\n const { x: x1, y: y1 } = segStart;\n const { x: x2, y: y2 } = segEnd;\n\n const A = px - x1;\n const B = py - y1;\n const C = x2 - x1;\n const D = y2 - y1;\n\n const dot = A * C + B * D;\n const lenSq = C * C + D * D;\n\n // 参数方程中的t参数\n const param = lenSq === 0 ? -1 : dot / lenSq;\n\n let xx: number;\n let yy: number;\n\n if (param < 0) {\n xx = x1;\n yy = y1;\n } else if (param > 1) {\n xx = x2;\n yy = y2;\n } else {\n xx = x1 + param * C;\n yy = y1 + param * D;\n }\n\n const dx = px - xx;\n const dy = py - yy;\n\n return Math.sqrt(dx * dx + dy * dy);\n};\n\n/**\n * Fork from: https://github.com/xyflow/xyflow/blob/main/packages/system/src/utils/edges/smoothstep-edge.ts\n * MIT License\n * Copyright (c) 2019-2024 webkid GmbH\n */\nexport namespace FoldLine {\n const EDGE_RADIUS = 5;\n const OFFSET = 20;\n\n function getEdgeCenter({ source, target }: { source: IPoint; target: IPoint }): [number, number] {\n const xOffset = Math.abs(target.x - source.x) / 2;\n const centerX = target.x < source.x ? target.x + xOffset : target.x - xOffset;\n\n const yOffset = Math.abs(target.y - source.y) / 2;\n const centerY = target.y < source.y ? target.y + yOffset : target.y - yOffset;\n\n return [centerX, centerY];\n }\n\n const getDirection = ({ source, target }: { source: LinePoint; target: LinePoint }): IPoint => {\n if (source.location === 'left' || source.location === 'right') {\n return source.x < target.x ? { x: 1, y: 0 } : { x: -1, y: 0 };\n }\n return source.y < target.y ? { x: 0, y: 1 } : { x: 0, y: -1 };\n };\n\n const handleDirections = {\n left: { x: -1, y: 0 },\n right: { x: 1, y: 0 },\n top: { x: 0, y: -1 },\n bottom: { x: 0, y: 1 },\n };\n // eslint-disable-next-line complexity\n export function getPoints({\n source,\n target,\n }: {\n source: LinePoint;\n target: LinePoint;\n }): IPoint[] {\n const sourceDir = handleDirections[source.location];\n const targetDir = handleDirections[target.location];\n const sourceGapped: LinePoint = {\n x: source.x + sourceDir.x * OFFSET,\n y: source.y + sourceDir.y * OFFSET,\n location: source.location,\n };\n const targetGapped: LinePoint = {\n x: target.x + targetDir.x * OFFSET,\n y: target.y + targetDir.y * OFFSET,\n location: target.location,\n };\n const dir = getDirection({\n source: sourceGapped,\n target: targetGapped,\n });\n const dirAccessor = dir.x !== 0 ? 'x' : 'y';\n const currDir = dir[dirAccessor];\n\n let points: IPoint[] = [];\n let centerX, centerY;\n\n const [defaultCenterX, defaultCenterY] = getEdgeCenter({\n source,\n target,\n });\n\n // 计算向量乘积\n if (sourceDir[dirAccessor] * targetDir[dirAccessor] === -1) {\n centerX = defaultCenterX;\n centerY = defaultCenterY;\n\n const verticalSplit: IPoint[] = [\n { x: centerX, y: sourceGapped.y },\n { x: centerX, y: targetGapped.y },\n ];\n\n const horizontalSplit: IPoint[] = [\n { x: sourceGapped.x, y: centerY },\n { x: targetGapped.x, y: centerY },\n ];\n\n if (sourceDir[dirAccessor] === currDir) {\n points = dirAccessor === 'x' ? verticalSplit : horizontalSplit;\n } else {\n points = dirAccessor === 'x' ? horizontalSplit : verticalSplit;\n }\n } else {\n // sourceTarget means we take x from source and y from target, targetSource is the opposite\n const sourceTarget: IPoint[] = [{ x: sourceGapped.x, y: targetGapped.y }];\n const targetSource: IPoint[] = [{ x: targetGapped.x, y: sourceGapped.y }];\n // this handles edges with same handle positions\n if (dirAccessor === 'x') {\n points = sourceDir.x === currDir ? targetSource : sourceTarget;\n } else {\n points = sourceDir.y === currDir ? sourceTarget : targetSource;\n }\n\n // these are conditions for handling mixed handle positions like Right -> Bottom for example\n const dirAccessorOpposite = dirAccessor === 'x' ? 'y' : 'x';\n const isSameDir = sourceDir[dirAccessor] === targetDir[dirAccessorOpposite];\n const sourceGtTargetOppo =\n sourceGapped[dirAccessorOpposite] > targetGapped[dirAccessorOpposite];\n const sourceLtTargetOppo =\n sourceGapped[dirAccessorOpposite] < targetGapped[dirAccessorOpposite];\n const flipSourceTarget =\n (sourceDir[dirAccessor] === 1 &&\n ((!isSameDir && sourceGtTargetOppo) || (isSameDir && sourceLtTargetOppo))) ||\n (sourceDir[dirAccessor] !== 1 &&\n ((!isSameDir && sourceLtTargetOppo) || (isSameDir && sourceGtTargetOppo)));\n\n if (flipSourceTarget) {\n points = dirAccessor === 'x' ? sourceTarget : targetSource;\n }\n\n const sourceGapPoint = { x: sourceGapped.x, y: sourceGapped.y };\n const targetGapPoint = { x: targetGapped.x, y: targetGapped.y };\n const maxXDistance = Math.max(\n Math.abs(sourceGapPoint.x - points[0].x),\n Math.abs(targetGapPoint.x - points[0].x)\n );\n const maxYDistance = Math.max(\n Math.abs(sourceGapPoint.y - points[0].y),\n Math.abs(targetGapPoint.y - points[0].y)\n );\n\n if (maxXDistance >= maxYDistance) {\n centerX = (sourceGapPoint.x + targetGapPoint.x) / 2;\n centerY = points[0].y;\n } else {\n centerX = points[0].x;\n centerY = (sourceGapPoint.y + targetGapPoint.y) / 2;\n }\n }\n\n const pathPoints = [\n source,\n { x: sourceGapped.x, y: sourceGapped.y },\n ...points,\n { x: targetGapped.x, y: targetGapped.y },\n target,\n ];\n\n return pathPoints;\n }\n\n function getBend(a: IPoint, b: IPoint, c: IPoint): string {\n const bendSize = Math.min(\n Point.getDistance(a, b) / 2,\n Point.getDistance(b, c) / 2,\n EDGE_RADIUS\n );\n const { x, y } = b;\n\n // no bend\n if ((a.x === x && x === c.x) || (a.y === y && y === c.y)) {\n return `L${x} ${y}`;\n }\n\n // first segment is horizontal\n if (a.y === y) {\n const xDir = a.x < c.x ? -1 : 1;\n const yDir = a.y < c.y ? 1 : -1;\n return `L ${x + bendSize * xDir},${y}Q ${x},${y} ${x},${y + bendSize * yDir}`;\n }\n\n const xDir = a.x < c.x ? 1 : -1;\n const yDir = a.y < c.y ? -1 : 1;\n return `L ${x},${y + bendSize * yDir}Q ${x},${y} ${x + bendSize * xDir},${y}`;\n }\n\n /**\n * 实现 reactFlow 原本的折叠线交互\n */\n export function getSmoothStepPath(points: IPoint[]): string {\n const path = points.reduce<string>((res, p, i) => {\n let segment = '';\n\n if (i > 0 && i < points.length - 1) {\n segment = getBend(points[i - 1], p, points[i + 1]);\n } else {\n segment = `${i === 0 ? 'M' : 'L'}${p.x} ${p.y}`;\n }\n\n res += segment;\n\n return res;\n }, '');\n\n return path;\n }\n export function getBounds(points: IPoint[]): Rectangle {\n const xList = points.map((p) => p.x);\n const yList = points.map((p) => p.y);\n const left = Math.min(...xList);\n const right = Math.max(...xList);\n const top = Math.min(...yList);\n const bottom = Math.max(...yList);\n return Rectangle.createRectangleWithTwoPoints(\n {\n x: left,\n y: top,\n },\n {\n x: right,\n y: bottom,\n }\n );\n }\n /**\n * 计算点到折线的最短距离\n * @param points 折线的所有端点\n * @param pos 待测试点\n * @returns 最短距离\n */\n export const getFoldLineToPointDistance = (points: IPoint[], pos: IPoint): number => {\n // 特殊情况处理\n if (points.length === 0) {\n return Infinity;\n }\n\n if (points.length === 1) {\n return Point.getDistance(points[0]!, pos);\n }\n\n // 构建线段数组\n const lines: [IPoint, IPoint][] = [];\n for (let i = 0; i < points.length - 1; i++) {\n lines.push([points[i]!, points[i + 1]!]);\n }\n\n // 计算点到每个线段的最短距离\n const distances = lines.map((line) => {\n const [p1, p2] = line;\n return getPointToSegmentDistance(pos, p1, p2);\n });\n\n return Math.min(...distances);\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { projectPointOnLine } from './point-on-line';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowStraightLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowStraightLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: StraightData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n const [start, end] = this.data.points;\n return Point.getDistance(pos, projectPointOnLine(pos, start, end));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = [\n {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n },\n {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n },\n ];\n\n const bbox = Rectangle.createRectangleWithTwoPoints(points[0], points[1]);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n // 生成直线路径\n const path = `M ${adjustedPoints[0].x} ${adjustedPoints[0].y} L ${adjustedPoints[1].x} ${adjustedPoints[1].y}`;\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\n/**\n * 计算点到直线的投影点\n */\nexport function projectPointOnLine(point: IPoint, lineStart: IPoint, lineEnd: IPoint): IPoint {\n const dx = lineEnd.x - lineStart.x;\n const dy = lineEnd.y - lineStart.y;\n\n // 如果是垂直线\n if (dx === 0) {\n return { x: lineStart.x, y: point.y };\n }\n // 如果是水平线\n if (dy === 0) {\n return { x: point.x, y: lineStart.y };\n }\n\n const t = ((point.x - lineStart.x) * dx + (point.y - lineStart.y) * dy) / (dx * dx + dy * dy);\n const clampedT = Math.max(0, Math.min(1, t));\n\n return {\n x: lineStart.x + clampedT * dx,\n y: lineStart.y + clampedT * dy,\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\n\nexport interface ArcData {\n fromPos: IPoint;\n toPos: IPoint;\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowArkLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowArkLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: ArcData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n\n const { fromPos, toPos, bbox } = this.data;\n\n // 首先检查点是否在包围盒范围内\n if (!bbox.contains(pos.x, pos.y)) {\n // 如果点在包围盒外,计算到包围盒边界的最短距离\n const dx = Math.max(bbox.x - pos.x, 0, pos.x - (bbox.x + bbox.width));\n const dy = Math.max(bbox.y - pos.y, 0, pos.y - (bbox.y + bbox.height));\n return Math.sqrt(dx * dx + dy * dy);\n }\n\n // 计算圆弧的中心点和半径\n const center = {\n x: (fromPos.x + toPos.x) / 2,\n y: (fromPos.y + toPos.y) / 2,\n };\n const radius = Point.getDistance(fromPos, center);\n\n // 计算点到圆心的距离\n const distanceToCenter = Point.getDistance(pos, center);\n\n // 返回点到圆弧的近似距离\n return Math.abs(distanceToCenter - radius);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: IPoint; toPos: IPoint }): void {\n const { fromPos, toPos } = params;\n const { vertical } = this.entity;\n\n const sourceOffset = {\n x: vertical ? 0 : POINT_RADIUS,\n y: vertical ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: vertical ? 0 : -POINT_RADIUS,\n y: vertical ? -POINT_RADIUS : 0,\n };\n\n const start = {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n };\n const end = {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n };\n\n // 计算圆弧的包围盒\n const bbox = this.calculateArcBBox(start, end);\n\n // 生成圆弧路径\n const path = this.getArcPath(start, end, bbox);\n\n this.data = {\n fromPos: start,\n toPos: end,\n path,\n bbox,\n };\n }\n\n private calculateArcBBox(start: IPoint, end: IPoint): Rectangle {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const radius = Math.sqrt(dx * dx + dy * dy) / 2;\n\n const centerX = (start.x + end.x) / 2;\n const centerY = (start.y + end.y) / 2;\n\n return new Rectangle(centerX - radius, centerY - radius, radius * 2, radius * 2);\n }\n\n private getArcPath(start: IPoint, end: IPoint, bbox: Rectangle): string {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const distance = Math.sqrt(dx * dx + dy * dy);\n\n // 调整点到相对坐标\n const startRel = {\n x: start.x - bbox.x + LINE_PADDING,\n y: start.y - bbox.y + LINE_PADDING,\n };\n const endRel = {\n x: end.x - bbox.x + LINE_PADDING,\n y: end.y - bbox.y + LINE_PADDING,\n };\n\n // 使用 SVG 圆弧命令\n return `M ${startRel.x} ${startRel.y} A ${distance / 2} ${distance / 2} 0 0 1 ${endRel.x} ${\n endRel.y\n }`;\n }\n}\n"],"mappings":";;;;;;;;;;;;AAKA,OAAO,cAAc;AACrB,OAAOA,UAAS,WAAW,gBAAgB;AAE3C,OAAO,gBAAgB;AACvB;AAAA,EACE;AAAA,EAEA;AAAA,EACA;AAAA,OACK;AACP,SAAS,iBAAiB,kBAAkB;;;ACRrC,IAAM,uBAAuB;AAE7B,IAAM,eAAe;AAErB,IAAM,qBAAqB;;;ACNlC,OAAO,YAAY;AAEZ,IAAM,qBAAqB,OAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACFzC,OAAO,WAAW;AAGH,SAAR,YAA0C;AAC/C,SACE,oCAAC,SAAI,WAAU,YACb,oCAAC,SAAI,WAAU,cAAa,CAC9B;AAEJ;;;AHsBO,IAAM;AAAA;AAAA,EAEXC,OAAM,KAA8B,CAAC,UAAmC;AACtE,UAAM,eAAe,WAAiC,oBAAoB;AAC1E,UAAM,eAAe,WAAiC,oBAAoB;AAC1E,UAAM,EAAE,QAAQ,QAAQ,IAAI;AAC5B,UAAM,EAAE,UAAU,kBAAkB,SAAS,IAAI;AACjD,UAAM,CAAC,eAAe,gBAAgB,IAAI,SAAS,OAAO,aAAa;AACvE,UAAM,CAAC,MAAM,UAAU,IAAI,SAAS,iBAAiB,CAAC;AACtD,UAAM,CAAC,MAAM,UAAU,IAAI,SAAS,iBAAiB,CAAC;AACtD,UAAM,CAAC,SAAS,UAAU,IAAI,SAAS,KAAK;AAC5C,UAAM,CAAC,QAAQ,SAAS,IAAI,SAAS,QAAQ,QAAQ,OAAO,MAAM,CAAC;AACnE,UAAM,CAAC,UAAU,WAAW,IAAI,SAAS,MAAM,OAAO,QAAQ;AAC9D,UAAM,WAAW,2BAA2B;AAE5C,cAAU,MAAM;AAEd,aAAO,SAAS;AAChB,kBAAY,OAAO,QAAQ;AAC3B,YAAM,UAAU,OAAO,eAAe,MAAM;AAE1C,YAAI,OAAO,eAAe;AACxB,cAAI,OAAO,kBAAkB,eAAe;AAC1C,6BAAiB,OAAO,aAAa;AAAA,UACvC;AACA;AAAA,QACF;AACA,cAAM,SAAS,OAAO;AAEtB,mBAAW,KAAK,MAAM,OAAO,CAAC,CAAC;AAC/B,mBAAW,KAAK,MAAM,OAAO,CAAC,CAAC;AAAA,MACjC,CAAC;AACD,YAAM,WAAW,aAAa,gBAAgB,CAAC,OAAO;AACpD,mBAAW,aAAa,UAAU,OAAO,EAAE,CAAC;AAAA,MAC9C,CAAC;AACD,YAAM,WAAW,OAAO,eAAe,MAAM;AAC3C,oBAAY,OAAO,QAAQ;AAAA,MAC7B,CAAC;AACD,YAAM,WAAW,aAAa,uBAAuB,MAAM;AACzD,mBAAW,MAAM;AACf,cAAI,aAAa,YAAY,OAAO,SAAU;AAC9C,oBAAU,QAAQ,OAAO,MAAM,MAAM,CAAC;AAAA,QACxC,GAAG,CAAC;AAAA,MACN,CAAC;AACD,aAAO,MAAM;AACX,gBAAQ,QAAQ;AAChB,iBAAS,QAAQ;AACjB,iBAAS,QAAQ;AACjB,iBAAS,QAAQ;AAAA,MACnB;AAAA,IACF,GAAG,CAAC,cAAc,QAAQ,aAAa,CAAC;AAGxC,UAAM,YAAY,WAAW,wBAAwB,MAAM,aAAa,IAAI;AAAA,MAC1E,SAAS,CAAC,YAAY,WAAW,CAAC,YAAY,aAAa;AAAA;AAAA,MAE3D;AAAA,IACF,CAAC;AAGD,UAAM,cAAsC,CAAC;AAC7C,QAAI,MAAM,cAAc;AACtB,kBAAY,iCAAiC,IAAI,MAAM;AAAA,IACzD;AACA,QAAI,MAAM,gBAAgB;AACxB,kBAAY,mCAAmC,IAAI,MAAM;AAAA,IAC3D;AACA,QAAI,MAAM,YAAY;AACpB,kBAAY,+BAA+B,IAAI,MAAM;AAAA,IACvD;AACA,QAAI,MAAM,iBAAiB;AACzB,kBAAY,oCAAoC,IAAI,MAAM;AAAA,IAC5D;AAEA,UAAM,gBAAgB,gBAClB,EAAE,GAAG,MAAM,OAAO,GAAG,YAAY,IACjC,EAAE,GAAG,MAAM,OAAO,GAAG,aAAa,MAAM,MAAM,KAAK,KAAK;AAE5D,UAAM,UACJ,gBAAAA,OAAA;AAAA,MAAC;AAAA;AAAA,QACC;AAAA,QACA,OAAO;AAAA,QACP,SAAS,CAAC,MAAM,UAAU,GAAG,MAAM;AAAA,QACnC,cAAc,CAAC,MAAM;AACnB,cAAI,CAAC,SAAS;AACZ;AAAA,UACF;AACA,0BAAgB,UAAU,GAAG,CAAC,eAAe;AAC3C,oBAAQ,YAA2D,MAAM;AAAA,UAC3E,CAAC;AAAA,QACH;AAAA,QACA,uBAAqB,OAAO;AAAA,QAC5B,yBAAuB,OAAO;AAAA,QAC9B,eAAY;AAAA;AAAA,MAEZ,gBAAAA,OAAA,cAAC,SAAI,WAAW,WAAW,aAAa,oBAAoB,GAAG;AAAA,MAC/D,gBAAAA,OAAA;AAAA,QAAC;AAAA;AAAA,UACC,WAAW,WAAW;AAAA,YACpB,IAAI;AAAA,YACJ,CAAC,kBAAkB,GAAG;AAAA,YACtB,qBAAqB;AAAA,YACrB;AAAA,UACF,CAAC;AAAA;AAAA,QAED,gBAAAA,OAAA,cAAC,eAAU;AAAA,MACb;AAAA,MACA,gBAAAA,OAAA,cAAC,SAAI,WAAU,gBAAe;AAAA,IAChC;AAEF,QAAI,eAAe;AACjB,aAAO,SAAS,aAAa,SAAS,aAAa;AAAA,IACrD;AACA,WAAO;AAAA,EACT,CAAC;AAAA;;;AI/II,IAAM,cAAc;AAEpB,IAAM,eAAe;;;ACH5B,SAAS,wBAAAC,6BAA4B;AACrC,SAAS,2BAA0C;;;ACDnD,OAAOC,eAAc;AACrB,OAAOC,UAAoB,iBAAiB,YAAAC,iBAAgB;AAE5D,SAAS,QAAQ,kBAAkB;AACnC,SAAS,gBAAgB;AACzB,SAAS,4BAA4B;AACrC,SAAS,8BAA8B;AACvC;AAAA,EACE;AAAA,EACA;AAAA,EACA,wBAAAC;AAAA,EACA;AAAA,EACA,0BAAAC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AACP,SAAS,OAAO,iBAAiB,oBAAoB,qBAAqB;;;ACjB1E,SAAS,YAAY;;;ACArB,OAAOC,YAAW;AAElB,OAAO,UAAU;AAEjB,SAAS,oBAAoB;AAC7B,SAAS,8BAA8B;;;ACLvC,OAAOC,aAAY;AAIZ,IAAM,YAAYA,QAAO,IAAI,MAAM;AAAA,EACxC,WAAW;AACb,CAAC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACND,OAAOC,YAAW;AAKX,SAAS,cAAc;AAAA,EAC5B;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,GAAuB;AACrB,MAAI,MAAM;AACR,WAAO;AAAA,EACT;AACA,QAAM,YAAY,WACd,eACE,KAAK,IAAI,IAAI,WAAW,IAAI,IAAI,CAAC,MAAM,IAAI,CAAC,IAAI,IAAI,IAAI,WAAW,MACjE,IAAI,IAAI,WACV,IAAI,IAAI,CAAC,KACT,KAAK,IAAI,IAAI,WAAW,IAAI,IAAI,IAAI,WAAW,MAAM,IAAI,CAAC,IAAI,IAAI,CAAC,MACjE,IAAI,IAAI,WACV,IAAI,IAAI,IAAI,WAAW,KACzB,eACA,KAAK,IAAI,CAAC,IAAI,IAAI,IAAI,WAAW,MAAM,IAAI,IAAI,WAAW,IAAI,IAAI,CAAC,MAAM,IAAI,CAAC,IAC5E,IAAI,IAAI,WACV,KACA,KAAK,IAAI,IAAI,WAAW,IAAI,IAAI,IAAI,WAAW,MAAM,IAAI,CAAC,IAAI,IAAI,CAAC,MACjE,IAAI,IAAI,WACV,IAAI,IAAI,IAAI,WAAW;AAE3B,SACE,gBAAAC,OAAA;AAAA,IAAC;AAAA;AAAA,MACC,GAAG;AAAA,MACH,eAAc;AAAA,MACd,QAAQ,QAAQ,EAAE;AAAA,MAClB,MAAK;AAAA,MACL;AAAA;AAAA,EACF;AAEJ;;;AF3BA,IAAM,UAAU;AAET,IAAM,UAAU,CAAC,UAA2B;AACjD,QAAM,EAAE,MAAM,OAAO,UAAU,UAAU,cAAc,iBAAiB,IAAI;AAC5E,QAAM,EAAE,UAAU,SAAS,WAAW,SAAS,IAAI;AAEnD,QAAM,aAAa,KAAK,QAAQ,sBAAsB;AACtD,QAAM,EAAE,QAAQ,MAAM,WAAW,IAAI;AAGrC,QAAM,aAAa,CAAC,OAAuB;AAAA,IACzC,GAAG,EAAE,IAAI,OAAO,IAAI;AAAA,IACpB,GAAG,EAAE,IAAI,OAAO,IAAI;AAAA,EACtB;AAEA,QAAM,UAAU,WAAW,SAAS,IAAI;AACxC,QAAM,QAAQ,WAAW,SAAS,EAAE;AAGpC,QAAM,aACJ,SAAS,GAAG,aAAa,QACrB,EAAE,GAAG,MAAM,GAAG,GAAG,MAAM,IAAI,aAAa,IACxC,EAAE,GAAG,MAAM,IAAI,cAAc,GAAG,MAAM,EAAE;AAC9C,QAAM,eACJ,SAAS,KAAK,aAAa,WACvB,EAAE,GAAG,QAAQ,GAAG,GAAG,QAAQ,IAAI,eAAe,YAAY,IAC1D,EAAE,GAAG,QAAQ,IAAI,eAAe,aAAa,GAAG,QAAQ,EAAE;AAEhE,QAAM,cAAc,WAChB,KAAK,QAAQ,uBAAuB,uBACpC,KAAK,QAAQ,eAAe;AAEhC,QAAM,WAAW,eAAe,GAAG,YAAY,IAAI,KAAK,EAAE,KAAK,KAAK;AAGpE,QAAM,sBAAsB,kBAAkB,0BAA0B,gBAAgB,GACpF;AACJ,QAAM,iBAAiB,uBAAuB;AAE9C,QAAM,OACJ,gBAAAC,OAAA;AAAA,IAAC;AAAA;AAAA,MACC,GAAG;AAAA,MACH,MAAK;AAAA,MACL,QAAQ,QAAQ,QAAQ;AAAA,MACxB;AAAA,MACA,OAAO,KAAK,QAAQ;AAAA,MACpB,WAAW;AAAA,QACT,KAAK;AAAA,QACL,KAAK,cAAc,KAAK,UAAU,6BAA6B;AAAA,MACjE;AAAA;AAAA,EACF;AAGF,SACE,gBAAAA,OAAA;AAAA,IAAC;AAAA;AAAA,MACC,OAAO;AAAA,QACL,MAAM,OAAO,IAAI;AAAA,QACjB,KAAK,OAAO,IAAI;AAAA,QAChB,UAAU;AAAA,MACZ;AAAA;AAAA,IAEC;AAAA,IACD,gBAAAA,OAAA,cAAC,SAAI,OAAO,OAAO,QAAQ,UAAU,GAAG,QAAQ,OAAO,SAAS,UAAU,KACxE,gBAAAA,OAAA,cAAC,cACC,gBAAAA,OAAA;AAAA,MAAC;AAAA;AAAA,QACC,IAAI,WAAW,SAAS;AAAA,QACxB,IAAI,WAAW,OAAO;AAAA,QACtB,IAAG;AAAA,QACH,IAAG;AAAA,QACH,IAAI;AAAA,QACJ,eAAc;AAAA;AAAA,MAEd,gBAAAA,OAAA,cAAC,UAAK,WAAW,OAAO,QAAO,MAAK;AAAA,MACpC,gBAAAA,OAAA,cAAC,UAAK,WAAW,OAAO,QAAO,QAAO;AAAA,IACxC,CACF,GACA,gBAAAA,OAAA,cAAC,WACE,MACD,gBAAAA,OAAA;AAAA,MAAC;AAAA;AAAA,QACC,IAAI;AAAA,QACJ,cAAc;AAAA,QACd,KAAK,UAAU,eAAe;AAAA,QAC9B;AAAA,QACA;AAAA,QACA,MAAM;AAAA,QACN;AAAA;AAAA,IACF,CACF,CACF;AAAA,EACF;AAEJ;;;ADrGO,IAAM,qBAAqB;AAAA,EAChC;AAAA,EACA,CAAC,WAAW,cAAc,UAAU,YAAY,UAAU;AAC5D;;;ADgBO,IAAM,qBAAN,cAAiC,MAAyB;AAAA,EAA1D;AAAA;AAoBL,SAAQ,UAAU,OAAO;AAEzB,SAAQ,eAOJ,oBAAI,IAAI;AAEZ,SAAQ,WAAW;AAKnB;AAAA;AAAA;AAAA,SAAO,OAAO,SAAS,mBAAmB,+CAA+C;AAAA;AAAA,EAElF,OAAO,OAAqB;AACjC,SAAK,KAAK,MAAM,YAAY,SAAS,KAAK;AAAA,EAC5C;AAAA,EAEO,UAAU;AACf,SAAK,aAAa,YAAY,KAAK,IAAI;AACvC,SAAK,UAAU,QAAQ;AAAA,MACrB,KAAK,cAAc,mBAAmB,MAAM,KAAK,OAAO,CAAC;AAAA,MACzD,KAAK,aAAa,gBAAgB,MAAM,KAAK,OAAO,CAAC;AAAA,MACrD,KAAK,iBAAiB,aAAa,cAAc,MAAM;AACrD,aAAK,aAAa,MAAM;AACxB,aAAK,YAAY;AACjB,aAAK,OAAO;AAAA,MACd,CAAC;AAAA,IACH,CAAC;AAAA,EACH;AAAA,EAEO,UAAU;AACf,SAAK,aAAa,MAAM;AAAA,EAC1B;AAAA,EAEO,SAAsB;AAC3B,UAAM,CAAC,EAAE,WAAW,IAAIC,UAAS,CAAC,CAAC;AAEnC,oBAAgB,MAAM;AACpB,YAAM,cAAc,MAAY;AAC9B,YAAI,cAAc;AAGlB,aAAK,MAAM,QAAQ,CAAC,SAAS;AAC3B,gBAAM,aAAa,KAAK,QAAQC,uBAAsB;AACtD,gBAAM,aAAa,WAAW;AAC9B,qBAAW,OAAO;AAElB,cAAI,WAAW,kBAAkB,YAAY;AAC3C,0BAAc;AAAA,UAChB;AAAA,QACF,CAAC;AAGD,YAAI,aAAa;AACf,sBAAY,CAAC,CAAC;AAAA,QAChB;AAAA,MACF;AAEA,YAAM,QAAQ,sBAAsB,WAAW;AAC/C,aAAO,MAAM,qBAAqB,KAAK;AAAA,IACzC,GAAG,CAAC,KAAK,KAAK,CAAC;AAEf,UAAM,QAAQ,KAAK,MAAM,IAAI,CAAC,SAAS,KAAK,WAAW,IAAI,CAAC;AAC5D,WAAO,gBAAAC,OAAA,cAAAA,OAAA,gBAAG,KAAM;AAAA,EAClB;AAAA;AAAA,EAGQ,cAAc;AACpB,SAAK,WAAW,KAAK,WAAW;AAChC,QAAI,KAAK,aAAa,OAAO,kBAAkB;AAC7C,WAAK,WAAW;AAAA,IAClB;AAAA,EACF;AAAA,EAEQ,UAAU,MAA2C;AAC3D,UAAM,EAAE,SAAS,IAAI,KAAK,iBAAiB;AAC3C,UAAM,WAAW,KAAK,cAAc,WAAW,KAAK,EAAE;AACtD,UAAM,UAAU,KAAK,aAAa,UAAU,KAAK,EAAE;AACnD,UAAM,UAAU,KAAK,YAAY,IAAI;AAErC,WAAO;AAAA,MACL,KAAK,KAAK;AAAA,MACV,OAAO,KAAK;AAAA,MACZ;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA,cAAc,KAAK;AAAA,MACnB,kBAAkB,KAAK;AAAA,IACzB;AAAA,EACF;AAAA,EAEQ,YAAY,MAAkC;AACpD,UAAM,aAAa,KAAK,QAAQD,uBAAsB;AACtD,UAAM,EAAE,cAAc,IAAI;AAC1B,UAAM,WAAW,KAAK,cAAc,WAAW,KAAK,EAAE;AACtD,UAAM,UAAU,KAAK,aAAa,UAAU,KAAK,EAAE;AACnD,UAAM,EAAE,SAAS,aAAa,MAAM,IAAI;AAExC,UAAM,UAAU,KAAK,KAAK,QAAQ,OAAO,WAAW,OAAO,aAAa,MAAM,KAAK,MACjF,WAAW,MAAM,GACnB,MAAM,UAAU,MAAM,GAAG;AAEzB,WAAO;AAAA,EACT;AAAA,EAEQ,cAAc,OAAmC;AACvD,UAAM,mBAAmB,KAAK,QAAQ,qBAAqB,MAAM,gBAAAC,OAAA,cAAAA,OAAA,cAAE;AACnE,WACE,gBAAAA,OAAA,cAAC,sBAAoB,GAAG,SACtB,gBAAAA,OAAA,cAAC,oBAAkB,GAAG,OAAO,CAC/B;AAAA,EAEJ;AAAA,EAEQ,WAAW,MAAqC;AACtD,UAAM,YAAY,KAAK,UAAU,IAAI;AACrC,UAAM,QAAQ,KAAK,aAAa,IAAI,KAAK,EAAE;AAC3C,UAAM,WAAW,UAAU;AAC3B,UAAM,EAAE,QAAQ,cAAc,SAAS,cAAc,IAAI,SAAS,CAAC;AACnE,QAAI,YAAY,kBAAkB,UAAU,SAAS;AAEnD,aAAO;AAAA,IACT;AACA,QAAI,CAAC,UAAU;AAEb,WAAK,cAAc,YAAY,KAAK,IAAI;AACxC,WAAK,UAAU,MAAM;AACnB,aAAK,aAAa,OAAO,KAAK,EAAE;AAChC,aAAK,KAAK,OAAO;AAAA,MACnB,CAAC;AAAA,IACH;AAEA,UAAM,SAASC,UAAS,aAAa,KAAK,cAAc,SAAS,GAAG,KAAK,IAAI;AAC7E,SAAK,aAAa,IAAI,KAAK,IAAI,EAAE,MAAM,QAAQ,SAAS,UAAU,QAAQ,CAAC;AAC3E,WAAO;AAAA,EACT;AAAA,EAEA,IAAY,gBAA6B;AACvC,WAAO,KAAK,aAAa;AAAA,EAC3B;AACF;AAvKa,mBACJ,OAAO;AAEgB;AAAA,EAA7B,OAAOC,qBAAoB;AAAA,GAHjB,mBAGmB;AAEC;AAAA,EAA9B,OAAO,qBAAqB;AAAA,GALlB,mBAKoB;AAEC;AAAA,EAA/B,OAAO,sBAAsB;AAAA,GAPnB,mBAOqB;AAEF;AAAA,EAA7B,OAAO,oBAAoB;AAAA,GATjB,mBASmB;AAEgB;AAAA,EAA7C,gBAAgB,kBAAkB;AAAA,GAXxB,mBAWmC;AAEA;AAAA,EAA7C,gBAAgB,kBAAkB;AAAA,GAbxB,mBAamC;AAGrC;AAAA,EADR,mBAAmB,oBAAoB,aAAa;AAAA,GAf1C,mBAgBF;AAE2B;AAAA,EAAnC,OAAO,gBAAgB;AAAA,GAlBb,mBAkByB;AAlBzB,qBAAN;AAAA,EADN,WAAW;AAAA,GACC;;;AKvBb,SAAS,cAAc;AACvB,SAAiB,OAAO,iBAAiB;AAMzC,SAAS,gBAAgB;;;ACJzB,SAAS,iBAAiB,UAAkB,WAA2B;AACrE,MAAI,YAAY,GAAG;AACjB,WAAO,MAAM;AAAA,EACf;AAEA,SAAO,YAAY,KAAK,KAAK,KAAK,CAAC,QAAQ;AAC7C;AAEA,SAAS,wBAAwB;AAAA,EAC/B;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,GAOW;AACT,UAAQ,UAAU;AAAA,IAChB,KAAK;AACH,aAAO;AAAA,QACL,GAAG,KAAK,iBAAiB,KAAK,IAAI,SAAS;AAAA,QAC3C,GAAG;AAAA,MACL;AAAA,IACF,KAAK;AACH,aAAO;AAAA,QACL,GAAG,KAAK,iBAAiB,KAAK,IAAI,SAAS;AAAA,QAC3C,GAAG;AAAA,MACL;AAAA,IACF,KAAK;AACH,aAAO;AAAA,QACL,GAAG;AAAA,QACH,GAAG,KAAK,iBAAiB,KAAK,IAAI,SAAS;AAAA,MAC7C;AAAA,IACF,KAAK;AACH,aAAO;AAAA,QACL,GAAG;AAAA,QACH,GAAG,KAAK,iBAAiB,KAAK,IAAI,SAAS;AAAA,MAC7C;AAAA,EACJ;AACF;AAEO,SAAS,uBACd,SACA,OACA,YAAY,MACF;AACV,QAAM,cAAc,wBAAwB;AAAA,IAC1C,UAAU,QAAQ;AAAA,IAClB,IAAI,QAAQ;AAAA,IACZ,IAAI,QAAQ;AAAA,IACZ,IAAI,MAAM;AAAA,IACV,IAAI,MAAM;AAAA,IACV;AAAA,EACF,CAAC;AACD,QAAM,YAAY,wBAAwB;AAAA,IACxC,UAAU,MAAM;AAAA,IAChB,IAAI,MAAM;AAAA,IACV,IAAI,MAAM;AAAA,IACV,IAAI,QAAQ;AAAA,IACZ,IAAI,QAAQ;AAAA,IACZ;AAAA,EACF,CAAC;AACD,SAAO,CAAC,aAAa,SAAS;AAChC;;;ADnDO,IAAM,iCAAN,MAA+E;AAAA,EAKpF,YAAY,QAA4B;AACtC,SAAK,SAAS;AAAA,EAChB;AAAA,EAIA,IAAW,OAAe;AACxB,WAAO,KAAK,MAAM,QAAQ;AAAA,EAC5B;AAAA,EAEO,aAAa,KAAqB;AACvC,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,OAAO;AAAA,IAChB;AACA,WAAO,MAAM,YAAY,KAAK,KAAK,KAAK,OAAO,QAAQ,GAAG,CAAC;AAAA,EAC7D;AAAA,EAEA,IAAW,SAAoB;AAC7B,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,IAAI,UAAU;AAAA,IACvB;AACA,WAAO,KAAK,KAAK;AAAA,EACnB;AAAA,EAEO,OAAO,QAAwD;AACpE,SAAK,OAAO,KAAK,WAAW,OAAO,SAAS,OAAO,KAAK;AAAA,EAC1D;AAAA,EAEQ,WAAW,SAAoB,OAA8B;AACnE,UAAM,WAAW,uBAAuB,SAAS,OAAO,KAAK,OAAO,QAAQ,SAAS;AACrF,UAAM,SAAS,IAAI,OAAO,CAAC,SAAS,GAAG,UAAU,KAAK,CAAC;AACvD,UAAM,OAAO,OAAO,KAAK;AACzB,UAAM,aAAa,IAAI;AAAA,MACrB,KAAK,EAAE;AAAA,MACP,KAAK,EAAE;AAAA,MACP,KAAK,EAAE,MAAM,KAAK,EAAE;AAAA,MACpB,KAAK,EAAE,MAAM,KAAK,EAAE;AAAA,IACtB;AAEA,UAAM,OAAO,KAAK,QAAQ,EAAE,MAAM,YAAY,SAAS,OAAO,SAAS,CAAC;AAExE,SAAK,OAAO;AAAA,MACV;AAAA,MACA;AAAA,MACA;AAAA,MACA,MAAM;AAAA,MACN;AAAA,MACA;AAAA,IACF;AACA,WAAO,KAAK;AAAA,EACd;AAAA,EAEQ,QAAQ,QAKL;AACT,UAAM,EAAE,KAAK,IAAI;AAEjB,UAAM,aAAa,CAAC,OAAuB;AAAA,MACzC,GAAG,EAAE,IAAI,KAAK,IAAI;AAAA,MAClB,GAAG,EAAE,IAAI,KAAK,IAAI;AAAA,IACpB;AACA,UAAM,UAAU,WAAW,OAAO,OAAO;AACzC,UAAM,QAAQ,WAAW,OAAO,KAAK;AAErC,UAAM,WAAW,OAAO,SAAS,IAAI,CAAC,MAAM,WAAW,CAAC,CAAC;AACzD,UAAM,SAAS,KAAK,OAAO,QAAQ;AAEnC,UAAM,gBACJ,OAAO,QAAQ,aAAa,WACxB,EAAE,GAAG,QAAQ,GAAG,GAAG,QAAQ,IAAI,OAAO,IACtC,EAAE,GAAG,QAAQ,IAAI,QAAQ,GAAG,QAAQ,EAAE;AAE5C,UAAM,cACJ,OAAO,MAAM,aAAa,QACtB,EAAE,GAAG,MAAM,GAAG,GAAG,MAAM,IAAI,OAAO,IAClC,EAAE,GAAG,MAAM,IAAI,QAAQ,GAAG,MAAM,EAAE;AAExC,UAAM,gBAAgB,SAAS,IAAI,CAAC,MAAM,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,EAAE,EAAE,KAAK,GAAG;AACnE,WAAO,IAAI,cAAc,CAAC,IAAI,cAAc,CAAC,MAAM,aAAa,KAAK,YAAY,CAAC,IAAI,YAAY,CAAC;AAAA,EACrG;AACF;AAxFa,+BACG,OAAO,SAAS;;;AEtBhC,SAAiB,aAAAC,kBAAiB;AAClC;AAAA,EACE,gBAAAC;AAAA,OAIK;AACP,SAAS,YAAAC,iBAAgB;;;ACPzB,SAAsB,SAAAC,QAAO,aAAAC,kBAAiB;AAS9C,IAAM,4BAA4B,CAAC,OAAe,UAAkB,WAA2B;AAC7F,QAAM,EAAE,GAAG,IAAI,GAAG,GAAG,IAAI;AACzB,QAAM,EAAE,GAAG,IAAI,GAAG,GAAG,IAAI;AACzB,QAAM,EAAE,GAAG,IAAI,GAAG,GAAG,IAAI;AAEzB,QAAM,IAAI,KAAK;AACf,QAAM,IAAI,KAAK;AACf,QAAM,IAAI,KAAK;AACf,QAAM,IAAI,KAAK;AAEf,QAAM,MAAM,IAAI,IAAI,IAAI;AACxB,QAAM,QAAQ,IAAI,IAAI,IAAI;AAG1B,QAAM,QAAQ,UAAU,IAAI,KAAK,MAAM;AAEvC,MAAI;AACJ,MAAI;AAEJ,MAAI,QAAQ,GAAG;AACb,SAAK;AACL,SAAK;AAAA,EACP,WAAW,QAAQ,GAAG;AACpB,SAAK;AACL,SAAK;AAAA,EACP,OAAO;AACL,SAAK,KAAK,QAAQ;AAClB,SAAK,KAAK,QAAQ;AAAA,EACpB;AAEA,QAAM,KAAK,KAAK;AAChB,QAAM,KAAK,KAAK;AAEhB,SAAO,KAAK,KAAK,KAAK,KAAK,KAAK,EAAE;AACpC;AAOO,IAAU;AAAA,CAAV,CAAUC,cAAV;AACL,QAAM,cAAc;AACpB,QAAM,SAAS;AAEf,WAAS,cAAc,EAAE,QAAQ,OAAO,GAAyD;AAC/F,UAAM,UAAU,KAAK,IAAI,OAAO,IAAI,OAAO,CAAC,IAAI;AAChD,UAAM,UAAU,OAAO,IAAI,OAAO,IAAI,OAAO,IAAI,UAAU,OAAO,IAAI;AAEtE,UAAM,UAAU,KAAK,IAAI,OAAO,IAAI,OAAO,CAAC,IAAI;AAChD,UAAM,UAAU,OAAO,IAAI,OAAO,IAAI,OAAO,IAAI,UAAU,OAAO,IAAI;AAEtE,WAAO,CAAC,SAAS,OAAO;AAAA,EAC1B;AAEA,QAAM,eAAe,CAAC,EAAE,QAAQ,OAAO,MAAwD;AAC7F,QAAI,OAAO,aAAa,UAAU,OAAO,aAAa,SAAS;AAC7D,aAAO,OAAO,IAAI,OAAO,IAAI,EAAE,GAAG,GAAG,GAAG,EAAE,IAAI,EAAE,GAAG,IAAI,GAAG,EAAE;AAAA,IAC9D;AACA,WAAO,OAAO,IAAI,OAAO,IAAI,EAAE,GAAG,GAAG,GAAG,EAAE,IAAI,EAAE,GAAG,GAAG,GAAG,GAAG;AAAA,EAC9D;AAEA,QAAM,mBAAmB;AAAA,IACvB,MAAM,EAAE,GAAG,IAAI,GAAG,EAAE;AAAA,IACpB,OAAO,EAAE,GAAG,GAAG,GAAG,EAAE;AAAA,IACpB,KAAK,EAAE,GAAG,GAAG,GAAG,GAAG;AAAA,IACnB,QAAQ,EAAE,GAAG,GAAG,GAAG,EAAE;AAAA,EACvB;AAEO,WAAS,UAAU;AAAA,IACxB;AAAA,IACA;AAAA,EACF,GAGa;AACX,UAAM,YAAY,iBAAiB,OAAO,QAAQ;AAClD,UAAM,YAAY,iBAAiB,OAAO,QAAQ;AAClD,UAAM,eAA0B;AAAA,MAC9B,GAAG,OAAO,IAAI,UAAU,IAAI;AAAA,MAC5B,GAAG,OAAO,IAAI,UAAU,IAAI;AAAA,MAC5B,UAAU,OAAO;AAAA,IACnB;AACA,UAAM,eAA0B;AAAA,MAC9B,GAAG,OAAO,IAAI,UAAU,IAAI;AAAA,MAC5B,GAAG,OAAO,IAAI,UAAU,IAAI;AAAA,MAC5B,UAAU,OAAO;AAAA,IACnB;AACA,UAAM,MAAM,aAAa;AAAA,MACvB,QAAQ;AAAA,MACR,QAAQ;AAAA,IACV,CAAC;AACD,UAAM,cAAc,IAAI,MAAM,IAAI,MAAM;AACxC,UAAM,UAAU,IAAI,WAAW;AAE/B,QAAI,SAAmB,CAAC;AACxB,QAAI,SAAS;AAEb,UAAM,CAAC,gBAAgB,cAAc,IAAI,cAAc;AAAA,MACrD;AAAA,MACA;AAAA,IACF,CAAC;AAGD,QAAI,UAAU,WAAW,IAAI,UAAU,WAAW,MAAM,IAAI;AAC1D,gBAAU;AACV,gBAAU;AAEV,YAAM,gBAA0B;AAAA,QAC9B,EAAE,GAAG,SAAS,GAAG,aAAa,EAAE;AAAA,QAChC,EAAE,GAAG,SAAS,GAAG,aAAa,EAAE;AAAA,MAClC;AAEA,YAAM,kBAA4B;AAAA,QAChC,EAAE,GAAG,aAAa,GAAG,GAAG,QAAQ;AAAA,QAChC,EAAE,GAAG,aAAa,GAAG,GAAG,QAAQ;AAAA,MAClC;AAEA,UAAI,UAAU,WAAW,MAAM,SAAS;AACtC,iBAAS,gBAAgB,MAAM,gBAAgB;AAAA,MACjD,OAAO;AACL,iBAAS,gBAAgB,MAAM,kBAAkB;AAAA,MACnD;AAAA,IACF,OAAO;AAEL,YAAM,eAAyB,CAAC,EAAE,GAAG,aAAa,GAAG,GAAG,aAAa,EAAE,CAAC;AACxE,YAAM,eAAyB,CAAC,EAAE,GAAG,aAAa,GAAG,GAAG,aAAa,EAAE,CAAC;AAExE,UAAI,gBAAgB,KAAK;AACvB,iBAAS,UAAU,MAAM,UAAU,eAAe;AAAA,MACpD,OAAO;AACL,iBAAS,UAAU,MAAM,UAAU,eAAe;AAAA,MACpD;AAGA,YAAM,sBAAsB,gBAAgB,MAAM,MAAM;AACxD,YAAM,YAAY,UAAU,WAAW,MAAM,UAAU,mBAAmB;AAC1E,YAAM,qBACJ,aAAa,mBAAmB,IAAI,aAAa,mBAAmB;AACtE,YAAM,qBACJ,aAAa,mBAAmB,IAAI,aAAa,mBAAmB;AACtE,YAAM,mBACH,UAAU,WAAW,MAAM,MACxB,CAAC,aAAa,sBAAwB,aAAa,uBACtD,UAAU,WAAW,MAAM,MACxB,CAAC,aAAa,sBAAwB,aAAa;AAEzD,UAAI,kBAAkB;AACpB,iBAAS,gBAAgB,MAAM,eAAe;AAAA,MAChD;AAEA,YAAM,iBAAiB,EAAE,GAAG,aAAa,GAAG,GAAG,aAAa,EAAE;AAC9D,YAAM,iBAAiB,EAAE,GAAG,aAAa,GAAG,GAAG,aAAa,EAAE;AAC9D,YAAM,eAAe,KAAK;AAAA,QACxB,KAAK,IAAI,eAAe,IAAI,OAAO,CAAC,EAAE,CAAC;AAAA,QACvC,KAAK,IAAI,eAAe,IAAI,OAAO,CAAC,EAAE,CAAC;AAAA,MACzC;AACA,YAAM,eAAe,KAAK;AAAA,QACxB,KAAK,IAAI,eAAe,IAAI,OAAO,CAAC,EAAE,CAAC;AAAA,QACvC,KAAK,IAAI,eAAe,IAAI,OAAO,CAAC,EAAE,CAAC;AAAA,MACzC;AAEA,UAAI,gBAAgB,cAAc;AAChC,mBAAW,eAAe,IAAI,eAAe,KAAK;AAClD,kBAAU,OAAO,CAAC,EAAE;AAAA,MACtB,OAAO;AACL,kBAAU,OAAO,CAAC,EAAE;AACpB,mBAAW,eAAe,IAAI,eAAe,KAAK;AAAA,MACpD;AAAA,IACF;AAEA,UAAM,aAAa;AAAA,MACjB;AAAA,MACA,EAAE,GAAG,aAAa,GAAG,GAAG,aAAa,EAAE;AAAA,MACvC,GAAG;AAAA,MACH,EAAE,GAAG,aAAa,GAAG,GAAG,aAAa,EAAE;AAAA,MACvC;AAAA,IACF;AAEA,WAAO;AAAA,EACT;AA/GO,EAAAA,UAAS;AAiHhB,WAAS,QAAQ,GAAW,GAAW,GAAmB;AACxD,UAAM,WAAW,KAAK;AAAA,MACpBF,OAAM,YAAY,GAAG,CAAC,IAAI;AAAA,MAC1BA,OAAM,YAAY,GAAG,CAAC,IAAI;AAAA,MAC1B;AAAA,IACF;AACA,UAAM,EAAE,GAAG,EAAE,IAAI;AAGjB,QAAK,EAAE,MAAM,KAAK,MAAM,EAAE,KAAO,EAAE,MAAM,KAAK,MAAM,EAAE,GAAI;AACxD,aAAO,IAAI,CAAC,IAAI,CAAC;AAAA,IACnB;AAGA,QAAI,EAAE,MAAM,GAAG;AACb,YAAMG,QAAO,EAAE,IAAI,EAAE,IAAI,KAAK;AAC9B,YAAMC,QAAO,EAAE,IAAI,EAAE,IAAI,IAAI;AAC7B,aAAO,KAAK,IAAI,WAAWD,KAAI,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,IAAI,WAAWC,KAAI;AAAA,IAC7E;AAEA,UAAM,OAAO,EAAE,IAAI,EAAE,IAAI,IAAI;AAC7B,UAAM,OAAO,EAAE,IAAI,EAAE,IAAI,KAAK;AAC9B,WAAO,KAAK,CAAC,IAAI,IAAI,WAAW,IAAI,KAAK,CAAC,IAAI,CAAC,IAAI,IAAI,WAAW,IAAI,IAAI,CAAC;AAAA,EAC7E;AAKO,WAAS,kBAAkB,QAA0B;AAC1D,UAAM,OAAO,OAAO,OAAe,CAAC,KAAK,GAAG,MAAM;AAChD,UAAI,UAAU;AAEd,UAAI,IAAI,KAAK,IAAI,OAAO,SAAS,GAAG;AAClC,kBAAU,QAAQ,OAAO,IAAI,CAAC,GAAG,GAAG,OAAO,IAAI,CAAC,CAAC;AAAA,MACnD,OAAO;AACL,kBAAU,GAAG,MAAM,IAAI,MAAM,GAAG,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC;AAAA,MAC/C;AAEA,aAAO;AAEP,aAAO;AAAA,IACT,GAAG,EAAE;AAEL,WAAO;AAAA,EACT;AAhBO,EAAAF,UAAS;AAiBT,WAAS,UAAU,QAA6B;AACrD,UAAM,QAAQ,OAAO,IAAI,CAAC,MAAM,EAAE,CAAC;AACnC,UAAM,QAAQ,OAAO,IAAI,CAAC,MAAM,EAAE,CAAC;AACnC,UAAM,OAAO,KAAK,IAAI,GAAG,KAAK;AAC9B,UAAM,QAAQ,KAAK,IAAI,GAAG,KAAK;AAC/B,UAAM,MAAM,KAAK,IAAI,GAAG,KAAK;AAC7B,UAAM,SAAS,KAAK,IAAI,GAAG,KAAK;AAChC,WAAOD,WAAU;AAAA,MACf;AAAA,QACE,GAAG;AAAA,QACH,GAAG;AAAA,MACL;AAAA,MACA;AAAA,QACE,GAAG;AAAA,QACH,GAAG;AAAA,MACL;AAAA,IACF;AAAA,EACF;AAjBO,EAAAC,UAAS;AAwBT,EAAMA,UAAA,6BAA6B,CAAC,QAAkB,QAAwB;AAEnF,QAAI,OAAO,WAAW,GAAG;AACvB,aAAO;AAAA,IACT;AAEA,QAAI,OAAO,WAAW,GAAG;AACvB,aAAOF,OAAM,YAAY,OAAO,CAAC,GAAI,GAAG;AAAA,IAC1C;AAGA,UAAM,QAA4B,CAAC;AACnC,aAAS,IAAI,GAAG,IAAI,OAAO,SAAS,GAAG,KAAK;AAC1C,YAAM,KAAK,CAAC,OAAO,CAAC,GAAI,OAAO,IAAI,CAAC,CAAE,CAAC;AAAA,IACzC;AAGA,UAAM,YAAY,MAAM,IAAI,CAAC,SAAS;AACpC,YAAM,CAAC,IAAI,EAAE,IAAI;AACjB,aAAO,0BAA0B,KAAK,IAAI,EAAE;AAAA,IAC9C,CAAC;AAED,WAAO,KAAK,IAAI,GAAG,SAAS;AAAA,EAC9B;AAAA,GAzOe;;;ADhCV,IAAM,+BAAN,MAA6E;AAAA,EAKlF,YAAY,QAA4B;AACtC,SAAK,SAAS;AAAA,EAChB;AAAA,EAIA,IAAW,OAAe;AACxB,WAAO,KAAK,MAAM,QAAQ;AAAA,EAC5B;AAAA,EAEO,aAAa,KAAqB;AACvC,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,OAAO;AAAA,IAChB;AACA,WAAO,SAAS,2BAA2B,KAAK,KAAK,QAAQ,GAAG;AAAA,EAClE;AAAA,EAEA,IAAW,SAAoB;AAC7B,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,IAAIK,WAAU;AAAA,IACvB;AACA,WAAO,KAAK,KAAK;AAAA,EACnB;AAAA,EAEO,OAAO,QAAwD;AACpE,UAAM,EAAE,SAAS,MAAM,IAAI;AAG3B,UAAM,eAAe;AAAA,MACnB,GAAG,QAAQ,aAAa,WAAW,IAAIC;AAAA,MACvC,GAAG,QAAQ,aAAa,WAAWA,gBAAe;AAAA,IACpD;AACA,UAAM,eAAe;AAAA,MACnB,GAAG,MAAM,aAAa,QAAQ,IAAI,CAACA;AAAA,MACnC,GAAG,MAAM,aAAa,QAAQ,CAACA,gBAAe;AAAA,IAChD;AAEA,UAAM,SAAS,SAAS,UAAU;AAAA,MAChC,QAAQ;AAAA,QACN,GAAG,QAAQ,IAAI,aAAa;AAAA,QAC5B,GAAG,QAAQ,IAAI,aAAa;AAAA,QAC5B,UAAU,QAAQ;AAAA,MACpB;AAAA,MACA,QAAQ;AAAA,QACN,GAAG,MAAM,IAAI,aAAa;AAAA,QAC1B,GAAG,MAAM,IAAI,aAAa;AAAA,QAC1B,UAAU,MAAM;AAAA,MAClB;AAAA,IACF,CAAC;AAED,UAAM,OAAO,SAAS,UAAU,MAAM;AAGtC,UAAM,iBAAiB,OAAO,IAAI,CAAC,OAAO;AAAA,MACxC,GAAG,EAAE,IAAI,KAAK,IAAI;AAAA,MAClB,GAAG,EAAE,IAAI,KAAK,IAAI;AAAA,IACpB,EAAE;AAEF,UAAM,OAAO,SAAS,kBAAkB,cAAc;AAEtD,SAAK,OAAO;AAAA,MACV;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AACF;AAvEa,6BACG,OAAOC,UAAS;;;AEnBhC,SAAiB,SAAAC,QAAO,aAAAC,kBAAiB;AACzC;AAAA,EACE,gBAAAC;AAAA,OAIK;;;ACKA,SAAS,mBAAmB,OAAe,WAAmB,SAAyB;AAC5F,QAAM,KAAK,QAAQ,IAAI,UAAU;AACjC,QAAM,KAAK,QAAQ,IAAI,UAAU;AAGjC,MAAI,OAAO,GAAG;AACZ,WAAO,EAAE,GAAG,UAAU,GAAG,GAAG,MAAM,EAAE;AAAA,EACtC;AAEA,MAAI,OAAO,GAAG;AACZ,WAAO,EAAE,GAAG,MAAM,GAAG,GAAG,UAAU,EAAE;AAAA,EACtC;AAEA,QAAM,MAAM,MAAM,IAAI,UAAU,KAAK,MAAM,MAAM,IAAI,UAAU,KAAK,OAAO,KAAK,KAAK,KAAK;AAC1F,QAAM,WAAW,KAAK,IAAI,GAAG,KAAK,IAAI,GAAG,CAAC,CAAC;AAE3C,SAAO;AAAA,IACL,GAAG,UAAU,IAAI,WAAW;AAAA,IAC5B,GAAG,UAAU,IAAI,WAAW;AAAA,EAC9B;AACF;;;ADdO,IAAM,mCAAN,MAAiF;AAAA,EAKtF,YAAY,QAA4B;AACtC,SAAK,SAAS;AAAA,EAChB;AAAA,EAIA,IAAW,OAAe;AACxB,WAAO,KAAK,MAAM,QAAQ;AAAA,EAC5B;AAAA,EAEO,aAAa,KAAqB;AACvC,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,OAAO;AAAA,IAChB;AACA,UAAM,CAAC,OAAO,GAAG,IAAI,KAAK,KAAK;AAC/B,WAAOC,OAAM,YAAY,KAAK,mBAAmB,KAAK,OAAO,GAAG,CAAC;AAAA,EACnE;AAAA,EAEA,IAAW,SAAoB;AAC7B,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,IAAIC,WAAU;AAAA,IACvB;AACA,WAAO,KAAK,KAAK;AAAA,EACnB;AAAA,EAEO,OAAO,QAAwD;AACpE,UAAM,EAAE,SAAS,MAAM,IAAI;AAG3B,UAAM,eAAe;AAAA,MACnB,GAAG,QAAQ,aAAa,WAAW,IAAIC;AAAA,MACvC,GAAG,QAAQ,aAAa,WAAWA,gBAAe;AAAA,IACpD;AACA,UAAM,eAAe;AAAA,MACnB,GAAG,MAAM,aAAa,QAAQ,IAAI,CAACA;AAAA,MACnC,GAAG,MAAM,aAAa,QAAQ,CAACA,gBAAe;AAAA,IAChD;AAEA,UAAM,SAAS;AAAA,MACb;AAAA,QACE,GAAG,QAAQ,IAAI,aAAa;AAAA,QAC5B,GAAG,QAAQ,IAAI,aAAa;AAAA,MAC9B;AAAA,MACA;AAAA,QACE,GAAG,MAAM,IAAI,aAAa;AAAA,QAC1B,GAAG,MAAM,IAAI,aAAa;AAAA,MAC5B;AAAA,IACF;AAEA,UAAM,OAAOD,WAAU,6BAA6B,OAAO,CAAC,GAAG,OAAO,CAAC,CAAC;AAGxE,UAAM,iBAAiB,OAAO,IAAI,CAAC,OAAO;AAAA,MACxC,GAAG,EAAE,IAAI,KAAK,IAAI;AAAA,MAClB,GAAG,EAAE,IAAI,KAAK,IAAI;AAAA,IACpB,EAAE;AAGF,UAAM,OAAO,KAAK,eAAe,CAAC,EAAE,CAAC,IAAI,eAAe,CAAC,EAAE,CAAC,MAAM,eAAe,CAAC,EAAE,CAAC,IAAI,eAAe,CAAC,EAAE,CAAC;AAE5G,SAAK,OAAO;AAAA,MACV;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AACF;AAvEa,iCACG,OAAO;;;AElBvB,SAAiB,SAAAE,QAAO,aAAAC,kBAAiB;AACzC;AAAA,EACE,gBAAAC;AAAA,OAGK;AAWA,IAAM,8BAAN,MAA4E;AAAA,EAKjF,YAAY,QAA4B;AACtC,SAAK,SAAS;AAAA,EAChB;AAAA,EAIA,IAAW,OAAe;AACxB,WAAO,KAAK,MAAM,QAAQ;AAAA,EAC5B;AAAA,EAEO,aAAa,KAAqB;AACvC,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,OAAO;AAAA,IAChB;AAEA,UAAM,EAAE,SAAS,OAAO,KAAK,IAAI,KAAK;AAGtC,QAAI,CAAC,KAAK,SAAS,IAAI,GAAG,IAAI,CAAC,GAAG;AAEhC,YAAM,KAAK,KAAK,IAAI,KAAK,IAAI,IAAI,GAAG,GAAG,IAAI,KAAK,KAAK,IAAI,KAAK,MAAM;AACpE,YAAM,KAAK,KAAK,IAAI,KAAK,IAAI,IAAI,GAAG,GAAG,IAAI,KAAK,KAAK,IAAI,KAAK,OAAO;AACrE,aAAO,KAAK,KAAK,KAAK,KAAK,KAAK,EAAE;AAAA,IACpC;AAGA,UAAM,SAAS;AAAA,MACb,IAAI,QAAQ,IAAI,MAAM,KAAK;AAAA,MAC3B,IAAI,QAAQ,IAAI,MAAM,KAAK;AAAA,IAC7B;AACA,UAAM,SAASC,OAAM,YAAY,SAAS,MAAM;AAGhD,UAAM,mBAAmBA,OAAM,YAAY,KAAK,MAAM;AAGtD,WAAO,KAAK,IAAI,mBAAmB,MAAM;AAAA,EAC3C;AAAA,EAEA,IAAW,SAAoB;AAC7B,QAAI,CAAC,KAAK,MAAM;AACd,aAAO,IAAIC,WAAU;AAAA,IACvB;AACA,WAAO,KAAK,KAAK;AAAA,EACnB;AAAA,EAEO,OAAO,QAAkD;AAC9D,UAAM,EAAE,SAAS,MAAM,IAAI;AAC3B,UAAM,EAAE,SAAS,IAAI,KAAK;AAE1B,UAAM,eAAe;AAAA,MACnB,GAAG,WAAW,IAAIC;AAAA,MAClB,GAAG,WAAWA,gBAAe;AAAA,IAC/B;AACA,UAAM,eAAe;AAAA,MACnB,GAAG,WAAW,IAAI,CAACA;AAAA,MACnB,GAAG,WAAW,CAACA,gBAAe;AAAA,IAChC;AAEA,UAAM,QAAQ;AAAA,MACZ,GAAG,QAAQ,IAAI,aAAa;AAAA,MAC5B,GAAG,QAAQ,IAAI,aAAa;AAAA,IAC9B;AACA,UAAM,MAAM;AAAA,MACV,GAAG,MAAM,IAAI,aAAa;AAAA,MAC1B,GAAG,MAAM,IAAI,aAAa;AAAA,IAC5B;AAGA,UAAM,OAAO,KAAK,iBAAiB,OAAO,GAAG;AAG7C,UAAM,OAAO,KAAK,WAAW,OAAO,KAAK,IAAI;AAE7C,SAAK,OAAO;AAAA,MACV,SAAS;AAAA,MACT,OAAO;AAAA,MACP;AAAA,MACA;AAAA,IACF;AAAA,EACF;AAAA,EAEQ,iBAAiB,OAAe,KAAwB;AAC9D,UAAM,KAAK,IAAI,IAAI,MAAM;AACzB,UAAM,KAAK,IAAI,IAAI,MAAM;AACzB,UAAM,SAAS,KAAK,KAAK,KAAK,KAAK,KAAK,EAAE,IAAI;AAE9C,UAAM,WAAW,MAAM,IAAI,IAAI,KAAK;AACpC,UAAM,WAAW,MAAM,IAAI,IAAI,KAAK;AAEpC,WAAO,IAAID,WAAU,UAAU,QAAQ,UAAU,QAAQ,SAAS,GAAG,SAAS,CAAC;AAAA,EACjF;AAAA,EAEQ,WAAW,OAAe,KAAa,MAAyB;AACtE,UAAM,KAAK,IAAI,IAAI,MAAM;AACzB,UAAM,KAAK,IAAI,IAAI,MAAM;AACzB,UAAM,WAAW,KAAK,KAAK,KAAK,KAAK,KAAK,EAAE;AAG5C,UAAM,WAAW;AAAA,MACf,GAAG,MAAM,IAAI,KAAK,IAAI;AAAA,MACtB,GAAG,MAAM,IAAI,KAAK,IAAI;AAAA,IACxB;AACA,UAAM,SAAS;AAAA,MACb,GAAG,IAAI,IAAI,KAAK,IAAI;AAAA,MACpB,GAAG,IAAI,IAAI,KAAK,IAAI;AAAA,IACtB;AAGA,WAAO,KAAK,SAAS,CAAC,IAAI,SAAS,CAAC,MAAM,WAAW,CAAC,IAAI,WAAW,CAAC,UAAU,OAAO,CAAC,IACtF,OAAO,CACT;AAAA,EACF;AACF;AAtHa,4BACG,OAAO;;;AZVhB,IAAM,wBAAwB,oBAAoB;AAAA,EACvD,WAAW;AAAA,EACX,QAAQ,CAAC,KAAoB,SAAiC;AAC5D,QAAI,WAAW,cAAc,oBAAoB;AAAA,MAC/C,GAAG;AAAA,IACL,CAAC;AAAA,EACH;AAAA,EACA,SAAS,CAAC,KAAoB,SAAiC;AAC7D,UAAM,eAAe,IAAI,UAAU,IAAIE,qBAAoB;AAC3D,iBACG,qBAAqB,8BAA8B,EACnD,qBAAqB,4BAA4B;AAEpD,QAAI,KAAK,eAAe;AACtB,WAAK,cAAc,QAAQ,CAAC,iBAAiB;AAC3C,qBAAa,qBAAqB,YAAY;AAAA,MAChD,CAAC;AAAA,IACH;AAEA,QAAI,KAAK,iBAAiB;AACxB,mBAAa,eAAe,KAAK,eAAe;AAAA,IAClD;AAAA,EACF;AACF,CAAC;","names":["React","React","WorkflowLinesManager","ReactDOM","React","useState","WorkflowHoverService","WorkflowLineRenderData","React","styled","React","React","React","useState","WorkflowLineRenderData","React","ReactDOM","WorkflowHoverService","Rectangle","POINT_RADIUS","LineType","Point","Rectangle","FoldLine","xDir","yDir","Rectangle","POINT_RADIUS","LineType","Point","Rectangle","POINT_RADIUS","Point","Rectangle","POINT_RADIUS","Point","Rectangle","POINT_RADIUS","Point","Rectangle","POINT_RADIUS","WorkflowLinesManager"]}
|
|
1
|
+
{"version":3,"sources":["../../src/components/workflow-port-render/index.tsx","../../src/constants/points.ts","../../src/components/workflow-port-render/style.ts","../../src/components/workflow-port-render/cross-hair.tsx","../../src/constants/lines.ts","../../src/create-free-lines-plugin.ts","../../src/layer/workflow-lines-layer.tsx","../../src/components/workflow-line-render/index.tsx","../../src/components/workflow-line-render/line-svg.tsx","../../src/components/workflow-line-render/index.style.ts","../../src/components/workflow-line-render/arrow.tsx","../../src/contributions/bezier/index.ts","../../src/contributions/bezier/bezier-controls.ts","../../src/contributions/fold/index.ts","../../src/contributions/fold/fold-line.ts","../../src/contributions/straight/index.ts","../../src/contributions/straight/point-on-line.ts","../../src/contributions/arc/index.ts"],"sourcesContent":["/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { useEffect, useState } from 'react';\n\nimport classNames from 'clsx';\nimport {\n WorkflowHoverService,\n type WorkflowPortEntity,\n usePlaygroundReadonlyState,\n WorkflowLinesManager,\n} from '@flowgram.ai/free-layout-core';\nimport { MouseTouchEvent, useService } from '@flowgram.ai/core';\n\nimport { PORT_BG_CLASS_NAME } from '../../constants/points';\nimport { WorkflowPointStyle } from './style';\nimport CrossHair from './cross-hair';\n\nexport interface WorkflowPortRenderProps {\n entity: WorkflowPortEntity;\n className?: string;\n style?: React.CSSProperties;\n onClick?: (e: React.MouseEvent<HTMLDivElement>, port: WorkflowPortEntity) => void;\n /** 激活状态颜色 (linked/hovered) */\n primaryColor?: string;\n /** 默认状态颜色 */\n secondaryColor?: string;\n /** 错误状态颜色 */\n errorColor?: string;\n /** 背景颜色 */\n backgroundColor?: string;\n}\n\nexport const WorkflowPortRender: React.FC<WorkflowPortRenderProps> =\n // eslint-disable-next-line react/display-name\n React.memo<WorkflowPortRenderProps>((props: WorkflowPortRenderProps) => {\n const hoverService = useService<WorkflowHoverService>(WorkflowHoverService);\n const linesManager = useService<WorkflowLinesManager>(WorkflowLinesManager);\n const { entity, onClick } = props;\n const { portType, relativePosition, disabled } = entity;\n const [targetElement, setTargetElement] = useState(entity.targetElement);\n const [posX, updatePosX] = useState(relativePosition.x);\n const [posY, updatePosY] = useState(relativePosition.y);\n const [hovered, setHovered] = useState(false);\n const [linked, setLinked] = useState(Boolean(entity?.lines?.length));\n const [hasError, setHasError] = useState(props.entity.hasError);\n const readonly = usePlaygroundReadonlyState();\n\n useEffect(() => {\n // useEffect 时序问题可能导致 port.hasError 非最新,需重新触发一次 validate\n entity.validate();\n setHasError(entity.hasError);\n const dispose = entity.onEntityChange(() => {\n // 如果有挂载的节点,不需要更新位置信息\n if (entity.targetElement) {\n if (entity.targetElement !== targetElement) {\n setTargetElement(entity.targetElement);\n }\n return;\n }\n const newPos = entity.relativePosition;\n // 加上 round 避免点位抖动\n updatePosX(Math.round(newPos.x));\n updatePosY(Math.round(newPos.y));\n });\n const dispose2 = hoverService.onHoveredChange((id) => {\n setHovered(hoverService.isHovered(entity.id));\n });\n const dispose3 = entity.onErrorChanged(() => {\n setHasError(entity.hasError);\n });\n const dispose4 = linesManager.onAvailableLinesChange(() => {\n setTimeout(() => {\n if (linesManager.disposed || entity.disposed) return;\n setLinked(Boolean(entity.lines.length));\n }, 0);\n });\n return () => {\n dispose.dispose();\n dispose2.dispose();\n dispose3.dispose();\n dispose4.dispose();\n };\n }, [hoverService, entity, targetElement]);\n\n // 监听变化\n const className = classNames('workflow-port-render', props.className || '', {\n hovered: !readonly && hovered && !disabled && portType !== 'input',\n // 有线条链接的时候深蓝色小圆点\n linked,\n });\n\n // 构建 CSS 自定义属性用于颜色覆盖\n const colorStyles: Record<string, string> = {};\n if (props.primaryColor) {\n colorStyles['--g-workflow-port-color-primary'] = props.primaryColor;\n }\n if (props.secondaryColor) {\n colorStyles['--g-workflow-port-color-secondary'] = props.secondaryColor;\n }\n if (props.errorColor) {\n colorStyles['--g-workflow-port-color-error'] = props.errorColor;\n }\n if (props.backgroundColor) {\n colorStyles['--g-workflow-port-color-background'] = props.backgroundColor;\n }\n\n const combinedStyle = targetElement\n ? { ...props.style, ...colorStyles }\n : { ...props.style, ...colorStyles, left: posX, top: posY };\n\n const content = (\n <WorkflowPointStyle\n className={className}\n style={combinedStyle}\n onClick={(e) => onClick?.(e, entity)}\n onTouchStart={(e) => {\n if (!onClick) {\n return;\n }\n MouseTouchEvent.onTouched(e, (mouseEvent) => {\n onClick(mouseEvent as unknown as React.MouseEvent<HTMLDivElement>, entity);\n });\n }}\n data-port-entity-id={entity.id}\n data-port-entity-type={entity.portType}\n data-testid=\"sdk.workflow.canvas.node.port\"\n >\n <div className={classNames('bg-circle', 'workflow-bg-circle')}></div>\n <div\n className={classNames({\n bg: true,\n [PORT_BG_CLASS_NAME]: true,\n 'workflow-point-bg': true,\n hasError,\n })}\n >\n <CrossHair />\n </div>\n <div className=\"focus-circle\" />\n </WorkflowPointStyle>\n );\n if (targetElement) {\n return ReactDOM.createPortal(content, targetElement);\n }\n return content;\n });\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 连接点半径\n\nexport const STROKE_WIDTH_SLECTED = 3;\n\nexport const STROKE_WIDTH = 2;\n\nexport const PORT_BG_CLASS_NAME = 'workflow-port-bg';\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\nexport const WorkflowPointStyle = styled.div`\n width: 20px;\n height: 20px;\n border-radius: 50%;\n margin-top: -10px;\n margin-left: -10px;\n left: 50%;\n top: 50%;\n position: absolute;\n // 非 hover 状态下的样式\n border: none;\n\n & > .symbol {\n opacity: 0;\n }\n\n .bg-circle {\n display: flex;\n align-items: center;\n justify-content: center;\n position: absolute;\n border-radius: 50%;\n width: 20px;\n height: 20px;\n background-color: var(--g-workflow-port-color-background, #fff);\n transform: scale(0.5);\n transition: all 0.2s linear 0s;\n }\n\n .bg {\n display: flex;\n align-items: center;\n justify-content: center;\n position: relative;\n width: 100%;\n height: 100%;\n border-radius: 50%;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n transform: scale(0.4, 0.4);\n transition: all 0.2s linear 0s;\n\n &.hasError {\n background: var(--g-workflow-port-color-error, red);\n }\n\n .symbol {\n position: absolute;\n width: 14px;\n height: 14px;\n opacity: 0;\n pointer-events: none;\n color: var(--g-workflow-port-color-background, #fff);\n transition: opacity 0.2s linear 0s;\n\n & > svg {\n width: 14px;\n height: 14px;\n }\n }\n\n .focus-circle {\n position: absolute;\n display: flex;\n justify-content: center;\n align-items: center;\n width: 8px;\n height: 8px;\n opacity: 0;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n border-radius: 50%;\n transition: opacity 0.2s linear 0s;\n }\n }\n\n &.linked .bg:not(.hasError) {\n background: var(--g-workflow-port-color-primary, #4d53e8);\n }\n\n &.hovered .bg:not(.hasError) {\n border: none;\n cursor: crosshair;\n transform: scale(1, 1);\n background: var(--g-workflow-port-color-primary, #4d53e8);\n\n & > .symbol {\n opacity: 1;\n }\n }\n\n .cross-hair {\n position: relative;\n left: 2px;\n top: 2px;\n\n &::after,\n &::before {\n content: '';\n background: var(--g-workflow-port-color-background, #fff);\n border-radius: 2px;\n position: absolute;\n }\n\n &::after {\n left: 4px;\n width: 2px;\n height: 6px;\n box-shadow: 0 4px var(--g-workflow-port-color-background, #fff);\n }\n\n &::before {\n top: 4px;\n width: 6px;\n height: 2px;\n box-shadow: 4px 0 var(--g-workflow-port-color-background, #fff);\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\n// demo 环境自绘 cross-hair,正式环境使用 IconAdd\nexport default function CrossHair(): JSX.Element {\n return (\n <div className=\"symbol\">\n <div className=\"cross-hair\" />\n </div>\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 箭头宽度\nexport const LINE_OFFSET = 6;\n\nexport const LINE_PADDING = 12;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { WorkflowLinesManager } from '@flowgram.ai/free-layout-core';\nimport { definePluginCreator, PluginContext } from '@flowgram.ai/core';\n\nimport { FreeLinesPluginOptions } from './type';\nimport { WorkflowLinesLayer } from './layer';\nimport { WorkflowBezierLineContribution, WorkflowFoldLineContribution } from './contributions';\n\nexport const createFreeLinesPlugin = definePluginCreator({\n singleton: true,\n onInit: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n ctx.playground.registerLayer(WorkflowLinesLayer, {\n ...opts,\n });\n },\n onReady: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n const linesManager = ctx.container.get(WorkflowLinesManager);\n linesManager\n .registerContribution(WorkflowBezierLineContribution)\n .registerContribution(WorkflowFoldLineContribution);\n\n if (opts.contributions) {\n opts.contributions.forEach((contribution) => {\n linesManager.registerContribution(contribution);\n });\n }\n\n if (opts.defaultLineType) {\n linesManager.switchLineType(opts.defaultLineType);\n }\n },\n});\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { ReactNode, useLayoutEffect, useState } from 'react';\n\nimport { inject, injectable } from 'inversify';\nimport { domUtils } from '@flowgram.ai/utils';\nimport { FlowRendererRegistry } from '@flowgram.ai/renderer';\nimport { StackingContextManager } from '@flowgram.ai/free-stack-plugin';\nimport {\n nanoid,\n WorkflowDocument,\n WorkflowHoverService,\n WorkflowLineEntity,\n WorkflowLineRenderData,\n WorkflowNodeEntity,\n WorkflowPortEntity,\n WorkflowSelectService,\n} from '@flowgram.ai/free-layout-core';\nimport { Layer, observeEntities, observeEntityDatas, TransformData } from '@flowgram.ai/core';\n\nimport { LineRenderProps, LinesLayerOptions } from '../type';\nimport { WorkflowLineRender } from '../components';\n\n@injectable()\nexport class WorkflowLinesLayer extends Layer<LinesLayerOptions> {\n static type = 'WorkflowLinesLayer';\n\n @inject(WorkflowHoverService) hoverService: WorkflowHoverService;\n\n @inject(WorkflowSelectService) selectService: WorkflowSelectService;\n\n @inject(StackingContextManager) stackContext: StackingContextManager;\n\n @inject(FlowRendererRegistry) rendererRegistry: FlowRendererRegistry;\n\n @observeEntities(WorkflowLineEntity) readonly lines: WorkflowLineEntity[];\n\n @observeEntities(WorkflowPortEntity) readonly ports: WorkflowPortEntity[];\n\n @observeEntityDatas(WorkflowNodeEntity, TransformData)\n readonly trans: TransformData[];\n\n @inject(WorkflowDocument) protected workflowDocument: WorkflowDocument;\n\n private layerID = nanoid();\n\n private mountedLines: Map<\n string,\n {\n line: WorkflowLineEntity;\n portal: ReactNode;\n version: string;\n }\n > = new Map();\n\n private _version = 0;\n\n /**\n * 节点线条\n */\n public node = domUtils.createDivWithClass('gedit-playground-layer gedit-flow-lines-layer');\n\n public onZoom(scale: number): void {\n this.node.style.transform = `scale(${scale})`;\n }\n\n public onReady() {\n this.pipelineNode.appendChild(this.node);\n this.toDispose.pushAll([\n this.selectService.onSelectionChanged(() => this.render()),\n this.hoverService.onHoveredChange(() => this.render()),\n this.workflowDocument.linesManager.onForceUpdate(() => {\n this.mountedLines.clear();\n this.bumpVersion();\n this.render();\n }),\n ]);\n }\n\n public dispose() {\n this.mountedLines.clear();\n }\n\n public render(): JSX.Element {\n const [, forceUpdate] = useState({});\n\n useLayoutEffect(() => {\n const updateLines = (): void => {\n let needsUpdate = false;\n\n // 批量处理所有线条的更新\n this.lines.forEach((line) => {\n const renderData = line.getData(WorkflowLineRenderData);\n const oldVersion = renderData.renderVersion;\n renderData.update();\n // 如果有任何一条线发生变化,标记需要更新\n if (renderData.renderVersion !== oldVersion) {\n needsUpdate = true;\n }\n });\n\n // 只在确实需要更新时触发重渲染\n if (needsUpdate) {\n forceUpdate({});\n }\n };\n\n const rafId = requestAnimationFrame(updateLines);\n return () => cancelAnimationFrame(rafId);\n }, [this.lines]); // 依赖项包含 lines\n\n const lines = this.lines.map((line) => this.renderLine(line));\n return <>{lines}</>;\n }\n\n // 用来绕过 memo\n private bumpVersion() {\n this._version = this._version + 1;\n if (this._version === Number.MAX_SAFE_INTEGER) {\n this._version = 0;\n }\n }\n\n private lineProps(line: WorkflowLineEntity): LineRenderProps {\n const { lineType } = this.workflowDocument.linesManager;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const version = this.lineVersion(line);\n\n return {\n key: line.id,\n color: line.color,\n selected,\n hovered,\n line,\n lineType,\n version,\n strokePrefix: this.layerID,\n rendererRegistry: this.rendererRegistry,\n };\n }\n\n private lineVersion(line: WorkflowLineEntity): string {\n const renderData = line.getData(WorkflowLineRenderData);\n const { renderVersion } = renderData;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const { version: lineVersion, color } = line;\n\n const version = `v:${this._version},lv:${lineVersion},rv:${renderVersion},c:${color},s:${\n selected ? 'T' : 'F'\n },h:${hovered ? 'T' : 'F'}`;\n\n return version;\n }\n\n private lineComponent(props: LineRenderProps): ReactNode {\n const RenderInsideLine = this.options.renderInsideLine ?? (() => <></>);\n return (\n <WorkflowLineRender {...props}>\n <RenderInsideLine {...props} />\n </WorkflowLineRender>\n );\n }\n\n private renderLine(line: WorkflowLineEntity): ReactNode {\n const lineProps = this.lineProps(line);\n const cache = this.mountedLines.get(line.id);\n const isCached = cache !== undefined;\n const { portal: cachedPortal, version: cachedVersion } = cache ?? {};\n if (isCached && cachedVersion === lineProps.version) {\n // 如果已有缓存且版本相同,则直接返回缓存的 portal\n return cachedPortal;\n }\n if (!isCached) {\n // 如果缓存不存在,则将 line 挂载到 renderElement 上\n this.renderElement.appendChild(line.node);\n line.onDispose(() => {\n this.mountedLines.delete(line.id);\n line.node.remove();\n });\n }\n // 刷新缓存\n const portal = ReactDOM.createPortal(this.lineComponent(lineProps), line.node);\n this.mountedLines.set(line.id, { line, portal, version: lineProps.version });\n return portal;\n }\n\n private get renderElement(): HTMLElement {\n return this.stackContext.node;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { memo } from 'react';\n\nimport { LineSVG } from './line-svg';\n\nexport const WorkflowLineRender = memo(\n LineSVG,\n (prevProps, nextProps) => prevProps.version === nextProps.version\n);\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport clsx from 'clsx';\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { POINT_RADIUS } from '@flowgram.ai/free-layout-core';\nimport { WorkflowLineRenderData } from '@flowgram.ai/free-layout-core';\n\nimport { type ArrowRendererComponent } from '../../types/arrow-renderer';\nimport { LineRenderProps } from '../../type';\nimport { STROKE_WIDTH_SLECTED, STROKE_WIDTH } from '../../constants/points';\nimport { LINE_OFFSET } from '../../constants/lines';\nimport { LineStyle } from './index.style';\nimport { ArrowRenderer } from './arrow';\n\nconst PADDING = 12;\n\nexport const LineSVG = (props: LineRenderProps) => {\n const { line, color, selected, children, strokePrefix, rendererRegistry } = props;\n const { position, reverse, hideArrow, vertical } = line;\n\n const renderData = line.getData(WorkflowLineRenderData);\n const { bounds, path: bezierPath } = renderData;\n\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bounds.x + PADDING,\n y: p.y - bounds.y + PADDING,\n });\n\n const fromPos = toRelative(position.from);\n const toPos = toRelative(position.to);\n\n // 箭头位置计算\n const arrowToPos: IPoint =\n position.to.location === 'top'\n ? { x: toPos.x, y: toPos.y - POINT_RADIUS }\n : { x: toPos.x - POINT_RADIUS, y: toPos.y };\n const arrowFromPos: IPoint =\n position.from.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + POINT_RADIUS + LINE_OFFSET }\n : { x: fromPos.x + POINT_RADIUS + LINE_OFFSET, y: fromPos.y };\n\n const strokeWidth = selected\n ? line.uiState.strokeWidthSelected ?? STROKE_WIDTH_SLECTED\n : line.uiState.strokeWidth ?? STROKE_WIDTH;\n\n const strokeID = strokePrefix ? `${strokePrefix}-${line.id}` : line.id;\n\n // 获取自定义箭头渲染器,如果没有则使用默认的\n const CustomArrowRenderer = rendererRegistry?.tryToGetRendererComponent('arrow-renderer')\n ?.renderer as ArrowRendererComponent;\n const ArrowComponent = CustomArrowRenderer || ArrowRenderer;\n\n const path = (\n <path\n d={bezierPath}\n fill=\"none\"\n stroke={`url(#${strokeID})`}\n strokeWidth={strokeWidth}\n className={line.processing || line.flowing ? 'dashed-line flowing-line' : ''}\n />\n );\n\n return (\n <LineStyle\n className={clsx('gedit-flow-activity-edge', line.className)}\n style={{\n ...line.uiState.style,\n left: bounds.x - PADDING,\n top: bounds.y - PADDING,\n position: 'absolute',\n }}\n >\n {children}\n <svg width={bounds.width + PADDING * 2} height={bounds.height + PADDING * 2}>\n <defs>\n <linearGradient\n x1={vertical ? '100%' : '0%'}\n y1={vertical ? '0%' : '100%'}\n x2=\"100%\"\n y2=\"100%\"\n id={strokeID}\n gradientUnits=\"userSpaceOnUse\"\n >\n <stop stopColor={color} offset=\"0%\" />\n <stop stopColor={color} offset=\"100%\" />\n </linearGradient>\n </defs>\n <g>\n {path}\n <ArrowComponent\n id={strokeID}\n reverseArrow={reverse}\n pos={reverse ? arrowFromPos : arrowToPos}\n strokeWidth={strokeWidth}\n vertical={vertical}\n hide={hideArrow}\n line={line}\n />\n </g>\n </svg>\n </LineStyle>\n );\n};\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\n// 添加一个固定类名,用于选中该节点\n\nexport const LineStyle = styled.div`\n position: absolute;\n\n @keyframes flowingDash {\n to {\n stroke-dashoffset: -13;\n }\n }\n\n .dashed-line {\n stroke-dasharray: 8, 5;\n }\n\n .flowing-line {\n animation: flowingDash 0.5s linear infinite;\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport { type ArrowRendererProps } from '../../types/arrow-renderer';\nimport { LINE_OFFSET } from '../../constants/lines';\n\nexport function ArrowRenderer({\n id,\n pos,\n reverseArrow,\n strokeWidth,\n vertical,\n hide,\n}: ArrowRendererProps) {\n if (hide) {\n return null;\n }\n const arrowPath = vertical\n ? reverseArrow\n ? `M ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${pos.y - LINE_OFFSET} L ${\n pos.x + LINE_OFFSET\n },${pos.y}`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x + LINE_OFFSET\n },${pos.y - LINE_OFFSET}`\n : reverseArrow\n ? `M ${pos.x},${pos.y + LINE_OFFSET} L ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${\n pos.y - LINE_OFFSET\n }`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x - LINE_OFFSET\n },${pos.y + LINE_OFFSET}`;\n\n return (\n <path\n d={arrowPath}\n strokeLinecap=\"round\"\n stroke={`url(#${id})`}\n fill=\"none\"\n strokeWidth={strokeWidth}\n />\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { Bezier } from 'bezier-js';\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { getBezierControlPoints } from './bezier-controls';\n\nexport interface BezierData {\n fromPos: IPoint;\n toPos: IPoint;\n bbox: Rectangle; // 外围矩形\n controls: IPoint[]; // 控制点\n bezier: Bezier;\n path: string;\n}\n\nexport class WorkflowBezierLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.BEZIER;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: BezierData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return Point.getDistance(pos, this.data.bezier.project(pos));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n this.data = this.calcBezier(params.fromPos, params.toPos);\n }\n\n private calcBezier(fromPos: LinePoint, toPos: LinePoint): BezierData {\n const controls = getBezierControlPoints(fromPos, toPos, this.entity.uiState.curvature);\n const bezier = new Bezier([fromPos, ...controls, toPos]);\n const bbox = bezier.bbox();\n const bboxBounds = new Rectangle(\n bbox.x.min,\n bbox.y.min,\n bbox.x.max - bbox.x.min,\n bbox.y.max - bbox.y.min\n );\n\n const path = this.getPath({ bbox: bboxBounds, fromPos, toPos, controls });\n\n this.data = {\n fromPos,\n toPos,\n bezier,\n bbox: bboxBounds,\n controls,\n path,\n };\n return this.data;\n }\n\n private getPath(params: {\n bbox: Rectangle;\n fromPos: LinePoint;\n toPos: LinePoint;\n controls: IPoint[];\n }): string {\n const { bbox } = params;\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n });\n const fromPos = toRelative(params.fromPos);\n const toPos = toRelative(params.toPos);\n\n const controls = params.controls.map((c) => toRelative(c));\n const shrink = this.entity.uiState.shrink;\n\n const renderFromPos: IPoint =\n params.fromPos.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + shrink }\n : { x: fromPos.x + shrink, y: fromPos.y };\n\n const renderToPos: IPoint =\n params.toPos.location === 'top'\n ? { x: toPos.x, y: toPos.y - shrink }\n : { x: toPos.x - shrink, y: toPos.y };\n\n const controlPoints = controls.map((s) => `${s.x} ${s.y}`).join(',');\n return `M${renderFromPos.x} ${renderFromPos.y} C ${controlPoints}, ${renderToPos.x} ${renderToPos.y}`;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { LinePoint, LinePointLocation } from '@flowgram.ai/free-layout-core';\n\nfunction getControlOffset(distance: number, curvature: number): number {\n if (distance >= 0) {\n return 0.5 * distance;\n }\n\n return curvature * 25 * Math.sqrt(-distance);\n}\n\nfunction getControlWithCurvature({\n location,\n x1,\n y1,\n x2,\n y2,\n curvature,\n}: {\n location: LinePointLocation;\n curvature: number;\n x1: number;\n x2: number;\n y1: number;\n y2: number;\n}): IPoint {\n switch (location) {\n case 'left':\n return {\n x: x1 - getControlOffset(x1 - x2, curvature),\n y: y1,\n };\n case 'right':\n return {\n x: x1 + getControlOffset(x2 - x1, curvature),\n y: y1,\n };\n case 'top':\n return {\n x: x1,\n y: y1 - getControlOffset(y1 - y2, curvature),\n };\n case 'bottom':\n return {\n x: x1,\n y: y1 + getControlOffset(y2 - y1, curvature),\n };\n }\n}\n\nexport function getBezierControlPoints(\n fromPos: LinePoint,\n toPos: LinePoint,\n curvature = 0.25\n): IPoint[] {\n const fromControl = getControlWithCurvature({\n location: fromPos.location,\n x1: fromPos.x,\n y1: fromPos.y,\n x2: toPos.x,\n y2: toPos.y,\n curvature,\n });\n const toControl = getControlWithCurvature({\n location: toPos.location,\n x1: toPos.x,\n y1: toPos.y,\n x2: fromPos.x,\n y2: fromPos.y,\n curvature,\n });\n return [fromControl, toControl];\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { FoldLine } from './fold-line';\n\nexport interface FoldData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowFoldLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.LINE_CHART;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: FoldData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return FoldLine.getFoldLineToPointDistance(this.data.points, pos);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = FoldLine.getPoints({\n source: {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n location: fromPos.location,\n },\n target: {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n location: toPos.location,\n },\n });\n\n const bbox = FoldLine.getBounds(points);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n const path = FoldLine.getSmoothStepPath(adjustedPoints);\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport { LinePoint } from '@flowgram.ai/free-layout-core';\n\n/**\n * 计算点到线段的距离\n * @param point 待测试点\n * @param segStart 线段起点\n * @param segEnd 线段终点\n */\nconst getPointToSegmentDistance = (point: IPoint, segStart: IPoint, segEnd: IPoint): number => {\n const { x: px, y: py } = point;\n const { x: x1, y: y1 } = segStart;\n const { x: x2, y: y2 } = segEnd;\n\n const A = px - x1;\n const B = py - y1;\n const C = x2 - x1;\n const D = y2 - y1;\n\n const dot = A * C + B * D;\n const lenSq = C * C + D * D;\n\n // 参数方程中的t参数\n const param = lenSq === 0 ? -1 : dot / lenSq;\n\n let xx: number;\n let yy: number;\n\n if (param < 0) {\n xx = x1;\n yy = y1;\n } else if (param > 1) {\n xx = x2;\n yy = y2;\n } else {\n xx = x1 + param * C;\n yy = y1 + param * D;\n }\n\n const dx = px - xx;\n const dy = py - yy;\n\n return Math.sqrt(dx * dx + dy * dy);\n};\n\n/**\n * Fork from: https://github.com/xyflow/xyflow/blob/main/packages/system/src/utils/edges/smoothstep-edge.ts\n * MIT License\n * Copyright (c) 2019-2024 webkid GmbH\n */\nexport namespace FoldLine {\n const EDGE_RADIUS = 5;\n const OFFSET = 20;\n\n function getEdgeCenter({ source, target }: { source: IPoint; target: IPoint }): [number, number] {\n const xOffset = Math.abs(target.x - source.x) / 2;\n const centerX = target.x < source.x ? target.x + xOffset : target.x - xOffset;\n\n const yOffset = Math.abs(target.y - source.y) / 2;\n const centerY = target.y < source.y ? target.y + yOffset : target.y - yOffset;\n\n return [centerX, centerY];\n }\n\n const getDirection = ({ source, target }: { source: LinePoint; target: LinePoint }): IPoint => {\n if (source.location === 'left' || source.location === 'right') {\n return source.x < target.x ? { x: 1, y: 0 } : { x: -1, y: 0 };\n }\n return source.y < target.y ? { x: 0, y: 1 } : { x: 0, y: -1 };\n };\n\n const handleDirections = {\n left: { x: -1, y: 0 },\n right: { x: 1, y: 0 },\n top: { x: 0, y: -1 },\n bottom: { x: 0, y: 1 },\n };\n // eslint-disable-next-line complexity\n export function getPoints({\n source,\n target,\n }: {\n source: LinePoint;\n target: LinePoint;\n }): IPoint[] {\n const sourceDir = handleDirections[source.location];\n const targetDir = handleDirections[target.location];\n const sourceGapped: LinePoint = {\n x: source.x + sourceDir.x * OFFSET,\n y: source.y + sourceDir.y * OFFSET,\n location: source.location,\n };\n const targetGapped: LinePoint = {\n x: target.x + targetDir.x * OFFSET,\n y: target.y + targetDir.y * OFFSET,\n location: target.location,\n };\n const dir = getDirection({\n source: sourceGapped,\n target: targetGapped,\n });\n const dirAccessor = dir.x !== 0 ? 'x' : 'y';\n const currDir = dir[dirAccessor];\n\n let points: IPoint[] = [];\n let centerX, centerY;\n\n const [defaultCenterX, defaultCenterY] = getEdgeCenter({\n source,\n target,\n });\n\n // 计算向量乘积\n if (sourceDir[dirAccessor] * targetDir[dirAccessor] === -1) {\n centerX = defaultCenterX;\n centerY = defaultCenterY;\n\n const verticalSplit: IPoint[] = [\n { x: centerX, y: sourceGapped.y },\n { x: centerX, y: targetGapped.y },\n ];\n\n const horizontalSplit: IPoint[] = [\n { x: sourceGapped.x, y: centerY },\n { x: targetGapped.x, y: centerY },\n ];\n\n if (sourceDir[dirAccessor] === currDir) {\n points = dirAccessor === 'x' ? verticalSplit : horizontalSplit;\n } else {\n points = dirAccessor === 'x' ? horizontalSplit : verticalSplit;\n }\n } else {\n // sourceTarget means we take x from source and y from target, targetSource is the opposite\n const sourceTarget: IPoint[] = [{ x: sourceGapped.x, y: targetGapped.y }];\n const targetSource: IPoint[] = [{ x: targetGapped.x, y: sourceGapped.y }];\n // this handles edges with same handle positions\n if (dirAccessor === 'x') {\n points = sourceDir.x === currDir ? targetSource : sourceTarget;\n } else {\n points = sourceDir.y === currDir ? sourceTarget : targetSource;\n }\n\n // these are conditions for handling mixed handle positions like Right -> Bottom for example\n const dirAccessorOpposite = dirAccessor === 'x' ? 'y' : 'x';\n const isSameDir = sourceDir[dirAccessor] === targetDir[dirAccessorOpposite];\n const sourceGtTargetOppo =\n sourceGapped[dirAccessorOpposite] > targetGapped[dirAccessorOpposite];\n const sourceLtTargetOppo =\n sourceGapped[dirAccessorOpposite] < targetGapped[dirAccessorOpposite];\n const flipSourceTarget =\n (sourceDir[dirAccessor] === 1 &&\n ((!isSameDir && sourceGtTargetOppo) || (isSameDir && sourceLtTargetOppo))) ||\n (sourceDir[dirAccessor] !== 1 &&\n ((!isSameDir && sourceLtTargetOppo) || (isSameDir && sourceGtTargetOppo)));\n\n if (flipSourceTarget) {\n points = dirAccessor === 'x' ? sourceTarget : targetSource;\n }\n\n const sourceGapPoint = { x: sourceGapped.x, y: sourceGapped.y };\n const targetGapPoint = { x: targetGapped.x, y: targetGapped.y };\n const maxXDistance = Math.max(\n Math.abs(sourceGapPoint.x - points[0].x),\n Math.abs(targetGapPoint.x - points[0].x)\n );\n const maxYDistance = Math.max(\n Math.abs(sourceGapPoint.y - points[0].y),\n Math.abs(targetGapPoint.y - points[0].y)\n );\n\n if (maxXDistance >= maxYDistance) {\n centerX = (sourceGapPoint.x + targetGapPoint.x) / 2;\n centerY = points[0].y;\n } else {\n centerX = points[0].x;\n centerY = (sourceGapPoint.y + targetGapPoint.y) / 2;\n }\n }\n\n const pathPoints = [\n source,\n { x: sourceGapped.x, y: sourceGapped.y },\n ...points,\n { x: targetGapped.x, y: targetGapped.y },\n target,\n ];\n\n return pathPoints;\n }\n\n function getBend(a: IPoint, b: IPoint, c: IPoint): string {\n const bendSize = Math.min(\n Point.getDistance(a, b) / 2,\n Point.getDistance(b, c) / 2,\n EDGE_RADIUS\n );\n const { x, y } = b;\n\n // no bend\n if ((a.x === x && x === c.x) || (a.y === y && y === c.y)) {\n return `L${x} ${y}`;\n }\n\n // first segment is horizontal\n if (a.y === y) {\n const xDir = a.x < c.x ? -1 : 1;\n const yDir = a.y < c.y ? 1 : -1;\n return `L ${x + bendSize * xDir},${y}Q ${x},${y} ${x},${y + bendSize * yDir}`;\n }\n\n const xDir = a.x < c.x ? 1 : -1;\n const yDir = a.y < c.y ? -1 : 1;\n return `L ${x},${y + bendSize * yDir}Q ${x},${y} ${x + bendSize * xDir},${y}`;\n }\n\n /**\n * 实现 reactFlow 原本的折叠线交互\n */\n export function getSmoothStepPath(points: IPoint[]): string {\n const path = points.reduce<string>((res, p, i) => {\n let segment = '';\n\n if (i > 0 && i < points.length - 1) {\n segment = getBend(points[i - 1], p, points[i + 1]);\n } else {\n segment = `${i === 0 ? 'M' : 'L'}${p.x} ${p.y}`;\n }\n\n res += segment;\n\n return res;\n }, '');\n\n return path;\n }\n export function getBounds(points: IPoint[]): Rectangle {\n const xList = points.map((p) => p.x);\n const yList = points.map((p) => p.y);\n const left = Math.min(...xList);\n const right = Math.max(...xList);\n const top = Math.min(...yList);\n const bottom = Math.max(...yList);\n return Rectangle.createRectangleWithTwoPoints(\n {\n x: left,\n y: top,\n },\n {\n x: right,\n y: bottom,\n }\n );\n }\n /**\n * 计算点到折线的最短距离\n * @param points 折线的所有端点\n * @param pos 待测试点\n * @returns 最短距离\n */\n export const getFoldLineToPointDistance = (points: IPoint[], pos: IPoint): number => {\n // 特殊情况处理\n if (points.length === 0) {\n return Infinity;\n }\n\n if (points.length === 1) {\n return Point.getDistance(points[0]!, pos);\n }\n\n // 构建线段数组\n const lines: [IPoint, IPoint][] = [];\n for (let i = 0; i < points.length - 1; i++) {\n lines.push([points[i]!, points[i + 1]!]);\n }\n\n // 计算点到每个线段的最短距离\n const distances = lines.map((line) => {\n const [p1, p2] = line;\n return getPointToSegmentDistance(pos, p1, p2);\n });\n\n return Math.min(...distances);\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { projectPointOnLine } from './point-on-line';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowStraightLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowStraightLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: StraightData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n const [start, end] = this.data.points;\n return Point.getDistance(pos, projectPointOnLine(pos, start, end));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = [\n {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n },\n {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n },\n ];\n\n const bbox = Rectangle.createRectangleWithTwoPoints(points[0], points[1]);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n // 生成直线路径\n const path = `M ${adjustedPoints[0].x} ${adjustedPoints[0].y} L ${adjustedPoints[1].x} ${adjustedPoints[1].y}`;\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\n/**\n * 计算点到直线的投影点\n */\nexport function projectPointOnLine(point: IPoint, lineStart: IPoint, lineEnd: IPoint): IPoint {\n const dx = lineEnd.x - lineStart.x;\n const dy = lineEnd.y - lineStart.y;\n\n // 如果是垂直线\n if (dx === 0) {\n return { x: lineStart.x, y: point.y };\n }\n // 如果是水平线\n if (dy === 0) {\n return { x: point.x, y: lineStart.y };\n }\n\n const t = ((point.x - lineStart.x) * dx + (point.y - lineStart.y) * dy) / (dx * dx + dy * dy);\n const clampedT = Math.max(0, Math.min(1, t));\n\n return {\n x: lineStart.x + clampedT * dx,\n y: lineStart.y + clampedT * dy,\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\n\nexport interface ArcData {\n fromPos: IPoint;\n toPos: IPoint;\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowArkLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowArkLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: ArcData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n\n const { fromPos, toPos, bbox } = this.data;\n\n // 首先检查点是否在包围盒范围内\n if (!bbox.contains(pos.x, pos.y)) {\n // 如果点在包围盒外,计算到包围盒边界的最短距离\n const dx = Math.max(bbox.x - pos.x, 0, pos.x - (bbox.x + bbox.width));\n const dy = Math.max(bbox.y - pos.y, 0, pos.y - (bbox.y + bbox.height));\n return Math.sqrt(dx * dx + dy * dy);\n }\n\n // 计算圆弧的中心点和半径\n const center = {\n x: (fromPos.x + toPos.x) / 2,\n y: (fromPos.y + toPos.y) / 2,\n };\n const radius = Point.getDistance(fromPos, center);\n\n // 计算点到圆心的距离\n const distanceToCenter = Point.getDistance(pos, center);\n\n // 返回点到圆弧的近似距离\n return Math.abs(distanceToCenter - radius);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: IPoint; toPos: IPoint }): void {\n const { fromPos, toPos } = params;\n const { vertical } = this.entity;\n\n const sourceOffset = {\n x: vertical ? 0 : POINT_RADIUS,\n y: vertical ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: vertical ? 0 : -POINT_RADIUS,\n y: vertical ? -POINT_RADIUS : 0,\n };\n\n const start = {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n };\n const end = {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n };\n\n // 计算圆弧的包围盒\n const bbox = this.calculateArcBBox(start, end);\n\n // 生成圆弧路径\n const path = this.getArcPath(start, end, bbox);\n\n this.data = {\n fromPos: start,\n toPos: end,\n path,\n bbox,\n };\n }\n\n private calculateArcBBox(start: IPoint, end: IPoint): Rectangle {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const radius = Math.sqrt(dx * dx + dy * dy) / 2;\n\n const centerX = (start.x + end.x) / 2;\n const centerY = (start.y + end.y) / 2;\n\n return new Rectangle(centerX - radius, centerY - radius, radius * 2, radius * 2);\n }\n\n private getArcPath(start: IPoint, end: IPoint, bbox: Rectangle): string {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const distance = Math.sqrt(dx * dx + dy * dy);\n\n // 调整点到相对坐标\n const startRel = {\n x: start.x - bbox.x + LINE_PADDING,\n y: start.y - bbox.y + LINE_PADDING,\n };\n const endRel = {\n x: end.x - bbox.x + LINE_PADDING,\n y: end.y - bbox.y + LINE_PADDING,\n };\n\n // 使用 SVG 圆弧命令\n return `M ${startRel.x} ${startRel.y} A ${distance / 2} ${distance / 2} 0 0 1 ${endRel.x} ${\n endRel.y\n }`;\n }\n}\n"],"mappings":"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","names":["React","React","WorkflowLinesManager","ReactDOM","React","useState","WorkflowHoverService","WorkflowLineRenderData","React","styled","React","React","React","useState","WorkflowLineRenderData","React","ReactDOM","WorkflowHoverService","Rectangle","POINT_RADIUS","LineType","Point","Rectangle","FoldLine","xDir","yDir","Rectangle","POINT_RADIUS","LineType","Point","Rectangle","POINT_RADIUS","Point","Rectangle","POINT_RADIUS","Point","Rectangle","POINT_RADIUS","Point","Rectangle","POINT_RADIUS","WorkflowLinesManager"]}
|
package/dist/index.js
CHANGED
|
@@ -324,9 +324,7 @@ var import_free_layout_core3 = require("@flowgram.ai/free-layout-core");
|
|
|
324
324
|
|
|
325
325
|
// src/components/workflow-line-render/index.style.ts
|
|
326
326
|
var import_styled_components2 = __toESM(require("styled-components"));
|
|
327
|
-
var LineStyle = import_styled_components2.default.div
|
|
328
|
-
className: "gedit-flow-activity-edge"
|
|
329
|
-
})`
|
|
327
|
+
var LineStyle = import_styled_components2.default.div`
|
|
330
328
|
position: absolute;
|
|
331
329
|
|
|
332
330
|
@keyframes flowingDash {
|
|
@@ -396,17 +394,15 @@ var LineSVG = (props) => {
|
|
|
396
394
|
fill: "none",
|
|
397
395
|
stroke: `url(#${strokeID})`,
|
|
398
396
|
strokeWidth,
|
|
399
|
-
|
|
400
|
-
className: (0, import_clsx2.default)(
|
|
401
|
-
line.className,
|
|
402
|
-
line.processing || line.flowing ? "dashed-line flowing-line" : ""
|
|
403
|
-
)
|
|
397
|
+
className: line.processing || line.flowing ? "dashed-line flowing-line" : ""
|
|
404
398
|
}
|
|
405
399
|
);
|
|
406
400
|
return /* @__PURE__ */ import_react4.default.createElement(
|
|
407
401
|
LineStyle,
|
|
408
402
|
{
|
|
403
|
+
className: (0, import_clsx2.default)("gedit-flow-activity-edge", line.className),
|
|
409
404
|
style: {
|
|
405
|
+
...line.uiState.style,
|
|
410
406
|
left: bounds.x - PADDING,
|
|
411
407
|
top: bounds.y - PADDING,
|
|
412
408
|
position: "absolute"
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/components/workflow-port-render/index.tsx","../src/constants/points.ts","../src/components/workflow-port-render/style.ts","../src/components/workflow-port-render/cross-hair.tsx","../src/constants/lines.ts","../src/create-free-lines-plugin.ts","../src/layer/workflow-lines-layer.tsx","../src/components/workflow-line-render/index.tsx","../src/components/workflow-line-render/line-svg.tsx","../src/components/workflow-line-render/index.style.ts","../src/components/workflow-line-render/arrow.tsx","../src/contributions/bezier/index.ts","../src/contributions/bezier/bezier-controls.ts","../src/contributions/fold/index.ts","../src/contributions/fold/fold-line.ts","../src/contributions/straight/index.ts","../src/contributions/straight/point-on-line.ts","../src/contributions/arc/index.ts"],"sourcesContent":["/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nexport * from './components/workflow-port-render';\nexport * from './constants/lines';\nexport * from './create-free-lines-plugin';\nexport * from './layer';\nexport * from './type';\nexport * from './types/arrow-renderer';\nexport * from './contributions';\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { useEffect, useState } from 'react';\n\nimport classNames from 'clsx';\nimport {\n WorkflowHoverService,\n type WorkflowPortEntity,\n usePlaygroundReadonlyState,\n WorkflowLinesManager,\n} from '@flowgram.ai/free-layout-core';\nimport { MouseTouchEvent, useService } from '@flowgram.ai/core';\n\nimport { PORT_BG_CLASS_NAME } from '../../constants/points';\nimport { WorkflowPointStyle } from './style';\nimport CrossHair from './cross-hair';\n\nexport interface WorkflowPortRenderProps {\n entity: WorkflowPortEntity;\n className?: string;\n style?: React.CSSProperties;\n onClick?: (e: React.MouseEvent<HTMLDivElement>, port: WorkflowPortEntity) => void;\n /** 激活状态颜色 (linked/hovered) */\n primaryColor?: string;\n /** 默认状态颜色 */\n secondaryColor?: string;\n /** 错误状态颜色 */\n errorColor?: string;\n /** 背景颜色 */\n backgroundColor?: string;\n}\n\nexport const WorkflowPortRender: React.FC<WorkflowPortRenderProps> =\n // eslint-disable-next-line react/display-name\n React.memo<WorkflowPortRenderProps>((props: WorkflowPortRenderProps) => {\n const hoverService = useService<WorkflowHoverService>(WorkflowHoverService);\n const linesManager = useService<WorkflowLinesManager>(WorkflowLinesManager);\n const { entity, onClick } = props;\n const { portType, relativePosition, disabled } = entity;\n const [targetElement, setTargetElement] = useState(entity.targetElement);\n const [posX, updatePosX] = useState(relativePosition.x);\n const [posY, updatePosY] = useState(relativePosition.y);\n const [hovered, setHovered] = useState(false);\n const [linked, setLinked] = useState(Boolean(entity?.lines?.length));\n const [hasError, setHasError] = useState(props.entity.hasError);\n const readonly = usePlaygroundReadonlyState();\n\n useEffect(() => {\n // useEffect 时序问题可能导致 port.hasError 非最新,需重新触发一次 validate\n entity.validate();\n setHasError(entity.hasError);\n const dispose = entity.onEntityChange(() => {\n // 如果有挂载的节点,不需要更新位置信息\n if (entity.targetElement) {\n if (entity.targetElement !== targetElement) {\n setTargetElement(entity.targetElement);\n }\n return;\n }\n const newPos = entity.relativePosition;\n // 加上 round 避免点位抖动\n updatePosX(Math.round(newPos.x));\n updatePosY(Math.round(newPos.y));\n });\n const dispose2 = hoverService.onHoveredChange((id) => {\n setHovered(hoverService.isHovered(entity.id));\n });\n const dispose3 = entity.onErrorChanged(() => {\n setHasError(entity.hasError);\n });\n const dispose4 = linesManager.onAvailableLinesChange(() => {\n setTimeout(() => {\n if (linesManager.disposed || entity.disposed) return;\n setLinked(Boolean(entity.lines.length));\n }, 0);\n });\n return () => {\n dispose.dispose();\n dispose2.dispose();\n dispose3.dispose();\n dispose4.dispose();\n };\n }, [hoverService, entity, targetElement]);\n\n // 监听变化\n const className = classNames('workflow-port-render', props.className || '', {\n hovered: !readonly && hovered && !disabled && portType !== 'input',\n // 有线条链接的时候深蓝色小圆点\n linked,\n });\n\n // 构建 CSS 自定义属性用于颜色覆盖\n const colorStyles: Record<string, string> = {};\n if (props.primaryColor) {\n colorStyles['--g-workflow-port-color-primary'] = props.primaryColor;\n }\n if (props.secondaryColor) {\n colorStyles['--g-workflow-port-color-secondary'] = props.secondaryColor;\n }\n if (props.errorColor) {\n colorStyles['--g-workflow-port-color-error'] = props.errorColor;\n }\n if (props.backgroundColor) {\n colorStyles['--g-workflow-port-color-background'] = props.backgroundColor;\n }\n\n const combinedStyle = targetElement\n ? { ...props.style, ...colorStyles }\n : { ...props.style, ...colorStyles, left: posX, top: posY };\n\n const content = (\n <WorkflowPointStyle\n className={className}\n style={combinedStyle}\n onClick={(e) => onClick?.(e, entity)}\n onTouchStart={(e) => {\n if (!onClick) {\n return;\n }\n MouseTouchEvent.onTouched(e, (mouseEvent) => {\n onClick(mouseEvent as unknown as React.MouseEvent<HTMLDivElement>, entity);\n });\n }}\n data-port-entity-id={entity.id}\n data-port-entity-type={entity.portType}\n data-testid=\"sdk.workflow.canvas.node.port\"\n >\n <div className={classNames('bg-circle', 'workflow-bg-circle')}></div>\n <div\n className={classNames({\n bg: true,\n [PORT_BG_CLASS_NAME]: true,\n 'workflow-point-bg': true,\n hasError,\n })}\n >\n <CrossHair />\n </div>\n <div className=\"focus-circle\" />\n </WorkflowPointStyle>\n );\n if (targetElement) {\n return ReactDOM.createPortal(content, targetElement);\n }\n return content;\n });\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 连接点半径\n\nexport const STROKE_WIDTH_SLECTED = 3;\n\nexport const STROKE_WIDTH = 2;\n\nexport const PORT_BG_CLASS_NAME = 'workflow-port-bg';\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\nexport const WorkflowPointStyle = styled.div`\n width: 20px;\n height: 20px;\n border-radius: 50%;\n margin-top: -10px;\n margin-left: -10px;\n left: 50%;\n top: 50%;\n position: absolute;\n // 非 hover 状态下的样式\n border: none;\n\n & > .symbol {\n opacity: 0;\n }\n\n .bg-circle {\n display: flex;\n align-items: center;\n justify-content: center;\n position: absolute;\n border-radius: 50%;\n width: 20px;\n height: 20px;\n background-color: var(--g-workflow-port-color-background, #fff);\n transform: scale(0.5);\n transition: all 0.2s linear 0s;\n }\n\n .bg {\n display: flex;\n align-items: center;\n justify-content: center;\n position: relative;\n width: 100%;\n height: 100%;\n border-radius: 50%;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n transform: scale(0.4, 0.4);\n transition: all 0.2s linear 0s;\n\n &.hasError {\n background: var(--g-workflow-port-color-error, red);\n }\n\n .symbol {\n position: absolute;\n width: 14px;\n height: 14px;\n opacity: 0;\n pointer-events: none;\n color: var(--g-workflow-port-color-background, #fff);\n transition: opacity 0.2s linear 0s;\n\n & > svg {\n width: 14px;\n height: 14px;\n }\n }\n\n .focus-circle {\n position: absolute;\n display: flex;\n justify-content: center;\n align-items: center;\n width: 8px;\n height: 8px;\n opacity: 0;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n border-radius: 50%;\n transition: opacity 0.2s linear 0s;\n }\n }\n\n &.linked .bg:not(.hasError) {\n background: var(--g-workflow-port-color-primary, #4d53e8);\n }\n\n &.hovered .bg:not(.hasError) {\n border: none;\n cursor: crosshair;\n transform: scale(1, 1);\n background: var(--g-workflow-port-color-primary, #4d53e8);\n\n & > .symbol {\n opacity: 1;\n }\n }\n\n .cross-hair {\n position: relative;\n left: 2px;\n top: 2px;\n\n &::after,\n &::before {\n content: '';\n background: var(--g-workflow-port-color-background, #fff);\n border-radius: 2px;\n position: absolute;\n }\n\n &::after {\n left: 4px;\n width: 2px;\n height: 6px;\n box-shadow: 0 4px var(--g-workflow-port-color-background, #fff);\n }\n\n &::before {\n top: 4px;\n width: 6px;\n height: 2px;\n box-shadow: 4px 0 var(--g-workflow-port-color-background, #fff);\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\n// demo 环境自绘 cross-hair,正式环境使用 IconAdd\nexport default function CrossHair(): JSX.Element {\n return (\n <div className=\"symbol\">\n <div className=\"cross-hair\" />\n </div>\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 箭头宽度\nexport const LINE_OFFSET = 6;\n\nexport const LINE_PADDING = 12;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { WorkflowLinesManager } from '@flowgram.ai/free-layout-core';\nimport { definePluginCreator, PluginContext } from '@flowgram.ai/core';\n\nimport { FreeLinesPluginOptions } from './type';\nimport { WorkflowLinesLayer } from './layer';\nimport { WorkflowBezierLineContribution, WorkflowFoldLineContribution } from './contributions';\n\nexport const createFreeLinesPlugin = definePluginCreator({\n singleton: true,\n onInit: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n ctx.playground.registerLayer(WorkflowLinesLayer, {\n ...opts,\n });\n },\n onReady: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n const linesManager = ctx.container.get(WorkflowLinesManager);\n linesManager\n .registerContribution(WorkflowBezierLineContribution)\n .registerContribution(WorkflowFoldLineContribution);\n\n if (opts.contributions) {\n opts.contributions.forEach((contribution) => {\n linesManager.registerContribution(contribution);\n });\n }\n\n if (opts.defaultLineType) {\n linesManager.switchLineType(opts.defaultLineType);\n }\n },\n});\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { ReactNode, useLayoutEffect, useState } from 'react';\n\nimport { inject, injectable } from 'inversify';\nimport { domUtils } from '@flowgram.ai/utils';\nimport { FlowRendererRegistry } from '@flowgram.ai/renderer';\nimport { StackingContextManager } from '@flowgram.ai/free-stack-plugin';\nimport {\n nanoid,\n WorkflowDocument,\n WorkflowHoverService,\n WorkflowLineEntity,\n WorkflowLineRenderData,\n WorkflowNodeEntity,\n WorkflowPortEntity,\n WorkflowSelectService,\n} from '@flowgram.ai/free-layout-core';\nimport { Layer, observeEntities, observeEntityDatas, TransformData } from '@flowgram.ai/core';\n\nimport { LineRenderProps, LinesLayerOptions } from '../type';\nimport { WorkflowLineRender } from '../components';\n\n@injectable()\nexport class WorkflowLinesLayer extends Layer<LinesLayerOptions> {\n static type = 'WorkflowLinesLayer';\n\n @inject(WorkflowHoverService) hoverService: WorkflowHoverService;\n\n @inject(WorkflowSelectService) selectService: WorkflowSelectService;\n\n @inject(StackingContextManager) stackContext: StackingContextManager;\n\n @inject(FlowRendererRegistry) rendererRegistry: FlowRendererRegistry;\n\n @observeEntities(WorkflowLineEntity) readonly lines: WorkflowLineEntity[];\n\n @observeEntities(WorkflowPortEntity) readonly ports: WorkflowPortEntity[];\n\n @observeEntityDatas(WorkflowNodeEntity, TransformData)\n readonly trans: TransformData[];\n\n @inject(WorkflowDocument) protected workflowDocument: WorkflowDocument;\n\n private layerID = nanoid();\n\n private mountedLines: Map<\n string,\n {\n line: WorkflowLineEntity;\n portal: ReactNode;\n version: string;\n }\n > = new Map();\n\n private _version = 0;\n\n /**\n * 节点线条\n */\n public node = domUtils.createDivWithClass('gedit-playground-layer gedit-flow-lines-layer');\n\n public onZoom(scale: number): void {\n this.node.style.transform = `scale(${scale})`;\n }\n\n public onReady() {\n this.pipelineNode.appendChild(this.node);\n this.toDispose.pushAll([\n this.selectService.onSelectionChanged(() => this.render()),\n this.hoverService.onHoveredChange(() => this.render()),\n this.workflowDocument.linesManager.onForceUpdate(() => {\n this.mountedLines.clear();\n this.bumpVersion();\n this.render();\n }),\n ]);\n }\n\n public dispose() {\n this.mountedLines.clear();\n }\n\n public render(): JSX.Element {\n const [, forceUpdate] = useState({});\n\n useLayoutEffect(() => {\n const updateLines = (): void => {\n let needsUpdate = false;\n\n // 批量处理所有线条的更新\n this.lines.forEach((line) => {\n const renderData = line.getData(WorkflowLineRenderData);\n const oldVersion = renderData.renderVersion;\n renderData.update();\n // 如果有任何一条线发生变化,标记需要更新\n if (renderData.renderVersion !== oldVersion) {\n needsUpdate = true;\n }\n });\n\n // 只在确实需要更新时触发重渲染\n if (needsUpdate) {\n forceUpdate({});\n }\n };\n\n const rafId = requestAnimationFrame(updateLines);\n return () => cancelAnimationFrame(rafId);\n }, [this.lines]); // 依赖项包含 lines\n\n const lines = this.lines.map((line) => this.renderLine(line));\n return <>{lines}</>;\n }\n\n // 用来绕过 memo\n private bumpVersion() {\n this._version = this._version + 1;\n if (this._version === Number.MAX_SAFE_INTEGER) {\n this._version = 0;\n }\n }\n\n private lineProps(line: WorkflowLineEntity): LineRenderProps {\n const { lineType } = this.workflowDocument.linesManager;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const version = this.lineVersion(line);\n\n return {\n key: line.id,\n color: line.color,\n selected,\n hovered,\n line,\n lineType,\n version,\n strokePrefix: this.layerID,\n rendererRegistry: this.rendererRegistry,\n };\n }\n\n private lineVersion(line: WorkflowLineEntity): string {\n const renderData = line.getData(WorkflowLineRenderData);\n const { renderVersion } = renderData;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const { version: lineVersion, color } = line;\n\n const version = `v:${this._version},lv:${lineVersion},rv:${renderVersion},c:${color},s:${\n selected ? 'T' : 'F'\n },h:${hovered ? 'T' : 'F'}`;\n\n return version;\n }\n\n private lineComponent(props: LineRenderProps): ReactNode {\n const RenderInsideLine = this.options.renderInsideLine ?? (() => <></>);\n return (\n <WorkflowLineRender {...props}>\n <RenderInsideLine {...props} />\n </WorkflowLineRender>\n );\n }\n\n private renderLine(line: WorkflowLineEntity): ReactNode {\n const lineProps = this.lineProps(line);\n const cache = this.mountedLines.get(line.id);\n const isCached = cache !== undefined;\n const { portal: cachedPortal, version: cachedVersion } = cache ?? {};\n if (isCached && cachedVersion === lineProps.version) {\n // 如果已有缓存且版本相同,则直接返回缓存的 portal\n return cachedPortal;\n }\n if (!isCached) {\n // 如果缓存不存在,则将 line 挂载到 renderElement 上\n this.renderElement.appendChild(line.node);\n line.onDispose(() => {\n this.mountedLines.delete(line.id);\n line.node.remove();\n });\n }\n // 刷新缓存\n const portal = ReactDOM.createPortal(this.lineComponent(lineProps), line.node);\n this.mountedLines.set(line.id, { line, portal, version: lineProps.version });\n return portal;\n }\n\n private get renderElement(): HTMLElement {\n return this.stackContext.node;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { memo } from 'react';\n\nimport { LineSVG } from './line-svg';\n\nexport const WorkflowLineRender = memo(\n LineSVG,\n (prevProps, nextProps) => prevProps.version === nextProps.version\n);\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport clsx from 'clsx';\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { POINT_RADIUS } from '@flowgram.ai/free-layout-core';\nimport { WorkflowLineRenderData } from '@flowgram.ai/free-layout-core';\n\nimport { type ArrowRendererComponent } from '../../types/arrow-renderer';\nimport { LineRenderProps } from '../../type';\nimport { STROKE_WIDTH_SLECTED, STROKE_WIDTH } from '../../constants/points';\nimport { LINE_OFFSET } from '../../constants/lines';\nimport { LineStyle } from './index.style';\nimport { ArrowRenderer } from './arrow';\n\nconst PADDING = 12;\n\nexport const LineSVG = (props: LineRenderProps) => {\n const { line, color, selected, children, strokePrefix, rendererRegistry } = props;\n const { position, reverse, hideArrow, vertical } = line;\n\n const renderData = line.getData(WorkflowLineRenderData);\n const { bounds, path: bezierPath } = renderData;\n\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bounds.x + PADDING,\n y: p.y - bounds.y + PADDING,\n });\n\n const fromPos = toRelative(position.from);\n const toPos = toRelative(position.to);\n\n // 箭头位置计算\n const arrowToPos: IPoint =\n position.to.location === 'top'\n ? { x: toPos.x, y: toPos.y - POINT_RADIUS }\n : { x: toPos.x - POINT_RADIUS, y: toPos.y };\n const arrowFromPos: IPoint =\n position.from.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + POINT_RADIUS + LINE_OFFSET }\n : { x: fromPos.x + POINT_RADIUS + LINE_OFFSET, y: fromPos.y };\n\n const strokeWidth = selected\n ? line.uiState.strokeWidthSelected ?? STROKE_WIDTH_SLECTED\n : line.uiState.strokeWidth ?? STROKE_WIDTH;\n\n const strokeID = strokePrefix ? `${strokePrefix}-${line.id}` : line.id;\n\n // 获取自定义箭头渲染器,如果没有则使用默认的\n const CustomArrowRenderer = rendererRegistry?.tryToGetRendererComponent('arrow-renderer')\n ?.renderer as ArrowRendererComponent;\n const ArrowComponent = CustomArrowRenderer || ArrowRenderer;\n\n const path = (\n <path\n d={bezierPath}\n fill=\"none\"\n stroke={`url(#${strokeID})`}\n strokeWidth={strokeWidth}\n style={line.uiState.style}\n className={clsx(\n line.className,\n line.processing || line.flowing ? 'dashed-line flowing-line' : ''\n )}\n />\n );\n\n return (\n <LineStyle\n style={{\n left: bounds.x - PADDING,\n top: bounds.y - PADDING,\n position: 'absolute',\n }}\n >\n {children}\n <svg width={bounds.width + PADDING * 2} height={bounds.height + PADDING * 2}>\n <defs>\n <linearGradient\n x1={vertical ? '100%' : '0%'}\n y1={vertical ? '0%' : '100%'}\n x2=\"100%\"\n y2=\"100%\"\n id={strokeID}\n gradientUnits=\"userSpaceOnUse\"\n >\n <stop stopColor={color} offset=\"0%\" />\n <stop stopColor={color} offset=\"100%\" />\n </linearGradient>\n </defs>\n <g>\n {path}\n <ArrowComponent\n id={strokeID}\n reverseArrow={reverse}\n pos={reverse ? arrowFromPos : arrowToPos}\n strokeWidth={strokeWidth}\n vertical={vertical}\n hide={hideArrow}\n line={line}\n />\n </g>\n </svg>\n </LineStyle>\n );\n};\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\n// 添加一个固定类名,用于选中该节点\n\nexport const LineStyle = styled.div.attrs({\n className: 'gedit-flow-activity-edge',\n})`\n position: absolute;\n\n @keyframes flowingDash {\n to {\n stroke-dashoffset: -13;\n }\n }\n\n .dashed-line {\n stroke-dasharray: 8, 5;\n }\n\n .flowing-line {\n animation: flowingDash 0.5s linear infinite;\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport { type ArrowRendererProps } from '../../types/arrow-renderer';\nimport { LINE_OFFSET } from '../../constants/lines';\n\nexport function ArrowRenderer({\n id,\n pos,\n reverseArrow,\n strokeWidth,\n vertical,\n hide,\n}: ArrowRendererProps) {\n if (hide) {\n return null;\n }\n const arrowPath = vertical\n ? reverseArrow\n ? `M ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${pos.y - LINE_OFFSET} L ${\n pos.x + LINE_OFFSET\n },${pos.y}`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x + LINE_OFFSET\n },${pos.y - LINE_OFFSET}`\n : reverseArrow\n ? `M ${pos.x},${pos.y + LINE_OFFSET} L ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${\n pos.y - LINE_OFFSET\n }`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x - LINE_OFFSET\n },${pos.y + LINE_OFFSET}`;\n\n return (\n <path\n d={arrowPath}\n strokeLinecap=\"round\"\n stroke={`url(#${id})`}\n fill=\"none\"\n strokeWidth={strokeWidth}\n />\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { Bezier } from 'bezier-js';\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { getBezierControlPoints } from './bezier-controls';\n\nexport interface BezierData {\n fromPos: IPoint;\n toPos: IPoint;\n bbox: Rectangle; // 外围矩形\n controls: IPoint[]; // 控制点\n bezier: Bezier;\n path: string;\n}\n\nexport class WorkflowBezierLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.BEZIER;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: BezierData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return Point.getDistance(pos, this.data.bezier.project(pos));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n this.data = this.calcBezier(params.fromPos, params.toPos);\n }\n\n private calcBezier(fromPos: LinePoint, toPos: LinePoint): BezierData {\n const controls = getBezierControlPoints(fromPos, toPos, this.entity.uiState.curvature);\n const bezier = new Bezier([fromPos, ...controls, toPos]);\n const bbox = bezier.bbox();\n const bboxBounds = new Rectangle(\n bbox.x.min,\n bbox.y.min,\n bbox.x.max - bbox.x.min,\n bbox.y.max - bbox.y.min\n );\n\n const path = this.getPath({ bbox: bboxBounds, fromPos, toPos, controls });\n\n this.data = {\n fromPos,\n toPos,\n bezier,\n bbox: bboxBounds,\n controls,\n path,\n };\n return this.data;\n }\n\n private getPath(params: {\n bbox: Rectangle;\n fromPos: LinePoint;\n toPos: LinePoint;\n controls: IPoint[];\n }): string {\n const { bbox } = params;\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n });\n const fromPos = toRelative(params.fromPos);\n const toPos = toRelative(params.toPos);\n\n const controls = params.controls.map((c) => toRelative(c));\n const shrink = this.entity.uiState.shrink;\n\n const renderFromPos: IPoint =\n params.fromPos.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + shrink }\n : { x: fromPos.x + shrink, y: fromPos.y };\n\n const renderToPos: IPoint =\n params.toPos.location === 'top'\n ? { x: toPos.x, y: toPos.y - shrink }\n : { x: toPos.x - shrink, y: toPos.y };\n\n const controlPoints = controls.map((s) => `${s.x} ${s.y}`).join(',');\n return `M${renderFromPos.x} ${renderFromPos.y} C ${controlPoints}, ${renderToPos.x} ${renderToPos.y}`;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { LinePoint, LinePointLocation } from '@flowgram.ai/free-layout-core';\n\nfunction getControlOffset(distance: number, curvature: number): number {\n if (distance >= 0) {\n return 0.5 * distance;\n }\n\n return curvature * 25 * Math.sqrt(-distance);\n}\n\nfunction getControlWithCurvature({\n location,\n x1,\n y1,\n x2,\n y2,\n curvature,\n}: {\n location: LinePointLocation;\n curvature: number;\n x1: number;\n x2: number;\n y1: number;\n y2: number;\n}): IPoint {\n switch (location) {\n case 'left':\n return {\n x: x1 - getControlOffset(x1 - x2, curvature),\n y: y1,\n };\n case 'right':\n return {\n x: x1 + getControlOffset(x2 - x1, curvature),\n y: y1,\n };\n case 'top':\n return {\n x: x1,\n y: y1 - getControlOffset(y1 - y2, curvature),\n };\n case 'bottom':\n return {\n x: x1,\n y: y1 + getControlOffset(y2 - y1, curvature),\n };\n }\n}\n\nexport function getBezierControlPoints(\n fromPos: LinePoint,\n toPos: LinePoint,\n curvature = 0.25\n): IPoint[] {\n const fromControl = getControlWithCurvature({\n location: fromPos.location,\n x1: fromPos.x,\n y1: fromPos.y,\n x2: toPos.x,\n y2: toPos.y,\n curvature,\n });\n const toControl = getControlWithCurvature({\n location: toPos.location,\n x1: toPos.x,\n y1: toPos.y,\n x2: fromPos.x,\n y2: fromPos.y,\n curvature,\n });\n return [fromControl, toControl];\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { FoldLine } from './fold-line';\n\nexport interface FoldData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowFoldLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.LINE_CHART;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: FoldData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return FoldLine.getFoldLineToPointDistance(this.data.points, pos);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = FoldLine.getPoints({\n source: {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n location: fromPos.location,\n },\n target: {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n location: toPos.location,\n },\n });\n\n const bbox = FoldLine.getBounds(points);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n const path = FoldLine.getSmoothStepPath(adjustedPoints);\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport { LinePoint } from '@flowgram.ai/free-layout-core';\n\n/**\n * 计算点到线段的距离\n * @param point 待测试点\n * @param segStart 线段起点\n * @param segEnd 线段终点\n */\nconst getPointToSegmentDistance = (point: IPoint, segStart: IPoint, segEnd: IPoint): number => {\n const { x: px, y: py } = point;\n const { x: x1, y: y1 } = segStart;\n const { x: x2, y: y2 } = segEnd;\n\n const A = px - x1;\n const B = py - y1;\n const C = x2 - x1;\n const D = y2 - y1;\n\n const dot = A * C + B * D;\n const lenSq = C * C + D * D;\n\n // 参数方程中的t参数\n const param = lenSq === 0 ? -1 : dot / lenSq;\n\n let xx: number;\n let yy: number;\n\n if (param < 0) {\n xx = x1;\n yy = y1;\n } else if (param > 1) {\n xx = x2;\n yy = y2;\n } else {\n xx = x1 + param * C;\n yy = y1 + param * D;\n }\n\n const dx = px - xx;\n const dy = py - yy;\n\n return Math.sqrt(dx * dx + dy * dy);\n};\n\n/**\n * Fork from: https://github.com/xyflow/xyflow/blob/main/packages/system/src/utils/edges/smoothstep-edge.ts\n * MIT License\n * Copyright (c) 2019-2024 webkid GmbH\n */\nexport namespace FoldLine {\n const EDGE_RADIUS = 5;\n const OFFSET = 20;\n\n function getEdgeCenter({ source, target }: { source: IPoint; target: IPoint }): [number, number] {\n const xOffset = Math.abs(target.x - source.x) / 2;\n const centerX = target.x < source.x ? target.x + xOffset : target.x - xOffset;\n\n const yOffset = Math.abs(target.y - source.y) / 2;\n const centerY = target.y < source.y ? target.y + yOffset : target.y - yOffset;\n\n return [centerX, centerY];\n }\n\n const getDirection = ({ source, target }: { source: LinePoint; target: LinePoint }): IPoint => {\n if (source.location === 'left' || source.location === 'right') {\n return source.x < target.x ? { x: 1, y: 0 } : { x: -1, y: 0 };\n }\n return source.y < target.y ? { x: 0, y: 1 } : { x: 0, y: -1 };\n };\n\n const handleDirections = {\n left: { x: -1, y: 0 },\n right: { x: 1, y: 0 },\n top: { x: 0, y: -1 },\n bottom: { x: 0, y: 1 },\n };\n // eslint-disable-next-line complexity\n export function getPoints({\n source,\n target,\n }: {\n source: LinePoint;\n target: LinePoint;\n }): IPoint[] {\n const sourceDir = handleDirections[source.location];\n const targetDir = handleDirections[target.location];\n const sourceGapped: LinePoint = {\n x: source.x + sourceDir.x * OFFSET,\n y: source.y + sourceDir.y * OFFSET,\n location: source.location,\n };\n const targetGapped: LinePoint = {\n x: target.x + targetDir.x * OFFSET,\n y: target.y + targetDir.y * OFFSET,\n location: target.location,\n };\n const dir = getDirection({\n source: sourceGapped,\n target: targetGapped,\n });\n const dirAccessor = dir.x !== 0 ? 'x' : 'y';\n const currDir = dir[dirAccessor];\n\n let points: IPoint[] = [];\n let centerX, centerY;\n\n const [defaultCenterX, defaultCenterY] = getEdgeCenter({\n source,\n target,\n });\n\n // 计算向量乘积\n if (sourceDir[dirAccessor] * targetDir[dirAccessor] === -1) {\n centerX = defaultCenterX;\n centerY = defaultCenterY;\n\n const verticalSplit: IPoint[] = [\n { x: centerX, y: sourceGapped.y },\n { x: centerX, y: targetGapped.y },\n ];\n\n const horizontalSplit: IPoint[] = [\n { x: sourceGapped.x, y: centerY },\n { x: targetGapped.x, y: centerY },\n ];\n\n if (sourceDir[dirAccessor] === currDir) {\n points = dirAccessor === 'x' ? verticalSplit : horizontalSplit;\n } else {\n points = dirAccessor === 'x' ? horizontalSplit : verticalSplit;\n }\n } else {\n // sourceTarget means we take x from source and y from target, targetSource is the opposite\n const sourceTarget: IPoint[] = [{ x: sourceGapped.x, y: targetGapped.y }];\n const targetSource: IPoint[] = [{ x: targetGapped.x, y: sourceGapped.y }];\n // this handles edges with same handle positions\n if (dirAccessor === 'x') {\n points = sourceDir.x === currDir ? targetSource : sourceTarget;\n } else {\n points = sourceDir.y === currDir ? sourceTarget : targetSource;\n }\n\n // these are conditions for handling mixed handle positions like Right -> Bottom for example\n const dirAccessorOpposite = dirAccessor === 'x' ? 'y' : 'x';\n const isSameDir = sourceDir[dirAccessor] === targetDir[dirAccessorOpposite];\n const sourceGtTargetOppo =\n sourceGapped[dirAccessorOpposite] > targetGapped[dirAccessorOpposite];\n const sourceLtTargetOppo =\n sourceGapped[dirAccessorOpposite] < targetGapped[dirAccessorOpposite];\n const flipSourceTarget =\n (sourceDir[dirAccessor] === 1 &&\n ((!isSameDir && sourceGtTargetOppo) || (isSameDir && sourceLtTargetOppo))) ||\n (sourceDir[dirAccessor] !== 1 &&\n ((!isSameDir && sourceLtTargetOppo) || (isSameDir && sourceGtTargetOppo)));\n\n if (flipSourceTarget) {\n points = dirAccessor === 'x' ? sourceTarget : targetSource;\n }\n\n const sourceGapPoint = { x: sourceGapped.x, y: sourceGapped.y };\n const targetGapPoint = { x: targetGapped.x, y: targetGapped.y };\n const maxXDistance = Math.max(\n Math.abs(sourceGapPoint.x - points[0].x),\n Math.abs(targetGapPoint.x - points[0].x)\n );\n const maxYDistance = Math.max(\n Math.abs(sourceGapPoint.y - points[0].y),\n Math.abs(targetGapPoint.y - points[0].y)\n );\n\n if (maxXDistance >= maxYDistance) {\n centerX = (sourceGapPoint.x + targetGapPoint.x) / 2;\n centerY = points[0].y;\n } else {\n centerX = points[0].x;\n centerY = (sourceGapPoint.y + targetGapPoint.y) / 2;\n }\n }\n\n const pathPoints = [\n source,\n { x: sourceGapped.x, y: sourceGapped.y },\n ...points,\n { x: targetGapped.x, y: targetGapped.y },\n target,\n ];\n\n return pathPoints;\n }\n\n function getBend(a: IPoint, b: IPoint, c: IPoint): string {\n const bendSize = Math.min(\n Point.getDistance(a, b) / 2,\n Point.getDistance(b, c) / 2,\n EDGE_RADIUS\n );\n const { x, y } = b;\n\n // no bend\n if ((a.x === x && x === c.x) || (a.y === y && y === c.y)) {\n return `L${x} ${y}`;\n }\n\n // first segment is horizontal\n if (a.y === y) {\n const xDir = a.x < c.x ? -1 : 1;\n const yDir = a.y < c.y ? 1 : -1;\n return `L ${x + bendSize * xDir},${y}Q ${x},${y} ${x},${y + bendSize * yDir}`;\n }\n\n const xDir = a.x < c.x ? 1 : -1;\n const yDir = a.y < c.y ? -1 : 1;\n return `L ${x},${y + bendSize * yDir}Q ${x},${y} ${x + bendSize * xDir},${y}`;\n }\n\n /**\n * 实现 reactFlow 原本的折叠线交互\n */\n export function getSmoothStepPath(points: IPoint[]): string {\n const path = points.reduce<string>((res, p, i) => {\n let segment = '';\n\n if (i > 0 && i < points.length - 1) {\n segment = getBend(points[i - 1], p, points[i + 1]);\n } else {\n segment = `${i === 0 ? 'M' : 'L'}${p.x} ${p.y}`;\n }\n\n res += segment;\n\n return res;\n }, '');\n\n return path;\n }\n export function getBounds(points: IPoint[]): Rectangle {\n const xList = points.map((p) => p.x);\n const yList = points.map((p) => p.y);\n const left = Math.min(...xList);\n const right = Math.max(...xList);\n const top = Math.min(...yList);\n const bottom = Math.max(...yList);\n return Rectangle.createRectangleWithTwoPoints(\n {\n x: left,\n y: top,\n },\n {\n x: right,\n y: bottom,\n }\n );\n }\n /**\n * 计算点到折线的最短距离\n * @param points 折线的所有端点\n * @param pos 待测试点\n * @returns 最短距离\n */\n export const getFoldLineToPointDistance = (points: IPoint[], pos: IPoint): number => {\n // 特殊情况处理\n if (points.length === 0) {\n return Infinity;\n }\n\n if (points.length === 1) {\n return Point.getDistance(points[0]!, pos);\n }\n\n // 构建线段数组\n const lines: [IPoint, IPoint][] = [];\n for (let i = 0; i < points.length - 1; i++) {\n lines.push([points[i]!, points[i + 1]!]);\n }\n\n // 计算点到每个线段的最短距离\n const distances = lines.map((line) => {\n const [p1, p2] = line;\n return getPointToSegmentDistance(pos, p1, p2);\n });\n\n return Math.min(...distances);\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { projectPointOnLine } from './point-on-line';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowStraightLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowStraightLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: StraightData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n const [start, end] = this.data.points;\n return Point.getDistance(pos, projectPointOnLine(pos, start, end));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = [\n {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n },\n {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n },\n ];\n\n const bbox = Rectangle.createRectangleWithTwoPoints(points[0], points[1]);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n // 生成直线路径\n const path = `M ${adjustedPoints[0].x} ${adjustedPoints[0].y} L ${adjustedPoints[1].x} ${adjustedPoints[1].y}`;\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\n/**\n * 计算点到直线的投影点\n */\nexport function projectPointOnLine(point: IPoint, lineStart: IPoint, lineEnd: IPoint): IPoint {\n const dx = lineEnd.x - lineStart.x;\n const dy = lineEnd.y - lineStart.y;\n\n // 如果是垂直线\n if (dx === 0) {\n return { x: lineStart.x, y: point.y };\n }\n // 如果是水平线\n if (dy === 0) {\n return { x: point.x, y: lineStart.y };\n }\n\n const t = ((point.x - lineStart.x) * dx + (point.y - lineStart.y) * dy) / (dx * dx + dy * dy);\n const clampedT = Math.max(0, Math.min(1, t));\n\n return {\n x: lineStart.x + clampedT * dx,\n y: lineStart.y + clampedT * dy,\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\n\nexport interface ArcData {\n fromPos: IPoint;\n toPos: IPoint;\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowArkLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowArkLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: ArcData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n\n const { fromPos, toPos, bbox } = this.data;\n\n // 首先检查点是否在包围盒范围内\n if (!bbox.contains(pos.x, pos.y)) {\n // 如果点在包围盒外,计算到包围盒边界的最短距离\n const dx = Math.max(bbox.x - pos.x, 0, pos.x - (bbox.x + bbox.width));\n const dy = Math.max(bbox.y - pos.y, 0, pos.y - (bbox.y + bbox.height));\n return Math.sqrt(dx * dx + dy * dy);\n }\n\n // 计算圆弧的中心点和半径\n const center = {\n x: (fromPos.x + toPos.x) / 2,\n y: (fromPos.y + toPos.y) / 2,\n };\n const radius = Point.getDistance(fromPos, center);\n\n // 计算点到圆心的距离\n const distanceToCenter = Point.getDistance(pos, center);\n\n // 返回点到圆弧的近似距离\n return Math.abs(distanceToCenter - radius);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: IPoint; toPos: IPoint }): void {\n const { fromPos, toPos } = params;\n const { vertical } = this.entity;\n\n const sourceOffset = {\n x: vertical ? 0 : POINT_RADIUS,\n y: vertical ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: vertical ? 0 : -POINT_RADIUS,\n y: vertical ? -POINT_RADIUS : 0,\n };\n\n const start = {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n };\n const end = {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n };\n\n // 计算圆弧的包围盒\n const bbox = this.calculateArcBBox(start, end);\n\n // 生成圆弧路径\n const path = this.getArcPath(start, end, bbox);\n\n this.data = {\n fromPos: start,\n toPos: end,\n path,\n bbox,\n };\n }\n\n private calculateArcBBox(start: IPoint, end: IPoint): Rectangle {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const radius = Math.sqrt(dx * dx + dy * dy) / 2;\n\n const centerX = (start.x + end.x) / 2;\n const centerY = (start.y + end.y) / 2;\n\n return new Rectangle(centerX - radius, centerY - radius, radius * 2, radius * 2);\n }\n\n private getArcPath(start: IPoint, end: IPoint, bbox: Rectangle): string {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const distance = Math.sqrt(dx * dx + dy * dy);\n\n // 调整点到相对坐标\n const startRel = {\n x: start.x - bbox.x + LINE_PADDING,\n y: start.y - bbox.y + LINE_PADDING,\n };\n const endRel = {\n x: end.x - bbox.x + LINE_PADDING,\n y: end.y - bbox.y + LINE_PADDING,\n };\n\n // 使用 SVG 圆弧命令\n return `M ${startRel.x} ${startRel.y} A ${distance / 2} ${distance / 2} 0 0 1 ${endRel.x} ${\n endRel.y\n }`;\n }\n}\n"],"mappings":"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","names":["import_react","styled","React","React","classNames","ReactDOM","import_free_layout_core","import_core","import_react_dom","import_react","import_free_layout_core","import_core","import_react","import_react","import_clsx","import_free_layout_core","import_styled_components","styled","import_react","React","React","clsx","React","ReactDOM","import_utils","import_free_layout_core","import_utils","import_free_layout_core","import_utils","FoldLine","xDir","yDir","import_utils","import_free_layout_core","import_utils","import_free_layout_core"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/components/workflow-port-render/index.tsx","../src/constants/points.ts","../src/components/workflow-port-render/style.ts","../src/components/workflow-port-render/cross-hair.tsx","../src/constants/lines.ts","../src/create-free-lines-plugin.ts","../src/layer/workflow-lines-layer.tsx","../src/components/workflow-line-render/index.tsx","../src/components/workflow-line-render/line-svg.tsx","../src/components/workflow-line-render/index.style.ts","../src/components/workflow-line-render/arrow.tsx","../src/contributions/bezier/index.ts","../src/contributions/bezier/bezier-controls.ts","../src/contributions/fold/index.ts","../src/contributions/fold/fold-line.ts","../src/contributions/straight/index.ts","../src/contributions/straight/point-on-line.ts","../src/contributions/arc/index.ts"],"sourcesContent":["/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nexport * from './components/workflow-port-render';\nexport * from './constants/lines';\nexport * from './create-free-lines-plugin';\nexport * from './layer';\nexport * from './type';\nexport * from './types/arrow-renderer';\nexport * from './contributions';\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { useEffect, useState } from 'react';\n\nimport classNames from 'clsx';\nimport {\n WorkflowHoverService,\n type WorkflowPortEntity,\n usePlaygroundReadonlyState,\n WorkflowLinesManager,\n} from '@flowgram.ai/free-layout-core';\nimport { MouseTouchEvent, useService } from '@flowgram.ai/core';\n\nimport { PORT_BG_CLASS_NAME } from '../../constants/points';\nimport { WorkflowPointStyle } from './style';\nimport CrossHair from './cross-hair';\n\nexport interface WorkflowPortRenderProps {\n entity: WorkflowPortEntity;\n className?: string;\n style?: React.CSSProperties;\n onClick?: (e: React.MouseEvent<HTMLDivElement>, port: WorkflowPortEntity) => void;\n /** 激活状态颜色 (linked/hovered) */\n primaryColor?: string;\n /** 默认状态颜色 */\n secondaryColor?: string;\n /** 错误状态颜色 */\n errorColor?: string;\n /** 背景颜色 */\n backgroundColor?: string;\n}\n\nexport const WorkflowPortRender: React.FC<WorkflowPortRenderProps> =\n // eslint-disable-next-line react/display-name\n React.memo<WorkflowPortRenderProps>((props: WorkflowPortRenderProps) => {\n const hoverService = useService<WorkflowHoverService>(WorkflowHoverService);\n const linesManager = useService<WorkflowLinesManager>(WorkflowLinesManager);\n const { entity, onClick } = props;\n const { portType, relativePosition, disabled } = entity;\n const [targetElement, setTargetElement] = useState(entity.targetElement);\n const [posX, updatePosX] = useState(relativePosition.x);\n const [posY, updatePosY] = useState(relativePosition.y);\n const [hovered, setHovered] = useState(false);\n const [linked, setLinked] = useState(Boolean(entity?.lines?.length));\n const [hasError, setHasError] = useState(props.entity.hasError);\n const readonly = usePlaygroundReadonlyState();\n\n useEffect(() => {\n // useEffect 时序问题可能导致 port.hasError 非最新,需重新触发一次 validate\n entity.validate();\n setHasError(entity.hasError);\n const dispose = entity.onEntityChange(() => {\n // 如果有挂载的节点,不需要更新位置信息\n if (entity.targetElement) {\n if (entity.targetElement !== targetElement) {\n setTargetElement(entity.targetElement);\n }\n return;\n }\n const newPos = entity.relativePosition;\n // 加上 round 避免点位抖动\n updatePosX(Math.round(newPos.x));\n updatePosY(Math.round(newPos.y));\n });\n const dispose2 = hoverService.onHoveredChange((id) => {\n setHovered(hoverService.isHovered(entity.id));\n });\n const dispose3 = entity.onErrorChanged(() => {\n setHasError(entity.hasError);\n });\n const dispose4 = linesManager.onAvailableLinesChange(() => {\n setTimeout(() => {\n if (linesManager.disposed || entity.disposed) return;\n setLinked(Boolean(entity.lines.length));\n }, 0);\n });\n return () => {\n dispose.dispose();\n dispose2.dispose();\n dispose3.dispose();\n dispose4.dispose();\n };\n }, [hoverService, entity, targetElement]);\n\n // 监听变化\n const className = classNames('workflow-port-render', props.className || '', {\n hovered: !readonly && hovered && !disabled && portType !== 'input',\n // 有线条链接的时候深蓝色小圆点\n linked,\n });\n\n // 构建 CSS 自定义属性用于颜色覆盖\n const colorStyles: Record<string, string> = {};\n if (props.primaryColor) {\n colorStyles['--g-workflow-port-color-primary'] = props.primaryColor;\n }\n if (props.secondaryColor) {\n colorStyles['--g-workflow-port-color-secondary'] = props.secondaryColor;\n }\n if (props.errorColor) {\n colorStyles['--g-workflow-port-color-error'] = props.errorColor;\n }\n if (props.backgroundColor) {\n colorStyles['--g-workflow-port-color-background'] = props.backgroundColor;\n }\n\n const combinedStyle = targetElement\n ? { ...props.style, ...colorStyles }\n : { ...props.style, ...colorStyles, left: posX, top: posY };\n\n const content = (\n <WorkflowPointStyle\n className={className}\n style={combinedStyle}\n onClick={(e) => onClick?.(e, entity)}\n onTouchStart={(e) => {\n if (!onClick) {\n return;\n }\n MouseTouchEvent.onTouched(e, (mouseEvent) => {\n onClick(mouseEvent as unknown as React.MouseEvent<HTMLDivElement>, entity);\n });\n }}\n data-port-entity-id={entity.id}\n data-port-entity-type={entity.portType}\n data-testid=\"sdk.workflow.canvas.node.port\"\n >\n <div className={classNames('bg-circle', 'workflow-bg-circle')}></div>\n <div\n className={classNames({\n bg: true,\n [PORT_BG_CLASS_NAME]: true,\n 'workflow-point-bg': true,\n hasError,\n })}\n >\n <CrossHair />\n </div>\n <div className=\"focus-circle\" />\n </WorkflowPointStyle>\n );\n if (targetElement) {\n return ReactDOM.createPortal(content, targetElement);\n }\n return content;\n });\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 连接点半径\n\nexport const STROKE_WIDTH_SLECTED = 3;\n\nexport const STROKE_WIDTH = 2;\n\nexport const PORT_BG_CLASS_NAME = 'workflow-port-bg';\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\nexport const WorkflowPointStyle = styled.div`\n width: 20px;\n height: 20px;\n border-radius: 50%;\n margin-top: -10px;\n margin-left: -10px;\n left: 50%;\n top: 50%;\n position: absolute;\n // 非 hover 状态下的样式\n border: none;\n\n & > .symbol {\n opacity: 0;\n }\n\n .bg-circle {\n display: flex;\n align-items: center;\n justify-content: center;\n position: absolute;\n border-radius: 50%;\n width: 20px;\n height: 20px;\n background-color: var(--g-workflow-port-color-background, #fff);\n transform: scale(0.5);\n transition: all 0.2s linear 0s;\n }\n\n .bg {\n display: flex;\n align-items: center;\n justify-content: center;\n position: relative;\n width: 100%;\n height: 100%;\n border-radius: 50%;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n transform: scale(0.4, 0.4);\n transition: all 0.2s linear 0s;\n\n &.hasError {\n background: var(--g-workflow-port-color-error, red);\n }\n\n .symbol {\n position: absolute;\n width: 14px;\n height: 14px;\n opacity: 0;\n pointer-events: none;\n color: var(--g-workflow-port-color-background, #fff);\n transition: opacity 0.2s linear 0s;\n\n & > svg {\n width: 14px;\n height: 14px;\n }\n }\n\n .focus-circle {\n position: absolute;\n display: flex;\n justify-content: center;\n align-items: center;\n width: 8px;\n height: 8px;\n opacity: 0;\n background: var(--g-workflow-port-color-secondary, #9197f1);\n border-radius: 50%;\n transition: opacity 0.2s linear 0s;\n }\n }\n\n &.linked .bg:not(.hasError) {\n background: var(--g-workflow-port-color-primary, #4d53e8);\n }\n\n &.hovered .bg:not(.hasError) {\n border: none;\n cursor: crosshair;\n transform: scale(1, 1);\n background: var(--g-workflow-port-color-primary, #4d53e8);\n\n & > .symbol {\n opacity: 1;\n }\n }\n\n .cross-hair {\n position: relative;\n left: 2px;\n top: 2px;\n\n &::after,\n &::before {\n content: '';\n background: var(--g-workflow-port-color-background, #fff);\n border-radius: 2px;\n position: absolute;\n }\n\n &::after {\n left: 4px;\n width: 2px;\n height: 6px;\n box-shadow: 0 4px var(--g-workflow-port-color-background, #fff);\n }\n\n &::before {\n top: 4px;\n width: 6px;\n height: 2px;\n box-shadow: 4px 0 var(--g-workflow-port-color-background, #fff);\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\n// demo 环境自绘 cross-hair,正式环境使用 IconAdd\nexport default function CrossHair(): JSX.Element {\n return (\n <div className=\"symbol\">\n <div className=\"cross-hair\" />\n </div>\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\n// 箭头宽度\nexport const LINE_OFFSET = 6;\n\nexport const LINE_PADDING = 12;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { WorkflowLinesManager } from '@flowgram.ai/free-layout-core';\nimport { definePluginCreator, PluginContext } from '@flowgram.ai/core';\n\nimport { FreeLinesPluginOptions } from './type';\nimport { WorkflowLinesLayer } from './layer';\nimport { WorkflowBezierLineContribution, WorkflowFoldLineContribution } from './contributions';\n\nexport const createFreeLinesPlugin = definePluginCreator({\n singleton: true,\n onInit: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n ctx.playground.registerLayer(WorkflowLinesLayer, {\n ...opts,\n });\n },\n onReady: (ctx: PluginContext, opts: FreeLinesPluginOptions) => {\n const linesManager = ctx.container.get(WorkflowLinesManager);\n linesManager\n .registerContribution(WorkflowBezierLineContribution)\n .registerContribution(WorkflowFoldLineContribution);\n\n if (opts.contributions) {\n opts.contributions.forEach((contribution) => {\n linesManager.registerContribution(contribution);\n });\n }\n\n if (opts.defaultLineType) {\n linesManager.switchLineType(opts.defaultLineType);\n }\n },\n});\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport ReactDOM from 'react-dom';\nimport React, { ReactNode, useLayoutEffect, useState } from 'react';\n\nimport { inject, injectable } from 'inversify';\nimport { domUtils } from '@flowgram.ai/utils';\nimport { FlowRendererRegistry } from '@flowgram.ai/renderer';\nimport { StackingContextManager } from '@flowgram.ai/free-stack-plugin';\nimport {\n nanoid,\n WorkflowDocument,\n WorkflowHoverService,\n WorkflowLineEntity,\n WorkflowLineRenderData,\n WorkflowNodeEntity,\n WorkflowPortEntity,\n WorkflowSelectService,\n} from '@flowgram.ai/free-layout-core';\nimport { Layer, observeEntities, observeEntityDatas, TransformData } from '@flowgram.ai/core';\n\nimport { LineRenderProps, LinesLayerOptions } from '../type';\nimport { WorkflowLineRender } from '../components';\n\n@injectable()\nexport class WorkflowLinesLayer extends Layer<LinesLayerOptions> {\n static type = 'WorkflowLinesLayer';\n\n @inject(WorkflowHoverService) hoverService: WorkflowHoverService;\n\n @inject(WorkflowSelectService) selectService: WorkflowSelectService;\n\n @inject(StackingContextManager) stackContext: StackingContextManager;\n\n @inject(FlowRendererRegistry) rendererRegistry: FlowRendererRegistry;\n\n @observeEntities(WorkflowLineEntity) readonly lines: WorkflowLineEntity[];\n\n @observeEntities(WorkflowPortEntity) readonly ports: WorkflowPortEntity[];\n\n @observeEntityDatas(WorkflowNodeEntity, TransformData)\n readonly trans: TransformData[];\n\n @inject(WorkflowDocument) protected workflowDocument: WorkflowDocument;\n\n private layerID = nanoid();\n\n private mountedLines: Map<\n string,\n {\n line: WorkflowLineEntity;\n portal: ReactNode;\n version: string;\n }\n > = new Map();\n\n private _version = 0;\n\n /**\n * 节点线条\n */\n public node = domUtils.createDivWithClass('gedit-playground-layer gedit-flow-lines-layer');\n\n public onZoom(scale: number): void {\n this.node.style.transform = `scale(${scale})`;\n }\n\n public onReady() {\n this.pipelineNode.appendChild(this.node);\n this.toDispose.pushAll([\n this.selectService.onSelectionChanged(() => this.render()),\n this.hoverService.onHoveredChange(() => this.render()),\n this.workflowDocument.linesManager.onForceUpdate(() => {\n this.mountedLines.clear();\n this.bumpVersion();\n this.render();\n }),\n ]);\n }\n\n public dispose() {\n this.mountedLines.clear();\n }\n\n public render(): JSX.Element {\n const [, forceUpdate] = useState({});\n\n useLayoutEffect(() => {\n const updateLines = (): void => {\n let needsUpdate = false;\n\n // 批量处理所有线条的更新\n this.lines.forEach((line) => {\n const renderData = line.getData(WorkflowLineRenderData);\n const oldVersion = renderData.renderVersion;\n renderData.update();\n // 如果有任何一条线发生变化,标记需要更新\n if (renderData.renderVersion !== oldVersion) {\n needsUpdate = true;\n }\n });\n\n // 只在确实需要更新时触发重渲染\n if (needsUpdate) {\n forceUpdate({});\n }\n };\n\n const rafId = requestAnimationFrame(updateLines);\n return () => cancelAnimationFrame(rafId);\n }, [this.lines]); // 依赖项包含 lines\n\n const lines = this.lines.map((line) => this.renderLine(line));\n return <>{lines}</>;\n }\n\n // 用来绕过 memo\n private bumpVersion() {\n this._version = this._version + 1;\n if (this._version === Number.MAX_SAFE_INTEGER) {\n this._version = 0;\n }\n }\n\n private lineProps(line: WorkflowLineEntity): LineRenderProps {\n const { lineType } = this.workflowDocument.linesManager;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const version = this.lineVersion(line);\n\n return {\n key: line.id,\n color: line.color,\n selected,\n hovered,\n line,\n lineType,\n version,\n strokePrefix: this.layerID,\n rendererRegistry: this.rendererRegistry,\n };\n }\n\n private lineVersion(line: WorkflowLineEntity): string {\n const renderData = line.getData(WorkflowLineRenderData);\n const { renderVersion } = renderData;\n const selected = this.selectService.isSelected(line.id);\n const hovered = this.hoverService.isHovered(line.id);\n const { version: lineVersion, color } = line;\n\n const version = `v:${this._version},lv:${lineVersion},rv:${renderVersion},c:${color},s:${\n selected ? 'T' : 'F'\n },h:${hovered ? 'T' : 'F'}`;\n\n return version;\n }\n\n private lineComponent(props: LineRenderProps): ReactNode {\n const RenderInsideLine = this.options.renderInsideLine ?? (() => <></>);\n return (\n <WorkflowLineRender {...props}>\n <RenderInsideLine {...props} />\n </WorkflowLineRender>\n );\n }\n\n private renderLine(line: WorkflowLineEntity): ReactNode {\n const lineProps = this.lineProps(line);\n const cache = this.mountedLines.get(line.id);\n const isCached = cache !== undefined;\n const { portal: cachedPortal, version: cachedVersion } = cache ?? {};\n if (isCached && cachedVersion === lineProps.version) {\n // 如果已有缓存且版本相同,则直接返回缓存的 portal\n return cachedPortal;\n }\n if (!isCached) {\n // 如果缓存不存在,则将 line 挂载到 renderElement 上\n this.renderElement.appendChild(line.node);\n line.onDispose(() => {\n this.mountedLines.delete(line.id);\n line.node.remove();\n });\n }\n // 刷新缓存\n const portal = ReactDOM.createPortal(this.lineComponent(lineProps), line.node);\n this.mountedLines.set(line.id, { line, portal, version: lineProps.version });\n return portal;\n }\n\n private get renderElement(): HTMLElement {\n return this.stackContext.node;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { memo } from 'react';\n\nimport { LineSVG } from './line-svg';\n\nexport const WorkflowLineRender = memo(\n LineSVG,\n (prevProps, nextProps) => prevProps.version === nextProps.version\n);\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport clsx from 'clsx';\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { POINT_RADIUS } from '@flowgram.ai/free-layout-core';\nimport { WorkflowLineRenderData } from '@flowgram.ai/free-layout-core';\n\nimport { type ArrowRendererComponent } from '../../types/arrow-renderer';\nimport { LineRenderProps } from '../../type';\nimport { STROKE_WIDTH_SLECTED, STROKE_WIDTH } from '../../constants/points';\nimport { LINE_OFFSET } from '../../constants/lines';\nimport { LineStyle } from './index.style';\nimport { ArrowRenderer } from './arrow';\n\nconst PADDING = 12;\n\nexport const LineSVG = (props: LineRenderProps) => {\n const { line, color, selected, children, strokePrefix, rendererRegistry } = props;\n const { position, reverse, hideArrow, vertical } = line;\n\n const renderData = line.getData(WorkflowLineRenderData);\n const { bounds, path: bezierPath } = renderData;\n\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bounds.x + PADDING,\n y: p.y - bounds.y + PADDING,\n });\n\n const fromPos = toRelative(position.from);\n const toPos = toRelative(position.to);\n\n // 箭头位置计算\n const arrowToPos: IPoint =\n position.to.location === 'top'\n ? { x: toPos.x, y: toPos.y - POINT_RADIUS }\n : { x: toPos.x - POINT_RADIUS, y: toPos.y };\n const arrowFromPos: IPoint =\n position.from.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + POINT_RADIUS + LINE_OFFSET }\n : { x: fromPos.x + POINT_RADIUS + LINE_OFFSET, y: fromPos.y };\n\n const strokeWidth = selected\n ? line.uiState.strokeWidthSelected ?? STROKE_WIDTH_SLECTED\n : line.uiState.strokeWidth ?? STROKE_WIDTH;\n\n const strokeID = strokePrefix ? `${strokePrefix}-${line.id}` : line.id;\n\n // 获取自定义箭头渲染器,如果没有则使用默认的\n const CustomArrowRenderer = rendererRegistry?.tryToGetRendererComponent('arrow-renderer')\n ?.renderer as ArrowRendererComponent;\n const ArrowComponent = CustomArrowRenderer || ArrowRenderer;\n\n const path = (\n <path\n d={bezierPath}\n fill=\"none\"\n stroke={`url(#${strokeID})`}\n strokeWidth={strokeWidth}\n className={line.processing || line.flowing ? 'dashed-line flowing-line' : ''}\n />\n );\n\n return (\n <LineStyle\n className={clsx('gedit-flow-activity-edge', line.className)}\n style={{\n ...line.uiState.style,\n left: bounds.x - PADDING,\n top: bounds.y - PADDING,\n position: 'absolute',\n }}\n >\n {children}\n <svg width={bounds.width + PADDING * 2} height={bounds.height + PADDING * 2}>\n <defs>\n <linearGradient\n x1={vertical ? '100%' : '0%'}\n y1={vertical ? '0%' : '100%'}\n x2=\"100%\"\n y2=\"100%\"\n id={strokeID}\n gradientUnits=\"userSpaceOnUse\"\n >\n <stop stopColor={color} offset=\"0%\" />\n <stop stopColor={color} offset=\"100%\" />\n </linearGradient>\n </defs>\n <g>\n {path}\n <ArrowComponent\n id={strokeID}\n reverseArrow={reverse}\n pos={reverse ? arrowFromPos : arrowToPos}\n strokeWidth={strokeWidth}\n vertical={vertical}\n hide={hideArrow}\n line={line}\n />\n </g>\n </svg>\n </LineStyle>\n );\n};\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport styled from 'styled-components';\n\n// 添加一个固定类名,用于选中该节点\n\nexport const LineStyle = styled.div`\n position: absolute;\n\n @keyframes flowingDash {\n to {\n stroke-dashoffset: -13;\n }\n }\n\n .dashed-line {\n stroke-dasharray: 8, 5;\n }\n\n .flowing-line {\n animation: flowingDash 0.5s linear infinite;\n }\n`;\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport React from 'react';\n\nimport { type ArrowRendererProps } from '../../types/arrow-renderer';\nimport { LINE_OFFSET } from '../../constants/lines';\n\nexport function ArrowRenderer({\n id,\n pos,\n reverseArrow,\n strokeWidth,\n vertical,\n hide,\n}: ArrowRendererProps) {\n if (hide) {\n return null;\n }\n const arrowPath = vertical\n ? reverseArrow\n ? `M ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${pos.y - LINE_OFFSET} L ${\n pos.x + LINE_OFFSET\n },${pos.y}`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x + LINE_OFFSET\n },${pos.y - LINE_OFFSET}`\n : reverseArrow\n ? `M ${pos.x},${pos.y + LINE_OFFSET} L ${pos.x - LINE_OFFSET},${pos.y} L ${pos.x},${\n pos.y - LINE_OFFSET\n }`\n : `M ${pos.x - LINE_OFFSET},${pos.y - LINE_OFFSET} L ${pos.x},${pos.y} L ${\n pos.x - LINE_OFFSET\n },${pos.y + LINE_OFFSET}`;\n\n return (\n <path\n d={arrowPath}\n strokeLinecap=\"round\"\n stroke={`url(#${id})`}\n fill=\"none\"\n strokeWidth={strokeWidth}\n />\n );\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { Bezier } from 'bezier-js';\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { getBezierControlPoints } from './bezier-controls';\n\nexport interface BezierData {\n fromPos: IPoint;\n toPos: IPoint;\n bbox: Rectangle; // 外围矩形\n controls: IPoint[]; // 控制点\n bezier: Bezier;\n path: string;\n}\n\nexport class WorkflowBezierLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.BEZIER;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: BezierData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return Point.getDistance(pos, this.data.bezier.project(pos));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n this.data = this.calcBezier(params.fromPos, params.toPos);\n }\n\n private calcBezier(fromPos: LinePoint, toPos: LinePoint): BezierData {\n const controls = getBezierControlPoints(fromPos, toPos, this.entity.uiState.curvature);\n const bezier = new Bezier([fromPos, ...controls, toPos]);\n const bbox = bezier.bbox();\n const bboxBounds = new Rectangle(\n bbox.x.min,\n bbox.y.min,\n bbox.x.max - bbox.x.min,\n bbox.y.max - bbox.y.min\n );\n\n const path = this.getPath({ bbox: bboxBounds, fromPos, toPos, controls });\n\n this.data = {\n fromPos,\n toPos,\n bezier,\n bbox: bboxBounds,\n controls,\n path,\n };\n return this.data;\n }\n\n private getPath(params: {\n bbox: Rectangle;\n fromPos: LinePoint;\n toPos: LinePoint;\n controls: IPoint[];\n }): string {\n const { bbox } = params;\n // 相对位置转换函数\n const toRelative = (p: IPoint): IPoint => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n });\n const fromPos = toRelative(params.fromPos);\n const toPos = toRelative(params.toPos);\n\n const controls = params.controls.map((c) => toRelative(c));\n const shrink = this.entity.uiState.shrink;\n\n const renderFromPos: IPoint =\n params.fromPos.location === 'bottom'\n ? { x: fromPos.x, y: fromPos.y + shrink }\n : { x: fromPos.x + shrink, y: fromPos.y };\n\n const renderToPos: IPoint =\n params.toPos.location === 'top'\n ? { x: toPos.x, y: toPos.y - shrink }\n : { x: toPos.x - shrink, y: toPos.y };\n\n const controlPoints = controls.map((s) => `${s.x} ${s.y}`).join(',');\n return `M${renderFromPos.x} ${renderFromPos.y} C ${controlPoints}, ${renderToPos.x} ${renderToPos.y}`;\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint } from '@flowgram.ai/utils';\nimport { LinePoint, LinePointLocation } from '@flowgram.ai/free-layout-core';\n\nfunction getControlOffset(distance: number, curvature: number): number {\n if (distance >= 0) {\n return 0.5 * distance;\n }\n\n return curvature * 25 * Math.sqrt(-distance);\n}\n\nfunction getControlWithCurvature({\n location,\n x1,\n y1,\n x2,\n y2,\n curvature,\n}: {\n location: LinePointLocation;\n curvature: number;\n x1: number;\n x2: number;\n y1: number;\n y2: number;\n}): IPoint {\n switch (location) {\n case 'left':\n return {\n x: x1 - getControlOffset(x1 - x2, curvature),\n y: y1,\n };\n case 'right':\n return {\n x: x1 + getControlOffset(x2 - x1, curvature),\n y: y1,\n };\n case 'top':\n return {\n x: x1,\n y: y1 - getControlOffset(y1 - y2, curvature),\n };\n case 'bottom':\n return {\n x: x1,\n y: y1 + getControlOffset(y2 - y1, curvature),\n };\n }\n}\n\nexport function getBezierControlPoints(\n fromPos: LinePoint,\n toPos: LinePoint,\n curvature = 0.25\n): IPoint[] {\n const fromControl = getControlWithCurvature({\n location: fromPos.location,\n x1: fromPos.x,\n y1: fromPos.y,\n x2: toPos.x,\n y2: toPos.y,\n curvature,\n });\n const toControl = getControlWithCurvature({\n location: toPos.location,\n x1: toPos.x,\n y1: toPos.y,\n x2: fromPos.x,\n y2: fromPos.y,\n curvature,\n });\n return [fromControl, toControl];\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\nimport { LineType } from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { FoldLine } from './fold-line';\n\nexport interface FoldData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowFoldLineContribution implements WorkflowLineRenderContribution {\n public static type = LineType.LINE_CHART;\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: FoldData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n return FoldLine.getFoldLineToPointDistance(this.data.points, pos);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = FoldLine.getPoints({\n source: {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n location: fromPos.location,\n },\n target: {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n location: toPos.location,\n },\n });\n\n const bbox = FoldLine.getBounds(points);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n const path = FoldLine.getSmoothStepPath(adjustedPoints);\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { type IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport { LinePoint } from '@flowgram.ai/free-layout-core';\n\n/**\n * 计算点到线段的距离\n * @param point 待测试点\n * @param segStart 线段起点\n * @param segEnd 线段终点\n */\nconst getPointToSegmentDistance = (point: IPoint, segStart: IPoint, segEnd: IPoint): number => {\n const { x: px, y: py } = point;\n const { x: x1, y: y1 } = segStart;\n const { x: x2, y: y2 } = segEnd;\n\n const A = px - x1;\n const B = py - y1;\n const C = x2 - x1;\n const D = y2 - y1;\n\n const dot = A * C + B * D;\n const lenSq = C * C + D * D;\n\n // 参数方程中的t参数\n const param = lenSq === 0 ? -1 : dot / lenSq;\n\n let xx: number;\n let yy: number;\n\n if (param < 0) {\n xx = x1;\n yy = y1;\n } else if (param > 1) {\n xx = x2;\n yy = y2;\n } else {\n xx = x1 + param * C;\n yy = y1 + param * D;\n }\n\n const dx = px - xx;\n const dy = py - yy;\n\n return Math.sqrt(dx * dx + dy * dy);\n};\n\n/**\n * Fork from: https://github.com/xyflow/xyflow/blob/main/packages/system/src/utils/edges/smoothstep-edge.ts\n * MIT License\n * Copyright (c) 2019-2024 webkid GmbH\n */\nexport namespace FoldLine {\n const EDGE_RADIUS = 5;\n const OFFSET = 20;\n\n function getEdgeCenter({ source, target }: { source: IPoint; target: IPoint }): [number, number] {\n const xOffset = Math.abs(target.x - source.x) / 2;\n const centerX = target.x < source.x ? target.x + xOffset : target.x - xOffset;\n\n const yOffset = Math.abs(target.y - source.y) / 2;\n const centerY = target.y < source.y ? target.y + yOffset : target.y - yOffset;\n\n return [centerX, centerY];\n }\n\n const getDirection = ({ source, target }: { source: LinePoint; target: LinePoint }): IPoint => {\n if (source.location === 'left' || source.location === 'right') {\n return source.x < target.x ? { x: 1, y: 0 } : { x: -1, y: 0 };\n }\n return source.y < target.y ? { x: 0, y: 1 } : { x: 0, y: -1 };\n };\n\n const handleDirections = {\n left: { x: -1, y: 0 },\n right: { x: 1, y: 0 },\n top: { x: 0, y: -1 },\n bottom: { x: 0, y: 1 },\n };\n // eslint-disable-next-line complexity\n export function getPoints({\n source,\n target,\n }: {\n source: LinePoint;\n target: LinePoint;\n }): IPoint[] {\n const sourceDir = handleDirections[source.location];\n const targetDir = handleDirections[target.location];\n const sourceGapped: LinePoint = {\n x: source.x + sourceDir.x * OFFSET,\n y: source.y + sourceDir.y * OFFSET,\n location: source.location,\n };\n const targetGapped: LinePoint = {\n x: target.x + targetDir.x * OFFSET,\n y: target.y + targetDir.y * OFFSET,\n location: target.location,\n };\n const dir = getDirection({\n source: sourceGapped,\n target: targetGapped,\n });\n const dirAccessor = dir.x !== 0 ? 'x' : 'y';\n const currDir = dir[dirAccessor];\n\n let points: IPoint[] = [];\n let centerX, centerY;\n\n const [defaultCenterX, defaultCenterY] = getEdgeCenter({\n source,\n target,\n });\n\n // 计算向量乘积\n if (sourceDir[dirAccessor] * targetDir[dirAccessor] === -1) {\n centerX = defaultCenterX;\n centerY = defaultCenterY;\n\n const verticalSplit: IPoint[] = [\n { x: centerX, y: sourceGapped.y },\n { x: centerX, y: targetGapped.y },\n ];\n\n const horizontalSplit: IPoint[] = [\n { x: sourceGapped.x, y: centerY },\n { x: targetGapped.x, y: centerY },\n ];\n\n if (sourceDir[dirAccessor] === currDir) {\n points = dirAccessor === 'x' ? verticalSplit : horizontalSplit;\n } else {\n points = dirAccessor === 'x' ? horizontalSplit : verticalSplit;\n }\n } else {\n // sourceTarget means we take x from source and y from target, targetSource is the opposite\n const sourceTarget: IPoint[] = [{ x: sourceGapped.x, y: targetGapped.y }];\n const targetSource: IPoint[] = [{ x: targetGapped.x, y: sourceGapped.y }];\n // this handles edges with same handle positions\n if (dirAccessor === 'x') {\n points = sourceDir.x === currDir ? targetSource : sourceTarget;\n } else {\n points = sourceDir.y === currDir ? sourceTarget : targetSource;\n }\n\n // these are conditions for handling mixed handle positions like Right -> Bottom for example\n const dirAccessorOpposite = dirAccessor === 'x' ? 'y' : 'x';\n const isSameDir = sourceDir[dirAccessor] === targetDir[dirAccessorOpposite];\n const sourceGtTargetOppo =\n sourceGapped[dirAccessorOpposite] > targetGapped[dirAccessorOpposite];\n const sourceLtTargetOppo =\n sourceGapped[dirAccessorOpposite] < targetGapped[dirAccessorOpposite];\n const flipSourceTarget =\n (sourceDir[dirAccessor] === 1 &&\n ((!isSameDir && sourceGtTargetOppo) || (isSameDir && sourceLtTargetOppo))) ||\n (sourceDir[dirAccessor] !== 1 &&\n ((!isSameDir && sourceLtTargetOppo) || (isSameDir && sourceGtTargetOppo)));\n\n if (flipSourceTarget) {\n points = dirAccessor === 'x' ? sourceTarget : targetSource;\n }\n\n const sourceGapPoint = { x: sourceGapped.x, y: sourceGapped.y };\n const targetGapPoint = { x: targetGapped.x, y: targetGapped.y };\n const maxXDistance = Math.max(\n Math.abs(sourceGapPoint.x - points[0].x),\n Math.abs(targetGapPoint.x - points[0].x)\n );\n const maxYDistance = Math.max(\n Math.abs(sourceGapPoint.y - points[0].y),\n Math.abs(targetGapPoint.y - points[0].y)\n );\n\n if (maxXDistance >= maxYDistance) {\n centerX = (sourceGapPoint.x + targetGapPoint.x) / 2;\n centerY = points[0].y;\n } else {\n centerX = points[0].x;\n centerY = (sourceGapPoint.y + targetGapPoint.y) / 2;\n }\n }\n\n const pathPoints = [\n source,\n { x: sourceGapped.x, y: sourceGapped.y },\n ...points,\n { x: targetGapped.x, y: targetGapped.y },\n target,\n ];\n\n return pathPoints;\n }\n\n function getBend(a: IPoint, b: IPoint, c: IPoint): string {\n const bendSize = Math.min(\n Point.getDistance(a, b) / 2,\n Point.getDistance(b, c) / 2,\n EDGE_RADIUS\n );\n const { x, y } = b;\n\n // no bend\n if ((a.x === x && x === c.x) || (a.y === y && y === c.y)) {\n return `L${x} ${y}`;\n }\n\n // first segment is horizontal\n if (a.y === y) {\n const xDir = a.x < c.x ? -1 : 1;\n const yDir = a.y < c.y ? 1 : -1;\n return `L ${x + bendSize * xDir},${y}Q ${x},${y} ${x},${y + bendSize * yDir}`;\n }\n\n const xDir = a.x < c.x ? 1 : -1;\n const yDir = a.y < c.y ? -1 : 1;\n return `L ${x},${y + bendSize * yDir}Q ${x},${y} ${x + bendSize * xDir},${y}`;\n }\n\n /**\n * 实现 reactFlow 原本的折叠线交互\n */\n export function getSmoothStepPath(points: IPoint[]): string {\n const path = points.reduce<string>((res, p, i) => {\n let segment = '';\n\n if (i > 0 && i < points.length - 1) {\n segment = getBend(points[i - 1], p, points[i + 1]);\n } else {\n segment = `${i === 0 ? 'M' : 'L'}${p.x} ${p.y}`;\n }\n\n res += segment;\n\n return res;\n }, '');\n\n return path;\n }\n export function getBounds(points: IPoint[]): Rectangle {\n const xList = points.map((p) => p.x);\n const yList = points.map((p) => p.y);\n const left = Math.min(...xList);\n const right = Math.max(...xList);\n const top = Math.min(...yList);\n const bottom = Math.max(...yList);\n return Rectangle.createRectangleWithTwoPoints(\n {\n x: left,\n y: top,\n },\n {\n x: right,\n y: bottom,\n }\n );\n }\n /**\n * 计算点到折线的最短距离\n * @param points 折线的所有端点\n * @param pos 待测试点\n * @returns 最短距离\n */\n export const getFoldLineToPointDistance = (points: IPoint[], pos: IPoint): number => {\n // 特殊情况处理\n if (points.length === 0) {\n return Infinity;\n }\n\n if (points.length === 1) {\n return Point.getDistance(points[0]!, pos);\n }\n\n // 构建线段数组\n const lines: [IPoint, IPoint][] = [];\n for (let i = 0; i < points.length - 1; i++) {\n lines.push([points[i]!, points[i + 1]!]);\n }\n\n // 计算点到每个线段的最短距离\n const distances = lines.map((line) => {\n const [p1, p2] = line;\n return getPointToSegmentDistance(pos, p1, p2);\n });\n\n return Math.min(...distances);\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n LinePoint,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\nimport { projectPointOnLine } from './point-on-line';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowStraightLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowStraightLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: StraightData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n const [start, end] = this.data.points;\n return Point.getDistance(pos, projectPointOnLine(pos, start, end));\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: LinePoint; toPos: LinePoint }): void {\n const { fromPos, toPos } = params;\n\n // 根据方向预先计算源点和目标点的偏移\n const sourceOffset = {\n x: fromPos.location === 'bottom' ? 0 : POINT_RADIUS,\n y: fromPos.location === 'bottom' ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: toPos.location === 'top' ? 0 : -POINT_RADIUS,\n y: toPos.location === 'top' ? -POINT_RADIUS : 0,\n };\n\n const points = [\n {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n },\n {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n },\n ];\n\n const bbox = Rectangle.createRectangleWithTwoPoints(points[0], points[1]);\n\n // 调整所有点到 SVG 视口坐标系\n const adjustedPoints = points.map((p) => ({\n x: p.x - bbox.x + LINE_PADDING,\n y: p.y - bbox.y + LINE_PADDING,\n }));\n\n // 生成直线路径\n const path = `M ${adjustedPoints[0].x} ${adjustedPoints[0].y} L ${adjustedPoints[1].x} ${adjustedPoints[1].y}`;\n\n this.data = {\n points,\n path,\n bbox,\n };\n }\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Rectangle } from '@flowgram.ai/utils';\n\nexport interface StraightData {\n points: IPoint[];\n path: string;\n bbox: Rectangle;\n}\n\n/**\n * 计算点到直线的投影点\n */\nexport function projectPointOnLine(point: IPoint, lineStart: IPoint, lineEnd: IPoint): IPoint {\n const dx = lineEnd.x - lineStart.x;\n const dy = lineEnd.y - lineStart.y;\n\n // 如果是垂直线\n if (dx === 0) {\n return { x: lineStart.x, y: point.y };\n }\n // 如果是水平线\n if (dy === 0) {\n return { x: point.x, y: lineStart.y };\n }\n\n const t = ((point.x - lineStart.x) * dx + (point.y - lineStart.y) * dy) / (dx * dx + dy * dy);\n const clampedT = Math.max(0, Math.min(1, t));\n\n return {\n x: lineStart.x + clampedT * dx,\n y: lineStart.y + clampedT * dy,\n };\n}\n","/**\n * Copyright (c) 2025 Bytedance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n */\n\nimport { IPoint, Point, Rectangle } from '@flowgram.ai/utils';\nimport {\n POINT_RADIUS,\n WorkflowLineEntity,\n WorkflowLineRenderContribution,\n} from '@flowgram.ai/free-layout-core';\n\nimport { LINE_PADDING } from '../../constants/lines';\n\nexport interface ArcData {\n fromPos: IPoint;\n toPos: IPoint;\n path: string;\n bbox: Rectangle;\n}\n\nexport class WorkflowArkLineContribution implements WorkflowLineRenderContribution {\n public static type = 'WorkflowArkLineContribution';\n\n public entity: WorkflowLineEntity;\n\n constructor(entity: WorkflowLineEntity) {\n this.entity = entity;\n }\n\n private data?: ArcData;\n\n public get path(): string {\n return this.data?.path ?? '';\n }\n\n public calcDistance(pos: IPoint): number {\n if (!this.data) {\n return Number.MAX_SAFE_INTEGER;\n }\n\n const { fromPos, toPos, bbox } = this.data;\n\n // 首先检查点是否在包围盒范围内\n if (!bbox.contains(pos.x, pos.y)) {\n // 如果点在包围盒外,计算到包围盒边界的最短距离\n const dx = Math.max(bbox.x - pos.x, 0, pos.x - (bbox.x + bbox.width));\n const dy = Math.max(bbox.y - pos.y, 0, pos.y - (bbox.y + bbox.height));\n return Math.sqrt(dx * dx + dy * dy);\n }\n\n // 计算圆弧的中心点和半径\n const center = {\n x: (fromPos.x + toPos.x) / 2,\n y: (fromPos.y + toPos.y) / 2,\n };\n const radius = Point.getDistance(fromPos, center);\n\n // 计算点到圆心的距离\n const distanceToCenter = Point.getDistance(pos, center);\n\n // 返回点到圆弧的近似距离\n return Math.abs(distanceToCenter - radius);\n }\n\n public get bounds(): Rectangle {\n if (!this.data) {\n return new Rectangle();\n }\n return this.data.bbox;\n }\n\n public update(params: { fromPos: IPoint; toPos: IPoint }): void {\n const { fromPos, toPos } = params;\n const { vertical } = this.entity;\n\n const sourceOffset = {\n x: vertical ? 0 : POINT_RADIUS,\n y: vertical ? POINT_RADIUS : 0,\n };\n const targetOffset = {\n x: vertical ? 0 : -POINT_RADIUS,\n y: vertical ? -POINT_RADIUS : 0,\n };\n\n const start = {\n x: fromPos.x + sourceOffset.x,\n y: fromPos.y + sourceOffset.y,\n };\n const end = {\n x: toPos.x + targetOffset.x,\n y: toPos.y + targetOffset.y,\n };\n\n // 计算圆弧的包围盒\n const bbox = this.calculateArcBBox(start, end);\n\n // 生成圆弧路径\n const path = this.getArcPath(start, end, bbox);\n\n this.data = {\n fromPos: start,\n toPos: end,\n path,\n bbox,\n };\n }\n\n private calculateArcBBox(start: IPoint, end: IPoint): Rectangle {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const radius = Math.sqrt(dx * dx + dy * dy) / 2;\n\n const centerX = (start.x + end.x) / 2;\n const centerY = (start.y + end.y) / 2;\n\n return new Rectangle(centerX - radius, centerY - radius, radius * 2, radius * 2);\n }\n\n private getArcPath(start: IPoint, end: IPoint, bbox: Rectangle): string {\n const dx = end.x - start.x;\n const dy = end.y - start.y;\n const distance = Math.sqrt(dx * dx + dy * dy);\n\n // 调整点到相对坐标\n const startRel = {\n x: start.x - bbox.x + LINE_PADDING,\n y: start.y - bbox.y + LINE_PADDING,\n };\n const endRel = {\n x: end.x - bbox.x + LINE_PADDING,\n y: end.y - bbox.y + LINE_PADDING,\n };\n\n // 使用 SVG 圆弧命令\n return `M ${startRel.x} ${startRel.y} A ${distance / 2} ${distance / 2} 0 0 1 ${endRel.x} ${\n endRel.y\n }`;\n }\n}\n"],"mappings":"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","names":["import_react","styled","React","React","classNames","ReactDOM","import_free_layout_core","import_core","import_react_dom","import_react","import_free_layout_core","import_core","import_react","import_react","import_clsx","import_free_layout_core","import_styled_components","styled","import_react","React","React","clsx","React","ReactDOM","import_utils","import_free_layout_core","import_utils","import_free_layout_core","import_utils","FoldLine","xDir","yDir","import_utils","import_free_layout_core","import_utils","import_free_layout_core"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@flowgram.ai/free-lines-plugin",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.2",
|
|
4
4
|
"homepage": "https://flowgram.ai/",
|
|
5
5
|
"repository": "https://github.com/bytedance/flowgram.ai",
|
|
6
6
|
"license": "MIT",
|
|
@@ -20,11 +20,11 @@
|
|
|
20
20
|
"clsx": "^1.1.1",
|
|
21
21
|
"inversify": "^6.0.1",
|
|
22
22
|
"reflect-metadata": "~0.2.2",
|
|
23
|
-
"@flowgram.ai/core": "0.4.
|
|
24
|
-
"@flowgram.ai/free-layout-core": "0.4.
|
|
25
|
-
"@flowgram.ai/free-stack-plugin": "0.4.
|
|
26
|
-
"@flowgram.ai/renderer": "0.4.
|
|
27
|
-
"@flowgram.ai/utils": "0.4.
|
|
23
|
+
"@flowgram.ai/core": "0.4.2",
|
|
24
|
+
"@flowgram.ai/free-layout-core": "0.4.2",
|
|
25
|
+
"@flowgram.ai/free-stack-plugin": "0.4.2",
|
|
26
|
+
"@flowgram.ai/renderer": "0.4.2",
|
|
27
|
+
"@flowgram.ai/utils": "0.4.2"
|
|
28
28
|
},
|
|
29
29
|
"devDependencies": {
|
|
30
30
|
"@types/bezier-js": "4.1.3",
|
|
@@ -40,8 +40,8 @@
|
|
|
40
40
|
"tsup": "^8.0.1",
|
|
41
41
|
"typescript": "^5.8.3",
|
|
42
42
|
"vitest": "^0.34.6",
|
|
43
|
-
"@flowgram.ai/eslint-config": "0.4.
|
|
44
|
-
"@flowgram.ai/ts-config": "0.4.
|
|
43
|
+
"@flowgram.ai/eslint-config": "0.4.2",
|
|
44
|
+
"@flowgram.ai/ts-config": "0.4.2"
|
|
45
45
|
},
|
|
46
46
|
"peerDependencies": {
|
|
47
47
|
"react": ">=16.8",
|