Skip to content

Commit

Permalink
Merge pull request #16 from mmacy/dungeon-explore-tui-pt2
Browse files Browse the repository at this point in the history
item, weapon factories + fixed autogen dungeon + pre-rolled party
  • Loading branch information
mmacy committed Nov 4, 2023
2 parents 084fd46 + 8114cf4 commit 15b1d5c
Show file tree
Hide file tree
Showing 20 changed files with 798 additions and 265 deletions.
61 changes: 61 additions & 0 deletions osrgame/osrgame/example_adventure.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
from osrlib import Location, Exit, Direction, Dungeon, Adventure

adventure = Adventure("Castle of the Copper Maiden")
adventure.introduction = "In the secluded vale of Lurimara, the palace of Duchess Elara stood tall, crafted from moonlit alabaster echoing the brilliance of winter's dawn. This land, filled with creatures of whispered legends, flourished under Elara's watchful eyes, and was particularly famed for its intricate artifacts and armaments, at the heart of which was a gleaming sapphire termed 'The Luminous Gem.' On an evening bathed in starlight, during a majestic carnival, envy took root amidst celebration. Although the palace boasted chambers painted in hues of crimson and azure, and a terrace granting views of enchanting flora and lustrous vines, it was 'The Luminous Gem' that ensnared every gaze. Rumors speak of mages and sprites, consumed by its beauty, orchestrating its disappearance. When dawn broke, the sapphire was lost, and Lurimara's peace with it. Now, wyvern's silhouettes darken the skies, with tales of a solitary knight astride it, in pursuit of the lost treasure, echoing through time."

loc_description_9 = ["small room", "hangers", "hooks", "chest", "drawers", "east wall"]
loc_description_10 = ["bathing room", "scenes", "spring", "summer", "enamel", "oval bathtub", "towels", "vase", "red", "blue", "yellow"]
loc_description_11 = ["massive beds", "three chairs", "huge south wall", "table", "fireplace", "food", "wine", "dishes"]
loc_description_12 = ["small", "stool", "table", "north wall", "wheel", "south wall"]
loc_description_13 = ["garden", "weeds", "paths", "underbrush", "statue", "vines", "water"]
loc_description_14 = ["double doors", "wooden throne", "statues", "warriors", "columns", "fire places", "tapestries", "pomp", "feasts"]
loc_description_15 = ["couches", "marble table", "marble bench", "fire place", "dust"]
loc_description_16 = ["narrow bridge", "logs", "chasm", "bottomless", "water", "dripping", "no handrails", "slick", "moisture"]
loc_description_17 = ["ornate fountain", "mermaid", "giant shell", "water", "blue glow", "cool", "refreshing"]
loc_description_18 = ["iron cages", "exotic creature", "growl", "cower", "desk", "papers", "experiments"]
loc_description_19 = ["circular platform", "center", "runes", "floor", "teleportation device"]
loc_description_20 = ["giant mushrooms", "spores", "luminescent glow", "large fungi"]
loc_description_21 = ["corridor", "archway"]
loc_description_22 = ["young woman", "ceiling", "men", "swords", "hair", "U shaped table", "fireplace", "north wall"]
loc_description_23 = ["empty room"]
loc_description_24 = ["statue", "girl", "dove", "bookcase", "benches", "windows", "scrolls", "dead tree"]
loc_description_25 = ["canopy bed", "curtains", "dresser", "chest of drawers", "easy chair", "rugs"]
loc_description_26 = ["copper vats", "fire", "tubes", "wall", "liquid", "distilled"]
loc_description_27 = ["high ceiling", "chains", "hooks", "meat", "faint odor"]
loc_description_28 = ["wizard's study", "books", "bookshelves", "scrolls", "desk", "devices", "cage", "blue bird"]
loc_description_29 = ["green moss", "walls", "pool", "water", "dripping sound"]
loc_description_30 = ["statues", "humanoids", "poses", "fear", "horror", "lifelike", "stone"]
loc_description_31 = ["quaint little room", "game table", "chess set", "large map", "wine decanter", "log", "fireplace", "chess pieces gold and silver plated", "pipe", "wine glass", "peacock fan"]


dungeon = Dungeon("Castle of the Copper Maiden", "Upper level of the Copper Maiden's castle.")
dungeon.add_location(Location(99, 10, 10, [Exit(Direction.NORTH, 9)], ["Randoville", "tavern", "The Beer and Whine"], None))
dungeon.add_location(Location( 9, 20, 20, [Exit(Direction.NORTH, 10), Exit(Direction.SOUTH, 99)], [loc_description_9], None))
dungeon.add_location(Location(10, 20, 20, [Exit(Direction.NORTH, 11), Exit(Direction.SOUTH, 9), Exit(Direction.EAST, 11)], [loc_description_10], None))
dungeon.add_location(Location(11, 20, 20, [Exit(Direction.WEST, 10), Exit(Direction.SOUTH, 12)], [loc_description_11], None))
dungeon.add_location(Location(12, 20, 20, [Exit(Direction.NORTH, 11), Exit(Direction.EAST, 14), Exit(Direction.WEST, 13)], [loc_description_12], None))
dungeon.add_location(Location(13, 20, 20, [Exit(Direction.EAST, 12)], [loc_description_13], None))
dungeon.add_location(Location(14, 30, 30, [Exit(Direction.WEST, 12)], [loc_description_14], None))
dungeon.add_location(Location(15, 20, 20, [Exit(Direction.EAST, 14), Exit(Direction.WEST, 16)], [loc_description_15], None))
dungeon.add_location(Location(16, 20, 20, [Exit(Direction.EAST, 15), Exit(Direction.NORTH, 17), Exit(Direction.SOUTH, 18)], [loc_description_16], None))
dungeon.add_location(Location(17, 20, 20, [Exit(Direction.SOUTH, 16)], [loc_description_17], None))
dungeon.add_location(Location(18, 20, 20, [Exit(Direction.NORTH, 16), Exit(Direction.WEST, 19)], [loc_description_18], None))
dungeon.add_location(Location(19, 20, 20, [Exit(Direction.NORTH, 20), Exit(Direction.EAST, 18)], [loc_description_19], None))
dungeon.add_location(Location(20, 20, 20, [Exit(Direction.SOUTH, 19)], [loc_description_20], None))
dungeon.add_location(Location(21, 30, 20, [Exit(Direction.WEST, 22), Exit(Direction.NORTH, 23)], [loc_description_21], None))
dungeon.add_location(Location(22, 20, 20, [Exit(Direction.EAST, 21)], [loc_description_22], None))
dungeon.add_location(Location(23, 20, 30, [Exit(Direction.SOUTH, 21), Exit(Direction.WEST, 24)], [loc_description_23], None))
dungeon.add_location(Location(24, 20, 30, [Exit(Direction.EAST, 23), Exit(Direction.WEST, 25)], [loc_description_24], None))
dungeon.add_location(Location(25, 20, 30, [Exit(Direction.EAST, 24), Exit(Direction.WEST, 26)], [loc_description_25], None))
dungeon.add_location(Location(26, 20, 20, [Exit(Direction.EAST, 25), Exit(Direction.SOUTH, 27)], [loc_description_26], None))
dungeon.add_location(Location(27, 20, 30, [Exit(Direction.NORTH, 26), Exit(Direction.SOUTH, 28)], [loc_description_27], None))
dungeon.add_location(Location(28, 20, 20, [Exit(Direction.NORTH, 27), Exit(Direction.WEST, 29)], [loc_description_28], None))
dungeon.add_location(Location(29, 40, 40, [Exit(Direction.WEST, 30), Exit(Direction.EAST, 28)], [loc_description_29], None))
dungeon.add_location(Location(30, 20, 20, [Exit(Direction.WEST, 31), Exit(Direction.EAST, 29)], [loc_description_30], None))
dungeon.add_location(Location(31, 20, 20, [Exit(Direction.EAST, 30)], [loc_description_31], None))
dungeon.set_start_location(99)
if dungeon.validate_dungeon():
print("Dungeon location connection graph is valid.")

adventure.add_dungeon(dungeon)
adventure.set_active_dungeon(dungeon)
2 changes: 1 addition & 1 deletion osrgame/osrgame/osrgame.py
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ class OSRConsole(App):
adventure.set_active_dungeon(dungeon)

# Initialize the Dungeon Master
dungeon_master = DungeonMaster(adventure)
#dungeon_master = DungeonMaster(adventure)

SCREENS = {"scr_character": CharacterScreen(),
"scr_welcome": WelcomeScreen(),
Expand Down
30 changes: 22 additions & 8 deletions osrgame/osrgame/screen.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,11 @@
from textual.screen import Screen
from textual.widgets import Button, Header, Footer, Log, Placeholder

from osrlib import DungeonMaster
from osrlib.dungeon import Direction
from widgets import CharacterStats, AbilityTable, ItemTable, SavingThrows, CharacterScreenButtons, ExploreLogs
from osrlib.utils import wrap_text
from example_adventure import adventure
from widgets import CharacterStats, AbilityTable, ItemTable, SavingThrows, CharacterScreenButtons


####################
Expand Down Expand Up @@ -165,11 +168,12 @@ class ExploreScreen(Screen):
("s", "move_south", "South"),
("e", "move_east", "East"),
("w", "move_west", "West"),
("u", "move_up", "Up"),
("d", "move_down", "Down"),
("k", "clear_logs", "Clear logs"),
("?", "summarize", "Summarize session"),
]

dungeon_master = DungeonMaster(adventure)

def compose(self) -> ComposeResult:
yield Header(show_clock=True)
yield Log(id="player_log", auto_scroll=True, classes="box")
Expand All @@ -183,15 +187,16 @@ def on_mount(self) -> None:

def action_start_session(self) -> None:
"""Start a new session."""
dm_response = self.app.dungeon_master.start_session()

dm_response = self.dungeon_master.start_session()

# TODO: Need to do this automatically (move the party to the first "real" location)
dm_response = self.app.dungeon_master.move_party(Direction.NORTH)
dm_response = self.dungeon_master.move_party(Direction.NORTH)

self.query_one("#player_log").clear()
self.query_one("#player_log").write_line("The party stands ready.")
self.query_one("#player_log").write_line("---")
self.query_one("#dm_log").write_line(dm_response)
self.query_one("#dm_log").write_line(wrap_text(dm_response))
self.query_one("#dm_log").write_line("---")

def action_quit(self) -> None:
Expand All @@ -202,8 +207,8 @@ def perform_move_action(self, direction: Direction, log_message: str) -> None:
"""Perform a move action in a given direction."""
self.query_one("#player_log").write_line(log_message)
self.query_one("#player_log").write_line("---")
dm_response = self.app.dungeon_master.move_party(direction)
self.query_one("#dm_log").write_line(dm_response)
dm_response = self.dungeon_master.move_party(direction)
self.query_one("#dm_log").write_line(wrap_text(dm_response))
self.query_one("#dm_log").write_line("---")

def action_move_north(self) -> None:
Expand Down Expand Up @@ -235,6 +240,15 @@ def action_clear_logs(self) -> None:
self.query_one("#player_log").clear()
self.query_one("#dm_log").clear()

def action_summarize(self) -> None:
"""An action to summarize the session."""
self.query_one("#player_log").write_line("Summarizing session...")
self.query_one("#player_log").write_line("===")
formatted_message = self.dungeon_master.format_user_message("Please summarize the game session thus far. Include only what the players would know.")
dm_response = self.dungeon_master.player_message(formatted_message)
self.query_one("#dm_log").write_line(wrap_text(dm_response))
self.query_one("#dm_log").write_line("===")


####################
# Combat Screen
Expand Down
10 changes: 10 additions & 0 deletions osrlib/osrlib/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,16 @@
ItemNotInInventoryError,
ItemNotUsableError,
)
from .item_factories import (
armor_data,
ArmorFactory,
equipment_data,
EquipmentFactory,
weapon_data,
WeaponFactory,
ItemDataNotFoundError,
equip_party,
)
from .monster import (
Monster,
)
Expand Down
8 changes: 8 additions & 0 deletions osrlib/osrlib/adventure.py
Original file line number Diff line number Diff line change
Expand Up @@ -104,3 +104,11 @@ def start_adventure(self):
"""
self.is_started = True
logger.debug(f"Started adventure {self.name}.")

def end_adventure(self):
"""End the adventure.
Call this method when the adventure is over.
"""
self.is_started = False
logger.debug(f"Ended adventure {self.name}.")
Loading

0 comments on commit 15b1d5c

Please sign in to comment.