在网页交互开发中,滚轮操作是用户高频使用的交互方式,除了默认的页面滚动行为,我们常常需要基于滚轮事件实现自定义交互,比如图片缩放、横向滚动切换、自定义滚动动画等。HTML原生的wheel事件可以精准捕获用户的滚轮操作,通过监听该事件可以获取滚动方向、滚动距离等关键信息,进而实现灵活的页面滚动控制。

wheel事件基础认知
wheel事件是当用户滚动鼠标滚轮、触摸板滑动或者使用其他滚动设备时触发的事件,它替代了早期的mousewheel事件,拥有更好的标准化支持。该事件的事件对象包含多个关键属性,用于描述滚动的具体信息:
- deltaX:水平方向的滚动距离,正值表示向右滚动,负值表示向左滚动
- deltaY:垂直方向的滚动距离,正值表示向下滚动,负值表示向上滚动
- deltaMode:滚动距离的单位,0表示像素,1表示行,2表示页
基础滚轮事件监听实现
我们可以通过addEventListener方法给目标元素添加wheel事件监听,最基础的监听代码如下:
// 监听整个document的滚轮事件
document.addEventListener('wheel', function(event) {
// 阻止默认滚动行为,方便测试自定义逻辑
event.preventDefault();
// 打印滚动相关信息
console.log('垂直滚动距离:', event.deltaY);
console.log('水平滚动距离:', event.deltaX);
console.log('距离单位:', event.deltaMode);
}, { passive: false });
需要注意的是,wheel事件的默认行为是触发页面滚动,如果我们需要自定义滚动逻辑,通常需要调用event.preventDefault()阻止默认行为。另外,现代浏览器为了优化滚动性能,默认将wheel事件的passive属性设为true,此时调用preventDefault会报错,所以需要在监听时显式设置{ passive: false }。
实现自定义页面滚动控制
基于wheel事件,我们可以实现完全自定义的页面滚动效果,比如控制滚动速度、添加滚动动画、实现横向滚动等。以下是一个自定义垂直滚动控制的示例,滚动时页面会以动画形式平滑移动,而不是默认的瞬移效果:
// 自定义滚动速度系数,值越大滚动越快
const scrollSpeed = 0.5;
// 当前滚动位置
let currentScrollTop = document.documentElement.scrollTop || document.body.scrollTop;
// 目标滚动位置
let targetScrollTop = currentScrollTop;
// 是否正在执行滚动动画
let isScrolling = false;
// 监听wheel事件
document.addEventListener('wheel', function(event) {
event.preventDefault();
// 根据滚轮方向计算目标滚动位置,deltaY为正表示向下滚动
targetScrollTop += event.deltaY * scrollSpeed;
// 限制滚动范围,不能超过页面最大滚动距离
const maxScrollTop = document.documentElement.scrollHeight - document.documentElement.clientHeight;
targetScrollTop = Math.max(0, Math.min(targetScrollTop, maxScrollTop));
// 如果没有在执行动画,启动动画
if (!isScrolling) {
isScrolling = true;
requestAnimationFrame(smoothScroll);
}
}, { passive: false });
// 平滑滚动动画函数
function smoothScroll() {
// 计算当前位置和目标位置的差值,使用缓动效果
const diff = targetScrollTop - currentScrollTop;
// 当差值小于1像素时,直接设置到目标位置,结束动画
if (Math.abs(diff) < 1) {
currentScrollTop = targetScrollTop;
document.documentElement.scrollTop = currentScrollTop;
document.body.scrollTop = currentScrollTop;
isScrolling = false;
return;
}
// 缓动计算,每次移动差值的10%
currentScrollTop += diff * 0.1;
document.documentElement.scrollTop = currentScrollTop;
document.body.scrollTop = currentScrollTop;
// 继续下一帧动画
requestAnimationFrame(smoothScroll);
}
实现横向滚动控制
如果需要实现横向滚动效果,只需要基于deltaY或者deltaX计算水平方向的滚动位置即可,以下是横向滚动的示例代码:
// 获取横向滚动的容器,这里假设容器id为horizontalContainer
const container = document.getElementById('horizontalContainer');
// 自定义横向滚动速度
const horizontalScrollSpeed = 1;
container.addEventListener('wheel', function(event) {
event.preventDefault();
// 使用deltaY控制横向滚动,向下滚动时容器向右滚动
container.scrollLeft += event.deltaY * horizontalScrollSpeed;
}, { passive: false });
常见问题与注意事项
兼容性问题
虽然wheel事件已经被所有现代浏览器支持,但在一些旧版本浏览器中可能存在差异,如果需要兼容旧浏览器,可以同时监听mousewheel事件作为降级方案,mousewheel事件的事件对象使用event.wheelDelta获取滚动距离,正值表示向上滚动,负值表示向下滚动。
性能优化
wheel事件触发频率很高,如果在事件处理函数中执行复杂逻辑,容易导致页面卡顿。建议将复杂计算放到requestAnimationFrame中执行,或者对事件处理函数进行节流处理,避免短时间内多次执行重复逻辑。
滚动边界处理
自定义滚动时一定要注意边界判断,避免滚动位置超出元素的可滚动范围,导致出现空白区域或者滚动失效的问题。计算边界时需要结合元素的scrollHeight、clientHeight、scrollWidth、clientWidth等属性。
注意:如果页面中同时存在默认滚动和自定义滚动逻辑,需要明确区分触发场景,避免滚动行为冲突,比如可以在特定区域内启用自定义滚动,其他区域保留默认滚动行为。
wheel_eventHTML滚动控制页面滚动监听滚轮事件处理修改时间:2026-06-28 14:39:21