reikhelm/.dev/2026-05-28-procgen-map-core/README.md
Parley Hatch 08e99e38a3 chore: scaffold reikhelm cargo workspace (core + viz crates)
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-05-28 20:56:24 -06:00

32 lines
3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# reikhelm — Procedural 2D Map Generator: Implementation Plan
**Goal:** Build a Rust Cargo workspace whose pure `reikhelm-core` library generates deterministic 2D dungeon maps from composable passes, with a `reikhelm-viz` macroquad binary that renders them interactively.
**Architecture:** `reikhelm-core` is a pure library (no rendering deps) layered as geometry → `Grid<T>` → semantic regions + connectivity graph → a `GenContext`/`Pass`/`Pipeline` engine → a vocabulary of passes (Partitioner / Shaper / Connector / Placer) → a `dungeon` recipe. The engine owns per-pass RNG forking so editing the pipeline never reshuffles an existing seed. The library's sole output is a plain-data `Map`; `reikhelm-viz` consumes a `Map` and paints it — it contains no generation logic. The dependency direction is enforced: `viz → core`, never the reverse.
**Tech Stack:** Rust (Cargo workspace), `rand` + `rand_chacha` (ChaCha8 deterministic RNG), `serde` (derive on `Map`), `macroquad` (viz renderer).
**Spec:** [`spec/design.md`](spec/design.md)
## v1 Scope
Ship a dungeon recipe end-to-end (BSP → rooms → MST-connect → corridors → doors), an ASCII debug renderer, and an interactive macroquad window with seed reroll. Towns, caves, additional tiles/decorators, sprite rendering, and serialization tooling are designed-for but explicitly deferred (spec §11).
## Inter-Pass Data Contract (read before any pass task)
Passes never call each other; they communicate only through `GenContext` fields. The v1 dungeon contract:
| Pass | Reads | Writes |
|------|-------|--------|
| `BspPartition` | (empty grid) | `ctx.regions`: one placeholder `Region { kind: Room, bounds: <leaf rect>, cells: [] }` per BSP leaf |
| `RoomCarver` | `ctx.regions` (placeholder Rooms) | carves `Floor` into `ctx.tiles`; shrinks each Room's `bounds` to its actual room rect and fills `cells` |
| `MstConnect` | `ctx.regions` (kind=Room, non-empty `cells`) centers | `ctx.graph`: edges `{ a, b, at: None }` forming an MST over rooms + a few extra loop edges |
| `CorridorCarver` | `ctx.graph` edges + Room region bounds/centers | carves L-shaped `Floor` corridors into `ctx.tiles`; appends `Region { kind: Corridor, .. }` per corridor |
| `DoorPlacer` | `ctx.tiles` + `ctx.regions` + `ctx.graph` | converts boundary `Wall` cells (room↔corridor) to `Door`; sets the corresponding `edge.at = Some(point)` |
This is the integration contract. Each pass is unit-tested by constructing a `GenContext` in its required input state, so all five passes are implementable in parallel against this table.
## Shared Wiring Files (parallel-edit note)
- `reikhelm-core/src/lib.rs` — each module-creating task appends its own `pub mod <name>;`. These tasks are mostly sequential, so appends don't conflict.
- `reikhelm-core/src/passes/mod.rs` — created empty (with the contract doc comment) by Task 6; each pass task (711) appends one `pub mod <name>;` + `pub use`. The pass tasks run in parallel, so the orchestrator merges these append-only lines at integration.