XHR в body. Динамические стили: быстро и просто. Оптимизация структуры веб-страниц
XHR в body
XHR в head
Быстрый XHR в head
DOM-метод
Результаты
Выводы
Выполняется XMLHttpRequest к CSS-файлу, затем содержимое последнего вставляется через innerHTML в body документа. Случай был выбран просто как базовый, потому что большое число узлов в DOM-дереве делает такую операцию сразу менее эффективной, чем вставка в head. Да и стили внутри тела документа запрещены стандартами.
// чтобы не копировать всем известный код, запишем так
var xhr = new XMLHttpRequest;
if (xhr) {
xhr.onreadystatechange = function() {
try {
if (xhr.readyState == 4) {
if (xhr.status == 200) {
// вставим полученные данные прямо в body
document.body.innerHTML +=
'<style type="text/css">' + xhr.responseText + '</style>';
}
}
} catch(e){}
};
xhr.open("GET", 'styles.css?'+Math.random(), true);
xhr.send(null);
}
Тут сразу встает вопрос: как считать применение стилей? Ведь у браузера нет такого события. Немного подумаем и вспомним всем известный и раскритикованный подход с использованием offsetHeight. Он, конечно, будет не самым лучшим выбором, так как добавляет небольшую задержку (пропорциональную числу узлов), но это будет допустимо в рамках выборанного метода (число узлов постоянно для всех измерений).
Итак, для снятия времени применения CSS-правил использовалась следующая конструкция (которая запускалась сразу после обращения к внешнему файлу):
var start = new Date();
var _timer = setInterval(function(){
// находим известный элемент документа и проверяем,
// применились ли к нему стили
if (document.getElementById('neck').offsetHeight < 300) {
// сообщаем о применении
alert('CSS files loaded in '+(new Date() - start));
// убиваем таймер
clearInterval(_timer);
}
}, 10);
Конечно, на время загрузки влияют сетевые задержки. Для борьбы с ними (и не только) бралась серия из 15 замеров, и значения, превосходящие текущее среднее более чем в 2 раза, просто отбрасывались (для контроля 3-дельта выбросов).
Все результаты приведены в конце раздела.