jQuery Ui Draggable在移动端浏览器不起作用解决方案

今天写一个东西发现的一个问题,在pc端的网页上用jQuery Ui的draggable可以实现拖拽,但是当用移动端的浏览器时却不起作用,应该是由于事件的处理方式产生了问题,所以得自己去处理事件。
于是乎在stackoverflow上面找到了遇到相同问题的人,地址:http://stackoverflow.com/questions/17221570/draggable-interaction-not-working-on-cellphone/26862611#26862611

代码为:

// This is a fix for mobile devices

/iPad|iPhone|Android/.test( navigator.userAgent ) && (function( $ ) {

var proto =  $.ui.mouse.prototype,
_mouseInit = proto._mouseInit;

$.extend( proto, {
    _mouseInit: function() {
        this.element
        .bind( "touchstart." + this.widgetName, $.proxy( this, "_touchStart" ) );
        _mouseInit.apply( this, arguments );
    },

    _touchStart: function( event ) {
         this.element
        .bind( "touchmove." + this.widgetName, $.proxy( this, "_touchMove" ) )
        .bind( "touchend." + this.widgetName, $.proxy( this, "_touchEnd" ) );

        this._modifyEvent( event );

        $( document ).trigger($.Event("mouseup")); //reset mouseHandled flag in ui.mouse
        this._mouseDown( event );

        //return false;           
    },

    _touchMove: function( event ) {
        this._modifyEvent( event );
        this._mouseMove( event );   
    },

    _touchEnd: function( event ) {
        this.element
        .unbind( "touchmove." + this.widgetName )
        .unbind( "touchend." + this.widgetName );
        this._mouseUp( event ); 
    },

    _modifyEvent: function( event ) {
        event.which = 1;
        var target = event.originalEvent.targetTouches[0];
        event.pageX = target.clientX;
        event.pageY = target.clientY;
    }

});

})( jQuery );

上面的代码解决了开启draggable的dom元素不能drag的问题,但是我做的东西里面还需要该dom元素可以点击,所以得对上面的代码进行修改,对点击事件进行处理。本人iOS开发菜鸟一只,对javascript不是很了解,但是大体思路还是有的,我的解决办法就是添加一个moveFlag,然后在_touchMove方法中翻转该变量,然后在_touchEnd中归位flag。最后只要判断flag有没有变就可以知道是点击还是move了。还有一个问题需要处理的就是当flag没有翻转时,也就是点击事件发生时得去主动触发点击事件,需要主动dispatch 一个click evnet,代码为:


	        // 主动触发点击事件
	        if (moveFlag == 0) {
	        	var evt = document.createEvent('Event'); 
			evt.initEvent('click',true,true); 
			element.dispatchEvent(evt);
	        };


如果这样的话会发现element没有定义,所以需要自己去找一个element来分发这个点击事件,此时我将this输出,看看当前点击的对象结构,




可以看到一个handleElement里面有我定义的一个class .btn-q-1它是一个span而不是一个button,这样也可以避免一些不必要的事件处理,方便很多。于是乎我们通过this.handleElement[0]来获取当前点击的按钮,然后通过该按钮触发点击。这样就解决了点击和移动的问题

最终代码:


var moveFlag = 0; // 是否移动的flag

/iPad|iPhone|Android/.test( navigator.userAgent ) && (function( $ ) {
	var proto =  $.ui.mouse.prototype,
	_mouseInit = proto._mouseInit;
	$.extend( proto, {
	    _mouseInit: function() {
	        this.element
	        .bind( "touchstart." + this.widgetName, $.proxy( this, "_touchStart" ) );
	        _mouseInit.apply( this, arguments );
	    },
	    _touchStart: function( event ) {
	         this.element
	        .bind( "touchmove." + this.widgetName, $.proxy( this, "_touchMove" ) )
	        .bind( "touchend." + this.widgetName, $.proxy( this, "_touchEnd" ) );

	        this._modifyEvent( event );

	        $( document ).trigger($.Event("mouseup")); //reset mouseHandled flag in ui.mouse
	        this._mouseDown( event );
	        console.log(this);
	        //return false;           
	    },
	    _touchMove: function( event ) {
	    		moveFlag = 1;
	        this._modifyEvent( event );
	        this._mouseMove( event );   

	    },
	    _touchEnd: function( event ) {
	        // 主动触发点击事件
	        if (moveFlag == 0) {
	        	var evt = document.createEvent('Event'); 
			evt.initEvent('click',true,true); 
			this.handleElement[0].dispatchEvent(evt);
	        };

	        this.element
	        .unbind( "touchmove." + this.widgetName )
	        .unbind( "touchend." + this.widgetName );
	        this._mouseUp( event ); 

	    		moveFlag = 0;
	    },
	    _modifyEvent: function( event ) {
	        event.which = 1;
	        var target = event.originalEvent.targetTouches[0];
	        event.pageX = target.clientX;
	        event.pageY = target.clientY;
	    }
	});
})( jQuery );


有心得的朋友可以留下一些自己的解决思路供然后分享,谢谢






你可能感兴趣的:(遇到过的细节问题)