Мы хотим, чтобы наши посетители получали наш контент как можно быстрее, а это значит, что контент должен быть легким и с минимальным количеством запросов. Но мы хотим держать пользователей на наших страницах и развлекаться. Это где встраивание видео выходит на сцену.
Видеоролики иллюстрируют наш текстовый контент, оживляют его и часто обслуживаются третьей стороной. Что еще спросить? Ну, есть скрытый ценник: видео загружаются медленно и тяжело, даже если посетитель их не смотрит .
Одно простое видео на странице, вызываемое через безобидный iframe, может добавить до 6 HTTP-запросов и до 450 КБ контента. Решение, которое я предлагаю в этой статье, может уменьшить эти числа до 1 запроса и около 50 КБ на видео вместе с несколькими байтами JavaScript (поверх библиотеки jQuery, если вам не нравится ванильный вкус).
И знаешь, что? Это решение не ново. Ранее он был предложен Амитом Агарвалом в апреле 2013 года .
Итак, что за хитрость?
В решении Amit DOM анализируется с помощью JavaScript при загрузке документа, и каждый вызов видео YouTube (через специальный div, а не обычный iframe) заменяется предварительным просмотром эскиза, к которому прикрепляется iframe при нажатии на него.
Таким образом, мы получаем хороший эскиз предварительного просмотра, который по-прежнему обслуживается сторонним сервером, что составляет небольшую долю от веса всего проигрывателя видео. Видеоплеер загружается только тогда, когда видео действительно просматривается.
Моя маленькая добавленная стоимость
Я переписал код Amit на простом JavaScript и jQuery для тех, кто заинтересован. Я сохранил оригинальные комментарии в коде, чтобы сделать его максимально понятным. Моя версия добавляет новую функцию в параметр данных HTML5, которая позволяет добавлять любой параметр в URL-адрес YouTube для настройки видео.
YouTube предлагает список параметров для отображения и скрытия элементов управления, маркировки и информации, а также для настройки качества видео или начального кадра вашего видео (среди прочего).
- Средства управления : установите это в 0, и средства управления слоем не отображаются на видео проигрывателе.
- modestbranding : установите для этого параметра значение 1, и логотип YouTube исчезнет с панели управления.
- rel : установите это значение в 0, и никакие связанные видео не будут показаны, когда закончится воспроизведение исходного видео.
- showinfo : установите для этого параметра значение 0, и проигрыватель не будет отображать информацию, такую как название видео и загрузчик, до начала воспроизведения видео.
- start : установите это значение в секундах, и проигрыватель начнет воспроизведение видео с этого времени (точнее, с ближайшего ключевого кадра).
- vq : установите желаемое качество видео, если оно поддерживается (например,
hd720
При добавлении iframe YouTube в событие click некоторым параметрам присваиваются значения, а именно autoplay
autohide
Поддерживаемые эскизы YouTube
Каждое видео на YouTube содержит список сгенерированных изображений. Вы можете получить к ним доступ через URL-адрес http://img.youtube.com/vi/<youtube-video-id>/<youtube-thumbnail>
img.youtube.com
i.ytimg.com
Те, которые нас интересуют:
- default.jpg (версия по умолчанию, 120px x 90px)
- hqdefault.jpg (высококачественная версия, 480px × 360px)
- mqdefault.jpg (версия среднего качества, 320 × 180 пикселей)
- sddefault.jpg (стандартная версия, 640 × 480 пикселей)
- maxresdefault.jpg (версия с максимальным разрешением, 1.280px × 720px)
В качестве примера, посмотрите этот URL , который вы можете использовать, чтобы поиграть со значениями, чтобы увидеть различные параметры изображения.
В следующем коде мы используем миниатюру sddefault.jpg. В зависимости от ваших потребностей и возможностей экрана пользователя его можно заменить любым из перечисленных поддерживаемых форматов.
HTML
HTML-код устанавливает идентификатор видео YouTube, определяет размер видео (ширину и высоту) и перечисляет параметры URL-адреса YouTube, если это необходимо.
<div class="youtube"
id="fsrJWUVoXeM"
style="width: 500px; height: 281px;">
</div>
<div class="youtube"
id="lR4tJr7sMPM"
data-params="modestbranding=1&showinfo=0&controls=0&vq=hd720"
style="width: 640px; height: 360px;">
</div>
CSS
В двух видео, использованных в качестве примеров, соотношение сторон составляет 16: 9, что возвращает миниатюру sddefault.jpg с горизонтальными черными полосами. Чтобы скрыть их при отображении этого эскиза, свойство background-position
center
div
style="width:500px;height:281px;"
, Таким образом, на одной странице можно показывать видео разных размеров.
Значок воспроизведения, который сообщает пользователям, что содержимое не является простым изображением, добавляется в слой поверх миниатюры с переходом непрозрачности, чтобы выделить его. Здесь мы используем png с кодировкой URI данных base64 (из IconFinder ), который сохраняет HTTP-запрос и работает до IE8.
.youtube {
background-position: center;
background-repeat: no-repeat;
position: relative;
display: inline-block;
overflow: hidden;
transition: all 200ms ease-out;
cursor: pointer;
}
.youtube .play {
background: url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEAAAABACAYAAACqaXHeAAAERklEQVR4nOWbTWhcVRTHb1IJVoxGtNCNdal2JYJReC6GWuO83PM/59yUS3FRFARdFlwYP1CfiojQWt36sRCUurRIdVFXIn41lAoVdRGrG1M01YpKrWjiYmaSl8ybZJL3cd+YA//NLObd3++eO8x79z5jSq5Gw+8kov0AP8vMR5l1BtBZQM4B8ks75wCdZdYZZj5qLZ4hov2Nht9Z9vhKKSIaB/gI4M4w62KeAO6Mte4lYOq20FxrlqqOibhHmeWbvNC9ZfDX1mLae391aN6limO/gwgvAPJbWeAZuSDingdwXTBw7/0IsyaA/Fkh+KqOkD+YNfHej1QKD+y7iVlOhgLvFqFfNJvNGyuBJ+KDAF8MDd0tgS8y64OlgSdJMsysL4cG7SOHkyQZLhTee7+d2R2rAVy/S+Jd7/32ouBHAP4gNNRGQyTHc/84NhqNywZp5rvjjnnvt21aABFeCQ+RLwAf2hQ8s7sv9OCLk6AHNgQvIrvbfzKCD76g/O6cu7lf/iER/aQGgy448pExZmhdegAPhR9sObFWH1gT3lp7DaA/5bkIgJhZPgsNmz02novj+KqeApj1ubwXWe4kdyeznAgNvTpE/HQmvKqOMeuFogTUVQSRno+iaLRLAJF7uIgL9O4ubgL8aWgB7S44mNX+35YpICUiAvS9sBLkq1WzT+NFffl6AuoiApi6NT37h6sWkBIRZGkQ8YtLgyji6e1mBYTqCEBPG2Naz+0BWQgtoGoRgCzEsd9hAN1X5BfnFZASUfrSAFQNsyZ1FJASUVpHiLinDJG8U2cBZYogkrcNs5waBAGdstbeU9zdqpw0gPwwSAI6VUxHyFlDpOcHUUBBIuYNs14aZAE5RVwyzPr3/0EAEY0TyfGNjBWQvwZ +CTSbehfAH29mrID8bET0+0EUkAd8WYDOmqJ3ecsG30yr9wqRfm6Y+a1BEFDEjHfHvWmY9ck6CygHvBVr8Xhtb4ZE5HZA3y8DvBNA1TjnrmXWf+sioMwZX5V/VHXMGGMMoKdDCxCRvRWBdzKzdHEO+EisilbPyopHYqp6S9UCAsz4iojI7hUDAtyXVQgIDd6KnOoaWNkbI6FaPSuZGyMArsi7MZoloB4zviI/Nhr3X95jltwTRQmoIfgisy5ai+me67OI7fE4nrqjrqfK1t0eby0FPRB6oGVlchL3rgnfrq19RKbVBdhV9IOSwJmfmJi4vi/4ThERitwyCxVAFqydshuCX5awhQ9KtmuIWd8IDZED/nXT77rvVVv6sHRKwjYi91poqP7Dr+Y6JJ1VSZIMA3wkPNy6bX+o8Bcm0sXMdwM8Fxo0A3xORPaWBp6uPXsmbxCRD0NDL0dOANhVCXy6iAjMcjbcrMt3RITKwdMVRdFo+y5yvkL4eWZ+zHt/ZVD4dEVRNGotpst+dZZZH8k86lqn2pIvT/eqrNfn2xuyqYPZ8mv7s8pfn/8Pybm4TIjanscAAAAASUVORK5CYII=") no-repeat center center;
background-size: 64px 64px;
position: absolute;
height: 100%;
width: 100%;
opacity: .8;
filter: alpha(opacity=80);
transition: all 0.2s ease-out;
}
.youtube .play:hover {
opacity: 1;
filter: alpha(opacity=100);
}
Реализация JavaScript в ванили
Без зависимостей и самой быстрой реализации, версия Vanilla JavaScript использует самый маленький готовый код DOM, который я смог найти.
Различия в браузерах по-прежнему необходимо учитывать, например, отсутствие поддержки метода getElementsByClassName
'use strict';
function r(f){/in/.test(document.readyState)?setTimeout('r('+f+')',9):f()}
r(function(){
if (!document.getElementsByClassName) {
// IE8 support
var getElementsByClassName = function(node, classname) {
var a = [];
var re = new RegExp('(^| )'+classname+'( |$)');
var els = node.getElementsByTagName("*");
for(var i=0,j=els.length; i<j; i++)
if(re.test(els[i].className))a.push(els[i]);
return a;
}
var videos = getElementsByClassName(document.body,"youtube");
} else {
var videos = document.getElementsByClassName("youtube");
}
var nb_videos = videos.length;
for (var i=0; i<nb_videos; i++) {
// Based on the YouTube ID, we can easily find the thumbnail image
videos[i].style.backgroundImage = 'url(http://i.ytimg.com/vi/' + videos[i].id + '/sddefault.jpg)';
// Overlay the Play icon to make it look like a video player
var play = document.createElement("div");
play.setAttribute("class","play");
videos[i].appendChild(play);
videos[i].onclick = function() {
// Create an iFrame with autoplay set to true
var iframe = document.createElement("iframe");
var iframe_url = "https://www.youtube.com/embed/" + this.id + "?autoplay=1&autohide=1";
if (this.getAttribute("data-params")) iframe_url+='&'+this.getAttribute("data-params");
iframe.setAttribute("src",iframe_url);
iframe.setAttribute("frameborder",'0');
// The height and width of the iFrame should be the same as parent
iframe.style.width = this.style.width;
iframe.style.height = this.style.height;
// Replace the YouTube thumbnail with YouTube Player
this.parentNode.replaceChild(iframe, this);
}
}
});
А вот демонстрация кода в действии:
Реализация jQuery
Будучи более выразительным на мой взгляд и с более широкой поддержкой браузера, реализация jQuery идет с ценой всей библиотеки jQuery и немного более медленной производительностью.
"use strict";
$(function() {
$(".youtube").each(function() {
// Based on the YouTube ID, we can easily find the thumbnail image
$(this).css('background-image', 'url(http://i.ytimg.com/vi/' + this.id + '/sddefault.jpg)');
// Overlay the Play icon to make it look like a video player
$(this).append($('<div/>', {'class': 'play'}));
$(document).delegate('#'+this.id, 'click', function() {
// Create an iFrame with autoplay set to true
var iframe_url = "https://www.youtube.com/embed/" + this.id + "?autoplay=1&autohide=1";
if ($(this).data('params')) iframe_url+='&'+$(this).data('params');
// The height and width of the iFrame should be the same as parent
var iframe = $('<iframe/>', {'frameborder': '0', 'src': iframe_url, 'width': $(this).width(), 'height': $(this).height() })
// Replace the YouTube thumbnail with YouTube HTML5 Player
$(this).replaceWith(iframe);
});
});
});
А вот демоверсия версии jQuery:
Окончательные результаты
Теперь давайте поговорим о том, что мы получаем в реальных ситуациях.
Это решение было реализовано на этой странице , которая представляет собой статью, которая содержит 3 встроенных видео YouTube. Вот результаты:
- Перед внедрением этого решения у нас было 20 HTTP-запросов и 636,2 Кбайт загруженного контента, что заняло 2,22 с (3,59 с при загрузке).
- После реализации мы сократили до 17 запросов, 370,7 КБ и 1,05 с (нагрузка: 733 мс).
- Это означает на 15% меньше запросов и веб-страницу, которая на 41% легче и на 52% быстрее (загрузка: на 80% быстрее).
Результаты довольно хорошие, даже с одним встроенным видео на YouTube, как на следующей странице , которая является нашим следующим примером. Вот результаты для страницы с одним видео:
- Перед внедрением решения у нас было 20 HTTP-запросов и 684,4 Кбайт загруженного контента, что заняло 2,13 с (загрузка 2,14 с).
- После реализации мы сократили до 17 запросов, 322,4 КБ и 1,24 с (нагрузка: 975 мс).
- Это означает, что мы получили на 15% меньше запросов и веб-страницу на 53% легче и на 42% быстрее (загрузка: на 54% быстрее).
Вывод
В заключение, я думаю, что мы все можем согласиться с тем, что сокращение веса страницы с 40 до 50% стоит того небольшого куска кода, не правда ли?
Если у вас есть какие-либо мысли по поводу кода или вы хотите улучшить его, не стесняйтесь раскошелиться на CodePen или поделиться своими взглядами в комментариях.
Эта статья также доступна на французском , испанском и португальском языках .