11 — UI-Geruest und Screen-Modell #12
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Teil der Map #1 · Type:
wayfinder:grilling· Blocked by: — · graduiert aus #7Wie sieht das konkrete Screen-Modell aus, das auf der Empfehlung aus #7 aufsetzt? Ein Stack oder zwei (Screens + Popups)? Wo lebt der ListState? Nur
KeyEventKind::Pressoder auchRepeat? Bleibtgame/ratatui-frei?Volle Fragestellung (kanonisch):
.scratch/rustkeep-1.0/issues/11-ui-geruest-screen-modell.mdAufgeloest in
2c19cb2. Kanonische Fassung:.scratch/rustkeep-1.0/issues/11-ui-geruest-screen-modell.md"Aktion" hiess zwei verschiedene Dinge
Der Bericht aus #7 empfahl "einen Eintrittspunkt
Game::apply(Action)" — #8 hatGame::applyaber fuer die Aktionen aus #2 vergeben. "Geh nach Norden" ist keine der sieben Aktionen und wird nie eine.Game::apply(action, source, target, reg)Game::execute(cmd, reg)Game::executeist die eine Stelle, an der ein Zug endet: Zaehler hoch, Modifikatoren ticken,turn_startedfeuern, Event-Warteschlange aus #9 leerarbeiten. Zwoelf Einzelmethoden aufGamehaetten dasselbe zwoelfmal gebraucht — eine haette es vergessen.Zwoelf Commands, alle kosten einen Zug
Move(Direction)·UseAbility(AbilityId, CreatureRef)·UseItem(usize)·Equip(usize)·Unequip(SlotId)·Drop(usize, u32)·PickUp(usize)·Descend·Talk(NpcId)·Buy(ItemId, u32)·Sell(usize, u32)·WaitWeder Angriff noch Flucht sind eigene Varianten — beides sind Faehigkeiten (
UseAbility("core:attack"),UseAbility("core:flee")). #3 hat Faehigkeiten als Registry festgelegt, also gehoeren sie dorthin; eine Klasse, die besser flieht, ist damit eine Datenaenderung statt eines Engine-Sonderfalls.Auch Handel kostet einen Zug. Ein
costs_turn()-Flag waere eine Ausnahmeliste, bei der irgendwann jemand falsch raet. Screen-Navigation ist reine UI und fasstGamenie an; Speichern und Laden sind keine Commands und bekommen ihren Weg von #10.Ein Stack, eine Antwort
Ein gemeinsamer
Vec<Screen>fuer Screens und Popups — Popup ueber Popup ist real (Inventar -> Detail -> "wirklich wegwerfen?"), getrennte Felder braeuchten fuer den dritten Layer eine zweite Mechanik.Der Screen gibt zurueck statt selbst zu schieben: sonst haelt er ein
&mutauf genau dieVec, in der er liegt. Dasselbe Muster wie die Event-Warteschlange in #9. Nebeneffekt:Response::Commandist der einzige Weg nachgame/.Ein
Response::Commandschliesst alle Overlay-Screens — das Flag existiert schon fuers Rendern und beantwortet damit auch "schliesst sich nach einer Rueckfrage von selbst". Eine Zeile, keine neue Variante.Confirm { text, on_yes: Command }ist dadurch fuer jede Rueckfrage wiederverwendbar;Inventoryals Vollbild bleibt nachUseItemoffen.Zehn Screens
MainMenu(mit der Ladewarnungs-Zeile aus #5) ·CharacterCreation·Explore·Combat·Inventory·CharacterSheet·QuestLog·Shop·Dialog·ConfirmListStatelebt in der Screen-Variante. Der Stack macht den wichtigen Fall gratis richtig: solange ein Screen im Stack liegt, ueberlebt sein Cursor.Eingabe
Nur
KeyEventKind::Press. Der Grund ist schwerer als die UX: ein Schritt ist ein Zug, beiRepeatbestimmte die Tastaturwiederholrate des Betriebssystems die Spielzeit — ein gehaltener Pfeil verbrennte ein Gift-Debuff mit dreissig Zuegen pro Sekunde. Gegen zaehes Laufen hilft ein Renn-Kommando ("laufe, bis etwas passiert"), das ingame/viele Zuege aufloest.Tastenbelegung fest im Code, Pfeiltasten und
hjkl. Einekeybindings.tomlbraeuchte Parser, Konfliktpruefung und einen Einstellungs-Screen.Modulstruktur
Apphaeltgameundregistriesals getrennte Felder (disjunkte Borrows aus #8).Commandliegt ingame/, sonst zeigte die Abhaengigkeit in die falsche Richtung. Die ratatui-Freiheit prueft ein#[test], dersrc/game/**/*.rsliest — ein Workspace waere echte Compiler-Durchsetzung und ist die Decke.Nachtrag an #2 (01): Darstellung muss moddbar sein
#2 hat
symbolals Schluessel definiert, dessen Zuordnungui/theme.rsmacht. Darin steckt eine Luecke:ui/theme.rsist Code. Ein Modder mitmeinmod:frostbitekann dort nichts eintragen — sein Statuseffekt haette weder Zeichen noch Farbe. Stattdessen traegt die TOML beides selbst:data/kennt nurcharund ein Farbnamen-Enum,ui/theme.rsuebersetzt inratatui::Color.Auflagen
MainMenu,Exploreund das Grid-Widget — alles andere ist Kulissecore:attackundcore:fleemuessen als Faehigkeiten im Kernspiel existieren