今天我们一起来用 JavaScript 实现一个回到顶部的功能。
首先,需要梳理一下我们需求:
- 在页面的右下角有一个"回到顶部"的按钮
- 点击这个按钮不是直接回到顶部而是要以渐慢的速度回到顶部
- 在回到顶部的滚动中如果用户滑动鼠标的滚动轮则停止回到顶部的滚动效果
- 只有在滚动超过页面可视窗口高度之后才显示"回到顶部"的按钮,否则隐藏"回到顶部"按钮
首先先写出最基本的 HTML 结构:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>js 回到顶部</title>
<style media="screen">
body,html {
margin: 0;
padding: 0;
}
#box {
width: 1190px;
margin: 0 auto;
}
#box > div {
background-color: #eee;
height: 10000px;
}
#btn {
height: 30px;
width: 100px;
background-color: #eee;
position: fixed;
right: 0px;
bottom: 40px;
-webkit-transition: background-color 1s;
-o-transition: background-color 1s;
transition: background-color 1s;
}
#btn:hover {
background-color: #ff0;
cursor: pointer;
}
</style>
</head>
<body>
<div id="box">
<div>用来撑开空间高度</div>
</div>
<div id="btn">回到顶部</div>
</body>
<script type="text/javascript">
/* 这里添加 js 代码 */
</script>
</html>
本文主要实现功能,css 这块不太好看希望谅解 _
接下来要实现点击"回到顶部"的执行事件
第一步呢,先实现点击按钮直接向上滚动 200 像素的效果
window.onload = function() {
var obtn = document.getElementById('btn');
obtn.onclick = function() {
// 获取当前视图最上方距这个内容区最顶部的距离(也就是已经滚动的距离)
var osTop = document.documentElement.scrollTop || document.body.scrollTop;
// 其实这里写法并不好
document.body.scrollTop = document.documentElement.scrollTop -= 200;
}
}
第二步,给上面这个向上滚动 200 像素的动作添加一个定时器自动执行,就实现了一个缓慢向上滚动到顶部的效果,注意当滚动到顶部的时候需要清除计时器。
第三步,改变这个 200 像素的值,速度的值应该是越靠顶部越慢的,所以还需要计算这个值。
下面是这部分的代码
var obtn = document.getElementById('btn');
// 定时器
var timer = null;
obtn.onclick = function() {
// 速度值
var speed = 0;
// 当前视图最上方距这个内容区最顶部的距离(也就是已经滚动的距离)
var osTop = 0;
timer = setInterval(function() {
osTop = document.documentElement.scrollTop || document.body.scrollTop;
// 改变回到顶部的速度(越来越慢)
// 注意此处是向上取整
speed = Math.ceil(-osTop / 2);
document.body.scrollTop = document.documentElement.scrollTop -= (osTop + speed);
if (speed === 0) {
clearInterval(timer);
}
}, 30);
}
完成到此其实基本的回到顶部的功能就已经完成了,下面就是一些优化操作。
第四步,如果在滚动回到顶部的过程中,用户滑动了鼠标的滚轮,那就停止回到顶部的滚动操作。此处我们需要调用 onmousewheel ,暂不考虑此方法的浏览器兼容性问题,代码如下:
// 监听鼠标滑轮的滚动事件
window.onmousewheel = function() {
clearInterval(timer);
}
最后一步,就是只有在滚动超过页面可视高度后才显示"回到顶部"按钮,否则隐藏该按钮,以下是代码:
#btn {
/* other code... */
display: none;
}
// 获取页面的可视窗口高度
var clientHeight = document.documentElement.clientHeight || document.body.clientHeight;
var obtn = document.getElementById('btn');
// 页面滚动时增加判断,超出页面可视化高度时显示回到顶部的按钮
window.onscroll = function() {
// 此处需要重新声明,因为和上面的 osTop 不在同一个函数域,不可忽略!
var osTop = document.documentElement.scrollTop || document.body.scrollTop;
if (osTop > clientHeight) {
obtn.style.display = 'block';
} else {
obtn.style.display = 'none';
}
}
写到此处一个回到顶部的功能就完成啦,是不是非常简单呢~
下面是完整的页面代码:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>js回到顶部</title>
<style media="screen">
body, html {
margin: 0;
padding: 0;
}
#box {
width: 1190px;
margin: 0 auto;
}
#box > div {
background-color: #eee;
height: 10000px;
}
#btn {
height: 30px;
line-height: 30px;
width: 100px;
background-color: #eee;
position: fixed;
right: 0px;
bottom: 40px;
display: none;
-webkit-transition: background-color 1s;
-o-transition: background-color 1s;
transition: background-color 1s;
}
#btn:hover {
background-color: #ff0;
cursor: pointer;
}
</style>
</head>
<body>
<div id="box">
<div>占位</div>
</div>
<div id="btn">回到顶部</div>
</body>
<script type="text/javascript">
window.onload = function() {
var obtn = document.getElementById('btn');
// 定时器
var timer = null;
// 获取页面的可视窗口高度
var clientHeight = document.documentElement.clientHeight || document.body.clientHeight;
obtn.onclick = function() {
var osTop = 0;
var speed = 0;
timer = setInterval(function() {
isScroll = true;
// 距内容区最顶部的距离
osTop = document.documentElement.scrollTop || document.body.scrollTop;
// 改变回到顶部的速度(越来越慢)
speed = Math.ceil(-osTop / 1.05);
document.body.scrollTop = document.documentElement.scrollTop -= (osTop + speed);
if (speed == 0) {
clearInterval(timer);
isScroll = false;
}
}, 30);
};
// 监听鼠标滑轮的滚动事件
window.onmousewheel = function() {
clearInterval(timer);
};
// 页面滚动时增加判断,超出页面可视化高度时显示回到顶部的按钮
window.onscroll = function() {
var osTop = document.documentElement.scrollTop || document.body.scrollTop;
if (osTop > clientHeight) {
obtn.style.display = 'block';
} else {
obtn.style.display = 'none';
}
};
};
</script>
</html>
其实这是一个非常简单的功能,也是提醒大家在使用框架的同时,这些 JavaScript 底层的功能也不要忘记,因为技术在不断的更新但是底层的知识是不会变的。