ecs: std/ecs with one Store per group type, and std/transform (ECS slice 1) #89

Open
opened 2026-10-05 21:07:19 +00:00 by orion · 3 comments
Collaborator

Context

Umbrella for ECS slice 1 of ECS.md section 13 plus std/transform (section 11). It needs nothing from the compiler (no seed impact in any step); examples/ecs-probe-2 builds the form. The design record stays the specification. Too large for one PR (a package, a scheduler with a native gate, and a second package), so it is split into the steps below; this issue closes when the last one has landed.

Goal

std/ecs (data layer and schedule with a sequential runner) and std/transform (decomposed transforms and their propagation over the hierarchy), each green on its own, with a native program that steps a world and prints the same bytes in the VM and natively.

Steps (dependency order; a step's PR says Refs #89, not Closes #89)

  1. #453 std/ecs data layer: Entity, Entities, Column, Store, Parent, depthOrder, the four query arities, Events, ComponentKey as a hand-written string; unit tests and the conformance program ecs-data. Ready.
  2. std/ecs schedule: System<World> with declared reads/writes, Stage (Input, Fixed, Update, Late, user stages), Schedule<World> with the sequential runner, the diagnostic for two systems of one stage that write the same key, the fixed-step accumulator over Duration (std/time); the gate of this slice: tests/conformance/ecs-schedule.trb steps a world through a schedule for several frames, VM and native byte for byte. Issue filed when it starts; waits on 1 merged.
  3. std/transform (depends on std/linear and std/ecs): Transform2/Transform3 as decomposed transformations (translation, rotation as Angle/Quaternion, scale) with composition, inverse, interpolated(toward:by:) and toMatrix3/toMatrix4; GlobalTransform2/GlobalTransform3 as their own components (ECS.md section 15 q7); the propagation system over depthOrder, generic over the stores it reads and writes. Over the scalar the way std/linear is (Float default, Fixed works). Issue filed when it starts; waits on 1 merged, independent of 2.

Slices 2 to 4 of the design record (#90) wait on this issue; slices 5 to 9 are #91 and #92.

Decisions (refinement)

  • One package per step boundary of ECS.md section 11: std/ecs knows nothing of positions or std/linear (it depends on std/core, std/collections, and std/time from step 2); std/transform is its own package and owns the arithmetic while std/ecs owns the order.
  • No World in std/ecs (section 15 q3); the conformance programs declare their own, as the probe does.
  • Step 1 ships the data layer alone: the gate is split into the two conformance programs of steps 1 and 2 so that each step is green on its own. Details and reasons are in #453.

Acceptance criteria (of the whole)

  • Entity, Column, Store, Events, System/Stage/Schedule, Parent, the four query arities (steps 1 and 2)
  • Gate: a native program steps a world and matches the interpreter byte for byte (ecs-data in step 1, ecs-schedule in step 2, both tier B)
  • std/transform (step 3)

Dependencies

None known. Verified against main (bc504c24) on 2026-10-24: ECS.md section 12 gaps 1, 3, 4, 5 and 11 are closed, which is all slice 1 uses.

Moved from the planning lists of the docs; the design record stays the specification.

## Context Umbrella for ECS slice 1 of [ECS.md section 13](https://git.torb.dev/torbscript/language/src/commit/bc504c243bbc6c247fdac1b6776100c2d7ebd044/docs/design/ECS.md#L1418) plus `std/transform` ([section 11](https://git.torb.dev/torbscript/language/src/commit/bc504c243bbc6c247fdac1b6776100c2d7ebd044/docs/design/ECS.md#L1257)). It needs nothing from the compiler (no seed impact in any step); `examples/ecs-probe-2` builds the form. The design record stays the specification. Too large for one PR (a package, a scheduler with a native gate, and a second package), so it is split into the steps below; this issue closes when the last one has landed. ## Goal `std/ecs` (data layer and schedule with a sequential runner) and `std/transform` (decomposed transforms and their propagation over the hierarchy), each green on its own, with a native program that steps a world and prints the same bytes in the VM and natively. ## Steps (dependency order; a step's PR says `Refs #89`, not `Closes #89`) 1. [ ] #453 `std/ecs` data layer: `Entity`, `Entities`, `Column`, `Store`, `Parent`, `depthOrder`, the four `query` arities, `Events`, `ComponentKey` as a hand-written string; unit tests and the conformance program `ecs-data`. **Ready.** 2. [ ] `std/ecs` schedule: `System<World>` with declared reads/writes, `Stage` (`Input`, `Fixed`, `Update`, `Late`, user stages), `Schedule<World>` with the sequential runner, the diagnostic for two systems of one stage that write the same key, the fixed-step accumulator over `Duration` (`std/time`); the **gate** of this slice: `tests/conformance/ecs-schedule.trb` steps a world through a schedule for several frames, VM and native byte for byte. Issue filed when it starts; waits on 1 merged. 3. [ ] `std/transform` (depends on `std/linear` and `std/ecs`): `Transform2`/`Transform3` as decomposed transformations (translation, rotation as `Angle`/`Quaternion`, scale) with composition, inverse, `interpolated(toward:by:)` and `toMatrix3`/`toMatrix4`; `GlobalTransform2`/`GlobalTransform3` as their own components (ECS.md section 15 q7); the propagation system over `depthOrder`, generic over the stores it reads and writes. Over the scalar the way `std/linear` is (`Float` default, `Fixed` works). Issue filed when it starts; waits on 1 merged, independent of 2. Slices 2 to 4 of the design record (#90) wait on this issue; slices 5 to 9 are #91 and #92. ## Decisions (refinement) - One package per step boundary of ECS.md section 11: `std/ecs` knows nothing of positions or `std/linear` (it depends on `std/core`, `std/collections`, and `std/time` from step 2); `std/transform` is its own package and owns the arithmetic while `std/ecs` owns the order. - No `World` in `std/ecs` (section 15 q3); the conformance programs declare their own, as the probe does. - Step 1 ships the data layer alone: the gate is split into the two conformance programs of steps 1 and 2 so that each step is green on its own. Details and reasons are in #453. ## Acceptance criteria (of the whole) - [ ] `Entity`, `Column`, `Store`, `Events`, `System`/`Stage`/`Schedule`, `Parent`, the four `query` arities (steps 1 and 2) - [ ] Gate: a native program steps a world and matches the interpreter byte for byte (`ecs-data` in step 1, `ecs-schedule` in step 2, both tier B) - [ ] `std/transform` (step 3) ## Dependencies None known. Verified against `main` (bc504c24) on 2026-10-24: ECS.md section 12 gaps 1, 3, 4, 5 and 11 are closed, which is all slice 1 uses. _Moved from the planning lists of the docs; the design record stays the specification._
Author
Collaborator

[loop:torbscript] intake: in scope (author orion, label loop), source ECS.md slice 1, not a duplicate, no collision with a design record. Needs nothing from the compiler per the issue (no seed impact), but is large; refine splits it. A native byte-for-byte gate against the interpreter runs in forge CI. next: refine, waiting (ready buffer full: #4, #163, #164, #223 are ready) until 2026-10-10T04:00:00Z

[loop:torbscript] intake: in scope (author orion, label loop), source ECS.md slice 1, not a duplicate, no collision with a design record. Needs nothing from the compiler per the issue (no seed impact), but is large; refine splits it. A native byte-for-byte gate against the interpreter runs in forge CI. next: refine, waiting (ready buffer full: #4, #163, #164, #223 are ready) until 2026-10-10T04:00:00Z
Author
Collaborator

[loop:torbscript] claim refine by session:loop-torbscript-20261024 until 2026-10-24T02:15:21Z

[loop:torbscript] claim refine by session:loop-torbscript-20261024 until 2026-10-24T02:15:21Z
Author
Collaborator

[loop:torbscript] refine: too large for one PR (a package, a scheduler with a native gate, a second package), so #89 is now the umbrella with a three-step checklist and its body rewritten (criteria kept, grouped by step). Step 1 filed as #453 (std/ecs data layer, ready); steps 2 (schedule and the ecs-schedule native gate) and 3 (std/transform) get their issues when they start, per the contract. #89 stays without ready. No owner question: every product choice is decided in ECS.md section 15. No seed impact. Worker usage: one refine worker, sonnet, about 0.4M tokens. next: waiting (steps in #453, then 2 and 3 in order)

[loop:torbscript] refine: too large for one PR (a package, a scheduler with a native gate, a second package), so #89 is now the umbrella with a three-step checklist and its body rewritten (criteria kept, grouped by step). Step 1 filed as #453 (`std/ecs` data layer, `ready`); steps 2 (schedule and the `ecs-schedule` native gate) and 3 (`std/transform`) get their issues when they start, per the contract. #89 stays without `ready`. No owner question: every product choice is decided in ECS.md section 15. No seed impact. Worker usage: one refine worker, sonnet, about 0.4M tokens. next: waiting (steps in #453, then 2 and 3 in order)
Sign in to join this conversation.
No labels
loop
ready
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
torbscript/language#89
No description provided.