首页 > 解决方案 > 我的脚本没有显示真正可见的元素

问题描述

我发现了有关如何执行此类操作的帖子和在线文章,但大多数示例都不是纯 JavaScript。因此,如果所有部分的高度相同,例如 220 像素,则此脚本几乎可以完美运行。所以我想我越来越接近让这个脚本工作我希望它像加班一样工作,但后来我意识到

当我决定更改部分高度并更多地使用代码以查看它是否有任何我不知道的缺陷时,它有缺陷,所以基本上这个脚本旨在输出名称

可见但未显示正确输出的部分,例如,如果部分 1 是 div 中唯一可见的部分,它将显示 section-1 如果多个部分可见,它将显示例如 section-1,section -2 等。基本上它应该像这样工作,无论部分高度如何

示例 1

示例 2

我知道我必须更改代码或对其进行更改,但是我玩得越多,我就越感到困惑,那么我该如何解决这个问题,以便始终获得正确的输出?如果我必须完全更改我的代码才能做到这一点,那么我不介意。

这是我的代码

document.addEventListener('DOMContentLoaded',function(){

document.querySelector('#building').addEventListener('scroll',whichSectionsAreInSight);

function whichSectionsAreInSight(){
  var building= document.querySelector('#building');
  var top = building.scrollTop;
  var bottom = top+building.offsetHeight;
  var arr = [];
  
  Array.prototype.forEach.call(
  building.querySelectorAll('#building .sections'),
  
 function(sections){
    if ((sections.offsetTop < top && top <sections.offsetTop+sections.offsetHeight) || (sections.offsetTop < bottom && bottom < sections.offsetTop+sections.offsetHeight)){
      arr.push(sections.id);
    }
   
   }
   
  );
	
  document.querySelector('#status').innerHTML = arr.join(',')
}

  whichSectionsAreInSight();
  
});
h1{
  margin: 0;
  text-align: center;
}
#building{
  background-color: gray;
  height: 200px;
  width: 200px;
  overflow: auto;
}
.sections{
  height: 80px;
  width: 100%;
}
#section-1{
    background-color: dodgerblue;
}
#section-2{
    background-color: gold;
}
#section-3{
    background-color: red;
}
#section-4{
    background-color: gray;
    height: 220px;
}
<p id='status'></p>
<div id='building'>
  <div id='section-1' class='sections'><h1>Section 1</h1></div>
  <div id='section-2' class='sections'><h1>Section 2</h1></div> 
<div id='section-3' class='sections'><h1>Section 3</h1></div>
  <div id='section-4' class='sections'><h1>Section 4</h1></div>
</div>

标签: javascript

解决方案


你非常接近!

首先,您需要将父元素设置为,position:relative否则要衡量的父元素是文档。

此外,该算法比您所拥有的更简单。只要确保元素的顶部小于父元素的底部,并且元素的底部大于父元素的顶部。

在你的情况下,这是offsetTop < bottomoffsetTop + offsetHeight > top

document.addEventListener('DOMContentLoaded', function() {

  document.querySelector('#building').addEventListener('scroll', whichSectionsAreInSight);

  function whichSectionsAreInSight() {
    var building = document.querySelector('#building');
    var top = building.scrollTop;
    var bottom = top + building.offsetHeight;
    var arr = [];

    Array.prototype.forEach.call(
      building.querySelectorAll('#building .sections'),

      function(section) {
        if (section.offsetTop < bottom && section.offsetTop + section.offsetHeight > top) {
          arr.push(section.id);
        }
      }

    );

    document.querySelector('#status').innerHTML = arr.join(',')
  }

  whichSectionsAreInSight();

});
h1 {
  margin: 0;
  text-align: center;
}

#building {
  background-color: gray;
  height: 200px;
  width: 200px;
  overflow: auto;
  position: relative;
}

.sections {
  height: 80px;
  width: 100%;
}

#section-1 {
  background-color: dodgerblue;
}

#section-2 {
  background-color: gold;
}

#section-3 {
  background-color: red;
}

#section-4 {
  background-color: gray;
  height: 220px;
}
<p id='status'></p>
<div id='building'>
  <div id='section-1' class='sections'>
    <h1>Section 1</h1>
  </div>
  <div id='section-2' class='sections'>
    <h1>Section 2</h1>
  </div>
  <div id='section-3' class='sections'>
    <h1>Section 3</h1>
  </div>
  <div id='section-4' class='sections'>
    <h1>Section 4</h1>
  </div>
</div>


推荐阅读