Skip to content

Commit 7a1975c

Browse files
christophe-gkaffarelllukasoppermann
authored
Dragleave (#540)
* dispatches sortenter event first time dragged item enters a container; makes sure original target is sent with the sortenter and sortstart event; * fix styling issues * Added containerClass, a css class added when dragitem hover on a container; fires sortenter when a dragitem enters a container; fires dragleave when a dragitem leaves a container. * Renamed variables and cleaned cde * Delete package-lock.json * Revert "Delete package-lock.json" This reverts commit 802a55f. * Update package-lock.json Trying to fix package-lock * Fixed typo, added comments for better understanding Co-authored-by: gabriel <gabrielgoller123@gmail.com> Co-authored-by: Lukas Oppermann <oppermann.lukas@gmail.com>
1 parent bf30788 commit 7a1975c

4 files changed

Lines changed: 98 additions & 1 deletion

File tree

README.md

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -183,6 +183,15 @@ sortable('.sortable')[0].addEventListener('sortupdate', function(e) {
183183
});
184184
```
185185

186+
### sortenter
187+
188+
Fired when a dragitem enters a sortable container.
189+
190+
### sortleave
191+
192+
Fired when a dragitem leaves a sortable container.
193+
194+
186195
## Options
187196

188197
### items
@@ -253,6 +262,15 @@ sortable('.sortable', {
253262
});
254263
```
255264

265+
### dropTargetContainerClass
266+
Use `dropTargetContainerClass` option to apply a css Class to the container. The class is added when dragged item enters the container and removed when it leaves it (or is dropped).
267+
268+
``` javascript
269+
sortable('.sortable', {
270+
dropTargetContainerClass: 'is-drop-target' // Defaults to false
271+
});
272+
```
273+
256274
### maxItems
257275
Use the `maxItems` option to restrict the number of items that can be added to a sortable from a [connected](#connectwith) sortable. `maxItems` should always be combined with the `items` option. Make sure `items` does not match placeholder and other options, so that they are not counted.
258276

docs/html5sortable.js

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -603,6 +603,7 @@ var sortable = (function () {
603603
placeholderClass: 'sortable-placeholder',
604604
draggingClass: 'sortable-dragging',
605605
hoverClass: false,
606+
dropTargetContainerClass: false,
606607
debounce: 0,
607608
throttleTime: 100,
608609
maxItems: 0,
@@ -719,6 +720,15 @@ var sortable = (function () {
719720
removeEventListener(items, 'mouseenter');
720721
removeEventListener(items, 'mouseleave');
721722
};
723+
// Remove container events
724+
var _removeContainerEvents = function () {
725+
if (originContainer) {
726+
removeEventListener(originContainer, 'dragleave');
727+
}
728+
if (previousContainer && (previousContainer !== originContainer)) {
729+
removeEventListener(previousContainer, 'dragleave');
730+
}
731+
};
722732
/**
723733
* _getDragging returns the current element to drag or
724734
* a copy of the element.
@@ -804,6 +814,7 @@ var sortable = (function () {
804814
removeEventListener(handles, 'mousedown');
805815
_removeItemEvents(items);
806816
_removeItemData(items);
817+
_removeContainerEvents();
807818
// clear sortable flag
808819
sortableElement.isSortable = false;
809820
};
@@ -865,6 +876,7 @@ var sortable = (function () {
865876
addData(sortableElement, '_disabled', 'false');
866877
// remove event handlers from items
867878
_removeItemEvents(items);
879+
_removeContainerEvents();
868880
removeEventListener(handles, 'mousedown');
869881
// remove event handlers from sortable
870882
removeEventListener(sortableElement, 'dragover');
@@ -995,6 +1007,9 @@ var sortable = (function () {
9951007
if (sortableContainer && sortableContainer !== previousContainer) {
9961008
destinationItemsBeforeUpdate = _filter(sortableContainer.children, addData(sortableContainer, 'items'))
9971009
.filter(function (item) { return item !== store(sortableElement).placeholder; });
1010+
if (options.dropTargetContainerClass) {
1011+
sortableContainer.classList.add(options.dropTargetContainerClass);
1012+
}
9981013
sortableContainer.dispatchEvent(new CustomEvent('sortenter', {
9991014
detail: {
10001015
origin: {
@@ -1010,6 +1025,25 @@ var sortable = (function () {
10101025
originalTarget: target
10111026
}
10121027
}));
1028+
addEventListener(sortableContainer, 'dragleave', function (e) {
1029+
var outTarget = e.releatedTarget || e.fromElement;
1030+
if (!e.currentTarget.contains(outTarget)) {
1031+
if (options.dropTargetContainerClass) {
1032+
sortableContainer.classList.remove(options.dropTargetContainerClass);
1033+
}
1034+
sortableContainer.dispatchEvent(new CustomEvent('sortleave', {
1035+
detail: {
1036+
origin: {
1037+
elementIndex: originElementIndex,
1038+
index: originIndex,
1039+
container: sortableContainer
1040+
},
1041+
item: dragging,
1042+
originalTarget: target
1043+
}
1044+
}));
1045+
}
1046+
});
10131047
}
10141048
previousContainer = sortableContainer;
10151049
});
@@ -1096,6 +1130,9 @@ var sortable = (function () {
10961130
var destinationElementIndex = _index(dragging, Array.from(dragging.parentElement.children)
10971131
.filter(function (item) { return item !== placeholder; }));
10981132
var destinationIndex = _index(dragging, destinationItems);
1133+
if (options.dropTargetContainerClass) {
1134+
destinationContainer.classList.remove(options.dropTargetContainerClass);
1135+
}
10991136
/*
11001137
* When a list item changed container lists or index within a list
11011138
* Fires Custom Event - 'sortupdate'

src/defaultConfiguration.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ export default {
1313
placeholderClass: 'sortable-placeholder',
1414
draggingClass: 'sortable-dragging',
1515
hoverClass: false,
16+
dropTargetContainerClass: false,
1617
debounce: 0,
1718
throttleTime: 100,
1819
maxItems: 0,

src/html5sortable.ts

Lines changed: 42 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,17 @@ const _removeItemEvents = function (items) {
6060
_off(items, 'mouseenter')
6161
_off(items, 'mouseleave')
6262
}
63+
64+
// Remove container events
65+
const _removeContainerEvents = function () {
66+
if (originContainer) {
67+
_off(originContainer, 'dragleave')
68+
}
69+
if (previousContainer && (previousContainer !== originContainer)) {
70+
_off(previousContainer, 'dragleave')
71+
}
72+
}
73+
6374
/**
6475
* _getDragging returns the current element to drag or
6576
* a copy of the element.
@@ -146,6 +157,7 @@ const _destroySortable = function (sortableElement) {
146157
_off(handles, 'mousedown')
147158
_removeItemEvents(items)
148159
_removeItemData(items)
160+
_removeContainerEvents()
149161
// clear sortable flag
150162
sortableElement.isSortable = false
151163
}
@@ -206,6 +218,7 @@ const _reloadSortable = function (sortableElement) {
206218
_data(sortableElement, '_disabled', 'false')
207219
// remove event handlers from items
208220
_removeItemEvents(items)
221+
_removeContainerEvents()
209222
_off(handles, 'mousedown')
210223
// remove event handlers from sortable
211224
_off(sortableElement, 'dragover')
@@ -349,6 +362,9 @@ export default function sortable (sortableElements, options: configuration|objec
349362
destinationItemsBeforeUpdate = _filter(sortableContainer.children, _data(sortableContainer, 'items'))
350363
.filter(item => item !== store(sortableElement).placeholder)
351364

365+
if (options.dropTargetContainerClass) {
366+
sortableContainer.classList.add(options.dropTargetContainerClass)
367+
}
352368
sortableContainer.dispatchEvent(new CustomEvent('sortenter', {
353369
detail: {
354370
origin: {
@@ -364,8 +380,29 @@ export default function sortable (sortableElements, options: configuration|objec
364380
originalTarget: target
365381
}
366382
}))
367-
}
368383

384+
_on(sortableContainer, 'dragleave', e => {
385+
// TODO: rename outTarget to be more self-explanatory
386+
// e.fromElement for very old browsers, similar to relatedTarget
387+
const outTarget = e.relatedTarget || e.fromElement
388+
if (!e.currentTarget.contains(outTarget)) {
389+
if (options.dropTargetContainerClass) {
390+
sortableContainer.classList.remove(options.dropTargetContainerClass)
391+
}
392+
sortableContainer.dispatchEvent(new CustomEvent('sortleave', {
393+
detail: {
394+
origin: {
395+
elementIndex: originElementIndex,
396+
index: originIndex,
397+
container: sortableContainer
398+
},
399+
item: dragging,
400+
originalTarget: target
401+
}
402+
}))
403+
}
404+
})
405+
}
369406
previousContainer = sortableContainer
370407
})
371408

@@ -464,6 +501,10 @@ export default function sortable (sortableElements, options: configuration|objec
464501
.filter(item => item !== placeholder))
465502
const destinationIndex = _index(dragging, destinationItems)
466503

504+
if (options.dropTargetContainerClass) {
505+
destinationContainer.classList.remove(options.dropTargetContainerClass)
506+
}
507+
467508
/*
468509
* When a list item changed container lists or index within a list
469510
* Fires Custom Event - 'sortupdate'

0 commit comments

Comments
 (0)