Интеграция с ванильным JavaScript

Dragula — это легковесная библиотека для реализации функционала drag-and-drop в веб-приложениях. Она не требует использования фреймворков и прекрасно работает с ванильным JavaScript. Для подключения доступны два варианта: через CDN или локальную установку через npm.

Через CDN:

<link rel="stylesheet" href="https://unpkg.com/dragula/dist/dragula.min.css">
<script src="https://unpkg.com/dragula/dist/dragula.min.js"></script>

Через npm:

npm install dragula

После установки через npm подключение осуществляется следующим образом:

import dragula from 'dragula';
import 'dragula/dist/dragula.css';

Инициализация контейнеров

Для использования Dragula необходимо указать контейнеры, элементы которых будут перетаскиваться. Контейнеры передаются в виде массива DOM-элементов или NodeList.

const container1 = document.getElementById('container1');
const container2 = document.getElementById('container2');

const drake = dragula([container1, container2]);

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

Основные параметры конфигурации

Dragula поддерживает ряд опций, которые позволяют гибко настраивать поведение перетаскивания:

  • moves — функция, определяющая, можно ли перемещать конкретный элемент:
const drake = dragula([container1], {
  moves: function (el, source, handle, sibling) {
    return handle.classList.contains('handle');
  }
});
  • accepts — функция, задающая правила, куда элемент можно перетащить:
const drake = dragula([container1, container2], {
  accepts: function (el, target, source, sibling) {
    return target !== source; // запрещает перемещать внутри того же контейнера
  }
});
  • copy — позволяет создавать копии перетаскиваемого элемента:
const drake = dragula([container1, container2], {
  copy: true
});
  • revertOnSpill — возвращает элемент на исходное место при неправильном переносе:
const drake = dragula([container1, container2], {
  revertOnSpill: true
});

Работа с событиями

Dragula предоставляет мощную систему событий для отслеживания всех этапов перетаскивания:

  • drag — вызывается при начале перетаскивания:
drake.on('drag', function (el) {
  el.style.opacity = '0.5';
});
  • drop — срабатывает при успешном размещении элемента в новом контейнере:
drake.on('drop', function (el, target, source, sibling) {
  el.style.opacity = '1';
  console.log(`Элемент перемещён из ${source.id} в ${target.id}`);
});
  • over и out — события при наведении элемента на контейнер и уходе с него:
drake.on('over', function (el, container) {
  container.style.backgroundColor = '#f0f0f0';
});

drake.on('out', function (el, container) {
  container.style.backgroundColor = '';
});
  • remove — срабатывает при удалении элемента через dragula.remove() или при включённой опции removeOnSpill:
drake.on('remove', function (el, container) {
  console.log(`Элемент удалён из ${container.id}`);
});

Продвинутая кастомизация

Dragula позволяет расширять функционал с помощью дополнительных условий и интеграции с другими библиотеками:

  • Группировка элементов: использование handle и классов для ограничения перетаскивания только определённых частей элемента.
  • Сортировка внутри контейнера: можно использовать sibling в событиях drop для определения позиции элемента и обновления порядка в массиве данных.
  • Динамическое добавление контейнеров: контейнеры могут добавляться после инициализации:
const newContainer = document.getElementById('container3');
drake.containers.push(newContainer);
  • Интеграция с AJAX: можно отправлять обновлённый порядок на сервер при каждом drop:
drake.on('drop', function (el, target) {
  const order = Array.from(target.children).map(item => item.dataset.id);
  fetch('/update-order', {
    method: 'POST',
    body: JSON.stringify(order),
    headers: { 'Content-Type': 'application/json' }
  });
});

Стилизация элементов и контейнеров

Для корректной работы Dragula требуется базовая стилизация:

  • Элементы контейнера должны быть блочными (display: block) или флекс-элементами.
  • Перетаскиваемый элемент можно визуально выделять через CSS, используя событие drag или класс gu-transit:
.gu-transit {
  opacity: 0.5;
  border: 2px dashed #000;
}
  • Контейнеры при наведении элемента можно подсвечивать через событие over, что улучшает визуальное восприятие интерфейса.

Совместимость и производительность

Dragula оптимизирована для работы с ванильным JavaScript и поддерживает все современные браузеры. Она использует события mousemove и mouseup, что обеспечивает высокую производительность и минимальную задержку при перетаскивании. Для больших списков рекомендуется использовать делегирование и минимизировать количество DOM-операций внутри событий drop и over.