반응형

Drag and Drop(끌어서 놓기) 기능은 웹 애플리케이션에서 자주 사용되는 인터랙션 방식 중 하나입니다. 특히 사용자 경험을 개선하고 직관적인 UI를 제공하는 데 유용합니다. 이번 글에서는 JavaScript를 사용해 Drag and Drop 기능을 구현하는 방법과 다양한 예제를 다룹니다.


1. Drag and Drop의 기본 개념

HTML5 Drag and Drop API는 다음과 같은 주요 이벤트와 속성으로 구성됩니다:

주요 이벤트

  1. dragstart: 드래그를 시작할 때 발생.
  2. drag: 드래그 중에 지속적으로 발생.
  3. dragend: 드래그가 끝날 때 발생.
  4. dragenter: 드래그 중인 요소가 드롭 가능한 영역에 들어올 때 발생.
  5. dragover: 드롭 가능한 영역 위에서 발생.
  6. dragleave: 드래그 중인 요소가 드롭 가능한 영역에서 나갈 때 발생.
  7. drop: 드롭 가능한 영역에 요소를 놓을 때 발생.

주요 속성

  • draggable: HTML 요소를 드래그 가능하게 설정.
  • dataTransfer: 드래그된 데이터의 전송을 처리.

2. 기본 Drag and Drop 예제

HTML 구조

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Drag and Drop Example</title>
  <style>
    .draggable {
      width: 100px;
      height: 100px;
      background-color: lightblue;
      margin: 10px;
      text-align: center;
      line-height: 100px;
      border: 1px solid navy;
      cursor: grab;
    }

    .dropzone {
      width: 300px;
      height: 300px;
      background-color: lightgray;
      border: 2px dashed darkgray;
      display: flex;
      justify-content: center;
      align-items: center;
    }
  </style>
</head>
<body>
  <div id="dragItem" class="draggable" draggable="true">Drag me</div>
  <div id="dropZone" class="dropzone">Drop here</div>

  <script>
    const dragItem = document.getElementById('dragItem');
    const dropZone = document.getElementById('dropZone');

    // 드래그 시작 이벤트
    dragItem.addEventListener('dragstart', (e) => {
      e.dataTransfer.setData('text/plain', dragItem.id);
      e.dataTransfer.effectAllowed = 'move';
    });

    // 드롭 영역 위로 이동 중
    dropZone.addEventListener('dragover', (e) => {
      e.preventDefault(); // 기본 동작을 막아야 drop 이벤트가 동작
      e.dataTransfer.dropEffect = 'move';
    });

    // 드롭 이벤트 처리
    dropZone.addEventListener('drop', (e) => {
      e.preventDefault();
      const data = e.dataTransfer.getData('text/plain');
      const draggableElement = document.getElementById(data);
      dropZone.appendChild(draggableElement);
      alert('Item dropped successfully!');
    });
  </script>
</body>
</html>

설명

  1. draggable="true": 드래그 가능 요소로 설정합니다.
  2. dragstart 이벤트: 드래그 시작 시 전송할 데이터를 설정합니다.
  3. dragover 이벤트: 드롭 영역 위에서 기본 동작을 막아 드롭 가능하도록 설정합니다.
  4. drop 이벤트: 드래그된 요소를 드롭 영역에 추가합니다.

3. 여러 요소 드래그 앤 드롭

HTML 구조

<div class="draggable" draggable="true" id="item1">Item 1</div>
<div class="draggable" draggable="true" id="item2">Item 2</div>
<div class="draggable" draggable="true" id="item3">Item 3</div>
<div id="dropZone" class="dropzone">Drop items here</div>

JavaScript 코드

const draggables = document.querySelectorAll('.draggable');
const dropZone = document.getElementById('dropZone');

draggables.forEach(item => {
  item.addEventListener('dragstart', (e) => {
    e.dataTransfer.setData('text/plain', item.id);
  });
});

dropZone.addEventListener('dragover', (e) => {
  e.preventDefault();
});

dropZone.addEventListener('drop', (e) => {
  e.preventDefault();
  const data = e.dataTransfer.getData('text/plain');
  const draggableElement = document.getElementById(data);
  dropZone.appendChild(draggableElement);
});

결과

여러 개의 드래그 가능한 요소를 동일한 드롭 영역에 드롭할 수 있습니다.


4. 스타일 동적 변경

드래그 중에 드롭 영역의 스타일을 변경하여 시각적 피드백을 제공합니다.

JavaScript 코드

const dropZone = document.getElementById('dropZone');

dropZone.addEventListener('dragenter', () => {
  dropZone.style.backgroundColor = 'lightgreen';
});

dropZone.addEventListener('dragleave', () => {
  dropZone.style.backgroundColor = 'lightgray';
});

결과

드롭 가능한 영역으로 드래그가 들어가거나 나갈 때 배경색이 변경됩니다.


5. 이미지와 데이터 전송

이미지와 함께 사용자 정의 데이터를 전송할 수도 있습니다.

HTML 구조

<img id="dragImage" src="example.jpg" draggable="true" alt="Example Image" style="width: 100px;">
<div id="dropZone" class="dropzone">Drop image here</div>

JavaScript 코드

const dragImage = document.getElementById('dragImage');

dragImage.addEventListener('dragstart', (e) => {
  e.dataTransfer.setData('text/plain', 'This is an example image.');
});

dropZone.addEventListener('drop', (e) => {
  e.preventDefault();
  const data = e.dataTransfer.getData('text/plain');
  alert(data);
});

결과

이미지를 드래그하여 드롭하면 사용자 정의 데이터가 알림으로 표시됩니다.


6. 정렬 기능 구현

목록의 순서를 드래그 앤 드롭으로 변경할 수 있습니다.

HTML 구조

<ul id="sortableList">
  <li draggable="true">Item 1</li>
  <li draggable="true">Item 2</li>
  <li draggable="true">Item 3</li>
</ul>

JavaScript 코드

const items = document.querySelectorAll('#sortableList li');
let draggedItem = null;

items.forEach(item => {
  item.addEventListener('dragstart', (e) => {
    draggedItem = item;
    setTimeout(() => item.style.display = 'none', 0);
  });

  item.addEventListener('dragend', () => {
    setTimeout(() => draggedItem.style.display = 'block', 0);
    draggedItem = null;
  });

  item.addEventListener('dragover', (e) => {
    e.preventDefault();
  });

  item.addEventListener('drop', (e) => {
    e.preventDefault();
    if (item !== draggedItem) {
      const list = draggedItem.parentNode;
      list.insertBefore(draggedItem, item.nextSibling);
    }
  });
});

결과

목록 항목을 드래그하여 순서를 변경할 수 있습니다.


마무리

Drag and Drop 기능은 사용자 경험을 향상시키는 데 유용합니다. 기본 API를 활용한 다양한 예제를 통해 실전 프로젝트에서 유연하게 적용해 보세요.

반응형

+ Recent posts