Управление видимостью

Popper.js предоставляет гибкие механизмы для управления видимостью всплывающих элементов относительно их якорей. Видимость может быть как полностью контролируемой вручную, так и автоматически зависеть от положения и пересечения с областью просмотра. Управление видимостью реализуется через модификаторы, события и динамическое обновление состояния поппера.

Модификатор preventOverflow и его влияние на видимость

Модификатор preventOverflow предотвращает выход поппера за границы определённого контейнера или окна просмотра. Его ключевые параметры:

  • boundariesElement — элемент, относительно которого производится проверка выхода.
  • padding — расстояние от границы контейнера, которое поппер должен учитывать.
  • altAxis — позволяет включить проверку по альтернативной оси для более точного контроля позиционирования.

Пример использования:

const popperInstance = Popper.createPopper(referenceElement, popperElement, {
  modifiers: [
    {
      name: 'preventOverflow',
      options: {
        boundariesElement: 'viewport',
        padding: 8,
        altAxis: true,
      },
    },
  ],
});

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

Модификатор hide и автоматическое управление видимостью

Модификатор hide позволяет Popper.js автоматически отслеживать, когда поппер полностью выходит за пределы видимой области. Он добавляет класс или флаг к элементу, который можно использовать для скрытия.

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

  • enabled — включает или отключает модификатор.
  • strategy — определяет способ скрытия: через класс CSS или через inline-стиль display: none.

Пример настройки:

const popperInstance = Popper.createPopper(referenceElement, popperElement, {
  modifiers: [
    {
      name: 'hide',
      enabled: true,
    },
  ],
});

Модификатор автоматически добавляет data-popper-reference-hidden="true", когда элемент выходит за границы, и false, когда возвращается в область видимости.

Динамическое обновление видимости с помощью update()

Popper.js предоставляет метод update(), который пересчитывает позиции и применяет модификаторы заново. Это позволяет динамически реагировать на изменения DOM, скролл, изменение размеров окна и изменение содержимого поппера.

popperInstance.update();

Метод возвращает промис с объектом состояния, который содержит актуальное положение и флаги видимости:

popperInstance.update().then(state => {
  if (state.modifiersData.hide.isReferenceHidden) {
    popperElement.style.display = 'none';
  } else {
    popperElement.style.display = 'block';
  }
});

События и наблюдение за видимостью

Для более сложной логики можно использовать MutationObserver или слушать события окна (resize, scroll) и вызывать update():

window.addEventListener('resize', () => {
  popperInstance.update();
});

window.addEventListener('scroll', () => {
  popperInstance.update();
});

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

Сочетание модификаторов для полного контроля

Для надёжного управления видимостью часто используют комбинацию модификаторов:

  1. preventOverflow — не позволяет попперу выйти за границы.
  2. flip — автоматически переворачивает поппер, если пространство ограничено.
  3. hide — скрывает элемент, если он полностью вне зоны видимости.

Пример:

const popperInstance = Popper.createPopper(referenceElement, popperElement, {
  placement: 'bottom-start',
  modifiers: [
    { name: 'flip', options: { fallbackPlacements: ['top', 'right', 'left'] } },
    { name: 'preventOverflow', options: { padding: 10 } },
    { name: 'hide', enabled: true },
  ],
});

Контроль видимости через CSS и классы

Popper.js позволяет добавлять динамические классы, например, data-popper-reference-hidden, для управления видимостью через CSS:

.popper[data-popper-reference-hidden="true"] {
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.2s ease;
}

.popper[data-popper-reference-hidden="false"] {
  opacity: 1;
}

Это даёт возможность реализовать плавное появление и исчезновение, не прибегая к прямому управлению через display.

Управление через strategy позиционирования

Popper.js поддерживает стратегии absolute и fixed:

  • absolute — поппер позиционируется относительно ближайшего предка с position: relative.
  • fixed — игнорирует поток документа, остаётся на месте при скролле.

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