当前位置:首页 > VUE

vue 实现拖动

2026-02-10 04:41:30VUE

Vue 实现拖动功能

使用 HTML5 原生拖放 API

在 Vue 中可以通过 HTML5 的拖放 API 实现基本的拖动功能。需要监听 dragstartdragoverdrop 事件。

<template>
  <div 
    @dragstart="handleDragStart" 
    @dragover.prevent 
    @drop="handleDrop"
    draggable="true"
  >
    拖动元素
  </div>
</template>

<script>
export default {
  methods: {
    handleDragStart(e) {
      e.dataTransfer.setData('text/plain', e.target.id)
    },
    handleDrop(e) {
      const id = e.dataTransfer.getData('text/plain')
      const draggableElement = document.getElementById(id)
      e.target.appendChild(draggableElement)
    }
  }
}
</script>

使用第三方库 vue-draggable

对于更复杂的拖动场景,推荐使用 vue-draggable 库。它基于 Sortable.js,提供了丰富的拖动功能。

安装:

npm install vuedraggable

使用:

<template>
  <draggable v-model="list" @end="onDragEnd">
    <div v-for="item in list" :key="item.id">
      {{ item.name }}
    </div>
  </draggable>
</template>

<script>
import draggable from 'vuedraggable'

export default {
  components: { draggable },
  data() {
    return {
      list: [
        { id: 1, name: 'Item 1' },
        { id: 2, name: 'Item 2' }
      ]
    }
  },
  methods: {
    onDragEnd() {
      console.log('拖动结束')
    }
  }
}
</script>

自定义拖动指令

可以创建自定义指令来实现更灵活的拖动控制。

Vue.directive('drag', {
  bind(el, binding) {
    let startX, startY, initialX, initialY

    el.style.position = 'absolute'

    el.addEventListener('mousedown', (e) => {
      startX = e.clientX
      startY = e.clientY
      initialX = el.offsetLeft
      initialY = el.offsetTop

      document.addEventListener('mousemove', move)
      document.addEventListener('mouseup', up)

      e.preventDefault()
    })

    function move(e) {
      const dx = e.clientX - startX
      const dy = e.clientY - startY

      el.style.left = initialX + dx + 'px'
      el.style.top = initialY + dy + 'px'
    }

    function up() {
      document.removeEventListener('mousemove', move)
      document.removeEventListener('mouseup', up)
    }
  }
})

拖动排序实现

结合 Vue 的响应式特性,可以实现拖动排序功能。

<template>
  <div 
    v-for="(item, index) in items" 
    :key="item.id"
    draggable="true"
    @dragstart="dragStart(index)"
    @dragover.prevent
    @dragenter="dragEnter(index)"
    @dragend="dragEnd"
  >
    {{ item.text }}
  </div>
</template>

<script>
export default {
  data() {
    return {
      items: [
        { id: 1, text: 'Item 1' },
        { id: 2, text: 'Item 2' }
      ],
      draggingIndex: null
    }
  },
  methods: {
    dragStart(index) {
      this.draggingIndex = index
    },
    dragEnter(index) {
      if (this.draggingIndex !== index) {
        const temp = this.items[this.draggingIndex]
        this.$set(this.items, this.draggingIndex, this.items[index])
        this.$set(this.items, index, temp)
        this.draggingIndex = index
      }
    },
    dragEnd() {
      this.draggingIndex = null
    }
  }
}
</script>

拖动边界限制

可以通过计算限制拖动元素的移动范围。

function move(e) {
  const dx = e.clientX - startX
  const dy = e.clientY - startY

  let newX = initialX + dx
  let newY = initialY + dy

  // 限制在父容器内
  const parentRect = el.parentElement.getBoundingClientRect()
  const elRect = el.getBoundingClientRect()

  newX = Math.max(0, Math.min(newX, parentRect.width - elRect.width))
  newY = Math.max(0, Math.min(newY, parentRect.height - elRect.height))

  el.style.left = newX + 'px'
  el.style.top = newY + 'px'
}

拖动性能优化

对于大量可拖动元素,应该使用事件委托来优化性能。

mounted() {
  this.$refs.container.addEventListener('mousedown', (e) => {
    if (e.target.classList.contains('draggable')) {
      // 拖动逻辑
    }
  })
}

触摸屏支持

为支持移动设备,需要添加触摸事件处理。

el.addEventListener('touchstart', (e) => {
  startX = e.touches[0].clientX
  startY = e.touches[0].clientY
  // 其他逻辑类似鼠标事件
})

以上方法可以根据具体需求选择使用,从简单的原生 API 到功能完善的第三方库,Vue 提供了多种实现拖动功能的方案。

vue 实现拖动

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

相关文章

vue中登陆实现逻辑

vue中登陆实现逻辑

Vue 中登录实现逻辑 前端实现逻辑 表单验证 使用 Vue 的表单验证库(如 VeeValidate)或自定义验证规则,确保用户输入的账号和密码符合要求。例如,检查邮箱格式、密码长度等。 发送登录…

vue实现星星

vue实现星星

实现星星评分的Vue组件 使用Vue实现星星评分功能可以通过组件化方式完成,以下是一个完整的实现方案: 模板部分 <template> <div class="star-ra…

实现vue模版

实现vue模版

Vue 模板的基本结构 Vue 模板基于 HTML 语法,通过 Vue 的指令和插值实现动态渲染。以下是一个基础模板示例: <template> <div id="app…

vue实现截图

vue实现截图

Vue 实现截图的方法 使用 html2canvas 库 安装 html2canvas 库: npm install html2canvas 在 Vue 组件中使用: import html2ca…

vue 实现滚动

vue 实现滚动

实现滚动的基本方法 在Vue中实现滚动效果可以通过多种方式完成,包括使用原生JavaScript、CSS或第三方库。以下是一些常见的方法: 使用window.scrollTo方法实现页面滚动 可以…

vue路由实现

vue路由实现

Vue 路由实现 Vue Router 是 Vue.js 的官方路由管理器,用于构建单页面应用(SPA)。以下是 Vue Router 的基本实现步骤和核心功能。 安装 Vue Router 通过…