От автора: свойства CSS и значения, запускающие перестройку, довольно сильно влияют на производительность. Они могут замедлить адаптивность интерфейсов (рендеринг страницы, плавность анимации и производительность во время прокрутки страницы). Спад особенно заметен на слабых устройствах типа смартфонов и смарт тв.
Что такое перестройка?
Перестройка – это операция изменения макета всей страницы или ее части. В качестве примеров можно привести изменение размеров элемента или обновление его левого позиционирования. Перестройка происходит потому, что такие элементы вынуждают браузер заново вычислять высоту, ширину и положение других элементов в документе.
Перерисовка похожа на перестройку, эта операция вынуждает браузер заново рендерить части документа. Один из примеров перерисовки – изменение цвета кнопки по состоянию :hover. С перерисовкой возникает меньше проблем, так как она не влияет на размеры и положение узлов. И все же перерисовку нужно сводить к минимуму.
Перестройка и перерисовка по большей части вызываются во время операций в DOM. Например, при добавлении и удалении элементов. Эти процессы также могут быть вызваны изменением свойств, отвечающих за размеры, видимость и положение элемента. Оба процесса срабатывают как при использовании JS, так и при использовании CSS-анимации.
Заметка: загрузка страниц
Загрузка страницы всегда вызывает перестройку и перерисовку, так как браузер парсит исходный HTML, CSS и JS.
Полностью исключить перестройки и перерисовки из проекта сложно. Однако мы можем находить эти процессы и снижать их влияние с помощью инструмента временной шкалы.
Инструменты временной шкалы
На первый взгляд инструменты временной шкалы немного запутаны. Они измеряют производительность front-end’а, показывая время, необходимое на выполнение различных задач. Записывая все во время взаимодействия со страницами, мы можем найти строки в CSS, вызывающие спад производительности.
Временная шкала находится в одноименной вкладке в панели разработчика. В Chrome, Opera и Firefox вкладка называется Timeline. В Safari вкладка называется Timelines, в IE более полное название UI Responsiveness.
Для записи процесса в любом браузере нажмите на кнопку Запись. Взаимодействуйте с проблемными частями страницы, после чего нажмите на соответствующую кнопку для остановки записи.
В зависимости от браузера данные будут видны сразу во время записи или после ее окончания. Safari и Firefox показывают данные в реальном времени, а Chrome, Opera и Internet Explorer показывают график производительности только после окончания записи.
Загрузка документа, вызовы функций, события DOM, перерасчет стилей и отрисовка, все эти данные логируются в любом браузере. По этой информации мы можем найти узкие места в производительности. Относительно производительности CSS мы ищем два связанных аспекта:
большое количество операций по перерасчету и отрисовке стилей;
операции, занимающие много времени, которые на временной шкале отображаются более длинным блоком.
Для разбора на практике мы сравним два стандартных документа: пример А и В. В обоих случаях будем двигать несколько div’ов из Х-положения (0) в Х-положение (1000). В обоих примерах будут использоваться CSS-переходы. В примере А мы будем анимировать свойство left. В примере В мы будем анимировать свойство transform с помощью трансформаций.
Разметка в обоих примерах одинаковая (результат можно посмотреть на Рисунке 3.16):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
<!DOCTYPE html> <html lang="en-US"> <head> <meta charset="utf-8"> <title>Performance example</title> <style type="text/css" > /* CSS will go here. */ </style> </head> <body> <button type="button" id="move">Move</button> <div></div> <div></div> <div></div> <div></div> <div></div> <div></div> <div></div> <div></div> <div></div> <div></div> <script type="text/javascript" src="toggle-move-class.js"> ↵</script> </body> </html> |
Рисунок 3.16 наша HTML-страница с div’ами в Safari
JS-код для обоих документов также один и тот же. По нажатию на кнопку move ко всем div’ав добавляется класс moved:
1 2 3 4 5 6 7 |
var move = document.getElementsById('move'); move.addEventListener('click', function(e) { var objs = document.body.querySelectorAll('div'); Array.prototype.map.call(objs, function(o){ o.classList.toggle('moved'); }); }); |
CSS-код, вот тут начинаются расхождения. CSS для примера А:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
div { background: #36f; margin-bottom: 1em; width: 30px; height: 30px; position: relative; left: 0; transition: left 2s ease-in; } .moved { left: 1000px; } |
Во время выполнения эта анимация генерирует большое количество вычислений стилей и перерисовок на временной линии. Изображение ниже показывает временную линию для переходов в Safari (Рисунок 3.17), Chrome (Рисунок 3.18), Internet Explorer (Рисунок 3.19) и Firefox (Рисунок 3.20).
Рисунок 3.17 временная линия в Safari для перехода свойства left
Рисунок 3.18 то же самое в Chrome
Рисунок 3.19 временная линия в IE11 для перехода свойства left
Рисунок 3.20 пример в Firefox
Причина вычислений и перерисовок стилей связана с используемым свойством left. Свойство left вызывает перестройку при любых изменениях, даже если изменения вызваны анимацией или переходом.
Теперь посмотрим на пример В:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
div { background: #f3f; margin-bottom: 1em; width: 30px; height: 30px; position: relative; left: 0; transition: transform 2s ease-in; transform: translateX(0); } .moved { transform: translateX(1000px); } |
Здесь мы используем свойство transform между translateX(0) и translateX(1000px).
В большинстве браузеров трансформации не вызывают перестройки, на временной линии заметно лишь несколько операций по перерисовке. Результаты в Safari (Рисунок 3.21), Chrome (Рисунок 3.22) и IE (Рисунок 3.23). Firefox является исключением. Сравните Рисунок 3.20 и 3.24. Временная линия для свойства left и трансформаций очень похожа.
Рисунок 3.21 временная линия в Safari для перехода –webkit-transform
Рисунок 3.22 то же самое в Chrome, в этот раз со свойством transform
Рисунок 3.23 пример в IE11
Рисунок 3.24 временная линия в Firefox для перехода свойства transform
Определение строк, которые нужно удалить
К сожалению, нет четкого списка свойств, вызывающих перестройку и перерисовку. Paul Lewis подошел к этому ближе всех на своем сайте CSS Triggers, но список заточен под Chrome. Для многих свойств браузеры ведут себя одинаково, однако этот ресурс дает вам хотя бы малейшее представление о том, какие свойства вызывают проблемы.
Вы нашли проблемные свойства, теперь нужно проверить свои предположения. Отключите свойство (закомментируйте или добавьте временный префикс x-) и перезапустите тест на временной линии.
Помните, что производительность относительна, а не абсолютна или совершенна. Цель – повысить ее, чтобы сайт работал быстрее, чем раньше. Если свойство или эффект слишком медленно выполняются, удалите его.
Автор: Tiffany Brown
Источник: //www.sitepoint.com/
Редакция: Команда webformyself.