![見出し画像](https://assets.st-note.com/production/uploads/images/83471514/rectangle_large_type_2_ee39001f150df5011690cc0d4701ec8e.png?width=1200)
gsapのScrollTriggerプラグインとlottie-reactを利用したスクロールアニメーションの実装について
こんにちわ。nap5です。
gsapのScrollTriggerプラグインとlottie-reactを利用したスクロールアニメーションの実装について紹介したいと思います。
Twitterにも投稿してみました。
I mocked up this scroll aniamtion using gsap ScrollTrigger and lottie-react.#react #javascript #100DaysOfCode #gsap #lottie
— nap5 (@napzak5) July 27, 2022
demo codehttps://t.co/DVSzRXDymo
demo sitehttps://t.co/w5ggrLHXw0
gsapのScrollTriggerプラグインについてはこちらのリンクになります。
lottie-reactについてはこちらのリンクになります。
以下のデモですが、不安定のため、zipにしたものも添付します。zipファイルダウンロード後、展開します。展開後のディレクトリに移動した後、以下のコマンド打つとデモが動きます。
$ cd 展開後のディレクトリ
$ yarn install
$ yarn dev
以下のcodesandboxのデモが見れない場合のフォールバックとしてrenderというホスティングサービスでデプロイしたものも用意しました。
デモサイトです。
デモコードです。
実装のポイントとしては2点あります。
1つ目はサイズをレスポンシブに調節することです。
emotionのcss文字列内挿でクラス指定できるのがハンディです。
// https://lottiereact.com/hooks/useLottie#params
const {goToAndStop, animationContainerRef, View, animationItem} = useLottie(
{
animationData,
loop: false,
autoplay: false,
className: css`
width: 400px;
height: 400px;
@media (max-width: 768px) {
width: 300px;
height: 300px;
}
`,
},
{}
);
もう一つはScrollTriggerのハンドリングをPCとSPのそれぞれ調節することです。
animationItemがマウントされたら、PCとSPのそれぞれでフレームを進捗率をもとに計算して、計算したフレームまで再生シークを進める実装になります。
useEffect(() => {
if (!animationItem) {
return;
}
gsap.registerPlugin(ScrollTrigger);
const itemDom = itemDomRef.current;
// https://greensock.com/docs/v3/Plugins/ScrollTrigger/static.matchMedia()
ScrollTrigger.matchMedia({
'(min-width: 769px)': function () {
gsap.timeline({
scrollTrigger: {
trigger: itemDom,
start: 'top 10%',
end: 'bottom+=300% top',
pin: true,
markers: true,
scrub: true,
onUpdate: function (e) {
const p = e.progress;
const maxFrames = animationItem.totalFrames;
const frame = maxFrames * p;
// console.log(p, frame, maxFrames);
animationItem.goToAndStop(frame, true);
},
},
});
},
'(max-width: 768px)': function () {
gsap.timeline({
scrollTrigger: {
trigger: itemDom,
start: 'top 20%',
end: 'bottom+=900% top',
pin: true,
markers: true,
scrub: true,
onUpdate: function (e) {
const p = e.progress;
const maxFrames = animationItem.totalFrames;
const frame = maxFrames * p;
// console.log(p, frame, maxFrames);
animationItem.goToAndStop(frame, true);
},
},
});
},
});
return () => {};
}, [animationItem]);
最近では、MENTAをはじめてみました。MENTAを使って提供していることを紹介している記事は以下になります。
また、Twitterでモックアップ動画を公開しているので、こちらもよかったら、覗いてみてください。
最後に、Udemyでコースを公開しました。
良かったら覗いてみてください。
https://www.udemy.com/course/count-down-up-using-javascript-animation-api/
また、コースの内容紹介記事は以下になります。
簡単ですが、以上です。