Поиск в реальном времени

Для использования функционала поиска в реальном времени в Isotope необходимо корректно подключить библиотеку и выполнить инициализацию контейнера с элементами. Базовый синтаксис выглядит следующим образом:

var grid = document.querySelector('.grid');
var iso = new Isotope(grid, {
  itemSelector: '.grid-item',
  layoutMode: 'fitRows'
});
  • itemSelector определяет CSS-класс элементов, по которым будет производиться фильтрация и поиск.
  • layoutMode задаёт способ раскладки элементов; для поиска в реальном времени часто используют fitRows или masonry для динамического изменения позиций элементов.

Создание фильтра поиска

Для фильтрации элементов по введённому тексту используется функция filter. Она принимает функцию, возвращающую true для элементов, которые должны оставаться видимыми, и false для скрытия. Пример реализации:

var searchInput = document.querySelector('#search-input');

searchInput.addEventListener('keyup', function() {
  var query = searchInput.value.toLowerCase();

  iso.arrange({
    filter: function(itemElem) {
      var text = itemElem.textContent.toLowerCase();
      return text.includes(query);
    }
  });
});
  • keyup позволяет обновлять фильтрацию при каждом вводе символа, создавая эффект мгновенного поиска.
  • Приведение текста к нижнему регистру через toLowerCase() обеспечивает регистронезависимый поиск.

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

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

function debounce(fn, delay) {
  let timeout;
  return function() {
    clearTimeout(timeout);
    timeout = setTimeout(() => fn.apply(this, arguments), delay);
  };
}

searchInput.addEventListener('keyup', debounce(function() {
  var query = searchInput.value.toLowerCase();
  iso.arrange({
    filter: function(itemElem) {
      return itemElem.textContent.toLowerCase().includes(query);
    }
  });
}, 200));
  • debounce откладывает выполнение фильтрации на 200 миллисекунд после последнего нажатия клавиши.
  • Это снижает нагрузку на рендеринг и повышает отзывчивость интерфейса при поиске среди сотен и тысяч элементов.

Расширение поиска по нескольким полям

В сложных интерфейсах элементы могут содержать несколько текстовых полей (например, название и описание). Для поиска по всем полям используют агрегирование текста:

iso.arrange({
  filter: function(itemElem) {
    var title = itemElem.querySelector('.title').textContent.toLowerCase();
    var description = itemElem.querySelector('.description').textContent.toLowerCase();
    return title.includes(query) || description.includes(query);
  }
});
  • Использование логического или (||) позволяет отображать элементы, если хотя бы одно поле содержит поисковый запрос.
  • Этот подход повышает точность и полезность поиска в интерфейсах с комплексным содержимым.

Интеграция с другими фильтрами

Isotope позволяет комбинировать поиск с другими фильтрами, например по категориям или тегам. Для этого применяется объединение функций фильтрации:

var selectedCategory = '*';

document.querySelectorAll('.category-button').forEach(function(button) {
  button.addEventListener('click', function() {
    selectedCategory = button.getAttribute('data-category');
    filterItems();
  });
});

searchInput.addEventListener('keyup', debounce(filterItems, 200));

function filterItems() {
  var query = searchInput.value.toLowerCase();
  iso.arrange({
    filter: function(itemElem) {
      var matchesQuery = itemElem.textContent.toLowerCase().includes(query);
      var matchesCategory = selectedCategory === '*' || itemElem.classList.contains(selectedCategory);
      return matchesQuery && matchesCategory;
    }
  });
}
  • Комбинирование фильтров через логическое и (&&) обеспечивает отображение только тех элементов, которые удовлетворяют сразу нескольким условиям.
  • Такой подход создаёт динамический многоуровневый поиск, который легко расширять и кастомизировать.

Анимация и плавное обновление

Isotope автоматически добавляет анимацию при изменении видимости элементов. Для настройки скорости и эффекта анимации используется опция transitionDuration:

var iso = new Isotope(grid, {
  itemSelector: '.grid-item',
  layoutMode: 'fitRows',
  transitionDuration: '0.4s'
});
  • transitionDuration задаёт время анимации при показе или скрытии элементов.
  • Плавные переходы повышают визуальное восприятие поиска и делают интерфейс более современным.

Поддержка пустого результата

При поиске может возникнуть ситуация, когда ни один элемент не удовлетворяет запросу. Для этого добавляют специальный контейнер с сообщением:

iso.on('arrangeComplete', function(filteredItems) {
  var noResults = document.querySelector('#no-results');
  noResults.style.display = filteredItems.length === 0 ? 'block' : 'none';
});
  • arrangeComplete срабатывает после завершения фильтрации и позволяет отслеживать количество видимых элементов.
  • Показывая или скрывая сообщение, интерфейс остаётся информативным даже при пустом результате поиска.

Резюме ключевых приёмов

  • Использовать keyup и filter для мгновенного поиска.
  • Применять debounce для оптимизации производительности при большом количестве элементов.
  • Агрегировать текст из нескольких полей для расширенного поиска.
  • Комбинировать поиск с другими фильтрами через логические условия.
  • Настраивать плавные анимации с помощью transitionDuration.
  • Обрабатывать пустой результат через событие arrangeComplete.

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