Feat/1 movement foundation #5

Merged
Dotts merged 40 commits from feat/1-movement-foundation into main 2026-06-03 21:34:25 -07:00
Owner
No description provided.
Dotts added the movement label 2026-06-03 21:33:44 -07:00
Dotts added 39 commits 2026-06-03 21:33:44 -07:00
- MovementStateMachine: core state machine base
- MovementParams: export-rich tunable resource
- StateGround/StateAir: grounded & aeriel locomotion with coyote, buffered jump, bunny hop
- StateWallRun / StateWallCling: wall-based traversal with wall-jump off
- StateSlide: sprint-parallel slide with friction fallout
- StateDash: burst dash with momentum brake
- PlayerMovementController: entry point wiring to CharacterBody3D
- input_map.cfg: full action map reference file
- characters/player/player_base.tscn: placeholder scene
- movement/tests/test_fsm_runner.gd: 9-state unit test runner

Closes #1
- state_dash.gd: Basis*Vector4 → Basis*Vector3 (no Vec4 in Godot 4.2)
- state_ground.gd: shape_owner_get_shape(0) → (0, 0); typed Variant vars; typed ray/normal
- state_slide.gd: same shape API fix + unique shape vars per branch
- state_wall_run.gd: split 'and' line into single typed bool expression
- scenes/test_level/test_level.tscn — playable test environment (30x30 floor + 4 walls + ramp)
  Floor at y=-1, Player spawn at (0, 1.5, 8), FpsCamera at head height (y=1.7)
  DirectionalLight + WorldEnvironment + UI label overlay (speed/state/chain)
- debug/debug_test_env.sh — launch wrapper for manual playtesting

No code changes: raw physics testbed. Intended to be opened as first scene in Godot window.

Closes #2 (test-level scene task)
Rewrote scene without ext_resource / subresource UIDs so it loads from the repo root.
SubResource UIDs: box_floor, box_wall_north, box_wall_east, box_wall_west
Removes parse error at line 9
- Removed all SubResource BoxShape3D references from test_level.tscn
- Changed PackedStringArray feature from 4.6 to 4.2
Scene is now pure nodes + transforms, no external resource IDs
- Use numeric SubResource(id) instead of uid:// strings (avoids parser error)
- Light transform: remove non-uniform scale, set only rotation + position
- Keep floor@y=-1.1, walls thin (0.4), PlayerSpawn unchanged
- test_level.tscn: minimal Node3D root (zero SubResource references)
- debug/test_level_builder.gd: runtime floor/walls/lighting/camera/UI
  shapes/meshes created from BoxShape3D/BoxMesh — no .tscn subresources
- project.godot: revert features to 4.6 (installed build is 4.6.3)
- _build_player: creates Player (CharacterBody3D) with capsule,
  MovementStateMachine + 6 state children, attaches movement script
- Calls player._ready() manually after set_script (GDScript
  set_script does not auto-trigger _ready)
- Camera parented under Player so it follows movement
- Restores _build_camera() which was accidentally dropped
- state_wall_run.gd: typed ray_origin/ray_end as Vector3
- test_level_builder.gd: restructure builder to put MovementStateMachine
  + state children under Player, attach camera under Player too
- player_movement_controller.gd: @onready uses get_node so type is not inferred
player_movement_controller.gd: use Node + get_node() instead of
typed MovementStateMachine + $ shorthand so runtime set_script paths
don't crash on @implicit_ready
Root cause: builder created plain Node instances for the state machine
and states, so _machine.player = self in PlayerMovementController
crashed with 'Invalid assignment ... on base object of type Node'.
Now each node gets its real script attached before _ready() runs.
Dotts added 1 commit 2026-06-03 21:34:18 -07:00
Dotts merged commit a54b3d89b1 into main 2026-06-03 21:34:25 -07:00
Dotts deleted branch feat/1-movement-foundation 2026-06-03 21:34:25 -07:00
Sign in to join this conversation.