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 密码强度判断代码
Sep 05 Javascript
Jquery判断IE6等浏览器的代码
Apr 05 Javascript
firebug的一个有趣现象介绍
Nov 30 Javascript
JS中 用户登录系统的解决办法
Apr 15 Javascript
JS截取字符串常用方法详细整理
Oct 28 Javascript
innerText 使用示例
Jan 23 Javascript
javascript实现2048游戏示例
May 04 Javascript
js格式化时间的简单实例
Nov 27 Javascript
jquery.uploadView 实现图片预览上传功能
Aug 10 jQuery
Canvas放置反弹效果随机图形(实例)
Aug 17 Javascript
Vue.js搭建移动端购物车界面
Jun 28 Javascript
vue实现百度搜索功能
Dec 28 Javascript
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
程序员编程十条戒律
2009/07/09 PHP
PHP文章采集URL补全函数(FormatUrl)
2012/08/02 PHP
PHP的preg_match匹配字符串长度问题解决方法
2014/05/03 PHP
PHP准确取得服务器IP地址的方法
2015/06/02 PHP
浅谈PHP中foreach/in_array的使用
2015/11/02 PHP
thinkPHP简单导入和使用阿里云OSSsdk的方法
2017/03/15 PHP
Yii2数据库操作常用方法小结
2017/05/04 PHP
Jquery 常用方法经典总结
2010/01/28 Javascript
js弹窗代码 可以指定弹出间隔
2010/07/03 Javascript
JSChart轻量级图形报表工具(内置函数中文参考)
2010/10/11 Javascript
js Html结构转字符串形式显示代码
2011/11/15 Javascript
node.js实现BigPipe详解
2014/12/05 Javascript
JS输入用户名自动显示邮箱后缀列表的方法
2015/01/27 Javascript
JS 清除字符串数组中,重复元素的实现方法
2016/05/24 Javascript
NodeJs的优势和适合开发的程序
2016/08/14 NodeJs
基于nodejs+express4.X实现文件下载的实例代码
2017/07/13 NodeJs
layui+SSM的数据表的增删改实例(利用弹框添加、修改)
2019/09/27 Javascript
Vue中使用JsonView来展示Json树的实例代码
2020/11/16 Javascript
vue-video-player 断点续播的实现
2021/02/01 Vue.js
Python 网络编程之UDP发送接收数据功能示例【基于socket套接字】
2019/10/11 Python
python os模块在系统管理中的应用
2020/06/22 Python
CSS3实现瀑布流布局与无限加载图片相册的实例代码
2016/12/22 HTML / CSS
HTML页面中添加Canvas标签示例
2015/01/01 HTML / CSS
美国礼品卡商城: Gift Card Mall
2017/08/25 全球购物
乌克兰在线电子产品商店:MTA
2019/11/14 全球购物
简述进程的启动、终止的方式以及如何进行进程的查看
2013/07/12 面试题
文员岗位职责范本
2014/03/08 职场文书
2014年3.15团委活动总结
2014/03/16 职场文书
村干部群众路线整改措施思想汇报
2014/10/12 职场文书
汽车销售助理岗位职责
2015/04/14 职场文书
关于召开会议的通知
2015/04/15 职场文书
毕业证明书
2015/06/19 职场文书
大学班干部竞选稿
2015/11/20 职场文书
高中语文教材(文学文化常识大全一)
2019/08/13 职场文书
导游词之丽江普济寺
2019/10/22 职场文书
解决thinkphp6(tp6)在状态码500下不报错,或者显示错误“Malformed UTF-8 characters”的问题
2021/04/01 PHP