当前位置:首页 > JavaScript

js实现拖动svg

2026-04-07 15:06:54JavaScript

实现 SVG 拖动的 JavaScript 方法

使用原生 JavaScript 实现 SVG 拖动

为 SVG 元素添加拖动功能需要监听鼠标事件(mousedownmousemovemouseup)。以下是一个基本实现:

js实现拖动svg

const svgElement = document.getElementById('draggable-svg');
let isDragging = false;
let offsetX, offsetY;

svgElement.addEventListener('mousedown', (e) => {
    isDragging = true;
    offsetX = e.clientX - svgElement.getBoundingClientRect().left;
    offsetY = e.clientY - svgElement.getBoundingClientRect().top;
    svgElement.style.cursor = 'grabbing';
});

document.addEventListener('mousemove', (e) => {
    if (!isDragging) return;
    svgElement.style.left = `${e.clientX - offsetX}px`;
    svgElement.style.top = `${e.clientY - offsetY}px`;
});

document.addEventListener('mouseup', () => {
    isDragging = false;
    svgElement.style.cursor = 'grab';
});

使用 transform 优化性能

直接修改 lefttop 可能触发重排,使用 transform 性能更好:

js实现拖动svg

svgElement.addEventListener('mousedown', (e) => {
    isDragging = true;
    const rect = svgElement.getBoundingClientRect();
    offsetX = e.clientX - rect.left;
    offsetY = e.clientY - rect.top;
});

document.addEventListener('mousemove', (e) => {
    if (!isDragging) return;
    svgElement.style.transform = `translate(${e.clientX - offsetX}px, ${e.clientY - offsetY}px)`;
});

处理 SVG 内部元素拖动

若需拖动 SVG 内的特定元素(如 <rect><circle>),需使用 SVG 的坐标系统:

const svg = document.querySelector('svg');
const rect = document.querySelector('rect');
let selectedElement = null;
let offset = { x: 0, y: 0 };

svg.addEventListener('mousedown', (e) => {
    if (e.target !== rect) return;
    selectedElement = e.target;
    const CTM = svg.getScreenCTM();
    offset.x = e.clientX - CTM.e - parseFloat(selectedElement.getAttribute('x'));
    offset.y = e.clientY - CTM.f - parseFloat(selectedElement.getAttribute('y'));
});

svg.addEventListener('mousemove', (e) => {
    if (!selectedElement) return;
    const CTM = svg.getScreenCTM();
    const x = e.clientX - CTM.e - offset.x;
    const y = e.clientY - CTM.f - offset.y;
    selectedElement.setAttribute('x', x);
    selectedElement.setAttribute('y', y);
});

svg.addEventListener('mouseup', () => {
    selectedElement = null;
});

使用第三方库简化操作

若项目允许,使用库如 Draggableinteract.js 可简化实现:

interact('.draggable-svg')
    .draggable({
        onmove: (event) => {
            const target = event.target;
            const x = (parseFloat(target.getAttribute('data-x')) || 0) + event.dx;
            const y = (parseFloat(target.getAttribute('data-y')) || 0) + event.dy;
            target.style.transform = `translate(${x}px, ${y}px)`;
            target.setAttribute('data-x', x);
            target.setAttribute('data-y', y);
        }
    });

注意事项

  • SVG 的坐标系统与 DOM 不同,需通过 getScreenCTM() 转换。
  • 对于嵌套 SVG 元素,确保事件冒泡被正确处理。
  • 移动端需额外处理 touchstarttouchmovetouchend 事件。

以上方法可根据具体需求调整,如限制拖动范围或添加动画效果。

标签: 拖动js
分享给朋友:

相关文章

js实现瀑布流

js实现瀑布流

实现瀑布流布局 瀑布流布局是一种常见的网页布局方式,常用于图片展示、商品列表等场景。以下是使用 JavaScript 实现瀑布流布局的几种方法。 纯 JavaScript 实现 通过计算元素的位置和…

js类实现

js类实现

使用类实现 JavaScript 功能 在 JavaScript 中,类(Class)是一种语法糖,基于原型继承机制。通过 class 关键字可以更直观地定义对象模板。 基本类定义 class…

js手势实现

js手势实现

手势识别实现方法 在JavaScript中实现手势识别通常涉及监听触摸事件(touchstart、touchmove、touchend)或鼠标事件(mousedown、mousemove、mouseu…

js实现代码雨

js实现代码雨

实现代码雨效果 使用HTML5 Canvas和JavaScript可以轻松实现经典的代码雨效果。以下是完整的实现代码和说明: HTML结构 <!DOCTYPE html> <…

js实现 功能

js实现 功能

在 JavaScript 中实现功能通常涉及多个关键步骤,具体取决于功能需求。以下是常见功能的实现方法和示例: 基本功能实现 使用函数封装逻辑是最直接的方式。例如,实现一个计算两数之和的函数: f…

实现继承js

实现继承js

实现继承的方式 在JavaScript中,实现继承可以通过多种方式完成,每种方式都有其优缺点。以下是几种常见的实现继承的方法: 原型链继承 原型链继承是最基本的继承方式,通过将子类的原型指向父类的实…