Javascript OnScroll性能比较

use*_*091 13 javascript jquery scroll onscroll

所以,假设我想在滚动触发的网站上添加一些昂贵的操作.例如,我在我的jsfiddle中使用视差效果.

现在我继续阅读它不能直接绑定到事件,有时后面的片段应该更好.只是一些例子:

  1. 将JavaScript处理程序附加到滚动事件=不好!
  2. 如何开发高性能onScroll事件?
  3. 如何制作更快的滚动效果?
  4. 60FPS onscroll事件监听器

他们说的基本上不这样做:

  // Bad guy 1
  $(window).scroll( function() {
    animate(ex1);
  });
Run Code Online (Sandbox Code Playgroud)

或这个

  // Bad guy 2
  window.addEventListener('scroll', onScroll, false);
  function onScroll() {
    animate(ex2);
  }
Run Code Online (Sandbox Code Playgroud)

但是使用超时,间隔,requestAnimationFrame等等,例如:

  // Good guy
  $(window).scroll( function() {
   scrolling1 = true;
  });

  setInterval( function() {
    if (scrolling1) {
      scrolling1 = false;
      animate(ex3);
    }
  }, 50 );
Run Code Online (Sandbox Code Playgroud)

所以,我把上面链接中找到的选项添加到jsfiddle,试图通过在每个方法中添加一个计数器来比较它们,如下所示:

  // Test
  $(window).scroll( function() {
    counter = counter + 1;
    // output result of counter
    animate(ex1);
  });
Run Code Online (Sandbox Code Playgroud)

最好先检查完整的jsfiddle或使用旧的浏览器:Scrolltest(相同,只是没有上的jsfiddle)

结果:一切顺利运行的计算数量大致相同.如果我可以忍受波涛汹涌的效果,也许我可以保护一些资源.对于我读到的所有内容,这对我来说似乎合乎逻辑!

第一个问题: 我错过了什么或者这是一个有效的测试吗?如果它无效,我该如何正确测试? 编辑:为了澄清,我想测试上述任何一种方法是否都能保存性能.

第二个问题: 如果它有效,为什么每个人都对onscroll感到紧张?如果流体动画需要在整个站点上进行5000次计算,那么无论如何都无法改变它?

(好吧,有时我使用检查来确定对象是否在视口中,但老实说,我甚至不知道这些检查是否不像阻止的代码本身那么昂贵,特别是如果它们涉及五个不同的变量,如offset,windowHeight,scrolltTop,getBoundingClientRect和outerHeight ...)

Sir*_*ple 7

我不完全确定我的问题和你的所有陈述是否正确但我会尽力给你答案:

  • 我错过了什么或这是一个有效的测试?如果它无效,我该如何正确测试?

如果您正在测量函数被调用的次数,这是一个有效的测试,这当然取决于浏览器,SO,如果是GPU增强以及已经在您的问题中评论的一些其他基准参数.

如果我们认为测量正确,则可以说通过使用超时或者requestAnimationFramework 可以节省时间,因为我们基本上遵循去抖动或限制的原则.基本上我们不想要求或调用函数的次数超过需要的次数.在计时器的情况下,我们将排队较少的函数调用,并且在requestAnimationFrame的情况下,因为它在重新绘制之前将调用排队并且将按顺序执行它们.在超时中,如果计算非常重,则可能会发生重叠.

我找到了一个更好的答案,为什么使用requestAnimationFrame来解释浏览器中动画的主要问题,如剪切,闪烁或帧跳过.它还包括一个很好的演示.

我认为你的测试方法是正确的,你也应该正确地解释它,因为你的硬件和你的引擎可能接近相同数量的呼叫,但正如所说,去抖和限制是一种性能缓解.

这里还有一篇文章支持不将处理程序附加到Twitter的窗口滚动.(免责声明:本文来自2011年,浏览器以不同方式处理滚动优化).

  • 为什么每个人都对onscroll感到紧张?如果流体动画需要在整个站点上进行5000次计算,那么无论如何都无法改变它?

我认为性能损失并不紧张,但是上述动画问题的用户体验将是最糟糕的,因为你的滚动过度调用可能导致,或者即使你的定时器与你的定时器失去同步,你仍然会得到相同的'表现'问题.人们只是建议保存调用滚动,因为:人类视觉持久性不需要超高的帧速率,因此尝试更频繁地显示图像是没用的.对于更复杂的计算或繁重的动画,浏览器已经在进行优化,就像你已经检查过一样,有些浏览器已经优化了这些东西,与2,3或6年前你公开的文章相比.


San*_*dro 5

因此,@ SirPeople已经正确回答了您的第一个问题,查看动画函数被调用的频率确实是一个很好的测试,但是比较不同摘录的性能却是一个糟糕的测试。

这是该执行的性能记录:

性能测试

该功能animate一点也不昂贵。我进行了性能记录(下一张图片),该记录显示我所查看的一次迭代(第1-5点)花费了0.64毫秒至1.29毫秒。一旦完成该功能,重新绘制就根本不需要时间(第6点),这可能是因为页面几乎没有内容。当我们看一下时间时,我们可以看到所有五个动画功能和重新绘制都在不到10ms的时间内完成,这在正常情况下意味着可以得到流畅的60fps动画(第7点)。

另外,如果我们想比较onscroll事件监听器,我们需要自己测试每个事件监听器并比较结果。如果其中一个侦听器确实阻塞了,则会对整个页面产生影响,并且如果不进行性能调试,您将不会知道它是哪一个。

我做了两个jsfiddles window.scrollRAF。而且,令我惊讶的是,似乎没有任何区别。

人们为什么对此感到担忧?

正如您在上面的jsfiddles中看到的那样,如果事件处理程序变得太大,则整个页面将滞后。

怎么办?

我自己不是表演专家,但是: