HullCourier
GamesThird-person driving

Courier

Every parcel, on time, across the valley. Hover-bike parcel delivery across a 1.28 km procedural valley, built to see whether the engine fits a game unlike Shroud.

Courier: a hover bike on the open road through a green valley, lakes and low-poly pines, speed 97 on the HUD
Courier, open road

The game

Hover-bike parcel delivery across a 1.28 km procedural valley: eight towns, ten farms, roads, lakes, forests and a mountain rim. Pick up parcels, deliver before par and keep your streak alive until the shift clock runs out. Everything is procedural; there are no asset files.

It was built to test the engine on something unlike Shroud: third person, open map, driving. Everything it needed that a third game would also need went into the engine.

~3,150
lines of game code, on the engine’s ~14,300
8.3 ms
average frame
~1,120
of 7,835 meshes drawn

Where the line falls

From the engine

  • Menus and screensMenuConfig, a shift-select and a records screen with register_screen, and a sticky results screen.
  • SettingsIts own CourierSettings section with Gameplay and Camera tabs ahead of the engine’s Controls, Video and Audio.
  • SceneryStreamAbout 9,000 props streamed by cell. Colliders are spawned once, outside streaming.
  • Metrics, control port, tracecourier.* control commands and its own metrics keys behind the dev feature.

In Courier

  • Terrain and propsNoise, the fixed map layout of towns, farms and roads, and where every house, tree and rock stands.
  • The bikeHover physics on avian: ray hover, steering, grip, boost, hop and reset.
  • Shift rulesJobs, par times, scoring, streaks and records, pure and tested.

Screens

What the engine gained from it

  • ChaseCameraThird-person follow for any root entity: trails the heading, looks ahead, orbits with the mouse and pulls in front of walls.
  • MeshKitLow-poly vertex-coloured meshes from primitives, for games with no models.
  • DataDir JSON savesRecords saved next to settings.json with the same atomic writes and corrupt-file handling.
  • SunSetupOpen maps need shadows to about 300 m with 4 cascades; the arena sun stopped at 90 m.
  • Two gotchas, now documentedA game names bevy in its own Cargo.toml so derives resolve. SpatialQuery plus a mutable Position query needs a ParamSet.
courier/src/menus.rs
.insert_resource(Theme::default().with_accent(Color::srgb(1.0, 0.78, 0.22)))
.insert_resource(MenuConfig {
    eyebrow: "Hover-bike parcel delivery",
    main_items: vec![
        ("Start shift", MenuAction::Open("shift")),
        ("Records", MenuAction::Open("records")),
        ("Settings", MenuAction::Settings),
        ("Quit", MenuAction::Quit),
    ],
    ..default()
})