Drag-and-Drop Support

Tree has built-in support for internal/external drag-and-drop.

Common Use

To enable drag-and-drop support for a tree, set the drag parameter to true:

Enabling drag-and-drop support for Tree

webix.ui({
    view:"tree",
    drag:true
});

Related sample:  Enabling Drag-and-Drop in Tree

The "move" Mode

This is the mode in which the dragged nodes are moved out. The "move" mode is enabled with drag:"move":

webix.ui({
    view:"tree",
    drag:"move"
});

Related sample:  The 'move' DnD Mode

The "order" Mode

This mode works like the "move" mode, but items can't be dragged out of the tree container boundaries. Besides, the remaining items are automatically rearranged while the item is being dragged. That's why, when you drop the item to the final destination, the remaining items won't need any rearrangements.

To enable the drag-n-drop support and activate the 'order' mode, just set the drag parameter to order.

Activating the 'order' mode for items

webix.ui({
    view:"tree",
    drag:"order"
});

Related sample:  The "order" Drag-and-Drop Mode

The 'source-target' Mode

When there are several trees on the page, you may want to set specific tree(s) as the source of drag-n-drop (to drag items from) and specific tree(s) as the target of drag-n-drop (to drag items to).

  • To set a tree as the drag-n-drop source (the user can drag items from the tree but can't drag to it), you should set the drag parameter to source.
  • To set a tree as the drag-n-drop target (the user can drag items to the tree but can't drag from it), you should set the
    drag parameter to target.

Using the 'source-target' mode

//you can drag items only from treeA to treeB.
//Dragging within treeA is denied. Dragging from treeB to treeA is denied.
webix.ui({
    id:"treeA",
    view:"tree",
    drag:"source"
});
 
webix.ui({
    id:"treeB",
    view:"tree",
    drag:"target"
});

Related sample:  Custom Dropping Behaviour

Advanced

Information stated in the Common part is enough in most cases. Use the info in this section only if you want to customize drag-and-drop behavior.

The part will describe these issues:

Custom text of the dragging items

To redefine the text displaying for the dragging item(s), you should use the onBeforeDrag event.
The desired template is set through the context.html property. It can contain any HTMLy.

Displaying custom text for dragged items

treea.attachEvent("onBeforeDrag", function(context, ev){
    context.html = "  "+context.source.length+" item(s)";
});

Related sample:  Custom Text of Dragged Items

Denying dragging specific items

To deny dragging specific items you can use the onBeforeDrag event and return false each time you want to block the operation.

Denying dragging even items

tree.attachEvent("onBeforeDrag", function(context, ev){
    if (tree.getItem(context.source).$level == 2){
        return true;     // allows dragging items with the second nesting level
    }
    return false;        // denies dragging in any other case
});

From now on, each time d-n-d is started, the item level will be checked, and the item can be dragged only if its level equal to 2.

Custom drop behavior

To specify custom behavior for the 'drop' operation, you can use the onBeforeDrop event.

Let's assume you want to specify the following behavior:

  • When you drag item(s) to the closed folder, the item is inserted as a sibling;
  • When you drag item(s) to the opened folder, the item is inserted as a child.

Custom dropping behavior

tree.attachEvent("onBeforeDrop", function(context, ev){
    if (this.getItem(context.target).$count && this.getItem(context.target).open){
        //drop as the first child
        context.parent = context.target;
        context.index = 0;
    } else {
        //drop as the next sibling
        context.index++;
    }
});

Related sample:  Custom Dropping Behaviour
Related sample:  Custom Dropping Behaviour. Denying Dropping

Related events

In the default scenario, there is no need to use any of the mentioned events, because Tree will process all the operations on its own. Use the events only when the default behavior needs customizing.

The following events are generated while d-n-d process:

  • onBeforeDrag - fires before the mouse button is pressed and moved over a draggable item
  • onBeforeDragIn - fires before a dragged element is moved over the drop area
  • onDragOut - fires when a dragged element is moved outside of the drop area
  • onBeforeDrop - fires before a dragged element is released over the drop area
  • onAfterDrop - fires after drag-n-drop was finished

Events order

Let's assume you have 2 identical trees and drag an item from one to the other.

So, here is the order in which events are invoked in trees:

  1. onBeforeDrag fires in tree1.
    Returning 'false' from the event handler will block the current drag-n-drop operation.
  2. onBeforeDragIn / onDragOut fire in tree1 as you drag the item within the tree1's container.
    Returning 'false' from the event handler will deny dropping to the related tree.
  3. onBeforeDragIn / onDragOut fire in tree2 as you drag the item within the tree2's container.
    Returning 'false' from the event handler will deny dropping to the related tree.
  4. onBeforeDrop fires in tree2.
    Returning 'false' from the event handler will block the current drag-n-drop operation.
  5. onAfterDrop fires in tree2.
Back to top