js 拖动功能组件

1.基于jquery

2.效率优先

3.可配置项(拖动者,鼠标样式,拖动范围)

欢迎PK效率!!

/**
 * dragdrop.js
 *
 * @example
 *
 * new DH.Widget.Dragdrop({
 *     el : 'string', // 被拖动元素选择器, 必须项
 *     dragSelector : 'string', // 拖动选择器, 非必须项
 *     opacity : 'number', // 拖动时透明度, 非必须项
 *     cursor : 'string', // 鼠标样式, 非必须项
 *     delay : true || false, // 是否延迟, 非必须项
 *     animate : true || false, // 延迟后是否动画, 非必须项
 *     speed : number, // 动画执行速度,越小越快,单位毫秒, 非必须项
 *     scopeSelector : 'string' // 被拖动元素移动范围, 非必须项
 * })
 * 
 */
(function($){

    var Dragdrop = DH.Base.create({
        init : function(){

            if(!this.el || !this.el.length) return;

            this.begin = {};

            this.canDrag = false;

            this.$drag = this.options.dragSelector ? this.el.find(this.options.dragSelector) : this.el; // 拖动元素

            this.$scope = this.options.scopeSelector && $(this.options.scopeSelector); // 拖动范围

            this.$move = this.el; // 移动元素

            this.cursor = this.options.cursor || 'move'; // 鼠标样式

            this.opacity = this.options.opacity || 1; // 拖动是透明度

            this.delay = !!this.options.delay; // 是否延迟

            this.animate = !!this.options.animate; // 是否动画

            this.speed = this.options.speed || 200; // 动画移动速度,默认200毫秒

            this.dragFn = this.proxy(this.drag);

            this.resetFn = this.proxy(this.reset);

            this.$drag.bind('mousedown', this.dragFn);

            $(window).bind('resize', this.resetFn);

            this.reset();

        },
        drag : function(e){

            var $move = this.$move,
                $drag = this.$drag,
                $scope = this.$scope,
                pageX = e.pageX,
                pageY = e.pageY,
                left = parseFloat($move.css('left')),
                top = parseFloat($move.css('top'))
                ;

            isNaN(left) && (left = 0); // fixed ie

            isNaN(top) && (top = 0); // fixed ie

            this.begin = {
                left : pageX - left,
                top : pageY - top
            };

            $drag.css('cursor', this.cursor);

            $move.css('-moz-user-select', 'none'); // stop moz text select

            $move.css('opacity', this.opacity);

            if(this.delay){
                if(!this.$delay){
                    var $delay = this.$delay = $('<div>').appendTo($move.parent());
                    $delay.css({
                        position : 'absolute',
                        cursor : this.cursor,
                        border : '1px dotted #333',
                        width : $move.outerWidth(true),
                        height : $move.outerHeight(true),
                        left : left,
                        top : top,
              zIndex : parseInt($move.css('zIndex')) + 1 }); }
else{ this.$delay.show(); } } this.moveFn = this.proxy(this.move); this.stopFn = this.proxy(this.stop); $(document) .bind('mousemove', this.moveFn) .bind('mouseup', this.stopFn) .bind('selectstart', this.stopBubble); // stop ie text select ; this.canDrag = true; this.trigger('drag', $move, left, top); }, move : function(e){ if(!this.canDrag) return; var $move = this.$move, $scope = this.$scope, pageX = e.pageX, pageY = e.pageY, begin = this.begin, left = pageX - begin.left, top = pageY - begin.top ; if(this.defaults){ var defaults = this.defaults; if(left < defaults.minLeft){ left = defaults.minLeft; }else if(left > defaults.maxLeft){ left = defaults.maxLeft; } if(top < defaults.minTop){ top = defaults.minTop; }else if(top > defaults.maxTop){ top = defaults.maxTop; } } if(this.delay){ this.$delay.css({ left : left, top : top }); }else{ $move.css({ left : left, top : top }); } this.trigger('move', $move, left, top); }, stop : function(){ var $move = this.$move, $drag = this.$drag, left = parseFloat($move.css('left')), top = parseFloat($move.css('top')) ; if(this.delay){ var $delay = this.$delay, left = parseFloat($delay.css('left')), top = parseFloat($delay.css('top')) ; if(this.animate){ $move.animate({ left : left, top : top }, this.speed, function(){ $delay.hide(); }); }else{ $move.css({ left : left, top : top }); $delay.hide(); } } $drag.css('cursor', ''); $move.css('-moz-user-select', ''); $move.css('opacity', ''); $(document) .unbind('mousemove', this.moveFn) .unbind('mouseup', this.stopFn) .unbind('selectstart', this.stopBubble); ; this.canDrag = false; this.trigger('stop', $move, left, top); }, stopBubble: function(){ return false; }, /** * 计算移动元素的活动范围 [description] */ reset : function(){ if(this.$scope){ var $move = this.$move, $scope = this.$scope, minLeft = 0, maxLeft = $move.width(), minTop = 0, maxTop = $move.height(), offset = $move.offset(), oleft = offset.left, otop = offset.top, position = $move.position(), pleft = position.left, ptop = position.top, eleft = parseFloat($move.css('left')), etop = parseFloat($move.css('top')), scopeOffset = $scope.position(), scopeLeft = scopeOffset.left, scopeTop = scopeOffset.top, scopeWith = $scope.width(), scopeHeight = $scope.height(), width = $move.width(), height = $move.height() ; if(parseFloat($scope.css('marginLeft')) > 0){ scopeLeft += parseFloat($scope.css('marginLeft')); } if(parseFloat($scope.css('marginTop')) > 0){ scopeTop += parseFloat($scope.css('marginTop')); } minLeft = scopeLeft - (oleft - pleft); maxLeft = scopeLeft - (oleft - pleft) + scopeWith - width; minTop = scopeTop - (otop - ptop); maxTop = scopeTop - (otop - ptop) + scopeHeight - height; this.defaults = { minLeft : minLeft, maxLeft : maxLeft, minTop : minTop, maxTop : maxTop } } }, destory : function(){ this.stop(); this.$drag.unbind('mousedown', this.dragFn); $(window).unbind('resize', this.resetFn); this.$drag = null; this.$move = null; this.$scope = null; this.start = null; this.defaults = null; } }); DH.Widget.Dragdrop = Dragdrop; })(window.jQuery);

  

原文地址:https://www.cnblogs.com/jackliu6/p/3669250.html