Help us understand the problem. What is going on with this article?

スクロールしたらメニューバーがトップに固定される方法

More than 5 years have passed since last update.

これは、XOOPSアドベント・カレンダー2012のリレーブログ記事です。

スクロールしたらメニューバーがトップに固定される方法

まずは、画像をご覧ください。私のサイトをテーマ tw_corp で表示させたものですが、1枚目がページトップが表示されており、グローバルメニューはヘッダー画像の下に表示されています。
そして、2枚目が少しスクロールさせたところ・・・グローバルメニューがブラウザ表示の一番上に固定されています。
ページトップ スクロールした状態

これ、グローバルメニューをヘッダー画像の下などに配置しておき、下にスクロールしてメニュー部分がトップに来たらそこに固定される。最近、私が作っているテーマで良く利用している方法です。

デザインとして考えると、メニュー位置をブラウザ表示画面の一番上ではなく、真ん中とかに配置したいこともありますよね? だけど、普通だったらスクロールするとメニューが見えなくなってしまいます。

そんなことを考えてると、javascriptを使うとスクロールしてトップ位置に来たらそこで位置を固定する方法を見つけて、応用することにしました。javascriptでブラウザの動作を判定して、それに応じたcssを適用させるという方法です。

jQueryをtheme.htmlで利用できるように設定

使うのは最近流行のjQuery、XOOPS Cobe Legacy2.2(XCL2.2)がデフォルトで採用しているもので、ちょうど都合が良いですね。XCL2.2を利用しているなら、デフォルトで読み込んでくれるので、特にテーマ内で読み込まなくてもよいのですが、とりあえずtheme.htmlのヘッダに次の記述があるものとして話を進めます。

jQueryの読み込み
<script type="text/javascript" src="<{$xoops_imageurl}>js/jquery-1.7.1.min.js"></script>

ここでは、最小サイズのものを読み込んでいます。

theme.htmlのbodyにメニューの記述

theme.htmlのbodyに次のようなメニュー用の記述をします。

ナビゲーション(グローバルメニュー)
<nav>
<div class="nav">
<ul class="clearfix">
    <li>メニュー1</li>
    <li>メニュー2</li>
    <li>メニュー3</li>
</ul>
</div>
</nav>

詳しくは、私が配布しているテーマを見ていただくとして・・・ここでは、省略して書かせていただきますね。 まあ、たいしたことはしていませんが。

これ、html5のナビゲーションなので

ナビゲーション(グローバルメニュー)
<nav>
<ul class="clearfix">
    <li>メニュー1</li>
    <li>メニュー2</li>
    <li>メニュー3</li>
</ul>
</nav>

でも良いようですが、上手く解釈してくれないブラウザもあるので、あえて div class="nav" も追加しています。(まあ、主にIEが問題なんですけど・・・jQueryでクラスを指定するので、そのためでもあります。)

ulには、変な回り込み防止用のclass="clearfix"を指定します。もちろん、cssで設定するということで。

クラスnavのスタイルは?

ちょっとstyle.cssを見てみましょう。クラスnavはどんなスタイルが指定されているのでしょう?

style.css クラスnavの記述内容
.nav { padding: 0; margin: 0 auto 10px; width: 100%; } 

実は、特に変わったことはしていません。普通のdivです。

positionが書かれていないので、デフォルトのstaticと同じということになりますね。ということは、前の要素に対して普通のdivとして表示されるということで、これでtheme.htmlに記述したデザインどおりの表示になります。

スクロールした時に上部に固定させる仕組みは?

では、スクロールしたときに上部に固定されるにはどうするか? そう、cssのfixedを利用します。
「スクロールしてnavがトップの位置に来たらfixedにする」ということで、jQueryでこれを実現させてあげます。はい。こんな感じです。

theme.htmlでjQUeryの動作を指定する

jQueryの動作指定
<script type="text/javascript">
  jQuery(function() {
    var nav = jQuery('.nav');
    var navTop = nav.offset().top;
    jQuery(window).scroll(function () {
      var winTop = jQuery(this).scrollTop();
      if (winTop >= navTop) {
        nav.addClass('fixed')
      } else if (winTop <= navTop) {
        nav.removeClass('fixed')
      }
    });
});
</script>

クラスnavについて、ウィンドウのトップに来たら、fixedというクラスを追加、ウィンドウのトップよりも下ならそのクラスを削除するという動作になります。

style.cssでトップに固定させるスタイルを指定

そうそう、cssはこんな感じです。

```css:style.css クラスfixed の記述内容

.fixed {
position: fixed;
top: 0;
left: 0;
width: 100%;
}
```

いかがですか? 他にも応用が利きそうですよね?

私のサイト xoops123.com にも是非ご訪問くださいね~(^O^)

Why do not you register as a user and use Qiita more conveniently?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away