Как определить направление прокрутки - PullRequest
56 голосов
/ 23 августа 2011

Я хочу запустить функцию, когда кто-то прокручивает элемент вниз.Примерно так:

 $('div').scrollDown(function(){ alert('down') });
 $('div').scrollUp(function(){ alert('up') });

Но этих функций не существует.Есть ли решение этой проблемы? Они , кажется, способны это сделать.К сожалению, исходный код сжат, так что не повезло ...Спасибо !!

Ответы [ 8 ]

104 голосов
/ 05 сентября 2011

В конце концов мне удалось выяснить это, поэтому, если кто-то ищет ответ:

49 голосов
/ 31 июля 2012

В следующем примере будут прослушиваться только прокрутка MOUSE, без прокрутки сенсорной панели и трекпада.

Используется jQuery.on () (Начиная с jQuery 1.7, метод .on ()предпочтительный метод для прикрепления обработчиков событий к документу).

$('#elem').on( 'DOMMouseScroll mousewheel', function ( event ) {
  if( event.originalEvent.detail > 0 || event.originalEvent.wheelDelta < 0 ) { //alternative options for wheelData: wheelDeltaX & wheelDeltaY
    //scroll down
    console.log('Down');
  } else {
    //scroll up
    console.log('Up');
  }
  //prevent page fom scrolling
  return false;
});

Работает во всех браузерах.

fiddle: http://jsfiddle.net/honk1/gWnNv/7/

40 голосов
/ 25 октября 2015

Этот заслуживает обновления - в настоящее время у нас есть событие wheel:

$(function() {

$(window).on('wheel', function(e) {

	var delta = e.originalEvent.deltaY;

	if (delta > 0) $('body').text('down');
	else $('body').text('up');

	return false; // this line is only added so the whole page won't scroll in the demo
});
});
body {
  font-size: 22px;
  text-align: center;
  color: white;
  background: grey;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

Поддержка уже довольно давно поддерживается современными браузерами:

  • Chrome 31 +
  • Firefox 17 +
  • IE9 +
  • Opera 18 +
  • Safari 7 +

https://developer.mozilla.org/en-US/docs/Web/Events/wheel

Еслитребуется более глубокая поддержка браузера, вероятно, лучше использовать mousewheel.js вместо того, чтобы возиться:

https://plugins.jquery.com/mousewheel/

$(function() {

$(window).mousewheel(function(turn, delta) {

	if (delta > 0) $('body').text('up');
	else $('body').text('down');

	return false; // this line is only added so the whole page won't scroll in the demo
});
});
body {
  font-size: 22px;
  text-align: center;
  color: white;
  background: grey;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/jquery-mousewheel/3.1.13/jquery.mousewheel.min.js"></script>
22 голосов
/ 18 апреля 2015

Существующее решение

Может быть 3 решение из этой публикации и другая статья stackoverflow .

Решение 1

    var lastScrollTop = 0;
    $(window).on('scroll', function() {
        st = $(this).scrollTop();
        if(st < lastScrollTop) {
            console.log('up 1');
        }
        else {
            console.log('down 1');
        }
        lastScrollTop = st;
    });

Решение 2

    $('body').on('DOMMouseScroll', function(e){
        if(e.originalEvent.detail < 0) {
            console.log('up 2');
        }
        else {
            console.log('down 2');
        }
    });

Решение 3

    $('body').on('mousewheel', function(e){
        if(e.originalEvent.wheelDelta > 0) {
            console.log('up 3');
        }
        else {
            console.log('down 3');
        }
    });

Мультибраузерный тест

Я не смог протестировать его в Safari

Chrome 42 (Win 7)

  • Решение 1
    • Наверх:1 событие на 1 прокрутку
    • Вниз: 1 событие на 1 прокрутку
  • Решение 2
    • Вверх: не работает
    • Вниз:Не работает
  • Решение 3
    • Вверх: 1 событие на 1 прокрутку
    • Вниз: 1 событие на 1 прокрутку

Firefox 37 (Win 7)

  • Решение 1
    • Вверх: 20 событий на 1 прокрутку
    • Вниз: 20 событий на 1 прокрутку
  • Решение 2
    • Вверх: не работает
    • Вниз: 1 событие на 1 прокрутку
  • Решение 3
    • Вверх: не работает
    • Вниз: не работает

IE 11 (Win 8)

  • Решение 1
    • Вверх: 10 событий на 1 прокрутку (побочный эффект: прокрутка вниз произошла наконец)
    • Вниз: 10 событий на 1 прокрутку
  • Soltion 2
    • Вверх: не работает
    • Вниз: не работает
  • Решение 3
    • Вверх: не работает
    • Вниз: 1 событие на 1 прокрутку

IE 10 (Win 7)

  • Решение 1
    • Вверх: 1 событие на 1 прокрутку
    • Вниз: 1 событие на 1 прокрутку
  • Решение 2
    • Вверх: не работает
    • Вниз: Не работает
  • Решение 3
    • Вверх: 1 событие на 1 прокрутку
    • Вниз: 1 событие на 1 прокрутку

IE 9 (Win 7)

  • Решение 1
    • Вверх: 1 событие на 1 прокрутку
    • Вниз: 1 событие на 1прокрутки
  • Soltion 2
    • Вверх: не работает
    • Вниз: не работает
  • Решение 3
    • Вверх: 1 событие на 1 свиток
    • Вниз: 1 событие на 1 свиток

IE 8 (Win 7)

  • Решение 1
    • Вверх: 2 события на 1 прокрутку (побочный эффект: прокрутка вниз произошла в конце)
    • Вниз: 2 ~ 4 события на 1 прокрутку
  • Soltion 2
    • Up: не работает
    • Down: не работает
  • Solution 3
    • Up: 1событие за 1 свиток
    • Вниз: 1 событие за 1 свиток

Комбинированное решение

Я проверил эту сторонуЭффект от IE 11 и IE 8 исходит из заявления if else.Итак, я заменил его на оператор if else if следующим образом.

Из теста с несколькими браузерами я решил использовать Solution 3 для обычных браузеров и Solution 1 для firefox и IE 11.

Я отправил этот ответ , чтобы обнаружить IE 11.

    // Detect IE version
    var iev=0;
    var ieold = (/MSIE (\d+\.\d+);/.test(navigator.userAgent));
    var trident = !!navigator.userAgent.match(/Trident\/7.0/);
    var rv=navigator.userAgent.indexOf("rv:11.0");

    if (ieold) iev=new Number(RegExp.$1);
    if (navigator.appVersion.indexOf("MSIE 10") != -1) iev=10;
    if (trident&&rv!=-1) iev=11;

    // Firefox or IE 11
    if(typeof InstallTrigger !== 'undefined' || iev == 11) {
        var lastScrollTop = 0;
        $(window).on('scroll', function() {
            st = $(this).scrollTop();
            if(st < lastScrollTop) {
                console.log('Up');
            }
            else if(st > lastScrollTop) {
                console.log('Down');
            }
            lastScrollTop = st;
        });
    }
    // Other browsers
    else {
        $('body').on('mousewheel', function(e){
            if(e.originalEvent.wheelDelta > 0) {
                console.log('Up');
            }
            else if(e.originalEvent.wheelDelta < 0) {
                console.log('Down');
            }
        });
    }
9 голосов
/ 23 августа 2011
$(function(){
    var _top = $(window).scrollTop();
    var _direction;
    $(window).scroll(function(){
        var _cur_top = $(window).scrollTop();
        if(_top < _cur_top)
        {
            _direction = 'down';
        }
        else
        {
            _direction = 'up';
        }
        _top = _cur_top;
        console.log(_direction);
    });
});

Демо: http://jsfiddle.net/AlienWebguy/Bka6F/

0 голосов
/ 25 октября 2015

Вы можете использовать этот простой плагин для добавления scrollUp и scrollDown к вашему jQuery

https://github.com/phpust/JQueryScrollDetector

var lastScrollTop = 0;
var action = "stopped";
var timeout = 100;
// Scroll end detector:
$.fn.scrollEnd = function(callback, timeout) {    
      $(this).scroll(function(){
        // get current scroll top 
        var st = $(this).scrollTop();
        var $this = $(this);
        // fix for page loads
        if (lastScrollTop !=0 )
        {
            // if it's scroll up
            if (st < lastScrollTop){
                action = "scrollUp";
            } 
            // else if it's scroll down
            else if (st > lastScrollTop){
                action = "scrollDown";
            }
        }
        // set the current scroll as last scroll top
        lastScrollTop = st;
        // check if scrollTimeout is set then clear it
        if ($this.data('scrollTimeout')) {
          clearTimeout($this.data('scrollTimeout'));
        }
        // wait until timeout done to overwrite scrolls output
        $this.data('scrollTimeout', setTimeout(callback,timeout));
    });
};

$(window).scrollEnd(function(){
    if(action!="stopped"){
        //call the event listener attached to obj.
        $(document).trigger(action); 
    }
}, timeout);
0 голосов
/ 24 ноября 2013
var mousewheelevt = (/Firefox/i.test(navigator.userAgent)) ? "DOMMouseScroll" : "mousewheel" //FF doesn't recognize mousewheel as of FF3.x
$(document).bind(mousewheelevt, 
function(e)
    {
        var evt = window.event || e //equalize event object     
        evt = evt.originalEvent ? evt.originalEvent : evt; //convert to originalEvent if possible               
        var delta = evt.detail ? evt.detail*(-40) : evt.wheelDelta //check for detail first, because it is used by Opera and FF
        if(delta > 0) 
            {
            scrollup();
            }
        else
            {
            scrolldown();
            }   
    }
);
0 голосов
/ 23 августа 2011

Вот пример , показывающий простой способ сделать это.Сценарий:

$(function() {
  var _t = $("#container").scrollTop();
  $("#container").scroll(function() {
    var _n = $("#container").scrollTop();
    if (_n > _t) {
      $("#target").text("Down");
    } else {
      $("#target").text("Up");
    }
    _t = _n;
  });
});

#container - это ваш div id.#target просто чтобы увидеть, как это работает.Измените на то, что вы хотите, когда вверх или когда вниз.

РЕДАКТИРОВАТЬ

ОП не говорил раньше, но, поскольку он использует div с overflow: hidden, прокруткане происходит, то сценарий для обнаружения прокрутки является наименьшим из этого.Ну, как обнаружить то, чего не происходит?!

Итак, ОП сам разместил ссылку с тем, что хочет, так почему бы не использовать эту библиотеку?http://cdn.jquerytools.org/1.2.5/full/jquery.tools.min.js.

Звонок просто:

$(function() {
    $(".scrollable").scrollable({ vertical: true, mousewheel: true });
});
...