Управление загрузкой изображений

в 8:08, , рубрики: веб-дизайн, Веб-разработка, высокая производительность, производительность
Управление загрузкой изображений

Быстрая и плавная загрузка изображений — это одна из немаловажных составляющих хорошего веб-интерфейса. Кроме того, появляется все больше сайтов, использующие крупные фотографии в дизайне, таким проектам особенно важно следить за корректной загрузкой графики. В этой статье описано несколько техник, которые помогут контролировать загрузку изображений.

Использование контейнера для каждого изображения

Простой способ, который можно применить к любому изображению на сайте. Заключается в том, что каждая картинка оборачивается в DIV, который предотвращает построчную загрузку:

<div class="img_wrapper">
    <img src="comicbookguy.jpg" alt=""/>
</div>

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

Например, чтобы задать соотношение сторон 4:3, можно использовать следующий CSS:

.img_wrapper{
    position: relative;
    padding-top: 75%;
    overflow: hidden;
}
 
.img_wrapper img{
    position: absolute;
    top: 0;
    width: 100%;
    opacity: 0;
}

Для того, чтобы изображение отображалось в браузере только после полной подгрузки, необходимо добавить событие onload для изображения и использовать JavaScript, который будет обрабатывать событие:

<div>
    <img src="comicbookguy.jpg" alt="" onload="imgLoaded(this)"/>
</div>

function imgLoaded(img){
    var $img = $(img);
 
    $img.parent().addClass('loaded');
};

Код функции внутри тега HEAD должен быть расположен в самом конце, после любого jQuery или другого плагина. После полной подгрузки изображения его необходимо показать на странице:

.img_wrapper.loaded img{
    opacity: 1;
}

Для эффекта плавного появления картинки можно использовать CSS3 transition:

.img_wrapper img{
    position: absolute;
    top: 0;
    width: 100%;
    opacity: 0;
 
    -webkit-transition: opacity 150ms;
    -moz-transition: opacity 150ms;
    -ms-transition: opacity 150ms;
    transition: opacity 150ms;
}

Живой пример этого способа можно посмотреть на Codepen.

Использование контейнера для множества изображений

Предыдущий способ хорошо подходит для отдельных изображений, а что если на странице их много, например галерея фотографий или слайдер? Подгружать сразу все нецелесообразно — картинки могут много весить. Для решения этой проблемы можно заставить JavaScript'ом загружать только нужные в данный момент времени изображения. Пример HTML-разметки для слайдшоу:

<div id="Slideshow">
    <img src="slide_1.jpg" alt="" onload="slideLoaded(this)" />
    <img src="slide_2.jpg" alt="" onload="slideLoaded(this)" />
    <img src="slide_3.jpg" alt="" onload="slideLoaded(this)" />
</div>

Используем функцию slideLoaded(), чтобы контролировать процесс:

function slideLoaded(img){
    var $img = $(img),
        $slideWrapper = $img.parent(),
        total = $slideWrapper.find('img').length,
        percentLoaded = null;
 
    $img.addClass('loaded');
 
    var loaded = $slideWrapper.find('.loaded').length;
 
    if(loaded == total){
        percentLoaded = 100;
        // INSTANTIATE PLUGIN
        $slideWrapper.easyFader();
    } else {
        // TRACK PROGRESS
        percentLoaded = loaded/total * 100;
    };
};

Подгруженным изображениям присваивается класс loaded, а также отображается общий прогресс. И снова, JavaScript должен быть помещен в конец тега HEAD, после всего остального.

Кэширование

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

<script>
    var heroArray = [
        '/uploads/hero_about.jpg',
        '/uploads/hero_history.jpg',
        '/uploads/hero_contact.jpg',
        '/uploads/hero_services.jpg'
    ]
</script>

Когда посетитель заходит на сайт, после загрузки главной страницы, начинают загружаться изображения в кэш. Для того, чтобы кэширование не мешало отображению текущего контента, необходимо функционал JavaScript добавить в событие window load:

function preCacheHeros(){
    $.each(heroArray, function(){
        var img = new Image();
        img.src = this;
    });
};
 
$(window).load(function(){
    preCacheHeros();
});

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

Загрузка по событию

способ заключается в том, что изображения начинают подгружаться после определенного события. Это увеличивает производительность и экономит трафик пользователя. HTML-разметка:

<div class="img_wrapper lazy_load">
    <img
        src="data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7"
        data-src="comicbookguy.jpg"
        alt="Comic Book Guy"
    />
</div>

Стоит заметить, что URL изображение задано в data-src, а не в src. Это необходимо, чтобы браузер не загружал картинку сразу. Вместо этого в src загружается прозрачный пиксель в GIF, заданный в base64, что уменьшает количество обращений к серверу.

Остается только при нужном событии изменить значение src на data-src. JavaScript позволяет загружать изображения постепенно:

function lazyLoad(){
    var $images = $('.lazy_load');
 
    $images.each(function(){
        var $img = $(this),
            src = $img.attr('data-src');
 
        $img
            .on('load',imgLoaded($img[0]))
            .attr('src',src);
    });
};
 
$(window).load(function(){
    lazyLoad();
};

Заключение

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

Автор: grokru

Источник

* - обязательные к заполнению поля


https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js