高亮显示错误

高亮显示错误

1
问题描述:为什么不加1的话用鼠标点击导航条高亮定位错误,offsetTop的值是整数,scrollTop的值却是有很多小数的,导致高亮显示错误。我在第111行加了1

   

相关代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <style>
        *{
            margin: 0;
            padding: 0;
        }
        .content-part{
            width: 700px;
            background-color: rgba(0,0,0,.6);
            margin: 0px auto;
            margin-bottom: 30px;
            text-align: center;
            font-size: 40px;
        }
        .part1{
            height: 400px;
        }
        .part2{
            height: 430px;
        }
        .part3{
            height: 480px;
        }
        .part4{
            height: 530px;
        }
        .part5{
            height: 670px;
        }
        nav{
            width: 60px;
            height: 150px;
            background-color: orange;
            position:fixed;
            right: 10px;
            top: 50%;
            margin-top: -75px;
        }
        nav ul{
            width: 60px;
            list-style: none;
        }
        nav ul li{
            height: 30px;
            line-height: 30px;
            text-align: center;
            cursor: pointer;
        }
        nav ul li.cur{
            background-color: purple;
        }
    </style>
</head>
<body>
    <!-- 要使用到绝对定位和data-自定义属性 -->
    <!-- offsetTop属性,此元素定位祖先元素的垂直距离,祖先元素就是离自己最近的且拥有定位属性的元素 -->
    <!-- 1、楼层导航 -->
    <!-- 每个内容区域和导航条是通过data-n属性来建立连接 -->
    <!-- 2、窗口卷动到哪个位置,导航条对应位置有高光 -->
    <nav>
        <ul id="list">
            <li data-n="新闻">新闻</li>
            <li data-n="娱乐">娱乐</li>
            <li data-n="天气">天气</li>
            <li data-n="图片">图片</li>
            <li data-n="视频">视频</li>
        </ul>
    </nav>
    <!-- 每个单独板块 -->
    <section class="content-part part1" data-n="新闻">新闻</section>
    <section class="content-part part2" data-n="娱乐">娱乐</section>
    <section class="content-part part3" data-n="天气">天气</section>
    <section class="content-part part4" data-n="图片">图片</section>
    <section class="content-part part5" data-n="视频">视频</section>
    <script>
        //获取ul元素
        var list=document.getElementById('list');
        //获取section元素
        var section = document.querySelectorAll('.content-part');
        //获取li元素
        var liS = document.querySelectorAll('#list li');
 
        //获取每个内容区域距离顶部值,并存入数组
        var offsetTopArr = [];
        for(var i =0;i<section.length;i++){
            offsetTopArr.push(section[i].offsetTop);
        }
        //给数组的最后一项推入无穷大值,防止楼层出错,因为用户可能从后面往前翻,如果当前滚动到的值为5,就会出错
        //li标签也给不了.cur的选择器
        offsetTopArr.push(Infinity);
        console.log(offsetTopArr);
        var contentPart;
        //list的事件监听用的是事件委托,采用冒泡阶段
        list.onclick=function(e){
            //源元素的标签名字是li时
            if(e.target.tagName.toLowerCase()=='li'){
                //获取非w3c标准的属性名用getAttribute
                var n =e.target.getAttribute('data-n');
                //使用属性选择器来获取带有某个data-n属性的标签,方括号指带有某种属性元素
                contentPart=document.querySelector('.content-part[data-n='+n+']');
                //用document.documentElement.scrollTop来设置距离页面顶部的位置
                //不加1鼠标点击li标签高亮定位错误,(点击楼层3,高亮在楼层2)
                document.documentElement.scrollTop = contentPart.offsetTop + 1;
                console.log(document.documentElement.scrollTop);
            }
        }
 
        var floor = -1;
        //建立页面滚动事件监听,楼层从0-4
        window.onscroll=function(){
            var scrollTop =document.documentElement.scrollTop;
            //for循环offsetTop数组,判断滚动的距离是否介于哪两项之间
            for(var i = 0;i<offsetTopArr.length;i++){
                if( scrollTop>=offsetTopArr[i] && scrollTop<=offsetTopArr[i+1]){
                    break;
                }
            }
            
            //var一个floor变量,意思为当前楼层,防止一直在输出楼层,当当前楼层和滚动到的不一致时,才输出i
            //记得把当前楼层赋值给floor变量
            if(floor != i){
                console.log('当前楼层时'+ i +'滚动值' + scrollTop);
                floor = i;
                for(var j =0;j<liS.length;j++){
                    if(i==j){
                        liS[j].className = 'cur';
                    }else{
                        liS[j].className = '';
                    }
            }
 
            }
            
        }
 
    </script>
</body>
</html>

       

下载视频          

下载视频          

正在回答

登陆购买课程后可参与讨论,去登陆

1回答

同学你好,解答如下:

1、这边测试代码chrome版本是

https://img1.sycdn.imooc.com//climg/616a3abf09ecebb604000118.jpg

滚动值不是小数

https://img1.sycdn.imooc.com//climg/616a3af609bb85d306600139.jpg

https://img1.sycdn.imooc.com//climg/616a3afc0955690e02370188.jpg

可能是chrome版本导致的显示小数,建议用Math.round()方法包裹转化一下。

2、代码中加1才能让右侧高亮显示正确

https://img1.sycdn.imooc.com//climg/616a3b49090e624707410039.jpg

是因为第一楼不需要滚动,也不会进入onscroll事件中,所以第一层导航没有高亮。建议将加1去掉,在第一层导航元素上添加类

https://img1.sycdn.imooc.com//climg/616a3bbd098e2dae05370117.jpg

https://img1.sycdn.imooc.com//climg/616a3bf40996a6e406940061.jpg

3、在滚动的时候,不需要等于下一楼的值,避免导航不准,小于即可

https://img1.sycdn.imooc.com//climg/616a3bff09da1d3b08730173.jpg

祝学习愉快!

  • Snakk 提问者 #1

    谢谢老师,差不多理解了。

    1、把document.documentElement.scrollTop用Math.round()四舍五入,让值为整数(我的版本也是最新,不知为啥是小数)(主要要注意这点,可以让高光正确显示)

    2、第0层楼无需滚动,给第一个li标签添加cur的class选择器,一进入页面第一个li就有高亮

    3、滚动事件监听那里,scrollTop小于下一个楼层高度即可

    下载视频          
    2021-10-16 10:56:48
问题已解决,确定采纳
还有疑问,暂不采纳

恭喜解决一个难题,获得1积分~

来为老师/同学的回答评分吧

0 星
请稍等 ...
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号

在线咨询

领取优惠

免费试听

领取大纲

扫描二维码,添加
你的专属老师
插入代码