Задача, которая описана ниже, демонстрирует результативный метод оптимизации страницы.
С целью экономии трафика и более быстрой загрузки страницы, изображения на ней заменяются на «макеты».
Вместо такого изображения:
<img src="yozhik.jpg" width="128" height="128">
Стоит вот такое:
<img *!*src="1.gif"*/!* width="128" height="128" *!*realsrc="yozhik.jpg"*/!*>
То есть, настоящий URL находится в атрибуте realsrc (название атрибута можно выбрать любое). А в src поставлен серый GIF размера 1x1, и так как width/height правильные, то он растягивается, так что вместо изображения виден серый прямоугольник.
При этом, чтобы браузер загрузил изображение, нужно заменить значение src на то, которое находится в realsrc.
Если страница большая, то замена больших изображений на такие макеты существенно убыстряет полную загрузку страницы. Это особенно заметно в случае, когда на странице много анонсов новостей с картинками или изображений товаров, из которых многие находятся за пределами прокрутки.
Кроме того, для мобильных устройств JavaScript может подставлять URL уменьшенного варианта картинки.
Напишите код, который при прокрутке окна загружает ставшие видимыми изображения. То есть, как только изображение попало в видимую часть документа — в src нужно прописать правильный URL из realsrc.
Работать должно так: открыть работающую страницу в новом окне.
- При начальной загрузке часть изображений становятся видимыми сразу, до прокрутки. Код должен это учитывать.
- Часть изображений могут быть изначально обычными, без
realsrc. Их код не должен трогать вообще. - Также код не должен перегружать уже показанное изображение.
Дополнительно: расширьте код, чтобы загружались изображения не только видимые сейчас, но и на страницу вперед и назад от текущего места.
Исходный документ с макетами и изображениями: tutorial/browser/dom/lazyimg-src/index.html.
P.S. Вам понадобится функция определения координат элемента. Она называется getOffsetRect и возвращает координаты верхнего-левого угла. Находится в исходном документе выше в файле lib.js.
P.P.S. Страница прокручивается только вверх или вниз, горизонтальной прокрутки нет.
Функция должна по текущей прокрутке определять, какие изображения видимы, и загружать их.
Она должна срабатывать не только при прокрутке, но и при загрузке. Вполне достаточно для этого — указать ее вызов в скрипте под страницей, вот так:
... страница ...
function showVisible() {
var imgs = document.getElementsByTagName('img');
for(var i=0; i<imgs.length; i++) {
var img = imgs[i];
var realsrc = img.getAttribute('realsrc');
if (!realsrc) continue;
if (*!*isVisible(img)*/!*) {
img.src = realsrc;
img.setAttribute('realsrc', '');
}
}
}
*!*
showVisible();
window.onscroll = showVisible;
*/!*
При запуске функция ищет все видимые картинки с realsrc и перемещает значение realsrc в src. Обратите внимание, т.к. атрибут realsrc нестандартный, то для доступа к нему мы используем get/setAttribute. А src — стандартный, поэтому можно обратиться по DOM-свойству.
Функция проверки видимости isVisible(elem) получает координаты текущей видимой области и сравнивает их с элементом.
Для видимости достаточно, чтобы координаты верхней(или нижней) границы элемента находились между границами видимой области.
Как получить метрики элемента и страницы, описано в статье Размеры и прокрутка элементов.
Итоговая функция:
function isVisible(elem) {
var coords = getOffsetRect(elem);
var windowTop = window.pageYOffset ||
document.documentElement.scrollTop;
var windowBottom = windowTop +
document.documentElement.clientHeight;
coords.bottom = coords.top + elem.offsetHeight;
// верхняя граница elem в пределах видимости
// ИЛИ нижняя граница видима
var topVisible = coords.top > windowTop
&& coords.top < windowBottom;
var bottomVisible = coords.bottom < windowBottom
&& coords.bottom > windowTop;
return topVisible || bottomVisible;
}
В решении также указан вариант с isVisible, который расширяет область видимости на +-1 страницу (высота страницы — document.documentElement.clientHeight).
Решение: tutorial/browser/dom/lazyimg/index.html.