Кроссбраузерный mousewheel, обработка события скролинга

Недавно наткнулся на маленькую проблемку, в одном из последних проектов нужно было прикрепить событие mousewheel, причем код должен был быть написан без сторонних фреймверков. Когда попытался повесить функцию на onmousewheel, убедился, что она работает по разному в некоторых браузерах, а в иных и вовсе не работает.

В этой статье я хочу поделится с вами функциями на JavaScript для кроссбраузерного события скролинга. Покопавшись в интернете нашел несколько неплохих идей, но почти все они были полуфабрикатами. Поэтому, собрав определенную коллекцию различных решений – вывел и оптимизировал их в одну легкую в использовании функцию, а что самое главное – универсальную.

Основной код функции:

// Основная Функция mousewheel
function wheel(event){
        var delta = 0;
        if (!event) event = window.event; // Событие IE.
        // Установим кроссбраузерную delta
        if (event.wheelDelta) {
                // IE, Opera, safari, chrome - кратность дельта равна 120
                delta = event.wheelDelta/120;
        } else if (event.detail) {
                // Mozilla, кратность дельта равна 3
                delta = -event.detail/3;
        }
        // Вспомогательня функция обработки mousewheel
        if (delta && typeof handle == 'function') {
                handle(delta);
                // Отменим текущее событие - событие поумолчанию (скролинг окна).
                if (event.preventDefault)
                        event.preventDefault();
                event.returnValue = false; // для IE
        }
}

// нициализация события mousewheel
if (window.addEventListener) // mozilla, safari, chrome
    window.addEventListener('DOMMouseScroll', wheel, false);
// IE, Opera.
window.onmousewheel = document.onmousewheel = wheel;

Функция wheel в коде является основной, но внутри себя она имеет не менее важную функцию handle, которая выполняет основные действия на странице в зависимости от полученной переменной delta. Пока handle является виртуальной функцией, но в зависимости от нужных нам действий мы будем присваивать ей реальные.

Теперь рассмотрим как же применить эти функции в примерах.

Пример 1: изменение ширины элемента с помощью колесика мышки

Вы можете открыть пример в новом окне.

function initScript()
{
    var _container = document.getElementById('main-container');
    var _el = document.getElementById('element');
    var _elWidth = 250;
    // нициализация вспомогательной функции
    _container.onmouseover = function(){
       handle = over;
    };
    // Удаление вспомогательной функции
    _container.onmouseout = function(){
       handle = null;
    }
     
    function over(delta) {
       // получаем delta из основной функции и по результатам
       // выполняем соответствующие действия,
       // в нашем примере изменяем ширину       
       if (delta > 0) _elWidth += 5;
       else _elWidth -= 5;
           
        if (_elWidth < 0) _elWidth = 0; // минимальная ширина
        if (_elWidth > 500) _elWidth = 500; // максимальная ширина
        _el.style.width = _elWidth+'px';
    }
}
if (window.addEventListener)
    window.addEventListener("load", initScript, false);
else if (window.attachEvent)
    window.attachEvent("onload", initScript);

Пример 2: изменение размера шрифта

Вы можете открыть пример в новом окне.

function initScript()
{
    var _container = document.getElementById('main-container');
    var _elFontSize = 12;
    // нициализация вспомогательной функции
    _container.onmouseover = function(){
       handle = over;
    };
    // Удаление вспомогательной функции
    _container.onmouseout = function(){
       handle = null;
    }
     
    function over(delta) {
       // получаем delta из основной функции и по результатам
       // выполняем соответствующие действия,
       // в нашем примере изменяем размер шрифта      
       if (delta > 0) _elFontSize++;
       else _elFontSize--;
           
        if (_elFontSize < 8) _elFontSize = 8; // минимальный размер шрифта
        if (_elFontSize > 50) _elFontSize = 50; // максимальный размер шрифта
        _container.style.fontSize = _elFontSize+'px';
    }
}
if (window.addEventListener)
    window.addEventListener("load", initScript, false);
else if (window.attachEvent)
    window.attachEvent("onload", initScript);

Скачать примеры

UPD: по замечаниям комментаторов ссылка на на основную идею

Tags: ,

Воскресенье, Май 24th, 2009 JavaScript, Методики

17 Коментариев to Кроссбраузерный mousewheel, обработка события скролинга

  • Вау, круто. Молодец так и продолжай

  • Неплохо, краткость – сестра таланта. Мне понравилось. Спасибо!

  • Отличная статья!

  • Супер статья! Блог в ридер

  • Прогрессбар понравился.
    Для чего, интересно, такие странные значения в wheelDelta и detail? Почему не просто +1/-1?

  • ну это скорее вопрос к разработчикам различных браузеров, чем они руководствуются когда выдумывают такие методы. В свое время я вообще был очень удивлен, что такой событие как mousewheel не работает кроссбраузерно :(

  • Прекрасные решения, а нужно кое что попроще, но тем не менее найти нигде не могу. Есть JS массив строк (изначально полученный из MySQL и с помощью PHP отправленный в JS), к примеру их 20 (хотя число может меняться), а нужно вывести только пять (выводим с 1 по 5), при этом при прокрутке мыши вниз должны выводится со 2 по 6, итд до конца, пока последним не окажется 20-ая строка. Когда крутим вверх так же по одной возвращаемся до начала. Естесвенно только когда мышь находится в зоне этого списка, или DIVa… и что бы страница сама не крутилась…

    Помогите, как быть? =((

    Нужно это что бы список умещался в блоке не растягивая его… при этом использование полосы прокрутке делает конструкцию нелепой…

  • Что бы ответить что-то конкретно нужно видеть дизайн. А пока могу предложить как вариант использовать вертикальную карусель.

  • Дмитрий:

    Отличная статья! Спасибо!

  • Алексей:

    Добрый день! Вы не подскажете как шаг значений сделать равным 1, а не 2.
    В любом случае спасибо за статью, очень пригодилась.

  • Не совсем понятно для какого значения вам нужно сделать 1…

  • Алексей:

    При перемещении колеса мыши на одно деление, значение увеличивается/уменьшается на два. В вашем примере со шрифтом: +/-2 px (8px + 2 + 2 …..50px).

    Я успешно применил данный скрипт для изменения количества товаров в корзине, но изменение (шаг значений) по прежнему равняется 2, а хотелось бы 1.

    Перед вашим решением применял jQuery MouseWheel Plugin с тем же результатом. Никак не разберусь в чем же дело.

  • Вам в принципе не важно что возвращается в параметре delta. Вам нужно создать функцию обработчик значения delta, как в моем примере это function over. В зависисмоти от дельта (положиттельная она или отрицательная) вы можете менять свою переменную на 1. По типу моего примера с шрифтом if (delta > 0) _elFontSize++; else _elFontSize–;

  • Алексей:

    Большое спасибо, Алексей!
    Заметил такую штуку. Только в Google Chrome единица изменения значений = 2. В Oper’е и Firefox’е = 1. В IE не тестировал.

  • Благодарю, взял на вооружение)))

  • Vlad:

    Статья хорошая. Но на автора основного скрипта линк тоже ставить следует.
    http://adomas.org/javascript-mouse-wheel/

  • помогло
    спасибо автору
    просто и понятно, как использовать скролинг в скрипте

  • Оставить сообщение

    Rotaban.ru - биржа банерной рекламы