28 января 2025 г. (изменено: 28 января 2025 г.)

Канал: @cherkashindev

1 893

ViewTransitionAPI view-transition-name

Прочитал статью “Same-document view transitions for single-page applications” и решил запилить свою демку с открытием приложения как на айфоне, используя viewTransitionAPI.

Анимация реализуется с помощью CSS свойства view-transition-name. Так мы указываем, что анимация для этого элемента должна происходить отдельно.

⚠️ Значение view-transition-name должно быть уникальным, если у разных элементов одно и то же значение view-transition-name, анимация скипнется и появится ошибка в консоли.

Но есть нюанс, на время перехода можно указать view-transition-name разным элементам. Так мы скажем браузеру, что один элемент должен анимироваться в другой.

В реакте, пока только появляется экспериментальная поддержка ViewTransition, поэтому придётся использовать flushSync, чтобы запустить рендер синхронно, что не есть гуд для производительности.

Код перехода выглядит так:

 
const handleAppOpened = (e: React.MouseEvent<HTMLButtonElement>, appName: string) => {
    openedApp.current = (e.target as HTMLButtonElement);
    // выставляем иконке такой же viewTransitionName как и для экрана приложения
    openedApp.current.style.viewTransitionName = 'app-content';
 
 // запускаем переход
    document.startViewTransition(() => {
      if (openedApp.current?.style) {
     // сбрасываем viewTransitionName для иконки
        openedApp.current.style.viewTransitionName = '';
      }
 
   // синхронный рендер
      flushSync(() => setApp(appName));
    })
  };

Во время анимации появляется дерево псевдо-элементов.

 
::view-transition
  ::view-transition-group(root)
  ::view-transition-group(app-content)
    ::view-transition-old(app-content)
    ::view-transition-new(app-content)

Так мы можем выставить кастомную анимацию:

 
::view-transition-new(app-content) {
  animation: 300ms ease;
}
 
::view-transition-old(app-content) {
  animation: 300ms ease reverse;
}

Отлаживать анимацию, можно с помощью панели Animations: ⚙️ > More tools > Animations

📂 Исходники здесь 🌐 Демка здесь

Ещё по теме

#frontend@cherkashindev

🔥 12 👍 4 1