Прежде чем браузер сможет отобразить страницу, ему необходимо построить деревья DOM и CSSOM. В результате нам необходимо обеспечить как можно более быструю доставку HTML и CSS в браузер.
Краткое содержание
- Байты → символы → токены → узлы → объектная модель.
- HTML-разметка преобразуется в объектную модель документа (DOM); Разметка CSS преобразуется в объектную модель CSS (CSSOM).
- DOM и CSSOM — независимые структуры данных.
- Панель Chrome DevTools Performance позволяет нам фиксировать и проверять затраты на создание и обработку DOM и CSSOM.
Объектная модель документа (DOM)
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width,initial-scale=1" />
<link href="style.css" rel="stylesheet" />
<title>Critical Path</title>
</head>
<body>
<p>Hello <span>web performance</span> students!</p>
<div><img src="awesome-photo.jpg" /></div>
</body>
</html>
Начнем с самого простого случая: простая HTML-страница с текстом и одним изображением. Как браузер обрабатывает эту страницу?
- Преобразование: браузер считывает необработанные байты HTML с диска или из сети и преобразует их в отдельные символы на основе указанной кодировки файла (например, UTF-8).
- Токенизация: браузер преобразует строки символов в отдельные токены — как указано в стандарте W3C HTML5 , например «<html>», «<body>» — и другие строки в угловых скобках. Каждый токен имеет особое значение и свой набор правил.
- Лексирование: выпущенные токены преобразуются в «объекты», которые определяют их свойства и правила.
- Конструкция DOM: Наконец, поскольку разметка HTML определяет отношения между различными тегами (некоторые теги содержатся в других тегах), созданные объекты связываются в древовидную структуру данных, которая также фиксирует отношения родитель-потомок, определенные в исходной разметке: объект HTML . является родительским элементом объекта body , тело является родительским элементом объекта абзаца и т. д.
Конечным результатом всего этого процесса является объектная модель документа (DOM) нашей простой страницы, которую браузер использует для всей дальнейшей обработки страницы.
Каждый раз, когда браузер обрабатывает HTML-разметку, он выполняет все описанные выше шаги: преобразует байты в символы, идентифицирует токены, преобразует токены в узлы и строит дерево DOM. Весь этот процесс может занять некоторое время, особенно если нам нужно обработать большой объем HTML.
Если вы откроете Chrome DevTools и запишите временную шкалу во время загрузки страницы, вы увидите фактическое время, затраченное на выполнение этого шага — в приведенном выше примере нам потребовалось ~5 мс, чтобы преобразовать фрагмент HTML в дерево DOM. Для страницы большего размера этот процесс может занять значительно больше времени. При создании плавной анимации это может легко стать узким местом, если браузеру приходится обрабатывать большие объемы HTML.
Дерево DOM фиксирует свойства и взаимосвязи разметки документа, но не говорит нам, как элемент будет выглядеть при визуализации. Это ответственность CSSOM.
Объектная модель CSS (CSSOM)
Пока браузер создавал DOM нашей простой страницы, он обнаружил тег ссылки в разделе заголовка документа, ссылающийся на внешнюю таблицу стилей CSS: style.css
. Предвидя, что ему понадобится этот ресурс для отображения страницы, он немедленно отправляет запрос на этот ресурс, который возвращается со следующим содержимым:
body {
font-size: 16px;
}
p {
font-weight: bold;
}
span {
color: red;
}
p span {
display: none;
}
img {
float: right;
}
Мы могли бы объявить наши стили непосредственно в разметке HTML (встроенными), но сохранение независимости CSS от HTML позволяет нам рассматривать контент и дизайн как отдельные задачи: дизайнеры могут работать с CSS, разработчики могут сосредоточиться на HTML и так далее.
Как и в случае с HTML, нам необходимо преобразовать полученные правила CSS во что-то, что браузер сможет понять и с чем сможет работать. Следовательно, мы повторяем процесс HTML, но для CSS вместо HTML:
Байты CSS преобразуются в символы, затем в токены, затем в узлы и, наконец, связываются в древовидную структуру, известную как «Объектная модель CSS» (CSSOM):
Почему CSSOM имеет древовидную структуру? При вычислении окончательного набора стилей для любого объекта на странице браузер начинает с самого общего правила, применимого к этому узлу (например, если он является дочерним элементом элемента body, то применяются все стили тела), а затем рекурсивно уточняет. вычисляемые стили путем применения более конкретных правил; то есть правила «нисходят каскадом».
Чтобы сделать это более конкретным, рассмотрим дерево CSSOM выше. Любой текст, содержащийся в теге <span>
, который размещен внутри элемента body, имеет размер шрифта 16 пикселей и имеет красный текст — директива font-size
каскадно распространяется от body
к span
. Однако если тег span
является дочерним по отношению к тегу абзаца ( p
), его содержимое не отображается.
Также обратите внимание, что приведенное выше дерево не является полным деревом CSSOM и показывает только те стили, которые мы решили переопределить в нашей таблице стилей. Каждый браузер предоставляет набор стилей по умолчанию, также известный как «стили пользовательского агента» — это то, что мы видим, когда не предоставляем никаких собственных стилей, — и наши стили просто переопределяют эти значения по умолчанию.
Чтобы узнать, сколько времени занимает обработка CSS, вы можете записать временную шкалу в DevTools и найти событие «Пересчитать стиль»: в отличие от анализа DOM, временная шкала не показывает отдельную запись «Разобрать CSS», а вместо этого фиксирует синтаксический анализ и дерево CSSOM. построение плюс рекурсивный расчет вычисляемых стилей в рамках этого одного события.
Наша тривиальная таблица стилей обрабатывается примерно за 0,6 мс и влияет на восемь элементов на странице — немного, но опять же, не бесплатно. Однако откуда взялись восемь элементов? CSSOM и DOM — независимые структуры данных! Оказывается, браузер скрывает важный шаг. Далее давайте поговорим о дереве рендеринга , которое связывает DOM и CSSOM вместе.