admin管理员组

文章数量:1305137

I'm making a drag and drop system with HTML and JavaScript. I would drag and drap a task (div elements) from the column "To Do" to "In Development" and vice versa. The only problem I've got is that you could drag and drop a task into another task and that I won't.

This is the begin situation:

and this is after a drag and drop:

Now I'll prevent that users could drag and drop task 2 into task 1. How could I do that? Below you could find my code.

Thanks in advance.

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));
}
table {
  font-family: "Segoe UI", sans-serif;
  border-collapse: collapse;
}
table,
th,
td {
  border: 1px solid gray;
  padding: 10px;
}
th {
  background-color: lightgray;
}
th,
td {
  width: 33.33%;
}
td {
  min-height: 80px;
}
.post-it {
  background-color: yellow;
  padding: 10px 5px;
  margin: 5px;
  margin-bottom: 20px;
  box-shadow: 5px 5px 5px gray;
  border: 1px black solid;
}
.post-it h4 {
  text-align: center;
  margin: 0;
}
<table>
  <tr>
    <th>To Do</th>
    <th>In Development</th>
    <th>Done</th>
  </tr>

  <tr>

    <td id="todo" ondrop="drop(event)" ondragover="allowDrop(event)">

      <div id="task1" class="post-it" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 1</h4>
        <p  draggable="false">Lorem ipsum dolor sit amet</p>
      </div>

      <div id="task2" class="post-it" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 2</h4>
        <p  draggable="false">Irish skinny, grinder affogato</p>
      </div>

    </td>

    <td id="indev" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
    <td id="done" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
  </tr>
</table>

I'm making a drag and drop system with HTML and JavaScript. I would drag and drap a task (div elements) from the column "To Do" to "In Development" and vice versa. The only problem I've got is that you could drag and drop a task into another task and that I won't.

This is the begin situation:

and this is after a drag and drop:

Now I'll prevent that users could drag and drop task 2 into task 1. How could I do that? Below you could find my code.

Thanks in advance.

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));
}
table {
  font-family: "Segoe UI", sans-serif;
  border-collapse: collapse;
}
table,
th,
td {
  border: 1px solid gray;
  padding: 10px;
}
th {
  background-color: lightgray;
}
th,
td {
  width: 33.33%;
}
td {
  min-height: 80px;
}
.post-it {
  background-color: yellow;
  padding: 10px 5px;
  margin: 5px;
  margin-bottom: 20px;
  box-shadow: 5px 5px 5px gray;
  border: 1px black solid;
}
.post-it h4 {
  text-align: center;
  margin: 0;
}
<table>
  <tr>
    <th>To Do</th>
    <th>In Development</th>
    <th>Done</th>
  </tr>

  <tr>

    <td id="todo" ondrop="drop(event)" ondragover="allowDrop(event)">

      <div id="task1" class="post-it" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 1</h4>
        <p  draggable="false">Lorem ipsum dolor sit amet</p>
      </div>

      <div id="task2" class="post-it" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 2</h4>
        <p  draggable="false">Irish skinny, grinder affogato</p>
      </div>

    </td>

    <td id="indev" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
    <td id="done" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
  </tr>
</table>

Share Improve this question edited May 29, 2017 at 12:36 H. Pauwelyn asked Aug 9, 2016 at 16:31 H. PauwelynH. Pauwelyn 14.3k28 gold badges92 silver badges161 bronze badges
Add a ment  | 

3 Answers 3

Reset to default 3

You can solve this problem by adding a "noDrop" class to your post-it div and then updating your drop function with a test for that class. The following uses jQuery to do the test, using the jQuery hasClass function.

function drop(ev) {
  var _target = $("#" + ev.target.id);
  var data = ev.dataTransfer.getData("text");
  if ($(_target).hasClass("noDrop")) {
    console.log("no transfer");
    ev.preventDefault();
  } else {
    ev.preventDefault();
    ev.target.appendChild(document.getElementById(data));
  }
}
table {
  font-family: "Segoe UI", sans-serif;
  border-collapse: collapse;
}
table,
th,
td {
  border: 1px solid gray;
  padding: 10px;
}
th {
  background-color: lightgray;
}
th,
td {
  width: 33.33%;
}
td {
  min-height: 80px;
}
.post-it {
  background-color: yellow;
  padding: 10px 5px;
  margin: 5px;
  margin-bottom: 20px;
  box-shadow: 5px 5px 5px gray;
  border: 1px black solid;
}
.post-it h4 {
  text-align: center;
  margin: 0;
}
<script src="https://ajax.googleapis./ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table>
  <tr>
    <th>To Do</th>
    <th>In Development</th>
    <th>Done</th>
  </tr>

  <tr>

    <td id="todo" ondrop="drop(event)" ondragover="allowDrop(event)">

      <div id="task1" class="post-it noDrop" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 1</h4>
        <p>Lorem ipsum dolor sit amet</p>
      </div>

      <div id="task2" class="post-it noDrop" draggable="true" droppab ondragstart="drag(event)">
        <h4 draggable="false">Task 2</h4>
        <p>Irish skinny, grinder affogato</p>
      </div>

    </td>

    <td id="indev" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
    <td id="done" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
  </tr>
</table>

Use ev.currentTarget instead of ev.target in the drag function as well as in the drop function. 1

The right answer

I know I am quite late here, but the accepted answer is not working so I am posting the solution for new visitors of this page.

The only thing you need to do is set a condition for you droppable <div>. For that modify the allowDrop() function to this:


    function allowDrop(ev) {
      if(ev.target.tagName.toLowerCase() == 'td')
         ev.preventDefault();
    }    

As of now you are allowing drop on all elements. By setting condition you can allow the drop only if the target is a <td> element.

Here's a demo after implementing the condition:

function allowDrop(ev) {
  if(ev.target.tagName.toLowerCase() == 'td')
     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));
}
table {
  font-family: "Segoe UI", sans-serif;
  border-collapse: collapse;
}
table,
th,
td {
  border: 1px solid gray;
  padding: 10px;
}
th {
  background-color: lightgray;
}
th,
td {
  width: 33.33%;
}
td {
  min-height: 80px;
}
.post-it {
  background-color: yellow;
  padding: 10px 5px;
  margin: 5px;
  margin-bottom: 20px;
  box-shadow: 5px 5px 5px gray;
  border: 1px black solid;
}
.post-it h4 {
  text-align: center;
  margin: 0;
}
<table>
  <tr>
    <th>To Do</th>
    <th>In Development</th>
    <th>Done</th>
  </tr>

  <tr>

    <td id="todo" ondrop="drop(event)" ondragover="allowDrop(event)">

      <div id="task1" class="post-it" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 1</h4>
        <p  draggable="false">Lorem ipsum dolor sit amet</p>
      </div>

      <div id="task2" class="post-it" draggable="true" ondragstart="drag(event)">
        <h4 draggable="false">Task 2</h4>
        <p  draggable="false">Irish skinny, grinder affogato</p>
      </div>

    </td>

    <td id="indev" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
    <td id="done" ondrop="drop(event)" ondragover="allowDrop(event)"></td>
  </tr>
</table>

Happy Coding :D

本文标签: javascriptHow to prevent drop into a div elementStack Overflow