Архитектура плагинов

Библиотека Shopify Draggable строится на модульной архитектуре с использованием плагинов, что позволяет расширять и изменять поведение перетаскивания без изменения базового ядра. Плагины представляют собой самостоятельные модули, которые подключаются к Draggable и реализуют конкретные функции, такие как сортировка, создание клона, управление зеркальным элементом и многое другое.


Основные принципы работы плагинов

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

  2. Событийная система Плагины активно используют события, предоставляемые Draggable: drag:start, drag:move, drag:stop, sortable:sorted и другие. Подписка на эти события позволяет плагину реагировать на действия пользователя и изменять поведение перетаскивания.

  3. Методы жизненного цикла Плагины реализуют стандартные методы жизненного цикла:

    • attach(draggable) – подключение плагина к экземпляру Draggable.
    • detach() – отключение плагина и очистка ресурсов.
    • Дополнительно плагин может реализовывать собственные вспомогательные методы для внутренней логики.
  4. Опции и конфигурация Каждый плагин принимает объект настроек при инициализации, что позволяет гибко управлять его поведением без изменения исходного кода. Настройки обычно включают селекторы, режимы работы, задержки и ограничения.


Взаимодействие ядра Draggable с плагинами

Ядро Draggable предоставляет базовый механизм перетаскивания, в котором реализованы:

  • определение элементов, доступных для перетаскивания,
  • отслеживание позиции курсора,
  • генерация события начала, движения и завершения перетаскивания.

Плагины подключаются к этому ядру через метод new Draggable(container, { plugins: [Plugin1, Plugin2], ... }). После инициализации:

  • ядро сообщает плагинам о каждом событии перетаскивания,
  • плагины могут перехватывать, модифицировать или расширять поведение,
  • изменения плагинов напрямую отражаются на DOM или внутреннем состоянии Draggable.

Таким образом, Draggable реализует паттерн наблюдатель, где ядро выступает как источник событий, а плагины — как подписчики, которые выполняют определенные действия.


Основные встроенные плагины

  1. Sortable Обеспечивает возможность сортировки элементов внутри контейнера. Управляет DOM, добавляет placeholder и генерирует событие sortable:sorted.

  2. Swappable Позволяет менять местами два элемента при перетаскивании. Плагин отслеживает позицию элементов и автоматически выполняет перестановку в DOM.

  3. Mirror Создает визуальный клон перетаскиваемого элемента, позволяя отображать его поверх других элементов, не изменяя исходный объект. Полезен для UX, когда требуется плавная анимация перемещения.

  4. Collidable Реализует взаимодействие с целевыми зонами (droppable). Отслеживает пересечение элементов и генерирует события collidable:over, collidable:out, collidable:dropped.


Создание собственного плагина

Плагин должен быть классом или функцией с методом attach(draggable) и, опционально, detach().

Пример структуры собственного плагина для логирования действий:

class LoggerPlugin {
  constructor(options = {}) {
    this.options = options;
  }

  attach(draggable) {
    this.draggable = draggable;
    this.handleDragStart = event => {
      console.log('Начало перетаскивания:', event.source);
    };
    this.handleDragStop = event => {
      console.log('Конец перетаскивания:', event.source);
    };

    draggable.on('drag:start', this.handleDragStart);
    draggable.on('drag:stop', this.handleDragStop);
  }

  detach() {
    this.draggable.off('drag:start', this.handleDragStart);
    this.draggable.off('drag:stop', this.handleDragStop);
  }
}

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

  • Плагин хранит ссылку на экземпляр Draggable (this.draggable) для управления событиями.
  • Методы attach и detach позволяют безопасно подключать и отключать функциональность.
  • Взаимодействие осуществляется через события, а не прямую модификацию ядра.

Рекомендации по архитектуре плагинов

  • Минимизировать зависимости между плагинами.
  • Использовать события вместо прямого изменения DOM ядра.
  • Поддерживать конфигурацию через опции, чтобы плагин был гибким и повторно используемым.
  • Освобождать ресурсы при отключении плагина (отписка от событий, удаление временных элементов).
  • Тестировать совместимость с другими плагинами, чтобы избежать конфликтов при множественном подключении.

Взаимодействие нескольких плагинов

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

  1. Плагин A может модифицировать поведение элемента до того, как плагин B получит событие.
  2. Плагин B может реагировать на изменения, внесенные плагином A.

Правильная организация порядка подключения и подписки на события позволяет строить сложные интерфейсы с поддержкой drag-and-drop, sortable, swappable и collidable одновременно без конфликтов.


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