← Назад к вопросам

Как Event Loop работает с рендерингом?

2.3 Middle🔥 261 комментариев
#JavaScript Core

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI2 апр. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Event Loop и рендеринг

Рендеринг в браузере привязан к Event Loop, но не является частью JavaScript. Это критически важное понимание для оптимизации производительности фронтенд-приложений.

Цикл Event Loop с рендерингом

Полный цикл выглядит так:

  1. Выполнить один Macrotask (или несколько Microtasks)
  2. Выполнить ВСЕ Microtasks
  3. Проверить, нужен ли рендеринг
  4. Если нужен:
    • Запустить requestAnimationFrame callbacks
    • Обновить DOM (layout, paint, composite)
  5. Если остаток времени до следующего кадра:
    • Выполнить следующий Macrotask
  6. Повторить

Временная шкала кадра (Frame Time)

В современных браузерах целевая частота кадров 60fps, то есть один кадр должен быть готов за ~16.67мс.

Идеальный сценарий:

  • 0ms: Macrotask (выполняется код)
  • 6ms: Microtasks (промисы, мутации)
  • 8ms: rAF callbacks (анимации)
  • 10ms: Рендеринг (layout, paint)
  • 16.67ms: Кадр отправлен на экран

Когда срабатывает рендеринг

Браузер проверяет рендеринг только после Macrotask + Microtasks. Если код достаточно быстрый, рендеринг может не произойти в текущем цикле.

setTimeout(() => {
  element.style.backgroundColor = 'red';
}, 0);

for (let i = 0; i < 1000; i++) {
  element.style.transform = `translateX(${i}px)`;
}

RequestAnimationFrame vs setTimeout

requestAnimationFrame (rAF) синхронизируется с рендерингом браузера:

function animate() {
  element.style.left = x + 'px';
  requestAnimationFrame(animate);
}
animate();

rAF вызывается перед рендерингом, a setTimeout — это Macrotask, может быть выполнен раньше или позже.

Практический пример: Force Layout

for (let i = 0; i < 100; i++) {
  element.style.width = (i * 10) + 'px';
  console.log(element.offsetWidth);
}

Paint/Layout/Composite

Браузер выполняет три этапа рендеринга:

  1. Layout (Reflow) — пересчёт размеров и позиций
  2. Paint (Repaint) — отрисовка пикселей
  3. Composite — объединение слоёв (самый быстрый)
element.style.transform = 'translateX(100px)';
element.style.left = '100px';

Ключевой вывод

Рендеринг — это независимый процесс браузера, синхронизированный с его частотой обновления (~60fps). Код JavaScript блокирует рендеринг, пока выполняется, поэтому долгие операции нужно разбивать на части, а для анимаций использовать requestAnimationFrame вместо setTimeout.