jacascript 滚动 scroll 与回到顶部

时间:2022-08-01 03:35:29

前言:这是笔者学习之后自己的理解与整理。如果有错误或者疑问的地方,请大家指正,我会持续更新!

滚动 scroll

  scrollHeight 表示元素的总高度,包括由于溢出而无法展示在网页的不可见部分;

  scrollWidth 表示元素的总宽度,包括由于溢出而无法展示在网页的不可见部分;

  没有滚动条时,scroll 和 client 属性的结果相等,即 scrollWidth= padding + width; scrollHeight= padding + height;

  存在滚动条时,但元素设置宽高大于等于元素内容宽高时(没有内容溢出),scroll 和 client 属性的结果相等,滚动条是有宽度的;

  存在滚动条,但元素设置宽高小于元素内容宽高(存在内容溢出),scroll 属性大于 client 属性;

  scrollHeight 属性存在兼容性问题,chrome 和 safari 浏览器中,scrollHeight 包含 padding-bottom;而 IE 和 firefox 不包含 padding-bottom;

        <style type="text/css">
*{padding: 0;margin: 0;}
#noScroll{
width: 100px;
height: 100px;
padding: 10px;
margin: 10px;
border: 1px solid black;
}
#noOverScroll{
width: 100px;
height: 100px;
padding: 10px;
margin: 10px;
border: 1px solid black;
overflow:scroll;
font-size:20px;
line-height:1;
}
#overScroll{
width: 100px;
height: 100px;
padding: 10px;
margin: 10px;
border: 1px solid black;
overflow:scroll;
font-size:20px;
line-height:200px;
}
</style> <div id="noScroll"></div>
<div id="noOverScroll">内容</div>
<div id="overScroll">内容</div> <script>
var oNoScroll = document.getElementById('noScroll');
//没有滚动条时,scrollHeight与clientHeight属性结果相等,scrollWidth与clientWidth属性结果相等
console.log(oNoScroll.scrollHeight);//120
console.log(oNoScroll.scrollWidth);//120
console.log(oNoScroll.clientHeight);//120
console.log(oNoScroll.clientWidth);//120 var oNoOverScroll = document.getElementById('noOverScroll');
//存在滚动条时,但元素设置宽高大于等于元素内容宽高时(没有内容溢出),scroll 和 client 属性的结果相等;
//103(120-17)
console.log(oNoOverScroll.scrollHeight);//120
console.log(oNoOverScroll.scrollWidth);//120
console.log(oNoOverScroll.clientHeight);//120
console.log(oNoOverScroll.clientWidth);//120 var oOverScroll = document.getElementById('overScroll');
//存在滚动条,但元素设置宽高小于元素内容宽高,即存在内容溢出的情况时,scroll属性大于client属性
//scrollHeight 属性存在兼容性问题,chrome 和 safari 浏览器中,scrollHeight 包含 padding-bottom;而 IE 和 firefox 不包含 padding-bottom;
//chrome/safari:220(200+10+10)
//firefox/IE:210(200+10)
console.log(oOverScroll.scrollHeight);//220
//103(120-17)
console.log(oOverScroll.scrollWidth);//103
//103(120-17)
console.log(oOverScroll.clientHeight);//103
console.log(oOverScroll.clientWidth);//103
</script>

  scrollTop 属性表示被隐藏在内容区域上方的像素数。元素未滚动时,scrollTop 的值为0,如果元素被垂直滚动了,scrollTop 的值大于0,且表示元素上方不可见内容的像素宽度;

  scrollLeft 属性表示被隐藏在内容区域左侧的像素数。元素未滚动时,scrollLeft 的值为0,如果元素被水平滚动了,scrollLeft 的值大于0,且表示元素左侧不可见内容的像素宽度;

  当滚动条滚动到内容底部时,scrollHeight == scrollTop + clientHeight;

  可以通过控制 scrollTop、scrollLeft,控制滚动条;(第一种控制滚动条的方法)

<style type="text/css">
#test{
width: 100px;
height: 100px;
padding: 10px;
margin: 10px;
border: 1px solid black;
overflow:scroll;
font-size:20px;
line-height:200px;
}
</style>
<div id="test">内容</div>
<button id='btnDown'>向下滚动</button>
<button id='btnUp'>向上滚动</button> <script>
var oTest = document.getElementById('test');
var oBtnDown = document.getElementById('btnDown');
var oBtnUp = document.getElementById('btnUp');
oBtnDown.onclick = function(){
oTest.scrollTop += 10;
}
oBtnUp.onclick = function(){
oTest.scrollTop -= 10;
}
</script>

页面尺寸

  document.documentElement.clientHeight 表示页面的可视区域的尺寸;

  document.documentElement.scrollHeight 表示 html 元素内容的实际尺寸;但是由于各个浏览器表现不一样,分为以下几种情况:

  1. html 元素没有滚动条时,IE 和 firefox 的 client 和 scroll 属性始终相同,且返回可视区的尺寸大小;而 chrome 和 safari 不一样,clientHeight 返回可视区域大小,而 scrollHeight 返回元素内容大小;
  2. html 元素存在滚动条时,各个浏览器都表现正常。clientHeight 返回可视区域大小,而 scrollHeight 返回元素内容大小;

  因此要取得文档实际高度时,要取得 <html> 元素的 scrollHeight 和 clientHeight 的最大值;

        <script type="text/javascript">
var docHeight = Math.max(document.documentElement.scrollHeight,document.documentElement.clientHeight);
var docWidth = Math.max(document.documentElement.scrollWidth,document.documentElement.clientWidth);
</script>

页面滚动

  理论上,通过 document.documentElement.scrollTop 和 scrollLeft 可以反映和控制页面的滚动;但是 chrome 和 safari 浏览器是通过 document.body.scrollTop 和scrollLeft 来控制的;

  所以,页面的滚动高度兼容写法是

        <script type="text/javascript">
var docScrollTop = document.documentElement.scrollTop || document.body.scrollTop;
</script>

  可以利用 scrollTop 来实现回到顶部的功能(第一种回到顶部的方法);

    <body style="height:1000px">
<button id='btn' style="position:fixed">回到顶部</button> <script>
var oBtn = document.getElementById('btn');
function scrollTop(){
var docScrollTop = document.documentElement.scrollTop || document.body.scrollTop;
if(docScrollTop != 0){
document.body.scrollTop = document.documentElement.scrollTop = 0;
}
}
oBtn.onclick = scrollTop;
</script>
</body>

  还有两个 window 的只读属性可以获取整个页面滚动的像素值,它们是 pageXOffset 和 pageYOffset;IE8及以下浏览器不支持

  window.pageXOffset 表示水平方向上页面滚动的像素值;

  window.pageYOffset 表示垂直方向上页面滚动的像素值;

滚动方法

scrollTo(x,y)

  scrollTo(x,y) 方法滚动当前 window 中显示的文档,让文档中由坐标 x 和 y 指定的点位于显示区域的左上角;

  第二种回到顶部的方法;

    <body style="height:1000px">
<button id='btn' style="position:fixed">滚动</button>
<script>
var oBtn = document.getElementById('btn');
oBtn.onclick = function(){
scrollTo(0,0);
}
</script>
</body>

scrollBy(x,y)

  scrollBy(x,y) 方法滚动当前 window 中显示的文档,x 和 y 指定滚动的相对量;

  第二种控制滚动条的方法;

  只要把当前页面的滚动长度 document.body.scrollTop 作为参数,逆向滚动(把滚动长度设为 y,并且为负值),则可以实现第三种回到顶部的效果;

    <body style="height:1000px">
<button id='btnDown' style="position:fixed">向下滚动</button>
<button id='btnUp' style="position:fixed;top:40px">向上滚动</button>
<script>
var oBtnDown = document.getElementById('btnDown');
var oBtnUp = document.getElementById('btnUp');
oBtnDown.onclick = function(){
scrollBy(0,10);
}
oBtnUp.onclick = function(){
scrollBy(0,-10);
}
</script>
</body>

scrollIntoView()

  Element.scrollIntoView() 方法滚动当前元素,进入浏览器的可见区域;

  该方法可以接受一个布尔值作为参数。如果为true,表示元素的顶部与当前区域的可见部分的顶部对齐(前提是当前区域可滚动);如果为false,表示元素的底部与当前区域的可见部分的尾部对齐(前提是当前区域可滚动)。如果没有提供该参数,默认为true

  第四种回到顶部的方法;

<style type="text/css">
*{padding: 0;margin: 0;}
#test{
height:100px;
width:100px;
position:absolute;
left:0;
top:200px;
background-color:green;
}
#btnTop{
position:fixed;
}
#btnBottom{
position:fixed;
top:40px;
}
</style>
<body style="height:1000px">
<div id="test"></div>
<button id='btnTop'>滚动到页面开头</button>
<button id='btnBottom'>滚动到页面结尾</button> <script>
var oTest = document.getElementById('test');
var oBtnTop = document.getElementById('btnTop');
var oBtnBottom = document.getElementById('btnBottom');
oBtnTop.onclick = function(){
oTest.scrollIntoView();
};
oBtnBottom.onclick = function(){
oTest.scrollIntoView(false);
}
</script>
</body>

scrollIntoViewIfNeeded(alignCenter)

  scrollIntoViewIfNeeded(alignCenter) 方法只在当前元素在视口中不可见的情况下,才滚动浏览器窗口或容器元素,最终让它可见。如果当前元素在视口中可见,这个方法什么也不做;该方法只有 chrome 和 safari 支持

  如果将可选的 alignCenter 参数设置为 true,则表示尽量将元素显示在视口中部(垂直方向);尽量的意思是可能不成功,比如有元素有一半显示,一半隐藏,那么只会全部显示,但不会显示在视口中部;

<style type="text/css">
#test{
height:100px;
width:100px;
/*position:absolute;
left:0;
top:500px;*/
background-color:green;
}
#btn{
position:fixed;
top: 0;
}
</style>
<body>
<ul>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
</ul>
<div id="test"></div>
<ul>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
<li></li>
</ul>
<button id='btn'>滚动到页面中间</button>
<script>
var oTest = document.getElementById('test');
var oBtn = document.getElementById('btn'); oBtn.onclick = function(){
oTest.scrollIntoViewIfNeeded();
};
</script>
</body>

scrollByLines(lineCount)

  scrollByLines(lineCount) 方法将元素的内容滚动指定的行髙,lineCount 值可以是正值, 也可以是负值,该方法只有 safari 支持;

scrollByPages(pageCount)

  scrollByPages(pageCount) 方法将元素的内容滚动指定的页面高度,具体高度由元素的高度决定;该方法只有safari支持;

回到顶部

  前文有很多种方法可以实现回到顶部功能,有时候需要为回到顶部增加动画效果,滚动条以一定的速度回滚到顶部;

  动画有两种:一种是CSS动画,需要有样式变化配合 transition;一种是 javascript 动画,使用定时器来实现;  

  在前文的实现中,scrollTop、scrollTo() 和 scrollBy() 方法可以增加动画,且由于无样式变化,只能增加javascript动画;

  定时器又有 setInterval、setTimeout 和 requestAnimationFrame 这三种可以使用,下面使用性能最好的定时器 requestAnimationFrame 来实现;

  IE9及以下浏览器不支持该方法,可以使用 setTimeout 来兼容;

  由于 scrollTop、scrollBy() 和 scrollTo()方法,都以 scrollTop 值是否减少为0作为动画停止的参照,且三个动画的原理和实现都基本相似,性能也相似。最终,以最常用的scrollTop属性实现动画增强效果;

  当然,如果觉得50的速度不合适,可以根据实际情况进行调整;

    <style>
*{padding: 0;margin: 0;}
.goTop{
position:fixed;
right:10px;
bottom: 10px;
height:50px;
width: 50px;
text-align:center;
background-color: lightblue;
border-radius: 20%;
overflow: hidden;
}
.goTop:hover:before{
top:50%;
}
.goTop:hover .directTop{
visibility: hidden;
}
.goTop:before{
position: absolute;
top: -50%;
left: 50%;
transform: translate(-50%,-50%);
content:'回到顶部';
width: 40px;
color:peru;
font-weight:bold;
}
.directTop{
visibility: visible;
display:inline-block;
margin-top: 20px;
height:20px;
width: 20px;
border: 3px solid;
border-color: white transparent transparent white;
transform:rotate(45deg);
}
</style> <body style="height:2000px;">
<div class="goTop">
<div class="directTop"></div>
</div>
<script>
var timer = null;
var oGoTop = document.getElementsByClassName('goTop')[0];
oGoTop.onclick = function(){
cancelAnimationFrame(timer);
timer = requestAnimationFrame(function fn(){
var oTop = document.body.scrollTop || document.documentElement.scrollTop;
if(oTop > 0){
document.body.scrollTop = document.documentElement.scrollTop = oTop - 50;
timer = requestAnimationFrame(fn);
}else{
cancelAnimationFrame(timer);
}
});
}
</script> <!--setTimeout 兼容写法-->
<!--<script>
var timer = null;
var oGoTop = document.getElementsByClassName('goTop')[0];
oGoTop.onclick = function(){
clearTimeout(timer);
timer = setTimeout(function fn(){
var oTop = document.body.scrollTop || document.documentElement.scrollTop;
if(oTop > 0){
document.body.scrollTop = document.documentElement.scrollTop = oTop - 50;
timer = setTimeout(fn,0);
}else{
clearTimeout(timer);
}
},0);
}
</script>-->
</body>

  

滚动事件

  scroll 事件是在 window 对象上发生的,它表示的是页面中相应元素的变化。当然,scroll 事件也可以用在有滚动条的元素上;

    <body style="height:1000px">
<div id="result" style="position:fixed;top:10px;"></div>
<script>
var oResult = document.getElementById('result');
window.onscroll = function(){
var docScrollTop = document.documentElement.scrollTop || document.body.scrollTop;
result.innerHTML = '页面的scrollTop:' + docScrollTop;
}
</script>
</body>

  有时候需要判断滚动方向,

    <script type="text/javascript">
function scroll( fn ) {
var beforeScrollTop = document.documentElement.scrollTop || document.body.scrollTop,
fn = fn || function() {};
window.addEventListener("scroll", function() {
var afterScrollTop = document.documentElement.scrollTop || document.body.scrollTop,
delta = afterScrollTop - beforeScrollTop;
if( delta === 0 ) return false;
fn( delta > 0 ? "down" : "up" );
beforeScrollTop = afterScrollTop;
}, false);
}
scroll(function(direction) {
if(direction == 'down'){
console.log('向下');
}else if(direction == 'up'){
console.log('向上');
}
});
</script>

  JQuery判断滚动方向,

    <script type="text/javascript">
function scroll( fn ) {
var $window = $(window),
beforeScrollTop = $window.scrollTop(),
fn = fn || function() {}; $window.scroll(function() {
var afterScrollTop = $window.scrollTop(),
delta = afterScrollTop - beforeScrollTop;
if( delta === 0 ) return false;
fn( delta > 0 ? "down" : "up" );
beforeScrollTop = afterScrollTop;
});
}
scroll(function(direction) {
if(direction == 'down'){
console.log('向下');
}else if(direction == 'up'){
console.log('向上');
}
});
</script>

  还有一种方法,

       <script>
var scrollFunc = function (e) {
var direct = 0;
e = e || window.event;
//滚轮事件中有一个 wheelDelta 属性,当用户向前滚动鼠标滚轮时,wheelDelta 是120的倍数;当用户向后滚动鼠标滚轮时,wheelDelta 是 -120 的倍数;
//firefox 浏览器有关鼠标滚轮的信息则保存在 detail 属性中。当向前滚动鼠标滚轮时,这个属性的值是 -3 的倍数;当向后滚动鼠标滚轮时,这个属性的值是 3 的倍数。
if (e.wheelDelta > 0 || e.detail < 0) {
console.log("滑轮向上滚动");
}
if (e.wheelDelta < 0 || e.detail > 0) {
console.log("滑轮向下滚动");
}
}
//firefox 浏览器不支持 mousewheel 事件,它支持 DOMMouseScroll 事件(该事件仅支持DOM2级事件处理程序的写法)
if (document.addEventListener) {
document.addEventListener('DOMMouseScroll', scrollFunc, false);
}
//滚动滑轮触发scrollFunc方法
window.onmousewheel = document.onmousewheel = scrollFunc;
</script>

jacascript 滚动 scroll 与回到顶部的更多相关文章

  1. jacascript 滚动scroll

    滚动 scroll scrollHeight 表示元素的总高度,包括由于溢出而无法展示在网页的不可见部分: scrollWidth 表示元素的总宽度,包括由于溢出而无法展示在网页的不可见部分: 没有滚 ...

  2. angularjs 水平滚动选中按钮高亮显示 swiper和回到顶部指令的实现ionic

    首先安装 swiper npm install --save swiper 或者 bower install --save swiper <link rel="stylesheet&q ...

  3. 页面滚动事件和利用JS实现回到顶部效果

    页面滚动 事件:window.onscroll, 获得页面滚动位置:document.body.scrollTop: HTML代码: 这里注意此处逻辑,大于500就显示,否则就隐藏,还有注意如果变量名 ...

  4. 通过HTML&plus;CSS&plus;Javascript实现向下滚动滚动条出现导航栏并出现回到顶部按钮点击按钮回到顶部(一)

    回到顶部实例一 效果:默认隐藏导航栏,当滚动条滚到超过300px后导航栏和按钮出现,点击回到顶部按钮回到顶部,并隐藏导航栏和按钮(导航栏和按钮都是固定定位) <!doctype html> ...

  5. iOS tableView 滚动后回到顶部

    - (void)scrollViewDidScroll:(UIScrollView *)scrollView { CGPoint contentOffsetPoint = self.tableView ...

  6. JQuery - 点击,滚动回到顶部 &sol; 底部刷新回到顶部

    if ($(document).scrollTop() != 0) { //刷新之后,回到顶部 $('body,html').animate({ scrollTop: 0 }, 500); }

  7. 【JQ&plus;锚标记实现点击页面回到顶部】

    前言:今天想写个页面常用到的[点击回到页面顶部或是首页的功能],生活和职场一样,总会有低谷的时候,这个时候咱也别怂.别怂.别怂,说三遍!那都不是事,工作没了,再找呗,就像我上周五,团队解散那天,我是笑 ...

  8. 深入理解滚动scroll

    前面的话 前面两篇博文分别介绍过偏移大小.客户区大小.本文介绍元素尺寸中内容最多的一部分——滚动scroll 滚动宽高 scrollHeight scrollHeight表示元素的总高度,包括由于溢出 ...

  9. 原生js实现吸顶导航和回到顶部特效

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

随机推荐

  1. 学堂在线 UWP 首版

    好久没有写博客了,主要是最近在写一个小小的App.<( ̄︶ ̄)> 不知道看各位有木有爱看慕课的,作为一名资深的大三学渣的我有看慕课的习惯.一直在看学堂在线的慕课,感觉质量确实还可以,但是遗 ...

  2. 关闭 Visual Studio 2013 的 Browser Link 功能

    最近公司弄新项目需要用 MVC,就把 IDE 升级到了 Visual Studio 2013,在开发的时候发现有好多请求一个本地49925的端口 . 很奇怪,一开始以为是 Visual Studio ...

  3. ThinkPad紧凑型蓝牙键盘(0B47189)鼠标滚轮用法,F1到F12功能键的功能切换以及其他技巧

    入手小红点蓝牙键盘(ThinkPad Compact Bluetooth),手感极佳,小红点特别适合程序员工作,双手无需离开键盘就可以操作鼠标,完全解决肩部.腕部疲劳酸痛问题,程序员健康的大福音! 使 ...

  4. Eclipse编译Arduino程序不能使用串口函数Serial&period;begin解决办法

    在Arduino官方的编译器当中Serial.begin(9600);初始化语句是可以直接使用的,而到Eclipse当中,同样的语句却不能用了.会出现下面的问题: 显然,这是Eclipse没有找到Se ...

  5. Docker 基于已有镜像的容器创建镜像

    Docker 基于已有镜像的容器创建镜像: docker:/root# docker run -it januswel/centos /bin/bash docker exec -it januswe ...

  6. 双11电商剁手节,最全的H5互动营销案例合集

    距离双11不足一个月! 是否准备好为双十一疯狂剁手! 自从天猫2009年首创双11购物节以来双十一不仅成为了消费者的"剁手日" 更是每年企业营销的"狂欢节" 各 ...

  7. &lbrack;总结&rsqb; 第二类Stirling数

    上一道例题 我们来介绍第二类Stirling数 定义 第二类Stirling数实际上是集合的一个拆分,表示将n个不同的元素拆分成m个集合的方案数,记为 或者 .和第一类Stirling数不同的是,集合 ...

  8. 为什么range不是迭代器?range到底是什么类型?

    迭代器是 23 种设计模式中最常用的一种(之一),在 Python 中随处可见它的身影,我们经常用到它,但是却不一定意识到它的存在.在关于迭代器的系列文章中(链接见文末),我至少提到了 23 种生成迭 ...

  9. hdu2586How far away ?-(LCA)

    http://acm.hdu.edu.cn/showproblem.php?pid=2586 题意:有n个点,有n-1条线连通,求两点间的最短距离,最近公共祖先的入门题.Tarjan离线算法. #in ...

  10. length、length&lpar;&rpar;、size&lpar;&rpar;区别 List与String相互转换

      字符串 数组 List对象 定义 String str = ""; String[] s = new String[5]; char[] s; List<String&g ...