ハシウェブ

Web制作、プログラミングに関する情報を発信するブログ

スクロールアニメーションを実現!Intersection Observer APIの使い方 デモあり

スクロールアニメーションを実現!Intersection Observer APIの使い方 デモあり

「動きがあるWebサイトをつくりたい」
「スクロールしたあとにフワっとアニメーション表示させたい」

悩み

こんな悩みにお答えします。

これまではjavascript(jQuery)でscrollイベントを使って地道に設定していくか、wow.js等のプラグインを使って設定していましたが、最近では、Intersection Observer APIを使うこと動きのあるWebサイトを実現させることができます。

この記事では、以下のことがわかります。

  • Intersection Observer APIの使い方
  • Intersection Observer APIを使ったデモを5つ紹介

記事を読み終えると、スクロールに連動した動きのあるWebサイトをつくることができます。

目次
  1. 使い方
    1. 読み込まなくていい
    2. オプションを指定する
    3. cssで動きを指定する
  2. デモ
    1. 下からフワっとfadeIn
    2. 右からフワっとfadeIn
    3. 背景色の変更
    4. 左から右へ横切る
    5. 表示セクションとドットナビゲーションの連動
  3. まとめ

使い方

読み込まなくていい

他のサイトで紹介されているのを見て、「なんで読み込むプラグイン書いてないの?不親切だな。」ってなりましたが、読み込まなくていいんです。
jsプラグインをいろいろ使っている人のほうが最初驚くと思います。
ブラウザがデフォルトで持っている機能だそうです。

ただ、IEには対応していないので、IE対応が必要な場合はpolifillを読み込む必要はあります。
以下をfooterに貼り付けてください。

//HTMLの場合
<script src="https://cdn.jsdelivr.net/npm/intersection-observer@0.9.0/intersection-observer.js"></script>

//PHPが使える場合 (IEのときだけ読み込む)
<?php 
	// ブラウザ取得判定するのに小文字にする
	$browser = strtolower($_SERVER['HTTP_USER_AGENT']);
	// ブラウザ判定
	if (strstr($browser , 'trident') || strstr($browser , 'msie')) {
?>
<script src="https://cdn.jsdelivr.net/npm/intersection-observer@0.9.0/intersection-observer.js"></script>
<?php 
	}
?>

オプションを指定する

以下のコードをfooterに記載します。
動かしたい要素(監視対象の要素)にclassを指定します。
(デモでは「js-monitored」というclass名を指定しました。)

基本的には、これだけで動作します。
監視対象がエリアに入ってきたらclassに「show」が追加されます。
開発ツールでスクロールさせながら確認して「show」が追加されれば成功です。

var boxes = document.querySelectorAll(".js-monitored");
var boxesArray = Array.prototype.slice.call(boxes, 0);
var options = {
  root: null,
  rootMargin: "0px 50%",
  threshold: 0,
};
var observer = new IntersectionObserver(doWhenIntersect, options);
boxesArray.forEach(function (box) {
  observer.observe(box);
});

function doWhenIntersect(entries) {
  var entriesArray = Array.prototype.slice.call(entries, 0);
  entriesArray.forEach(function (entry) {
    if (entry.isIntersecting) {
      entry.target.classList.add("show");
    }
  });
}

cssで動きを指定する

動きはcssで指定します。
よくあるフェイドインアップであれば、以下のように指定します。

.fadeInUp {
  position: relative;
  bottom: -50px;
  opacity: 0;
  transition: bottom 1s, opacity 1s;
}
.fadeInUp.show {
  bottom: 0;
  opacity: 1;
}

デモ

下からフワっとfadeIn

HTML
<h1 class="js-monitored fadeInUp">intersection observerデモ</h1>
CSS
.fadeInUp {
  position: relative;
  bottom: -50px;
  opacity: 0;
  transition: bottom 1s, opacity 1s;
}
.fadeInUp.show {
  bottom: 0;
  opacity: 1;
}

右からフワっとfadeIn

HTML
<img class="js-monitored inRight" src="apple.png" alt="りんご">
CSS
.inRight {
  position: relative;
  right: -100px;
  opacity: 0;
  transition: right 1s, opacity 1s;
}
.inRight.show {
  right: 0;
  opacity: 1;
}

背景色の変更

HTML
<section id="section3" class="js-section section js-monitored bgChange">
  <p>背景チェンジ</p>
</section>
CSS
.bgChange {
  transition: background-color 2s;
  transition-delay: 1s;
}
.bgChange.show {
  background-color: green;
}

左から右へ横切る

HTML
<section id="section4" class="js-section section js-monitored across">
  <p>横切る</p>
</section>
CSS
.across {
  overflow: hidden;
  position: relative;
}
.across:before {
  content: "";
  position: absolute;
  left: -100%;
  top: 0;
  width: 100%;
  height: 100vh;
  background-color: blue;
  opacity: 0;
  transition: left 1s, opacity 1s;
  transition-delay: 1s;
}
.across.show:before {
  left: 100%;
  opacity: 1;
}

表示セクションとドットナビゲーションの連動

これまでのIntersection Observer APIの動きを応用して、スクロールとドットナビゲーションさせて現在のセクションをわかりやすくし、リンクもさせます。
javascriptを基本のものから変更していきます。

javascript
  var nodelist = document.querySelectorAll(".js-section");
  var node = Array.prototype.slice.call(nodelist, 0);
  var options = {
    root: null,
    rootMargin: "-50% 0px",
    threshold: 0,
  };
  var observer = new IntersectionObserver(doWhenIntersect1, options);

  node.forEach(function (section) {
    observer.observe(section);
  });

  function doWhenIntersect1(entries) {
    //console.log(entries);
    entries.forEach(function (entry) {
      if (entry.isIntersecting) {
        activateIndex(entry.target);
      }
    });
  }

  function activateIndex(element) {
    var currentActiveIndex = document.querySelector("#indexList .active");

    if (currentActiveIndex !== null) {
      currentActiveIndex.classList.remove("active");
    }

    var newActiveIndex = document.querySelector("#indexList a[href='#" + element.id + "']");
    newActiveIndex.classList.add("active");
  }

まとめ

Intersection Observer APIの使い方を紹介しました。

Intersection Observer APIで、指定した要素が設定表示エリアまできたらclassに「show」が追加されるだけなので、動きはcssで自由に指定できます。
transition-delay等を使えば、もっと複雑な動きを連動させられます。