HTML5 拖放
拖放 (Drag and Drop) 是 HTML5 中一个非常直观和强大的功能。它允许用户使用鼠标选择一个可拖动的元素,将其“拖”到指定的“放置区”并“放”下。
使元素可拖动
要让一个元素变得可以拖动,你需要将它的 draggable 属性设置为 true。
html
<img src="logo.png" draggable="true">默认情况下,只有链接和图片是可拖动的。对于其他元素,如 <div> 或 <p>,你必须显式地设置 draggable="true"。
拖放事件周期
整个拖放过程由一系列事件组成,我们可以监听这些事件来控制拖放的行为。
拖动元素上的事件
ondragstart: 当用户开始拖动元素时触发。这是整个过程的起点。ondrag: 在元素被拖动期间,此事件会持续触发。ondragend: 当用户完成拖动(无论是成功放置还是取消)时触发。
放置区域上的事件
ondragenter: 当被拖动的元素进入放置区域时触发。ondragover: 当被拖动的元素在放置区域上方移动时持续触发。ondragleave: 当被拖动的元素离开放置区域时触发。ondrop: 当被拖动的元素在放置区域上被释放时触发。这是放置操作的核心。
一个完整的拖放示例
让我们看一个将一张图片拖动到 <div> 容器中的完整例子。
HTML:
html
<div id="drop-zone" ondrop="drop(event)" ondragover="allowDrop(event)">
<p>将图片拖到这里</p>
</div>
<br>
<img id="drag-item" src="logo.png" draggable="true" ondragstart="drag(event)" width="150">CSS (用于视觉反馈):
css
#drop-zone {
width: 200px;
height: 100px;
padding: 10px;
border: 2px dashed #aaaaaa;
}JavaScript:
javascript
// 1. ondragover: 必须阻止默认行为
function allowDrop(ev) {
// 默认情况下,元素无法被放置到其他元素中。
// 为了允许放置,我们必须阻止浏览器的默认处理方式。
ev.preventDefault();
}
// 2. ondragstart: 记录被拖动的数据
function drag(ev) {
// dataTransfer.setData() 方法设置被拖动的数据类型和值。
// 在这里,我们将被拖动元素的 id ('drag-item') 保存起来。
ev.dataTransfer.setData("text", ev.target.id);
}
// 3. ondrop: 执行放置操作
function drop(ev) {
// 同样,阻止浏览器的默认行为(比如图片默认会在新标签页打开)。
ev.preventDefault();
// 使用 dataTransfer.getData() 获取在 drag() 函数中保存的数据。
var data = ev.dataTransfer.getData("text");
// 获取被拖动的元素 (id='drag-item')。
var draggedElement = document.getElementById(data);
// 将被拖动的元素追加到放置区域中。
ev.target.appendChild(draggedElement);
}代码解析
allowDrop(event): 这是最容易被忽略但至关重要的一步。默认情况下,浏览器会阻止在一个元素上进行放置操作。通过调用event.preventDefault(),我们告诉浏览器:“这个区域是有效的放置目标”。drag(event): 当拖动开始时,我们需要一种方法来“记住”我们正在拖动哪个元素。event.dataTransfer.setData("text", event.target.id)就是在做这件事。它将拖动元素的id以文本形式存储在dataTransfer对象中。drop(event): 当元素被放下时,我们首先通过event.dataTransfer.getData("text")取出之前存储的id,然后使用document.getElementById()找到这个元素,最后用appendChild()将它移动到放置区域。