概要
- Unityの機能を使ったスプライトアニメーションでは、単純なものを作る場合でも余計なファイルができてしまう
- 単体でアニメーション可能なスクリプトを組んだ
- UniRx使用なので記述がシンプルに & Coroutine使わないので エディタ上で実行して確認可能
Unityでは複数のスプライトを選択してシーンにドラッグ&ドロップすれば、自動でスプライトアニメーションが設定されたオブジェクトができます。
ただこの方法だとAnimationClipとAnimatorControllerのファイルができてしまいます。
たとえば一種類のアニメーションしか使わない場合、AnimatorControllerがあるのは正直きもちわるいですね。
ということで、無駄ファイルを作成せずに一種類のアニメーションを実行するだけ&インスペクタから実行確認可能なスクリプトを作りました。
UniRxを使うことで記述がシンプルになり、さらにエディタ上で確認するのも簡単にすることができました。
目次
UniRxのインポート
まずUniRxをストアからダウンロード&プロジェクトにインポートしておきます。
https://www.assetstore.unity3d.com/jp/#!/content/17276
アニメーション用スクリプトを作成
SpriteAnimation.cs という名前で、下のスクリプトを作成します。
using System; using System.Collections; using UnityEngine; using UniRx; public class SpriteAnimation: MonoBehaviour { public float fps = 24.0f; // FPSを設定 public Sprite[] frames; // スプライトのリストを設定 SpriteRenderer renderer; int frameIndex; IDisposable disposable; // 途中停止用 public enum DefaultAction { // OnEnable時の動作指定 None, Play, Loop } [SerializeField] DefaultAction defaultAction; void OnStart() { switch (defaultAction) { case DefaultAction.Play: Play(); break; case DefaultAction.Loop: Loop(); break; } } /** * アニメーション初期化 */ void Init() { Stop(); renderer = GetComponentInChildren<SpriteRenderer>(); renderer.sprite = null; frameIndex = 0; } /** * 一回だけアニメーション実行 */ public void Play() { Init(); disposable = Observable.Interval(System.TimeSpan.FromMilliseconds(1000 / fps)) .Take(frames.Length + 1) .Subscribe(_ => { if (frames.Length <= frameIndex) { renderer.sprite = null; frameIndex = 0; OnAnimationFinish(); } else { renderer.sprite = frames[frameIndex]; frameIndex++; } }); } // アニメーション終了時に呼び出す関数 protected virtual void OnAnimationFinish() { } /** * ループ実行 */ public void Loop() { Init(); disposable = Observable.Interval(System.TimeSpan.FromMilliseconds(1000 / fps)) .Take(frames.Length) .RepeatUntilDisable(this) .Subscribe(_ => { if (frames.Length <= frameIndex) { renderer.sprite = null; frameIndex = 0; } renderer.sprite = frames[frameIndex]; frameIndex++; }); } /** * 停止 */ public void Stop() { if (disposable != null) { disposable.Dispose(); } disposable = null; } }
エディター上で実行するための拡張スクリプト
Assets/Editor ディレクトリを作成し、下のスクリプトを SpriteAnimationEditor.cs として保存します。
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEditor; [CustomEditor(typeof(SpriteAnimation), true)] public class SpriteAnimationEditor : Editor { public override void OnInspectorGUI(){ if (GUILayout.Button("Play")){ (target as SpriteAnimation).Play(); } if (GUILayout.Button("Loop")){ (target as SpriteAnimation).Loop(); } if (GUILayout.Button("Stop")){ (target as SpriteAnimation).Stop(); } base.OnInspectorGUI (); } }
実行してみる
インスペクタからSpriteオブジェクトにスクリプトをアタッチし、下のように設定してみます。
Frames はアニメーションのコマ、DefaultAction はオブジェクト作成時のデフォルトの動作を設定します。
設定したら、インスペクタのPlayボタンを押してください。
よきかな。