JSFiddle - React, Tailwind, and code Playground
HTML
<header><div>menu1</div><div>menu2</div></header>
<section class="Gray">
<div>contentsGray</div>
</section>
<section class="Red">
<div>contentsRed</div>
</section>
<section class="Blue">
<div>contentsBlue</div>
</section>
CSS
body {
background: #fff;
padding: 0;
margin: 0;
}
section {
height: calc(100vh - 50px);
padding: 50px 0 0 0;
background: gray;
}
section.Red.is_view{
background: red;
}
section.Blue.is_view{
background: blue;
}
header {
display: flex;
align-items: center;
justify-content: space-evenly;
position: fixed;
top: 0; right: 0; left: 0;
height: 50px;
background: black;
color: white;
}
JavaScript
const opts = {
root: null, // 任意のHTML*Elementを指定して表示領域を設定できる
rootMargin: '50px 0px 0px 0px', // viewport(root)のマージン指定例
// 監視対象の交差率でイベント発火回数を指定
// 未表示 <-- --> 表示しきった(解釈が微妙ですが)
threshold: [0, 0.25, 0.75, 1]
};
let iObserver = new IntersectionObserver((entries) => {
// entries is {Array.<IntersectionObserverEntry>}
entries.forEach( (entry, idx) => {
/*
console.log({
entryNumber: idx,
isIntersecting: entry.isIntersecting,
intersectionRatio: entry.intersectionRatio,
rootBounds: JSON.stringify(entry.rootBounds),
boundingClientRect: JSON.stringify(entry.boundingClientRect),
intersectionRect: JSON.stringify(entry.intersectionRect )
});
*/
let elm = entry.target;
// 指定した threshold と比較できる プロパティが intersectionRatio の様子
/*
if( entry.intersectionRatio < 0.25 || 0.75 < entry.intersectionRatio ) {
elm.classList.remove("is_view");
console.log(elm.className + 'を脱色');
return;
}
*/
if( entry.isIntersecting ){
console.log(elm.className + 'を着色');
elm.classList.add('is_view');
}
});
}, opts);
// 監視対象要素を登録
//iObserver.observe( document.querySelector(".Gray") );
iObserver.observe( document.querySelector(".Red") );
//iObserver.observe( document.querySelector(".Blue") );