Параметр fallbackFocus

Библиотека Focus-trap предназначена для управления фокусом в веб-приложениях, обеспечивая его ограничение внутри определённой области DOM, такой как модальные окна, всплывающие панели или кастомные диалоговые компоненты. Один из ключевых параметров конфигурации — fallbackFocus, который играет важную роль в случаях, когда фокус не может быть установлен на элементы внутри контейнера.


Назначение fallbackFocus

Параметр fallbackFocus используется как резервный вариант установки фокуса. Он применяется, когда:

  • Внутри контейнера нет видимых или фокусируемых элементов.
  • Все элементы внутри контейнера имеют атрибут disabled или tabindex="-1".
  • Фокус был утерян после закрытия предыдущего активного элемента.

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


Типы значений

fallbackFocus может принимать несколько типов значений:

  1. CSS-селектор Позволяет указать элемент внутри контейнера, на который будет установлен фокус, если стандартные элементы фокусировки недоступны. Например:

    const trap = focusTrap(container, {
      fallbackFocus: '#default-button'
    });

    В этом примере, если внутри контейнера нет фокусируемых элементов, фокус будет перенесён на элемент с id="default-button".

  2. Функция Функция должна возвращать DOM-элемент, на который будет установлен фокус. Это удобно, когда элемент выбирается динамически или зависит от состояния приложения:

    const trap = focusTrap(container, {
      fallbackFocus: () => document.querySelector('.modal-footer button')
    });

    Использование функции позволяет вычислять элемент в момент активации focus-trap, обеспечивая актуальность выбора.

  3. DOM-элемент Можно передать конкретный элемент напрямую:

    const defaultButton = document.getElementById('close-modal');
    const trap = focusTrap(container, {
      fallbackFocus: defaultButton
    });

    Такой способ гарантирует, что фокус будет точно на нужном элементе без вычислений.


Поведение при активации focus-trap

При вызове метода activate():

  1. Focus-trap проверяет наличие фокусируемых элементов внутри контейнера.

  2. Если подходящие элементы отсутствуют, библиотека проверяет наличие fallbackFocus.

  3. В зависимости от типа значения параметра, устанавливается фокус:

    • Для CSS-селектора — ищется элемент через querySelector.
    • Для функции — вызывается функция и результат используется как элемент фокуса.
    • Для DOM-элемента — фокус устанавливается напрямую.

Если fallbackFocus не задан и фокусировать не на что, фокус остаётся на текущем документе, что может привести к нарушению клавиатурной навигации и потенциальным проблемам доступности.


Взаимодействие с другими параметрами

fallbackFocus тесно связан с другими конфигурационными опциями:

  • initialFocus — задаёт элемент для установки фокуса при активации. Если initialFocus не найден или недоступен, срабатывает fallbackFocus.
  • allowOutsideClick — при клике вне контейнера фокус может перемещаться на элемент вне trap; fallbackFocus не используется в таких случаях.
  • escapeDeactivates — при деактивации focus-trap через Escape, fallbackFocus не активируется автоматически, если используется для установки фокуса после активации.

Примеры применения

  1. Модальные окна без кнопок внутри

    const modalTrap = focusTrap(document.querySelector('.modal'), {
      fallbackFocus: '.modal-close'
    });
    modalTrap.activate();

    Даже если внутри модального окна нет интерактивных элементов, фокус гарантированно будет установлен на кнопку закрытия.

  2. Динамически создаваемый контент

    const dynamicTrap = focusTrap(document.querySelector('.dynamic-panel'), {
      fallbackFocus: () => document.querySelector('.dynamic-panel .first-focusable')
    });
    dynamicTrap.activate();

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


Рекомендации по использованию

  • Всегда задавать fallbackFocus для модальных и интерактивных компонентов, чтобы поддерживать доступность.
  • Предпочтительно использовать функцию, если элементы могут создаваться динамически.
  • Проверять, что элемент, указанный в fallbackFocus, действительно фокусируемый (tabindex ≥ 0, не disabled, видимый на странице).

Особенности поведения

  • fallbackFocus не инициирует событие focusin на элементе, если он уже имеет фокус.
  • Если fallbackFocus указывает на несуществующий элемент, библиотека выбрасывает предупреждение в консоль (в режиме разработки), но не ломает работу страницы.
  • Использование CSS-селектора позволяет гибко управлять фокусом без прямого взаимодействия с DOM в коде.

Использование fallbackFocus делает работу с Focus-trap предсказуемой, повышает стабильность клавиатурной навигации и обеспечивает соблюдение стандартов доступности. Этот параметр особенно важен в сложных интерфейсах с динамическими и условными элементами фокусировки.