JavaScript обёртка скроллбара в виде jQuery плагина

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

Существует два основных подхода для стилизации скроллбара средствами HTML/CSS, каждый из которых имеет свои плюсы и минусы:

  • Эмуляция скролла средствами JavaScript
  • JavaScript обёртка над родным скроллом


Эмуляция скролла средствами JavaScript


Огромным преимуществом данного подхода является то, что это полностью JavaScript решение. Благодаря этому данное решение легче в разработке и является максимально кроссбраузерным (в том плане, что поведение скролла во всех браузерах будет одинаковым, не зависимо от особенностей реализации скролла браузера), оказывая минимальное влияние на HTML структуру и применяемые CSS стили. Подобным подходом пользуются jScrollPane, FleXcroll, Tiny Scrollbar и многие другие.

Однако сильная сторона данного подхода является одновременно и его слабой стороной:

  • Сложность или невозможность эмулировать/перехватить все события
  • JavaScript эмуляция работает медленнее родного скролла


JavaScript обёртка над родным скроллом


Данный подход заключается в том, что родной скролл скрывается средствами HTML/CSS, продолжая выполнять своё предназначение — прокрутку содержимого. Подобное решение является более предпочтительным по той причине, что родной скролл в любом случае работает лучше эмулированного. Многие пробовали создавать плагины на базе этого подхода, но из-за отсутствия каких-либо стандартов, кроссбраузерная реализация очень сложна, и накладывает определённые ограничения на HTML структуру и используемые стили CSS. По этой причине многие разработчики создают реализацию только вертикального скролла, который ведёт себя во всех браузерах более-менее предсказуемо.

Одна из неплохих реализаций подобного подхода была описана совсем недавно в статье Кроссбраузерная кастомизация системного скроллбара с достаточно подробным объяснением.

Изобретение трёхколёсного велосипеда

Одной из причин создания очередного велосипеда явилось то, что поиск по скриптам для стилизации скролла показал более 20 разнообразных плагинов, ни один из которых не подошёл для заказанного проекта. Большинство из известных плагинов не подошли по причине медленной работы при большом количестве инициализированных скроллов на странице. Другие же не подошли из-за неудобной реализации или недостаточной кроссбраузерности.

Было решено сделать собственную реализацию, отвечающую следующим требованиям:

  • Поведение скролла должно быть максимально приближённым к родному
  • Вертикальный и горизонтальный скроллбар
  • Минимальная нагрузка на процессор
  • Полная стилизация внешнего вида средствами HTML/CSS
  • Возможность применить свою HTML структуру для скроллбара, либо указать плагину использовать уже существующий элемент в качестве скроллбара
  • Автоматическое изменение скролла при изменении содержимого или изменении размеров самого контейнера без необходимости переинициализации скрипта
  • Ширина и высота контейнера может быть установлена как в пикселях, так и в процентах, либо ограничена средствами CSS max-height/max-width
  • Скролл может находиться как в любом месте внутри контейнера, так и за его пределами
  • Автоматическое вычисление размеров скроллбара, либо значение, устанавливаемое через CSS стили
  • Поддержка IE7+, Firefox, Chrome, Opera, Safari
  • Возможность «из коробки» отключения скролла для мобильных браузеров


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

Избежать полной эмуляции скролла всё же не получилось — необходимо эмулировать поведение скролла, когда мышь находится над стилизуемым скроллом: отлавливать скролл мыши, drag&drop, клики по самому скроллу и стрелочкам. Идеального решения «Подключил и забыл», конечно же, не получилось. Но практически всех поставленных целей удалось добиться в полной мере.

Демонстрация

Исходные файлы

Сравнение функциональности популярных скроллбаров


На заметку


Следует помнить, что для работы стилизованного скроллбара необходима определённая HTML структура, для которой исходный контейнер JavaScript-ом оборачивается в другой контейнер при инициализации. По этой причине сущестуют некоторые особенности использования, стуктуры HTML и стилей CSS:

  1. Исходный контейнер не должен содержать инлайновые стили
  2. Следует избегать использования padding/margin для контейнера. Если нужен отступ, лучше добавить внутрь ещё один контейнер с необходимым отступом
  3. При изменении содержимого контейнера не стоит обращаться к контейнеру по классу, т.к. эти классы будут использоваться и контейнером-обёрткой


К небольшим недочётам можно отнести разность высоты/ширины прокрутки колёсиком мыши в случаях, когда мышь находится над содержимым контейнера (родное поведение) и когда мышь находится над скроллбаром (эмулируемый скролл). Есть несколько идей, которые довольно сложны в реализации, поэтому оставляю их «на потом».

Также пока не удаётся избавиться от неприятного эффекта прокрутки контейнера при выделении текста в WebKit браузерах Chrome и Safari. Частично удалось это сделать при использовании outer-скролла (есть в демонстрации).

Примечания


Из-за разности поведения скролла не только в разных браузерах, но и в разных версиях одного и того же браузера (да-да, того самого браузера), пришлось перепробовать множество комбинаций margin/padding/border/position для вычисления схожего поведения. Во время поиска решения, нашлось несколько интересных особенностей:

  • В ИЕ8 — баги с использованием max-height: в некоторых случаях рендерер 8-й версии ИЕ крашится, либо пытается сделать высоту контейнера равной max-height (официальный баг релиз версии)
  • WebKit-браузеры (Chrome, Safari) при выделении текста делают прокрутку внутреннего контейнера, «обнажая» скрытый скроллбар
  • Если содержимое превышает размеры контейнера, то отображение правого и нижнего паддинга остаётся на усмотрение самого браузера
  • При поиске плагинов, чтобы быстро узнать используется ли стандартный механизм скроллинга, достаточно нажать на скролл мыши, находясь над прокручиваемым контентом


Обновление до версии 0.1.3 (20130425):


  • улучшена эмуляция скролла: теперь скролл колёсиком мыши над эмулируемым скроллом работает почти идентично натуральному скроллу; также изменено поведение при нажатии и удержании мыши на подложке скроллбара
  • исправлено CSS позиционирование, при котором происходил «лишний» сдвиг контейнера при выделении текста в WebKit браузерах Google Chrome / Safari


Обновление до версии 0.1.4 (20130430):


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


Обновление до версии 0.1.6 (20131018):


  • добавлена опция игнорирования инициализации скролла на мобильных устройствах
  • добавлена поддержка drag для скролла на тач-устройствах


Обновление до версии 0.1.7 (20140307):


  • добавлен хак для исправления появления скроллбара при 1-пиксельном зазоре в ИЕ


Обновление до версии 0.1.8 (20140308):


  • исправлен баг с отображением горизонтального скроллбара если высота содержимого меньше высоты контейнера (случаи с height:100%)


Обновление до версии 0.1.9 (20140310):


  • исправлен баг с отображением вертикального скроллбара если контент содержит div с height:100%; overflow: hidden;, внутри которого div с высотой, превышающей высоту внешнего контейнера (спасибо за отзывы и замечания Evangeline Rei)
  • добавлена опция autoUpdate отвечающая за автоматическую реинициализацию скроллбара при изменении размеров контента/контейнера


Обновление до версии 0.2.0 (20140312):


  • добавлена опция onUpdate для возможности пересчёта размеров скроллбара вручную. благодаря данной опции был добавлен скроллбар в виде карты страницы
  • добавлена опция stepScrolling отвечающая за пошаговую прокрутку к месту, где удерживается нажатой кнопка мыши на скроллбаре. если опция отключена, то содержимое будет прокручено сразу до местоположения мыши, в противном случае будет происходить пошаговая прокрутка с ускорением до места удерживания мыши (эмуляция поведения скролла)
  • скрытие/отображение скроллбаров полностью перенесено в CSS
  • изменено поведение onInit — теперь запуск функции происходит только один раз при инициализации


Обновление до версии 0.2.1 (20140323):


  • исправлена ошибка с прокруткой к #anchor-элементу, когда становится видимым горизонтальный скролл


Обновление до версии 0.2.2 (20140411):


  • исправлена ошибка с инициализацией нескольких скроллбаров с настройками по умолчанию
  • добавлен элемент scroll-element_corner для удобной CSS настройки уголка если видны оба скроллбара


Обновление до версии 0.2.3 (20140703):


  • исправлена ошибка с видимым скроллбаром при изменении zoom-а в браузере
  • исправлена ошибка с неверной инициализацией размеров скроллбара для ИЕ при использовании CSS * { box-sizing: border-box; }
  • добавлена callback функция onScroll, которая позволяет легче определять степень прокручивания контейнера
  • скроллбар может быть использован как директива для отличного фреймворка Angular.JS
  • добавлена возможность переопределять значения по-умолчанию через глобальную переменную jQueryScrollbarOptions до загрузки плагина
  • оптимизирована проверка изменения размеров контейнера


Обновление до версии 0.2.4 (20140715):


  • добавлена возможность стилизации скроллбара для TEXTAREA наконец-то
Поделиться публикацией

Комментарии 62

    +18
    Дизайнеров, которые требуют нестандартных скроллбаров, надо ИМХО наказывать за непрофессионализм.
      +12
      На самом деле этот вопрос довольно сложен — в некоторых случаях необходимо избавиться от скроллбара в центре сайта, т.к. это портит весь дизайн. Про замену системного скроллбара, который скроллит всю страницу, здесь речи не идёт.
        +2
        Наличие прокручиваемого блока само по себе нередко говорит о беспомощности дизайнера. Необходимость нестандартной стилизации соответствующей локальной полосы прокрутки — лишь следствие.
          0
          На всякий случай: если работа с дизайном, использующим локальную (и нестандартно стилизованную) полосу прокрутки, неизбежна, то наличие JavaScript-решений, несомненно, полезно. Главное — чтобы использование JS-решения было способом воплощения неправильного дизайна, а не, наоборот, дизайнер беспечно использовал локальную прокрутку только на том основании, что технические решения для реализации нестандартной полосы прокрутки существуют. На уровне дизайна использование локальной прокрутки — решение в подавляющем большинстве случаев неудачное.
        –5
        Поддерживаю. Люто ненавижу замену системным скролам. Для google wave например даже расширение в хроме было, возвращающее родной скролл.
        0
        Если вести по диагонали и упереться в одну из сторон, то начинает глючить.
          0
          Как именно и в каком браузере?
            0
            win7 x64 chrome 26
              0
              А как именно начинает глючить? В чём проявляется?
              Просто у меня во время тестирования на такой же конфигурации никаких отклонений от стандартного поведения не наблюдалось. Возможно я что-то упустил во время тестов.
                0
                Если вести допустим строго в право а потом вниз, вместо прокрутки (на втором примере, на первом похоже работает как надо), браузер прокручивает основное окно.

                PS в примере с XP барами, не хватает эффекта вдавленности.
                  +1
                  Такое поведение наблюдается в Хроме и с родным скроллом. Дело в том, что при достижении конца скролла (т.е. когда контент полностью прокручен в том направлении, в котором Вы его ведёте), скролл перехватывается основным окном, и обратно на элемент уже не возвращается.

                  Кстати, первый и второй скролл абсолютно одинаковы по функциональности. Различие — применяемые стили.

                  Насчёт вдавленности: скролл поддерживает изменение стилей для dragged-скролла, просто не добавлены CSS-стили.

                  Прмеры CSS-изменения цвета в зависимости от hover и от dragged добавлены во втором и третьем примере (Simple outer scrollbar): hover делается нативным CSS, а при нажатии мыши скроллу добавляется класс scroll-draggable.

                  Чуть позже добавлю пример для скролла в стиле MacOS — из-за изменения системы позиционирования, стили для этого скролла не были переписаны, поэтому пример не был добавлен.
                    0
                    Я вам еще раз повторяю, в первом скроле все работает как надо (стиль XP), во втором возникает этот баг.
                    Честно говорю — без понятия почему так происходит, попробуйте. Если не верите могу сделать видео.
          –1
          Тормозит.
            +1
            Что именно тормозит? Какие действия производите?
            Для сравнения справа есть две кнопки Init и Destroy для возможности сравнить с оригинальным поведением скролла.
              –3
              Скроллинг тормозит, нативный работает нормально, ваш же имеет задержку в несколько миллисекунд.
                +2
                Возможно тормозит изменение позиции бегунка скроллбара, но скролл контента тормозить не должен. Отличие JavaScript обёртки от полной эмуляции скролла в том, что в полной эмуляции вначале генерируется событие, которое изменяет всё почти одновременно, а в обёртке вначале браузер производит действие, потом генерирует событие, обрабатываемое JavaScript-ом.

                Если же речь идёт об изменении размеров содержимого, то там стоит задрежка в 300 мс для пересчёта размеров скроллбара. Другого способа автоматически отловить изменение размеров контейнера я не нашёл.

                Можно, конечно же, вызывать переинициализацию скролла и вручную сразу после изменения размеров контейнера/содержимого, но задача стояла именно в том, чтобы «подключить и забыть». По этой причине я не стал делать переинициализацию сразу же, а показываю то, что ожидает пользователя при практическом применении.

                Если задержка критична, можно вручную вызывать переинициализацию нужного контейнера после обновления.
                  +7
                  Вы настолько крут, что замечаете задержку в несколько миллисекунд? Оо
              +1
              Понравился, скроллбар близок к идеалу
                +1
                Спасибо, этого и добивался.
                0
                Не люблю, когда заказчик просит кастомизировать скролл.
                Но, когда приходилось, jScrollPane jscrollpane.kelvinluck.com очень спасал в таких ситуациях.
                  0
                  jScrollPane отличный плагин, сталкивался с ним. Но на тот момент, когда мы им пользовался, сталкивался с проблемами переинициализации скролла, после того, как контейнер становился невидимым или изменял свой размер.
                    0
                    Там же есть функция для принудительно переинициализации. То же самое приходится делать при изменении содержимого прокручиваемой области. Да, решение генерит лапшу в коде, но вполне реально сделать красиво.
                      +1
                      В том-то и проблема. что в нашем случае переинициализация не помогала. Возможно проблема была в том, что менялись стили — контейнер скрывался/показывался с помощью jQuery slideUp/slideDown. После подобного помогает только дестрой и новая инициализация скролла. Помимо этой, были и некоторые другие проблемы, связанные с тем, что данная реализация — это всё же эмуляция скролла, а не родное поведение.
                  +1
                  Нажатия на стрелки по краям полос срабатывают только при отпускании, в родном же варианте при нажатии, а при задержании нажатия начинается продолжительная прокрутка.
                    0
                    Довольно сложно обработать все нативные события скролла. Для обработки подобных событий необходимо подключать дополнительную библиотеку обработки событий мыши, чего мне очень не хотелось делать так же, как и увеличивать размер плагина. По этой причине я ограничился минимальным необходимым для эмуляции фукнцоиналом.

                    Если честно, то сейчас меня больше интересует проблема несоответствия прокручивания когда мышь находится над стилизованным скроллом по той причине, что в большинстве дизайнерских проектов у скролла стрелочек нет вообще, да и сами пользователи редко пользуются функционалом, выходящим за рамки простого клика.
                      +1
                      Для обработки подобных событий необходимо подключать дополнительную библиотеку обработки событий мыши

                      Это есть в JavaScript без библиотек, и событие уже обрабатывается, но не верно (отпускание/нажатие кнопки мыши).
                        +3
                        Изменил поведение на mousedown — это действительно удобнее, чем клик. Однако насколько необходима поддержка удерживания кнопки мыши нажатой на данном элементе — вот в чём вопрос.
                      0
                      Обновил плагин и добавил поддержку удержания мыши. Хотя поведение немного и отличается от родного, но работает почти также.

                      Отличие в том, что родной скролл перестаёт работать если убрать мышь за пределы стрелочки. В JavaScript-е это сделать нельзя, т.к. событие mouseleave не происходит, если кнопка мыши не отпущена. Но думаю, что это событие можно отследить через mousemove.
                      0
                      В отличие от многих плагинов, работает почти как ожидалось. Не понравилось только одно: докрутил до конца блока по вертикали, стал прокручивать страничку. Картинка уехала, мышка попала на горизонтальный скроллбар и при любом вертикальном жесте срабатывает именно этот горизонтальный скроллбар, а не скроллинг странички.
                        0
                        Планирую добавить по возможности отключение скролла всей страницы, если у контента прокручивается, т.к. мне тоже не нравится подобное поведение. Однако текущей задачей стояло сохранение родного поведения скролла браузера.
                          0
                          В родном как раз-таки наоборот: вертикальные жесты прокручивают только по вертикали, горизонтальные — по горизонтали, независимо от положения мышки на каком-либо из скроллбаров (macosx, magic mouse).
                            0
                            Извиняюсь, обдумывал другую проблему, поэтому не до конца вник в смысл предыдущего комментария.

                            Сейчас довольно сильно отличается прокрутка колёсиком мыши основного контента, от эмулируемой прокрутки (когда указатель мыши находится над скроллбаром — упомянуто в топике), и отличия не только в различии шага прокрутки, но и в не очень хорошей поддержке JavaScript-обработки событий скроллинга мыши. Насколько я знаю, не во всех браузерах указывается отдельно указывается прокрученное растояние по осям X/Y (по крайней мере так написано в док-е по jQuery MouseWheel event).

                            Так что управление колёсиком мыши горизонтальным скроллом — это действительно нестандартное поведение. Меня всегда удивляло, почему если мышь находится над горизонтальным скроллом, прокрутка колёсиком продолжает прокручивать контент вертикально, а не горизонтально. Думаю, что подобное поведение было бы логичным.

                            Другой вопрос — то, что есть мыши, позволяющие прокручивать и по горизонтали, как в Вашем примере. Исходя из того, что я возможно не смогу отличить скролл по вертикали от скролла по горизонтали средствами JavaScript, считаете, что стоит отключить подобное поведение?
                              0
                              Вот уж не знаю, как лучше… Кажется, мышки с жестами (apple, ms) и те, что с двумя колёсами, в js никак не определить (может, что изменилось? но я не припомню. но хорошо бы проверить). По мне, так наименьшим злом было бы, если бы прокрутка хотя бы не останавливалась. То есть, сейчас я начал скроллить страничку, попал на скроллбар и опа: оно остановилось — а можно было бы начинать скроллить скроллбаром только если за несколько миллисекунд до этого сама страничка не была в состоянии прокрутки.
                              Хотя конечно самый приятный вариант — как в системе (но понимаю, что желания заказчиков разные бывают, да).
                                0
                                Учтено. Отключил обработку скролла мыши горизонтальным скроллбаром. Но пока комитить не буду, т.к. работаю над другой задачей и изменения нестабильны.
                        +6
                        Для анимаций лучше использовать requestAnimationFrame и transform: translateX[Y] (поддержка gpu) в купе с фоллбэками для старых браузеров.

                        Советую посмотреть исходники скроллера Sly и статью Leaner, Meaner, Faster Animations with requestAnimationFrame.

                        Разница может быть такой (а в мобильных браузерах она будет особенно заметна):
                          +1
                          Спасибо за наводку. Прежде не сталкивался с оптимизацией анимации, но в данном случае мне хватает возможностей, предоставляемых jQuery. В данном плагине я стараюсь свести количество используемой анимации к минимальному, либо вообще отказаться от анимации.
                          +3
                          Есть техника отслеживания изменения размеров блока через подписку на события «overflowchanged» / «resize» — работает в IE, Firefox, Chrome, Opera, Safari
                          Это позволит вам избавится от setInterval для проверки изменения размеров блока.
                          Там, где эта техника не работает (напр., Opera), можно оставить setInterval.
                            +1
                            Большое спасибо за ссылку, не знал про это. Протестирую и добавлю функционал в плагин в ближайшее время.
                              0
                              Я попробовал воспользоваться методом, используемым в той статье, но, увы, у меня ничего не получилось. Данный метод позволяет обнаружить изменения в размере самого блока, но не изменения размера внутреннего содержимого. К сожалению, пока что придётся оставить обновление по интервалу, а в критичных случаях — вручную пользователем, после какого-либо изменения.
                                0
                                Сделал pull request
                                Чтобы детектить изменения размера контента, достаточно его обернуть в блок, который флотнуть- а на этом блоке уже «слушать» события «overflowChanged»/«resize».
                                Теперь во всех юраузерах, где срабатывает способ, описанный в ссылке выше- используется он вместо setInterval.
                                Иначе- все по-старому.
                                Метод без setInterval не сработал, как и ожидалось, только в Opera.
                                  0
                                  Большое спасибо за участие в проекте.

                                  К сожалению, я не могу принять Ваши изменения, т.к. придерживаюсь политики минимального вмешательства в оригинальное поведение элементов, а данное решение изменяет содержимое оригинального контейнера, оборачивая его содержимое в подконтейнер.

                                  Как Вы видели в обсуждении, даже минимально необходимое вмешательство в структуру HTML может привести к недопониманию «почему мой код раньше изменял элемент, а теперь не работает?», подобное же вмешательство может привести к пересмотру кода и необходимости исправить его с учётом наличия/отсутствия подконтейнера resize-listener.

                                  Пользователь всегда может вручную переинициализировать скролл при изменении содержимого.
                              –1
                              Ну и как теперь делать программную прокрутку в нужную позицию?

                              $(".class:first")[0].scrollTop = pixelsFromStart;

                              Это больше не работает.
                                +1
                                Следует помнить, что для работы стилизованного скроллбара необходима определённая HTML структура, для которой исходный контейнер JavaScript-ом оборачивается в другой контейнер при инициализации.

                                При изменении содержимого контейнера не стоит обращаться к контейнеру по классу, т.к. эти классы будут использоваться и контейнером-обёрткой


                                Фукнцоинал скролла родной — браузерный, т.е. все нативные фукнции работы со скроллом работают.

                                Решения два:
                                • добавить нужному контейнеру айди: $('#elementId').get(0).scrollTop = pixelsFromStart;
                                • отсеивать элементы по классу с помощью not: $('.class').not('.scroll-wrapper').eq(0).get(0).scrollTop = pixelsFromStart;
                                  0
                                  Спасибо! Извините, что невнимательно читал, просто нужно было быстро внедрить этот плагин, а на первый взгляд в посте ничего особенно важного не сообщалось.
                                +1
                                Вообще-то работает.
                                Попробуйте на демонстрационной странице выполнить:
                                $(".scroll-content")[0].scrollTop = 100;
                                  0
                                  Простите, а чем не подошёл baron, ссылка на который даже есть в статье? Удовлетворяет всем пунктам кроме последнего — отключение на мобильниках «из коробки», что решается трёхстрочной обёрткой.

                                  diokuz.github.com/baron
                                    +1
                                    От использования baron-а остановила незавершённость плагина — отсутствие горизонтального скролла. Кстати, именно с горизонтальным скроллом проблем намного больше, чем с вертикальным, т.к. все браузеры заточены именно на растягивание по ширине, но не по высоте. Либо для элемента необходимо выставлять фиксированную высоту, что, имхо, неправильно. Ну, плюс ещё несколько особенностей, среди которых неперекрывающий и внешний скролл.
                                      0
                                      Горизонтальный скролл давно реализован в бароне, это можно посмотреть на странице с тестами.

                                      Внешний скролл / скролл произвольных размеров и позиций также возможен.
                                        +1
                                        Наверно, фразу в конце вашей статьи: «К недостаткам можно отнести отсутствие горизонтального скроллбара…» стоит подкорректировать, потому что мне, например, пришлось из-за нее продолжить поиск альтернативного решения. К тому же, страница diokuz.github.io/baron/ не содержит примера с горизонтальным скроллом. Спасибо за отличный скрипт.
                                          0
                                          Статья была написана на конкретную версию барона — с тех пор много воды утекло.
                                    0
                                    Кстати баг в вебките с горизонтальным скроллом в бароне вылечен — об этом тоже в статье написано.
                                      +1
                                      Буду честен, если скажу, что про баг в вебките я узнал именно из вашей статьи. Это свело на нет мою предыдущую реализацию, пришлось тотально пересматривать проблему позиционирования, что отложило выход этого поста на несколько дней. В представленной реализации баг решён только частично, а ваш способ с процентными размерами не подходит для высчитвания высоты контейнера.

                                      Точное значение, на которое прокручивается контейнер при выделении текста, я высчитать пока не могу, но подозреваю, что это около 10-12 пикселей, даже если высота и ширина скролла в вебките выставлена в 0. Так что я нахожусь в активном поиске решения или хака
                                        0
                                        Прекратите поиски)) Под решением я подразумевал обнуление ширины скроллбара через

                                        .scroller::-webkit-scrollbar { /* Preventing webkit cross-direction scrolling bug */
                                            width: 0;
                                        }
                                        


                                        Но вы можете вычислить и точное значение если хотите — это offsetWidth — clientWidth при обнуленном бордере.
                                          +1
                                          Ширину и высоту обнулил — браузер всё равно продолжает скроллить. В демонстрации даже есть блок, помеченный (bug on text selecton in webkit browsers: chrome & safari), который всё равно продолжает скроллиться. Думаю, что тут дело в видимости внутреннего контейнера.

                                          Не нашёл ссылки на демо с горизонтальным скроллом.

                                            0
                                            Там нет ссылки, нужно склонировать проект и посмотреть в тестах.

                                            Также подключение горизонтального скролла описано в readme.
                                              0
                                              Да, чуть позже после комментария я скачал исходники и посмотрел тесты.
                                              ИМХО, стоит обновить статью и добавить горизонтальный скроллбар в демо.
                                      0
                                      Хорошо бы, если иннер аутохайд скроллбар не пропадал, если он тягается, но мышь уже за пределами блока.
                                        0
                                        Легко — где-то на 446 строке (для сохранения порядка стилей) в CSS прописать

                                        .scroll-simple_inner > .scroll-element.scroll-draggable .scroll-bar { display: block; }

                                        Вечером внесу изменения в демо.
                                          0
                                          Пасиб!
                                        0
                                        CSS решение (webkit)
                                        ::-webkit-scrollbar {
                                            width: 9px;
                                        }
                                        
                                        ::-webkit-scrollbar-track {
                                            -webkit-box-shadow: inset 0 0 6px rgba(0,0,0,0.3); 
                                            -webkit-border-radius: 10px;
                                            border-radius: 10px;
                                        }
                                        
                                        ::-webkit-scrollbar-thumb {
                                            -webkit-border-radius: 10px;
                                            border-radius: 10px;
                                            background: rgba(241, 170, 44, 0.9);
                                            -webkit-box-shadow: inset 0 0 6px rgba(0,0,0,0.5); 
                                        }
                                        
                                        
                                          0
                                          Не хватает пары вещей. Было бы неплохо, если бы mousewheel крутил горизонтальный скролл, если вертикальный отсутствует, либо если на горизонтальный навели курсор).
                                          А так неплохо
                                            0
                                            Как обсуждалось выше, данный функционал был специально отключён, т.к. данное поведение отличается от браузерного.

                                            Однако его легко обратно включить — достаточно закомментировать условие на строке 249 (не забывая про закрывающую скобку): if(d == 'y'){

                                          Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.

                                          Самое читаемое