今回は、特定の位置までスクロールすると、上からひょこっとグローバルナビやヘッダーが出てきて、そのまま追従する方法を紹介します。
文字で説明するよく分かりませんね。
百聞は一見に如かず。意味不明だと思った方は、下のデモをご覧ください。
こういう動きを取り入れているサイトはたまに見かけますね。
これをjQueryは使わず、HTML、CSS、生のJavaScriptで実装します。
特定の位置までスクロールする追いついてきて、上に固定されるメニューの実装方法
それでは、実装方法を書いていきます。
HTML
<header id="header" class="header">
<nav class="global-nav" id="js-global-nav">
<ul class="global-nav__list">
<li><a href="">メニュー1</a></li>
<li><a href="">メニュー2</a></li>
<li><a href="">メニュー3</a></li>
<li><a href="">メニュー4</a></li>
<li><a href="">メニュー5</a></li>
</ul>
</nav>
</header><!-- /header -->
ポイントは、ナビに「js-global-nav」というidをふっているところです。
CSS
お次はCSSです。
.header {
height: 50px;
background-color: #fff;
box-shadow: 0 2px 2px rgba(0,0,0,.2);
}
.global-nav {
position: absolute;
width: 100%;
z-index: 10;
}
.global-nav__list {
margin: 0;
padding: 0;
list-style: none;
display: flex;
justify-content: center;
}
.global-nav__list li {
padding: 0 14px;
}
.global-nav__list li a {
display: block;
height: 50px;
line-height: 50px;
color: #111;
text-decoration: none;
}
.global-nav.clone-nav {
position: fixed;
top: -100px;
left: 0;
transition: all 1s;
background-color: #fff;
box-shadow: 0 2px 2px rgba(0,0,0,.2);
}
.global-nav.clone-nav.is-fixed-nav {
top: 0;
}
この段階では下のあたりのCSSはよく分からないと思います。そこはJavaScriptのコードの後に解説します。
JavaScript
/**
* グローバルナビのクローンを生成
*/
function setCloneNav() {
var body = document.body;
var globalNav = document.getElementById('js-global-nav');
if(!globalNav) return;
var cloneNav = globalNav.cloneNode(true);
cloneNav.id = 'js-clone-nav';
cloneNav.classList.add('clone-nav');
body.insertBefore(cloneNav, body.firstChild);
}
setCloneNav();
/**
* グローバルナビのクローンをページ上部に移動・固定
*/
function fixedGlobalNav() {
var scrollY = window.pageYOffset;
var trigger = document.getElementById('js-trigger');
var cloneNav = document.getElementById('js-clone-nav');
if(!cloneNav || !trigger) return;
var triggerClientRect = trigger.getBoundingClientRect();
var triggerY = scrollY + triggerClientRect.top;
if(scrollY > triggerY) {
cloneNav.classList.add('is-fixed-nav');
} else {
cloneNav.classList.remove('is-fixed-nav');
}
}
window.addEventListener('scroll', fixedGlobalNav);
最初の setCloneNav() は、グローバルナビを複製する関数です。
複製されたグローバルナビには、js-clone-navというidと、clone-navというclassを付けています。
上のCSS見ていただければ分かりますが、top: -100pxにして画面の外に隠しています。
二つ目の関数 fixedGlobalNav() は、id=”is-trigger”の位置までくるとメニューを表示させます。
id=”is-trigger” の位置まで来ると、.is-fixed-navが加わり、top:-100px → top: 0となり、上からにょきっと現れるのです。
要素が見つからない場合、処理を止める
上のJavaScriptのコードにある、
if(!globalNav) return;
と、
if(!cloneNav || !trigger) return;
は、要素がない場合それ以降の処理を止めるために記述します。
要素が見つからないのに、処理を進めるとエラーの原因になったり無駄なコードが動いたりするので、止めましょう。
まとめ
仕組みさえ分かってしまえば、結構簡単な処理です。
最初からfixedで固定させるより、あとから追従させた方が良い感じですね。
最後に、もう一度デモのリンクを貼っておきます。
他にもこんな記事があります。
CSSだけでサイドバーを固定・スクロール追従する方法(JavaScript不要)