2015-07-20 230 views
1

我的网站有一个弹出窗口,显示有关在主屏幕中显示的元素的附加信息。我需要同步两个窗口之间的滚动,当用户滚动其中一个窗口时,另一个窗口会自动滚动到同一个ammount中。如何在两个窗口之间同步滚动

我能够做到这一点使用jQuery的滚动事件,并使用scrollTop函数来设置滚动位置。是这样的:

$("#localDiv").scroll(function() {   
    var scrollPos = $("#localDiv").scrollTop(); 
    $("targetElement").scrollTop(scrollPos); 
}); 

我已经简化了实际的代码,因为我已经做了一些工作,以达到在另一个窗口中的元素,但这不是问题。

问题是,此代码在Chrome和IE中正常工作,但在FireFox中滚动变得非常慢。

我在这里创建了一个示例:http://jsfiddle.net/Lv2dw787/4/。这个问题似乎也与DIV在同一页面中出现。您可以注意到,当滚动同步被禁用时,速度将恢复正常。

有没有人有关于如何解决这个问题的线索在FireFox?戴夫·陈回答后


编辑:

接受的答案解决我的问题,但它有一个陷阱。我第一次尝试这样做:

lock = true; 
try { 
    var scrollPos = $("#contentDivA").scrollTop(); 
    $("#contentDivB").scrollTop(scrollPos); 
} 
finally 
{ 
    lock = false; 
} 

$("#contentDivB").scrollTop(scrollPos);线似乎只有当前函数执行完毕后产生的DIVB滚动事件,所以try..finally的最后部分是之前执行。因此,我不得不这样:

lock = true; 

var scrollPos = $("#contentDivA").scrollTop(); 
$("#contentDivB").scrollTop(scrollPos); 

和DIVB滚动事件:

if (lock) 
    lock = false; 
else { 
    (Do the scroll on DivA) 
} 
+1

工作正常。你有没有试过第二台电脑,并确认它不是本地安装?你的Firefox只是很慢吗? – Jan

+0

我可以确认它在Mac上的FireFox上运行得更慢 –

回答

4

的原因是因为两个原因:

  1. Firefox没有它滚动
  2. jQuery的平滑scrollTop将触发事件

让我们看看一些伪代码:

When divA is scrolled -> scroll divB to the same spot 
When divB is scrolled -> scroll divA to the same spot 

的问题是,当你scroll divA or divB to the same spot,也会导致when再次发生。

因此,例如,当您滚动耍大牌,这是发生了什么:

scroll divA -> scroll divB to the same spot -> scroll divA to the same spot 

这将导致DIVA坚持在同一地点滚动一点之后,因而是什么原因导致在firefox低迷的影响。

一个解决方法就是忽略滚动事件滚动时:我的Mac上的Firefox

$(document).ready(function() { 

    var ignore = false; 

    $("#contentDivA").scroll(function() { 
     var tmpIgnore = ignore; 
     ignore = false; 
     if (!tmpIgnore && $("#chkSyncEnabled")[0].checked) 
     { 
      var scrollPos = $("#contentDivA").scrollTop(); 
      scrollTop($("#contentDivB"), scrollPos); 
     } 
    }); 

    $("#contentDivB").scroll(function() { 
     var tmpIgnore = ignore; 
     ignore = false; 
     if (!tmpIgnore && $("#chkSyncEnabled")[0].checked) 
     { 
      console.log("here"); 
      var scrollPos = $("#contentDivB").scrollTop(); 
      scrollTop($("#contentDivA"), scrollPos); 
     } 
    }); 

    function scrollTop(el, position) { 
     ignore = true; 
     el.scrollTop(position); 
    } 
}); 

Example

+0

我看到它运行在您发送的示例上,但我无法理解为什么。 :)。如果ignore最初被设置为true,并且tmpIgnore被设置为忽略,并且if语句是“if(!tmpIgnore”,if语句内部的代码如何执行的呢? – Marlon

+0

哦,现在我明白了,这只会发生 – Marlon

+0

对不起,忽略的初始值是什么都没有关系,重要的是忽略会作为一个标志,检测它是一个人的滚动还是当电脑滚动时其他div –