Drag and drop multiple browser windows / tabs
Wrote some code to drag and drop items to other items. This works great.
var currentDragElement = null;
var draggableElements = document.querySelectorAll('[draggable="true"]');
[].forEach.call(draggableElements, function(element) {
element.addEventListener('dragstart', handleDragStart, false);
element.addEventListener('dragenter', handleDragEnter, false);
element.addEventListener('dragover', handleDragOver, false);
element.addEventListener('dragleave', handleDragLeave, false);
element.addEventListener('drop', handleDrop, false);
element.addEventListener('dragend', handleDragEnd, false);
});
function handleDragStart(event) {
currentDragElement = event.target;
event.dataTransfer.setData("text/plain", event.target.dataset.uuid);
}
function handleDragOver(event) {
event.preventDefault();
event.dataTransfer.dropEffect = 'move';
return false;
}
function handleDragEnter(event) {
this.classList.add('over');
}
function handleDragLeave(event) {
this.classList.remove('over');
}
function handleDrop(event) {
event.stopPropagation();
event.preventDefault();
if(currentDragElement == event.target) {
return;
}
console.log('dragged element ', currentDragElement.dataset.uuid , ' on element ', event.target.dataset.uuid)
return false;
}
function handleDragEnd(event) {
[].forEach.call(draggableElements, function (element) {
element.classList.remove('over');
});
}
section {
border: solid 5px green;
margin: 20px;
float: left;
width: 40%;
}
[draggable="true"]:hover {
opacity: 0.6;
}
[draggable="true"] {
cursor: move;
background-color: #acacac;
padding: 10px;
margin: 10px;
}
.over[draggable="true"] {
background-color: orange;
}
<section>
<div draggable="true" data-uuid="1.1">draggable 1.1</div>
<div draggable="true" data-uuid="1.2">draggable 1.2</div>
<div draggable="true" data-uuid="1.3">draggable 1.3</div>
</section>
<section>
<div draggable="true" data-uuid="2.1">draggable 2.1</div>
<div draggable="true" data-uuid="2.2">draggable 2.2</div>
<div draggable="true" data-uuid="2.3">draggable 2.3</div>
</section>
But I want to be able to have two open windows from one browser and then drag and drop items draggable="true"
from one window to another.
As my code is not working now because
var currentDragElement = null;
remains null
if executed from another window / tab. The question is, how can I get the drag and drop launcher item if it is launched in another window or tab of the same browser? So I want the console to indicate the same when dragging from different windows, as it does now when dragging in the same window.
Please don't answer jQuery, thanks for the help!
source to share
As @Mouser pointed out, localstorage does the trick even without any ajax request or the like.
Tested on Google Chrome only
Using localstorage is not allowed in SO scripts, so if anyone wants to try it, copy the following file, save it, open in two browser windows and have fun with drag and drop
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>drag - drop - demo</title>
<style>
section {
border: solid 5px green;
margin: 20px;
float: left;
width: 40%;
}
[draggable="true"]:hover {
opacity: 0.6;
}
[draggable="true"] {
cursor: move;
background-color: #acacac;
padding: 10px;
margin: 10px;
}
.over[draggable="true"] {
background-color: orange;
}
</style>
</head>
<body>
<section>
<div draggable="true" data-uuid="1.1">draggable 1.1</div>
<div draggable="true" data-uuid="1.2">draggable 1.2</div>
<div draggable="true" data-uuid="1.3">draggable 1.3</div>
<div draggable="true" data-uuid="1.4">draggable 1.4</div>
<div draggable="true" data-uuid="1.5">draggable 1.5</div>
</section>
<section>
<div draggable="true" data-uuid="2.1">draggable 2.1</div>
<div draggable="true" data-uuid="2.2">draggable 2.2</div>
<div draggable="true" data-uuid="2.3">draggable 2.3</div>
<div draggable="true" data-uuid="2.4">draggable 2.4</div>
<div draggable="true" data-uuid="2.5">draggable 2.5</div>
</section>
<script>
var draggableElements = document.querySelectorAll('[draggable="true"]');
[].forEach.call(draggableElements, function(element) {
element.addEventListener('dragstart', handleDragStart, false);
element.addEventListener('dragenter', handleDragEnter, false);
element.addEventListener('dragover', handleDragOver, false);
element.addEventListener('dragleave', handleDragLeave, false);
element.addEventListener('drop', handleDrop, false);
element.addEventListener('dragend', handleDragEnd, false);
});
function handleDragStart(event) {
localStorage.setItem('currentDragElement', event.target.dataset.uuid);
event.dataTransfer.setData("text/plain", event.target.dataset.uuid);
}
function handleDragOver(event) {
event.preventDefault();
event.dataTransfer.dropEffect = 'move';
return false;
}
function handleDragEnter(event) {
this.classList.add('over');
}
function handleDragLeave(event) {
this.classList.remove('over');
}
function handleDrop(event) {
event.stopPropagation();
event.preventDefault();
if(localStorage.getItem('currentDragElement') == event.target.dataset.uuid) {
return;
}
currentDragElement = document.querySelector('[data-uuid="'+localStorage.getItem('currentDragElement')+'"]');
console.log('dragged element ', currentDragElement , ' on element ', event.target)
localStorage.setItem('currentDragElement', null);
return false;
}
function handleDragEnd(event) {
[].forEach.call(draggableElements, function (element) {
element.classList.remove('over');
});
}
</script>
</body>
</html>
source to share