import Vue from 'vue'; Vue.directive('drag', (el, binding) => { const oDiv = el // 当前元素 const minTop = oDiv.getAttribute('drag-min-top') const drawBox = document.getElementById("drawBox"); const ifMoveSizeArea = 20 oDiv.onmousedown = e => { let target = oDiv if(e.button == 2){ while (window.getComputedStyle(target).position !== 'absolute' && target !== document.body) { target = target.parentElement } document.onselectstart = () => { return false } if (!target.getAttribute('init_x')) { target.setAttribute('init_x', target.offsetLeft) target.setAttribute('init_y', target.offsetTop) } const newE = e; const initX = parseInt(target.getAttribute('init_x')) const initY = parseInt(target.getAttribute('init_y')) // 鼠标按下,计算当前元素距离可视区的距离 // 获取div元素的坐标点 let drawRect = el.getBoundingClientRect(); let init_x = e.clientX - drawRect.x; let init_y = e.clientY - drawRect.y; const drawRect_x = drawRect.x; const drawRect_y = drawRect.y; const disX = e.clientX - (target.offsetLeft >= 0 ? target.offsetLeft : 0) const disY = e.clientY - (target.offsetTop >= 0 ? target.offsetTop : 0) let l_type = 'none'; let t_type = 'none'; document.onmousemove = e => { if(e.preventDefault){ e.preventDefault() } else { e.returnValue = false } // 通过事件委托,计算移动的距离 // 因为浏览器里并不能直接取到并且使用clientX、clientY,所以使用事件委托在内部做完赋值 let l = (e.clientX - disX) - (drawRect.x > drawRect_x ? parseInt(drawRect.x - drawRect_x) : 0); let t = (e.clientY - disY) - (drawRect.y > drawRect_y ? parseInt(drawRect.y - drawRect_y) : 0); const { marginTop: mt, marginLeft: ml } = window.getComputedStyle(target) // 计算移动当前元素的位置,并且给该元素样式中的left和top值赋值 // target.style.left = l - parseInt(ml) + 'px' // target.style.top = t + 'px' let div = document.getElementById("drawDiv"); if(!div){ div = document.createElement("div"); div.id = "drawDiv"; div.className = "innerDiv"; div.style.border = "1px dashed red"; div.style.borderRadius = "5px"; div.style.top = init_x + 'px'; div.style.left = init_y + 'px'; div.style.position = "absolute"; drawBox.append(div); } if(l < 0 && l_type != 'right') { div.style.right = (oDiv.offsetWidth - init_x) + 'px'; div.style.removeProperty('left'); l_type = 'right'; } else if (l > 0 && l_type != 'left') { div.style.left = init_x + 'px'; div.style.removeProperty('right'); l_type = 'left'; } else { l_type = 'none'; } if(t < 0 && t_type != 'bottom') { div.style.bottom = (oDiv.offsetHeight - init_y) + 'px'; div.style.removeProperty('top'); t_type = 'bottom'; } else if (t > 0 && t_type != 'top') { div.style.top = init_y + 'px'; div.style.removeProperty('bottom'); t_type = 'top'; } else { t_type = 'none'; } div.style.width = Math.abs(l) + 'px'; div.style.height = Math.abs(t) + 'px'; } document.onmouseup = e => { // 因为浏览器里并不能直接取到并且使用clientX、clientY,所以使用事件委托在内部做完赋值 const l = e.clientX - disX const t = e.clientY - disY let drawDialog = document.getElementById("draw-dialog-type"); drawDialog.style.top = '60px'; drawDialog.style.right = '0px'; drawDialog.style.display = "block"; document.onmousemove = null document.onmouseup = null document.onselectstart = null } } else { while (window.getComputedStyle(target).position !== 'absolute' && target !== document.body) { target = target.parentElement } document.onselectstart = () => { return false } if (!target.getAttribute('init_x')) { target.setAttribute('init_x', target.offsetLeft) target.setAttribute('init_y', target.offsetTop) } const initX = parseInt(target.getAttribute('init_x')) const initY = parseInt(target.getAttribute('init_y')) // 鼠标按下,计算当前元素距离可视区的距离 const disX = e.clientX - target.offsetLeft const disY = e.clientY - target.offsetTop document.onmousemove = e => { if(e.preventDefault){ e.preventDefault() } else { e.returnValue = false } // 通过事件委托,计算移动的距离 // 因为浏览器里并不能直接取到并且使用clientX、clientY,所以使用事件委托在内部做完赋值 const l = e.clientX - disX const t = e.clientY - disY const { marginTop: mt, marginLeft: ml } = window.getComputedStyle(target) // 计算移动当前元素的位置,并且给该元素样式中的left和top值赋值 target.style.left = l - parseInt(ml) + 'px' target.style.top = t + 'px' if (Math.abs(l - initX) > ifMoveSizeArea || Math.abs(t - initY) > ifMoveSizeArea) { target.setAttribute('dragged', '') } else { target.removeAttribute('dragged') } } document.onmouseup = e => { document.onmousemove = null document.onmouseup = null document.onselectstart = null } } // return false不加的话可能导致黏连,拖到一个地方时div粘在鼠标上不下来,相当于onmouseup失效 return false } })