You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何自动在任意位置的两个div间绘制SVG箭头

优化SVG绘制Div间箭头方案

你的代码无法实现预期效果,核心问题有三个:

  1. SVG尺寸固定且过小,没法覆盖页面所有区域,箭头很容易超出SVG范围导致看不见
  2. SVG处于正常文档流,会挤压Div的布局,同时getBoundingClientRect()获取的是元素相对于视口的坐标,和SVG的局部坐标不匹配
  3. JS执行时机可能过早,DOM还没完全加载就去获取元素,容易出现获取不到的情况

下面是修复后的完整实现,能自动适配Div的任意位置,无需手动定位箭头:

完整代码

HTML

<!DOCTYPE html>
<html>
<head>
    <link rel="stylesheet" href="styles/styles.css">
</head>
<body>
    <div id="div1"><p>First div</p></div>
    <div id="div2"><p>Second div</p></div>

    <!-- 全屏覆盖的SVG,用于绘制箭头 -->
    <svg id="arrow-svg" style="position: fixed; top: 0; left: 0; width: 100vw; height: 100vh; pointer-events: none; z-index: 1000;">
        <defs>
            <marker id="arrow" markerWidth="13" markerHeight="13" refX="2" refY="6" orient="auto">
                <path d="M2,2 L2,11 L10,6 L2,2" fill="black" />
            </marker>
        </defs>
        <path id="arr1" style="stroke:black; stroke-width: 1.25px; fill: none; marker-end: url(#arrow);" />
    </svg>

    <script src="script.js"></script>
</body>
</html>

CSS(styles/styles.css)

div{
    display: inline-block;
    margin-right: 100px;
    border-color: green;
    border-width: 3px;
    border-style: solid;
}

JS(script.js)

// 等待DOM加载完成后执行
document.addEventListener('DOMContentLoaded', function() {
    const div1 = document.getElementById('div1');
    const div2 = document.getElementById('div2');
    const arrowPath = document.getElementById('arr1');

    // 计算并更新箭头位置的函数
    function updateArrow() {
        const rect1 = div1.getBoundingClientRect();
        const rect2 = div2.getBoundingClientRect();

        // 起点:div1右侧中点
        const startX = rect1.right;
        const startY = rect1.top + rect1.height / 2;

        // 终点:div2左侧中点
        const endX = rect2.left;
        const endY = rect2.top + rect2.height / 2;

        // 设置SVG路径
        arrowPath.setAttribute('d', `M${startX},${startY} L${endX},${endY}`);
    }

    // 初始加载时更新箭头
    updateArrow();

    // 窗口大小变化或滚动时,实时更新箭头位置
    window.addEventListener('resize', updateArrow);
    window.addEventListener('scroll', updateArrow);
});

关键优化点

  • 全屏SVG:将SVG设置为fixed定位,铺满整个视口,这样getBoundingClientRect()的视口坐标可以直接对应SVG的绘图坐标,避免位置偏移
  • 无干扰布局:给SVG加上pointer-events: none,确保它不会遮挡页面元素的交互,同时不占据文档流,不会影响Div的原有布局
  • 动态更新:监听窗口resize和scroll事件,实时更新箭头位置,适配页面变化
  • 正确执行时机:通过DOMContentLoaded确保JS在DOM完全加载后执行,避免获取不到元素的问题

这个方案不管两个Div是横向排列还是纵向排列,都能准确在它们之间画出箭头,完全符合你的预期效果。

内容的提问来源于stack exchange,提问作者shaelebrown

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 17:07:51