plan adjustments

This commit is contained in:
bQUARKz 2026-04-13 20:19:40 +01:00
parent 5c1e6dac83
commit 0723057038
Signed by: bquarkz
SSH Key Fingerprint: SHA256:Z7dgqoglWwoK6j6u4QC87OveEq74WOhFN+gitsxtkf8
6 changed files with 201 additions and 54 deletions

View File

@ -1,4 +1,4 @@
{"type":"meta","next_id":{"DSC":26,"AGD":26,"DEC":14,"PLN":16,"LSN":30,"CLSN":1}}
{"type":"meta","next_id":{"DSC":26,"AGD":26,"DEC":14,"PLN":17,"LSN":30,"CLSN":1}}
{"type":"discussion","id":"DSC-0023","status":"done","ticket":"perf-full-migration-to-atomic-telemetry","title":"Agenda - [PERF] Full Migration to Atomic Telemetry","created_at":"2026-04-10","updated_at":"2026-04-10","tags":["perf","runtime","telemetry"],"agendas":[{"id":"AGD-0021","file":"workflow/agendas/AGD-0021-full-migration-to-atomic-telemetry.md","status":"done","created_at":"2026-04-10","updated_at":"2026-04-10"}],"decisions":[{"id":"DEC-0008","file":"workflow/decisions/DEC-0008-full-migration-to-atomic-telemetry.md","status":"accepted","created_at":"2026-04-10","updated_at":"2026-04-10"}],"plans":[{"id":"PLN-0007","file":"workflow/plans/PLN-0007-full-migration-to-atomic-telemetry.md","status":"done","created_at":"2026-04-10","updated_at":"2026-04-10"}],"lessons":[{"id":"LSN-0028","file":"lessons/DSC-0023-perf-full-migration-to-atomic-telemetry/LSN-0028-converging-to-single-atomic-telemetry-source.md","status":"done","created_at":"2026-04-10","updated_at":"2026-04-10"}]}
{"type":"discussion","id":"DSC-0020","status":"done","ticket":"jenkins-gitea-integration","title":"Jenkins Gitea Integration and Relocation","created_at":"2026-04-07","updated_at":"2026-04-07","tags":["ci","jenkins","gitea"],"agendas":[{"id":"AGD-0018","file":"workflow/agendas/AGD-0018-jenkins-gitea-integration-and-relocation.md","status":"done","created_at":"2026-04-07","updated_at":"2026-04-07"}],"decisions":[{"id":"DEC-0003","file":"workflow/decisions/DEC-0003-jenkins-gitea-strategy.md","status":"accepted","created_at":"2026-04-07","updated_at":"2026-04-07"}],"plans":[{"id":"PLN-0003","file":"workflow/plans/PLN-0003-jenkins-gitea-execution.md","status":"done","created_at":"2026-04-07","updated_at":"2026-04-07"}],"lessons":[{"id":"LSN-0021","file":"lessons/DSC-0020-jenkins-gitea-integration/LSN-0021-jenkins-gitea-integration.md","status":"done","created_at":"2026-04-07","updated_at":"2026-04-07"}]}
{"type":"discussion","id":"DSC-0021","status":"done","ticket":"asset-entry-codec-enum-with-metadata","title":"Asset Entry Codec Enum Contract","created_at":"2026-04-09","updated_at":"2026-04-09","tags":["asset","runtime","codec","metadata"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0024","file":"lessons/DSC-0021-asset-entry-codec-enum-contract/LSN-0024-string-on-the-wire-enum-in-runtime.md","status":"done","created_at":"2026-04-09","updated_at":"2026-04-09"}]}
@ -17,7 +17,7 @@
{"type":"discussion","id":"DSC-0012","status":"open","ticket":"perf-runtime-introspection-syscalls","title":"Agenda - [PERF] Runtime Introspection Syscalls","created_at":"2026-03-27","updated_at":"2026-03-27","tags":[],"agendas":[{"id":"AGD-0011","file":"workflow/agendas/AGD-0011-perf-runtime-introspection-syscalls.md","status":"open","created_at":"2026-03-27","updated_at":"2026-03-27"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0013","status":"done","ticket":"perf-host-debug-overlay-isolation","title":"Agenda - [PERF] Host Debug Overlay Isolation","created_at":"2026-03-27","updated_at":"2026-04-10","tags":[],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0027","file":"lessons/DSC-0013-perf-host-debug-overlay-isolation/LSN-0027-host-debug-overlay-isolation.md","status":"done","created_at":"2026-04-10","updated_at":"2026-04-10"}]}
{"type":"discussion","id":"DSC-0024","status":"done","ticket":"generic-memory-bank-slot-contract","title":"Agenda - Generic Memory Bank Slot Contract","created_at":"2026-04-10","updated_at":"2026-04-10","tags":["runtime","asset","memory-bank","slots","host"],"agendas":[],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0029","file":"lessons/DSC-0024-generic-memory-bank-slot-contract/LSN-0029-slot-first-bank-telemetry-belongs-in-asset-manager.md","status":"done","created_at":"2026-04-10","updated_at":"2026-04-10"}]}
{"type":"discussion","id":"DSC-0025","status":"open","ticket":"scene-bank-and-viewport-cache-refactor","title":"Agenda - Scene Bank and Viewport Cache Refactor","created_at":"2026-04-11","updated_at":"2026-04-13","tags":["gfx","tilemap","runtime","render"],"agendas":[{"id":"AGD-0025","file":"AGD-0025-scene-bank-and-viewport-cache-refactor.md","status":"accepted","created_at":"2026-04-11","updated_at":"2026-04-13"}],"decisions":[{"id":"DEC-0013","file":"DEC-0013-scene-bank-and-viewport-cache-model.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_agenda":"AGD-0025"}],"plans":[{"id":"PLN-0011","file":"PLN-0011-scene-core-types-and-bank-contract.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0012","file":"PLN-0012-scene-viewport-cache-structure.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0013","file":"PLN-0013-scene-viewport-resolver-and-rematerialization.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0014","file":"PLN-0014-renderer-migration-to-scene-viewport-cache.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0015","file":"PLN-0015-api-bank-integration-and-tests.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]}],"lessons":[]}
{"type":"discussion","id":"DSC-0025","status":"open","ticket":"scene-bank-and-viewport-cache-refactor","title":"Agenda - Scene Bank and Viewport Cache Refactor","created_at":"2026-04-11","updated_at":"2026-04-13","tags":["gfx","tilemap","runtime","render"],"agendas":[{"id":"AGD-0025","file":"AGD-0025-scene-bank-and-viewport-cache-refactor.md","status":"accepted","created_at":"2026-04-11","updated_at":"2026-04-13"}],"decisions":[{"id":"DEC-0013","file":"DEC-0013-scene-bank-and-viewport-cache-model.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_agenda":"AGD-0025"}],"plans":[{"id":"PLN-0011","file":"PLN-0011-scene-core-types-and-bank-contract.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0012","file":"PLN-0012-scene-viewport-cache-structure.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0013","file":"PLN-0013-scene-viewport-resolver-and-rematerialization.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0014","file":"PLN-0014-renderer-migration-to-scene-viewport-cache.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0015","file":"PLN-0015-api-bank-integration-and-tests.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]},{"id":"PLN-0016","file":"PLN-0016-scene-binary-payload-format-and-decoder.md","status":"accepted","created_at":"2026-04-13","updated_at":"2026-04-13","ref_decisions":["DEC-0013"]}],"lessons":[]}
{"type":"discussion","id":"DSC-0014","status":"open","ticket":"perf-vm-allocation-and-copy-pressure","title":"Agenda - [PERF] VM Allocation and Copy Pressure","created_at":"2026-03-27","updated_at":"2026-03-27","tags":[],"agendas":[{"id":"AGD-0013","file":"workflow/agendas/AGD-0013-perf-vm-allocation-and-copy-pressure.md","status":"open","created_at":"2026-03-27","updated_at":"2026-03-27"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0015","status":"open","ticket":"perf-cartridge-boot-and-program-ownership","title":"Agenda - [PERF] Cartridge Boot and Program Ownership","created_at":"2026-03-27","updated_at":"2026-03-27","tags":[],"agendas":[{"id":"AGD-0014","file":"workflow/agendas/AGD-0014-perf-cartridge-boot-and-program-ownership.md","status":"open","created_at":"2026-03-27","updated_at":"2026-03-27"}],"decisions":[],"plans":[],"lessons":[]}
{"type":"discussion","id":"DSC-0016","status":"done","ticket":"tilemap-empty-cell-vs-tile-id-zero","title":"Tilemap Empty Cell vs Tile ID Zero","created_at":"2026-03-27","updated_at":"2026-04-09","tags":[],"agendas":[{"id":"AGD-0015","file":"workflow/agendas/AGD-0015-tilemap-empty-cell-vs-tile-id-zero.md","status":"done","created_at":"2026-03-27","updated_at":"2026-04-09"}],"decisions":[],"plans":[],"lessons":[{"id":"LSN-0022","file":"lessons/DSC-0016-tilemap-empty-cell-semantics/LSN-0022-tilemap-empty-cell-convergence.md","status":"done","created_at":"2026-04-09","updated_at":"2026-04-09"}]}

View File

@ -10,11 +10,11 @@ tags: [gfx, tilemap, runtime, render]
## Objective
Implement the `SceneViewportCache` as the operational render cache for one `Scene`, including one internal ringbuffer per layer and lightweight derived cache entries for raster acceleration.
Implement the `SceneViewportCache` as the operational render cache for one `SceneBank`, including one internal ringbuffer per layer and lightweight derived cache entries for raster acceleration.
## Background
`DEC-0013` locks `SceneViewportCache` as the renderer-facing view of scene data and prefers internal ringbuffer storage per layer. This plan isolates the cache data structure and update API before resolver and renderer integration.
`DEC-0013` locks `SceneViewportCache` as the renderer-facing view of scene data and prefers internal ringbuffer storage per layer. `PLN-0011` already established the canonical source as `SceneBank` with exactly four `SceneLayer`s in a fixed array and moved per-layer movement metadata to `motion_factor`. This plan isolates the cache data structure and update API before resolver and renderer integration.
## Scope
@ -56,10 +56,10 @@ Create the internal data model for one viewport cache layer and for cached tile
### Step 2 - Define `SceneViewportCache` as a four-layer aggregate
**What:**
Create the top-level cache aggregate for one `Scene`.
Create the top-level cache aggregate for one `SceneBank`.
**How:**
- Represent one cache aggregate containing four internal layer caches.
- Represent one cache aggregate containing four internal layer caches aligned to `SceneBank.layers`.
- Thread through cache dimensions and tile-size assumptions for V1.
- Make the cache explicitly scene-derived and non-canonical.
@ -90,7 +90,7 @@ Define the update surface that later plans will use for rematerialization.
Add helpers that copy canonical scene data into cache entries.
**How:**
- Build helpers that read canonical `SceneLayer`/`TileMap` data and populate cache entries.
- Build helpers that read canonical `SceneBank` / `SceneLayer` / `TileMap` data and populate cache entries.
- Keep the helpers unaware of camera policy; they should only perform requested materialization work.
- Ensure per-layer movement factors remain metadata of the scene layer, not cache-only state.
@ -122,7 +122,7 @@ Protect the cache shape and update operations before wiring the resolver.
- Line/column/region refresh APIs only rewrite the requested area.
### Integration Tests
- Materialization from `Scene` into `SceneViewportCache` succeeds across all four layers.
- Materialization from `SceneBank` into `SceneViewportCache` succeeds across all four layers.
### Manual Verification
- Inspect debug output or temporary probes to confirm cache updates do not expose ringbuffer details outside the cache boundary.
@ -137,7 +137,7 @@ Protect the cache shape and update operations before wiring the resolver.
## Dependencies
- Depends on `PLN-0011` for canonical `Scene` / `SceneLayer` / `TileMap` types.
- Depends on `PLN-0011` for canonical `SceneBank` / `SceneLayer` / `TileMap` types and the fixed four-layer shape.
- Source decision: `DEC-0013`
## Risks

View File

@ -10,17 +10,17 @@ tags: [gfx, tilemap, runtime, render]
## Objective
Implement `SceneViewportResolver` as the owner of master totem, per-layer totems, drift, hysteresis, clamp, cache update decisions, and per-layer copy instrumentation metadata.
Implement `SceneViewportResolver` as the owner of master anchor, per-layer anchors, drift, hysteresis, clamp, cache update decisions, and per-layer copy instrumentation metadata.
## Background
`DEC-0013` makes the resolver the owner of movement policy between camera input and viewport cache updates. This plan isolates the decision logic before final renderer migration.
`DEC-0013` makes the resolver the owner of movement policy between camera input and viewport cache updates. `PLN-0011` already fixed the canonical source as `SceneBank` and renamed per-layer movement metadata to `motion_factor`. This plan isolates the decision logic before final renderer migration.
## Scope
### Included
- Define `SceneViewportResolver`.
- Implement master totem and per-layer derived totems.
- Implement master anchor and per-layer derived anchors.
- Implement drift and hysteresis.
- Implement clamp behavior.
- Implement cache-update triggering and copy instrumentation metadata.
@ -39,8 +39,8 @@ Create the resolver state model and its public input surface.
**How:**
- Define resolver state to own:
- master totem
- per-layer derived totems
- master anchor
- per-layer derived anchors
- viewport dimensions
- hysteresis thresholds
- clamp-relevant scene bounds
@ -52,10 +52,10 @@ Create the resolver state model and its public input surface.
### Step 2 - Implement master-to-layer totem derivation
**What:**
Make layer motion derive from the master totem using each layers `totem_factor`.
Make layer motion derive from the master anchor using each layers `motion_factor`.
**How:**
- Compute per-layer effective motion from the master totem.
- Compute per-layer effective motion from the master anchor.
- Preserve support for normal layers (`1.0`) and parallax/background-like layers (`!= 1.0`).
- Keep the derivation explicit and testable per axis.
@ -66,10 +66,10 @@ Make layer motion derive from the master totem using each layers `totem_facto
### Step 3 - Implement drift, hysteresis, and clamp
**What:**
Translate camera motion into discrete totem advancement safely.
Translate camera motion into discrete anchor advancement safely.
**How:**
- Implement drift calculation in pixel space against totem centers in tile space.
- Implement drift calculation in pixel space against anchor centers in tile space.
- Implement hysteresis with:
- internal safe band
- external trigger band
@ -117,8 +117,8 @@ Protect resolver correctness before renderer integration.
**How:**
- Add tests for:
- master totem updates
- per-layer totem factor derivation
- master anchor updates
- per-layer motion-factor derivation
- hysteresis stability
- repeated high-speed movement
- clamp at scene edges
@ -131,8 +131,8 @@ Protect resolver correctness before renderer integration.
### Unit Tests
- Hysteresis prevents edge flick/thrash.
- Totem movement occurs discretely in tile steps.
- Per-layer totems follow the master according to `totem_factor`.
- Anchor movement occurs discretely in tile steps.
- Per-layer anchors follow the master according to `motion_factor`.
- Clamp behavior is correct near scene edges.
### Integration Tests
@ -144,7 +144,7 @@ Protect resolver correctness before renderer integration.
## Acceptance Criteria
- [ ] `SceneViewportResolver` exists with the full state required by `DEC-0013`.
- [ ] Master and per-layer totems are derived correctly.
- [ ] Master and per-layer anchors are derived correctly.
- [ ] Hysteresis and clamp are implemented and tested.
- [ ] Cache refresh requests are emitted by line, column, and region as required.
- [ ] Copy instrumentation metadata is available for later renderer use.

View File

@ -10,11 +10,11 @@ tags: [gfx, tilemap, runtime, render]
## Objective
Migrate world rendering from direct canonical map consumption to `SceneViewportCache` consumption while preserving the accepted observable composition order.
Migrate world rendering from direct canonical `SceneBank` consumption to `SceneViewportCache` consumption while preserving the accepted observable composition order.
## Background
`DEC-0013` makes `SceneViewportCache` the immediate source of copy data for world blits and preserves the visible order of world layers, interleaved sprites, and HUD. This plan focuses on the renderer migration itself.
`DEC-0013` makes `SceneViewportCache` the immediate source of copy data for world blits and preserves the visible order of world layers, interleaved sprites, and HUD. `PLN-0011` already removed the old canonical `TileLayer` / `ScrollableTileLayer` model and cleaned the bridge surface accordingly. This plan focuses on the renderer migration itself.
## Scope
@ -35,10 +35,10 @@ Migrate world rendering from direct canonical map consumption to `SceneViewportC
### Step 1 - Identify and isolate direct canonical map consumption in the renderer
**What:**
Locate current renderer paths that read canonical layer maps directly.
Locate current renderer paths that read canonical scene/layer maps directly.
**How:**
- Replace direct `TileMap` reads in [crates/console/prometeu-drivers/src/gfx.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/gfx.rs) with abstraction points prepared to accept cache-sourced copy requests.
- Replace any remaining direct `SceneBank` / `SceneLayer` / `TileMap` reads in [crates/console/prometeu-drivers/src/gfx.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/gfx.rs) with abstraction points prepared to accept cache-sourced copy requests.
- Keep the migration incremental enough to preserve buildability.
**File(s):**
@ -124,7 +124,7 @@ Protect the migrated composition order and world rendering behavior.
## Acceptance Criteria
- [ ] Renderer world composition no longer reads canonical scene maps directly in the hot path.
- [ ] Renderer world composition no longer reads canonical `SceneBank` data directly in the hot path.
- [ ] World layers are copied from `SceneViewportCache`.
- [ ] Sprite interleaving and HUD ordering remain correct.
- [ ] V1 destructive composition still works end-to-end.

View File

@ -10,17 +10,16 @@ tags: [gfx, tilemap, runtime, render]
## Objective
Finish the scene/viewport-cache migration by aligning exposed APIs, bank-loading integration, and test coverage across HAL, drivers, and system entry points.
Finish the scene/viewport-cache migration by aligning exposed APIs, final integration surfaces, and test coverage across HAL, drivers, and system entry points.
## Background
After core types, cache, resolver, and renderer migration exist, the remaining work is to align the surrounding surfaces so the new architecture is usable as the runtimes operational model.
After core types, cache, resolver, and renderer migration exist, the remaining work is to align the surrounding surfaces so the new architecture is usable as the runtimes operational model. `PLN-0011` already removed the old canonical tile-layer APIs and introduced `BankType::SCENE` plus scene-aware bank slots. The binary `SCENE` payload contract and decoder are now isolated in `PLN-0016`.
## Scope
### Included
- Update bridge APIs and exposed runtime surfaces.
- Align bank-loading/integration paths with scene-backed content.
- Remove stale tile-layer-era interfaces.
- Add cross-layer regression coverage.
@ -36,7 +35,7 @@ After core types, cache, resolver, and renderer migration exist, the remaining w
Remove or replace public APIs still shaped around the old scrollable tile-layer model.
**How:**
- Update `GfxBridge` and adjacent bridge traits so they no longer expose obsolete canonical layer ownership assumptions.
- Verify `GfxBridge` and adjacent bridge traits stay free of obsolete canonical layer ownership assumptions after cache/resolver integration.
- Introduce scene/cache/resolver-oriented access only where required by runtime consumers.
**File(s):**
@ -50,43 +49,29 @@ Ensure hardware and driver initialization paths can construct and own the new sc
**How:**
- Update hardware bootstrap and driver ownership paths to instantiate the canonical scene and viewport-cache stack.
- Remove any remaining ownership assumptions tied to `ScrollableTileLayer`.
- Remove any remaining ownership assumptions tied to the pre-`SceneBank` model.
**File(s):**
- [crates/console/prometeu-drivers/src/hardware.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/hardware.rs)
- [crates/console/prometeu-drivers/src/gfx.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/gfx.rs)
### Step 3 - Align asset/bank integration paths
**What:**
Make sure bank-loading and asset integration paths understand the scene-backed model at the operational layer.
**How:**
- Update asset-side or loader-side integration points so scene-backed content can be staged, installed, and referenced coherently.
- Keep the work scoped to the bank-loading path; do not reopen the canonical model here.
**File(s):**
- [crates/console/prometeu-drivers/src/asset.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/asset.rs)
- [crates/console/prometeu-drivers/src/memory_banks.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/memory_banks.rs)
- [crates/console/prometeu-hal/src/cartridge_loader.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-hal/src/cartridge_loader.rs)
- Related asset/bank shared types
### Step 4 - Remove stale type and API remnants
### Step 3 - Remove stale type and API remnants
**What:**
Clean out old interfaces that would leave the codebase in a dual-model state.
**How:**
- Remove obsolete references to:
- Remove any remaining obsolete references to:
- `TileLayer`
- `ScrollableTileLayer`
- direct old-layer scroll ownership APIs
- transitional commented fallback paths left during migration
- Keep only the canonical scene model and the viewport-cache/render pipeline required by the decision.
**File(s):**
- HAL and driver modules touched by earlier plans
### Step 5 - Add full-stack regression coverage
### Step 4 - Add full-stack regression coverage
**What:**
Add the minimum test family needed to execute the migration safely one plan at a time.
@ -125,17 +110,15 @@ Add the minimum test family needed to execute the migration safely one plan at a
- [ ] Bridge and runtime-facing APIs align with the new scene/cache model.
- [ ] Hardware/driver construction paths instantiate the new architecture correctly.
- [ ] Asset/bank integration paths accept the scene-backed model.
- [ ] Stale old-layer APIs are removed.
- [ ] Full-stack regression coverage exists for the migration.
## Dependencies
- Depends on `PLN-0011`, `PLN-0012`, `PLN-0013`, and `PLN-0014`.
- Depends on `PLN-0011`, `PLN-0012`, `PLN-0013`, `PLN-0014`, and `PLN-0016`.
- Source decision: `DEC-0013`
## Risks
- API cleanup is where hidden dependencies on the old model are most likely to surface.
- Asset/bank integration can expand in scope if loader assumptions are too tightly coupled to current bank enums.
- If stale APIs are not removed aggressively, the codebase can get stuck in a fragile dual-model transition.

View File

@ -0,0 +1,164 @@
---
id: PLN-0016
ticket: scene-bank-and-viewport-cache-refactor
title: Plan - Scene Binary Payload Format and Decoder
status: accepted
created: 2026-04-13
completed:
tags: [asset, runtime, scene, codec, binary-format]
---
## Objective
Define the canonical binary payload contract for `SCENE` assets and implement the runtime decoder needed to load `SceneBank` content without JSON-based scene payloads.
## Background
`DEC-0013` established `SceneBank` as the canonical loaded scene aggregate. `PLN-0011` introduced `BankType::SCENE` and the scene-aware bank slot model, but intentionally left `SCENE` payload decoding open. A temporary `todo!()` now blocks scene payload materialization in the asset manager until the binary contract is closed. This plan isolates that format and decoder work before the final integration pass.
## Scope
### Included
- Define the binary on-disk/on-wire payload format for `SCENE`.
- Define the minimum metadata contract needed in `AssetEntry` for `SCENE`.
- Implement the runtime decoder from payload bytes into `SceneBank`.
- Add format and decode tests for valid and invalid scene payloads.
- Re-enable scene asset load/preload coverage once the decoder exists.
### Excluded
- `SceneViewportCache`
- `SceneViewportResolver`
- renderer migration
- cartridge authoring tooling beyond what is strictly needed to encode test fixtures
- reopening canonical scene/runtime type design
## Execution Steps
### Step 1 - Define the binary `SCENE` payload contract
**What:**
Close the binary layout for serialized `SceneBank` assets.
**How:**
- Define a versioned binary format with:
- file/payload prelude or version marker
- fixed four-layer scene layout
- per-layer metadata block
- per-layer tilemap dimensions
- serialized tile records
- Keep the format aligned with the canonical runtime shape from `PLN-0011`:
- `SceneBank`
- `[SceneLayer; 4]`
- `motion_factor`
- `TileMap`
- `Tile`
- Document field sizes, endianness, ordering, and validation rules.
**File(s):**
- [crates/console/prometeu-hal/src/asset.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-hal/src/asset.rs)
- [crates/console/prometeu-hal/src/cartridge_loader.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-hal/src/cartridge_loader.rs)
- Additional shared asset-format module(s) if needed
### Step 2 - Define `SCENE` metadata requirements in `AssetEntry`
**What:**
Decide what belongs in `AssetEntry.metadata` versus the binary payload itself.
**How:**
- Keep metadata minimal and stable.
- Add only fields that materially help validation or loader routing.
- Avoid duplicating large structural scene information in both metadata and payload.
- Add typed metadata helpers in HAL if required for scene assets.
**File(s):**
- [crates/console/prometeu-hal/src/asset.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-hal/src/asset.rs)
### Step 3 - Implement the runtime `SCENE` decoder
**What:**
Replace the current `todo!()` loader path with a real binary decoder.
**How:**
- Implement `perform_load_scene_bank(...)` using the accepted binary contract.
- Decode from slice/reader into canonical runtime objects:
- `SceneBank`
- `SceneLayer`
- `TileMap`
- `Tile`
- Add explicit validation for:
- invalid version
- short payload
- invalid tile-size values
- layer count mismatch
- tile count mismatch
- numeric overflow / malformed dimensions
- Keep decode logic self-contained and free of viewport/cache behavior.
**File(s):**
- [crates/console/prometeu-drivers/src/asset.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/asset.rs)
- Supporting HAL/shared modules if decoder helpers are factored out
### Step 4 - Re-enable scene asset loading paths and tests
**What:**
Turn scene asset loading back on in the asset manager and restore coverage.
**How:**
- Re-enable the `SCENE` load/preload path currently blocked by the `todo!()`.
- Add tests for:
- scene payload decode success
- scene asset load
- scene preload on initialization
- malformed scene payload rejection
- Ensure glyph/sound behavior remains unchanged.
**File(s):**
- [crates/console/prometeu-drivers/src/asset.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-drivers/src/asset.rs)
### Step 5 - Confirm cartridge-loader and asset-table compatibility
**What:**
Ensure the broader cartridge/asset pipeline accepts the finalized `SCENE` contract cleanly.
**How:**
- Verify `AssetEntry` and cartridge-loading paths accept the new scene metadata contract.
- Add targeted tests for asset-table parsing or preload validation if needed.
- Keep this step scoped to compatibility with the finalized binary scene payload, not new tooling features.
**File(s):**
- [crates/console/prometeu-hal/src/cartridge_loader.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-hal/src/cartridge_loader.rs)
- [crates/console/prometeu-hal/src/asset.rs](/Users/niltonconstantino/personal/workspace.personal/intrepid/prometeu/runtime/crates/console/prometeu-hal/src/asset.rs)
## Test Requirements
### Unit Tests
- Valid binary scene payloads decode into the expected `SceneBank`.
- Invalid payloads fail with explicit decoder errors.
- Per-layer metadata and tile contents survive round-trip fixture decode.
### Integration Tests
- `SCENE` assets can be loaded and preloaded through `AssetManager`.
- Scene bank slot installation works without breaking glyph/sound behavior.
### Manual Verification
- Inspect one representative binary scene fixture and confirm the decoded `SceneBank` matches the expected four-layer canonical shape.
## Acceptance Criteria
- [ ] The binary `SCENE` payload format is explicitly defined and versioned.
- [ ] `AssetEntry` requirements for `SCENE` are documented and implemented.
- [ ] `perform_load_scene_bank(...)` is implemented without JSON payload parsing.
- [ ] Scene load/preload tests pass against the finalized binary decoder.
- [ ] Glyph and sound asset paths remain unaffected.
## Dependencies
- Depends on `PLN-0011`.
- Should complete before the final integration/cleanup pass in `PLN-0015`.
- Source decision: `DEC-0013`
## Risks
- Overloading `AssetEntry.metadata` can duplicate scene structure and make the contract brittle.
- A weak binary format definition can create hidden compatibility problems for future scene growth.
- Decoder validation gaps can surface later as corrupted scene state instead of explicit asset-load failures.