在原生 javascript (2020) 中同步 2 个 div 之间的滚动

synchronise scrolling between 2 divs in native javascript (2020)

我正在尝试制作一个 fake/duplicated 滚动元素,该元素与原生 javaScript 中 div 的实际 x 滚动同步。我的用例是在很长的 table 上,当您不在 table.

的底部时,让 x 滚动出现在屏幕上

这解决了具有超宽 table 且最小宽度超过当前 page/view-port 宽度,导致 table 变为 side/x-scroll 的情况。但是,如果 table 很长,滚动条只能设置在 table 的顶部或底部。这意味着如果人们在 table 的中间位置并想要滚动查看所有列,他们将很难在那里做到这一点。

见图:

是的,在 JQUERY 中已经死了。根据我的研究,SO 上没有人知道或有兴趣在原生 javaScript(尤其是 2020 年)中执行此操作。我的参考版本也在jQuery,需要转换

  $dupScroll.scroll(function () {
    if (scrolling) {
      scrolling = false;
      return true;
    }
    scrolling = true;
    $tableParent.scrollLeft($dupScroll.scrollLeft());
  });
  $tableParent.scroll(function () {
    if (scrolling) {
      scrolling = false;
      return true;
    }
    scrolling = true;
    $dupScroll.scrollLeft($tableParent.scrollLeft());
  });

全部jQuery解:

  1. How to Scroll two div's at the same time?
  2. synchronizing scrolling between 2 divs
  3. synchronizing scrolling between 2 divs with different text size
  4. synchronise scrolling of two divs

感谢您提供帮助,这对所有需要做同样事情的人都是有用的 post-jQuery。我目前正在自己​​处理这个问题,但 运行 到处都是障碍,第一个是将滚动事件附加到元素上。如果我做了一些有用的东西,我会 post 放在这里。谢谢。

这是保持两个 div 对齐的简单方法。 Javascript 默认情况下不会在脚本的操作上分派事件,因此无需跟踪正在滚动的 div。

const divs = document.querySelectorAll( 'div' );

divs.forEach(div => div.addEventListener( 'scroll', e => {
  
  divs.forEach(d => {
  
    d.scrollTop = div.scrollTop;
    d.scrollLeft = div.scrollLeft;
  
  });
  
}) );
html, body {

  height: 100%;
  
}
body {

  display: flex;
  padding: 0;
  margin: 0;

}
div {

  width: 50%;
  height: 100%;
  overflow: scroll;

}
span {

  width: 200vw;
  height: 300vh;
  display: block;
  background: linear-gradient(90deg, transparent, yellow), linear-gradient( 0deg, red, blue, green );
  
}
#div2 {

  margin-top: 30px;
  
}
<div id="div1"><span></span></div>
<div id="div2"><span></span></div>

在不同大小的容器中使用相对滚动

如果您想使用不同大小的容器和相对滚动来完成此操作,只需标准化滚动值并再次乘以它:

const divs = document.querySelectorAll( 'div' );

divs.forEach(div => div.addEventListener( 'scroll', e => {
  
  const offsetTop = div.scrollTop / (div.scrollHeight - div.clientHeight);
  
  const offsetLeft = div.scrollLeft / (div.scrollWidth - div.clientWidth);
  
  divs.forEach(d => {
  
    d.scrollTop = offsetTop * (d.scrollHeight - d.clientHeight);
    d.scrollLeft = offsetLeft * (d.scrollWidth - d.clientWidth);
    
  });
  
}) );
html, body {

  height: 100%;
  
}
body {

  display: flex;
  padding: 0;
  margin: 0;

}
div {

  width: 50%;
  height: 100%;
  overflow: scroll;

}
span {

  width: 200vw;
  height: 300vh;
  display: block;
  background: linear-gradient(90deg, transparent, yellow), linear-gradient( 0deg, red, blue, green );
  
}
#div2 span {
  
  height: 500vh;
  width: 500vw;
  
}
<div id="div1"><span></span></div>
<div id="div2"><span></span></div>