原生JS快速实现拖放(drag and drop)效果

论坛 期权论坛 期权     
web前端学习圈   2019-7-8 00:32   2184   0
拖放是很常见的一种交互效果,很多时候我们都会借助于第三方的控件来实现,其实用原生js实现起来也非常的方便。接下来我们就用原生js和css快速实现这样的拖放效果:

HTML
HTML的内容很简单,就是五个空的容器和一个可以被拖拽的元素:
html:
  1.                
复制代码
注意点:1. 容器的的
  1. class
复制代码
  1. droppable
复制代码
,用于接收被拖拽的元素,可被拖拽的元素
  1. class
复制代码
  1. draggable
复制代码
,同时设置
  1. draggable
复制代码
属性为
  1. true
复制代码
,表示该元素可以被拖拽。2. 默认情况下,只有图片、链接还有被选中的文字能被拖拽,其他元素需要设置
  1. draggable
复制代码
  1. true
复制代码
才能被拖拽。所以为了凸显
  1. draggable
复制代码
的用法,这里使用
  1. [/code]而不是[code]
复制代码
来作为被拖拽的元素。
CSS在实现样式的时候,除了实现静态的样式,一些过渡状态也需要增加样式以提升视觉体验:1. 元素被拖动的过程中增加边框等效果;2. 当元素被拖动到容器上方时,容器也应增加样式表明容器可以接收一个被拖拽的元素。
  1. css:
复制代码
  1. body {  background-color: darksalmon;}.draggable {  background-image: url('http://source.unsplash.com/random/150x150');  position: relative;  height: 150px;  width: 150px;  top: 5px;  left: 5px;  cursor: pointer;}.droppable {  display: inline-block;  height: 160px;  width: 160px;  margin: 10px;  border: 3px salmon solid;  background-color: white;}.dragging {  border: 4px yellow solid;}.drag-over {  background-color: #f4f4f4;  border-style: dashed;}.invisible {  display: none;}
复制代码
注意点:1. 图片来源于
  1. https://source.unsplash.com/
复制代码
的随机图片;2.
  1. .dragging
复制代码
为draggable元素正在被拖动的状态,增加黄色border;3.
  1. .drag-over
复制代码
为draggable元素被拖动到容器上方时容器的状态,增加灰色虚线border。
JS最后,我们需要通过js监听
  1. draggable
复制代码
  1. droppable
复制代码
的相关的事件。
js:
  1. // 查询draggable和droppableconst draggable = document.querySelector('.draggable');const droppables = document.querySelectorAll('.droppable');// 监听draggable的相关事件draggable.addEventListener('dragstart', dragStart);draggable.addEventListener('dragend', dragEnd);function dragStart() {  this.className += ' dragging';  setTimeout(() => {    this.className = 'invisible';  }, 0);}function dragEnd() {  this.className = 'draggable';}// 监听droppable的相关事件for (const droppable of droppables) {  droppable.addEventListener('dragover', dragOver);  droppable.addEventListener('dragleave', dragLeave);  droppable.addEventListener('dragenter', dragEnter);  droppable.addEventListener('drop', dragDrop);}function dragOver(e) {  e.preventDefault();}function dragEnter(e) {  e.preventDefault();  this.className += ' drag-over';}function dragLeave(e) {  this.className = 'droppable';}function dragDrop(e) {  this.className = 'droppable';  this.append(draggable);}
复制代码
注意点:1. 当draggable元素被拖动时,原来容器中的draggable元素并不会消失,需要我们手动将其隐藏(
  1. class
复制代码
设置为
  1. invisible
复制代码
),如果同步操作会立马触发
  1. dragend
复制代码
事件导致拖动效果消失,所以在
  1. setTimeout
复制代码
的回调中异步设置可确保拖动操作开始后再隐藏draggable元素;2. 在
  1. dragEnter
复制代码
  1. dragOver
复制代码
方法中我们需要通过
  1. preventDefault
复制代码
来取消事件以表明容器是一个合法的
  1. droppable
复制代码
元素,不然容器的
  1. drop
复制代码
事件将无法触发,接下来的操作也将无法进行,详细解释请参考 MDN DropTarget;3. 在
  1. dragDrop
复制代码
方法中直接使用
  1. append
复制代码
方法将
  1. draggable
复制代码
元素移动至当前容器下面。
好了,demo比较简单,但是细节还是有一些的,自己实践一下才能更深刻的领悟。
完整示例:https://codepen.io/mudontire/...
源自:https://segmentfault.com/a/1190000019554950
声明:文章著作权归作者所有,如有侵权,请联系小编删除。
感谢 · 转发欢迎大家留言
分享到 :
0 人收藏
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

积分:30
帖子:6
精华:0
期权论坛 期权论坛
发布
内容

下载期权论坛手机APP