资讯专栏INFORMATION COLUMN

Vue开发——实现吸顶效果

amuqiao / 3196人阅读

摘要:因为项目需求,最近开始转到微信公众号开发,接触到了框架,这个效果的实现虽说是基于框架下实现的,但是同样也可以借鉴到其他地方,原理都是一样的。上面我们得到了一个的属性值,接下来我们只需要根据它的值来设置吸顶元素的属性就可以了。

因为项目需求,最近开始转到微信公众号开发,接触到了Vue框架,这个效果的实现虽说是基于Vue框架下实现的,但是同样也可以借鉴到其他地方,原理都是一样的。

进入正题,先看下效果图:


其实js做这个效果还是挺简单的,因为在css中我们可以设置一个元素的position: fixed;,这样它就可以固定在那里,这样不管页面怎么滚动,它的位置都不受影响,所以我们的思路就是在合适的时机把要吸顶的头部元素的position属性设置为fixed就可以了。但是这个合适的时机是什么时候呢,这就需要我们计算了,我们需要监听页面的滚动状态,当页面滚动到要吸顶元素所处的位置的时候就是我们设置它固定的时候,所以就需要我们:

1.监听页面的滚动状态:

在mounted回调中加入以下代码:

mounted() {
  // handleScroll为页面滚动的监听回调
  window.addEventListener("scroll", this.handleScroll);
 },

同时在destroyed回调中移除监听:

destroyed(){
  window.removeEventListener("scroll", this.handleScroll);
},
2.计算吸顶元素到页面顶部的距离:

计算出来这个距离之后就可以确定固定吸顶元素的时机了,如果你的吸顶元素上面的元素的高度是固定的话,那就简单了,直接在handleScroll方法中进行判断就可以了,可以直接跳到第三步了,如果是动态的,那就需要我们在接口请求完数据,dom元素渲染完之后进行动态计算了,Vue中有一个很好用的方法,可以很方便的监听dom渲染完成:

// 监听dom渲染完成
this.$nextTick(function(){
  // 这里fixedHeaderRoot是吸顶元素的ID
  let header = document.getElementById("fixedHeaderRoot");
  // 这里要得到top的距离和元素自身的高度
  this.offsetTop = header.offsetTop;
  this.offsetHeight = header.offsetHeight;
  console.log("offsetTop:" + this.offsetTop + "," + this.offsetHeight);
});
3.判断页面滚动距离:
handleScroll(){
  // 得到页面滚动的距离
  let scrollTop = window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop;
  // 判断页面滚动的距离是否大于吸顶元素的位置
  this.headerFixed = scrollTop > (this.offsetTop - this.offsetHeight * 2);
},

ps:这里理论上其实应该是scrollTop > (this.offsetTop - this.offsetHeight),但是不知道为啥我这里做出来后滚动到吸顶元素位置的时候scrollTop还是比this.offsetTop - this.offsetHeight的值小,所以这里*2,这样得出来的值才刚刚好,如果有知道的朋友可以帮忙解惑一下。

上面我们得到了一个headerFixed的boolean属性值,接下来我们只需要根据它的值来设置吸顶元素的position: fixed;属性就可以了。
我们可以写一个css样式:

.isFixed{
  position: fixed;
  top: px2rem(110);
  left: px2rem(20);
  right: px2rem(20);
}

然后Vue可以在dom元素里这样动态设置class,非常方便:

知识模块
知识点
能力要求
其实到这里这个效果已经实现完成了,不过我在测试过程中发现,因为ios手机页面滚动到底部的时候,还可以上拉,有一个橡皮筋效果,这个效果会导致一个我们页面的一个Bug,因为它的这种橡皮筋效果也会触发页面滚动的监听,当数据很多的时候其实看不出来,只有当数据刚好占满屏幕的时候,这个时候你再继续往上滑动屏幕,就会触发页面的滚动监听,这个时候handleScroll方法中计算出来的值scrollTop是大于吸顶元素top的距离,所以吸顶元素会被设置为固定属性,大家知道一个元素一旦被设置为position: fixed;,那么它就会相对于浏览器窗口进行定位,这样我们下面的内容就会往上顶,这样的话scrollTop的值又小于了吸顶元素top的距离,这样headerFixed属性又为false,position: fixed;属性又没有了,这样它就又相对与它原本的父元素进行定位,这样就成了一个循环,你会发现页面会上下跳到,这样是肯定不行的,所以我下面又针对这个问题进行了一个优化,当然这个方案感觉不是特别完美,不过确实可以解决这个问题。 通过上面的分析我们可以得知造成这个问题的原因是因为我们把设置了元素的position: fixed;属性,使得下面的内容往上顶,所以要想解决这个问题,那我们就不固定这个元素,但是这样的话就达不到吸顶的效果了,所以我们需要再加一个和吸顶元素一模一样的元素,它一直就是固定状态:
知识模块
知识点
能力要求
这个元素默认是隐藏的,只有当页面滚动的距离达到了它的位置的时候我们才让它显示,由于它是固定状态,所以它的隐藏显示并不会对页面产生影响,这样下面的内容就不会往上顶了,就可以解决ios手机上拉页面橡皮筋效果的Bug了,当然这种方式有些取巧,但是暂时没有更好的解决方案了,如果大家有更好的解决方案,欢迎在下面评论。最后给大家看一下我的页面布局:
知识模块
知识点
能力要求
知识模块
知识点
能力要求
{{kpointItem.knowModule}}
{{kpointItem.knowPoint}}
{{kpointItem.abilityRequire}}

参考

喜欢的麻烦动动小手点个赞来支持我,有不对的地方欢迎大家指正,有什么问题也可以在下方留言,我看到后会第一时间回复!谢谢您来看这篇文章!

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/106073.html

相关文章

  • 【前端词典】5 种滚动吸顶实现方式的比较[性能升级版]

    摘要:用于获得当前元素到定位父级顶部的距离偏移值。后来在项目中总会遇到滚动吸顶的效果需要实现,现在我将我知道的种滚动吸顶实现方式做详细介绍。有兼容性问题,在微信浏览器某些版本中的值会为,于是乎也就有了第三种方案的兼容性写法。修改版预览 这篇文章是三天前写就的,有大佬给我提了一些修改意见,我觉得这个意见确实中肯。所以就有了这个升级的修改版本。代码同步更新到 GitHub 了。 修改内容如下: 添加...

    happyfish 评论0 收藏0
  • 踩坑日记(持续更新...)

    摘要:二按照官方的提示解决了意思就是切到分支,自己的分支解决冲突,提交。这是和二相反向的操作页面标题无效的解决办法强类型转换的坑条件用正则返回的布尔值结果返回了条件结果也返回了。 2018/3/2 1,vue的{{}}怎么失效了项目使用了twig模板渲染 语法{{}}冲突,使用v-text v-html渲染 可以写表达式的写法 字符+变量 2,函数防抖节流封装实用的下拉加载更多代码demo...

    taoszu 评论0 收藏0
  • WEB移动端粘黏吸顶效果的解决方案

    摘要:原文链接一般的吸顶,通常是给上一个定位便可实现,而类似于上图这样的粘黏吸顶,也是一个比较常见的需求粘黏吸顶大概的思路是这样首先,给吸顶栏一个或者定位,通过去监听事件触发一个判断吸顶栏高度的函数,当吸顶栏的高度距离可视区域顶部小于等于时,将其 原文链接: Fyerls Blog showImg(https://segmentfault.com/img/bVJMAs?w=360&h=240...

    macg0406 评论0 收藏0

发表评论

0条评论

amuqiao

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<