jQuery UI Sortable + Droppable both trigger when dropped on droppable - jquery-ui

I have a list of elements that are sortable and sort fine. I also have a droppable that resides outside of the sortable list. When I drop items on the droppable, it is intended to perform a copy operation, meaning that sorting during this operation is not desirable.
Unfortunately however, dragging a sortable to an external droppable causes sortable.update to fire. Is there a way to have all sortable drag/drop events ignored if a sortable is dragged outside of a given element?
I've gone through all the relevant sortable events, and I can't seem to find any reference to the element the sortable was dropped on, in order to see if they have common parents.
Here's a fiddle to demonstrate: http://jsfiddle.net/6yhbG/
Dragging either sortable 1/2 to the droppable causes the sortable.sort to fire.

OK finally got to the bottom of it: sortable('cancel') needs to be called from sortable.stop and I'm simply adding a class to the sortable so it knows whether to cancel itself or not:
$('div').droppable({
drop: function(e, ui) {
ui.draggable.parent().addClass('dropped');
}
});
$('ul').sortable({
stop: function(){
if ($(this).hasClass('dropped')){
$(this).sortable('cancel');
$(this).removeClass('dropped');
}
}
});
With my updated example at: http://jsfiddle.net/6yhbG/1/

Related

Droppable not recognising draggables

I'm using jQuery to create a droppable element - this appears to work fine, as the element gets the class ui-droppable.
I've set it up like this:
$('#trashcan').droppable({
drop: function( event, ui ) {
alert('Dropped');
}
});
where #trashcan is an image.
Later, in response to a user action, I set up some draggables. These are table rows, and I set them up like this ('element' is just the created table row):
$(element).draggable({
revert: false,
helper: 'clone',
intersect: 'pointer',
stop: function() {
alert('dropped');
}});
Afterwards, they look like this:
<tr class="ui-draggable">
<td>First</td>
<td>Name</td>
</tr>
So it all looks like it's set up ok. However, when I drag a table row over the trashcan, I get the 'dropped' from the draggable code, but not from the droppable. So the draggable has been dragged, but the droppable hasn't recognised it.
I'm not sure what to check for here. Is there any reason why it wouldn't work on table rows, for instance? I've checked things like z-index, and that doesn't appear to be the issue. Do I have to do something special to connect the draggable and droppable after the draggables are created (i.e. something that gets done when the droppable is created, which I need to re-do because the draggables are created later)?

Allow list reordering when drag from an icon in the list line

I'm using JQuery UI Sortable to allow reordering elements within a list when dragging element. I would like to improve this processing by allowing reordering only when dragging from an icon present in each element (this icon is a span within the li) not for the whole element.
Is it possible to do this with Sortable?
Thanks very much for your help!
Thierry
Yes, jQuery-UI provides a "handle" option:
http://jqueryui.com/demos/sortable/#option-handle
Restricts sort start click to the specified element...
Initialize a sortable with the handle option specified.
$( ".selector" ).sortable({ handle: 'h2' });

locking one tab in jQuery's sortable tab

I'm creating a sortable tab in jQuery UI but I want to lock the last tab. I already panned it to the right, but it can still be sorted. What do I need to do to lock the last added tab?
Officially, you can specify on the sortable which sub-items you want to be sortable, just set the property items to a selector.
While it disables sorting when moving the other tabs (meaning the disabled tab never moves), it can still be dragged. To work around this issue, just bind a function to the item's mousedown event and call stopPropagation() to prevent the drag.
See this jsfiddle example: http://jsfiddle.net/wZ4c6/1/
$('#tabs').tabs().find('.ui-tabs-nav').sortable({
axis: 'x',
items: '> li:not(.locked)' //This will prevent sortables to move around the locked item
});
$('button').button().click(function(){
// Lock last tab
$('#tabs > ul > li:last').addClass('locked').mousedown(function(event){
event.stopPropagation();
});
// Refresh sortable items
$('#tabs').find('.ui-tabs-nav').sortable('refresh');
});

Working with jQuery UI Draggable, Droppable and Sortable

I have an ul of draggable items (#doc-editor-options ul li), an area for dropping those items (#doc-editor-content) and an ul within that area for holding those items (#items-holder), which is sortable. This dragging and dropping is only one-way, only items from the list can be dragged and dropped into the holder.
$("#doc-editor-options ul li").draggable({
helper: 'clone',
connectToSortable: '#item-holder',
containment: $(".doc-editor")
});
$("#doc-editor-content").droppable({
drop: function(e, ui){
console.log('dropped');
}
});
$("#item-holder").sortable({
placeholder: 'placeholder-highlight',
cursor: 'pointer',
});
Two questions that I have:
Right now when I drag an item from the list and drop it into the other list, the drop callback for .droppable() is called twice. I think this has something to do with the #item-holder being sortable. I want it to only be fired when I drop an item into the list and only know about that item's event and ui in the callback.
I also need the functionality where by default, the items-holder is not sortable. The only time it becomes sortable is when you are dragging and hovering an item over it. So I can't sort the list by default, but if I drag an item over to it, I can choose where to place that item in the list (i.e. the list is now sortable) and once I drop it, the list becomes unsortable again.
EDIT: I figured out #2, I needed to bind mousedown to the draggable items which enables sorting then disables it on mouseup. Still having problems with #1, it seems like some of the sortable events are firing the drop callback when I drop an item in or I hover out of the item holder.
1:
Your drop() gets called twice because connectToSortable is also triggering a drop().
My suggestion would be to delete $("#doc-editor-content").droppable() altogether, and instead add the receive(e, ui) handler to your sortable.
2:
Your fix works. However I would suggest a much easier alternative: leave the sortable always enabled and add the option "handle: h2". (Pick any tag that will not exist within your LIs.) This will let you drop into the list, but disable user sorting in-place.
Example:
$('#item-holder').sortable({
placeholder: 'placeholder-highlight',
cursor: 'pointer',
handle: 'h2',
receive: function(e, ui) {
console.log('dropped');
}
});

message in empty <div> to drag

I am working on drag and drop tool using jQuery UI's sortable widget.
I'd like to add a message into an empty div where something can be dragged into, like: "drag here". I'd like to remove this message as soon as something is in that div. There will be times when the page loads with something already in that div, so it can't be only on action, but onload needs to check it too.
How do I go about it?
Here's my code:
$("#divFrom, #divTo").sortable({
connectWith: '.connectedSortable'
}).disableSelection();
You should be able to set up a draggable, and droppable and tap into droppable's drop event handler, which is fired when an item is dropped:
$("#target").droppable({
drop: function() {
// Empty the droppable div:
$(".message").remove();
}
});
Demo here: http://jsfiddle.net/andrewwhitaker/rUgJF/2/
As for doing something similar on load, if you provided your markup it would make providing a solution a little easier (is there a specific element inside the droppable div that you could check for?)
Hope that helps.

Resources