diff --git a/cypress/platform/saurabh.html b/cypress/platform/saurabh.html index b83aa2a3b..ecf3463c1 100644 --- a/cypress/platform/saurabh.html +++ b/cypress/platform/saurabh.html @@ -62,16 +62,18 @@
- flowchart TD - B2@{ icon: "fa:bell", form: "square", pos: "t", h: 80 } + flowchart LR + B2@{ icon: "fa:address-book", form: "square", pos: "b", h: 80 } - W --> B2 - X --> B2 - Y --> B2 - Z --> B2 + W --> B2 --> x1 + X --> B2 --> x2 + Y --> B2 --> x3 + Z --> B2 --> x4 B2 --sas--> C + A --> B2 +
diff --git a/packages/mermaid/src/rendering-util/rendering-elements/shapes/icon.ts b/packages/mermaid/src/rendering-util/rendering-elements/shapes/icon.ts index 051ae3119..f1c928346 100644 --- a/packages/mermaid/src/rendering-util/rendering-elements/shapes/icon.ts +++ b/packages/mermaid/src/rendering-util/rendering-elements/shapes/icon.ts @@ -19,18 +19,20 @@ export const icon = async ( const iconSize = Math.max(assetHeight, assetWidth); const defaultWidth = flowchart?.wrappingWidth; node.width = Math.max(iconSize, defaultWidth ?? 0); - const { nodeBorder } = themeVariables; - const { stylesMap } = compileStyles(node); const { shapeSvg, bbox, label } = await labelHelper(parent, node, 'icon-shape default'); const topLabel = node.pos === 't'; const height = iconSize; - const width = Math.max(iconSize, bbox.width); + const width = iconSize; + const { nodeBorder } = themeVariables; + const { stylesMap } = compileStyles(node); const x = -width / 2; const y = -height / 2; + const labelPadding = node.label ? 8 : 0; + // @ts-ignore - rough is not typed const rc = rough.svg(shapeSvg); const options = userNodeOverrides(node, { stroke: 'none', fill: 'none' }); @@ -42,7 +44,17 @@ export const icon = async ( const iconNode = rc.rectangle(x, y, width, height, options); + const outerWidth = Math.max(width, bbox.width); + const outerHeight = height + bbox.height + labelPadding; + + const outerNode = rc.rectangle(-outerWidth / 2, -outerHeight / 2, outerWidth, outerHeight, { + ...options, + fill: 'none', + stroke: 'none', + }); + const iconShape = shapeSvg.insert(() => iconNode, ':first-child'); + const outerShape = shapeSvg.insert(() => outerNode); if (node.icon) { const iconElem = shapeSvg.append('g'); @@ -52,21 +64,26 @@ export const icon = async ( const iconBBox = iconElem.node().getBBox(); const iconWidth = iconBBox.width; const iconHeight = iconBBox.height; + const iconX = iconBBox.x; + const iconY = iconBBox.y; iconElem.attr( 'transform', - `translate(${-iconWidth / 2},${topLabel ? height / 2 - iconHeight + bbox.height / 2 : -height / 2 - bbox.height / 2})` + `translate(${-iconWidth / 2 - iconX},${topLabel ? outerHeight / 2 - iconHeight - iconY : -outerHeight / 2 - iconY})` ); iconElem.selectAll('path').attr('fill', stylesMap.get('stroke') || nodeBorder); } label.attr( 'transform', - `translate(${-width / 2 + width / 2 - bbox.width / 2},${topLabel ? -height / 2 - 5 - bbox.height / 2 : height / 2 - bbox.height / 2})` + `translate(${-width / 2 + width / 2 - bbox.width / 2},${topLabel ? -height / 2 - bbox.height / 2 - labelPadding / 2 : height / 2 - bbox.height / 2 + labelPadding / 2})` ); - iconShape.attr('transform', `translate(${0},${topLabel ? bbox.height / 2 : -bbox.height / 2})`); + iconShape.attr( + 'transform', + `translate(${0},${topLabel ? bbox.height / 2 + labelPadding / 2 : -bbox.height / 2 - labelPadding / 2})` + ); - updateNodeBounds(node, shapeSvg); + updateNodeBounds(node, outerShape); node.intersect = function (point) { log.info('iconSquare intersect', node, point); @@ -75,51 +92,34 @@ export const icon = async ( } const dx = node.x ?? 0; const dy = node.y ?? 0; - const nodeWidth = node.width ?? 0; const nodeHeight = node.height ?? 0; - + let points = []; if (topLabel) { - const points = [ - { x: dx - nodeWidth / 2, y: dy - nodeHeight / 2 - bbox.height / 2 }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 - bbox.height / 2 }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2 }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2, - y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2, - y: dy + nodeHeight / 2 - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2 - width, - y: dy + nodeHeight / 2 - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2 - width, - y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2, - }, - { x: dx - nodeWidth / 2, y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2 }, + points = [ + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx + width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx + width / 2, y: dy + nodeHeight / 2 }, + { x: dx - width / 2, y: dy + nodeHeight / 2 }, + { x: dx - width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, ]; - const pos = intersect.polygon(node, points, point); - return pos; } else { - const points = [ - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2, y: dy - nodeHeight / 2 }, - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2 + width, y: dy - nodeHeight / 2 }, - { - x: dx - nodeWidth / 2 + (bbox.width - width) / 2 + width, - y: dy - nodeHeight / 2 + height, - }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 + height }, - { x: dx + nodeWidth / 2, y: dy + nodeHeight / 2 }, - { x: dx - nodeWidth / 2, y: dy + nodeHeight / 2 }, - { x: dx - nodeWidth / 2, y: dy + nodeHeight / 2 - bbox.height }, - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2, y: dy + nodeHeight / 2 - bbox.height }, + points = [ + { x: dx - width / 2, y: dy - nodeHeight / 2 }, + { x: dx + width / 2, y: dy - nodeHeight / 2 }, + { x: dx + width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx + bbox.width / 2 / 2, y: dy + nodeHeight / 2 }, + { x: dx - bbox.width / 2, y: dy + nodeHeight / 2 }, + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx - width / 2, y: dy - nodeHeight / 2 + height }, ]; - const pos = intersect.polygon(node, points, point); - return pos; } + + const pos = intersect.polygon(node, points, point); + return pos; }; return shapeSvg; diff --git a/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconCircle.ts b/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconCircle.ts index 2d0072d11..df7c55f53 100644 --- a/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconCircle.ts +++ b/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconCircle.ts @@ -19,15 +19,13 @@ export const iconCircle = async ( const iconSize = Math.max(assetHeight, assetWidth); const defaultWidth = flowchart?.wrappingWidth; node.width = Math.max(iconSize, defaultWidth ?? 0); - const { shapeSvg, bbox, halfPadding, label } = await labelHelper( - parent, - node, - 'icon-shape default' - ); + const { shapeSvg, bbox, label } = await labelHelper(parent, node, 'icon-shape default'); + + const padding = 20; + const labelPadding = node.label ? 8 : 0; const topLabel = node.pos === 't'; - const diameter = iconSize + halfPadding * 2; const { nodeBorder, mainBkg } = themeVariables; const { stylesMap } = compileStyles(node); // @ts-ignore - rough is not typed @@ -39,32 +37,48 @@ export const iconCircle = async ( options.fillStyle = 'solid'; } - const iconNode = rc.circle(0, 0, diameter, options); - - const iconShape = shapeSvg.insert(() => iconNode, ':first-child'); const iconElem = shapeSvg.append('g'); if (node.icon) { iconElem.html( `${await getIconSVG(node.icon, { height: iconSize, fallbackPrefix: '' })} ` ); - const iconBBox = iconElem.node().getBBox(); - const iconWidth = iconBBox.width; - const iconHeight = iconBBox.height; - iconElem.attr( - 'transform', - `translate(${-iconWidth / 2},${topLabel ? diameter / 2 - iconHeight - halfPadding + bbox.height / 2 : -diameter / 2 + halfPadding - bbox.height / 2})` - ); - iconElem.selectAll('path').attr('fill', stylesMap.get('stroke') || nodeBorder); } + const iconBBox = iconElem.node().getBBox(); + const iconWidth = iconBBox.width; + const iconHeight = iconBBox.height; + const iconX = iconBBox.x; + const iconY = iconBBox.y; + const diameter = Math.max(iconWidth, iconHeight) + padding * 2; + const iconNode = rc.circle(0, 0, diameter, options); + + const outerWidth = Math.max(diameter, bbox.width); + const outerHeight = diameter + bbox.height + labelPadding; + + const outerNode = rc.rectangle(-outerWidth / 2, -outerHeight / 2, outerWidth, outerHeight, { + ...options, + fill: 'none', + stroke: 'none', + }); + + const iconShape = shapeSvg.insert(() => iconNode, ':first-child'); + const outerShape = shapeSvg.insert(() => outerNode); + iconElem.attr( + 'transform', + `translate(${-iconWidth / 2 - iconX},${topLabel ? diameter / 2 - iconHeight - padding + bbox.height / 2 - iconY : -diameter / 2 + padding - bbox.height / 2 - labelPadding / 2 - iconY})` + ); + iconElem.selectAll('path').attr('fill', stylesMap.get('stroke') || nodeBorder); label.attr( 'transform', - `translate(${-diameter / 2 + diameter / 2 - bbox.width / 2},${topLabel ? -diameter / 2 - bbox.height / 2 : diameter / 2 - bbox.height / 2})` + `translate(${-diameter / 2 + diameter / 2 - bbox.width / 2},${topLabel ? -diameter / 2 - bbox.height / 2 : diameter / 2 - bbox.height / 2 + labelPadding / 2})` ); - iconShape.attr('transform', `translate(${0},${topLabel ? bbox.height / 2 : -bbox.height / 2})`); + iconShape.attr( + 'transform', + `translate(${0},${topLabel ? bbox.height / 2 : -bbox.height / 2 - labelPadding / 2})` + ); - updateNodeBounds(node, shapeSvg); + updateNodeBounds(node, outerShape); node.intersect = function (point) { log.info('iconSquare intersect', node, point); diff --git a/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconRounded.ts b/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconRounded.ts index 8aca67682..1c5d46568 100644 --- a/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconRounded.ts +++ b/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconRounded.ts @@ -1,6 +1,6 @@ import { log } from '../../../logger.js'; import { labelHelper, updateNodeBounds } from './util.js'; -import type { Node, RenderOptions } from '../../types.js'; +import type { Node, RenderOptions } from '../../types.d.ts'; import type { SVG } from '../../../diagram-api/types.js'; import { compileStyles, styles2String, userNodeOverrides } from './handDrawnShapeStyles.js'; import rough from 'roughjs'; @@ -36,6 +36,8 @@ export const iconRounded = async ( const x = -width / 2; const y = -height / 2; + const labelPadding = node.label ? 8 : 0; + // @ts-ignore - rough is not typed const rc = rough.svg(shapeSvg); const options = userNodeOverrides(node, { stroke: stylesMap.get('fill') || mainBkg }); @@ -47,7 +49,17 @@ export const iconRounded = async ( const iconNode = rc.path(createRoundedRectPathD(x, y, width, height, 5), options); + const outerWidth = Math.max(width, bbox.width); + const outerHeight = height + bbox.height + labelPadding; + + const outerNode = rc.rectangle(-outerWidth / 2, -outerHeight / 2, outerWidth, outerHeight, { + ...options, + fill: 'none', + stroke: 'none', + }); + const iconShape = shapeSvg.insert(() => iconNode, ':first-child'); + const outerShape = shapeSvg.insert(() => outerNode); if (node.icon) { const iconElem = shapeSvg.append('g'); @@ -57,21 +69,26 @@ export const iconRounded = async ( const iconBBox = iconElem.node().getBBox(); const iconWidth = iconBBox.width; const iconHeight = iconBBox.height; + const iconX = iconBBox.x; + const iconY = iconBBox.y; iconElem.attr( 'transform', - `translate(${-iconWidth / 2},${topLabel ? height / 2 - iconHeight - halfPadding + bbox.height / 2 : -height / 2 + halfPadding - bbox.height / 2})` + `translate(${-iconWidth / 2 - iconX},${topLabel ? outerHeight / 2 - iconHeight - halfPadding - iconY : -outerHeight / 2 + halfPadding - iconY})` ); iconElem.selectAll('path').attr('fill', stylesMap.get('stroke') || nodeBorder); } label.attr( 'transform', - `translate(${-width / 2 + width / 2 - bbox.width / 2},${topLabel ? -height / 2 - 5 - bbox.height / 2 : height / 2 - bbox.height / 2})` + `translate(${-width / 2 + width / 2 - bbox.width / 2},${topLabel ? -height / 2 - bbox.height / 2 - labelPadding / 2 : height / 2 - bbox.height / 2 + labelPadding / 2})` ); - iconShape.attr('transform', `translate(${0},${topLabel ? bbox.height / 2 : -bbox.height / 2})`); + iconShape.attr( + 'transform', + `translate(${0},${topLabel ? bbox.height / 2 + labelPadding / 2 : -bbox.height / 2 - labelPadding / 2})` + ); - updateNodeBounds(node, shapeSvg); + updateNodeBounds(node, outerShape); node.intersect = function (point) { log.info('iconSquare intersect', node, point); @@ -80,51 +97,34 @@ export const iconRounded = async ( } const dx = node.x ?? 0; const dy = node.y ?? 0; - const nodeWidth = node.width ?? 0; const nodeHeight = node.height ?? 0; - + let points = []; if (topLabel) { - const points = [ - { x: dx - nodeWidth / 2, y: dy - nodeHeight / 2 - bbox.height / 2 }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 - bbox.height / 2 }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2 }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2, - y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2, - y: dy + nodeHeight / 2 - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2 - width, - y: dy + nodeHeight / 2 - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2 - width, - y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2, - }, - { x: dx - nodeWidth / 2, y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2 }, + points = [ + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx + width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx + width / 2, y: dy + nodeHeight / 2 }, + { x: dx - width / 2, y: dy + nodeHeight / 2 }, + { x: dx - width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, ]; - const pos = intersect.polygon(node, points, point); - return pos; } else { - const points = [ - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2, y: dy - nodeHeight / 2 }, - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2 + width, y: dy - nodeHeight / 2 }, - { - x: dx - nodeWidth / 2 + (bbox.width - width) / 2 + width, - y: dy - nodeHeight / 2 + height, - }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 + height }, - { x: dx + nodeWidth / 2, y: dy + nodeHeight / 2 }, - { x: dx - nodeWidth / 2, y: dy + nodeHeight / 2 }, - { x: dx - nodeWidth / 2, y: dy + nodeHeight / 2 - bbox.height }, - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2, y: dy + nodeHeight / 2 - bbox.height }, + points = [ + { x: dx - width / 2, y: dy - nodeHeight / 2 }, + { x: dx + width / 2, y: dy - nodeHeight / 2 }, + { x: dx + width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx + bbox.width / 2 / 2, y: dy + nodeHeight / 2 }, + { x: dx - bbox.width / 2, y: dy + nodeHeight / 2 }, + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx - width / 2, y: dy - nodeHeight / 2 + height }, ]; - const pos = intersect.polygon(node, points, point); - return pos; } + + const pos = intersect.polygon(node, points, point); + return pos; }; return shapeSvg; diff --git a/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconSquare.ts b/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconSquare.ts index 9d0375874..b49d76cf6 100644 --- a/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconSquare.ts +++ b/packages/mermaid/src/rendering-util/rendering-elements/shapes/iconSquare.ts @@ -35,6 +35,8 @@ export const iconSquare = async ( const x = -width / 2; const y = -height / 2; + const labelPadding = node.label ? 8 : 0; + // @ts-ignore - rough is not typed const rc = rough.svg(shapeSvg); const options = userNodeOverrides(node, { stroke: stylesMap.get('fill') || mainBkg }); @@ -46,7 +48,17 @@ export const iconSquare = async ( const iconNode = rc.rectangle(x, y, width, height, options); + const outerWidth = Math.max(width, bbox.width); + const outerHeight = height + bbox.height + labelPadding; + + const outerNode = rc.rectangle(-outerWidth / 2, -outerHeight / 2, outerWidth, outerHeight, { + ...options, + fill: 'none', + stroke: 'none', + }); + const iconShape = shapeSvg.insert(() => iconNode, ':first-child'); + const outerShape = shapeSvg.insert(() => outerNode); if (node.icon) { const iconElem = shapeSvg.append('g'); @@ -56,21 +68,26 @@ export const iconSquare = async ( const iconBBox = iconElem.node().getBBox(); const iconWidth = iconBBox.width; const iconHeight = iconBBox.height; + const iconX = iconBBox.x; + const iconY = iconBBox.y; iconElem.attr( 'transform', - `translate(${-iconWidth / 2},${topLabel ? height / 2 - iconHeight - halfPadding + bbox.height / 2 : -height / 2 + halfPadding - bbox.height / 2})` + `translate(${-iconWidth / 2 - iconX},${topLabel ? outerHeight / 2 - iconHeight - halfPadding - iconY : -outerHeight / 2 + halfPadding - iconY})` ); iconElem.selectAll('path').attr('fill', stylesMap.get('stroke') || nodeBorder); } label.attr( 'transform', - `translate(${-width / 2 + width / 2 - bbox.width / 2},${topLabel ? -height / 2 - 5 - bbox.height / 2 : height / 2 - bbox.height / 2})` + `translate(${-width / 2 + width / 2 - bbox.width / 2},${topLabel ? -height / 2 - bbox.height / 2 - labelPadding / 2 : height / 2 - bbox.height / 2 + labelPadding / 2})` ); - iconShape.attr('transform', `translate(${0},${topLabel ? bbox.height / 2 : -bbox.height / 2})`); + iconShape.attr( + 'transform', + `translate(${0},${topLabel ? bbox.height / 2 + labelPadding / 2 : -bbox.height / 2 - labelPadding / 2})` + ); - updateNodeBounds(node, shapeSvg); + updateNodeBounds(node, outerShape); node.intersect = function (point) { log.info('iconSquare intersect', node, point); @@ -79,51 +96,34 @@ export const iconSquare = async ( } const dx = node.x ?? 0; const dy = node.y ?? 0; - const nodeWidth = node.width ?? 0; const nodeHeight = node.height ?? 0; - + let points = []; if (topLabel) { - const points = [ - { x: dx - nodeWidth / 2, y: dy - nodeHeight / 2 - bbox.height / 2 }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 - bbox.height / 2 }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2 }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2, - y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2, - y: dy + nodeHeight / 2 - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2 - width, - y: dy + nodeHeight / 2 - bbox.height / 2, - }, - { - x: dx + nodeWidth / 2 - (bbox.width - width) / 2 - width, - y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2, - }, - { x: dx - nodeWidth / 2, y: dy - nodeHeight / 2 + bbox.height - bbox.height / 2 }, + points = [ + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx + width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx + width / 2, y: dy + nodeHeight / 2 }, + { x: dx - width / 2, y: dy + nodeHeight / 2 }, + { x: dx - width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 + bbox.height + labelPadding }, ]; - const pos = intersect.polygon(node, points, point); - return pos; } else { - const points = [ - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2, y: dy - nodeHeight / 2 }, - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2 + width, y: dy - nodeHeight / 2 }, - { - x: dx - nodeWidth / 2 + (bbox.width - width) / 2 + width, - y: dy - nodeHeight / 2 + height, - }, - { x: dx + nodeWidth / 2, y: dy - nodeHeight / 2 + height }, - { x: dx + nodeWidth / 2, y: dy + nodeHeight / 2 }, - { x: dx - nodeWidth / 2, y: dy + nodeHeight / 2 }, - { x: dx - nodeWidth / 2, y: dy + nodeHeight / 2 - bbox.height }, - { x: dx - nodeWidth / 2 + (bbox.width - width) / 2, y: dy + nodeHeight / 2 - bbox.height }, + points = [ + { x: dx - width / 2, y: dy - nodeHeight / 2 }, + { x: dx + width / 2, y: dy - nodeHeight / 2 }, + { x: dx + width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx + bbox.width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx + bbox.width / 2 / 2, y: dy + nodeHeight / 2 }, + { x: dx - bbox.width / 2, y: dy + nodeHeight / 2 }, + { x: dx - bbox.width / 2, y: dy - nodeHeight / 2 + height }, + { x: dx - width / 2, y: dy - nodeHeight / 2 + height }, ]; - const pos = intersect.polygon(node, points, point); - return pos; } + + const pos = intersect.polygon(node, points, point); + return pos; }; return shapeSvg;