docs: wayfinder-map fuer rustkeep 1.0 anlegen

This commit is contained in:
2026-08-11 15:13:49 +02:00
parent 290d985bc6
commit 8ad5da82c1
11 changed files with 286 additions and 0 deletions

View File

@@ -0,0 +1,21 @@
# 01 — Effekt-Vokabular
Type: grilling
Status: open
Blocked by: —
## Question
Was kann ein Effekt ausdrücken, und wie sieht er in TOML aus?
Das Effekt-Vokabular ist die Mod-API: ein Modder kann exakt das bauen, was hier definiert wird.
Zu klären:
- Welche Wirkungen gibt es? Stat-Modifikator (flach, prozentual), Sofortschaden/Heilung,
Ressourcenverbrauch, Statuseffekt anwenden/entfernen, Event auslösen.
- Zeitlichkeit: permanent (Rasse), solange ausgerüstet (Item), N Runden (Statuseffekt), einmalig (Trank).
- Wie werden Effekte gestapelt und in welcher Reihenfolge verrechnet? Erst flach, dann prozentual?
- Wie referenziert ein Effekt sein Ziel — Träger, Gegner, alle Gegner?
- Wie sieht die TOML-Repräsentation aus, und bleibt sie lesbar genug für Modder ohne Doku?
Ergebnis: eine Liste der Effekt-Varianten mit TOML-Beispiel je Variante.

View File

@@ -0,0 +1,21 @@
# 02 — Typ-Registry statt Enums
Type: grilling
Status: open
Blocked by: 01
## Question
Wie werden Item-Typen, Rassen und Klassen zu Daten statt zu Rust-Enums?
`enum ItemType` kann ein Modder nicht erweitern — es muss eine Registry aus String-IDs werden.
Zu klären:
- Was deklariert ein Typ? Ausrüstungsslot, welche Felder Pflicht sind, welche Effekte er tragen darf.
- Gibt es Slots als eigene Registry (`core:helmet`), oder ist der Slot ein fester Aufzählungswert?
- Wie prüft das Spiel beim Laden, dass ein Item einen existierenden Typ nennt — und was passiert, wenn nicht?
- Wie unterscheiden sich Rasse und Klasse strukturell, oder sind beide dasselbe: eine benannte Effektliste
plus Metadaten?
- Was verliert man ohne Enum an Compile-Zeit-Sicherheit, und was fängt das ab (Validierung beim Laden)?
Ergebnis: das Registry-Datenmodell plus TOML-Beispiel für einen selbstdefinierten Item-Typ.

View File

@@ -0,0 +1,20 @@
# 03 — Mod-Ladepipeline und Manifest
Type: grilling
Status: open
Blocked by: 02
## Question
Wie findet, ordnet und lädt das Spiel Mods — inklusive sich selbst?
Das Kernspiel ist `core:` und damit selbst ein Mod. Zu klären:
- Ordnerstruktur: Wo liegt `core`, wo liegen fremde Mods, was ist relativ zur Binary vs. zum Benutzerprofil?
- Manifest: Welche Felder? ID-Namespace, Anzeigename, Version, Abhängigkeiten, Ladepriorität.
- Ladereihenfolge: aus Abhängigkeiten berechnet oder vom Spieler festgelegt? Wie werden Zyklen behandelt?
- Überschreiben: Wie sagt Mod B, dass er `core:iron_sword` ersetzt statt ergänzt? Ganz oder feldweise?
- In welchen Phasen läuft das Laden — erst alle Typen, dann alle Instanzen? Was passiert bei Vorwärtsreferenzen?
- Wird beim Start alles geladen, oder gibt es ein Nachladen zur Laufzeit?
Ergebnis: Ordnerlayout, Manifest-Schema und die Phasen der Ladepipeline.

View File

@@ -0,0 +1,23 @@
# 04 — Fehlerstrategie für kaputte Mods
Type: grilling
Status: open
Blocked by: 03
## Question
Was passiert, wenn ein Mod kaputt ist — und wie sieht das im Rust-Code aus?
Explizites Rust-Lernticket. Heute macht `items.rs::parse()` ein `panic!` mit Backtrace; bei Mod-Support
ist fehlerhaftes TOML der Normalfall, nicht der Ausnahmefall. Zu klären:
- Welche Fehlerklassen gibt es? TOML-Syntax kaputt, Pflichtfeld fehlt, unbekannte Typ-ID,
Abhängigkeit nicht installiert, ID-Kollision ohne Override-Absicht.
- Welche davon sind hart (Start abbrechen) und welche weich (Mod überspringen, Rest laden, warnen)?
- Wie erreicht die Meldung den Spieler — vor dem TUI-Start auf stderr, oder als Bildschirm im TUI?
Braucht es ein Mod-Log?
- Rust-seitig: eigener Fehlertyp mit `thiserror`, oder `anyhow` mit Kontext, oder handgeschriebenes
`enum LoadError`? Wo endet die `Result`-Kette?
- Wie kommt die Herkunft in die Meldung — Datei, Zeile, Mod-ID?
Ergebnis: Fehlerklassifikation, Reaktion je Klasse, und die gewählte Rust-Fehlerbehandlung mit Begründung.

View File

@@ -0,0 +1,21 @@
# 05 — Research: Script-Engine für Mod-Stufe (c)
Type: research
Status: open
Blocked by: —
## Question
Welche Script-Engine trägt modderseitiges Verhalten in rustkeep — Rhai, Lua via `mlua`, oder WASM?
Fakten sammeln, keine Entscheidung treffen. Zu klären:
- Einbindung: Braucht es eine C-Toolchain unter Windows? Wie groß ist der Build-Overhead?
- Typ-Brücke: Wie schmerzhaft ist es, Rust-Structs (Stats, Item, Game-State) für Scripts zugänglich zu machen?
- Sandbox: Kann ein bösartiges Mod-Script Dateien lesen oder Prozesse starten? Was lässt sich abschalten?
- Fehlerbehandlung: Bekommt man brauchbare Fehlermeldungen mit Zeilennummer aus dem Script zurück?
- Hot-Reload: Lassen sich Scripts zur Laufzeit neu laden?
- Zielgruppe: Wie viele Hobby-Modder kennen die Sprache schon? Lua hat Vorsprung, Rhai ist Rust-nativ.
- Reifegrad: Wartungsstand, Release-Frequenz, Größe des Ökosystems, Beispiele aus echten Spielen.
Ergebnis: Vergleichstabelle plus Empfehlung mit Begründung; die Entscheidung fällt der Mensch später.

View File

@@ -0,0 +1,24 @@
# 06 — Research: ratatui-App-Architektur
Type: research
Status: open
Blocked by: —
## Question
Wie strukturiert man eine ratatui-Anwendung mit mehreren Bildschirmen sauber?
rustkeep braucht Grid-Ansicht, Kampfbildschirm, Inventar, Shop, Questlog, Charakterbogen, Hauptmenü.
Fakten sammeln. Zu klären:
- Welches App-Muster ist etabliert — Elm-artig (Message/Update/View), Screen-Stack, State-Machine?
Was empfiehlt ratatui selbst, was machen echte Projekte?
- Wie werden Bildschirme gestapelt, wenn ein Popup über dem Kampf liegt?
- Wie trennt man Spiellogik von Rendering, damit der Kern ohne Terminal testbar bleibt?
- Event-Loop: Wie läuft Eingabe gegen Rendering, braucht ein rundenbasiertes Spiel überhaupt einen Tick?
- Welche Widgets bringt ratatui mit (Liste, Tabelle, Gauge, Popup), und was muss man selbst bauen —
insbesondere ein Dungeon-Grid?
- Terminal-Aufräumen bei Panic, damit kein kaputtes Terminal zurückbleibt.
- Stand der Versionen: aktuelle ratatui- und crossterm-Version, bekannte Fallstricke unter Windows.
Ergebnis: empfohlenes App-Muster mit Skizze der Modulstruktur, plus Quellenliste.

View File

@@ -0,0 +1,21 @@
# 07 — Game-State-Baum
Type: grilling
Status: open
Blocked by: 01, 02
## Question
Wie sieht der Weltzustand als Rust-Datenstruktur aus?
Entschieden ist: ein `Game`-Ownership-Baum mit Verweisen über IDs oder Indizes, kein ECS. Zu klären:
- Was besitzt was? Wo leben Held, aktuelle Etage, Räume, Gegner, Bodenloot, Questfortschritt?
- Trennung von unveränderlichen Definitionen (aus Mods geladen) und veränderlichem Laufzeitzustand:
zwei getrennte Strukturen, oder eine mit Verweisen in den Katalog?
- Referenzform: `String`-ID überall, oder beim Laden zu `usize`-Index auflösen? Was kostet das beim Speichern?
- Wo werden aktive Statuseffekte gehalten — am Träger oder in einer zentralen Liste?
- Welche Operation kämpft absehbar mit dem Borrow-Checker (Gegner greift Held an, während beide im selben
`Game` hängen), und wie wird das aufgelöst?
Ergebnis: Skizze der Structs mit Besitzverhältnissen und Referenzform.

View File

@@ -0,0 +1,23 @@
# 08 — Event- und Trigger-System
Type: grilling
Status: open
Blocked by: 07
## Question
Welche Ereignisse meldet das Spiel, und wie hängen Quests und Effekte daran?
Quests sind Bedingung plus Belohnung als Daten; Script-Mods hängen sich später an dieselben Events.
Zu klären:
- Welche Events gibt es, und welche Daten trägt jedes? `enemy_killed`, `item_picked_up`, `floor_entered`,
`npc_talked`, `turn_started`, `damage_taken`, `player_died`.
- Wie werden Events benannt und für Modder erweiterbar gemacht — feste Liste oder auch namespaced IDs?
- Bedingungen: reines Zählen (töte 5 Ratten) oder auch Zustandsabfragen (habe 100 Gold, Level ≥ 3)?
Braucht es Verknüpfung mit UND/ODER?
- Wie wird ein Questfortschritt gespeichert und wie überlebt er das Deaktivieren des Quest-Mods?
- Reihenfolge und Rekursion: Was passiert, wenn eine Belohnung selbst ein Event auslöst?
- Ist das synchrone Aufrufe (Handler direkt ausführen) oder eine Warteschlange?
Ergebnis: Eventliste mit Nutzlast, Bedingungs-Grammatik, TOML-Beispiel für eine Quest.

View File

@@ -0,0 +1,23 @@
# 09 — Save-Schema
Type: grilling
Status: open
Blocked by: 07
## Question
Was steht in einem Speicherstand, und wie überlebt er geänderte Mods?
Entschieden ist: TOML, Mod-Liste im Header, fehlender Mod bedeutet Warnung und Verwerfen statt Abbruch.
Zu klären:
- Was genau wird gespeichert? Held mit Stats und Effekten, Inventar, Ausrüstung, aktuelle Etage,
Etagen-Layout (oder Seed?), erkundete Räume, Gegnerzustand, Questfortschritt, Gold.
- Etage: gesamtes Layout speichern oder nur den Generator-Seed? Seed ist kompakt, bricht aber, sobald
der Generator oder ein Prefab-Mod sich ändert.
- Versionierung: Was steht im Header — Spielversion, Save-Schema-Version, Liste aus Mod-ID und Version?
- Migration: Was passiert bei älterem Schema? Migrieren, ablehnen, oder Best-Effort-Laden?
- Verwerfen im Detail: Wenn ein Item fehlt, wird der Slot leer — was, wenn die *Klasse* des Helden fehlt?
- Wie viele Speicherstände, Autosave, und speichert man mitten im Kampf?
Ergebnis: Save-Schema als kommentiertes TOML-Beispiel plus Regeln für fehlende Mods.

View File

@@ -0,0 +1,22 @@
# 10 — Raum-Prefab-Format
Type: grilling
Status: open
Blocked by: 03
## Question
Wie sieht ein Raum-Prefab in TOML aus, und wie fügt der Generator daraus eine Etage zusammen?
Entschieden ist der Hybrid: Modder bauen Prefabs, der Generator setzt prozedural zusammen. Zu klären:
- Prefab-Inhalt: Grid als ASCII-Block oder als Koordinatenliste? Wie werden Ausgänge markiert?
Wie Spawn-Punkte für Gegner, Loot, NPCs, Treppen?
- Wie flexibel ist die Größe — feste Raster oder beliebige Rechtecke, Rotation und Spiegelung erlaubt?
- Verbindungsregeln: Wie weiß der Generator, welche Prefabs aneinanderpassen? Tags an den Ausgängen?
- Steuerung durch Daten: Welche Prefabs auf welcher Etage, mit welcher Gewichtung? Pflichträume
(Eingang, Treppe, Boss) versus optionale?
- Garantien: Wie wird sichergestellt, dass die Treppe erreichbar ist?
- Wie greift ein Mod ein — nur neue Prefabs hinzufügen, oder auch Generator-Parameter ändern?
Ergebnis: Prefab-Schema mit Beispiel plus die Regeln, nach denen der Generator zusammensetzt.

View File

@@ -0,0 +1,67 @@
# Map: rustkeep 1.0
Gitea-Spiegel: [Issue #1](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/1).
Diese Datei ist die kanonische Quelle — bei Abweichung gilt `.scratch/`.
Gitea hat keine nativen Parent-Child- oder Blocking-Beziehungen, deshalb steht beides
dort als Konvention im Body. Zuordnung Ticket → Gitea-Issue:
| Ticket | Gitea | Ticket | Gitea |
|---|---|---|---|
| 01 Effekt-Vokabular | [#2](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/2) | 06 Research ratatui | [#7](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/7) |
| 02 Typ-Registry | [#3](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/3) | 07 Game-State-Baum | [#8](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/8) |
| 03 Mod-Ladepipeline | [#4](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/4) | 08 Event-System | [#9](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/9) |
| 04 Fehlerstrategie | [#5](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/5) | 09 Save-Schema | [#10](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/10) |
| 05 Research Script-Engine | [#6](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/6) | 10 Raum-Prefab-Format | [#11](https://gitlab.hive-brain.de/MDietermann/rustkeep/issues/11) |
## Destination
Alle Architektur- und Design-Entscheidungen für rustkeep 1.0 sind getroffen — nicht gebaut, entschieden.
1.0 heißt: 5 Etagen mit Boss, Solo-Held mit Rasse und Klasse, Grid-Erkundung mit Menü-Kampf,
Inventar und Ausrüstung, Quests, NPCs, Handel, Speichern/Laden, Mod-Support auf drei Stufen.
## Notes
Domain: Rust-Terminal-Roguelike, moddbar. Repo: `MDietermann/rustkeep`.
Jede Session konsultiert: `ponytail` (dauerhaft aktiv), `/grilling` und `/domain-modeling` für
Grilling-Tickets, `/research` für Research-Tickets, `/prototype` für Prototype-Tickets.
Feststehende Rahmenentscheidungen aus der Charter-Session:
| Thema | Entscheidung |
|---|---|
| Motivation | Rust lernen **und** Spiel bauen — Lern-Entscheidungen bekommen eigene Tickets, wo sie echte Architekturfragen sind |
| Kernschleife | Grid-Bewegung zum Erkunden, Kampf im Menü (Dungeon Master / Etrian Odyssey) |
| Held | Solo, kein Party-System |
| Rendering | ratatui + crossterm; `print_box` fliegt raus, sobald ratatui steht |
| Etagen | Hybrid — Raum-Prefabs in TOML, prozedural zusammengesetzt |
| Daten | Alles TOML, zur Laufzeit geladen. `include_str!` und `enum ItemType` fallen |
| Mod-IDs | Namespaced (`core:iron_sword`), Ladereihenfolge aus Mod-Manifest. Das Kernspiel ist selbst ein Mod |
| Mod-Stufen | Daten → Typen → Scripting, in dieser Reihenfolge. Scripting setzt auf der Typ-Registry auf |
| Effekte | Ein generisches Effekt-System mit Wirkung auf Stats. Rasse, Klasse, Items, Statuseffekte, Quest-Belohnungen und später Scripts nutzen dasselbe Vokabular — dieses Vokabular *ist* die Mod-API |
| Quests | Bedingung + Belohnung als Daten, generisches Event-/Trigger-System |
| Weltzustand | `Game`-Ownership-Baum, Verweise über IDs/Indizes. Kein ECS |
| Fehler | `Result` statt `panic!` — kaputte Mod-TOMLs sind der Normalfall, nicht der Ausnahmefall |
| Save | TOML, Mod-Liste im Header, fehlender Mod = Warnung und Verwerfen, kein harter Abbruch |
## Decisions so far
<!-- eine Zeile pro geschlossenem Ticket -->
## Not yet specified
- **Kampfmechanik im Detail** — Initiative, Aktionen pro Runde, Trefferformel, Krit, Flucht. Wartet auf das Effekt-Vokabular (01), weil Angriffe und Fähigkeiten Effekte sind.
- **Loot-Tabellen** — wie Drops definiert und gewichtet werden, wie `luck` einwirkt. Wartet auf die Typ-Registry (02).
- **XP-Kurve und Progression** — was Level-ups geben, wie Rasse/Klasse mitskalieren. Wartet auf 01.
- **Boss-Design** — ob Bosse nur Gegner mit besseren Werten sind oder eigene Mechanik brauchen (Phasen, Skripte). Berührt Stufe (c) des Mod-Supports.
- **NPC- und Handelsmodell** — Warenbestand, Preisbildung über `charisma`, Dialogdaten. Wartet auf das Event-System (08).
- **Inventar-UX** — Slots, Gewicht oder Kapazität, Sortierung, Vergleichsansicht. Wartet auf die ratatui-Architektur (06).
- **Mod-Verteilung** — wie Spieler an Mods kommen und ob es eine Versionsprüfung gibt. Wartet auf das Manifest-Format (03).
## Out of scope
- **Story-Modul** — kommt später als eigenes Modul, linear statt prozedural, ebenfalls moddbar. Eigene Map, wenn 1.0 steht.
- **Party-System** — bewusst gegen Solo entschieden; ein Wechsel wäre ein Umbau der Kampfarchitektur, keine Erweiterung.
- **Multiplayer**
- **Grafik jenseits des Terminals**