CharacterBody3Dの移動とジャンプの実装
このドキュメントでは、Godot EngineにおけるCharacterBody3Dノードを用いたプレイヤーキャラクターの移動とジャンプの実装について、技術的な側面から掘り下げて解説します。牛肉、豚肉、鶏肉、ジビエといった食肉の情報は、この文脈では直接的な関連がありませんが、もしキャラクターのステータスや能力に何らかの形で影響を与える、といったゲームデザイン上の意図があれば、それらをコードに落とし込む際の思考プロセスや、具体的な実装例についても触れる可能性があります。ただし、本題はあくまでCharacterBody3Dの物理的な挙動に焦点を当てます。
移動の実装
入力を受け取る
キャラクターの移動は、プレイヤーからの入力に基づいて行われます。Godot Engineでは、InputMapに定義されたアクション(例: “move_forward”, “move_backward”, “move_left”, “move_right”)を検知することで、キーボード、ゲームパッド、タッチスクリーンなどの入力を抽象化します。
これらのアクションは、Input.get_action_strength(action_name)やInput.is_action_pressed(action_name)といったメソッドで取得できます。移動方向の決定には、通常、get_vector()メソッドが便利です。これは、複数の方向アクション(例: 前進と後退)を組み合わせて、正規化された2Dベクトルを返します。
var input_vector = Vector2()
input_vector.x = Input.get_action_strength("move_right") - Input.get_action_strength("move_left")
input_vector.y = Input.get_action_strength("move_backward") - Input.get_action_strength("move_forward")
input_vector = input_vector.normalized()
方向ベクトルへの変換
取得した2Dの入力ベクトルは、3D空間での移動方向ベクトルに変換する必要があります。これは、カメラの向きやキャラクター自身の向きを考慮して行われます。一般的には、カメラの前方ベクトルや右方ベクトルを用いて、ワールド空間での移動方向を算出します。
例えば、カメラの向きを考慮する場合、Camera3Dノードのglobal_transform.basisから前方ベクトルを取得し、それにinput_vector.yを乗算します。同様に、右方ベクトルとinput_vector.xを組み合わせて、最終的な移動方向ベクトルmove_directionを生成します。
var camera_transform = get_viewport().get_camera_3d().global_transform
var forward_direction = -camera_transform.basis.z.normalized()
var right_direction = camera_transform.basis.x.normalized()
var move_direction = forward_direction * input_vector.y + right_direction * input_vector.x
move_direction = move_direction.normalized()
velocityへの適用
算出されたmove_directionと、設定された移動速度(move_speed)を掛け合わせ、CharacterBody3Dのvelocityプロパティに設定します。ここで、velocityはCharacterBody3Dが物理演算によって移動する際の速度を表します。
CharacterBody3Dは、move_and_slide()メソッドを呼び出すことで、このvelocityに基づいて移動し、衝突を処理します。move_and_slide()は、velocityを移動量として使用し、衝突が発生した場合はvelocityを適切に調整します。
var move_speed = 5.0
if move_direction:
velocity.x = move_direction.x * move_speed
velocity.z = move_direction.z * move_speed
else:
velocity.x = lerp(velocity.x, 0.0, 0.1) # 入力がない場合は徐々に減速
velocity.z = lerp(velocity.z, 0.0, 0.1)
地面との接地判定
移動処理において、キャラクターが地面に接地しているかどうかの判定は非常に重要です。CharacterBody3Dは、is_on_floor()メソッドを提供しており、これにより現在のフレームで地面に接触しているかを確認できます。この情報は、ジャンプの可否や、落下時の挙動を制御するために使用されます。
減速処理
プレイヤーからの入力がない場合、キャラクターはすぐに停止するのではなく、徐々に減速する方が自然な挙動になります。これは、lerp()関数を使用して現在のvelocityと目標速度(この場合は0)の間を滑らかに補間することで実現できます。減速の速さは、補間係数(例: 0.1)で調整します。
牛肉・豚肉・鶏肉・ジビエとの関連性(仮説)
もし、ゲームデザインにおいて、例えば「牛肉を摂取すると一時的に移動速度が向上する」といった要素がある場合、move_speedの値を動的に変更する処理を実装することになります。
具体的には、プレイヤーが牛肉アイテムを拾った際に、move_speedに加算する処理や、一定時間後に元の速度に戻すタイマー処理などを追加します。同様に、豚肉や鶏肉、ジビエについても、それぞれ異なる効果(例: 落下ダメージ軽減、ジャンプ力向上など)をvelocityやその他のパラメータに反映させる形で実装が考えられます。
ジャンプの実装
ジャンプ入力の検知
ジャンプも移動と同様に、プレイヤーからの入力(例: “jump”アクション)によってトリガーされます。Input.is_action_just_pressed("jump")を使用することで、ジャンプボタンが押された瞬間にのみtrueを返します。
ジャンプの条件
ジャンプは、キャラクターが地面に接地している場合にのみ実行可能としたい場合がほとんどです。そのため、ジャンプ入力の検知と同時にis_on_floor()メソッドの結果を確認します。
var jump_force = 8.0
if Input.is_action_just_pressed("jump") and is_on_floor():
velocity.y = jump_force
重力の影響
ジャンプ後、キャラクターは重力によって落下します。Godot EngineのCharacterBody3Dは、move_and_slide()メソッドが内部的に重力を考慮してvelocityを更新してくれるため、別途重力値をvelocity.yに適用する必要はありません。ただし、CharacterBody3Dのgravity_scaleプロパティなどを調整することで、重力の強さを変更することは可能です。
move_and_slide()は、is_on_floor()がfalseである場合、velocity.yに重力による加速度を加算します。これにより、キャラクターは自然な放物線を描いて落下します。
二段ジャンプなどの応用
is_on_floor()の判定を応用することで、二段ジャンプや壁キックなどの高度なジャンプアクションも実装できます。
- 二段ジャンプ: 最初のジャンプ後、空中にいる間に再度ジャンプボタンが押された場合に、追加のジャンプ力を与えます。この場合、ジャンプ回数をカウントする変数などを導入します。
-
壁キック: 壁に接触していることを判定し(
get_slide_collision_count()などを利用)、壁に跳ね返るような力を加えます。
牛肉・豚肉・鶏肉・ジビエとの関連性(仮説)
例えば、「ジビエ(例: 鹿肉)を摂取すると、一時的にジャンプ力が強化される」といったゲームデザインの場合、ジャンプ力を決定するjump_forceの値を、ジビエの摂取に応じて一時的に増加させる処理を実装します。
これは、jump_forceを直接変更するだけでなく、キャラクターのジャンプ力を管理する別の変数(例: base_jump_forceとjump_force_modifier)を用意し、それらを組み合わせて最終的なジャンプ力を決定することで、より柔軟な制御が可能になります。
まとめ
CharacterBody3Dを用いた移動とジャンプの実装は、入力の取得、方向ベクトルの計算、velocityへの適用、そしてmove_and_slide()メソッドの活用が基本となります。is_on_floor()メソッドは、これらの機能において重要な役割を果たします。
牛肉、豚肉、鶏肉、ジビエといった食肉情報をゲームプレイに結びつける場合、それらのアイテムや効果が、移動速度、ジャンプ力、あるいはその他のキャラクターパラメータに直接影響を与えるように、move_speedやjump_forceなどの変数を操作する形で実装することが考えられます。これにより、プレイヤーは食料の選択がキャラクターの行動能力に影響を与えるという、ユニークなゲーム体験を得られるでしょう。
これらの実装は、ゲームのジャンルや目指すゲームプレイの感触によって、さらに細かく調整していく必要があります。例えば、よりアーケードライクな操作感を目指す場合は、減速や加速のカーブを滑らかにする、あるいは、よりリアルな物理演算を求める場合は、move_and_slide()の引数やCharacterBody3Dのその他のプロパティを調整するといったアプローチが考えられます。
