External Drag and Drop

Dragging events on the Mobiscroll event calendar

Events can be scheduled by dragging and dropping an external item onto the scheduler with Mobiscroll draggable. In order for that to work you will need to have two things set up:

  • Enable the scheduler to receive external events by setting externalDrop to true.
  • Initialize the external events (containers) as draggable components.

Set up a container as draggable with the mbsc-draggable attribute. Pass a skeleton event definition through the data-drag-data attribute as a stringified json object. This will be added to the event calendar on drop. If omitted, a default event will be created. For a more programmatic approach you might want to use the component initialization where the draggable is initialized in js code and the dragData can be passed as an object.

Working together with SortableJS and Dragula lists

Mobiscroll provides built-in support for two widely used reorderable drag-and-drop list libraries: SortableJS and Dragula. If you are already using any of these libraries to reorder list items, they can be seamlessly integrated with the scheduler. This integration enables a smooth workflow where items can be dragged from external lists and scheduled directly onto the calendar.

Events can be created and scheduled by dragging items from third-party lists into the event calendar. To enable this behavior you will need to:

  • Allow the scheduler to receive external drops by setting externalDrop.
  • Use the sortableJsDraggable or dragulaDraggable plugins to connect the third-party list with the scheduler.

The event data will be read from the dragged element's data-drag-data attribute, or the plugin's options expose an eventData function where the event definition (title, start, end, resource, etc.) can be specified.

You can then handle the calendars lifecycle events such as onEventCreate, onEventCreated or onEventCreateFailed to run custom logic (e.g. showing a toast) when a drop succeeds or fails.

Unscheduling events (or dragging them off a calendar)

Additionally events can be unscheduled by dragging them out from the scheduler and dropping them onto an external drop container. To activate this, you will need to:

  • Enable the scheduler to allow dragging events out by setting externalDrag to true.

Use the dropcontainer component and its onItemDrop event to handle dropped events.

Events can also be dropped on another event calendar with externalDrop enabled.

When an event is dropped into an external drop container or another calendar, it will be deleted from the original calendar and the onEventDelete will be fired.

You can also use the onEventDragLeave and onEventDragEnter, and the drop container's onItemDragEnter and onItemDragLeave events to provide visual feedback or running custom logic during drag.

Learn more from the external drag & drop documentation.

Unscheduling events to SortableJS and Dragula lists

Dropping events from the Eventcalendar to SortableJS and Dragula lists is also possible with the sortableJsDraggable and dragulaDraggable plugins. To enable this behavior you will need to set the following under the options configuration:

  • Allow the list to receive external drops by setting externalDrop to true
  • Use the onExternalDrop callback to update the content of the third-party list. The function arguments return the afterElement - the list element before which the clone is dropped,

container - the list container, dragData - the dragged event data, position - the index where the clone is dropped on the list.

For details, and option lists see the externalDrop section in the documentation

Looking for external drag into a calendar?  Check out this example →
Download and try example

Demo

Loading the live demo

Preview in full screen

Connect SortableJS or Dragula lists to the Scheduler — drag items in to schedule events and drag events out to unschedule them.

Code

mobiscroll.setOptions({
  locale:  ,
  theme: ' ',
  themeVariant: ' '
});

var draggedTask;

function addToExternalList(args) {
  var afterElement = args.afterElement;
  var dragData = args.dragData;
  var eventLength = Math.abs(Math.abs(new Date(dragData.end).getTime() - new Date(dragData.start).getTime()) / (60 * 60 * 1000));
  var newItem = document.createElement('div');
  newItem.className = 'mds-drag-drop-sort-task';
  newItem.style.background = dragData.color || '';
  newItem.setAttribute('data-drag-data', JSON.stringify(dragData));
  newItem.innerHTML = '<div>' + dragData.title + '</div><div>' + eventLength + ' hour' + (eventLength > 1 ? 's' : '') + '</div>';
  args.container.insertBefore(newItem, afterElement || null);
}

var myCalendar = mobiscroll.eventcalendar('#demo-drag-drop-sortable-dragula', {
  view: {
    scheduler: { type: 'week' },
  },
  dragToMove: true,
  dragToCreate: true,
  externalDrop: true,
  externalDrag: true,
  onEventCreated: function (args) {
    if (draggedTask && args.action === 'externalDrop') {
      draggedTask.remove();
    }
    mobiscroll.toast({
      message: args.event.title + ' added',
    });
    var elm = document.getElementById('mds-event-' + args.event.id);
    if (elm) {
      elm.remove();
    }
  },
  onEventDeleted: function (args) {
    mobiscroll.toast({
      message: args.event.title + ' unscheduled',
    });
  },
});

mobiscroll.dropcontainer('#external-drop-cont', {
  onItemDrop: function (args) {
    if (args.data) {
      var event = args.data;
      var eventLength = Math.round(Math.abs(new Date(event.end) - new Date(event.start)) / (60 * 60 * 1000));
      var elm = document.createElement('div');

      elm.setAttribute('id', 'mds-event-' + event.id);
      elm.classList.add('mds-drag-drop-sort-task');
      elm.style.background = event.color;
      elm.innerHTML = '<div>' + event.title + '</div><div>' + eventLength + ' hour' + (eventLength > 1 ? 's' : '') + '</div>';

      document.getElementById('mds-event').appendChild(elm);

      mobiscroll.draggable('#mds-event-' + event.id, {
        dragData: event,
      });
    }
  },
});

var sortableInstance = new Sortable(document.getElementById('demo-sortable-list'), {
  animation: 150,
  forceFallback: true,
  onStart: function (e) {
    draggedTask = e.item;
  },
  onEnd: function () {
    setTimeout(function () {
      draggedTask = null;
    });
  },
});

mobiscroll.sortableJsDraggable.init(sortableInstance, {
  cloneSelector: '.sortable-drag',
  externalDrop: true,
  onExternalDrop: function (args) {
    addToExternalList(args);
  },
});

var drake = dragula([document.getElementById('demo-dragula-list')]);

drake.on('drag', function (e) {
  draggedTask = e;
});

drake.on('cancel', function () {
  draggedTask = null;
});

drake.on('drop', function () {
  setTimeout(function () {
    draggedTask = null;
  });
});

mobiscroll.dragulaDraggable.init(drake, {
  externalDrop: true,
  onExternalDrop: function (args) {
    addToExternalList(args);
  },
});

mobiscroll.getJson(
  'https://trial.mobiscroll.com/drag-drop-events/',
  function (events) {
    myCalendar.setEvents(events);
  },
  'jsonp',
);
  

Duplicate Session

You have signed in on a different machine. To keep everything in sync, you have been signed out of this session.

If you need to invite team members, manage seats and accounts you can do it from the licenses page.

Duplicate Session

We noticed you are logged in on a different machine and have closed your old session.

If you need to invite team members, manage seats and accounts you can do it from the licenses page.