0. 首先看看效果圖,是不是你想要的效果;
1. 建立 drag.js檔案 實作拖拽源碼;
/**
* 拖拽移動
* @param {elementObjct} bar 滑鼠點選控制拖拽的元素
* @param {elementObjct} target 移動的元素
* @param {function} callback 移動後的回調
*/
export function startDrag(bar, target, callback) {
var params = {
top: 0,
left: 0,
currentX: 0,
currentY: 0,
flag: false,
cWidth: 0,
cHeight: 0,
tWidth: 0,
tHeight: 0
};
// 給拖動塊添加樣式
bar.style.cursor = 'move';
// 擷取相關CSS屬性
// o是移動對象
// var getCss = function (o, key) {
// return o.currentStyle ? o.currentStyle[key] : document.defaultView.getComputedStyle(o, false)[key];
// };
bar.onmousedown = function (event) {
// 按下時初始化params
var e = event ? event : window.event;
params = {
top: target.offsetTop,
left: target.offsetLeft,
currentX: e.clientX,
currentY: e.clientY,
flag: true,
cWidth: document.body.clientWidth,
cHeight: document.body.clientHeight,
tWidth: target.offsetWidth,
tHeight: target.offsetHeight
};
// 給被拖動塊初始化樣式
target.style.margin = 0;
target.style.top = params.top + 'px';
target.style.left = params.left + 'px';
if (!event) {
// 防止IE文字選中
bar.onselectstart = function () {
return false;
}
}
document.onmousemove = function (event) {
// 防止文字選中
window.getSelection ? window.getSelection().removeAllRanges() : document.selection.empty();
var e = event ? event : window.event;
if (params.flag) {
var nowX = e.clientX;
var nowY = e.clientY;
// 差異距離
var disX = nowX - params.currentX;
var disY = nowY - params.currentY;
// 最終移動位置
var zLeft = 0;
var zTop = 0;
zLeft = parseInt(params.left) + disX;
// 限制X軸範圍
if (zLeft <= -parseInt(params.tWidth / 2)) {
zLeft = -parseInt(params.tWidth / 2);
}
if (zLeft >= params.cWidth - parseInt(params.tWidth * 0.5)) {
zLeft = params.cWidth - parseInt(params.tWidth * 0.5);
}
zTop = parseInt(params.top) + disY;
// 限制Y軸範圍
if (zTop <= 0) {
zTop = 0;
}
if (zTop >= params.cHeight - parseInt(params.tHeight * 0.5)) {
zTop = params.cHeight - parseInt(params.tHeight * 0.5);
}
// 執行移動
target.style.left = zLeft + 'px';
target.style.top = zTop + 'px';
}
if (typeof callback == "function") {
callback(zLeft, zTop);
}
}
document.onmouseup = function () {
params.flag = false;
document.onmousemove = null;
document.onmouseup = null;
};
};
}
2. 第二步建立指令 建立 directive.js 檔案
// 引入拖拽js
import { startDrag } from '@/drag.js'
/**
* 為el-dialog彈框增加拖拽功能
* @param {*} el 指定dom
* @param {*} binding 綁定對象
* desc 隻要用到了el-dialog的元件,都可以通過增加v-draggable屬性變為可拖拽的彈框
*/
const draggable = (el, binding) => {
// 綁定拖拽事件 [綁定拖拽觸發元素為彈框頭部、拖拽移動元素為整個彈框]
startDrag(el.querySelector('.el-dialog__header'), el.querySelector('.el-dialog'), binding.value);
};
export dafault {
draggable,
}
3. 第三步 全局注冊指令 在main.js檔案中編寫
import directive from '@/directive';
/* 注冊全局指令 */
Object.keys(directive).forEach(key => {
Vue.directive(`${key}`, directive[key]);
});
4. 開始使用指令 v-draggable
此指令Demo為彈框拖拽展示;拖拽觸發點為彈框頭部,移動部分已整個彈框
<el-dialog
v-draggable
title="新增"
:visible.sync="isShow"
@close="handleCancelConfigInfo">
<-- xxxx 彈框内容... -->
</el-form>
<div slot="footer">
<el-button size="small">取消</el-button>
<el-button size="small">儲存</el-button>
</div>
</el-dialog>