HTML5 Drag and Drop

Asked

Viewed 539 times

2

I am using the example provided on the website of w3schools, to generate a Drag/Drop with two columns (DIV). The objects that will be moved between these DIV’s are identified by Ids 1 to 5.

So far this is all working as it should, the problem occurs at the moment the user moves one item over the other.

EX: The user drags the ID item 1 and drops it over the ID item 2, instead of passing the DIV ID and grabbing the ID of the P element.

log result:

Correto:
ITEM: 1 - COLUNA: DIV2

Errado:
ITEM: 2 - COLUNA: 1

I wonder if it is possible to block the P element so that it is not dropped, or to pick up the ID of the DIV even the item being dropped on another item.

function allowDrop(ev) {
    ev.preventDefault();
}

function drag(ev) {
    ev.dataTransfer.setData("text", ev.target.id);
}

function drop(ev) {
    ev.preventDefault();
    var data = ev.dataTransfer.getData("text");
    ev.target.appendChild(document.getElementById(data));
	
	console.log("ITEM: " + data + " - COLUNA: " + ev.target.id);
}
#DIV1, #DIV2 {
    float: left;
    width: 150px;
    height: 400px;
    margin: 10px;
    padding: 10px;
    border: 1px solid black;
}
p {
color:red
}
<div id="DIV1" ondrop="drop(event)" ondragover="allowDrop(event)">
<h3><center>INICIO</center></h3>
<hr>
    <p draggable="true" ondragstart="drag(event)" id="1">UM</p>
    <p draggable="true" ondragstart="drag(event)" id="2">DOIS</p>
    <p draggable="true" ondragstart="drag(event)" id="3">TRES</p>
    <p draggable="true" ondragstart="drag(event)" id="4">QUATRO</p>
    <p draggable="true" ondragstart="drag(event)" id="5">CINCO</p>
</div>

<div id="DIV2" ondrop="drop(event)" ondragover="allowDrop(event)">
<h3><center>MEIO</center></h3>
<hr>
</div>

2 answers

1

It is not necessary to import whole libs as jQuery and jQuery-UI, just check in the drop who is the element that is receiving the event dragover, thus:

function drop(ev) {
    ev.preventDefault();

    if (["DIV1", "DIV2"].indexOf(ev.target.id) === -1) {
        return;
    }

The ["DIV1", "DIV2"].indexOf(ev.target.id) === -1 checks if id is DIV1 or DIV2, otherwise it does not move.

following example:

function allowDrop(ev) {
    ev.preventDefault();
}

function drag(ev) {
    ev.dataTransfer.setData("text", ev.target.id);
}

function drop(ev) {
    ev.preventDefault();

    if (["DIV1", "DIV2"].indexOf(ev.target.id) === -1) {
        return;
    }

    var data = ev.dataTransfer.getData("text");
    ev.target.appendChild(document.getElementById(data));
    
    console.log("ITEM: " + data + " - COLUNA: " + ev.target.id);
}
#DIV1, #DIV2 {
    float: left;
    width: 150px;
    height: 400px;
    margin: 10px;
    padding: 10px;
    border: 1px solid black;
}
p {
   color:red
}
<div id="DIV1" ondrop="drop(event)" ondragover="allowDrop(event)">
<h3><center>INICIO</center></h3>
<hr>
    <p draggable="true" ondragstart="drag(event)" id="1">UM</p>
    <p draggable="true" ondragstart="drag(event)" id="2">DOIS</p>
    <p draggable="true" ondragstart="drag(event)" id="3">TRES</p>
    <p draggable="true" ondragstart="drag(event)" id="4">QUATRO</p>
    <p draggable="true" ondragstart="drag(event)" id="5">CINCO</p>
</div>

<div id="DIV2" ondrop="drop(event)" ondragover="allowDrop(event)">
<h3><center>MEIO</center></h3>
<hr>
</div>


However if you want to be dropped into the element you have ondragover even that loose on top of another sub-element you can change in function drop the event.target for event.currentTarget, thus:

function drop(ev) {
    ev.preventDefault();

    var data = ev.dataTransfer.getData("text");
    ev.currentTarget.appendChild(document.getElementById(data));

    console.log("ITEM: " + data + " - COLUNA: " + ev.currentTarget.id);
}

Particularly I believe that it is well to improve for the end user, example:

function allowDrop(ev) {
    ev.preventDefault();
}

function drag(ev) {
    ev.dataTransfer.setData("text", ev.target.id);
}

function drop(ev) {
    ev.preventDefault();

    var data = ev.dataTransfer.getData("text");
    ev.currentTarget.appendChild(document.getElementById(data));
    
    console.log("ITEM: " + data + " - COLUNA: " + ev.currentTarget.id);
}
#DIV1, #DIV2 {
    float: left;
    width: 150px;
    height: 400px;
    margin: 10px;
    padding: 10px;
    border: 1px solid black;
}
p {
   color:red
}
<div id="DIV1" ondrop="drop(event)" ondragover="allowDrop(event)">
<h3><center>INICIO</center></h3>
<hr>
    <p draggable="true" ondragstart="drag(event)" id="1">UM</p>
    <p draggable="true" ondragstart="drag(event)" id="2">DOIS</p>
    <p draggable="true" ondragstart="drag(event)" id="3">TRES</p>
    <p draggable="true" ondragstart="drag(event)" id="4">QUATRO</p>
    <p draggable="true" ondragstart="drag(event)" id="5">CINCO</p>
</div>

<div id="DIV2" ondrop="drop(event)" ondragover="allowDrop(event)">
<h3><center>MEIO</center></h3>
<hr>
</div>

-1


Problem can be solved using the example below:

Original source: http://embed.plnkr.co/WcIZlD/

	$(document).ready(function() {

  $('.box-item').draggable({
    cursor: 'move',
    helper: "clone"
  });

  $("#INICIO").droppable({
    drop: function(event, ui) {
      var itemid = $(event.originalEvent.toElement).attr("itemid");
      $('.box-item').each(function() {
        if ($(this).attr("itemid") === itemid) {
          $(this).appendTo("#INICIO");
		  console.log("ITEM: " + itemid + " - COLUNA: INICIO");
        }
      });
    }
  });
  
    $("#MEIO").droppable({
    drop: function(event, ui) {
      var itemid = $(event.originalEvent.toElement).attr("itemid");
      $('.box-item').each(function() {
        if ($(this).attr("itemid") === itemid) {
          $(this).appendTo("#MEIO");
		  console.log("ITEM: " + itemid + " - COLUNA: MEIO");
        }
      });
    }
  });
  
    $("#FIM").droppable({
    drop: function(event, ui) {
      var itemid = $(event.originalEvent.toElement).attr("itemid");
      $('.box-item').each(function() {
        if ($(this).attr("itemid") === itemid) {
          $(this).appendTo("#FIM");
		  console.log("ITEM: " + itemid + " - COLUNA: FIM");
        }
      });
    }
  });


});
/* Styles go here */

.box-container {
	height: 200px;
}

.box-item {
	width: 100%;
	z-index: 1000
}
<!DOCTYPE html>
<html>

  <head>
    
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css" />
    <link rel="stylesheet" href="https://code.jquery.com/ui/1.11.4/themes/ui-lightness/jquery-ui.css" />
    
    <script type="text/javascript" src="https://code.jquery.com/jquery-2.2.3.min.js"></script>
    <script type="text/javascript" src="https://code.jquery.com/ui/1.11.4/jquery-ui.min.js"></script>
    
  </head>

  <body>
   <div class="container-fluid">
      <div class="row">
        <div class="col-xs-3">
          <div class="panel panel-default">
            <div class="panel-heading">
              <h1 class="panel-title">INICIO</h1>
            </div>
            <div id="INICIO" class="panel-body box-container">
              <div itemid="itm-1" class="btn btn-default box-item">Item 1</div>
              <div itemid="itm-2" class="btn btn-default box-item">Item 2</div>
              <div itemid="itm-3" class="btn btn-default box-item">Item 3</div>
              <div itemid="itm-4" class="btn btn-default box-item">Item 4</div>
              <div itemid="itm-5" class="btn btn-default box-item">Item 5</div>
            </div>
          </div>
        </div>
        <div class="col-xs-3">
          <div class="panel panel-default">
            <div class="panel-heading">
              <h1 class="panel-title">MEIO</h1>
            </div>
            <div id="MEIO" class="panel-body box-container"></div>
          </div>
        </div>
		<div class="col-xs-3">
          <div class="panel panel-default">
            <div class="panel-heading">
              <h1 class="panel-title">FIM</h1>
            </div>
            <div id="FIM" class="panel-body box-container"></div>
          </div>
        </div>
      </div>
    </div>
  </body>

</html>

Browser other questions tagged

You are not signed in. Login or sign up in order to post.