Vueの世界にCreateJS(Canvas操作ライブラリ)を連携してみた | Dev Driven 開発・デザインチーム Vueの世界にCreateJS(Canvas操作ライブラリ)を連携してみた | 働くひとと組織の健康を創る iCARE

BLOG

Vueの世界にCreateJS(Canvas操作ライブラリ)を連携してみた

赤松正悟
2022/01/26

以前紹介したCanvas制御ライブラリのCreateJSによるモーフィングアニメーション

【サヨナラは言わないよ!きっと良い未来はやってくる。またね、Flash!】の記事
https://qiita.com/seigo_akamatsu/items/c9c88b114d135f5468cc

の中で以下のようなモーフィングアニメーションを
Adobe AnimateCC(旧Flash)で簡単にJSファイルとして生成できる事を紹介させていただきました。
http://www.seigo-akamatsu.net/icare/iCARE2Carely.html

ただ、このままでは単体のコンテンツとしては利用できても
Vue.jsの世界と連携される事はできませんでした。
そこで今回はVue.jsの世界の中にCreateJSを連携させて
以前作ったアニメーションをコントロールしてみる事にチャレンジしてみました。

CodePen上に実装してみた。

以前の例とは異なり、アニメーションは自動では再生されないようにして
[play]ボタンをクリックする事でモーフィングアニメーションが再生されるように
若干手を加えました。
この[play]ボタンはVue.jsの世界で生成されたボタンで、このボタンをクリックする事でCreateJSの世界のCanvas上のムービークリップの再生が始まります。
このボタンは頭出し再生の機能として実装してあるので、クリックする度にアニメーションの頭から再生されます。

See the Pen
vue_createjs
by seigo_akamatsu (@seigo_akamatsu)
on CodePen.

ざっくりとした解説

以前作成済みのAnimateCCのflaファイルと、そこから書き出したhtml及びjsファイルは参考までに以下のリポジトリに設置してあるので、興味のある方は見てみてください。
https://github.com/seigo-akamatsu-icare/vue-createjs
AnimateCCのシェイプトゥイーンという機能で、2つのシェイプ(ベクターデータ)を時系列で変形されるモーフィーングアニメーションとして作成してあります。

基本的にはCodePen上のソースコードについて簡単に解説します。
まず初めに当たり前ですが、Vue.jsとCreateJSを読み込んでいます。
これはCodePenの性質上、CodePenのSettingsのJSの項目をご覧いただくと
2つのjsファイルの読み込み設定をご確認いただけると思います。

読み込みが成功していると、VueはグローバルスコープでVueの名称で参照可能になるので、そこからcreateApp, createComponent, hの3つのメソッドを再定義しているのが最初の行となります。
同じようにCreateJSの場合は、読み込みに成功しているとWindowオブジェクトの下にcreatejsの名称でライブラリが参照可能になっているので、
次の行でcreatejsという変数名で改めて参照を渡してあります。
今回はCodePen上で実現する為、このような方法を選択しましたが
Webpackなどでモジュールとしても利用可能なので、そちらについては
以下の記事などをご参考ください。
https://qiita.com/ruby_kumagoro/items/276cad77c78b39c09201

次にCreateJSの基礎的な説明ですが、
見た目を伴うオブジェクトはDisplayObjectという名称のクラス(オブジェクト)が用意されており、そのクラスに時間軸の概念が加わったクラスがMovieClip(ムービークリップ)クラスという名称で定義されてあります。
MovieClipクラスはDisplayObjectがtimelineプロパティを持ったオブジェクトで1コマ単位でコマアニメーションなどを作成する事が可能です。
今回の例では全60コマのアニメーションとして作成してありますが、
最初のコマと最後のコマがキーフレームで、その間のコマはAnimateCCにより
自動的に計算されて補完されています。
詳しくは公式ドキュメントを参照ください。
https://createjs.com/docs/easeljs/modules/EaselJS.html

本題に戻りますが、DisplayObject及びMovieClipはHTMLのDOMのように入れ子にする事が可能ですが、HTMLのbodyタグのようにroot要素として、Stageクラス(オブジェクト)をCanvasに1つ定義して、その中にMovieClipを入れる(addChild)してやる必要があります。
またstageはインスタンス生成時にCanvasへの参照を渡してやる必要があり、
それをおこなっているのが6行目の
const stage = new createjs.Stage(document.getElementById("app"))
部分になります。
次に7行目以降ですが、
const mc = new createjs.MovieClip()
にて時間軸を持った空のDisplayObjectとしてMovieClipのインスタンスを生成しています。
そして9〜11行目ですが、

mc.shape = new createjs.Shape()
mc.shape.graphics.f("#CA4F53").s().p("***")
mc.shape.setTransform(96.4688,80.3203);

GitHubのリポジトリ上にアップしてあるjsファイルでは、
頭のmcの部分がthisになっているかと思いますが
生成されたjsファイルではthisがMovieClipのインスタンスを意味する為
thisで成立するのですが、Vueのコンテキスト上ではthisの意味合いが異なる為、予め7行目で生成した空のムービークリップインスタンスのmc(MovieClipの略)に置換する事で対応させています。

9行目から1211行目までは似たような理解し難い記述があると思いますが
mc.shape
mc.shape_1
...
mc.shape_300
まで基本的には名前の通りシェイプでflaファイル上に配置したベクターデータがsvgなどと同じような形式で機械的に生成されたものなので
iCAREとCarelyのロゴ画像のベクターデータをここで定義していると
ざっくりと理解していただければ大丈夫です。

重要なのは1213行目のmc.timeline.addTweenの部分で
ここで1211行目までに定義したシェイプデータをタイムライン(アニメーションのコマ)に配置してあります。
ここも機械的に生成されたものなので、直接理解するのは困難ですが
timelineクラスは、手動でも扱えるような機能を兼ね備えてあるので
きっちり理解できれば、十分に自身でコーディング可能です。
以下、timelineクラス
https://www.createjs.com/docs/tweenjs/classes/Timeline.html

最後にTickerについて少しだけ触れておきます。
Tickerは時間軸を管理するイベントクラスです。
1コマという最小単位を管理しています。
1216行目の
createjs.Ticker.framerate = 60
はフレームレート(fps:frame per seconds)を60と定義しており
※).1秒あたり理論値60コマ再生されるという意味合いです。
1217行目の
createjs.Ticker.addEventListener("tick", stage)
が非常に重要で、先に諸々設置設定したstageをTickerイベントの管理下に設定する事で、初めてtickイベント毎にアニメーションのリレンダリングが実行されるようになります。
ですので、この1行が無いと画面上には何もレンダリングされません。

加えてオマケの扱いとなってしまいましたがVueの世界と連動している部分を紹介すると、
1219行目のmc.stop()によりアニメーションの自動再生を停止しています。
以前のブログ記事では、この制御をおこなっていなかった為に自動再生するという違いがあります。
1222行目に定義してある
clickPlay関数(method)はVueのテンプレートから呼び出されるメソッドとして定義されており、
1227行目のtemplate定義部分で@click="clickPlay()"として
ボタンをクリック時にこのメソッドが呼び出され実行されます。
実行ないようのmc.gotoAndPlay(0)
mcのtimelineの0フレーム目(1コマ目)から再生を始めなさいという意味の命令になります。
タイムラインアニメーションが最終コマに達したら、そこで停止しますが
随時クリック可能で、クリックされたタイミングでアニメーションの1コマ目から都度リプレイされます。

いかがだったでしょうか?
今回の記事は、以前に自動生成したjsファイルを活用してモーフィングアニメーションをVue.jsの世界に取り込もうというものだったので、そのままCreateJSのライブラリを利用しましたが、多少残念な事に今回の執筆にあたってCreateJSのその後の開発状況を確認したところ、メンテナンスが止まってしまっているようなので、Opsが必要なコンテンツでは限定的なシーンの利用などに留めた方が良いかもしれません。
似たようなライブラリでPixi.js
https://pixijs.com/
などは現在もメンテナンスされており、使用感も近いものなので参考にしていただくと良いかと思います。