js实现多个标题吸顶效果


Posted in Javascript onJanuary 08, 2020

对于导航的吸顶效果,pc端和移动端的需求可能有些差异。在pc端,我们通常只需要一个顶部导航;在移动端,在滑动页面的时候,更需要多个标题的吸顶(例如地区的选择,需要将省份吸顶)。

单个标题吸顶和多个标题吸顶的区别在于:多个标题吸顶需要确定一个高度范围,在这个范围中只能有一个标题吸顶,其他都是固定效果。

一、页面布局及样式

此处为了测试效果,用了几个重复的section标签,大家根据实际需求编写布局和样式。

<body>
 <ul id="container">
 <h1>实现多个标题的吸顶</h1>
 <section>
  <div class="box">header1</div>
  <li>1</li>
  <li>1</li>
  <li>1</li>
  <li>1</li>
  <li>1</li>
  <li>1</li>
 </section>
 
 <!--设置多个如header1的子列表,窗口可以进行滚动,此处省略-->
 
 <section>
  <div class="box">header5</div>
  <li>1</li>
  <li>1</li>
  <li>1</li>
  <li>1</li>
  <li>1</li>
  <li>1</li>
 </section>
 
 </ul>
</body>
<style type="text/css">
 * {
 padding: 0;
 margin: 0;
 }
 ul {
 width: 100%;
 }
 li {
 width: 200px;
 color: white;
 margin: 10px;
 list-style: none;
 border-radius: 5px;
 border: 1px solid #191970;
 background: #4169E1;
 text-align: center;
 }
 div {
 width: 100%;
 height: 30px;
 color: white;
 padding-left: 20px;
 background: #DC143C;
 }
 .box1 {
 position: fixed;
 top: 0;
 }
</style>

二、js的编写

1、获取所有需要吸顶效果的标题。这里的标题最好用相同的布局和样式,获取时能够更快捷和统一。

var box = document.getElementsByClassName('box'), //获取所有需要吸顶效果的标题
  section = document.getElementsByTagName('section'); //获取所有子列表,后面有用

2、获取标题个数和定义一个数组,用来存放每个标题到父元素的距离(offsetTop)。

var ot = [],  //存储每个标题的offsetTop
  len = box.length;   //标题的个数

3、遍历所有标题,获取offsetTop,并存入ot数组中。

for(let i=0; i<len; i++) {
 ot.push(box[i].offsetTop);  //获取每个标题的offsetTop
}

4、监听window的滚动事件,获取scrollTop;如果滚动高度位于第i个标题的offsetTop和第i+1个标题的offsetTop之间(例如滚动的高度位于header1和header2的offsetTop之间,heade1吸顶),则第i个标题添加box1样式,实现吸顶。

window.onscroll = function () {
 //获取滚动的高度
 var st = document.documentElement.scrollTop || document.body.scrollTop;
 
 for(let i=0; i<len; i++) {
 if(st>ot[i] && st<ot[i+1]) { //滚动时监听位置,为标题的吸顶设置一个现实范围
  box[i].className = 'box box1';
 } else {
  box[i].className = 'box';
 }
 
 }
}

5、第四步中,有个问题:当滚动道最后一个标题(i)时,无法获取(i+1)。

解决方法:从第一步中获得的section标签集合中拿出最后一个子列表(section[0]),然后获取最后一个子列表的高度,计算出最后一个标题的显示高度范围,并存入ot数组中。

//获取最后一个子列表的高度,为了设置最后一个吸顶标题的位置
//section[len-1].getBoundingClientRect().height
//此方法返回一个number
 
ot.push(box[len-1].offsetTop + section[len-1].getBoundingClientRect().height);

三、最后效果

js实现多个标题吸顶效果

js实现多个标题吸顶效果

完整js代码

var box = document.getElementsByClassName('box'), //获取所有需要吸顶效果的标题
 section = document.getElementsByTagName('section'); //获取所有子列表
 
var ot = [],       //存储每个标题的offsetTop
 len = box.length;   //标题的个数
 
for(let i=0; i<len; i++) {
 ot.push(box[i].offsetTop);  //获取每个标题的offsetTop
}
 
//获取最后一个子列表的高度,为了设置最后一个吸顶标题的位置
//section[len-1].getBoundingClientRect().height
//此方法返回一个number
 
ot.push(box[len-1].offsetTop + section[len-1].getBoundingClientRect().height);
 
window.onscroll = function () {
 //获取滚动的高度
 var st = document.documentElement.scrollTop || document.body.scrollTop;
 
 for(let i=0; i<len; i++) {
 if(st>ot[i] && st<ot[i+1]) { //滚动时监听位置,为标题的吸顶设置一个现实范围
  box[i].className = 'box box1';
 } else {
  box[i].className = 'box';
 }
 
 }
}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
javascript题目,重写函数让其无限相加
Feb 15 Javascript
js 定时器setTimeout无法调用局部变量的解决办法
Nov 28 Javascript
instanceof和typeof运算符的区别详解
Jan 06 Javascript
Bootstrap Fileinput文件上传组件用法详解
May 10 Javascript
使用jquery提交form表单并自定义action的方法
May 25 Javascript
jQuery中实现prop()函数控制多选框(全选,反选)
Aug 19 Javascript
原生JS仿QQ阅读点击展开、收起效果
Mar 08 Javascript
jquery.flot.js简单绘制折线图用法示例
Mar 13 Javascript
vue和webpack项目构建过程常用的npm命令详解
Jun 15 Javascript
Vue中的验证登录状态的实现方法
Mar 09 Javascript
微信小程序拼接图片链接无底洞深入探究
Sep 03 Javascript
vue前端工程的搭建
Mar 31 Vue.js
Vue v-model组件封装(类似弹窗组件)
Jan 08 #Javascript
jquery实现吸顶导航效果
Jan 08 #jQuery
JS实现网站吸顶条
Jan 08 #Javascript
js实现移动端吸顶效果
Jan 08 #Javascript
vue.js自定义组件实现v-model双向数据绑定的示例代码
Jan 08 #Javascript
微信小程序实现吸顶效果
Jan 08 #Javascript
JS实现吸顶特效
Jan 08 #Javascript
You might like
ubuntu 编译安装php 5.3.3+memcache的方法
2010/08/05 PHP
PHP对接微信公众平台消息接口开发流程教程
2014/03/25 PHP
PHP中实现crontab代码分享
2015/03/26 PHP
php封装的mysqli类完整实例
2016/10/18 PHP
Zend Framework前端控制器用法示例
2016/12/11 PHP
php PDO实现的事务回滚示例
2017/03/23 PHP
支持ie与FireFox的剪切板操作代码
2009/09/28 Javascript
使用js dom和jquery分别实现简单增删改
2014/09/11 Javascript
浅谈下拉菜单中的Option对象
2015/05/10 Javascript
nodeJs链接Mysql做增删改查的简单操作
2017/02/04 NodeJs
微信小程序 action-sheet 反馈上拉菜单简单实例
2017/05/11 Javascript
JavaScript无操作后屏保功能的实现方法
2017/07/04 Javascript
JavaScrpt中如何使用 cookie 设置查看与删除功能
2017/07/09 Javascript
微信小程序实现复选框效果
2018/12/28 Javascript
如何在Angular应用中创建包含组件方法示例
2019/03/23 Javascript
vue 的 solt 子组件过滤过程解析
2019/09/07 Javascript
Javascript实现贪吃蛇小游戏(含详细注释)
2020/10/23 Javascript
微信小程序实现星星评分效果
2020/11/01 Javascript
[47:02]2018DOTA2亚洲邀请赛3月29日 小组赛B组 VP VS paiN
2018/03/30 DOTA
简析Python的闭包和装饰器
2016/02/26 Python
Python原始字符串与Unicode字符串操作符用法实例分析
2017/07/22 Python
python实现括号匹配的思路详解
2018/08/23 Python
python实现图片识别汽车功能
2018/11/30 Python
Python通过paramiko远程下载Linux服务器上的文件实例
2018/12/27 Python
python中logging模块的一些简单用法的使用
2019/02/22 Python
利用python绘制数据曲线图的实现
2020/04/09 Python
Python连接mysql方法及常用参数
2020/09/01 Python
芬兰灯具网上商店:Nettilamppu.fi
2018/06/30 全球购物
保健品市场营销方案
2014/03/31 职场文书
幼儿园小班教师寄语
2014/04/03 职场文书
项目经理任命书
2014/06/04 职场文书
大学生实习证明范文(5篇)
2014/09/18 职场文书
地道战观后感300字
2015/06/04 职场文书
房屋所有权证明
2015/06/19 职场文书
我的中国梦主题班会
2015/08/14 职场文书
MySQL数据库Innodb 引擎实现mvcc锁
2022/05/06 MySQL