Skip to content

Player controller

The character controller is the vendored Hello Mario Framework by Hello Fangaming (Assets/HelloMarioFramework, MIT licensed). It is a complete 3D-platformer kit — player, enemies, items, menus, save system — of which hoseboy uses the player, the camera helper and a handful of utilities.

Do not edit the framework in place

Assets/HelloMarioFramework is third-party code with its own assembly definition (HelloMarioFramework.asmdef). Project code lives in Assets/Scripts and compiles into Assembly-CSharp, which references the framework assembly. Extend by adding components alongside, not by patching framework files — an upstream update should stay a clean overwrite.

Player

Assets/HelloMarioFramework/Script/Player.cs, ~980 lines, namespace HelloMarioFramework. Static Player.singleton. Rigidbody-based, not CharacterController.

Movement model

Physics is hand-rolled rather than left to the engine:

  • Speed cap. Horizontal velocity is capped at magnitude 9. When the cap is broken it is clamped at 18 instead, and the cap re-arms automatically once speed falls back under 9.
  • Gravity is applied manually in FixedUpdate, not by the rigidbody: 75 normally, 30 while a variable jump is rising, 0 when grounded or in heavy contact, and 1200 for the ground-pound hack. Fall speed is clamped at −24.
  • Variable jump height comes from switching gravity while the jump button is held.
  • Wall jumps, wall pushes, ground pound, double jump, moving-platform inheritance and floor snapping are all in the same FixedUpdate.

Public API hoseboy uses

Member Used by
Player.singleton FreeLookHelper
BreakSpeedCap() HoseRecoil, above half pressure
EnableControls(bool) intended for dialogue and cutscenes
hatAttachTransform FreeLookHelper look-at height

Also available and currently unused: Hurt(bool burn, Vector3 knockback), Knockback(Vector3), BounceUp(float), GetHealth(), Heal(), Kill(), Victory(bool), DisablePhysics() / EnablePhysics(Vector3), LockZAxis(bool), Rumble(float).

Beetle knockdown

Knockback(Vector3) and BounceUp(float) are the obvious substrate for the beetle swoop, which knocks the player down the mountain rather than damaging them. Prefer them over Hurt, which spends health.

Interaction with the hose

Two framework behaviours actively fight hoseboy code, and both are worked around rather than patched:

  1. Idle drag. The player parks linearDamping at 100 when idle, which would absorb the recoil entirely. HoseRecoil clamps drag down to sprayDrag while spraying.
  2. HideNearCamera. Added to the player by Player.Start at runtime; it shrinks the whole character when the camera gets close, which fights true first person. TrueFirstPersonBody disables it while in first person.

The third is ordering: HoseRecoil and FirstPersonBodyYaw both run at [DefaultExecutionOrder(200)] so their writes land after Player.FixedUpdate has written velocity and rotation for the step.

The character

The visible character is the Suriyun chibi model in Assets/Suriyun — a placeholder monkey for the boy. It is driven by the framework's BoneFollower (Script/Utility/BoneFollower.cs, execution order −10), which retargets the framework's own skeleton onto the model. Every pose-modifying script in the project — the arm IK, the head collapse, the bone attachments — is ordered after it for that reason.

Utilities worth knowing about

Assets/HelloMarioFramework/Script/Utility/ ships a lot that hoseboy will want rather than rewrite:

Component Use
Mover, MoverMulti, MoverButton moving platforms and button-driven platforms — the substrate for water inlets
Rotator, RotatorButton, RotatorReverse rotating geometry
Hazard, HazardCSG damage volumes
Respawner, HubRespawnPoint checkpointing
Wind directional force volumes
BoneFollower skeleton retargeting (in use)
HideNearCamera camera-proximity shrink (suppressed in first person)

Script/Enemy/ contains a full Mario-style enemy set (Galoomba, Thwomp, Magikoopa and so on). None of it is used. Beetles are being written fresh against the hose rather than against stomping, and the framework enemies should be treated as reference only.

NPC.cs is the framework's own dialogue NPC — a cursor above the head, a string[] dialogue array and a Cinemachine camera. hoseboy uses the Ink dialogue system instead, but NPC is a useful reference for the proximity-cursor and camera-cut behaviour a hoseboy NPC will need.