JSFiddle - React, Tailwind, and code Playground

by Aksel B.

HTML

<div class="dTime" style="display: flex; justify-content: flex-end; gap: 10px; margin-right: 20px;"></div>
<div class="cat"><span>Box 1 </span><span>Box 2 </span></div>
<div style="width: 100%">
<div class="droppable">


<div class="draggable" draggable="true">
<div class="handle">handle1</div><br />
<div class="content">content1 </div>
</div>

<div class="draggable" draggable="true">
  <div class="handle">handle2</div><br />
  <div class="content">content2 </div>
</div>


<div class="draggable" draggable="true">
  <div class="handle">handle3</div><br />
  <div class="content">content3 </div>
</div>

</div>

<div class="droppable">


<div class="draggable" draggable="true">
  <div class="handle">handle4</div><br />
  <div class="content">content4 </div>
</div>

<div class="draggable" draggable="true">
  <div class="handle">handle5</div><br />
  <div class="content">content5 </div>
</div>


<div class="draggable" draggable="true">
  <div class="handle">handle6</div><br />
  <div class="content">content6 </div>
</div>


<div class="draggable" draggable="true">
  <div class="handle">handle7</div><br />
  <div class="content">content7 </div>
</div>


</div>
</div>

CSS

* {
  margin: 0;
  padding: 0;
  font-family: "Open Sans", sans-serif;
}

::-webkit-scrollbar {
  width: 6px;
}

::-webkit-scrollbar-track {
  background-color: #f1f1f1;
}

::-webkit-scrollbar-thumb {
  background-color: #c0c0c0;
}

body {
  vertical-align: top;
  background: #AAA;
}

.droppable {
  border: 1px solid #EEE;
  border-radius: 0.5rem;
  overflow: auto;
}

.droppable:first-child {
  width: 40%;
}

.droppable:nth-child(2) {
	width: 40%;
  max-width: 700px;
  border: 2px solid #F00;
  overflow: auto;
  height: 800px;
}

h3 {
  color: #FFF;
  font-weight: normal;
  font-size: 1.2rem;
}

div.btns {
  display: flex;
  justify-content: flex-end;
  align-items: flex-end;
  align-content: space-around;
  gap: 10px;
  padding: 0px 30px;
}

.shadow {
  -webkit-box-shadow: 6px 8px 6px -6px black;
  -moz-box-shadow: 6px 8px 6px -6px black;
  box-shadow: 6px 8px 6px -6px black;
}

.btn1 {
  cursor: pointer;
  border-radius: 0.5rem;
}

a:link {
  color: #333;
  text-decoration: none;
}

div.cat {
  color: #FFF;
  width: 100%;
  height: 30px;
  display: flex;
  justify-content: space-around;
  font-style: italic;
}

.draggable {
  margin: 1rem 1rem;
  min-width: 10rem;
  max-width: 10rem;
  min-height: 9rem;
  cursor: move;
  display: inline-block;
  padding: 5px;
  text-align: center;
  font-size: 1rem;
  color: #e9550c;
  background-color: rgba(240, 240, 240, 0.7);
  border: 1px solid #CCC;
  border-radius: 0.5rem;
  transition: var(--transitionTime);
}

.dragging {
  opacity: 0.5;
}

div {
  display: inline-block;
  vertical-align: top;
}

.new-added {
  animation: insert var(--transitionTime) linear;
}

.will-remove {
  animation: remove var(--transitionTime) linear;
  animation-fill-mode: forwards;
}

@keyframes insert {
  from {
    max-height: 0;
  }
  to {
    max-height: 10vh;
  }
}

@keyframes remove {
  from {
    max-height: 100vh;
  }
  to {
    max-height: 0;
    opacity: 0;
  }
}
.handle {
  background: #FEF;
  width: 100%;
  border: 1px solid #333;
}

JavaScript

const droppables = document.querySelectorAll('.droppable');
const draggables = document.querySelectorAll('.draggable');
const transitionTime = 500;
let dragging;
let cloned;

document.body.style.setProperty('--transitionTime', transitionTime + 'ms');

function cleanClass(className) {
  const elements = document.querySelectorAll(`.${className}`);
  for (const el of elements) {
    el.classList.remove(className);
  }
}

function delCookie() {
  setCookie('cBrowser','','Fri, 02 Jan 1970 00:00:00 UTC');
  setCookie('cCode','','Fri, 02 Jan 1970 00:00:00 UTC');
  setCookie('cZeit','','Fri, 02 Jan 1970 00:00:00 UTC');
  setCookie('cHost','','Fri, 02 Jan 1970 00:00:00 UTC');
  setCookie('cVers','','Fri, 02 Jan 1970 00:00:00 UTC');
  window.location.href='./srv/inc/logout.php';
}

// drag start
document.addEventListener('dragstart', e => {
  if (e.target.classList.contains('draggable')) {
    dragging = e.target;
    dragging.classList.add('dragging');
    cloned = dragging.cloneNode(true);
  }
});

//document.addEventListener(eventName, function (e) {
//  // loop parent nodes from the target to the delegation node
//  for (var target = e.target; target && target != this; target = target.parentNode) {
//    if (target.matches(elementSelector)) {
//      handler.call(target, e);
//      break;
//    }
//  }
//}, false);

function handleDragEnd() {
  if (!dragging) return;
  dragging.classList.add('will-remove');
  setTimeout(() => {
    dragging.remove();
    cleanClass('dragging');
  }, [transitionTime]);
}

// drag end
document.addEventListener('dragend', e => {
  cleanClass('dragging');
  cleanClass('new-added');
});

// drag over
droppables.forEach(droppable => {
  droppable.addEventListener('dragover', e => {
    e.preventDefault();
    // In the column to be moved to, the closest element in front of dragging
    const frontSib = getClosestFrontSibling(droppable, e.clientY);
    // dragging the previous element currently in the DOM tree
    const previousSib =...