はじめに
表題通り、スクロールに合わせて表示、非表示を制御するコードを記載します。
成果物
仕組み
現在のスクロール位置、スクロール後の位置を取得し比較。比較の結果、スクロールアップかダウンを検知し、それに合わせてCSSを変更する処理。聞いてみれば意外と単純。。。
ソースコード
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>スクロールアップ</title>
<link rel="stylesheet" type="text/css" href="styles.css">
</head>
<body>
<header id="header">ヘッダー</header>
<main>
<p>要素1</p>
<p>要素2</p>
<p>要素3</p>
<p>要素4</p>
<p>要素5</p>
<p>要素6</p>
<p>要素7</p>
<p>要素8</p>
<p>要素9</p>
<p>要素10</p>
<p>要素11</p>
<p>要素12</p>
<p>要素13</p>
<p>要素14</p>
<p>要素15</p>
<p>要素16</p>
<p>要素17</p>
<p>要素18</p>
<p>要素19</p>
<p>要素20</p>
<p>要素21</p>
<p>要素22</p>
<p>要素23</p>
<p>要素24</p>
<p>要素25</p>
</main>
<footer id="footer">ヘッダー</footer>
<script src="script.js"></script>
</body>
</html>
styles.css
body {
padding: 0;
margin: 0;
}
header {
display: flex; /* Flexコンテナを使用して水平・垂直方向に中央揃えにする */
justify-content: center; /* 水平方向の中央揃え */
align-items: center; /* 垂直方向の中央揃え */
position: fixed;
background: #ddd;
background-color: antiquewhite;
padding: 0;
width: 100%;
height: 90px;
margin-top: 0px;
transition: margin 100ms;
}
footer {
display: none;
background: #333;
color: #fff;
padding: 20px;
text-align: center;
}
.scroll-down header {
margin-top: -90px;
}
.scroll-up header {
margin-top: 0px;
}
main {
height: 200vh;
background: #ccc;
padding: 120px 30px;
}
script.js
// スクロール前のスクロール位置を保持する変数
let lastScrollPosition = window.scrollY;
// 現在のスクロール位置を保持する変数
let currentScrollPosition = 0;
// requestAnimationFrameの実行中かどうかを保持する変数。過剰な発火を防ぐ
let ticking = false;
function scrollUpDown(scrollPos, lastScrollPos) {
// 現在のスクロール位置が前回のスクロール位置よりも大きい場合、スクロールダウンを検知
if (scrollPos > lastScrollPos) {
// スクロールダウン
document.body.classList.remove('scroll-up');
document.body.classList.add('scroll-down');
console.log('SCROLLING DOWN: scrollPos: ',scrollPos,"lastScrollPos", lastScrollPos)
} else {
document.body.classList.add('scroll-up');
document.body.classList.remove('scroll-down');
console.log('SCROLLING UP: scrollPos: ',scrollPos,"lastScrollPos", lastScrollPos)
}
}
// ウインドウのスクロールイベントを監視
window.addEventListener('scroll', function (e) {
// スクロールイベントが発火したら、現在のスクロール位置を保持する
currentScrollPosition = window.scrollY;
//スクロールイベントの過剰な実行を制御します。
if (!ticking) {
// requestAnimationFrameを使って、scrollUpDown関数を実行する
window.requestAnimationFrame(function () {
scrollUpDown(currentScrollPosition, lastScrollPosition);
lastScrollPosition = currentScrollPosition;
ticking = false;
});
ticking = true;
}
});