title: "Swap" using interact.js, when dragging item A from area A to area B, and area B is already populated
body: <p>Is it possible the &quot;Swap out&quot; draggable items using InteractJS, when dragging a draggable item from a &quot;origin&quot; to a &quot;target&quot; zone?</p>
  <p>I cannot find any reference in their Documentation <a href="https://interactjs.io/docs" rel="nofollow noreferrer">https://interactjs.io/docs</a> about this specific use case</p>
  <p>To explain better the situation and goal I made this rough fiddle:
  <a href="https://jsfiddle.net/09afor6w/" rel="nofollow noreferrer">https://jsfiddle.net/09afor6w/</a></p>
  <p>It has 2 draggable &quot;boxes&quot; each in a &quot;parent box&quot;. When dragging the first box to the second, the second should automatically swap locations with the first, instead of staying put, or <em>at least</em> not allow the dragged element to be superposed to the element already there.</p>
  <p>I assumed they would have a specific &quot;swap&quot; feature but it does not seem so.
  With the &quot;restrict&quot; method, I can only restrict size and area of (size and drag), but not control that no items should <em>overlap</em> and thus maybe use this as a workaround to create a &quot;swap&quot; experience.</p>
  <p>The goal behind this is creating a UI where the user can drag and drop single form elements into different places in a restricted, &quot;gridded&quot; area and resize the form elements.
  When dragging elements from A to B, the element from the target area should change location to the &quot;origin&quot; area of the dragged item, that's all.
  So if there is an easier, lighter way to do this, I am also happy to hear about.</p>
  <p>This is the code I use.
  HTML:</p>
  <pre><code>&lt;div class=&quot;contain-all&quot;&gt;
      &lt;div class=&quot;contain-some&quot;&gt;
          &lt;div class=&quot;grid-snap&quot;&gt;
            Move this box to the white target area below
          &lt;/div&gt;
      &lt;/div&gt;
      &lt;div class=&quot;contain-some&quot;&gt;
          &lt;div class=&quot;grid-snap&quot;&gt;
            This box should automatically swap place with the moved box
          &lt;/div&gt;
      &lt;/div&gt;
  &lt;/div&gt;
  </code></pre>
  <p>JS:</p>
  <pre><code>var elements = document.getElementsByClassName('grid-snap');
  $(elements).each(function(){
  var x = 0; var y = 0
      interact(this)
    .resizable({
      // resize from all edges and corners
      edges: { left: true, right: true, bottom: true, top: true },
  
      listeners: {
        move (event) {
          var target = event.target
          var x = (parseFloat(target.getAttribute('data-x')) || 0)
          var y = (parseFloat(target.getAttribute('data-y')) || 0)
  
          // update the element's style
          target.style.width = event.rect.width + 'px'
          target.style.height = event.rect.height + 'px'
  
          // translate when resizing from top or left edges
          x += event.deltaRect.left
          y += event.deltaRect.top
  
          target.style.transform = 'translate(' + x + 'px,' + y + 'px)'
  
          target.setAttribute('data-x', x)
          target.setAttribute('data-y', y)
        }
      },
      modifiers: [
        // keep the edges inside the parent
        interact.modifiers.restrictEdges({
          outer: 'parent'
        }),
  
        // minimum size
        interact.modifiers.restrictSize({
          min: { width: 100, height: 50 }
        })
      ],
  
      inertia: true
    })
    .draggable({
      listeners: { move: window.dragMoveListener },
      inertia: true,
      modifiers: [
        interact.modifiers.restrictRect({
          restriction: '#formthing',
        }),
        interact.modifiers.snap({
          targets: [
            interact.snappers.grid({ x: 30, y: 30 })
          ],
          range: Infinity,
          relativePoints: [ { x: 0, y: 0 } ]
        }),
      ]
    })
    .on('dragmove', function (event) {
      x += event.dx
      y += event.dy
  
      event.target.style.transform = 'translate(' + x + 'px, ' + y + 'px)'
    })
  });
  </code></pre>