Использование с React

Для начала необходимо установить библиотеку через npm или yarn:

npm install driver.js
# или
yarn add driver.js

После установки библиотеку можно импортировать в компонент React:

import Driver from 'driver.js';
import 'driver.js/dist/driver.min.css';

Подключение CSS обязательно для корректного отображения подсветки и тултипов.


Создание и конфигурация экземпляра Driver

Экземпляр Driver создаётся с помощью конструктора и может принимать объект с глобальными настройками:

const driver = new Driver({
  opacity: 0.75,               // Прозрачность фона вокруг элемента
  padding: 10,                 // Отступы вокруг подсвечиваемого элемента
  allowClose: true,            // Возможность закрыть тур кликом по фону
  overlayClickNext: false,     // Переход к следующему шага при клике на фон
  doneBtnText: 'Готово',       // Текст кнопки завершения
  closeBtnText: 'Закрыть',     // Текст кнопки закрытия
  nextBtnText: 'Далее',        // Текст кнопки перехода
  prevBtnText: 'Назад',        // Текст кнопки возврата
});

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


Определение шагов тура

Шаги задаются в виде массива объектов. Каждый объект описывает конкретный элемент и поведение подсветки:

const steps = [
  {
    element: '#button-start',       // CSS селектор или HTMLElement
    popover: {
      title: 'Начало работы',
      description: 'Нажмите эту кнопку, чтобы начать',
      position: 'bottom'            // top, bottom, left, right, auto
    }
  },
  {
    element: '#menu-settings',
    popover: {
      title: 'Настройки',
      description: 'Здесь можно изменить параметры',
      position: 'right'
    }
  }
];

Каждый шаг может содержать:

  • element — обязательный селектор или ссылку на DOM-элемент.
  • popover.title — заголовок подсказки.
  • popover.description — описание действия.
  • popover.position — положение тултипа относительно элемента.
  • popover.className — дополнительный CSS класс для кастомизации.
  • onNext, onPrevious, onHighlightStarted, onHighlighted, onReset — колбэки для управления поведением тура.

Запуск тура в React

Для интеграции с React тур удобно запускать через эффекты:

import React, { useEffect } from 'react';

const AppTour = () => {
  useEffect(() => {
    const driver = new Driver({
      opacity: 0.6,
      padding: 15,
      doneBtnText: 'Завершить'
    });

    driver.defineSteps(steps);
    driver.start();
  }, []);

  return null;
};

useEffect без зависимостей обеспечивает запуск тура один раз при монтировании компонента.


Управление состоянием тура

Driver.js предоставляет методы для управления туром:

  • driver.start() — запуск тура.
  • driver.reset() — сброс состояния и удаление подсветки.
  • driver.highlight(element) — подсветка конкретного элемента вне основного тура.
  • driver.moveNext() и driver.movePrevious() — переход между шагами программно.
  • driver.defineSteps(steps) — определение или переопределение шагов.

В React часто удобно хранить экземпляр Driver в состоянии или ref:

import React, { useRef } from 'react';

const TourController = () => {
  const driverRef = useRef(null);

  const startTour = () => {
    driverRef.current = new Driver({ opacity: 0.7 });
    driverRef.current.defineSteps(steps);
    driverRef.current.start();
  };

  return <button onCl ick={startTour}>Начать тур</button>;
};

Динамические шаги и элементы

В React часто элементы создаются динамически, поэтому важно убедиться, что они уже присутствуют в DOM до подсветки. Для этого используют setTimeout, MutationObserver или useLayoutEffect:

useLayoutEffect(() => {
  const driver = new Driver({ opacity: 0.5 });
  
  const interval = setInterval(() => {
    if (document.querySelector('#dynamic-button')) {
      driver.defineSteps([
        {
          element: '#dynamic-button',
          popover: { title: 'Динамическая кнопка', description: 'Эта кнопка создана позже' }
        }
      ]);
      driver.start();
      clearInterval(interval);
    }
  }, 100);

  return () => clearInterval(interval);
}, []);

Кастомизация стилей

Driver.js использует CSS-классы:

  • .driver-highlighted — подсвеченный элемент.
  • .driver-popover — тултип с заголовком и описанием.
  • .driver-overlay — затемнённый фон.

Можно добавить собственные стили для изменения цвета, шрифта, анимации появления:

.driver-popover {
  background-color: #fff;
  border-radius: 8px;
  box-shadow: 0 4px 12px rgba(0,0,0,0.15);
}

.driver-highlighted {
  border: 3px solid #007bff;
  border-radius: 6px;
}

Интеграция с состоянием приложения

Туры можно привязывать к состоянию Redux или React Context. Например, показывать тур только один раз для нового пользователя:

const hasSeenTour = useSelector(state => state.user.hasSeenTour);
const dispatch = useDispatch();

useEffect(() => {
  if (!hasSeenTour) {
    const driver = new Driver();
    driver.defineSteps(steps);
    driver.start();
    dispatch({ type: 'MARK_TOUR_SEEN' });
  }
}, [hasSeenTour, dispatch]);

Особенности работы с портальными компонентами

Если элементы рендерятся через React Portal, обычный CSS-селектор может не найти их сразу. Необходимо либо использовать useLayoutEffect для уверенности в наличии DOM, либо передавать элемент напрямую:

const portalButton = document.getElementById('portal-button');
driver.defineSteps([
  { element: portalButton, popover: { title: 'Портальная кнопка', description: 'Рендер через портал' } }
]);

Работа с событиями и колбэками

Driver.js поддерживает несколько жизненных циклов:

  • onHighlightStarted — срабатывает перед анимацией подсветки.
  • onHighlighted — после завершения подсветки.
  • onNext/onPrevious — при переходе между шагами.
  • onReset — при сбросе тура.

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

const driver = new Driver();
driver.defineSteps([
  {
    element: '#step1',
    popover: { title: 'Шаг 1' },
    onHighlighted: () => console.log('Шаг 1 подсвечен')
  }
]);
driver.start();

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