Javascript

【anime.js】を使用したアニメーション①

完成イメージが以下になります。

ラインと画像がフェードインした後に、
テキストが順番にフェードインアップするアニメーションです。

【anime.js】とスクロールで発火させるプラグイン【jquery.inview】を使用してアニメーションを実装します。


【anime.js】の基本的な使用方法は以下から


軽量アニメーションJavascriptライブラリ【anime.js】を使ってみた

サンプルコード

HTML

<!-- contents start -->
<div class="container">
    <section data-fadeup-delay="0.3" class="content_item js-inview">
        <div class="content_wrap">
            <div class="content_imgBox anime_fadeUpWrap">
                <img data-delay-reset="on" class="anime_target" src="img/img_01.png" alt="">
            </div>
            <div class="content_textBox">
                <h2 class="content_heading">
                    <div class="textWrap">
                        <div class="anime_fadeUpWrap"><span class="text anime_target">Block FadeUp</span></div><span class="textDeco anime_widthRight"></span>
                    </div><br>
                    <div class="textWrap">
                        <div class="anime_fadeUpWrap"><span class="text anime_target">Title</span>
                        </div><span class="textDeco anime_widthRight"></span>
                    </div>
                </h2>
                <div class="anime_fadeUpWrap">
                    <p class="content_text anime_target">Block FadeUp Text.Block FadeUp Text. Block FadeUp Text. Block FadeUp Text. Block FadeUp Text. Block FadeUp Text. Block FadeUp Text. Block FadeUp Text.</p>
                </div>
                <div class="anime_fadeUpWrap">
                    <div class="content_btn anime_target"><a href="#">Read More</a></div>
                </div>
            </div>
        </div>
    </section>
</div>
<!-- contents end -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.4/jquery.min.js"></script>
<script src="js/jquery.inview.min.js"></script>
<script src="js/anime.min.js"></script>
<script src="js/main.js"r></script>

スクリプトの読み込み

必要なスクリプトを読み込ませます。

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.4/jquery.min.js"></script>
<script src="js/jquery.inview.min.js"></script>
<script src="js/anime.min.js"></script>
<script src="js/main.js"r></script>

アニメーションは【anime.js】の他に、スクロールで発火させるため【jquery.inview】を使用しています。

「jquery.inview」はjQueryに依存するため、合わせて読み込みます。

inviewの発火

スクロール発火用のclassを「js-inview」としてアニメーションのラップ要素に指定します。

今回の場合sectionに指定しているため、sectionが見えたタイミングで発火するようになっています。

<section  class="content_item js-inview">

フェードアップアニメーションの設定

ポイントはフェードインさせたい要素「anime_target」を初期表示では隠れるように「anime_fadeUpWrap」で囲います。

<div class="content_imgBox anime_fadeUpWrap">
 <img data-delay-reset="on" class="anime_target" src="img/img_01.png" alt="">
</div>

タイトルのラインアニメーションの設定

タイトルのラインアニメーション用のクラスに「anime_widthRight」を指定します。

<span class="textDeco anime_widthRight"></span>

CSS

.anime_fadeUpWrap {
  overflow: hidden;
}

.anime_target {
  -webkit-transform: translateY(-110%);
          transform: translateY(-110%);
}

.anime_widthRight {
  width: 0;
}

.content {
  position: relative;
}

.content_item {
  position: relative;
  width: 100%;
  min-height: 100vh;
  top: 0;
  left: 0;
  z-index: 0;
  opacity: 1;
  background: #000 url(https://images.unsplash.com/photo-1579722353261-8beb38ddff96?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=3004&q=80) no-repeat center;
  background-size: cover;
}

.content_item::after {
  position: absolute;
  content: "";
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  background: rgba(0, 0, 0, 0.7);
  z-index: 1;
}

.content_wrap {
  position: absolute;
  width: 92%;
  top: 50%;
  left: 50%;
  -webkit-transform: translate(-50%, -50%);
          transform: translate(-50%, -50%);
  height: 100%;
  z-index: 2;
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
  -webkit-box-align: center;
      -ms-flex-align: center;
          align-items: center;
  -webkit-box-orient: horizontal;
  -webkit-box-direction: reverse;
      -ms-flex-direction: row-reverse;
          flex-direction: row-reverse;
}

@media screen and (max-width: 960px) {
  .content_wrap {
    display: block;
  }
}

.content_imgBox {
  margin: 0 auto;
}

@media screen and (min-width: 961px) {
  .content_imgBox {
    padding-top: 0;
    padding-bottom: 0;
  }
}

@media screen and (max-width: 960px) {
  .content_imgBox {
    padding-top: 30px;
    padding-bottom: 30px;
  }
}

@media screen and (min-width: 961px) {
  .content_imgBox {
    width: auto;
  }
}

@media screen and (max-width: 960px) {
  .content_imgBox {
    width: 90%;
  }
}

.content_imgBox img {
  width: 100%;
}

.content_textBox {
  -ms-flex-negative: 0;
      flex-shrink: 0;
}

@media screen and (min-width: 961px) {
  .content_textBox {
    width: 50%;
  }
}

@media screen and (max-width: 960px) {
  .content_textBox {
    width: 100%;
  }
}

.content_heading .textWrap {
  position: relative;
  display: inline-block;
}

@media screen and (min-width: 961px) {
  .content_heading .textWrap {
    padding-right: 20px;
  }
}

@media screen and (max-width: 960px) {
  .content_heading .textWrap {
    padding-right: 10px;
  }
}

.content_heading .text {
  display: block;
  color: #fff;
  font-weight: bold;
  font-size: 32px;
  font-size: 2.13333rem;
  letter-spacing: 0.1em;
  line-height: 1.25;
}

@media screen and (min-width: 961px) {
  .content_heading .text {
    font-size: 54px;
    font-size: 3.6rem;
  }
}

.content_heading .textDeco {
  position: absolute;
  height: 50%;
  left: 0;
  bottom: -10%;
  z-index: -1;
  background: -webkit-gradient(linear, left top, right top, from(#7b29ff), to(#304ffe));
  background: linear-gradient(90deg, #7b29ff, #304ffe);
}

.content_text {
  color: #fff;
  font-size: 14px;
  font-size: 0.93333rem;
  line-height: 2;
}

@media screen and (min-width: 961px) {
  .content_text {
    padding-top: 40px;
  }
}

@media screen and (max-width: 960px) {
  .content_text {
    padding-top: 20px;
  }
}

@media screen and (min-width: 961px) {
  .content_text {
    font-size: 16px;
    font-size: 1.06667rem;
  }
}

@media screen and (min-width: 961px) {
  .content_btn {
    padding-top: 40px;
  }
}

@media screen and (max-width: 960px) {
  .content_btn {
    padding-top: 20px;
  }
}

.content_btn a {
  display: block;
  border: 1px solid #fff;
  color: #fff;
  width: 250px;
  height: 60px;
  text-align: center;
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
  -webkit-box-align: center;
      -ms-flex-align: center;
          align-items: center;
}

アニメーション用のCSS設定

「anime_fadeUpWrap」に「overflow:hidden」、「anime_target」に「transform:translateY(-110%)」を指定して、アニメーションさせる要素が隠れるようにします。

-110%にしているのは、タイトルラインまで隠すためです。装飾が無い場合は-100%で問題ありません。

.anime_fadeUpWrap {
  overflow: hidden;
}

.anime_target {
  -webkit-transform: translateY(-110%);
          transform: translateY(-110%);
}

.anime_widthRight {
  width: 0;
}

Javascript

$(function () {

    /* fadeUpアニメーション */
    var fadeUpAnime = function (element) {
        var targets = $(element).find('.anime_fadeUpWrap .anime_target').length;
        var delay;
        var delayReset;

        //追加delay
        if ($(element).data('fadeupDelay')) {
            delay = $(element).data('fadeupDelay') * 1000;
        } else {
            delay = 0;
        }

        //順にアニメーション発火
        for (var i = 0; i < targets; i++) {

            //delayリセット
            if ($(element).find('.anime_fadeUpWrap .anime_target').eq(i).data('delayReset') == 'on') {
                delayReset = 0;
            } else {
                delayReset = 1;
            }

            //アニメーション対象の箱
            var wrapH = $(element).find('.anime_fadeUpWrap').eq(i).outerHeight();

            //アニメーション設定
            //anime用ターゲットの為DOMオブジェクト指定のgetを使う
            anime({
                targets: $(element).find('.anime_fadeUpWrap .anime_target').get(i),
                translateY: [wrapH, 0],
                easing: 'easeOutQuart',
                duration: 800,
                delay: (delay + 100 * i) * delayReset
            });

        }
    }

    /* widthRightアニメーション */
    var widthRightAnime = function (element) {
        var targets = $(element).find('.anime_widthRight').length;

        for (var i = 0; i < targets; i++) {
            anime({
                targets: $(element).find('.anime_widthRight').get(i),
                width: [0, '100%'],
                easing: 'easeOutQuart',
                duration: 500,
                delay: 100 * i
            });
        }
    }

    /* inview */
    $('.js-inview').one('inview', function (event, isInView) {
        if (isInView) {
            fadeUpAnime(this);
            widthRightAnime(this);
        }
    });
});

フェードアップの関数

    /* fadeUpアニメーション */
    var fadeUpAnime = function (element) {
        var targets = $(element).find('.anime_fadeUpWrap .anime_target').length;
        var delay;
        var delayReset;
 
        //追加delay
        if ($(element).data('fadeupDelay')) {
            delay = $(element).data('fadeupDelay') * 1000;
        } else {
            delay = 0;
        }
 
        //順にアニメーション発火
        for (var i = 0; i < targets; i++) {
 
            //delayリセット
            if ($(element).find('.anime_fadeUpWrap .anime_target').eq(i).data('delayReset') == 'on') {
                delayReset = 0;
            } else {
                delayReset = 1;
            }
 
            //アニメーション対象の箱
            var wrapH = $(element).find('.anime_fadeUpWrap').eq(i).outerHeight();
 
            //アニメーション設定
            //anime用ターゲットの為DOMオブジェクト指定のgetを使う
            anime({
                targets: $(element).find('.anime_fadeUpWrap .anime_target').get(i),
                translateY: [wrapH, 0],
                easing: 'easeOutQuart',
                duration: 800,
                delay: (delay + 100 * i) * delayReset
            });
 
        }
    }

「js-inview」クラス内の「.anime_fadeUpWrap .anime_target」の数をカウントするための変数です。

var targets = $(element).find('.anime_fadeUpWrap .anime_target').length;

フェードアップアニメーションがタイトルラインの後に動き出すようにするためのディレイ設定用に以下を書きます。

発火用クラス「js-inview」の「data-fadeup-delay」に指定することでフェードアップアニメーション全体のスタートを遅らせることができます。

今回はdata-fadeup-delay=”0.3″としています。

        //追加delay
        if ($(element).data('fadeupDelay')) {
            delay = $(element).data('fadeupDelay') * 1000;
        } else {
            delay = 0;
        }

遅延させたくない要素がある場合、data-delay-reset=”on”を指定しているターゲットは遅延させないようにします。

デモの場合、メイン画像にdata-delay-reset=”on”を設定しています。

            //delayリセット
            if ($(element).find('.anime_fadeUpWrap .anime_target').eq(i).data('delayReset') == 'on') {
                delayReset = 0;
            } else {
                delayReset = 1;
            }

タイトルラインの関数

タイトルライン装飾はwidthを0から100%になるようにアニメーションを設定します。

    /* widthRightアニメーション */
    var widthRightAnime = function (element) {
        var targets = $(element).find('.anime_widthRight').length;
 
        for (var i = 0; i < targets; i++) {
            anime({
                targets: $(element).find('.anime_widthRight').get(i),
                width: [0, '100%'],
                easing: 'easeOutQuart',
                duration: 500,
                delay: 100 * i
            });
        }
    }

inviewイベントの作成

最後にinviewイベントを作成して、フェードアップアニメーションとラインのアニメーションを発火させるようにします。

これでどの位置にアニメーションさせたい要素があっても、スクロールで表示されたタイミングでアニメーションが開始されます。

    /* inview */
    $('.js-inview').one('inview', function (event, isInView) {
        if (isInView) {
            fadeUpAnime(this);
            widthRightAnime(this);
        }
    });

完成デモ

以下から完成したデモが確認できます。

関連リンク

軽量アニメーションJavascriptライブラリ【anime.js】を使ってみた