1.在被拖拽的元素中首先添加mousedown事件,用于在dragstart事件前生成图片内容;

var img = new Image();
img.src = '图片的路径或者svg格式的代码等'

2.在dragstart事件中设置e.dataTransfer.setDragIamge()

handleOndragstart(e) {
	// 设置自定义鼠标拖拽过程中显示的图像
	e.dataTransfer.setDragIamge(img, xOffset, yOffset)
}

在这里插入图片描述
3.代码示例(可直接使用参考):

<template>
  <div id="bigbox">
    <!-- 被拖拽列表 -->
    <div class="dragarea">
      <div 
        class="drag-item" 
        v-for="(item, index) in list" 
        :key="index"
        draggable="true"
        @mousedown="onMousedown($event, item)"
        @dragstart="onDragstart($event, item)"
        @dragend="onDragEnd($event)"
      >{{ item.label }}</div>
    </div>
    <!-- 拖放区域 -->
    <div class="droparea" @dragover.prevent @drop="onDrop">
      <div style="border-bottom:1px solid gray; fontSize:24px;">我是拖放区域</div>
      <div class="dropbox">
        <div class="drop-item" v-for="(item,index) in dropList" :key="index">我是{{ item.label }}</div>
      </div>
    </div>
  </div>
</template>

<script>
let currentId = 0
export default {
  data() {
    return {
      list: [
        {
          id: 0,
          label: '正方形'
        },
        {
          id: 1,
          label: '长方形'
        },
        {
          id: 2,
          label: '柱状图'
        },
        {
          id: 3,
          label: '图片'
        },
      ],
      dropList: [],
      img: new Image()
    }
  },
  methods: {
    onMousedown(event, item) {
      console.log('mousedown鼠标按下', event, item);
      // 设置图像src为svg代码, 也可以是本地方路径(用require引入)
      // this.img.src = "data:image/svg+xml,%3Csvg width='100' height='40' viewBox='0 0 100 40' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Crect width='100' height='40' rx='8' fill='%230273CF'/%3E%3Cpath d='M27.496 16.936v3.304H22.96v.938h4.536v3.752h-5.698v.994h12.418v-.994h-5.698v-3.752h4.536v-.938h-4.536v-3.304h5.208v-.994h-5.768l.546-.21c-.196-.672-.462-1.4-.812-2.198l-.98.266c.336.686.63 1.4.868 2.142h-5.292v.994h5.208zm9.016-2.814v.91h4.13v1.246H37.38v3.528h3.682c-.224.392-.462.812-.714 1.246H36.33v.924h3.458c-.308.476-.616.966-.952 1.456 1.162.266 2.324.574 3.486.924-1.26.49-3.15.882-5.642 1.176l.378.896c3.024-.406 5.208-.966 6.538-1.68a55.038 55.038 0 0 1 4.648 1.736l.63-.826a56.235 56.235 0 0 0-4.368-1.526c.742-.602 1.26-1.316 1.54-2.156h3.01v-.924h-7.574c.224-.392.462-.798.714-1.246h5.824v-3.528h-3.262v-1.246h4.13v-.91H36.512zm6.916 9.688a49.868 49.868 0 0 0-3.164-.798c.21-.308.434-.658.672-1.036h4.088c-.28.728-.812 1.344-1.596 1.834zm.364-7.532h-2.184v-1.246h2.184v1.246zm3.262 2.66h-2.296V17.16h2.296v1.778zm-3.262 0h-2.184V17.16h2.184v1.778zm-3.15 0h-2.296V17.16h2.296v1.778zm22.708-3.78h-3.276a18.26 18.26 0 0 0-.602-1.708l-1.022.168c.224.476.434.98.616 1.54h-3.22v2.814h.952v-1.904h5.586v1.848h.966v-2.758zm-4.9 1.792a32.85 32.85 0 0 1-.644 2.254H55.51v.966h1.96a20.284 20.284 0 0 1-1.022 2.226c.924.49 1.792.966 2.604 1.428-.952.7-2.338 1.26-4.186 1.68l.406.952c2.184-.518 3.752-1.204 4.732-2.072 1.26.742 2.31 1.414 3.15 2.03l.686-.798a38.204 38.204 0 0 0-3.178-1.946c.742-.924 1.232-2.1 1.456-3.5h1.68v-.966h-4.97a40.97 40.97 0 0 0 .602-2.17l-.98-.084zm2.702 3.22c-.238 1.232-.7 2.226-1.386 3.01-.658-.35-1.372-.714-2.128-1.106.294-.532.574-1.176.854-1.904h2.66zm-8.526 6.104c.798 0 1.204-.406 1.204-1.218V21.01c.434-.196.868-.392 1.302-.602v-1.022c-.434.224-.868.434-1.302.63v-2.8h1.316v-.966H53.83v-2.646h-1.036v2.646h-1.638v.966h1.638v3.206c-.616.224-1.26.42-1.918.574l.252 1.008a29.45 29.45 0 0 0 1.666-.574v3.374c0 .364-.182.546-.518.546s-.686-.028-1.05-.056l.21.98h1.19zM76.748 15.13l-.21 4.158h-2.576l.364-4.158h2.422zm-3.766 4.158h-1.778v.98h1.694L72.478 25h-1.694v.98h7.756V25h-1.26l.504-10.822h-6.216v.952h1.778l-.364 4.158zM73.444 25l.434-4.732h2.618L76.272 25h-2.828zm-5.908-11.41c-.392 1.68-1.022 3.206-1.89 4.578l.826.518c.49-.77.924-1.638 1.302-2.59h2.912v-.938H68.11c.14-.448.28-.896.406-1.372l-.98-.196zm-.42 4.382v.91h.882v1.722H66.08v.924h1.918v3.178c0 .196-.14.35-.42.462l.434.868c1.092-.322 2.072-.728 2.912-1.232l-.182-.896c-.588.378-1.176.686-1.75.924v-3.304h1.932v-.924h-1.932v-1.722h1.456v-.91h-3.332z' fill='%23fff'/%3E%3C/svg%3E"

      // 根据不同类型显示不同的拖拽中样式图片
      let label = item.label
      switch(label) {
        case '正方形':
          this.img.src = 'https://t7.baidu.com/it/u=1595072465,3644073269&fm=193&f=GIF' 
          // this.img.style.width = '100px' //设置为网图或者本地图片,即使设置了图片大小不知为啥不生效
          // this.img.style.height = '100px'
          break;
        case '长方形':
          this.img.src = "data:image/svg+xml,%3Csvg width='160' height='160' viewBox='0 0 160 160' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M14.5 7.134a1 1 0 0 1 0 1.732l-9 5.196a1 1 0 0 1-1.5-.866V2.804a1 1 0 0 1 1.5-.866l9 5.196z'/%3E%3C/svg%3E"
          break;
        case '柱状图':
          this.img.src = "data:image/svg+xml,%3Csvg width='160' height='160' viewBox='0 0 160 160' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath fill-rule='evenodd' clip-rule='evenodd' d='M13 2H6a1 1 0 0 0-1 1H4a2 2 0 0 1 2-2h7a2 2 0 0 1 2 2v7a2 2 0 0 1-2 2v-1a1 1 0 0 0 1-1V3a1 1 0 0 0-1-1zM3 5h7a1 1 0 0 1 1 1v7a1 1 0 0 1-1 1H3a1 1 0 0 1-1-1V6a1 1 0 0 1 1-1zM1 6a2 2 0 0 1 2-2h7a2 2 0 0 1 2 2v7a2 2 0 0 1-2 2H3a2 2 0 0 1-2-2V6z'/%3E%3C/svg%3E"
          break;
        case '图片':
          this.img.src = "data:image/svg+xml,%3Csvg width='100' height='40' viewBox='0 0 100 40' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Crect width='100' height='40' rx='8' fill='%230273CF'/%3E%3Cpath d='M27.496 16.936v3.304H22.96v.938h4.536v3.752h-5.698v.994h12.418v-.994h-5.698v-3.752h4.536v-.938h-4.536v-3.304h5.208v-.994h-5.768l.546-.21c-.196-.672-.462-1.4-.812-2.198l-.98.266c.336.686.63 1.4.868 2.142h-5.292v.994h5.208zm9.016-2.814v.91h4.13v1.246H37.38v3.528h3.682c-.224.392-.462.812-.714 1.246H36.33v.924h3.458c-.308.476-.616.966-.952 1.456 1.162.266 2.324.574 3.486.924-1.26.49-3.15.882-5.642 1.176l.378.896c3.024-.406 5.208-.966 6.538-1.68a55.038 55.038 0 0 1 4.648 1.736l.63-.826a56.235 56.235 0 0 0-4.368-1.526c.742-.602 1.26-1.316 1.54-2.156h3.01v-.924h-7.574c.224-.392.462-.798.714-1.246h5.824v-3.528h-3.262v-1.246h4.13v-.91H36.512zm6.916 9.688a49.868 49.868 0 0 0-3.164-.798c.21-.308.434-.658.672-1.036h4.088c-.28.728-.812 1.344-1.596 1.834zm.364-7.532h-2.184v-1.246h2.184v1.246zm3.262 2.66h-2.296V17.16h2.296v1.778zm-3.262 0h-2.184V17.16h2.184v1.778zm-3.15 0h-2.296V17.16h2.296v1.778zm22.708-3.78h-3.276a18.26 18.26 0 0 0-.602-1.708l-1.022.168c.224.476.434.98.616 1.54h-3.22v2.814h.952v-1.904h5.586v1.848h.966v-2.758zm-4.9 1.792a32.85 32.85 0 0 1-.644 2.254H55.51v.966h1.96a20.284 20.284 0 0 1-1.022 2.226c.924.49 1.792.966 2.604 1.428-.952.7-2.338 1.26-4.186 1.68l.406.952c2.184-.518 3.752-1.204 4.732-2.072 1.26.742 2.31 1.414 3.15 2.03l.686-.798a38.204 38.204 0 0 0-3.178-1.946c.742-.924 1.232-2.1 1.456-3.5h1.68v-.966h-4.97a40.97 40.97 0 0 0 .602-2.17l-.98-.084zm2.702 3.22c-.238 1.232-.7 2.226-1.386 3.01-.658-.35-1.372-.714-2.128-1.106.294-.532.574-1.176.854-1.904h2.66zm-8.526 6.104c.798 0 1.204-.406 1.204-1.218V21.01c.434-.196.868-.392 1.302-.602v-1.022c-.434.224-.868.434-1.302.63v-2.8h1.316v-.966H53.83v-2.646h-1.036v2.646h-1.638v.966h1.638v3.206c-.616.224-1.26.42-1.918.574l.252 1.008a29.45 29.45 0 0 0 1.666-.574v3.374c0 .364-.182.546-.518.546s-.686-.028-1.05-.056l.21.98h1.19zM76.748 15.13l-.21 4.158h-2.576l.364-4.158h2.422zm-3.766 4.158h-1.778v.98h1.694L72.478 25h-1.694v.98h7.756V25h-1.26l.504-10.822h-6.216v.952h1.778l-.364 4.158zM73.444 25l.434-4.732h2.618L76.272 25h-2.828zm-5.908-11.41c-.392 1.68-1.022 3.206-1.89 4.578l.826.518c.49-.77.924-1.638 1.302-2.59h2.912v-.938H68.11c.14-.448.28-.896.406-1.372l-.98-.196zm-.42 4.382v.91h.882v1.722H66.08v.924h1.918v3.178c0 .196-.14.35-.42.462l.434.868c1.092-.322 2.072-.728 2.912-1.232l-.182-.896c-.588.378-1.176.686-1.75.924v-3.304h1.932v-.924h-1.932v-1.722h1.456v-.91h-3.332z' fill='%23fff'/%3E%3C/svg%3E"
          break;
        default:
          break;
      }
    },
    onDragstart(event, item) {
      console.log('dragstart开始', event, item);
      
      // 设置拖拽中图片.   坐标指定鼠标指针相对于图片的偏移量。若使图像居中,则使用图像宽度和高度的一半即可。
      event.dataTransfer.setDragImage(this.img, 10, 10)

      event.dataTransfer.setData('my-Data', JSON.stringify(item)) //在被拖拽对象的 dropstart 事件中传递消息
    },
    onDragEnd(event) {
      event.dataTransfer.clearData() //在被拖拽对象的 dragend 事件中清除消息
    },
    onDrop(event) {
      console.log('drop放置', event);
      let mydata = JSON.parse(event.dataTransfer.getData('my-Data')) //在拖放区的 drop 事件中获取消息
      this.dropList.push(mydata)
    },
  }
}
</script>

<style scoped>
#bigbox {
  display: flex;
}
.dragarea {
  width: 200px;
  height: 100vh;
  background: #9e9e9e;
}
.drag-item {
  width: 100px;
  height: 100px;
  border: 1px solid red;
  text-align: center;
  line-height: 100px;
  margin: 10px;
}
.droparea {
  width: 500px;
  height: 100vh;
  background: #eee;
  
}
.dropbox {
   display: flex;
  flex-wrap: wrap;
}
.drop-item {
  width: 100px;
  height: 100px;
  background: palegreen;
  text-align: center;
  line-height: 100px;
  margin: 10px;
}
</style>

在实现过程中有个疑问点未解决:
已经设置了拖拽中图片的宽高大小,但是不知道为什么没有生效。有知道的小伙伴可以互相交流。

参考链接地址:https://developer.mozilla.org/zh-CN/docs/Web/API/DataTransfer/setDragImage

Logo

前往低代码交流专区

更多推荐