CSS view():以后做滚动动画不用写JS了

更新日期: 2026-04-30 阅读: 18 标签: 滚动

以前做滚动动画,一看代码里有scroll监听、getBoundingClientRect()、节流、防抖,还要自己算进度条,我就知道后面要麻烦了。

不是说不能写。是这种代码一多,动画、性能、后面好不好改,这三样经常都保不住。浏览器明明自己就知道元素有没有进到视野里、滚动到哪了,结果我们非要用JavaScript再算一遍。

现在这事,CSS已经接过去一大块了。滚动动画可以直接跟滚动条走,view()就是里面最好用的一个。它会根据元素在滚动容器里的可见程度来推动动画。


以前要写一大堆代码

很多人以前是这么写的:

const cards = document.querySelectorAll('.card')

function update() {
  const vh = window.innerHeight
  
  cards.forEach((card) => {
    const rect = card.getBoundingClientRect()
    const start = vh * 0.9
    const end = vh * 0.2
    const progress = Math.min(
      1,
      Math.max(0, (start - rect.top) / (start - end))
    )
    
    card.style.opacity = progress
    card.style.transform = `translateY(${(1 - progress) * 40}px)`
  })
}

window.addEventListener('scroll', update, { passive: true })
window.addEventListener('resize', update)
update()

这段代码不是随便写的例子,很多线上项目真就这么干的。问题也很明显:

第一,你得自己算“什么时候开始进场、什么时候算结束”。

第二,页面一复杂,滚动的不止是整个页面,还有里面的小区域,判断就开始乱。

第三,动画逻辑全散在JS里,样式和行为搅在一起,后面谁接手谁头疼。


用view()怎么写

换成view(),思路就清爽多了:

.card {
  opacity: 0;
  transform: translateY(40px);
  animation: card-in both linear;
  animation-timeline: view();
  animation-range: entry 20% cover 40%;
}

@keyframes card-in {
  to {
    opacity: 1;
    transform: translateY(0);
  }
}
html
<section class="card">订单服务</section>
<section class="card">库存服务</section>
<section class="card">通知服务</section>

这里没写一行滚动计算的代码。元素滚进视野,动画自己动;往回滚,动画也跟着倒回去。这个机制说白了就是“动画走到哪跟滚动条走到哪绑在一起”,不像以前那样时间到了自己播完。


view()适合干什么

我自己会拿它做这几类东西:

  • 页面往下翻的时候,卡片一个个淡入

  • 文章里的章节标题、配图、时间线进场

  • 那种“滚到哪一块,哪一块亮起来”的简单效果

这类动画以前最烦人的不是写不出来,是你得一直维护那套“滚动位置转成动画进度”的代码。现在浏览器自己能管,就别自己扛着了。


再来个例子

做一个侧边目录高亮的效果,同样不用碰JS:

.doc-block {
  --p: 0;
  animation: block-focus both linear;
  animation-timeline: view(block);
  animation-range: entry 10% cover 30%;
}

@keyframes block-focus {
  from {
    opacity: .5;
    transform: scale(.98);
  }
  to {
    opacity: 1;
    transform: scale(1);
  }
}

这里的view(block)意思是沿着块方向跟踪可见进度。view()可以加轴参数,也能调inset来改“多早算进入视野”。


这东西也有毛病

第一,现在还不是所有浏览器都支持。MDN上标的“Limited availability”,就是说主流浏览器还没全覆盖。真要用在正式项目上,还是得看看你的用户用什么浏览器。

第二,它代替不了所有JavaScript。你要做复杂的联动、跟数据挂钩的动画、滚动和业务状态绑得紧的,JS还是得上。但那种只是“元素滚进来动一下”的需求,再写满屏监听和计算,就有点说不过去了。


说句实在话

更准确的说法不是“JavaScript滚动动画死了”,是很多本来就不该让JS管的滚动动画,终于可以还给CSS了。

前端这几年有些进步我是真喜欢,不是功能变花哨了,是浏览器终于开始接手那些本来就该它干的累活。view()就属于这种。能少写一段滚动监听,就少留一个掉帧的地方。文章页、官网、活动页,用这个东西能省你不少事。

本文内容仅供个人学习、研究或参考使用,不构成任何形式的决策建议、专业指导或法律依据。未经授权,禁止任何单位或个人以商业售卖、虚假宣传、侵权传播等非学习研究目的使用本文内容。如需分享或转载,请保留原文来源信息,不得篡改、删减内容或侵犯相关权益。感谢您的理解与支持!

链接: https://fly63.com/article/detial/13740

相关推荐

js禁止页面滚动

发移动端页面的时候有一个很比较常见的需求,在出现弹窗时,禁止滑动弹窗后面的主体页面。如何实现呢,往下看

js如何实现滚动到一定位置将内容固定在页面顶部

window.onscroll为滚轮监听,document.body.scrollTop||document.documentElement.scrollTop 写两个是为了兼容不同浏览器。固定位置的top要设为负值,原因不明,若为0则会跟上方有空隙。左右位置虽然是0也要设,不然若为不是100%宽度的内容会出现左右跳动。

js 禁止/允许页面滚动

passive,设置该属性的目的主要是为了在阻止事件默认行为导致的卡顿。等待监听器的执行是耗时的,有些甚至耗时很明显,这样就会导致页面卡顿。即便监听器是个空函数,也会产生一定的卡顿,毕竟空函数的执行也会耗时

js实现返回顶部效果的方法总结

当页面特别长的时候,用户想回到页面顶部,必须得滚动好几次滚动键才能回到顶部,如果在页面右下角有个返回顶部的按钮,用户点击一下,就可以回到顶部,对于用户来说,是一个比较好的体验。

js+css 实现 滚动条滑动时显示,不滑动时隐藏

把原有的滚动条隐藏,创建个新的滚动条,并拓展其宽度,达到隐藏的效果,而判断滚动条是否滚动,保存原有的滚动条到顶部的距离,看是否发生改变,做出相应的判断。

使用elementUI滚动条之横向滚动

这里要简单的设置一下,将标签的height设为100%,读者查看效果的时候,会出现一个横向的滚动条,如果你不想要横向的滚动条,使用下面css属性设置就可以只显示竖向滚动条。

BetterScroll移动端滚动场景的应用

BetterScroll 是一款重点解决移动端各种滚动场景需求的开源插件,有下列功能支持滚动列表,下拉刷新,上拉刷新,轮播图,slider等功能。better-scroll通过使用惯性滚动、边界回弹、滚动条淡入淡出来确保滚动的流畅。

原生js获取浏览器获X轴,Y轴的滚动距离

在前端开发中,需要获取浏览器滚动距离的需求,这篇文章主要讲解如何使用原生Js兼容实现获取浏览器获X轴,Y轴的滚动距离。并延伸扩展下我们一些不知道的js知识,希望对你有所帮助。

CSS让页面平滑滚动

在PC浏览器中,网页默认滚动是在<html>标签上的,移动端大多数在<body>标签上,业界浏览器的CSS reset都可以加上这么一条规则:凡是需要滚动的地方都加一句scroll-behavior:smooth就好了!

原生js判断加载更多事件,通过获取页面滚动距离、文档总高度、浏览器视口高度

原生js获取滚动条在Y轴上的滚动距离、获取文档的总高度、获取浏览器视口的高度的方法实现,用于判断页面加载数据。

点击更多...

内容以共享、参考、研究为目的,不存在任何商业目的。其版权属原作者所有,如有侵权或违规,请与小编联系!情况属实本人将予以删除!