diff --git a/player.gd b/player.gd index a0fa87c..f0458ca 100644 --- a/player.gd +++ b/player.gd @@ -1,12 +1,25 @@ extends CharacterBody3D -const SPEED = 5.0 +const WALK_SPEED = 6.0 +const CHARGE_SPEED = 18.0 +const WALK_ACCEL = 14.0 +const CHARGE_ACCEL = 40.0 # snaps to charge speed quickly — burst feel +const DECELERATION = 12.0 +const CHARGE_DECEL = 3.5 # momentum lingers after releasing shift + +const WALK_TURN_FAST = 8.0 # rad/s at rest +const WALK_TURN_SLOW = 3.5 # rad/s at full walk speed +const CHARGE_TURN = 0.55 # rad/s — ~31 deg/s, very wide committed arc + const JUMP_VELOCITY = 4.5 -@export var turn_speed: float = 10.0 +@export var visual_turn_speed: float = 12.0 @onready var camera_pivot: Node3D = $SpringArmPivot -@onready var cube_guy: Node3D = $bull_v10 +@onready var cube_guy: Node3D = $bull_v10 + +var current_speed: float = 0.0 +var facing_angle: float = 0.0 func _physics_process(delta: float) -> void: @@ -16,19 +29,38 @@ func _physics_process(delta: float) -> void: if Input.is_action_just_pressed("jump") and is_on_floor(): velocity.y = JUMP_VELOCITY - var input_dir := Input.get_vector("move_left", "move_right", "move_forward", "move_back") - var cam_basis := camera_pivot.global_transform.basis + var input_dir := Input.get_vector("move_left", "move_right", "move_forward", "move_back") + var cam_basis := camera_pivot.global_transform.basis var flat_forward := -Vector3(cam_basis.z.x, 0.0, cam_basis.z.z).normalized() - var flat_right := Vector3(cam_basis.x.x, 0.0, cam_basis.x.z).normalized() - var direction := (flat_forward * -input_dir.y + flat_right * input_dir.x).normalized() + var flat_right := Vector3(cam_basis.x.x, 0.0, cam_basis.x.z).normalized() + var direction := (flat_forward * -input_dir.y + flat_right * input_dir.x).normalized() + # Logic for mimicking 4 legged animal movement if direction: - velocity.x = direction.x * SPEED - velocity.z = direction.z * SPEED - else: - velocity.x = move_toward(velocity.x, 0.0, SPEED) - velocity.z = move_toward(velocity.z, 0.0, SPEED) + var target_angle := atan2(direction.x, direction.z) - cube_guy.rotation.y = lerp_angle(cube_guy.rotation.y, camera_pivot.rotation.y + PI, delta * turn_speed) + # Snap on first movement so there is no startup arc from 0 + if current_speed < 0.01: + facing_angle = target_angle + + var charging := Input.is_key_pressed(KEY_SHIFT) + var speed_t: float = clampf(current_speed / WALK_SPEED, 0.0, 1.0) + var turn_rate: float = CHARGE_TURN if charging else lerpf(WALK_TURN_FAST, WALK_TURN_SLOW, speed_t) + + var diff := wrapf(target_angle - facing_angle, -PI, PI) + facing_angle += clampf(diff, -turn_rate * delta, turn_rate * delta) + + var top_speed: float = CHARGE_SPEED if charging else WALK_SPEED + var accel: float = CHARGE_ACCEL if charging else WALK_ACCEL + current_speed = move_toward(current_speed, top_speed, accel * delta) + else: + var charging := Input.is_key_pressed(KEY_SHIFT) + var decel: float = CHARGE_DECEL if charging else DECELERATION + current_speed = move_toward(current_speed, 0.0, decel * delta) + + velocity.x = sin(facing_angle) * current_speed + velocity.z = cos(facing_angle) * current_speed + + cube_guy.rotation.y = lerp_angle(cube_guy.rotation.y, facing_angle, delta * visual_turn_speed) move_and_slide() diff --git a/scene.tscn b/scene.tscn index 3cafe85..6b581bf 100644 --- a/scene.tscn +++ b/scene.tscn @@ -4,24 +4,24 @@ [ext_resource type="PackedScene" uid="uid://dio67r8ambe7h" path="res://Assets/arena_placeholder_v01.glb" id="2_nxogm"] [sub_resource type="BoxShape3D" id="BoxShape3D_ulcgi"] +size = Vector3(1, 1, 1) [node name="scene" type="Node3D" unique_id=22320312] [node name="Player" parent="." unique_id=165510044 instance=ExtResource("1_ulcgi")] -transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 2.3040223, 0) +transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1.5, 0) [node name="DirectionalLight3D" type="DirectionalLight3D" parent="." unique_id=818712731] transform = Transform3D(0.030703627, 0.98235905, -0.18446636, -0.1612905, 0.18700416, 0.9690277, 0.9864293, -1.2735805e-08, 0.16418687, -4.08134, 0.3070748, 0.97087634) shadow_enabled = true [node name="Node3D" type="Node3D" parent="." unique_id=1081100876] -transform = Transform3D(3.5710833, 0, 0, 0, 1, 0, 0, 0, 2.2964425, 0, 0, 0) +transform = Transform3D(10, 0, 0, 0, 1, 0, 0, 0, 10, 0, 0, 0) [node name="StaticBody3D" type="StaticBody3D" parent="Node3D" unique_id=2072095624] -transform = Transform3D(1.0000001, 0, 0, 0, 1.0000001, 0, 0, 0, 1.0000001, 0, 0, 0) [node name="CollisionShape3D" type="CollisionShape3D" parent="Node3D/StaticBody3D" unique_id=1444198204] -transform = Transform3D(7.6892185, 0, 0, 0, 0.34217754, 0, 0, 0, 8.638921, 0, 0, 0) +transform = Transform3D(30, 0, 0, 0, 1, 0, 0, 0, 30, 0, -0.5, 0) shape = SubResource("BoxShape3D_ulcgi") [node name="arena_placeholder_v01" parent="Node3D" unique_id=1341659233 instance=ExtResource("2_nxogm")]