Question

See fiddle: http://jsfiddle.net/mrcarllister/Z2GjN/

Basically, I've got the click-drag-scroll working EXCEPT when you click and drag on an anchor/link.

It only seems to be when the mouse cursor remains on the link on release that the url is followed (for instance if you drag far enough and the link is off the window, that works fine.)

;(function($){ 

$.fn.scrollsync = function( options ){
var settings = $.extend(
        {   
            targetSelector:':first',
            axis: 'xy'
        },options || {});


function scrollHandler(event) {
    if (event.data.xaxis){
        event.data.followers.scrollLeft(event.data.target.scrollLeft());
    }
    if (event.data.yaxis){
        event.data.followers.scrollTop(event.data.target.scrollTop());
    }
}

settings.target = this.filter(settings.targetSelector).filter(':first');
settings.followers=this.not(settings.target); // the rest of elements

settings.xaxis= (settings.axis=='xy' || settings.axis=='x') ? true : false; 
settings.yaxis= (settings.axis=='xy' || settings.axis=='y') ? true : false;
if (!settings.xaxis && !settings.yaxis) return;  

settings.target.bind('scroll', settings, scrollHandler);

};

})( jQuery ); 

;(function($){




$.fn.dragscrollable = function( options ){

var settings = $.extend(
    {   
        dragSelector:'>:first',
        acceptPropagatedEvent: true,
        preventDefault: true
    },options || {});


var dragscroll= {
    mouseDownHandler : function(event) {

        if (event.which!=1 ||
            (!event.data.acceptPropagatedEvent && event.target != this)){ 
            return false; 
        }


        event.data.lastCoord = {left: event.clientX, top: event.clientY}; 


        $.event.add( document, "mouseup", 
                     dragscroll.mouseUpHandler, event.data );
        $.event.add( document, "mousemove", 
                     dragscroll.mouseMoveHandler, event.data );
        if (event.data.preventDefault) {
            event.preventDefault();
            return false;
        }
    },
    mouseMoveHandler : function(event) { 


        var delta = {left: (event.clientX - event.data.lastCoord.left),
                     top: (event.clientY - event.data.lastCoord.top)};

        event.data.scrollable.scrollLeft(
                        event.data.scrollable.scrollLeft() - delta.left);
        event.data.scrollable.scrollTop(
                        event.data.scrollable.scrollTop() - delta.top);


        event.data.lastCoord={left: event.clientX, top: event.clientY}
        if (event.data.preventDefault) {
            event.preventDefault();
            return false;
        }

    },
    mouseUpHandler : function(event) { 
        $.event.remove( document, "mousemove", dragscroll.mouseMoveHandler);
        $.event.remove( document, "mouseup", dragscroll.mouseUpHandler);
        if (event.data.preventDefault) {
            event.preventDefault();
            return false;
        }
    }
}


this.each(function() {

    var data = {scrollable : $(this),
                acceptPropagatedEvent : settings.acceptPropagatedEvent,
                preventDefault : settings.preventDefault }

    $(this).find(settings.dragSelector).
                    bind('mousedown', data, dragscroll.mouseDownHandler);
});
}; 

})( jQuery ); 

I'm pretty sure I have to 'return:false;' for anchors but I'm not sure how to do it ONLY when drag/scrolling.

Any help would be appreciated.

EDIT - Ian's suggestion worked but I just need a couple of amends:

  1. Only scroll up and down (not left or right)
  2. To be restricted to the content / div size - and to not scroll any further.

--->>>>>>>>>>>>>

Cheers,

Carl

Was it helpful?

Solution

Alright well the problem here is this uses mouse up and down to work, so you can either disable the anchor permanently or it'll work, so you need to have some business logic to say when it's on and off. If you want to edit dragscrollable, put this in the code and it'll work

http://jsfiddle.net/Z2GjN/33/

I added

event.data.initCoord = event.data.lastCoord

to mouseDownHandler and I added

        if(event.data.lastCoord != event.data.initCoord){
            obj = $(this);
            $('a', obj).on('click', function(event) {
             event.preventDefault();                      
            });
            setTimeout(function(){$('a', obj).off('click'); },300);
        }

to mouseUpHandler and I turned on preventdefault

$('#viewport, #inner').
        dragscrollable({dragSelector: '.dragger:first', preventDefault: true});

OTHER TIPS

based off your example this seems to work on fiddle.

<head>
    <title>iPhone Test</title>
    <link rel="stylesheet" href="http://code.jquery.com/ui/1.9.1/themes/base/jquery-ui.css" />
    <script src="http://code.jquery.com/jquery-1.8.2.js"></script>
    <script src="http://code.jquery.com/ui/1.9.1/jquery-ui.js"></script>

<script type="text/javascript">
  $(document).ready(function() {


    // Set drag scroll on first descendant of class dragger on both selected elements
    $('.dragger').
        draggable({ start:function(){ console.log("HI");

    }});

  });

</script>


</head>
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top