Анимация при фильтрации

Packery — это мощная библиотека для создания динамических сеток с возможностью перетаскивания, перестановки и фильтрации элементов. Одной из ключевых возможностей при работе с фильтрацией является плавная анимация изменения расположения элементов, что обеспечивает визуально приятный переход и улучшает пользовательский опыт.

При фильтрации элементов важны два аспекта: скрытие ненужных элементов и перераспределение видимых элементов в сетке. Packery сам по себе не включает встроенную анимацию фильтрации, но интеграция с библиотекой GSAP или использованием CSS-переходов позволяет добиться плавного эффекта.


Скрытие и показ элементов

Элементы, которые не соответствуют фильтру, необходимо скрывать. Для этого используются классы или атрибуты, управляемые через Jav * aScript:

const grid = document.querySelector('.grid');
const pckry = new Packery(grid, {
  itemSelector: '.grid-item',
  gutter: 10
});

function filterItems(filterClass) {
  const items = grid.querySelectorAll('.grid-item');
  items.forEach(item => {
    if (!item.classList.contains(filterClass)) {
      item.style.transition = 'opacity 0.4s';
      item.style.opacity = 0;
      setTimeout(() => {
        item.style.display = 'none';
        pckry.layout(); // Пересчет сетки после скрытия
      }, 400);
    } else {
      item.style.display = 'block';
      setTimeout(() => {
        item.style.opacity = 1;
      }, 20);
    }
  });
}

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

  • transition отвечает за плавное изменение прозрачности.
  • opacity обеспечивает визуальный эффект исчезновения.
  • setTimeout синхронизирует скрытие с завершением анимации.
  • pckry.layout() пересчитывает позиции видимых элементов, создавая эффект перераспределения сетки.

Анимация перемещения элементов

Packery автоматически управляет позиционированием элементов в сетке, но по умолчанию перемещения происходят мгновенно. Для плавной анимации используется CSS-свойство transform с transition или библиотека GSAP:

.grid-item {
  transition: transform 0.5s, opacity 0.5s;
}

При изменении позиции Packery обновляет transform: translate для каждого элемента. Переходы CSS позволяют перемещения выглядеть плавно без дополнительного кода.


Использование GSAP для продвинутой анимации

GSAP позволяет управлять анимацией плавно и с большим контролем, включая временные функции, задержки и синхронизацию:

import { gsap } from "gsap";

function animateFilter(filterClass) {
  const items = grid.querySelectorAll('.grid-item');

  items.forEach(item => {
    if (!item.classList.contains(filterClass)) {
      gsap.to(item, { opacity: 0, duration: 0.4, onComplete: () => {
        item.style.display = 'none';
        pckry.layout();
      }});
    } else {
      item.style.display = 'block';
      gsap.fromTo(item, { opacity: 0 }, { opacity: 1, duration: 0.4 });
    }
  });
}

Преимущества GSAP:

  • Поддержка кривых ускорения (ease) для более естественного движения.
  • Синхронизация нескольких анимаций одновременно.
  • Управление последовательностью событий через timeline.

Последовательность действий при фильтрации

  1. Определение фильтра (класс или атрибут элемента).
  2. Скрытие элементов, которые не соответствуют фильтру, с анимацией opacity или через GSAP.
  3. Отображение подходящих элементов с плавным появлением.
  4. Вызов pckry.layout() для перераспределения сетки.
  5. Плавное смещение видимых элементов с использованием CSS transition или GSAP.

Оптимизация производительности

При большом количестве элементов следует учитывать производительность:

  • Использовать will-change: transform для элементов, чтобы браузер заранее оптимизировал рендер.
  • Минимизировать количество изменений DOM за один раз.
  • Предпочтительно использовать CSS-переходы для базовой анимации и GSAP только для сложных эффектов.

Комбинирование с фильтрацией по категориям

Packery отлично работает с фильтрацией по категориям. Для этого можно использовать атрибуты data-category и фильтровать элементы через Jav * aScript:

function filterCategory(category) {
  const items = grid.querySelectorAll('.grid-item');
  items.forEach(item => {
    const isMatch = item.dataset.category === category || category === 'all';
    gsap.to(item, { 
      opacity: isMatch ? 1 : 0, 
      duration: 0.4, 
      display: isMatch ? 'block' : 'none',
      onComplete: () => pckry.layout()
    });
  });
}

Это позволяет создавать динамическую сетку с анимированным переходом элементов между состояниями видимости и обеспечивает плавную реакцию интерфейса на действия пользователя.


Packery в сочетании с CSS-переходами и GSAP предоставляет гибкий инструмент для создания плавных анимаций при фильтрации, улучшая визуальное восприятие сетки и повышая интерактивность веб-приложений.