Buravo46's Note

学んだ事を書いていくブログです。

【Unity】スクリプトでAnimationClipの作成

経緯

AnimationClipを利用して色々したいときに

スクリプトで作成できれば楽だと思い、調べることにしました。

利用場面

オブジェクトを現在位置から目標位置まで指定した秒数で移動させたり、

AnimationViewを使用してAnimationClipを制御するのが面倒なときに利用することができます。

手順の流れ

  1. スクリプトからAnimationClipを生成する。
  2. キーフレームを定義するAnimationCurveを作成しAnimationClipに追加する。
  3. AnimationClipをAnimationコンポーネントに追加して再生する。

上記の手順で、スクリプトからAnimationClipを作成することが出来ます。

AnimationCurveの作成には、

  1. Keyframeによる実装
  2. EaseInOut関数による実装
  3. Linear関数による実装

上記3種類の方法が有ります。

Keyframeによる実装

下記がKeyframeによる実装となります。

using UnityEngine;
using System.Collections;
/*===============================================================*/
/**
* Keyframeによる実装サンプル
* 2015年1月28日 Buravo
*/
public class KeyframeExample : MonoBehaviour 
{
    #region メンバ変数
    /*===============================================================*/
    /**
    * @brief 開始時間
    */ 
    private float m_start_time = 0.0f;
    /**
    * @brief 開始値
    */ 
    private float m_start_value = 0.0f;
    /**
    * @brief 終了時間
    */ 
    private float m_end_time = 5.0f;
    /**
    * @brief 終了値
    */ 
    private float m_end_value = 10.0f;
    /*===============================================================*/
    #endregion
    
    /*===============================================================*/
    /**
    * @brief 最初に一度だけ実行されるメソッド
    */ 
    void Start ()
    {
        // もしもアニメーションコンポーネントがなければ追加.
        if (!animation)
        {
            gameObject.AddComponent<Animation>();
        }
        // AnimationClipの生成.
        AnimationClip clip = new AnimationClip();
        // AnimationCurveの生成.
        AnimationCurve curve = new AnimationCurve();
        // Keyframeの生成.
        Keyframe startKeyframe = new Keyframe(m_start_time, m_start_value);
        Keyframe endKeyframe = new Keyframe(m_end_time, m_end_value);
        // Keyframeの追加.
        curve.AddKey(startKeyframe);
        curve.AddKey(endKeyframe);
        // AnimationCurveの追加.
        clip.SetCurve("", typeof(Transform), "localPosition.x", curve);
        // AnimationClipの追加.
        animation.AddClip(clip, "Move");
        // AnimationClipの再生.
        animation.Play("Move");
    }
    /*===============================================================*/
}
/*===============================================================*/

このスクリプトではアニメーションクリップでオブジェクトのX座標を0~10へと動かしています。

それではこのスクリプトの簡単な解説をしていきます。

まずはアニメーションクリップの生成を

AnimationClip clip = new AnimationClip();

でしています。

次にアニメーションカーブの生成を

AnimationCurve curve = new AnimationCurve();

でしています。

このアニメーションカーブに追加するためのキーフレームを

Keyframe startKeyframe = new Keyframe(m_start_time, m_start_value);

で生成しています。

Keyframeは引数に

  • 時間

をfloat型の値として渡すことで生成することが出来ます。

このスクリプトでは開始キーフレームと終了キーフレームを生成して、

5秒かけて値を0から10へと変化させるようにしています。

そして、この生成したキーフレームを

curve.AddKey(startKeyframe);

で追加しています。

このスクリプトでは丁寧にキーフレームを追加していますが、下記のコードのようにAnimationCurveを生成する段階でまとめて追加することも可能です。

// もしもアニメーションコンポーネントがなければ追加する.
if (!animation)
{
    gameObject.AddComponent<Animation>();
}
// AnimationClipの生成.
AnimationClip clip = new AnimationClip();
// Keyframeの生成.
Keyframe startKeyframe = new Keyframe(m_start_time, m_start_value);
Keyframe endKeyframe = new Keyframe(m_end_time, m_end_value);
// AnimationCurveの生成.
AnimationCurve curve = new AnimationCurve(startKeyframe, endKeyframe);
// AnimationCurveの追加.
clip.SetCurve("", typeof(Transform), "localPosition.x", curve);
// AnimationClipの追加.
animation.AddClip(clip, "Move");
// AnimationClipの再生.
animation.Play("Move");

そうして作成したAnimationCurveを

clip.SetCurve("", typeof(Transform), "localPosition.x", curve);

で追加しています。

AnimationClip.SetCurveではアニメーション化する情報を設定しており、

引数には

  • オブジェクトのパス
  • アニメーションするコンポーネントのタイプ
  • プロパティ名
  • AnimationCurve

を渡すことで設定することが出来ます。

オブジェクトのパスが空の場合、スクリプトを付加しているオブジェクト自身になります。

そうでない場合はスクリプトを付加しているオブジェクト自身からみた子供オブジェクトのパスという風に書けばいいと思います。

例えば、

clip.SetCurve(" Child", typeof(Transform), "localPosition.x", curve);

だとするとスクリプトを付加しているオブジェクトの子供オブジェクトであるChildのX座標を0~10へと動かすことになります。

あとはアニメーションクリップをアニメーションコンポーネントに追加して再生することをしています。

AnimationCurve.EaseInOutによる実装

下記がAnimationCurve.EaseInOutによる実装となります。

using UnityEngine;
using System.Collections;
/*===============================================================*/
/**
* EaseInOutによる実装サンプル
* 2015年1月28日 Buravo
*/
public class EaseInOutExample : MonoBehaviour 
{
    #region メンバ変数
    /*===============================================================*/
    /**
    * @brief 開始時間
    */ 
    private float m_start_time = 0.0f;
    /**
    * @brief 開始値
    */ 
    private float m_start_value = 0.0f;
    /**
    * @brief 終了時間
    */ 
    private float m_end_time = 5.0f;
    /**
    * @brief 終了値
    */ 
    private float m_end_value = 10.0f;
    /*===============================================================*/
    #endregion

    /*===============================================================*/
    /**
    * @brief 最初に一度だけ実行されるメソッド
    */ 
    void Start ()
    {
        // もしもアニメーションコンポーネントがなければ追加.
        if (!animation)
        {
            gameObject.AddComponent<Animation>();
        }
        // AnimationClipの生成.
        AnimationClip clip = new AnimationClip();
        // AnimationCurveの生成.
        AnimationCurve curve = AnimationCurve.EaseInOut(m_start_time, m_start_value, m_end_time, m_end_value);
        // AnimationCurveの追加.
        clip.SetCurve("", typeof(Transform), "localPosition.x", curve);
        // AnimationClipの追加.
        animation.AddClip(clip, "Move");
        // AnimationClipの再生.
        animation.Play("Move");
    }
    /*===============================================================*/
}
/*===============================================================*/

このスクリプトはKeyframeによる実装内容と同じことをしています。

違っている点はAnimationCurveの作成方法と値の変化速度です。

AnimationCurve curve = AnimationCurve.EaseInOut(m_start_time, m_start_value, m_end_time, m_end_value);

AnimationCurve.EaseInOutではゆっくりと開始して徐々に速度が上がり、真ん中辺りで徐々に速度を下げてゆっくりと終了する値の変化をします。

AnimationCurve.EaseInOutの引数には

  • 開始時間
  • 始値
  • 終了時間
  • 終了値

をfloat型の値として渡すことで作成することが出来ます。

AnimationCurve.Linearによる実装

下記がAnimationCurve.Linearによる実装となります。

using UnityEngine;
using System.Collections;
/*===============================================================*/
/**
* Linearによる実装サンプル
* 2015年1月28日 Buravo
*/
public class LinearExample : MonoBehaviour 
{
    #region メンバ変数
    /*===============================================================*/
    /**
    * @brief 開始時間
    */ 
    private float m_start_time = 0.0f;
    /**
    * @brief 開始値
    */ 
    private float m_start_value = 0.0f;
    /**
    * @brief 終了時間
    */ 
    private float m_end_time = 5.0f;
    /**
    * @brief 終了値
    */ 
    private float m_end_value = 10.0f;
    /*===============================================================*/
    #endregion

    /*===============================================================*/
    /**
    * @brief 最初に一度だけ実行されるメソッド
    */ 
    void Start ()
    {
        // もしもアニメーションコンポーネントがなければ追加.
        if (!animation)
        {
            gameObject.AddComponent<Animation>();
        }
        // AnimationClipの生成.
        AnimationClip clip = new AnimationClip();
        // AnimationCurveの生成.
        AnimationCurve curve = AnimationCurve.Linear(m_start_time, m_start_value, m_end_time, m_end_value);
        // AnimationCurveの追加.
        clip.SetCurve("", typeof(Transform), "localPosition.x", curve);
        // AnimationClipの追加.
        animation.AddClip(clip, "Move");
        // AnimationClipの再生.
        animation.Play("Move");
    }
    /*===============================================================*/
}
/*===============================================================*/

このスクリプトもKeyframeによる実装内容と同じことをしています。

違っている点はAnimationCurveの作成方法と値の変化速度です。

AnimationCurve curve = AnimationCurve.Linear(m_start_time, m_start_value, m_end_time, m_end_value);

AnimationCurve.Linearでは直線的な値の変化をします。

AnimationCurve.Linearの引数には

  • 開始時間
  • 始値
  • 終了時間
  • 終了値

をfloat型の値として渡すことで作成することが出来ます。

まとめ

AnimationClipは上記のような手順で作成することができます。

円運動をするアニメーションを作成したければ、細かく値を変化できるKeyframeによる実装を

真っ直ぐ動くアニメーションのような、直線的な値の変化であればLinearによる実装を

真っすぐは動くけど緩急を持たせたいのならば、値の変化に緩急を持たせれるEaseInOutによる実装をするなど場面に応じて使い分けるといいと思います。

参考サイト

Unityスクリプトリファレンス - AnimationClip

Unityスクリプトリファレンス - AnimationCurve

Unityスクリプトリファレンス - Keyframe