Unityでキャラクターがジャンプ出来るようにする

記事内に広告が含まれています。

今回はUnityでキャラクターをジャンプさせる機能を搭載してみます。
すでに80記事以上書いていて、今になってやっとジャンプ機能か、という感じですが・・・。

キャラクターを移動させる処理であったり、重力の処理がいまいちうまくいっておらず手を付けていませんでした。
そこら辺の処理が出来てきたので、今回ジャンプする機能をやってみました。

重力に関する記事は

Unityで間違った重力の計算をしているかも!?
Unityのキャラクター等に重力を働かせる事は多いですが、重力を働かせる処理が実は間違っているかもしれません。

を参考にしてください。

上の重力処理を間違えていると、ジャンプ機能がうまく出来ません。

スポンサーリンク

ジャンプ機能をキャラクター移動スクリプトに追加する

まずは、キャラクター移動スクリプトJumpCharaを作成します。

地面に接地している時に、方向キーで縦横の動きの処理を入れますが、その後に

で、Jumpに設定されているキーを押した時に、ジャンプさせる処理を入れます。

デフォルトでは、SPACEキーがJumpに設定されているので、SPACEキーを押すとジャンプするようになります。

キーの設定は、UnityのメニューでEdit→Project Settings→Inputで、設定されているキーの確認と変更が出来ます。

スクリプトではvelocity.yの値にjumpPowerを足して、上方向に移動値を加えます。

jumpPowerはインスペクタで値を設定出来るようにしています。

ジャンプキーを検知するのは、characterController.isGroundedがtrueの時、つまり地面に接地している時に行います。

それ以外の所でジャンプキーの検知をすれば、ジャンプ中にさらにジャンプさせ2段ジャンプの機能も作れると思いますが、重力値の計算との兼ね合いで混乱する可能性があります。

2段階ジャンプについては

Unityのゲームで2段階ジャンプの機能を作成する
Unityのアクションゲームで2段階ジャンプの機能を作成します。ジャンプ中にジャンプキーが押されたらそこからさらにジャンプ出来るようにします。

を参照してください。

これで、SPACEキーを押せばキャラクターがジャンプするようになります。

Unityの実行ボタンを押して確認してみてください。

jump1

立っている時と移動している時にSPACEキーを押すと、キャラクターがジャンプします。
移動中にジャンプキー押せば、縦横の移動をしながらジャンプするのがわかると思います。

ジャンプ中はジャンプ用アニメーションを再生する

ここまでの機能だと、ジャンプ中のアニメーションはその時のアニメーションを再生している状態です。

そこで、ジャンプ中はジャンプのアニメーションを再生するように変更します。

jump2

上のようにJump状態とアニメーションパラメータにJumpをBool型で作成します。

jump3

Idle→JumpへはJumpがtrueになった時に遷移するようにします。

Jumpのアニメーションクリップには、Standard AssetsのJumpを設定します。

このJumpは助走が入っているので、23%左に移動させ、助走部分が入らないようにします。

jump4

Jump→Idleへの遷移は、Has Exit Timeのチェックを入れ、条件にJumpがfalseの時を設定します。
これで、Jumpがfalseになってもジャンプアニメーションを最後まで再生するようになります。

着地後に、すぐ別のアニメーションに遷移させたい場合はHas Exit Timeのチェックを外し、スクリプトで着地後すぐアニメーションパラメータのJumpをfalseにします。

ジャンプアニメーションへ遷移させる処理をスクリプトに追加

これでアニメーターコントローラの設定が終わったのでJumpCharaスクリプトにアニメーション操作の処理を加えます。

ジャンプキーが押された時に

でアニメーションを遷移させます。

条件に

を追加していますが、これは現在ジャンプアニメーションを再生中でない時という意味で、着地後もジャンプアニメーションが再生されているので、それが終わるまでは再度ジャンプしないようにします。

キャラクターの移動処理の部分にも同じ処理が追加されていますが、着地後のジャンプアニメーション中にキャラが移動しないようにする為です。

着地後すぐジャンプアニメーションをやめ、移動できるようにする場合はこの条件はいりません。

これでスクリプトの編集が終わりました。

しかし、このままだとアニメーションパラメータのJumpがfalseになる事がないので、ジャンプのアニメーションの最後で止まってしまいます。

Behaviourを使ってアニメーションパラメータを操作する

せっかくなので以前に作成した記事

UnityのアニメーターコントローラーのStateMachineBehaviourでアニメを制御する
Unityのアニメーターコントローラーを通常のスクリプトで制御するのではなくBehaviourを使って制御するようにします

を使ってアニメーションパラメータを操作してみます。

jump5

アニメーターコントローラーのJumpの状態を選択し、インスペクタでAdd Behaviourをクリックし新しいスクリプトEndJumpを作成します。

現在の所、ビヘイビアはC#でしか作れないみたい?(JavaScriptでも作成出来ました)

ビヘイビアを作成するとデフォルトで以下のような記述がされています。

今回は、Jumpに遷移後にアニメーションパラメータのJumpをfalseにしたいので、OnStateEnterのコメント化されている部分を削除し、中に

という処理を追加します。

これでJump状態に遷移してすぐにアニメーションパラメータのJumpがfalseになります。

JavaScriptでEndJampビヘイビアスクリプトを作成するにはまず通常のJavaScriptファイルを作成し、StateMachineBehaviourクラスを継承して新しいクラスを作成します。

あとは通常のスクリプトのC#とJavaScriptの違いで使い方は同じです。

ビヘイビアはアニメーターコントローラーの状態のインスペクタのAdd Behaviourを押して追加します。

これでジャンプ機能が完成しました。

Unityの実行ボタンを押して確認してみましょう。

jump7

今回は、ジャンプのアニメーションが終了するまで操作不可にしてますが、前述したとおり、着地と同時にアニメーション遷移や移動させる事も可能なので、そこら辺は好みに応じてスクリプトを組んでいくといいと思います。

坂のような場所を下っている時に、CharacterControllerのIsGroundedがfalseになり、ジャンプが出来ない事があります。

そんな時は

UnityのCharacterControllerの接地が判断出来ない時にスクリプトを使う
UnityのキャラクターをCharacterControllerで動かしている場合に地面とキャラクター(厳密にはコライダ)が接地しているかどうかはIsGroundedプロパティで判断していますが、坂を下っている時はこの値がfalseになっています。そんな時にスクリプトで接地を判断してみます。

を参照してください。

下り坂やデコボコな道でIsGroundedで接地を判断出来ない時にも、スクリプトで設置を判断しジャンプさせる事が出来るようになります。

また2段階ジャンプをさせたい場合は

Unityのゲームで2段階ジャンプの機能を作成する
Unityのアクションゲームで2段階ジャンプの機能を作成します。ジャンプ中にジャンプキーが押されたらそこからさらにジャンプ出来るようにします。

↑も参考にしてください。

ジャンプ中に移動キーで移動させる

ツイッターで質問を頂きましたので、ジャンプ中に移動キーを押した時にキャラクターを移動させる方法を追記します。

ここまでのジャンプ機能では、ジャンプ中は操作できないような仕様にしていたので、ジャンプ中は移動キーを押してもキャラクターは空中で移動出来ませんでした。

しかし、ジャンプ中もキャラクターを動かしたい場合もあると思います。

そんな時は、キャラクターが地面に接地中に移動値を取得するという条件を外してしまいましょう。

接地した時は、velocityの値を初期化するだけにして、Update関数内で移動値は常に取得するようにします。

また、移動値はX方向とZ方向のvelocityを別に代入するようにします。

今までは接地している時だけvelocityに値を足すという形にしていましたが、そのまま足すという処理のままだとジャンプ中の移動でものすごく速い移動をしてしまいます。

なので、重力値であるvelocity.zの値を書き換えず個別に値を代入しています。

また、ジャンプ中にジャンプキーを押すと、たまにジャンプしてしまう不具合が発生したので

というアニメーションが遷移途中でないという条件を加えました。

これで、ジャンプ中の移動が出来るようになったので試してみましょう。

ジャンプ中に移動出来るサンプル

↑のようにジャンプ中に移動キーを押すと移動出来るようになりました。

終わりに

今回のジャンプ機能ではアニメーションパラメータのJumpをBool型で作成し、ビヘイビアを使ってJumpをfalseにしています。

ビヘイビアを使うという事も含めてそういう風に作りましたが、ビヘイビアを使わなくても出来ます。

アニメーションパラメータのJumpをTriggerで作成し、Jump→Idleの遷移はHas Exit Timeにチェックを入れるだけで他の条件を入れないようにします。

その他のJumpがtrueの時に遷移していた条件をTriggerのJumpにします。

JumpをTrigger型にしたのでスクリプトでアニメーションパラメータを変更する箇所では、

という風に記述します。

こちらの方がシンプルですね。

タイトルとURLをコピーしました