我希望当同级div到达视口顶部时,更改div的css属性。
具体来说,我希望“ second-subdiv”仅在“ first-subdiv”到达视口顶部时才具有overflow: scroll
。
基本上,我想在“ second-subdiv”上设置overflow: hidden
,然后写几行js,其中我会说:add.EventListener(when-first-subdiv-is-on-top, change the overflow property)
<div class="first-div">
<h1>Title</h1>
</div>
<div class= "second-div">
<div class="first subdiv">
<h1>You are Beautiful</h1>
</div>
<div class="second subdiv">
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
<h2>Something Good</h2>
</div>
</div>
html, body {
margin: 0;
padding: 0;
}
.first-div {
margin: 0;
width: 100%;
height: 80vh;
background-color: red;
display: flex;
justify-content: center;
align-items: center;
h1 {
color: white;
}
}
.second-div {
display: flex;
justify-content: space-around;
}
.subdiv {
width: 50%;
height: 100vh;
text-align: center;
overflow: scroll;
}
.first.subdiv {
background-color: magenta;
}
.second.subdiv {
}
有什么帮助吗?
谢谢,
马泰奥
最佳答案
我们首先定义一个实现所需样式逻辑的函数。
const EPSILON = 0.5;
function setOverflow () {
var firstDiv = document.querySelector('.first.subdiv');
var secondDiv = document.querySelector('.second.subdiv');
var rect = firstDiv.getBoundingClientRect();
if (Math.abs(rect.top) < EPSILON) {
secondDiv.style.overflow = 'scroll';
}
else {
secondDiv.style.overflow = 'hidden';
}
}
函数
setOverflow
将使用getBoundingClientRect读取.first.subdiv
的位置,并检查其top
坐标是否足够接近零(即窗口的顶部边框),并相应地设置溢出样式属性。由于top
坐标通常不会完全为0,因此EPSILON
变量将足够接近0的公差定义为-0.5至0.5。每当
.first.subdiv
元素的位置更改时,该函数都必须运行,以便可以重新计算溢出属性。您至少需要以下事件:load
,resize
,scroll
,但是根据最终结果,可能还需要更多事件。例如,如果动态添加图像,则.first.subdiv
的位置可能会更改,而不会触发任何上述事件。您可能需要研究Dale Harris的建议并选择Intersection Observer API。为避免过多地重新计算溢出,请将函数调用包装在window.requestAnimationFrame中。
function maybeSetOverflow () {
if (!setOverflow.isBusy) {
setOverflow.isBusy = true;
window.requestAnimationFrame(() => {setOverflow.isBusy = false; setOverflow()});
}
}
window.addEventListener('scroll', maybeSetOverflow);
window.addEventListener('resize', maybeSetOverflow);
window.addEventListener('load' , maybeSetOverflow);
函数
maybeSetOverflow
将忽略对setOverflow的重复调用(如果已调用但未在动画帧中执行)。只需将这两个代码部分包装在
<script>
中,并将其放在<body>
的底部。