🕺

Lottieを使ったローディングアニメーションをAEで作成→実装してみた

2024/02/18に公開

はじめに

最近、Lottieという単語をSNSなどでよくお見かけします。
その存在だけは知っていたものの、軽量なアニメーションライブラリなんだろうな、くらいの認識でした。
ギャラリーサイトに載っているサイトなんかでもLottieが使用されているサイトをチラホラとお見かけします。
Lottieとは何ぞや!ということでキャッチアップのため、アニメーション作成から実装まで、一通り試してみましたので備忘録として記事を残させて頂きます。

結論

実際に実装した画面とソースコードはこちら
※アニメーション描画にjsonファイルを使用する関係上、codepenであげられませんでした。
(有料プランでしか、外部ファイルのアップロード機能は使えないため)

index.html
index.html
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/lottie-web/5.9.6/lottie.min.js" defer></script>
</head>

<body>
	<div class="loading">
		<div class="loading-wrapper"></div>
	</div>
	<h1>SITE TITLE</h1>
</body>
style.css
style.css
/* =========調整用スタイル========= */
body {
	background-color: #13302c;
	min-height: 100vh;
}
h1 {
	color: white;
	font-size: 200px;
	text-align: center;
	line-height: 100vh;
}
/* =========ここまで調整用スタイル========= */

.loading {
	z-index: calc(infinity);
	position: fixed;
	top: 0;
	left: 0;
	display: flex;
	justify-content: center;
	align-items: center;
	width: 100vw;
	height: 100vh;
	background-color: #8b9ba8;
}
.loading-wrapper {
	height: 100%;
}
/*アニメーション終了後の非表示処理*/
.loading.isLoaded {
	transition: opacity 0.5s;
	opacity: 0;
}
.loading-wrapper > svg {
	scale: 2;
}

script.js
script.js
// ローディングアニメーションの設定
function loadingAnimation() {
	const setAnimation = lottie.loadAnimation({
		container: document.querySelector(".loading-wrapper"), //アニメーションを描画したいDOM要素を指定
		renderer: "svg", //svgとして描画する
		loop: false, //一度のみ実行なのでfalse(ループさせたい場合はtrue)
		autoplay: true, //自動再生させる
		path: "./loading-animation.json", //jsonファイルのパスを記述
	});

	// アニメーション終了時に実行
	setAnimation.addEventListener("complete", function () {
		const loadingElement = document.querySelector(".loading");
		loadingElement.classList.add("isLoaded"); //isLoadedクラスを付与
	});
}

// 初回訪問時のみアニメーションを実行
if (!sessionStorage.getItem("visited")) {
	// 初回訪問時
	sessionStorage.setItem("visited", "first");
	loadingAnimation();
} else {
	// 2回目以降の訪問時
	const loadingElement = document.querySelector(".loading");
	loadingElement.classList.add("isLoaded");
}

loading-animation.json
loading-animation.json
{"v":"5.9.0","fr":29.9700012207031,"ip":0,"op":48.0000019550801,"w":1920,"h":1080,"nm":"load-animation","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":4,"nm":"円小","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[0,0,0],"ix":1,"l":2},"s":{"a":0,"k":[21.778,21.778,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"d":1,"ty":"el","s":{"a":1,"k":[{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":3,"s":[0,0]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":16,"s":[500,500]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":22,"s":[450,450]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":26,"s":[420,420]},{"i":{"x":[0.839,0.839],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":30,"s":[450,450]},{"t":48.0000019550801,"s":[10325,10325]}],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"nm":"楕円形パス 1","mn":"ADBE Vector Shape - Ellipse","hd":false},{"ty":"fl","c":{"a":0,"k":[0.074610287535,0.186504289216,0.170964603798,1],"ix":4},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"塗り 1","mn":"ADBE Vector Graphic - Fill","hd":false},{"ty":"tr","p":{"a":0,"k":[2,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"トランスフォーム"}],"nm":"楕円形 1","np":3,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false}],"ip":0,"op":48.0000019550801,"st":0,"bm":0},{"ddd":0,"ind":2,"ty":4,"nm":"円大","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[0,0,0],"ix":1,"l":2},"s":{"a":0,"k":[21.778,21.778,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"d":1,"ty":"el","s":{"a":1,"k":[{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":0,"s":[0,0]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":16,"s":[900,900]},{"i":{"x":[0.833,0.833],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":22,"s":[800,800]},{"t":48.0000019550801,"s":[10325,10325]}],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"nm":"楕円形パス 1","mn":"ADBE Vector Shape - Ellipse","hd":false},{"ty":"fl","c":{"a":0,"k":[0.278146242628,0.438817401961,0.416503607058,1],"ix":4},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"塗り 1","mn":"ADBE Vector Graphic - Fill","hd":false},{"ty":"tr","p":{"a":0,"k":[2,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"トランスフォーム"}],"nm":"楕円形 1","np":3,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false}],"ip":0,"op":48.0000019550801,"st":0,"bm":0},{"ddd":0,"ind":3,"ty":1,"nm":"背景","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[960,540,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"sw":1920,"sh":1080,"sc":"#8b9ba8","ip":0,"op":60.0000024438501,"st":0,"bm":0}],"markers":[]}

GitHubでもソースコードを公開しています。
https://github.com/Takanami-Kosuke/lottie-loading-animation

Lottieとは?

「Airbnb」が開発したモーショングラフィックスを扱うためのライブラリのこと。
After EffectsやLottieFiles、Lottielabで作成したアニメーションを、
Webやモバイルアプリケーションに埋め込むためのツールとして利用されます。

Lottieを使用すると、作成したアニメーションをSVGで表示します。
SVGなのでどれだけ拡大しても高画質かつ軽量、実装も簡単なライブラリです。

アニメーション作成から実装までの手順

  1. 各種ツールを使用してアニメーションデータを作成する
    (※本記事ではAfterEffectsを使用してアニメーションデータを作成していきます)
  2. jsonデータとしてアニメーションを書き出す
  3. Lottieライブラリを使用してjsonデータをアニメーションとして実装する

1.Lottieで使うためのアニメーションデータの作成

Lottieではjson形式で書き出したアニメーション用のデータを用いて実装します。
jsonデータの作成には以下に挙げるツールを使用して作成することができます。

・AfterEffects
・Figma
・LottieLab
・Lottie Creator

様々なツールで作成することができ、その中で今回はAfter Effectsを使用して作成していきます。
※ご参考までに、Figma・LottieLab・Lottie CreatorでのLottie用データの作成は、下記の方々が記事を上げられておりました。
https://zenn.dev/spicato_blog/articles/92d07ae018cbdc
https://zenn.dev/s134/articles/20231209figmatolottie

AfterEffectsで作成してみる

キーフレームやイージングを設定してアニメーションを作成していきます。

AfterEffectsでアニメーションを作成

2.アニメーションの書き出し

Bodymovinプラグインのインストール

AfterEffectsからLottie用のjsonへの書き出しには「Bodymovin」という専用のAEプラグインを使用する必要があります。

プラグインのインストールにはいくつか方法があり、
Adobe CC経由でプラグインをインストールするのが最も簡単で手軽かと思います。
https://exchange.adobe.com/apps/cc/12557

その他のインストール方法についてはairbnbの公式ドキュメントをご確認ください
https://github.com/airbnb/lottie-web?tab=readme-ov-file#plugin-installation

書き出し

インストールが正常に完了すると、
AfterEffextsの[ウィンドウ] > [エクステンション]に[Bodymovin]が新たに追加されます。

それでは、作成したアニメーション(コンポジション)をLottie専用のjsonファイルへ書き出ししていきます。

[ウィンドウ]>[エクステンション]>[Bodymovin]を選択

書き出ししたいアニメーションを選択・書き出し先を指定し[Rendor]を選択

【完了画面】指定されたディレクトリにjsonファイルが書き出されます

3.実装

それでは、上記手順で書き出ししたjsonファイルを使用して、実装していきましょう。

loading-animation.json
loading-animation.json
{"v":"5.9.0","fr":29.9700012207031,"ip":0,"op":48.0000019550801,"w":1920,"h":1080,"nm":"load-animation","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":4,"nm":"円小","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[0,0,0],"ix":1,"l":2},"s":{"a":0,"k":[21.778,21.778,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"d":1,"ty":"el","s":{"a":1,"k":[{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":3,"s":[0,0]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":16,"s":[500,500]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":22,"s":[450,450]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":26,"s":[420,420]},{"i":{"x":[0.839,0.839],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":30,"s":[450,450]},{"t":48.0000019550801,"s":[10325,10325]}],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"nm":"楕円形パス 1","mn":"ADBE Vector Shape - Ellipse","hd":false},{"ty":"fl","c":{"a":0,"k":[0.074610287535,0.186504289216,0.170964603798,1],"ix":4},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"塗り 1","mn":"ADBE Vector Graphic - Fill","hd":false},{"ty":"tr","p":{"a":0,"k":[2,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"トランスフォーム"}],"nm":"楕円形 1","np":3,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false}],"ip":0,"op":48.0000019550801,"st":0,"bm":0},{"ddd":0,"ind":2,"ty":4,"nm":"円大","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[0,0,0],"ix":1,"l":2},"s":{"a":0,"k":[21.778,21.778,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"d":1,"ty":"el","s":{"a":1,"k":[{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":0,"s":[0,0]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":16,"s":[900,900]},{"i":{"x":[0.833,0.833],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":22,"s":[800,800]},{"t":48.0000019550801,"s":[10325,10325]}],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"nm":"楕円形パス 1","mn":"ADBE Vector Shape - Ellipse","hd":false},{"ty":"fl","c":{"a":0,"k":[0.278146242628,0.438817401961,0.416503607058,1],"ix":4},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"塗り 1","mn":"ADBE Vector Graphic - Fill","hd":false},{"ty":"tr","p":{"a":0,"k":[2,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"トランスフォーム"}],"nm":"楕円形 1","np":3,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false}],"ip":0,"op":48.0000019550801,"st":0,"bm":0},{"ddd":0,"ind":3,"ty":1,"nm":"背景","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[960,540,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"sw":1920,"sh":1080,"sc":"#8b9ba8","ip":0,"op":60.0000024438501,"st":0,"bm":0}],"markers":[]}

ライブラリの読み込み

まずはnpmもしくはCDNでLottieライブラリを読み込みます。

▼npmの場合

npm install lottie-web

▼CDNの場合

<script src="https://cdnjs.cloudflare.com/ajax/libs/lottie-web/5.9.6/lottie.min.js" defer></script>

※バージョン指定や最新版は下記よりご確認ください
https://cdnjs.com/libraries/bodymovin

マークアップ

Lottieを描画するための、DOM要素を用意しておきます。

index.html
<div class="loading-wrapper"></div>

JSで動かす

script.js
lottie.loadAnimation({
		container: document.querySelector(".loading-wrapper"), //アニメーションを描画したいDOM要素を指定
		renderer: "svg", //svgとして描画する
		loop: false, //一度のみ実行なのでfalse(ループさせたい場合はtrue)
		autoplay: true, //自動再生させる
		path: "./loading-animation.json", //jsonファイルのパスを記述
	});

これだけで、指定したDOM要素に作成したアニメーションが表示されます。
実装が非常に簡単です。

オープニングアニメーションとして使用するための調整

オープニングアニメーションなので、少し調整を加えていきます。
具体的には下記の仕様を実装していきます。

・Lottieを描画する要素はposition:fixedで画面幅いっぱい、最前面で表示する
・アニメションが終了したら、Lottie表示の要素を非表示にする
・アニメーションは初回訪問時のみ実行し、2回目以降の訪問時は再生させない。

Lottieを描画する要素はposition:fixedで画面幅いっぱい、最前面で表示する

HTMLとCSSを調整します

<div class="loading">
	<div class="loading-wrapper"></div>
</div>
<h1>SITE TITLE</h1>

Lottie描画要素に親要素を追加します。
(この後の要素の非表示は直接Lottieの要素ではなく、この親要素を操作して実施します。)

.loading {
z-index: calc(infinity);
position: fixed;
top: 0;
left: 0;
display: flex;
justify-content: center;
align-items: center;
width: 100vw;
height: 100vh;
background-color: #8b9ba8;
}
.loading-wrapper {
height: 100%;
}

アニメションが終了したら、Lottie表示の要素を非表示にする

script.js
const setAnimation = lottie.loadAnimation({
	container: document.querySelector(".loading-wrapper"), //アニメーションを描画したいDOM要素を指定
	renderer: "svg", //svgとして描画する
	loop: false, //一度のみ実行なのでfalse(ループさせたい場合はtrue)
	autoplay: true, //自動再生させる
	path: "./loading-animation.json", //jsonファイルのパスを記述
});

Lottieは各種イベントが使用できるようなので、completeイベントを使用します。
予めアニメーションをsetAnimation変数にセットしておき、イベントリスナーでアニメーション終了時に、非表示にするための「isLoaded」クラスを付与します。

script.js
// アニメーション終了時に実行
setAnimation.addEventListener("complete", function () {
	const loadingElement = document.querySelector(".loading");
	loadingElement.classList.add("isLoaded"); //isLoadedクラスを付与
});
/*アニメーション終了後の非表示処理*/
.loading.isLoaded {
transition: opacity 0.5s;
opacity: 0;
}

アニメーションは初回訪問時のみ実行し、2回目以降の訪問時は再生させない

// 初回訪問時のみアニメーションを実行
if (!sessionStorage.getItem("visited")) {
	// 初回訪問時
	sessionStorage.setItem("visited", "first");
	loadingAnimation();
} else {
	// 2回目以降の訪問時
	const loadingElement = document.querySelector(".loading");
	loadingElement.classList.add("isLoaded");
}

sessionStorageAPIを使用して、初回訪問時、2回目以降の訪問時の処理を分けます。
初回訪問時→ローディングアニメーションを実行し、ローディングアニメーションの要素を非表示
2回目以降の訪問時→ローディングアニメーションの要素を非表示

完成

これでLottieを使用したローディングアニメーションの完成です。
改めて完成したソースコードを記載しておきます。

index.html
index.html
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/lottie-web/5.9.6/lottie.min.js" defer></script>
</head>

<body>
	<div class="loading">
		<div class="loading-wrapper"></div>
	</div>
	<h1>SITE TITLE</h1>
</body>
style.css
style.css
/* =========調整用スタイル========= */
body {
	background-color: #13302c;
	min-height: 100vh;
}
h1 {
	color: white;
	font-size: 200px;
	text-align: center;
	line-height: 100vh;
}
/* =========ここまで調整用スタイル========= */

.loading {
	z-index: calc(infinity);
	position: fixed;
	top: 0;
	left: 0;
	display: flex;
	justify-content: center;
	align-items: center;
	width: 100vw;
	height: 100vh;
	background-color: #8b9ba8;
}
.loading-wrapper {
	height: 100%;
}
/*アニメーション終了後の非表示処理*/
.loading.isLoaded {
	transition: opacity 0.5s;
	opacity: 0;
}
.loading-wrapper > svg {
	scale: 2;
}

script.js
script.js
// ローディングアニメーションの設定
function loadingAnimation() {
	const setAnimation = lottie.loadAnimation({
		container: document.querySelector(".loading-wrapper"), //アニメーションを描画したいDOM要素を指定
		renderer: "svg", //svgとして描画する
		loop: false, //一度のみ実行なのでfalse(ループさせたい場合はtrue)
		autoplay: true, //自動再生させる
		path: "./loading-animation.json", //jsonファイルのパスを記述
	});

	// アニメーション終了時に実行
	setAnimation.addEventListener("complete", function () {
		const loadingElement = document.querySelector(".loading");
		loadingElement.classList.add("isLoaded"); //isLoadedクラスを付与
	});
}

// 初回訪問時のみアニメーションを実行
if (!sessionStorage.getItem("visited")) {
	// 初回訪問時
	sessionStorage.setItem("visited", "first");
	loadingAnimation();
} else {
	// 2回目以降の訪問時
	const loadingElement = document.querySelector(".loading");
	loadingElement.classList.add("isLoaded");
}

loading-animation.json
loading-animation.json
{"v":"5.9.0","fr":29.9700012207031,"ip":0,"op":48.0000019550801,"w":1920,"h":1080,"nm":"load-animation","ddd":0,"assets":[],"layers":[{"ddd":0,"ind":1,"ty":4,"nm":"円小","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[0,0,0],"ix":1,"l":2},"s":{"a":0,"k":[21.778,21.778,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"d":1,"ty":"el","s":{"a":1,"k":[{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":3,"s":[0,0]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":16,"s":[500,500]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":22,"s":[450,450]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":26,"s":[420,420]},{"i":{"x":[0.839,0.839],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":30,"s":[450,450]},{"t":48.0000019550801,"s":[10325,10325]}],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"nm":"楕円形パス 1","mn":"ADBE Vector Shape - Ellipse","hd":false},{"ty":"fl","c":{"a":0,"k":[0.074610287535,0.186504289216,0.170964603798,1],"ix":4},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"塗り 1","mn":"ADBE Vector Graphic - Fill","hd":false},{"ty":"tr","p":{"a":0,"k":[2,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"トランスフォーム"}],"nm":"楕円形 1","np":3,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false}],"ip":0,"op":48.0000019550801,"st":0,"bm":0},{"ddd":0,"ind":2,"ty":4,"nm":"円大","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[0,0,0],"ix":1,"l":2},"s":{"a":0,"k":[21.778,21.778,100],"ix":6,"l":2}},"ao":0,"shapes":[{"ty":"gr","it":[{"d":1,"ty":"el","s":{"a":1,"k":[{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":0,"s":[0,0]},{"i":{"x":[0.667,0.667],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":16,"s":[900,900]},{"i":{"x":[0.833,0.833],"y":[1,1]},"o":{"x":[0.333,0.333],"y":[0,0]},"t":22,"s":[800,800]},{"t":48.0000019550801,"s":[10325,10325]}],"ix":2},"p":{"a":0,"k":[0,0],"ix":3},"nm":"楕円形パス 1","mn":"ADBE Vector Shape - Ellipse","hd":false},{"ty":"fl","c":{"a":0,"k":[0.278146242628,0.438817401961,0.416503607058,1],"ix":4},"o":{"a":0,"k":100,"ix":5},"r":1,"bm":0,"nm":"塗り 1","mn":"ADBE Vector Graphic - Fill","hd":false},{"ty":"tr","p":{"a":0,"k":[2,0],"ix":2},"a":{"a":0,"k":[0,0],"ix":1},"s":{"a":0,"k":[100,100],"ix":3},"r":{"a":0,"k":0,"ix":6},"o":{"a":0,"k":100,"ix":7},"sk":{"a":0,"k":0,"ix":4},"sa":{"a":0,"k":0,"ix":5},"nm":"トランスフォーム"}],"nm":"楕円形 1","np":3,"cix":2,"bm":0,"ix":1,"mn":"ADBE Vector Group","hd":false}],"ip":0,"op":48.0000019550801,"st":0,"bm":0},{"ddd":0,"ind":3,"ty":1,"nm":"背景","sr":1,"ks":{"o":{"a":0,"k":100,"ix":11},"r":{"a":0,"k":0,"ix":10},"p":{"a":0,"k":[960,540,0],"ix":2,"l":2},"a":{"a":0,"k":[960,540,0],"ix":1,"l":2},"s":{"a":0,"k":[100,100,100],"ix":6,"l":2}},"ao":0,"sw":1920,"sh":1080,"sc":"#8b9ba8","ip":0,"op":60.0000024438501,"st":0,"bm":0}],"markers":[]}

https://github.com/Takanami-Kosuke/lottie-loading-animation

実際にLottieを試してみて感じたメリット

・SVGなので軽量でサイズ変更しても劣化しない
・実装コストがほとんど必要ない
・デザイナーの思い通りにアニメーションが作れる(デザイナーの学習コストは多少あるかも...)
・JSと組み合わせてアニメーションできるので、あれやこれや色々と調整できて便利そう

キーフレームやイージングをデザイナーの頭の中にある通りに設定できるので、デザイナー・エンジニア間での表現認識のズレやコミュニケーションコスト削減が期待できるのかな〜、なんて思っています。

おわりに

LottieはあくまでもSVGベースなので、アニメーション表現として
画像・音声を使用したアニメーションやマスク・グラデーションなどの特殊な表現は苦手のようです。(グラデーションは出来る出来ないは諸説あるようだけど、未検証)

あらかじめLottieができること・出来ない事を把握しておき
アニメーションのデザイン・実装の選択肢の1つとして、活かせていけたら良いなと思います。

Discussion