Горизонтальная прокрутка с ява-скрипт 3
(перевод Виктории Шидловской Fun with Overflows)
Добавлен урок по горизонтальной прокрутке изображений, растягивающихся на весь экран.
Пара человек попросили объяснить, как работает прокрутка на Plurk’s browse timeline. Затем на свое десятилетие Google выпустил 10 year timeline. Так что я решил показать, как сделать прокрутку, используя оба метода – прокрутку с помощью колесика мыши и с помощью перетаскивания мышкой.
Далее представлены два урока по горизонтальной прокрутке с ява-скриптом.
Первый урок – прокручиваемый дневник. Второй урок написан по запросу Trevor Morris, который хотел сделать «перетекание» радуги в шапке своего сайта более плавным.
1. Горизонтальная прокрутка мышью и колесиком мышки с помощью ява-скрипта
При создании горизонтально прокручиваемого дневника мы обеспечим поддержку прокрутки как на Plurk и как на Google.
Для начала сделаем тянущийся (wrapping) div со значением overflow: auto; (которое мы потом изменим на overflow: hidden; с помощью jQuery). Внутренний элемент (в нашем случае ul) будет иметь достаточную ширину, чтобы вместить в себя все необходимые элементы li, а чтобы li не растягивали div вертикально (не создавали новую линию), все li имеют определенную ширину и свойство float: left;.
Постановка задачи
- Уловить событие mouse down, определить положение прокручиваемого элемента и X-координату мышки.
- Когда мышка двигается (в нажатом состоянии), то прокручивать элемент на расстояние от старого до нового положения мышки.
- Когда мышка находится вне окна прокрутки, то отменить событие mouse down или запустить событие mouse up.
CSS
Не буду приводить весь код, только то, что имеет отношение к делу.
#timeline {
height: 375px; /* fixed */
overflow: auto; /* changed to hidden via JavaScript */
}
.tl-events { /* the UL */
width: 11800px; /* the width required to hold all the info */
}
.tl-events li {
float: left; /* allows the lis to stack against eachother */
width: 300px;
}
jQuery
Код, используемый в demo
Мы используем три встроенные функции: mousedown, mouseup and mousemove. Затем добавляем jQuery mousewheel plugin перед изменением overflow в CSS:
// Когда DOM готов...
$(document).ready(function () {
$('#timeline').mousedown(function (event) {
// прикрепить 3 data элементу #timeline
$(this)
.data('down', true) // индикатор того, что мышь нажата
.data('x', event.clientX) // текущая X-координата мышки
.data('scrollLeft', this.scrollLeft); // текущая позиция скролла
// вернуть false, чтобы избежать выделение текста и перетаскивания ссылок
//внутри окна прокрутки
return false;
}).mouseup(function (event) {
// Когда мышь отжата (mouse up), «выключить» индикатор down
$(this).data('down', false);
}).mousemove(function (event) {
// если мышь нажата – начать эффект перетаскивания (drag)
if ($(this).data('down') == true) {
// this.scrollLeft - это scrollbar, появившийся из-за слишком большого
//контента (overflowing content)
// Новая позиция высчитывается по формуле: начальная позиция скролла +
//начальная X-координата нажатой мышки – новая X-координата
// Ищу того, кто мог бы как-то увеличить скорость прокрутки
this.scrollLeft = $(this).data('scrollLeft') + $(this).data('x') - event.clientX;
}
}).mousewheel(function (event, delta) {
// Сейчас подключаем плагин mouse wheel и прокручиваем на значение 'delta',
// что является движением колесика, умноженное на произвольное число.
this.scrollLeft -= (delta * 30);
}).css({
'overflow' : 'hidden', // изменить на hidden для пользователей с поддержкой JS
'cursor' : '-moz-grab' // добавить курсор с изображением лапки
});
});
// И наконец, вызываем событие, если мышка вышла за пределы прокручиваемой области
// Мы не вызываем событие mouse up (так как мышь все еще нажата)
$(window).mouseout(function (event) {
if ($('#timeline').data('down')) {
try {
// *try* (попробовать) вычислить элемент, на который перешла мышка после того,
//как покинула область
// и если мы мы действительно вышли за пределы этой области,
//то отключаем индикатор события mouse down
if (event.originalTarget.nodeName == 'BODY' || event.originalTarget.nodeName == 'HTML') {
$('#timeline').data('down', false);
}
} catch (e) {}
}
});
2. Эффект радуги на сайте Trevor Morris
Используя тот же this.scrollLeft
DOM мы можем создать совершенно другой эффект.
Он будет работать также при отсутствии поддержки ява-скрипта.
Разметка
Пустой экстра-div
— это широкий элемент, а div#rainbow
— это элемент с overflow, который будет перемещаться внутри.
<div id="headerEffect">
<div id="rainbow"><div></div></div>
<div id="swirl"></div>
</div>
CSS
Кроме CSS я также прописал код поддержки прозрачности PNG-изображений для IE6, для корректной работы при отключенных ява-скриптах.
#headerEffect {
position: absolute;
width: 100%;
height: 400px;
overflow: hidden;
top: 0; /* Убедитесь, что IE растягивает его правильно */
left: 0;
}
#rainbow {
height: 400px;
width: 100%;
overflow: hidden;
}
#rainbow div {
height: 400px;
width: 3312px; /* хорошая ширина, чтобы быть уверенным, что картинка будет повторяться */
background: url(/css/img/header.colour.3.png) repeat-x scroll -20% 0;
}
#swirl {
background: url(/css/img/header.swirl.png) no-repeat scroll 50% 0;
height: 400px;
width: 100%;
position: absolute; /* располагает swirl *над* rainbow */
top: 0;
left: 0;
}
Несколько специальных стилей для IE6:
<!--[if lte IE 6]>
<style type="text/css" media="screen">
/* Добавил alpha прозрачность в CSS для отображения в браузерах без поддежки JS */
#swirl {
background-image: none;
filter: progid:DXImageTransform.Microsoft.AlphaImageLoader(src='http://www.trovster.com/css/img/header.swirl.png', sizingMethod='scale');
}
</style>
<![endif]-->
JavaScript
Заметьте, что этот раздел я назвал JavaScript, а не jQuery; мы используем свойство scrollLeft
для div#rainbow
, и jQuery нужен нам только для готового события.
$(document).ready(function () {
// определяем элемент rainbow
var rainbow = document.getElementById('rainbow'),
lastPos, // хранит последнюю позицию scrollLeft
width = 1656; // точка повтора бэкграунда
// мы каждый раз сбрасывем все значения при перезагрузке страницы, так что бэкграунд всегда один и тот же
rainbow.scrollLeft = width;
// используем интервал для прокрутки радуги
setInterval(function () {
// заставляем бэкграунд прокручиваться слева направо
rainbow.scrollLeft -= 5;
// если мы достигнем начала, то lastPos будет равен scrollLeft
if (lastPos == rainbow.scrollLeft) {
// reset
rainbow.scrollLeft = width;
}
lastPos = rainbow.scrollLeft;
}, 100); // комбинация миллисекунд
});
Прикрепил скрипт с шаблону Joomla. http://brandingunion.com/index.php?option=com_content&view=category&layout=blog&id=9&Itemid=137
Но почему-то не получается прокручивать страницу. Получается только передвигать курсором. При этом курсор прилипает к блоку с прокруткой.
Не подскажете, в чём может быть дело?
НравитсяНравится
А вот такое как реализовать? ( http://www.urealty.ru ) — панель у шапки.
НравитсяНравится
Спам?
НравитсяНравится
Разобрался и сделал вот пример работы
Находим строчку .mouseup(function (event) { и добавляем $(this).css({‘cursor’ : ‘-moz-grab’});
А теперь дописываем следующий код
.mousedown(function (event) {//если мышка нажата то меняем курсор
$(this).css({‘cursor’ : ‘-moz-grabbing’});
})
НравитсяНравится
Вопрос по поводу курсоров можно ли как нибудь реализовать отображения курсора при на видении -moz-grab а при перетаскивании -moz-grabbing
НравитсяНравится
Вот тоже пример, интересно как реализовано? http://emfire.ru/
НравитсяНравится
В самом деле — очень клевый сайт! Поставлю на главную.
НравитсяНравится
Тьфу ты, вертикальное перетаскивание.
НравитсяНравится
Ой, нет, извините! Отдельный тьютор надо искать и переводить. Боюсь еще, что слишком странная просьба, если сайт можно прокручивать вертикально колесиком мыши, то зачем перетаскивать? Не юзер фрэндли.
НравитсяНравится
Привет. Не подскажите плз как прикрутить горизонтальное перетаскивание мышкой? Я фотограф и хочу подобным образом организовать свое портфолио на сайте. Спасибо.
НравитсяНравится
Присоединяюсь к просьбе, хочу тоже свое портфолио подобным образом оформить.
НравитсяНравится
Этот пример — ссылка на который идет с картинки — он как раз перетаскивается мышью! То есть там и скролл и драг!
НравитсяНравится