PassFront
  1. PassFront
  2. База знаний
  3. Асинхронность и Event Loop

Какие были проблемы с анимацией до requestAnimationFrame?

Асинхронность и Event Loop

До `requestAnimationFrame` анимации делали через `setTimeout`/`setInterval`, что вызывало проблемы: рассинхронизацию с частотой обновления экрана, дёрганость, лишнюю работу в фоновых вкладках и высокую нагрузку.

Проблемы анимаций через setTimeout/setInterval

Рассинхронизация с кадрами

setInterval(fn, 16) не синхронизирован с реальной перерисовкой браузера (~60 FPS). Кадры анимации могли не совпадать с обновлением экрана → дёрганость (jank), пропущенные или лишние кадры:

setInterval(() => {
  box.style.left = pos++ + 'px';
}, 16); // не синхронно с кадрами → рывки

Неточность таймеров

setTimeout/setInterval гарантируют минимум задержки, а не точное время. Накопление неточностей → неравномерная анимация.

Работа в фоновых вкладках

Таймеры продолжали работать в неактивных вкладках, тратя CPU и батарею на невидимую анимацию.

Отсутствие оптимизации

Браузер не мог оптимизировать анимацию (объединить с рендерингом, пропустить при перегрузке).

Как requestAnimationFrame решил

function animate(time) {
  box.style.transform = `translateX(${pos}px)`;
  requestAnimationFrame(animate);
}
requestAnimationFrame(animate);
  • Синхронизация с кадрами — вызывается перед перерисовкой (плавно).
  • Пауза в фоне — не выполняется в неактивной вкладке (экономия).
  • Адаптивная частота — под дисплей (в т. ч. 120 Гц).
  • Точное время в коллбэке (DOMHighResTimeStamp).

Коротко для собеседования

До requestAnimationFrame анимации на setTimeout/setInterval страдали: рассинхронизация с частотой экрана (дёрганость/jank), неточность таймеров, работа в фоновых вкладках (трата CPU/батареи), отсутствие оптимизации. requestAnimationFrame синхронизирует с кадрами (плавность), паузит в фоне и адаптируется к частоте дисплея.

Другие вопросы раздела