如何在Safari中禁用垂直滑块弹跳效果同时允许页面滚动
Safari垂直滑块禁用弹跳且允许后续页面滚动的解决方案
直接上可行方案,分两种场景适配:
适配Safari 16.4+(支持overscroll-behavior)
利用动态切换overscroll-behavior-y属性,只有滑块在非边界位置时禁用弹跳,到达边界时恢复默认滚动行为,让滚动事件传递给页面。
CSS 基础样式
.slider-container { overflow-y: scroll; height: 400px; /* 按实际需求设置滑块高度 */ }
JavaScript 逻辑
const slider = document.querySelector('.slider-container'); slider.addEventListener('scroll', () => { const isAtTop = slider.scrollTop === 0; const isAtBottom = slider.scrollTop + slider.clientHeight >= slider.scrollHeight; slider.style.overscrollBehaviorY = isAtTop || isAtBottom ? 'auto' : 'none'; });
原理:滑块滚动时实时检测位置,非边界时禁用弹跳,到达顶部/底部时恢复默认,此时继续滑动会触发页面的滚动。
适配旧版Safari(不支持overscroll-behavior)
通过监听触摸事件,判断滑动方向和滑块位置,仅在滑块未到边界时阻止默认触摸行为,禁用弹跳;到达边界时允许事件冒泡,让页面滚动。
JavaScript 逻辑
let startY; const slider = document.querySelector('.slider-container'); slider.addEventListener('touchstart', (e) => { startY = e.touches[0].clientY; }); slider.addEventListener('touchmove', (e) => { const currentY = e.touches[0].clientY; const deltaY = currentY - startY; // 正数为向下滑,负数为向上滑 const isAtTop = slider.scrollTop === 0; const isAtBottom = slider.scrollTop + slider.clientHeight >= slider.scrollHeight; // 已在顶部且向下滑,或已在底部且向上滑,允许页面滚动,不阻止事件 if ((deltaY > 0 && isAtTop) || (deltaY < 0 && isAtBottom)) { return; } // 其他情况阻止默认触摸行为,禁用弹跳 e.preventDefault(); }, { passive: false }); // 必须设置passive: false才能调用preventDefault
注意:这种方式需要确保滑块容器的touch-action属性没有被其他样式覆盖,若有冲突可添加touch-action: pan-y;到滑块CSS中。
内容的提问来源于stack exchange,提问作者Poetiq
相关产品推荐
相关产品推荐

