将处理程序附加到窗口滚动事件

时间:2011-02-08 02:35:26

标签: javascript jquery javascript-events

John Resig建议使用setInterval()以减少调用处理程序的次数 - 请参阅http://ejohn.org/blog/learning-from-twitter/

约翰在博客文章中提出的解决方案:

var outerPane = $details.find(".details-pane-outer"),
    didScroll = false;

$(window).scroll(function() {
    didScroll = true;
});

setInterval(function() {
    if ( didScroll ) {
        didScroll = false;
        // Check your page position and then
        // Load in more results
    }
}, 250);

可以调用一个持续间隔真的是一个明智的想法吗?

迈克尔杰克逊的方法是否更有意义,因为它并不意味着我们不断进行民意调查?

迈克尔的评论解决方案:

var timer = 0;

$(window).scroll(function () {
  if (timer) {
    clearTimeout(timer);
  }

  // Use a buffer so we don't call myCallback too often.
  timer = setTimeout(myCallback, 100);
});

任何人都可以分享任何建议/意见吗?

2 个答案:

答案 0 :(得分:4)

我正在阅读同一篇文章,但以一些混合的方式结束。

Jhon Resig和MJ对我都不好。虽然我真的很赞赏他们研究的亮点

这是我的代码,它会在事件触发后立即执行,但每250ms运行一次,当它被“重新启用”时

var scrollEnabled = true;

$(window).on('scroll', function(event) {
  if (!scrollEnabled) {
    return;
  }
  scrollEnabled = false; 
  console.log('i am scrolling');
  return setTimeout((function() {
    scrollEnabled = true;
    console.log('scroll enabled now');
  }), 250);
});

答案 1 :(得分:1)

John Resig的方法是最明智的。在大多数现代浏览器中,都会调度滚动事件ALOT。对于y轴上仅50px的快速滚动动作,可以发送20-30次。如果你在每个事件中都调用了一个处理程序,那么你将锁定UI线程并滚动(如John指出的那样)。

另外,请记住,在现代浏览器中,每50ms执行一次快速功能并不是什么大问题。这是每5或6帧的函数调用。您要避免的是每个帧上的函数调用,如果您使用滚动事件,则会发生这种情况。

<强>被修改

哦对不起,当我发布第一个版本时,我错过了那个评论(我只搜索了MJ的名字而不是评论的帖子)。限制scrollEvent处理程序是一种智能方法+1。我实际上比Resig的策略更喜欢它,因为你总是在它发生时获得第一个滚动事件,然后将每次滚动事件限制为每100ms最多抛出一次。

使用Resig的方法,在收到滚动事件通知回拨之前,您可能会延迟最多100毫秒。 100分钟的延迟可能被重度用户视为缓慢的界面。