gsap.matchMedia() для responsive-анимаций

Библиотека GSAP предоставляет мощный инструмент для создания анимаций, адаптирующихся под различные размеры экранов — gsap.matchMedia(). Этот метод позволяет условно применять анимации в зависимости от ширины окна, устройства или других медиа-запросов, что делает интерфейс гибким и отзывчивым.


Основы работы с gsap.matchMedia()

gsap.matchMedia() создаёт объект для управления анимациями на основе медиа-запросов. Основная идея заключается в том, чтобы регистрировать различные анимации для разных условий, а затем автоматически включать или отключать их при изменении размеров окна.

Пример базового синтаксиса:

const mm = gsap.matchMedia();

mm.add("(min-width: 1024px)", () => {
  // Анимации для экранов шире 1024px
  gsap.to(".box", { x: 500, duration: 2 });
});

mm.add("(max-width: 1023px)", () => {
  // Анимации для экранов меньше 1024px
  gsap.to(".box", { x: 200, duration: 1.5 });
});

Ключевые моменты:

  • add(mediaQuery, callback) — регистрирует анимации для конкретного медиа-запроса.
  • Анимации автоматически уничтожаются или создаются при изменении размеров окна.
  • Можно регистрировать несколько медиа-запросов для одного элемента.

Использование нескольких условий

Метод add поддерживает не только строки с медиа-запросами, но и объект с множественными условиями, что упрощает управление комплексными responsive-анимациями.

mm.add({
  "(min-width: 1200px)": () => {
    gsap.to(".title", { scale: 1.5, duration: 1 });
  },
  "(min-width: 768px) and (max-width: 1199px)": () => {
    gsap.to(".title", { scale: 1.2, duration: 0.8 });
  },
  "(max-width: 767px)": () => {
    gsap.to(".title", { scale: 1, duration: 0.5 });
  }
});

Такой подход делает код более читаемым и легко поддерживаемым. Каждое условие выполняется только при соответствующем размере экрана.


Очистка анимаций при смене медиа-запросов

GSAP автоматически уничтожает анимации при изменении условий медиа-запроса, если возвращается функция очистки. Это предотвращает накопление ненужных анимаций и утечки памяти.

mm.add("(min-width: 1024px)", () => {
  const tl = gsap.timeline();
  tl.to(".box", { x: 500, duration: 2 });

  return () => {
    tl.kill(); // удаление анимации при смене медиа-запроса
  };
});

Возвращаемая функция всегда выполняется при деактивации текущего условия.


Интеграция с timeline

gsap.matchMedia() удобно использовать с таймлайнами, чтобы создавать сложные, адаптивные анимации для различных устройств:

mm.add("(max-width: 767px)", () => {
  const tl = gsap.timeline();
  tl.from(".item", { y: 50, opacity: 0, stagger: 0.2 })
    .to(".item", { rotation: 360, duration: 1 });

  return () => tl.kill();
});

mm.add("(min-width: 768px)", () => {
  const tl = gsap.timeline();
  tl.from(".item", { x: -100, opacity: 0, stagger: 0.1 })
    .to(".item", { scale: 1.2, duration: 1 });

  return () => tl.kill();
});

Такой подход позволяет создавать разные анимационные сценарии для мобильных и десктопных устройств без дублирования кода.


Совмещение с другими методами GSAP

gsap.matchMedia() отлично сочетается с другими функциями GSAP:

  • ScrollTrigger: позволяет активировать анимации при скролле только на определённых размерах экрана.
  • ScrollToPlugin: условный скролл для разных устройств.
  • Easing и keyframes: адаптивное управление плавностью анимации.
mm.add("(min-width: 1024px)", () => {
  gsap.to(".section", {
    scrollTrigger: ".section",
    x: 400,
    duration: 2,
    ease: "power2.inOut"
  });
});

Практические советы

  1. Использовать matchMedia для крупных компонентов, которые меняются в зависимости от устройства.
  2. Избегать глобальных селекторов внутри медиа-запросов, чтобы не создавать лишние анимации.
  3. Всегда возвращать функцию очистки для предотвращения утечек.
  4. Можно комбинировать с динамическим изменением классов CSS для более сложной адаптации.

gsap.matchMedia() делает код анимации более модульным и удобным для поддержки. Он заменяет громоздкие условия с window.innerWidth и позволяет сосредоточиться на анимации, а не на логике адаптации.