jQuery

スクロールで要素をフェードインさせる:再アニメーション(何度でも発火)するバージョン(throttle 関数 付き)

・要素はあらかじめ非表示にしておく

・スクロールしたらフェードインさせる要素にクラス付与する

throttle(スロットル) 関数

同じイベントが連続して発火するような状況で、発火した回数分処理を実行すると負荷が高くなってしまう場合に、
最初のイベント発火から指定した秒数を経過するまで、次のイベント処理を遅延させる手法です。

<必要かどうかはこれで判断できる>

・要素数が少ない(10個以下) → throttle なくてもいい

・要素数が多い(20個〜) → throttle は入れた方が良い

・SP でのパフォーマンスが大事 → throttle 必須

・もし商用サイト・企業サイトなら → ほぼ 100% throttle or IntersectionObserver を使う。

下からフェードイン

▼▼▼▼▼ スクロール ▼▼▼▼▼

左からフェードイン

▼▼▼▼▼ スクロール ▼▼▼▼▼

右からフェードイン

▼▼▼▼▼ スクロール ▼▼▼▼▼

左右からフェードイン

▼▼▼▼▼ スクロール ▼▼▼▼▼

javascript
                  
//フェードイン

//「.in-fade-up」下かららフェードイン
//「.in-fade-left」左からフェードイン
//「.in-fade-right」右からフェードイン

// throttle:指定した時間ごとにしか処理を実行しない
function throttle(fn, delay) {
  let last = 0;
  return function (...args) {
    const now = Date.now();
    if (now - last >= delay) {
      last = now;
      fn.apply(this, args);
    }
  };
}

$(function () {
  const $targets = $('.in-fade-up, .in-fade-left, .in-fade-right');

  function checkAnimation() {
    const windowBottom = $(window).scrollTop() + $(window).height();

    $targets.each(function () {
      const $this = $(this);
      const elementTop = $this.offset().top;

      if (windowBottom > elementTop + $(window).height() * 0.1) {
        $this.addClass('is-active');  // 画面に入った
      } else {
        $this.removeClass('is-active'); // 画面外でリセット
      }
    });
  }

  // throttle(100msごとに実行)
  const throttledCheck = throttle(checkAnimation, 100);

  $(window).on('scroll resize', throttledCheck);
  checkAnimation(); // 初回実行
});
                  
                
CSS
                  
/* 下からフェードイン */
.in-fade-up {
  opacity: 0;
  visibility: hidden;
  transform: translateY(40px);
  transition: opacity 0.8s ease, transform 0.8s ease;
}
.in-fade-up.is-active {
  opacity: 1;
  visibility: visible;
  transform: translateY(0);
}

/* 左からフェードイン */
.in-fade-left {
  opacity: 0;
  visibility: hidden;
  transform: translateX(-100%);
  transition: opacity 0.8s ease, transform 0.8s ease;
}
.in-fade-left.is-active {
  opacity: 1;
  visibility: visible;
  transform: translateX(0);
}

/* 右からフェードイン */
.in-fade-right {
  opacity: 0;
  visibility: hidden;
  transform: translateX(100%);
  transition: opacity 0.8s ease, transform 0.8s ease;
}
.in-fade-right.is-active {
  opacity: 1;
  visibility: visible;
  transform: translateX(0);
}