feat(ecs): ludic.vehicles on a Table<Vehicle>

The vehicles are rows of a ludic.base Table with kind and owner as columns, every player's own by
an owner index and a nid map: vehicle_of walks only that player's rows, vehicle_by_nid is a map
lookup, and a player who leaves has their rows removed instead of the whole list rebuilt. ve_add
takes the owner, so the owner is filed once and never assigned around the table. Positions stay
on the record: a boat moves every frame and there are at most two a player. vehicles_test holds
the table (9 tests); the game builds against it and lab/unit passes (88 tests).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Orkun ÇAKILKAYA 2026-09-27 21:50:23 +03:00
parent 52270ab5d1
commit 045bf22e10
8 changed files with 87 additions and 18 deletions

View file

@ -344,4 +344,23 @@ program VehiclesTest {
expect_near(vehicle_find(vehicles_st, VEHICLE_HORSE).food, 77.0, 0.01)
expect(not vehicle_find(vehicles_st, VEHICLE_BOAT).owned)
}
test "the table: a nid finds its vehicle, each player's own by the owner index, and a release takes both" (vehicles_st: mut VehiclesState, vehicles_test_st: mut VehiclesTestState) {
fresh(vehicles_st, vehicles_test_st)
vehicle_call_for(vehicles_st, 5, VEHICLE_HORSE, 0)
vehicle_call_for(vehicles_st, 5, VEHICLE_BOAT, 0)
vehicle_call_for(vehicles_st, 6, VEHICLE_BOAT, 1)
let b = vehicle_of(vehicles_st, 6, VEHICLE_BOAT)
expect(b != null)
expect(vehicle_by_nid(vehicles_st, b.nid) == b)
expect(vehicle_of(vehicles_st, 6, VEHICLE_HORSE) == null)
let h = vehicle_of(vehicles_st, 5, VEHICLE_HORSE)
vehicles_release(vehicles_st, 5)
expect_eq(len(vehicles_all(vehicles_st)), 1)
expect(vehicle_by_nid(vehicles_st, h.nid) == null)
expect(vehicle_of(vehicles_st, 6, VEHICLE_BOAT) == b)
vehicles_reset(vehicles_st)
expect_eq(len(vehicles_all(vehicles_st)), 0)
expect(vehicle_by_nid(vehicles_st, b.nid) == null)
}
}