使用 Pointer Events
Baseline 广泛可用 *
本指南演示如何使用 pointer events 和 HTML <canvas> 元素构建支持多点触控的绘图应用程序。此示例基于 touch events overview 中的示例,但它使用了 pointer events 输入事件模型。另一个不同之处在于,由于 pointer events 是设备无关的,因此该应用程序使用相同的代码接受来自鼠标、笔或指尖的基于坐标的输入。
此应用程序仅在支持 pointer events 的浏览器中运行。
定义
- Surface
-
一个支持触摸的表面。这可能是一个触摸板、触摸屏,甚至是用户桌面表面(或鼠标垫)与物理屏幕的虚拟映射。
- Touch point
-
与表面的接触点。这可能是一个手指(或肘部、耳朵、鼻子,任何东西,但通常是手指)、手写笔、鼠标,或任何其他用于在表面上指定单个点的方法。
示例
注意: 下面的文本在描述与表面的接触时使用了“手指”一词,但当然也可以是手写笔、鼠标或其他指向某个位置的方法。
Drawing application
HTML
HTML 由一个单独的 <canvas> 元素组成。曲线将根据用户的触摸手势绘制。还包含一个用于清除画布的按钮。
html
<canvas id="canvas" width="600" height="600">
Your browser does not support the canvas element.
</canvas>
<button id="clear">Clear canvas</button>
CSS
设置了 touch-action 属性为 none,以防止浏览器对应用程序应用其默认的触摸行为。
css
#canvas {
border: solid black 1px;
touch-action: none;
display: block;
}
JavaScript
我们将跟踪所有正在进行的触摸,并为每个触摸绘制线条。colors 用于区分不同的手指。
js
const canvas = document.getElementById("canvas");
const ctx = canvas.getContext("2d");
// Mapping from the pointerId to the current finger position
const ongoingTouches = new Map();
const colors = ["red", "green", "blue"];
handleStart 函数监听 pointerdown 事件,并在触摸开始时绘制一个圆圈。
js
function handleStart(event) {
const touch = {
pageX: event.pageX,
pageY: event.pageY,
color: colors[ongoingTouches.size % colors.length],
};
ongoingTouches.set(event.pointerId, touch);
ctx.beginPath();
ctx.arc(touch.pageX, touch.pageY, 4, 0, 2 * Math.PI, false);
ctx.fillStyle = touch.color;
ctx.fill();
}
canvas.addEventListener("pointerdown", handleStart);
handleEnd 函数监听 pointerup 事件,并在触摸结束时绘制一个正方形。
js
function handleEnd(event) {
const touch = ongoingTouches.get(event.pointerId);
if (!touch) {
console.error(`End: Could not find touch ${event.pointerId}`);
return;
}
ctx.lineWidth = 4;
ctx.fillStyle = touch.color;
ctx.beginPath();
ctx.moveTo(touch.pageX, touch.pageY);
ctx.lineTo(event.pageX, event.pageY);
ctx.fillRect(event.pageX - 4, event.pageY - 4, 8, 8);
ongoingTouches.delete(event.pointerId);
}
canvas.addEventListener("pointerup", handleEnd);
handleCancel 函数监听 pointercancel 事件,并停止跟踪触摸。
js
function handleCancel(event) {
const touch = ongoingTouches.get(event.pointerId);
if (!touch) {
console.error(`Cancel: Could not find touch ${event.pointerId}`);
return;
}
ongoingTouches.delete(event.pointerId);
}
canvas.addEventListener("pointercancel", handleCancel);
handleMove 函数监听 pointermove 事件,并在触摸的开始和结束之间绘制一条线。
js
function handleMove(event) {
const touch = ongoingTouches.get(event.pointerId);
// Event was not started
if (!touch) {
return;
}
ctx.beginPath();
ctx.moveTo(touch.pageX, touch.pageY);
ctx.lineTo(event.pageX, event.pageY);
ctx.lineWidth = 4;
ctx.strokeStyle = touch.color;
ctx.stroke();
const newTouch = {
pageX: event.pageX,
pageY: event.pageY,
color: touch.color,
};
ongoingTouches.set(event.pointerId, newTouch);
}
canvas.addEventListener("pointermove", handleMove);
最后,添加清除功能。
js
document.getElementById("clear").addEventListener("click", () => {
ctx.clearRect(0, 0, canvas.width, canvas.height);
});
规范
| 规范 |
|---|
| 指针事件 # pointerevent-interface |
浏览器兼容性
加载中…