Сколько я себя помню, веб-разработчики всегда обращались к старой-доброй пагинации в случае, когда им необходимо было отобразить большое количество контента. Не поймите меня неправильно, пагинация до сих пор является эффективным способом отображения контента, но в этой статье мы поговорим о другом подходе — “ленивой” прокрутке, также известной под названием “бесконечной прокрутки” и “отказом от пагинации”. С помощью этой техники подгрузка контента производится с помощью AJAX, когда пользователь прокручивает страницу до места, где загруженный контент заканчивается. Ленивая прокрутка используется некоторыми гигантами интернета, такими как Facebook и Pinterest. В этом посте мы попробуем реализовать свой плагин для ленивой загрузки на jQuery.
Преимущества и недостатки
Преимущества такого метода очевидны. Для того, чтобы получить дополнительную порцию контента вам нет необходимости переходить на другую страницу, что также сбивает ваше внимание и заставляет смотреть в другую область страницы. Добавив возможность ленивой загрузки вы удерживаете внимание пользователя на одной и той же области в процессе чтения.
Ленивая загрузка эффективна не во всех ситуациях. Например, в случаях, когда пользователь переходит по ссылке, а затем хочет вернуться на предыдущую страницу с помощью истории браузера, он теряет позицию в той части, которая была подгружена с помощью AJAX. Одним из способов решения подобной проблемы — открывать все ссылки в новом окне или вкладке.
Недостаток, который следует из вышесказанного — у пользователя нет возможности запомнить свою позицию в части документа, которая была подгружена с помощью AJAX. Представим, что вы хотите поделиться чем-нибудь со страницы с ленивой подгрузкой со своим другом по электронной почте. Вы не сможете этого сделать, так как ссылка приведет вас обратно к вашей изначальной позиции. Так что, прежде чем бросаться внедрять ленивую загрузку на вашем сайте, подумайте о юзабилити такого решения иненно в рамках вашего сайта.
В добавок, перед тем, как решите использовать эту технологию знайте, что поисковые системы не очень-то дружны с такими решениями. Для того, чтобы избежать проблемы видимости контента поисковикам, убедитесь, что вы можете предоставить альтернативу с пагинацией или картой сайта.
Начинаем
Начнем с наброска очень простой страницы. Самые важные части страницы показаны в коде ниже. Полные файлы можно посмотреть в исходниках.
HTML
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
<div id="data-container"> <div class="data-item"> Привет! Я - первый элемент </div> <div class="data-item"> Привет! Я - второй элемент </div> <div class="data-item"> Привет! Я - третий элемент </div> <div class="data-item"> Итак, это становится скучным... </div> <div class="data-item"> Попробуем кое-что новенькое </div> <div class="data-item"> Как насче того, чтобы загрузить еще элементов посредством AJAX </div> <div class="data-item"> Нажмите на кнопку ниже, чтобы загрузить больше элементов </div> </div> <div id="button-more" onclick="lazyload.load()"> загрузить еще </div> <div id="loading-div"> загружаю дополнительные элементы </div> |
CSS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
#data-container { margin: 10px; } #data-container .data-item { background-color: #444444; border-radius: 5px; -moz-border-radius: 5px; -webkit-border-radius: 5px; padding: 5px; margin: 5px; color: #fff; } #loading-div { display: none; } #button-more{ cursor: pointer; margin: 0 auto; background-color: #aeaeae; color: #fff; width: 200px; height: 50px; line-height: 50px; } |
Основные замечания
Если вы приглядитесь к документу, что мы создали, то увидите, что новые посты будут загружены при клике на кнопку “загрузить еще”. Вот пункты, которые мы будем реализовывать:
- необходимо сделать запрос на URL, который вернет нам список элементов, которые необходимо будет вставить на странице
- этот процесс должен повторяться каждый раз, как будет нажата кнопка, но в результате должны возвращаться новые посты
- новые посты должны выдаваться на каждый запрос до тех пор, пока есть, что возвращать
- когда больше не осталось постов, необходимо сообщить пользователю, что он достиг конца
Шаблоны ответа AJAX
В идеале необходимо объявить переменную, в которой мы будем хранить номер страницы, и с помощью этого номера определять URL, на который мы будем отправлять запрос. В нашем демонстрационном примере у нас будут три таких страницы: 2.html, 3.html и пустая страница 4.html.
Когда вы нажимаете на кнопку загрузки следующей порции данных, проходит некоторое время от момента отправки запроса и получения ответа. В таком случае мы будем прятать кнопку загрузки, а вместо нее будем показывать некоторый текст, говорящий о том, что идет загрузка элементов:
1 2 |
$(buttonId).hide(); $(loadingId).show(); |
Добавляем полученные данные на страницу
Сначала вернем обратно те изменения, которые мы проделали, пока запрос еще выполнялся, то есть, показать кнопку “загрузить еще”, и спрятать информационный текст. Во-вторых, необходимо вставить полученные данные на страницу, после тех элементов, что уже есть на странице. Заметьте, что для упрощения в этом примере мы получаем данные HTML сразу, как результат запроса. Можно отсылать ответ в формате JSON, добавив в него дополнительные переменные, как статус или сообщение. Код ставки данных представлен ниже:
1 2 3 4 |
$(buttonId).show(); $(loadingId).hide(); $(response).appendTo($(container)); page += 1; |
Обрабатываем вариант, когда данные закончились
Как только вы достигнете последнего поста, вам нужно показать пользователю, что больше постов нет. Сделать это можно различными способами. Можно отсылать статус в виде встроенного в ответ кода или сообщения. Так как мы напрямую используем разметку HTML в этом примере, то пустой ответ в нашем случае будет говорить о том, что данные закончились.
1 2 3 4 5 6 7 8 9 10 11 12 13 |
$.ajax({ ... success: function(response) { // Действие при пустом ответе if (response.trim() == "") { $(buttonId).fadeOut(); $(loadingId).text("No more entries to load!"); return; } // Если ответ верный }, ... }); |
Заключение
В данном демонстрационном примере мы привели очень базовый вариант обработки ленивой загрузки. Конечно же, можно сделать гораздо лучше, если постараться. Для начала, можно вообще избавиться от кнопки, и отправлять запрос, когда пользователь прокрутит страницу до конца. Это избавит пользователя от дополнительной необходимости нажимать кнопку, и в целом ускоряет процесс просмотра информации. Во-вторых, можно просто отсылать чистые данные в формате JSON, а разметку создавать налету, используя jQuery, например:
1 2 3 4 5 6 |
$.each(response.items, function(index, value) { $("<div />", { "class" : "data-item", "text" : value }); }); |
И, наконец, ответ в JSON может содержать сообщение, говорящее, прошел ли запрос корректно; данные; а также информацию о том, есть ли еще посты для загрузки. В данном случае это более эффективный способ отправлять результат. When youre working on another persons idea, youre adopting it http://www.paper-writer.org