今回はUnityのキャラクターがジャンプをしている時にジャンプのアニメーションに合わせてコライダのサイズを調整して狭い場所もジャンプで通れるようにしていきたいと思います。
前回
でジャンプの機能を作成する事が出来ました。
単純に高い場所に到達するというだけのジャンプであれば問題はないのですが、
狭い空間を狙ってジャンプしそこを通り抜けるというような場面を作りたい場合は前回のジャンプ機能だけでは出来ません。
ジャンプで通り抜ける事が出来るかを確認
まずはジャンプで通り抜けられる狭い空間を作成し、そこをジャンプさせて確認してみます。
狭い空間はCubeを繋げて作り、キャラクターがジャンプした時に抜けられるだけの空間を空けておきます。
では前回までのジャンプ機能を使って通り抜けさせてみます。
ジャンプを実行した結果が上です。
うまく出来ても空間の下の地面に立てますが、奥に抜ける事が出来ません。
地面に立てても奥に歩いていく事も出来ません。なぜならコライダのサイズが空間の縦のサイズより大きいからです。
ではジャンプ中にうまくやれば通り抜けられるだろうと思われるかもしれませんが、
上がジャンプ中のキャラクターとコライダになります。
キャラクターはアニメーションでジャンプ中に丸まっていますが、コライダのサイズはそのままなので、空間を超える事が出来ません。
アニメーションカーブでコライダのサイズを変更出来る
これではジャンプであろうが、歩いてであろうが通り抜ける事が出来ません。
これを解消するにはジャンプ中にコライダのサイズを変更してアニメーションの状態にあったコライダにする必要があります。
これを実行出来るのがアニメーションカーブの機能です。
上のようにAssetsフォルダでジャンプのアニメーションのfbxを選択します。
アニメーションのインポートセッティングのAnimationsを選択すると上のような項目でCurvesがあります。
このCurveでコライダのサイズを変更していきます。
まずはアニメーションパラメータに上のようにColliderHeight、ColliderRadius、ColliderCenterというパラメータをfloatで作成します。
それぞれコライダの高さ、半径、中心位置を表しています。
CharacterControllerを使用しているのであれば、キャラクターに設定しているCharacterControllerのパラメータ値と同じ値をアニメーションパラメータの初期値として設定しておきます。
RigidbodyとCapsuleColliderでキャラを動かしている場合はCapsuleColliderの値を入れます。
アニメーションカーブのパラメータを調整する
次に上の赤い四角部分の+をクリックしCurveのパラメータを足していきます。
名前をさきほど作成したアニメーションパラメータと同じ名前にしてください。
同じ名前にする事によってCurveで変更した値がアニメーションパラメータに反映されるようになります。
上の画像ではすでにCurveのパラメータを設定してありますが、本来はアニメーションの再生位置によってパラメータを変更していく必要があります。
今回はColliderHeight(コライダの高さ)のCurveのパラメータを設定だけやってみます。
上の画像の右の赤い四角部分をクリックするとそこにKeyを打てます。
パラメータ値の変更地点を作りたい時に使います。
通常はアニメーションの最初と最後に自動的に設定されています。
最初はコライダの高さを1.6にします。これはキャラクターに設定したコライダのインスペクタの値と同じです。
次にKeyを打つのはジャンプ直後のアニメーション位置です。
ここまではコライダの高さを変更させない為にKeyを打ち値を1.6に設定します。
次にKeyを打つのはジャンプ後の最高点に達した時です。
この時のアニメーションは体を丸めているので、コライダの高さを小さくします。
パラメータは0.8と通常の半分に設定しています。
前の位置とこの位置との間のアニメーションではコライダの高さが補間されなめらかに変更されます。
次のKeyは着地した時です。
Unityの実行ボタンを押してジャンプキーを押し、一時停止ボタンを押した後にSceneタブを開きコマ送りボタンを押してジャンプ中のコライダの高さを確認し、インスペクタでCharacterControllerのコライダを変更しながら目的のサイズを探すといいです。
次はジャンプ後に少し体が跳ね上がる部分でKeyを打ちます。
前述したように、実行時にインスペクタのコライダ値を調整して高さを調べて設定します。
パラメータは1.4に設定します。
アニメーションの最後のKeyでは着地後に走り出す状態なので、通常のコライダの高さ1.6に戻します。
これでコライダの高さの調整が終わりました。
さきほど記述しましたが、設定するパラメータの値はUnityの実行ボタンを押して一時停止させ、Scene画面を表示し、コマ送りボタンで少しづつ再生し、インスペクタのコライダの値を調整して調べていきます。
コライダの半径や中心位置も同じように設定していきます。
今回調整した値は上のようになります。
参考にしてください。
少し気をつけなければいけないのがColliderCenterの値で、ジャンプ後の着地の時(少し前から)に位置を少し上にしておかないと足の部分が地面にめり込んでしまいます。
ここら辺は実行ボタンを押しながら確認し調整値を探る必要があります。
今回設定した値はめり込まないとは思います。
これでアニメーションカーブの設定が終了しました。
スクリプトでアニメーションパラメータの値を取得し、コライダのサイズを変更する
あとはパラメータ値をスクリプトで取得し、コライダのサイズを変更する処理を加えます。
キャラクターの移動スクリプトのUpdateメソッドにコライダの取得処理を追加します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 | void Update () { if (characterController.isGrounded) { velocity = Vector3.zero; } var input = new Vector3(Input.GetAxis("Horizontal"), 0f, Input.GetAxis("Vertical")); // 方向キーが多少押されている if(input.magnitude > 0f) { animator.SetFloat("Speed", input.magnitude); transform.LookAt(transform.position + input); velocity.x = input.normalized.x * 2; velocity.z = input.normalized.z * 2; // キーの押しが小さすぎる場合は移動しない } else { animator.SetFloat("Speed", 0f); } // ジャンプキー(デフォルトではSpace)を押したらY軸方向の速度にジャンプ力を足す if(Input.GetButtonDown("Jump") && !animator.GetCurrentAnimatorStateInfo(0).IsName("Jump") && !animator.IsInTransition(0) ) { animator.SetBool ("Jump", true); velocity.y += jumpPower; } // コライダの高さの調整 characterController.height = animator.GetFloat("ColliderHeight"); // コライダの中心位置の調整 characterController.center = new Vector3(characterController.center.x, animator.GetFloat("ColliderCenter"), characterController.center.z); // コライダの半径の調整 characterController.radius = animator.GetFloat("ColliderRadius"); velocity.y += Physics.gravity.y * Time.deltaTime; characterController.Move(velocity * Time.deltaTime); } |
CharacterControllerを使ってキャラクターを動かしている場合はCharacterControllerコンポーネントを取得しておきます。
変数名をcharacterControllerとしたならば
characterController.heightがコライダの高さ
characterController.centerがコライダの中心位置
characterController.radiusがコライダの半径
となるので
1 2 3 | characterController.height = animator.GetFloat("ColliderHeight"); |
とすればアニメーションパラメータColliderHeight(アニメーションカーブで設定した値が入る)の値をコライダの高さにします。
コライダのサイズを変更する条件に
1 2 3 | animator.GetCurrentAnimatorStateInfo(0).IsName("Jump") |
という条件を加えてコライダのサイズを変更しようとしましたが、これだとIdleやRunとのアニメーションミックス時に検出出来ない?っぽいので条件は入れませんでした。
アニメーションパラメータの初期値にコライダのインスペクタの初期値を入れておかないと、
animator.GetFloat(“ColliderHeight”)等の値が0になってしまう為、アニメーターコントローラーのアニメーションパラメータ
ColliderHeight
ColliderCenter
ColliderRadius
に必ず初期値を入れておいてください。
これでコライダのサイズ調整の処理が完成したので、ジャンプ中にコライダのサイズがどう変わるか確認してみます。
上のようにジャンプ中にアニメーションによってコライダのサイズが変更されるようになりました。
では狭い空間を飛び越えさせてみます。
上のように最初はコライダが邪魔して通れなかった空間をコライダのサイズを変更する事で、飛び越えられるようになりました。
画像ではジャンプタイミングとの兼ね合いで少しひっかかってしまってますが・・・・(^_^;)
頻繁にジャンプで狭い空間を通り抜けるようなゲームで、ひっかかりを少なくする為にはジャンプ中のコライダのサイズをもう少し小さくした方がいいかもしれません。
これでUnityのキャラクターコライダのサイズをアニメーションに応じて調整するようにし、ジャンプ中のコライダのサイズを変更して、狭い場所も通れるようになりました。
今回使っているジャンプアニメーションのように飛んだあとに前宙し、着地、その後反動で少しはねるのような場合はコライダの調整が面倒ですが、ただ足を上げて着地時に戻すようなジャンプアニメーションであればアニメーションカーブの値の設定も楽になると思います。