Draggable Elements 元素拖拽功能实现代码(2)


this.startListening = function() {
if(listening || disposed) return;
listening = true;
hookEvent(attachEl, 'mousedown', dragStart);
};


前两行就是做个判断, 如果已经开始对拖拽事件进行监听或者清理过了, 就什么都不做直接return. 否则把listening状态设为true, 表示我们开始监听啦, 把dragStart函数关联到attachEl的mousedown事件上. 这里碰到个hookEvent函数, 我们来看看它的样子:

复制代码 代码如下:


function hookEvent(el, eventName, callback) {
if(typeof el == 'string')
el = document.getElementById(el);
if(!el) return;
if(el.addEventListener)
el.addEventListener(eventName, callback, false);
else if (el.attachEvent)
el.attachEvent('on' + eventName, callback);
}


其实也没什么, 就是对元素事件的监听做了个跨浏览器的封装, 同样的unhookEvent方法如下

复制代码 代码如下:


function unhookEvent(el, eventName, callback) {
if(typeof el == 'string')
el = document.getElementById(el);
if(!el) return;
if(el.removeEventListener)
el.removeEventListener(eventName, callback, false);
else if(el.detachEvent)
el.detachEvent('on' + eventName, callback);
}


接着我们来看看dragStart函数的实现, 它是drag object的一个私有函数

复制代码 代码如下:


function dragStart(eventObj) {
if(dragging || !listening || disposed) return;
dragging = true;
if(startCallback)
startCallback(eventObj, el);
cursorStartPos = absoluteCursorPosition(eventObj);
elementStartPos = new Position(parseInt(getStyle(el, 'left')), parseInt(getStyle(el, 'top')));
elementStartPos = elementStartPos.check();
hookEvent(document, 'mousemove', dragGo);
hookEvent(document, 'mouseup', dragStopHook);
return cancelEvent(eventObj);
}


attachEl所指的dom对象捕获到mousedown事件后调用此函数. 首先我们先确定drag object在一个适合拖拽的状态, 如果拖拽正在进行, 或者没有在监听拖拽事件, 再或者已经处理完"后事"了, 那就什么都不做. 如果一切ok, 我们把 dragging状态设为true, 然后"开工了", 如果startCallback定义了, 那我们就调用下它, 以mousedown event和el为参数. 接着我们定位鼠标的绝对位置, 保存到cursorStartPos中. 然后拿到拖拽元素当前的top, left,封装成Position对象保存到elementStartPos中. 保险起见我们检查下elementStartPos中属性是否合法. 再看两个hookEvent的调用, 一个是mousemove事件, 表示正在dragging,调用dragGo函数. 一个是mouseup事件, 代表拖拽的结束, 调用dragStopHook函数.可能你会问,为什么事件绑定在document上, 而不是要拖拽的元素上,比如我们这里的el或者attachEl.因为考虑到直接将事件绑定到元素上,可能由于浏览器的一些延时会影响效果,所以直接把事件绑定到document上. 如果实在不是很理解, 或许影响也不大: P.... 看最后一句话中的cancelEvent(eventObj)

复制代码 代码如下:

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wdfdgs.html