实现鼠标移动时背景图片去模糊效果(参考Canva注册页)
实现Canva风格鼠标移动背景去模糊效果
我帮你完善并梳理这个效果的实现逻辑,先从你现有代码的小问题入手,再补全核心的背景模糊交互功能:
首先,你的distance函数没写完,先补全它:
function distance(x1, y1, x2, y2) { var a = x1 - x2; var b = y1 - y2; return Math.sqrt(a * a + b * b); }
接下来,要实现Canva那种「鼠标划过区域背景从模糊变清晰」的效果,核心思路是:
- 底层放清晰的背景图
- 上层放模糊的背景遮罩层
- 用Canvas覆盖在最上层,通过鼠标移动绘制的路径,把上层的模糊遮罩“擦除”,露出底层的清晰背景
完整实现代码
HTML结构
<div class="bg-container"> <div class="bg-clear"></div> <div class="bg-blur"></div> <canvas id="log"></canvas> </div>
CSS样式
.bg-container { position: fixed; top: 0; left: 0; width: 100vw; height: 100vh; overflow: hidden; } .bg-clear, .bg-blur { position: absolute; width: 100%; height: 100%; background-image: url('你的清晰背景图地址'); /* 替换成你的背景图 */ background-size: cover; background-position: center; } .bg-blur { filter: blur(8px); /* 模糊程度,可根据需求调整 */ } #log { position: absolute; top: 0; left: 0; width: 100%; height: 100%; cursor: crosshair; /* 关键:让Canvas的绘制内容作为遮罩,擦除上层模糊层 */ mix-blend-mode: destination-out; }
JavaScript逻辑
var canvas, ctx, prevX = 0, currX = 0, prevY = 0, currY = 0; function init() { canvas = document.getElementById('log'); ctx = canvas.getContext("2d"); // 适配窗口大小 resizeCanvas(); window.addEventListener('resize', resizeCanvas); // 鼠标移动事件处理 canvas.addEventListener('mousemove', function(e) { currX = e.clientX; currY = e.clientY; // 计算鼠标移动距离,动态调整线条宽度 var d = distance(prevX, prevY, currX, currY); // 移动越慢线条越宽,移动越快线条越窄,贴合Canva的自然效果 var lineWidth = d > 0 ? Math.min(80 / d, 60) : 60; ctx.beginPath(); // 用圆形衔接路径起点,让轨迹更顺滑 ctx.arc(prevX, prevY, lineWidth / 2, 0, Math.PI * 2); ctx.fill(); // 绘制鼠标移动的轨迹线条 ctx.moveTo(prevX, prevY); ctx.lineTo(currX, currY); ctx.lineCap = "round"; ctx.lineWidth = lineWidth; ctx.stroke(); prevX = currX; prevY = currY; }); // 鼠标离开窗口时重置位置,避免回到窗口时出现突兀线条 canvas.addEventListener('mouseleave', function() { prevX = currX = 0; prevY = currY = 0; }); } function distance(x1, y1, x2, y2) { var a = x1 - x2; var b = y1 - y2; return Math.sqrt(a * a + b * b); } function resizeCanvas() { canvas.width = window.innerWidth; canvas.height = window.innerHeight; // 重置Canvas状态,确保窗口大小变化后效果正常 ctx.globalCompositeOperation = 'source-over'; ctx.fillStyle = '#fff'; ctx.fillRect(0, 0, canvas.width, canvas.height); ctx.globalCompositeOperation = 'destination-out'; } // 页面加载完成后初始化效果 window.onload = init;
关键细节解释
- CSS的
mix-blend-mode: destination-out:这是实现擦除效果的核心,Canvas上绘制的内容会把上层的模糊背景层“挖掉”,从而露出底层的清晰背景。 - 动态线条宽度:通过计算鼠标移动的距离,让快速移动时线条更窄、慢速移动时更宽,模拟Canva那种自然的跟随手感。
- 窗口适配:监听窗口
resize事件,实时调整Canvas尺寸,保证效果在窗口大小变化时依然正常显示。
内容的提问来源于stack exchange,提问作者Yuki.kuroshita
相关产品推荐
相关产品推荐

