要素をスクロールに追随させたいならsticky!

画面のスクロールに合わせて特定の要素が追随してくるようなWEBサイトを見たことがありませんか?

ヘッダー部分がページの先頭から終わりのスクロールまでずっと付いてくるというような追随の仕方ではなく、スクロールの途中に出現した要素が、それからずっと付いてくるような感じの追随です。

ゆんつ
このブログをPCで見ている場合、サイドバーにある「もくじ」がそのような感じになってます

こういう仕組みを見るとjQueryなどで実装してそうな感じがありますが、CSSだけで簡単に実装することができます。

今日はサイドバーの要素をスクロールに合わせて追随させてみます。

実装

要素をスクロールにあわせて追随させるにはCSSのstickyというプロパティを利用します。

方法は簡単で

  • スクロールに追随させたい要素のpositionにstickyを設定する
  • top、bottom、left、rightで固定する位置を設定する

の2点です。

さっそく具体的にコードを書いていきたいと思います。

<body>
  <div id="wrapper">
    <header>ヘッダー</header>

     <div id="content">
      <main id="main">メイン画面</main><!-- /#main -->
      <aside id="secondery">
        <div class="widget widget1">1</div>
        <div class="widget widget2">2</div>
        <div class="widget widget3">3</div>
      </aside><!-- /#secondery -->
    </div><!-- /#content -->

    <footer>フッター</footer>
    
  </div><!-- /#wrapper -->
</body>
body {
  font-weight: 700;
  color: white;
  font-size: 30px;
}

#wrapper {
  width: 70%;
  margin: auto;
}

header {
  height: 100px;
  line-height: 100px;
  background: red;
  text-align: center;
}

#content {
  display: flex;
  height: 1000px;
}

#main {
  width: 70%;
  background: green;
  line-height: 1000px;
  text-align: center;
}

#secondery {
  width: 29%;
  margin-left: auto;
}

.widget {
  height: 100px;
  line-height: 100px;
  text-align: center;
}

.widget1 {
  background: orange;
  margin-bottom: 10px;
}

.widget2 {
  background: brown;
  margin-bottom: 10px;
}

/* stickyの設定と位置の調整 */
.widget3 {
  background: pink;
  position: sticky;
  top: 10px;
}

footer {
  height: 100px;
  line-height: 100px;
  background: blue;
  text-align: center;
}

ヘッダー、フッター、メイン画面とサイドバーで構成された、ブログなどでよく見かけるオーソドックスな構成です。

こちらがデモになります。

スクロールさせてみてください。

See the Pen sticky by konpure (@yuntu) on CodePen.

スクロールによりサイドバーにあるピンク色の「3」 という要素が出現すると、その後ピンク色の「3」はメイン画面のスクロールに合わせて追随してくるのが解ると思います。

このピンクの「3」という要素にはCSSで「position: sticky」と「top: 10px」が設定されています。

ですので画面をスクロールしてサイドバーに「3」の要素が現れると、topから10pxの位置で固定されてスクロールに追随するようになります。

topの数値を変更することで追随するときの要素の位置を自分の好きなように変更することが出来ます。

注意点

stickyの使用にあたり、ちょっとだけ注意点があります。

親要素や祖先の要素にoverflow: hiddenがあるとうまく使えないことがある

position: stickyは親要素や祖先の要素にoverflow: hiddenがあるとうまく動作しないことがあるようです。

先ほどと同じコードで、全体を包む.wapperというクラスにoverflow-x: hiddenを設定してみると

See the Pen sticky_overflow_x by konpure (@yuntu) on CodePen.

スクロールしてもstickyが設定されたピンク色の「3」が追随してきません。

うまく動作しない場合はCSSのoverflowの値を探ってみると良いかもしれません。

カラムの高さを揃えること

2カラムでの構成の場合、メインカラムと追随させたい要素があるサイドカラムの高さは同じである必要があります。

先ほどの例では2カラムの部分はflexboxで作成したので互いの高さは一致しています。

でも、これをサイドバー側は高さを設定せずにfloatで作成したらメイン画面とサイドバーの高さが合わなくなります。

すると以下のようにstickyが働きません(サイドバーにメインと同じ高さを設定すればちゃんと働きます)

See the Pen sticky_height by konpure (@yuntu) on CodePen.

ですのでstickyを使う際はカラムの高さを揃えることが必要です。

便利だと思います

長い文章を読んでいる途中で目次がみたくなったときなどに、いちいち最初の方までもどって目次を確認するのは結構面倒くさいです。

そのようなときにサイドバーに目次が追随してくれていると便利です。

position: fixedでは最初から画面の特定の位置に固定されますが、stickyは設定した要素が スクロールにより画面内に現れるまでは固定されませんし、逆方向にスクロールして本来要素が見えない位置になるとサッと位置の固定が解除されるので使い勝手が良いです。

上手に使って、読みやすいブログを作りたいですね。

ゆんつ
それでは、またー。