JavaScript运动框架:解决防抖动问题与悬浮对联实现
本文详解JavaScript运动框架在解决防抖动问题中的应用。通过解析scrollTop与offsetTop属性,分析小数目标值导致的抖动原因,并给出取整解决方案。结合代码实例,实现网页滚动时右侧悬浮对联的缓冲运动效果,提升视觉体验。
JavaScript运动框架应用概述
本文实例展示了对JavaScript运动框架(一)中内容的具体应用。
关于scrollTop:当网页内容高度超过显示器可视区域时,页面会出现滚动条。此时,向上滚动的距离即为scrollTop值。
获取scrollTop的标准写法为:var scrollTop = document.documentElement.scrollTop || document.body.scrollTop;
关键属性scrollTop与offsetTop解析
关于offsetTop:该属性用于获取元素上外边缘距离最近的一个已定位(position值为relative、absolute或fixed)父元素内壁的距离。若父元素均未定位,则获取距离文档内壁的距离。

如图所示,黑色框代表整个网页文档,其总高度可通过document.documentElement.scrollHeight获取。
绿色框表示当前可见的客户区部分(不含工具栏和状态栏),红色框则是需要固定在客户区右侧中央的对联元素。若网页高度很大,用户滚动页面时,要求对联以缓冲运动的形式保持在客户区右侧中央。虽然position:fixed可以稳定固定元素,但我们需要实现的是运动到目标位置的效果。
我们希望元素最终能运动并停留在目标位置。
实现方式主要有两种:1. 直接计算好位置并硬赋值;2. 通过缓冲运动到达目标位置,视觉效果更柔和。通常不采用第一种硬赋值方式,因为视觉效果生硬,体验较差。
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>运动框架(二)</title>
<style type="text/css">
* {
padding: 0;
margin: 0;
}
#div1 {
width: 100px;
height: 200px;
background: orange;
position: absolute;
right: 0;
}
</style>
</head>
<body style="height: 30000000px;">
<div id="div1"></div>
<script type="text/javascript">
var oDiv = document.getElementById('div1');
var timer = null;
window.onscroll = function() {
//每次滚动网页,都要重新计算目标值,当前值就是offsetTop
var scrollTop = document.documentElement.scrollTop || document.body.scrollTop;
var target = (document.documentElement.clientHeight - oDiv.offsetHeight)/2 + scrollTop;
//下面是硬赋值,计算好位置后,直接将值付给style.top,太生硬
//oDiv.style.top = target;
startMove(target);
};
function startMove(iTarget) {
clearInterval(timer);
timer = setInterval(function() {
var speed = (iTarget - oDiv.offsetTop) / 10;
speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed);
if (iTarget == oDiv.offsetTop) {
clearInterval(timer);
} else {
oDiv.style.top = oDiv.offsetTop + speed + 'px';
document.title = iTarget + ',' + oDiv.offsetTop;
}
}, 30);
}
</script>
</body>
</html>
防抖动问题的成因与解决方案
然而,直接运行结果会出现问题:对联不停地上下抖动,即offsetTop的值在两个整数之间来回跳变,如下图所示。


观察上述图片中的title显示,计算出的目标值为小数267.5px,即对联最终style.top应停留的值。此时speed = (267.5 - 267)/10 → 1,元素跨1px到达268;接着speed = (267.5 - 268)/10 → -1,元素退1px回到267。由于上一篇文章中规定速度只能取整,且计算机不处理小数像素,导致元素始终无法到达267.5的目标值,从而陷入“跨一步过界,退一步过头”的僵持状态,产生抖动。解决方法很简单:不允许目标值为小数,需进行取整处理。
原始代码为:var target = (document.documentElement.clientHeight - oDiv.offsetHeight)/2 + scrollTop;
修改后的代码如下:
var target = parseInt((document.documentElement.clientHeight - oDiv.offsetHeight)/2 + scrollTop);
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持本站。
JavaScript入门书籍避坑:这些书不适合初学者
2026-11-05 16:31:15
JS使用Math.round实现保留两位小数的原理与代码
2026-11-05 15:35:55
JavaScript 原生 Date 对象怎么实现日期加减
2026-11-05 14:30:00
JavaScript函数定义的三种方式:声明、表达式与箭头函数
2026-11-05 13:50:55
JavaScript中escape、encodeURI和encodeURIComponent对空格的处理差异
2026-11-05 12:47:23
