From 4c40702738d6a0101930f3e8ef7e1476de794a87 Mon Sep 17 00:00:00 2001 From: rr- Date: Sun, 4 Nov 2018 17:48:34 +0100 Subject: [PATCH] ui: add spell book view --- pqcli/mechanic.py | 20 +++++++++++++++----- pqcli/ui/game_view.py | 38 ++++++++++++++++++++++++++++++++++++-- 2 files changed, 51 insertions(+), 7 deletions(-) diff --git a/pqcli/mechanic.py b/pqcli/mechanic.py index 06c4b9e..e44d505 100644 --- a/pqcli/mechanic.py +++ b/pqcli/mechanic.py @@ -13,17 +13,22 @@ from pqcli.lingo import * logger = logging.getLogger(__name__) +SENTINEL = object() + + class SignalMixin: def __init_subclass__(cls: T.Any, **kwargs: T.Any) -> None: urwid.signals.register_signal(cls, cls.signals) super().__init_subclass__(**kwargs) - def emit(self, signal_name: str, user_data: T.Any = None) -> None: + def emit(self, signal_name: str, user_data: T.Any = SENTINEL) -> None: urwid.signals.emit_signal(self, signal_name, user_data) def connect(self, signal_name: str, callback: T.Callable) -> None: urwid.signals.connect_signal( - self, signal_name, lambda _sender, *args: callback(*args) + self, + signal_name, + lambda arg: callback() if arg is SENTINEL else callback(arg), ) @@ -155,7 +160,9 @@ class Spell: level: int -class SpellBook: +class SpellBook(SignalMixin): + signals = ["add", "change"] + def __init__(self) -> None: self.spells: T.List[Spell] = [] @@ -167,10 +174,13 @@ class SpellBook: if spell.name == spell_name: spell.level += level logger.info("Learned %s at level %d", spell_name, spell.level) + self.emit("change", spell) break else: - self.spells.append(Spell(name=spell_name, level=level)) - logger.info("Learned %s at level %d", spell_name, level) + spell = Spell(name=spell_name, level=level) + self.spells.append(spell) + logger.info("Learned %s at level %d", spell.name, spell.level) + self.emit("add", spell) @dataclass diff --git a/pqcli/ui/game_view.py b/pqcli/ui/game_view.py index 837348c..d75b953 100644 --- a/pqcli/ui/game_view.py +++ b/pqcli/ui/game_view.py @@ -4,7 +4,8 @@ import typing as T import urwid from pqcli.config import StatType -from pqcli.mechanic import Player, Simulation +from pqcli.lingo import to_roman +from pqcli.mechanic import Player, Simulation, Spell from pqcli.ui.custom_line_box import CustomLineBox from pqcli.ui.custom_progress_bar import CustomProgressBar @@ -49,6 +50,36 @@ class CharacterSheetView(CustomLineBox): self.stat_texts[stat].set_text(str(self.player.stats[stat])) +class SpellBookView(CustomLineBox): + def __init__(self, player: Player) -> None: + self.player = player + + self.list_box = urwid.ListBox([]) + + self.player.spell_book.connect("add", self.sync_spell_add) + self.player.spell_book.connect("change", self.sync_spell_change) + self.sync_spells() + + super().__init__(self.list_box, title="Spell Book") + + def sync_spells(self) -> None: + del self.list_box.body[:] + for spell in self.player.spell_book: + self.sync_spell_add(spell) + + def sync_spell_add(self, spell: Spell) -> None: + self.list_box.body.append( + urwid.Columns( + [urwid.Text(spell.name), urwid.Text(to_roman(spell.level))] + ) + ) + + def sync_spell_change(self, spell: Spell) -> None: + for widget in self.list_box.body: + if widget.contents[0][0].text == spell.name: + widget.contents[1][0].set_text(to_roman(spell.level)) + + class TaskView(urwid.Pile): def __init__(self, player: Player) -> None: self.player = player @@ -86,13 +117,16 @@ class GameView(urwid.Pile): self.last_tick = datetime.datetime.now() self.character_sheet_view = CharacterSheetView(player) + self.spell_book_view = SpellBookView(player) self.task_view = TaskView(player) super().__init__( [ urwid.Columns( [ - urwid.Pile([self.character_sheet_view]), + urwid.Pile( + [self.character_sheet_view, self.spell_book_view] + ) ] ), ("pack", self.task_view),