刮刮卡
实现步骤
- 创建 canvas 蒙层,监听鼠标和触屏事件
- 定义擦除事件,做下节流
- 判断刮刮卡完成
核心代码
擦除的关键是 globalCompositeOperation = "destination-out",让绘制的笔触「擦掉」已有像素(变透明),露出下层奖品:
const ctx = canvas.getContext("2d");
// 1. 铺一层灰色蒙层
ctx.fillStyle = "#c0c0c0";
ctx.fillRect(0, 0, canvas.width, canvas.height);
// 2. 设置为擦除模式
ctx.globalCompositeOperation = "destination-out";
let isDrawing = false;
function scratch(x, y) {
ctx.beginPath();
ctx.arc(x, y, 20, 0, Math.PI * 2); // 笔触半径 20
ctx.fill();
}
canvas.addEventListener("mousedown", () => (isDrawing = true));
canvas.addEventListener("mouseup", () => (isDrawing = false));
canvas.addEventListener("mousemove", (e) => {
if (!isDrawing) return;
const rect = canvas.getBoundingClientRect();
scratch(e.clientX - rect.left, e.clientY - rect.top); // 注意坐标换算
});
判断刮开完成
用 getImageData 统计透明像素(alpha = 0)占比,超过阈值(如 50%)就视为刮完,可直接清空整个蒙层:
function getClearPercent() {
const { data } = ctx.getImageData(0, 0, canvas.width, canvas.height);
let cleared = 0;
for (let i = 3; i < data.length; i += 4) {
if (data[i] === 0) cleared++; // alpha 通道
}
return cleared / (data.length / 4);
}
统计像素较耗时,应在
mouseup时或节流后再算,不要每次 move 都算。
功能要点
- 画布操作:刮刮卡通常是通过在画布上涂抹来实现效果的。在实现刮刮卡功能时,需要处理画布的绘制、涂抹操作以及刮开后的效果展示。
- 性能优化:涂抹的效果需要有流畅的交互体验,这就需要考虑到性能优化的问题,尤其是针对移动设备的性能优化。
- 响应式设计:刮刮卡功能需要能够适配不同屏幕尺寸和设备类型,因此需要考虑响应式设计和移动端适配的问题。
- 安全性:在刮刮卡中,需要确保用户无法通过非正常手段提前看到刮开后的内容,这需要在实现上考虑安全性。
- 用户体验:良好的用户体验是实现刮刮卡功能的关键,需要考虑动画效果、触摸交互、反馈等方面,以提供令人满意的体验。
总的来说,实现刮刮卡功能需要综合考虑到画布操作、性能优化、响应式设计、安全性和用户体验等多个方面的技术挑战