Fix numerous bugs

Finally fixed the 'alias' bug that has plaqued me.
This commit is contained in:
Howard Abrams 2025-08-10 22:42:08 -07:00
parent 0ad4936f48
commit 2719bce82b
14 changed files with 1233 additions and 528 deletions

View file

@ -697,7 +697,9 @@ class CmdFeed(MuxCommand):
feeder = self.caller feeder = self.caller
if self.rhs: if self.rhs:
eater = feeder.search(self.rhs) eater = feeder.search(self.rhs)
food = feeder.search(self.lhs) food = feeder.search(self.lhs, location=feeder)
if not food:
return
else: else:
eater = feeder.search(self.lhs) eater = feeder.search(self.lhs)
food = None food = None

View file

@ -16,11 +16,12 @@ from evennia.contrib.game_systems.gendersub import GenderCharacter
from evennia.contrib.rpg.rpsystem import ContribRPCharacter, send_emote from evennia.contrib.rpg.rpsystem import ContribRPCharacter, send_emote
from evennia.prototypes.spawner import spawn from evennia.prototypes.spawner import spawn
from evennia.utils import delay, logger, int2str from evennia.utils import delay, logger, int2str
from evennia.utils.search import search_object, search_objects_by_typeclass from evennia.utils.search import (search_object, search_account,
search_objects_by_typeclass)
from utils.word_list import routput, choices, fix_msg from utils.word_list import routput, choices, fix_msg
from .objects import Object from typeclasses.objects import Object, ObjectParent
from .tutorial import TutorBird, TutorialState from typeclasses.tutorial import TutorBird, TutorialState
INTRO = """ INTRO = """
@ -118,18 +119,24 @@ class Character(Object, GenderCharacter, ContribRPCharacter):
obj.delete() obj.delete()
# Move them to the Grove to begin their adventure: # Move them to the Grove to begin their adventure:
grove = self.search("mp01", global_search=True, quiet=True) self.location = search_object("mp01").first()
if isinstance(grove, list):
grove = grove[0] # Reset the "running state" that character may have
# self.move_to(grove, quiet=True, use_destination=True) # experienced. This way, new guests get to _re-experience_ it:
self.location = grove
# Start the tutorial:
self.db.visited = False self.db.visited = False
self.db.jumped_times = 0 self.db.jumped_times = 0
self.db.tutorstate = 0 self.db.tutorstate = 0
self.db.thrown_times = 0 self.db.thrown_times = 0
self.db.knocker_conversation_state = None self.db.knocker_conversation_state = None
self.ndb.cozy_house_number_of_bookshelves = 0
self.db.received_pipe=False
self.ndb.assortment_of_jars_view_index=0
self.ndb.shelf_full_of_jars_view_index=0
self.db.wee_beastie_friendly_level = 0
self.db.big_hairy_beast_friendly_level = 0
# Finally, star the tutorial:
TutorBird.do_start_tutorial(self) TutorBird.do_start_tutorial(self)
self.msg(INTRO) self.msg(INTRO)
@ -141,10 +148,7 @@ class Character(Object, GenderCharacter, ContribRPCharacter):
""" """
self.msg("You wake up in a meadow with a strange dream of a bar...") self.msg("You wake up in a meadow with a strange dream of a bar...")
self.delete_inv("typeclasses.drinkables.Cocktail") self.delete_inv("typeclasses.drinkables.Cocktail")
meadow = self.search("Frog Meadow", global_search=True, quiet=True) self.move_to(search_object("mp05").first(), quiet=True, use_destination=True)
if isinstance(meadow, list):
meadow = meadow[0]
self.move_to(meadow, quiet=True, use_destination=True)
def at_post_puppet(self, **kwargs): def at_post_puppet(self, **kwargs):
""" """
@ -243,10 +247,8 @@ class Character(Object, GenderCharacter, ContribRPCharacter):
This replaces the weird, auto-generated name with the This replaces the weird, auto-generated name with the
character's actual name. character's actual name.
""" """
letter = self.search('letter', location=self, quiet=True) # letter = search_object('letter', location=self).first()
if letter and isinstance(letter, list) and len(letter) > 0: letter = self.search('letter', quiet=True).first()
letter = letter[0]
if letter: if letter:
text = sub(r"My dear [^,]*", f"My dear {self.name}", letter.db.inside) text = sub(r"My dear [^,]*", f"My dear {self.name}", letter.db.inside)
letter.db.inside = text letter.db.inside = text
@ -447,10 +449,24 @@ class Character(Object, GenderCharacter, ContribRPCharacter):
if location == "home": if location == "home":
dest = self.home dest = self.home
else: else:
dest = self.global_search(location) if location.startswith("*"):
if dest and dest.is_typeclass("typeclasses.characters.Character"): acc = search_account(location[1:]).first()
if acc:
pups = acc.get_all_puppets()
dest = pups[0].location
else:
dest = search_object(location).first()
if not dest:
self.msg(f"Not sure where, '{location}' is.")
return
if dest.is_typeclass("typeclasses.characters.Character"):
dest = dest.location dest = dest.location
elif not dest or not dest.is_typeclass("typeclasses.rooms.Room"): elif dest.is_typeclass("typeclasses.accounts.Account"):
self.msg(f"Looking for account, eh?")
return
elif not dest.is_typeclass("typeclasses.rooms.Room"):
self.msg(f"Not sure where, '{location}' is.") self.msg(f"Not sure where, '{location}' is.")
return return
@ -495,7 +511,3 @@ class Character(Object, GenderCharacter, ContribRPCharacter):
if len(inv_items) > 0: if len(inv_items) > 0:
return inv_items return inv_items
return None return None
# Local Variables:
# jinx-local-words: "Marsivan"
# End:

View file

@ -13,6 +13,7 @@ from enum import Enum
from urllib.request import urlopen from urllib.request import urlopen
from typeclasses.objects import Object from typeclasses.objects import Object
from typeclasses.characters import Character
from typeclasses.npcs import CarriableNPC from typeclasses.npcs import CarriableNPC
from utils.word_list import routput from utils.word_list import routput
@ -94,6 +95,14 @@ class Fish(CarriableNPC):
""" """
return "say", "What was that? I must have water in my ear." return "say", "What was that? I must have water in my ear."
def at_say(self, message):
"""
Spoken out loud to the world, even if owned.
"""
owner = self.location
if owner.is_typeclass(Character) and owner.is_connected:
self.location.announce_action(f"$Your() fish says, \"{message}\"")
def do_speak(self): def do_speak(self):
""" """
Called at a repeatable sequence by the ticker, and Called at a repeatable sequence by the ticker, and

View file

@ -12,9 +12,10 @@ with a location in the game world (like Characters, Rooms, Exits).
from re import split, match, sub, IGNORECASE from re import split, match, sub, IGNORECASE
from django.conf import settings from django.conf import settings
from evennia.contrib.rpg.rpsystem.rpsystem import ContribRPObject from evennia.contrib.rpg.rpsystem.rpsystem import ContribRPObject, parse_sdescs_and_recogs
from evennia.prototypes.spawner import spawn from evennia.prototypes.spawner import spawn
from evennia.utils import delay, logger from evennia.utils import delay, logger
from evennia.utils.search import search_object
from utils.word_list import routput from utils.word_list import routput
@ -36,7 +37,53 @@ class ObjectParent:
"""True if this object has a method of a particular name.""" """True if this object has a method of a particular name."""
return hasattr(self, method_name) and callable(getattr(self, method_name)) return hasattr(self, method_name) and callable(getattr(self, method_name))
def has(self, item):
"""
Return true if object has an item.
Where item is probably a string name to match an item's key.
It can also be a type, for instance:
character.has(typeclasses.drinkables.TeaCup)
"""
for i in self.contents:
if isinstance(item, str) and (i.key == item or i.aliases.get(item)):
return i
if item is type(i):
return i
if i == item:
return i
return None
def client_height(self):
"""
Get the client screenheight for the session using this command.
Returns:
client height (int): The height (in characters) of the client window.
Not sure why this isn't part of the engine.
"""
if self.sessions:
session = self.sessions.get()[0]
return session.protocol_flags.get(
"SCREENHEIGHT", {0: settings.CLIENT_DEFAULT_HEIGHT}
)[0]
return settings.CLIENT_DEFAULT_HEIGHT
def characters_here(self, puppets=False):
"""
Return a list of characters in the current location.
"""
return [char
for char in self.location.contents
if char != self and
(char.is_typeclass("typeclasses.characters.Character")
or (char.is_typeclass("typeclasses.puppets.Puppet") and puppets))]
# Removing the ContribRPObject
class Object(ObjectParent, ContribRPObject): class Object(ObjectParent, ContribRPObject):
""" """
This is the root Object typeclass, representing all entities that This is the root Object typeclass, representing all entities that
@ -227,61 +274,6 @@ class Object(ObjectParent, ContribRPObject):
at_desc(looker=None) at_desc(looker=None)
""" """
def global_search(self, searchdata):
"""
Search for something globally.
"""
results = super().search(searchdata, global_search=True, quiet=True)
if isinstance(results, list):
return results[0]
return results
def has(self, item):
"""
Return true if object has an item.
Where item is probably a string name to match an item's key.
It can also be a type, for instance:
character.has(typeclasses.drinkables.TeaCup)
"""
for i in self.contents:
if isinstance(item, str) and (i.key == item or i.aliases.get(item)):
return i
if item is type(i):
return i
if i == item:
return i
return None
def client_height(self):
"""
Get the client screenheight for the session using this command.
Returns:
client height (int): The height (in characters) of the client window.
Not sure why this isn't part of the engine.
"""
if self.sessions:
session = self.sessions.get()[0]
return session.protocol_flags.get(
"SCREENHEIGHT", {0: settings.CLIENT_DEFAULT_HEIGHT}
)[0]
return settings.CLIENT_DEFAULT_HEIGHT
def characters_here(self, puppets=False):
"""
Return a list of characters in the current location.
"""
return [char
for char in self.location.contents
if char != self and
(char.is_typeclass("typeclasses.characters.Character")
or (char.is_typeclass("typeclasses.puppets.Puppet") and puppets))]
def delay_sequence(self, sequence_str, time_delay=1, *args): def delay_sequence(self, sequence_str, time_delay=1, *args):
"""Run a sequence of messages or commands with a delay. """Run a sequence of messages or commands with a delay.
@ -312,10 +304,10 @@ class Object(ObjectParent, ContribRPObject):
except ValueError: except ValueError:
return x return x
if self.db.current_sequence and self.db.current_sequence == sequence_str: if self.ndb.current_sequence and self.ndb.current_sequence == sequence_str:
logger.info("Duplicate sequences. Ignoring.") logger.info("Duplicate sequences. Ignoring.")
return return
self.db.current_sequence = sequence_str self.ndb.current_sequence = sequence_str
lines = [convert(line) for line in split(r" *;; *", sequence_str)] lines = [convert(line) for line in split(r" *;; *", sequence_str)]
pause = 0 pause = 0
@ -333,7 +325,7 @@ class Object(ObjectParent, ContribRPObject):
cmd = routput(line, *args) cmd = routput(line, *args)
delay(pause, self.do_cmd, cmd) delay(pause, self.do_cmd, cmd)
delay(pause, self.attributes.remove, "current_sequence") delay(pause, self.nattributes.remove, "current_sequence")
def at_post_move(self, source_location, move_type="move", **kwargs): def at_post_move(self, source_location, move_type="move", **kwargs):
""" """
@ -351,6 +343,44 @@ class Object(ObjectParent, ContribRPObject):
if hasattr(getter, 'other_given') and callable(getter.other_given): if hasattr(getter, 'other_given') and callable(getter.other_given):
getter.other_given(giver, self) getter.other_given(giver, self)
# The RPSystem overrides the `get_search_result` function to be
# able to look for words in the `sdesc` field, but in the process,
# dropped the ability to search for objects by `alias`.
def get_search_result(
self,
searchdata,
candidates=None,
**kwargs,
):
"""
Override of the parent method for producing search results
that understands sdescs. These are used in the main .search()
method of the parent class.
"""
# we also want to use the default search method
search_obj = super().get_search_result
results = []
if candidates is not None:
searched_results = parse_sdescs_and_recogs(
self, candidates, "/" + searchdata, search_mode=True
)
if not searched_results:
results = search_obj(searchdata, candidates=candidates, **kwargs)
else:
# We do a default search on each result by key, here,
# to apply extra filtering kwargs
for searched_obj in searched_results:
results.extend([
obj
for obj in search_obj(searched_obj.key, candidates=[searched_obj], **kwargs)
if obj not in results])
else:
# no candidates means it's a global search, so we pass it back to the default
results = search_obj(searchdata, **kwargs)
return results
class Listener: class Listener:
""" """
@ -434,10 +464,10 @@ class Listener:
logger.info(f"Executing: {cmd}") logger.info(f"Executing: {cmd}")
m = match(r"teleport +(.*?) *= *(.*)", cmd) m = match(r"teleport +(.*?) *= *(.*)", cmd)
if m: if m:
o = self.global_search(m.group(1)) o = search_object(m.group(1)).first()
d = self.global_search(m.group(2)) d = search_object(m.group(2)).first()
logger.info(f"Teleporting: {m.group(1)} {o} to {d}")
if o and d: if o and d:
logger.info(f"Teleporting: {m.group(1)} {o} to {d}")
o.move_to(d, quiet=True) o.move_to(d, quiet=True)
return return
@ -477,7 +507,7 @@ class Listener:
@set thing/objects_here = [one_object, two_object] @set thing/objects_here = [one_object, two_object]
""" """
def move_to_me(obj): def move_to_me(obj):
o = self.global_search(obj) o = search_object(obj).first()
if o: if o:
o.move_to(self, quiet=True) o.move_to(self, quiet=True)

View file

@ -18,6 +18,7 @@ import random
from evennia import TICKER_HANDLER from evennia import TICKER_HANDLER
from evennia.utils import logger from evennia.utils import logger
from evennia.utils.gametime import schedule from evennia.utils.gametime import schedule
from evennia.utils.search import search_object
from typeclasses.objects import Object from typeclasses.objects import Object
from typeclasses.characters import Character from typeclasses.characters import Character
@ -420,7 +421,7 @@ class Friendly(Pet):
self.db.last_actions.append(msg) self.db.last_actions.append(msg)
# Limit this list so it doesn't grow too large: # Limit this list so it doesn't grow too large:
self.db.last_actions = self.db.last_actions[-5:] self.db.last_actions = self.db.last_actions[-5:]
focus.announce_action(msg) focus.announce_action(msg, focus)
def pet_response(self, petter): def pet_response(self, petter):
""" """
@ -496,8 +497,8 @@ class BHB(Friendly):
elif minute == 58: elif minute == 58:
msg = f"The {noun} lets loose a big yawn." msg = f"The {noun} lets loose a big yawn."
meadow = self.global_search("mp05") meadow = search_object("mp05").first()
cave = self.global_search("mp07") cave = search_object("mp06").first()
if 'portal_open' in self.location.room_states: if 'portal_open' in self.location.room_states:
msg = f"The {noun} becomes frightened of the flying lights." msg = f"The {noun} becomes frightened of the flying lights."

View file

@ -63,24 +63,32 @@ class Changling(StoryCube):
else: else:
return "" return ""
# randomly get the index for one of the descriptions # Randomly get the index for one of the descriptions:
descs = self.db.descs descs = self.db.descs
clueindex = randint(0, len(descs) - 1) clueindex = randint(0, len(descs) - 1)
# Remember the last view as it could be a clue for later:
key_id = self.key.lower().replace(" ", "_") + "_view_index"
if self.attributes.get("desc_first_prefix") and \
not caller.nattributes.get(key_id):
prefix = optional(self.db.desc_first_prefix, True)
else:
prefix = optional(self.db.desc_prefix, True)
# set this description, with the random extra # set this description, with the random extra
self.db.desc = optional(self.db.desc_prefix, True) + \ self.db.desc = prefix + descs[clueindex] + optional(self.db.desc_postfix)
descs[clueindex] + optional(self.db.desc_postfix)
# Might as well remember the last view we got, as it could be
# a clue we could refer to.
caller.attributes.add(key=f"{self.key}_view_index",
value=clueindex)
caller.nattributes.add(key=key_id, value=clueindex)
# call the parent function as normal (this will use # call the parent function as normal (this will use
# the new desc Attribute we just set) # the new desc Attribute we just set)
# return super().return_appearance(caller) # return super().return_appearance(caller)
return self.db.desc return self.db.desc
def at_object_receive(self, obj, giver, **kwargs): def at_object_receive(self, obj, giver, **kwargs):
"""
Workaround for a particular puzzle. Perhaps we can get rid of this.
"""
if obj.key == 'conch': if obj.key == 'conch':
return super().at_object_receive(obj, giver) return super().at_object_receive(obj, giver)

View file

@ -2,17 +2,152 @@
from datetime import datetime from datetime import datetime
from random import choice from random import choice
from re import sub
from evennia import Command, CmdSet
from evennia.utils import logger from evennia.utils import logger
from evennia.prototypes.spawner import spawn from evennia.prototypes.spawner import spawn
from typeclasses.objects import Object from typeclasses.objects import Object
from typeclasses.consumables import Producer
from utils.word_list import routput from utils.word_list import routput
from commands.misc import CmdSetWrite from commands.misc import CmdSetWrite
class Readable(Object):
"""
Create with a command:
@create/drop sign : typeclasses.readables.Readable
@desc sign = A tall wooden post.
@set sign/inside = "What happens when you read it."
"""
class Letter(Readable):
"""
Something that can be read, but is _personal_, so if it is
dropped, it is destroyed.
"""
def at_pre_drop(self, dropper, **kwargs):
dropper.msg(f"You throw your {self.get_display_name(dropper)} away.")
self.delete()
class Book(Readable):
"""
A book is a readable thing (has an 'inside' attribute),
but if dropped near a bookshelf, it is deleted instead of left.
"""
def do_read(self, reader):
"""
Announces reading this book.
Doesn't tell the 'reader' what is inside, however. ;-)
"""
reader.announce_action("$You() $conj(read) $pron(your) book.")
def at_pre_drop(self, dropper, **kwargs):
"""
If book is dropped next to a Bookshelf (that created it),
the book is _returned_ (that is, deleted).
"""
if dropper.location.key == "Cozy House":
dropper.msg("You drop the book, but flapping its pages, flies back to its section on a shelf.")
self.delete()
return False
shelf = dropper.search_first("", quiet=True,
typeclass="typeclasses.readables.Bookshelf")
if shelf:
dropper.announce_action(f"$You() $conj(return) a book to {shelf.name}.")
self.delete()
return False
return True
class WriteableBook(Book):
"""
Along with reading, the user can write in this book.
Actually, append to the text file associated with it.
"""
def at_object_creation(self):
"""
called at creation
"""
self.cmdset.add_default(CmdSetWrite)
def do_read(self, reader):
"""
Announces reading this book.
Doesn't tell the 'reader' what is inside, however. ;-)
"""
reader.announce_action(f"$You() $conj(read) the {self.name}.")
def do_write_begin(self, writer):
"""
Announces writing in this.
"""
writer.announce_action(
self.db.pre_write_msg or
"$You() $conj(grab) the quill, $conj(dip) it in the ink well, "
"and $conj(begin) to pen a message in the book...")
writer.msg("|/<< Pardon the quaint, twentieth-century approach to "
"capturing your prose (but this works with all MUD "
"clients). Easiest approach: just type your message, hit "
"the |wReturn|n key, type |g:q|n, and his the "
"|wReturn|n key again...>>|/")
return ""
def do_write(self, writer, message):
"""
Stores the message and metadata in file mentioned 'inside'.
This assumes the object's 'inside' starts with 'file:', as in:
@set book/inside = "file:somefile.md"
"""
session = writer.sessions.get()[0]
contents = self.db.inside
if contents.startswith("file:"):
filename = contents[5:]
with open(filename, "a") as myfile:
myfile.write(f"# {writer.name}\n\n")
myfile.write(message)
myfile.write("\n\n")
myfile.write(f"> User: {writer.account.name}\n")
myfile.write(f"> Addr: {session.protocol_key}:{session.address}\n")
myfile.write(f"> Cmds: {session.cmd_total}\n\n")
def do_write_end(self, writer):
"""
Announces the end of writing.
"""
writer.announce_action(
self.db.post_write_msg or
"$You() $conj(put) down the quill, and $conj(stop) writing.")
class Journal(WriteableBook):
"""
A special writeable book, that stores the contents
in a different file based on the date.
"""
def do_write(self, writer, message):
"""
Change the self.db.inside to a date.
"""
today = datetime.now()
self.db.inside = 'file:/home/howard/howardabrams/thoughts/' + \
today.strftime("%Y%m%d")
super().do_write(writer, message)
# ------------------------------------------------------------------------
# RANDOM BOOKS
# ------------------------------------------------------------------------
BOOK_EMOTIONS = [ BOOK_EMOTIONS = [
"sad", "sad",
"heartfelt", "heartfelt",
@ -71,171 +206,26 @@ BOOKS = {
} }
class CmdLookBook(Command): class Bookshelf(Producer):
""" """
Respond with a new book to look at. Special producer,
Keeps a "state" of time, the bookshelf was "looked" at,
and creates _that_ book when the "get" command is issued.
""" """
auto_help = False
key = "look book"
aliases = "l book"
def func(self):
self.obj.do_look(self.caller)
class CmdTakeBook(Command):
"""
Generate a new book to store it with the reader.
"""
auto_help = False
key = "get book"
aliases = "take book"
def func(self):
self.obj.do_take(self.caller)
class CmdSetRead(CmdSet):
def at_cmdset_creation(self):
pass # self.add(CmdReadBook)
class CmdSetBook(CmdSet):
def at_cmdset_creation(self):
# self.add(CmdBurnBook)
# self.add(CmdDropBook)
pass
class CmdSetShelf(CmdSet):
def at_cmdset_creation(self):
self.add(CmdLookBook)
self.add(CmdTakeBook)
# ----------------------------------------------------------------------
class Readable(Object):
"""
Create with a command:
@create/drop sign : typeclasses.readables.Readable
@desc sign = A tall wooden post.
@set sign/inside = "What happens when you read it."
"""
pass
class Letter(Readable):
"""
Something that can be read, but is _personal_, so if it is
dropped, it is destroyed.
"""
def at_object_creation(self):
"""
called at creation
"""
self.cmdset.add_default(CmdSetBook)
def at_pre_drop(self, dropper):
dropper.msg(f"You throw your {self.get_display_name(dropper)} away.")
self.delete()
class Book(Readable):
def at_object_creation(self):
"""
called at creation
"""
self.cmdset.add_default(CmdSetBook)
def do_read(self, reader):
reader.announce_action("$You() $conj(read) $pron(your) book.")
def at_pre_drop(self, reader):
if reader.location.key == "Cozy House":
reader.msg("You drop the book, but flapping its pages, flies back to its section on a shelf.")
self.delete()
else:
return True
class WriteableBook(Book):
"""
Along with reading, the user can write in this book.
Actually, append to the text file associated with it.
"""
def at_object_creation(self):
"""
called at creation
"""
self.cmdset.add_default(CmdSetWrite)
def do_read(self, reader):
reader.announce_action(f"$You() $conj(read) the {self.name}.")
def do_write_begin(self, writer):
writer.announce_action(
self.db.pre_write_msg or
"$You() $conj(grab) the quill, $conj(dip) it in the ink well, "
"and $conj(begin) to pen a message in the book...")
writer.msg("|/<< Pardon the quaint, twentieth-century approach to "
"capturing your prose (but this works with all MUD "
"clients). Easiest approach: just type your message, hit "
"the |wReturn|n key, type |g:q|n, and his the "
"|wReturn|n key again...>>|/")
return ""
def do_write(self, writer, message):
session = writer.sessions.get()[0]
contents = self.db.inside
if contents.startswith("file:"):
filename = contents[5:]
with open(filename, "a") as myfile:
myfile.write(f"# {writer.name}\n\n")
myfile.write(message)
myfile.write("\n\n")
myfile.write(f"> User: {writer.account.name}\n")
myfile.write(f"> Addr: {session.protocol_key}:{session.address}\n")
myfile.write(f"> Cmds: {session.cmd_total}\n\n")
def do_write_end(self, writer):
writer.announce_action(
self.db.post_write_msg or
"$You() $conj(put) down the quill, and $conj(stop) writing.")
class Journal(WriteableBook):
"""
A special writeable book, that stores the contents
in a different file based on the date.
"""
def do_write(self, writer, message):
"""
Change the self.db.inside to a date.
"""
today = datetime.now()
self.db.inside = 'file:/home/howard/howardabrams/thoughts/' + \
today.strftime("%Y%m%d")
super().do_write(writer, message)
class Books(Object):
book_prototype = { book_prototype = {
"typeclass": "typeclasses.readables.Book", "typeclass": "typeclasses.readables.Book",
"key": "book", "key": "book",
"desc": "An old, worn, leather-bound book.", "desc": "An old, worn, leather-bound book.",
} }
def at_object_creation(self):
"""
called at creation
"""
self.cmdset.add_default(CmdSetShelf, persistent=True)
def new_book_details(self): def new_book_details(self):
"""
Choose a random book, and return tuple of details.
Return: (title, description, inside_description)
"""
title = choice(list(BOOKS.keys())) title = choice(list(BOOKS.keys()))
return ( return (
title, title,
@ -253,24 +243,72 @@ class Books(Object):
) )
) )
def do_look(self, reader): def new_book(self):
(self.db.last_title, self.db.last_desc, """
self.db.last_inside) = self.new_book_details() Return the description of a newly seen book.
reader.msg(f"You see {self.db.last_desc}.") This also _stores_ the details of that book for later.
"""
(title, desc, inside) = self.new_book_details()
self.db.last_title = title
self.db.last_desc = desc
self.db.last_inside = inside
return desc
def return_appearance(self, looker, **kwargs):
"""
Only the first time looker view this, do we return the description.
Otherwise, we return a new book.
"""
book_desc = self.new_book()
this_id = sub(r" +", "_", self.location.key.lower()) + \
"_" + sub(r" +", "_", self.key.lower())
num_books = looker.nattributes.get(this_id, 0)
looker.nattributes.add(this_id, num_books + 1)
filler = routput(""" You
<< browse ^ browse through ^ scan ^ scan through ^ examine ^
peruse ^ peruse through ^ inspect >>
the books << on the shelf ^ >>, and
<< find ^ discover ^ encounter ^ spot ^ stumble upon ^
this book catches your eye, >> """.replace("\n", " "))
if num_books == 0:
return self.db.desc + " " + filler + " " + book_desc + "."
else:
return filler + " " + book_desc + "."
def do_make(self, reader):
"""
Create a book, and give it to the 'reader'.
If the reader has seen a book previously, with the 'look'
command, give them that book, otherwise, give them a new one
at random.
"""
if not self.db.last_title:
filler = "a"
(title, desc, inside) = self.new_book_details()
else:
filler = "the"
title = self.db.last_title
desc = self.db.last_desc
inside = self.db.last_inside
def do_take(self, reader):
if self.db.last_title:
booktype = self.book_prototype booktype = self.book_prototype
booktype['desc'] = self.db.last_desc booktype['desc'] = desc
booktype['aliases'] = [self.db.last_title] booktype['aliases'] = [title]
book = spawn(booktype)[0] book = spawn(booktype)[0]
book.db.inside = self.db.last_inside book.db.inside = inside
book.location = reader book.location = reader
reader.msg("You pick up the book.") reader.msg(f"You pick up {filler} book, |w{title}|n.")
self.db.last_title = None self.db.last_title = None
self.db.last_desc = None self.db.last_desc = None
self.db.last_inside = None self.db.last_inside = None
else:
reader.msg("Which book do you want to take. The shelves are full of them. Perhaps you want to |glook|n at a |gbook|n?")

View file

@ -19,7 +19,7 @@ from random import choice
from evennia.scripts.scripts import DefaultScript from evennia.scripts.scripts import DefaultScript
from evennia.prototypes.spawner import spawn from evennia.prototypes.spawner import spawn
from evennia.utils import logger, delay from evennia.utils import logger, delay
from evennia.utils.search import search_object
from typeclasses.characters import Character from typeclasses.characters import Character
@ -116,14 +116,11 @@ class KnockScript(Script):
def at_start(self, **kwargs): def at_start(self, **kwargs):
knocker = self.attributes.get("knocker") knocker = self.attributes.get("knocker")
if knocker: if knocker:
room = knocker.global_search(self.attributes.get("room")) room = search_object(self.attributes.get("room")).first()
if room: if room:
room.msg_contents("Someone is knocking on the door...") room.msg_contents("Someone is knocking on the door...")
gnome = knocker.search("Dabbler", quiet=True, gnome = search_object("Dabbler").first()
global_search=True)
if isinstance(gnome, list):
gnome = gnome[0]
if gnome: if gnome:
gnome.msg(f"With your seer stone, you see the knocker is {knocker.key}, {knocker.db._sdesc}.") gnome.msg(f"With your seer stone, you see the knocker is {knocker.key}, {knocker.db._sdesc}.")
@ -159,8 +156,8 @@ class CreateHorns(Script):
""" """
def at_repeat(self, **kwargs): def at_repeat(self, **kwargs):
hut = self.attributes.get("destination") hut = self.attributes.get("destination")
results = hut.search('horn') results = hut.search('horn').first()
if results and len(results) > 0 and results[0].location == hut: if results and results.location == hut:
pass pass
else: else:
horn = spawn({ horn = spawn({

View file

@ -268,7 +268,7 @@ class Pipe(Object):
details = details or "" details = details or ""
msg = choices(f"""$You() $conj(blow) a {details} smoke ring. msg = choices(f"""$You() $conj(blow) a {details} smoke ring.
;; The smoke from $your() forms a << beautiful ^ swirling ^ spiraling >> ring. ;; The smoke from $your() {self.name} forms a << beautiful ^ swirling ^ spiraling >> ring.
""") """)
smoker.announce_action(msg) smoker.announce_action(msg)
if randint(1, 10) < 5: if randint(1, 10) < 5:

View file

@ -120,7 +120,10 @@ def routput(text, *substitutions):
# leaving on the phrases to join: # leaving on the phrases to join:
phrases = [phrase for phrase in parts if not _routput_empty(phrase)] phrases = [phrase for phrase in parts if not _routput_empty(phrase)]
if substitutions:
proposal = ' '.join(phrases).format(*substitutions) proposal = ' '.join(phrases).format(*substitutions)
else:
proposal = ' '.join(phrases)
# If a choice is at the end of a sentence, and we could have # If a choice is at the end of a sentence, and we could have
# "no choice", as in: # "no choice", as in:

View file

@ -194,7 +194,7 @@ cozy_house:
Each time you |glook book|n, you will see a new book. Each time you |glook book|n, you will see a new book.
Type |gget book|n, to put it in your |ginventory|n. Type |gget book|n, to put it in your |ginventory|n.
Type |gread book|n, to get a summary. Type |gread book|n, to get a summary.
No, I did not feel like writing multiple novels for this game. No, we did not feel like writing multiple novels for this game.
cramped_kitchen: cramped_kitchen:
hints: hints:
@ -259,7 +259,7 @@ bedroom:
hints: hints:
default: >- default: >-
Don't steal the slippers, as they are decoration (as even Don't steal the slippers, as they are decoration (as even
Dabbler can keep them on his toes). The |Ywardrobe|n is Dabbler can't keep them on his toes). The |Ywardrobe|n is
obviously interesting. obviously interesting.
wardrobe: If you |gopen|n the |gwardrobe|n, you will find a new exit. wardrobe: If you |gopen|n the |gwardrobe|n, you will find a new exit.

View file

@ -154,6 +154,9 @@ switch $phase {
send "look trees\n" send "look trees\n"
expectit "You feel dwarfed by colossal trees" expectit "You feel dwarfed by colossal trees"
send "look flowers\n"
expectit "Beautiful, but giant flowers look down on you and nod a friendly greeting."
send "hint\n" send "hint\n"
expectit "Look at everything" expectit "Look at everything"
@ -214,6 +217,18 @@ sleep 1
send "get book\n" send "get book\n"
expectit "The owner designed a guest book to be read and written by guests" expectit "The owner designed a guest book to be read and written by guests"
send "look symbol\n"
expectit "You move an ivy runner to see three curves join together as if it were three legs."
send "look moss\n"
expectit "Even in this light, the moss radiates a surreal color of green."
send "look ivy\n"
expectit "You see...well, ivy. Uhm, it's green, and..."
send "look rune\n"
expectit "The runes read ᛞ ᚪ ᛒ ᛚ ᚱ"
dont_expect "Exits" "boulder" dont_expect "Exits" "boulder"
send "look boulder\n" send "look boulder\n"
@ -234,7 +249,7 @@ send "get vines\n"
expectit "The vines are too strong to break or cut." expectit "The vines are too strong to break or cut."
send "pull vines\n" send "pull vines\n"
expectit "You pull the vines, but don't let go." expectit "You pull the vines, but they don't let go."
send "push vines\n" send "push vines\n"
expectit "That doesn't seem to do much." expectit "That doesn't seem to do much."
@ -245,6 +260,15 @@ expectit "You grab hold of some"
# Did we arrive? # Did we arrive?
expectit "Boulder Top" expectit "Boulder Top"
send "look trees\n"
expectit "You feel dwarfed by colossal trees"
send "look down\n"
expectit "The climb seemed easy, but you're not sure you can handle the footholds going the other way around."
send "look moss\n"
expectit "A cushioned patch of moss of the most vibrant green."
send "sit moss\n" send "sit moss\n"
expectit "You sit on the patch of moss." expectit "You sit on the patch of moss."
@ -252,6 +276,9 @@ expectit "You sit on the patch of moss."
send "get moss\n" send "get moss\n"
expectit "The moss is a bryophyte" expectit "The moss is a bryophyte"
send "look vines\n"
expectit "While difficult to cut, the study and tough vines are easy to pull"
send "pull vines\n" send "pull vines\n"
expectit "You pull the vines" expectit "You pull the vines"
@ -310,12 +337,6 @@ expectit "A slow-moving stream meanders like a snake in the grassy field."
send "get stream\n" send "get stream\n"
expectit "Seriously? You can't get that." expectit "Seriously? You can't get that."
# send "look water\n"
# expectit "A slow-moving stream meanders like a snake in the grassy field."
# send "get water\n"
# expectit "Seriously? You can't get that."
dont_expect "You notice" "tickleweed" dont_expect "You notice" "tickleweed"
send "hint\n" send "hint\n"
@ -369,10 +390,13 @@ expect {
expectit "it tries to hide behind a tall clump of grass" expectit "it tries to hide behind a tall clump of grass"
send "pet bhb\n" send "pet bhb\n"
expectit "can't get near the wild beast to pet it" expectit "can't get near"
send "get hairy beast\n" send "get hairy beast\n"
expectit "beast is far larger than you." expectit "beast is far larger than you."
send "feed beast\n"
expectit "doesn't appear interested in anything you have."
} }
timeout { timeout {
if {$phase == "night"} { if {$phase == "night"} {
@ -387,7 +411,7 @@ send "look south\n"
expectit "Looks like the river spreads into a marsh." expectit "Looks like the river spreads into a marsh."
send "south\n" send "south\n"
expectit "perched on three stilts" expectit "perched on three"
send "look north\n" send "look north\n"
expectit "The meadow to the north looks easier to walk around." expectit "The meadow to the north looks easier to walk around."
@ -410,9 +434,6 @@ expectit "The pixies ignore you as their coreography keeps them focused on their
send "look grass\n" send "look grass\n"
expectit "Guess this kind of grass doesn't mind the wet environment." expectit "Guess this kind of grass doesn't mind the wet environment."
send "look mud\n"
expectit "Pretty brown and sticky."
send "hut\n" send "hut\n"
expectit "the hut scurries away" expectit "the hut scurries away"
@ -434,6 +455,13 @@ set timeout 90
expectit "The hut, straining against its bounds, finally breaks free" expectit "The hut, straining against its bounds, finally breaks free"
set timeout 30 set timeout 30
send "look river\n"
expectit "A muddy, almost stagnant river."
# The 'get water' should work, but issues with aliases...
send "get river\n"
expectit "Slippery things, those rivers."
send "say Hello there, big bird.\n" send "say Hello there, big bird.\n"
expectit "heron" expectit "heron"
@ -446,8 +474,7 @@ expectit "Extremely tall, white reeds tipped with white gooey clumps."
send "get reeds\n" send "get reeds\n"
expectit "You pluck and shape a ten-foot pole from a marsh reed" expectit "You pluck and shape a ten-foot pole from a marsh reed"
# send "look\n" dont_expect "You notice" "pixie dust"
# dont_expect "You notice" "pixie dust"
send "use rope on hut\n" send "use rope on hut\n"
expectit "Something tells you that the rope won't last for long." expectit "Something tells you that the rope won't last for long."
@ -455,6 +482,9 @@ expectit "Something tells you that the rope won't last for long."
send "hut\n" send "hut\n"
expectit "Homey Hut" expectit "Homey Hut"
send "look jar\n"
expect -re "You look at one.*labeled"
dont_expect "You notice" "skull" dont_expect "You notice" "skull"
send "look skull\n" send "look skull\n"
@ -506,9 +536,28 @@ expectit "Frog Meadow"
send "west\n" send "west\n"
expectit "Grove of the Matriarchs" expectit "Grove of the Matriarchs"
send "look south\n"
expectit "You see a dock on a lavender sea"
send "south\n" send "south\n"
expectit "Lazy Dock" expectit "Lazy Dock"
send "look north\n"
expectit "This path leads into the forest of collosal trees."
send "look boat\n"
expectit "The mastless ship looks like a giant leaf. Wonder if it comes to shore?"
send "look waves\n"
expectit "Despite the inclement weather, the waves ripple softly against the shore."
send "look sea\n"
expectit "A gently waving sea."
# This should be 'get water'!
send "get sea\n"
expectit "You can only hold the sea in your heart."
send "look chair\n" send "look chair\n"
expectit "A cushioned wood chair of craftsmanship" expectit "A cushioned wood chair of craftsmanship"
@ -557,6 +606,54 @@ expectit "I think the swamp is called"
send "hint horn\n" send "hint horn\n"
expectit "The mystical south wind gathers the mystical mist from the sea" expectit "The mystical south wind gathers the mystical mist from the sea"
# Currently at Lazy Dock
send "look south\n"
expectit "You see a shack down along the sandy shore."
send "south\n"
expectit "Shore"
send "look north\n"
expectit "The sandy shore to the north ends at a dock, jutting into the lavender sea."
send "look waves\n"
expectit "Despite the inclement weather, the waves ripple gently against the shore."
send "look lavender sea\n"
expectit "you see sailing the sea in the distance?"
send "look boat\n"
expectit "The mastless ship looks like a giant leaf. Wonder if it comes to shore?"
send "look shack\n"
expectit "Standing crookedly at the edge of the sandy shore, this shack's weathered planks"
dont_expect "You notice" "sand"
send "look sand\n"
expect -re "You notice.*sand"
send "get sand\n"
expectit "You fill a small bag of sand"
send "look sign\n"
expectit "A hand-painted sign with beautiful calligraphy reads"
send "read sign\n"
expectit "For Rent. See Dabbler for details."
send "get sign\n"
expectit "You can't get that."
send "look door\n"
expectit "Barnacle encrusted door with rusty irons bands and a comically large padlock."
#
send "door\n"
expectit "The door is obviously locked."
send "north\n"
expectit "Lazy Dock"
send "north\n" send "north\n"
expectit "Grove of the Matriarchs" expectit "Grove of the Matriarchs"
@ -573,13 +670,13 @@ send "look tree\n"
expectit "The trees in this forest are massive, but a smaller tree has a red door." expectit "The trees in this forest are massive, but a smaller tree has a red door."
send "look bridge\n" send "look bridge\n"
expectit "bridge leads over a tiny stream" expectit "bridge leads over a tiny"
send "look cabbage\n" send "look cabbage\n"
expectit "Large glossy green leaves with big yellow flowers that looks like cobras in drag" expectit "Large glossy green leaves with big yellow flowers that looks like cobras in drag"
send "look ferns\n" send "look ferns\n"
expectit "Mostly sword ferns interrupted by Maiden Hairs that sing to the stream." expectit "Sword ferns rattling sabers against the wards from the Maiden Hairs' flailing their fronds."
send "pick berries\n" send "pick berries\n"
expectit "You pick" expectit "You pick"
@ -591,6 +688,13 @@ expectit "You pick"
send "eat berry\n" send "eat berry\n"
send "look stream\n"
expectit "A small stream, almost hidden behind the ferns and brambleberry bushes"
# send "get water\n"
send "get stream\n"
expectit "Seriously? You can't get that."
send "knock\n" send "knock\n"
expectit "You grab the ring" expectit "You grab the ring"
@ -614,7 +718,7 @@ expectit "So try to talk to it."
send "inside\n" send "inside\n"
expectit "Cozy House" expectit "Cozy House"
expectit "Oddly angled shelves with books and knickknackery" expectit "The subtle smell of wood smoke, incense and fresh-baked scones"
send "look tapestry\n" send "look tapestry\n"
expectit "The muted colors of the tapestry" expectit "The muted colors of the tapestry"
@ -641,18 +745,21 @@ send "get wood\n"
expectit "You get a small log from the wood rack." expectit "You get a small log from the wood rack."
send "feed log to fire\n" send "feed log to fire\n"
expectit "You give a log to fireplace." expect "You start a fire"
send "look trinkets\n" send "look trinkets\n"
expectit "."
# First time, we get the full description:
send "look books\n" send "look books\n"
expectit "Books of different sizes and colors." expectit "Shelves at various angles embellish the walls of this small, cozy room."
# Second time, we get a shorter message:
send "look book\n" send "look book\n"
expect -re "You see.*book" expect -re "You .*book.*titled"
send "get book\n" send "get book\n"
expectit "You pick up the book." expectit "You pick up the book"
send "read book\n" send "read book\n"
expect -re "You.*open your book" expect -re "You.*open your book"
@ -667,7 +774,10 @@ send "hint\n"
expectit "You are in a cozy and casual place" expectit "You are in a cozy and casual place"
send "pet beastie\n" send "pet beastie\n"
expectit "While it doesn't stop" expectit "beastie"
send "feed beastie\n"
expectit "Wee beastie doesn't appear interested in anything you have."
send "kitchen\n" send "kitchen\n"
expectit "Cramped Kitchen" expectit "Cramped Kitchen"
@ -706,6 +816,242 @@ expect -re "You empty your teacup"
send "hint\n" send "hint\n"
expectit "Grab yourself some breakfast" expectit "Grab yourself some breakfast"
send "leave\n"
expectit "Cozy House"
dont_expect "You notice" "sconce"
send "look sconce\n"
expectit "A black iron sconce holding a single"
send "look\n"
expect -re "You notice.*sconce"
send "get candle\n"
expectit "You take the candle, but another magically appears in its place"
send "pull sconce\n"
expectit "You hear a click, and the bookcase next to the candle swings forward revealing"
send "look\n"
expect -re "Exits:.*stairs behind bookcase"
send "look stairs behind bookcase\n"
expectit "Behind the protruding bookcase, you see a staircase leading down into the darkness."
send "down\n"
expectit "Secret Room"
send "look stairs\n"
expectit "Stone steps leading back to the surface."
send "look table\n"
expectit "Made from a polish black wood, etched with intricate runes that shimmer faintly in the candlelight."
send "look alchemical equipment\n"
expectit "all surround a black"
send "look mortar and pestle\n"
expectit "An obsidian mortar, its surface smooth and cool to the touch."
send "look vials\n"
expectit "Scattered across a small shelf, an array of empty glass vials."
send "look phials\n"
expectit "Delicate crystal phials, each shaped like a teardrop, attach to a wrought iron rack."
send "look tools\n"
expectit "A set of finely crafted tools lies neatly arranged on a velvet cloth"
send "look jar\n"
expect -re "You look at one.*labeled"
#
send "look jar\n"
expect -re "You look at one.*labeled"
send "look stool\n"
expectit "A place to sit while synthesizing experiments."
send "sit\n"
expectit "You sit on the stool."
send "stand\n"
expectit "You stand up"
send "get stool\n"
expectit "Stop trying to steal everything not nailed down."
send "look grimoire\n"
expectit "An old brown book where even the cover has seen considerable wear with stains and scratches in the leather."
send "read book\n"
expectit "Undoing the brass clasp that bind the old leather book"
send "get book\n"
expectit "The book is chained to the table."
send "look cauldron\n"
expectit "A small, cast-iron cauldron sits on an iron stand, its interior stained from countless brews."
send "get cauldron\n"
expectit "You can't get that."
send "look shelf\n"
expectit "Cluttered with some empty brown"
send "get bottle\n"
expectit "You pick up a bottle."
send "look imp\n"
expectit "Peculiar little fellow gives you are quizical look from its roost"
send "say Hello there, little guy.\n"
expect -re "Imp"
# We left our tester in the Secret room, so ...
send "leave\n"
expectit "Cozy House"
send "look up stairs\n"
expectit "Ornate black irons banister outline the thick wood planks that form steps leading to some lofty alcove."
send "up\n"
expectit "Bedroom"
send "look down stairs\n"
expectit "Ornate black irons banister outline the thick wood planks that form steps leading down to living space below."
send "look slippers\n"
expectit "Red-leather and worn with an ornate tassel on top."
send "get slippers\n"
expectit "You pick up a pair slippers."
# Make sure we start this test with a closed wardrobe:
send "close wardrobe\n"
expectit "closed."
send "look wardrobe\n"
expectit "While resting on the floor, this wardrobe scratches the ceiling. Large furniture, or perhaps a small room?"
send "get wardrobe\n"
expectit "The wardrobe is way too big to lift."
send "open wardrobe\n"
expectit "You open the wardrobe, revealing the cloaks, jackets, and"
send "look through the wardrobe\n"
expectit "Behind the cloaks and jackets, you see long, green needles from pine trees, and beyond that, a clearing!"
send "wardrobe\n"
expectit "Prairie"
send "look copse\n"
expectit "A copse of trees covers the top of the knoll."
send "look knoll\n"
expectit "The land stretches and buckles in small rolls."
send "look lantern\n"
expectit "Curious iron worked lantern sways in the subtle breeze."
send "look campfire\n"
expectit "Only a thin wisp of smoke escapes to the skies; fragrating the air."
send "look figure\n"
expectit "A curious figure wearing dark robes and a gleaming white skull of a mare."
send "look ears\n"
expectit "They look real, and twitch as if alive."
puts "Waiting to get a pipe as a gift."
set timeout 240
expectit "gives you a pipe"
set timeout 20
send "copse\n"
expectit "Bedroom"
send "close wardrobe\n"
expectit "The wardrobe door is closed."
send "down\n"
expectit "Cozy House"
send "leave\n"
expectit "Grotto"
send "east\n"
expectit "Grove of the Matriarchs"
send "climb boulder\n"
expectit "Boulder Top"
send "look patch of mushrooms\n"
expectit "A vibrant patch of mushrooms bursts forth like a painter's palette, each cap shimmering with iridescent hues of violet, emerald, and gold"
send "get mushroom\n"
expectit "You harvest a gigglecap mushroom."
send "climb down\n"
expectit "Grove of the Matriarchs"
send "east\n"
expectit "Frog Meadow"
send "look tickleweed\n"
expectit "Patches of this vivid grass vibrates as if giggling."
send "get tickleweed\n"
expectit "You harvest a bunch of tickleweed."
send "fill bottle\n"
expectit "you fill it with sparkling water"
# Head to secret lab...
send "west\n"
expectit "Grove of the Matriarchs"
send "west\n"
expectit "Grotto"
send "red door\n"
expectit "Cozy House"
send "pull sconce\n"
expectit "You hear a click"
send "down stairs\n"
expectit "Secret Room"
send "add mushroom\n"
expectit "You add gigglecap mushroom to black cauldron."
send "add tickleweed\n"
expectit "You add bunch of tickleweed to black cauldron."
send "add bottle\n"
expectit "You pour the fizzy water from your bottle into the black cauldron."
send "create\n"
expectit "making it ready"
send "bottle\n"
expectit "You fill a small vial with your stew."
send "empty\n"
# Since almost anything can be written, we look for a period
expectit "."
send "empty\n"
expectit "The black cauldron is already empty."
send "up\n"
expectit "Cozy House"
send "give laughing potion to gnome\n"
expectit "You give a laughing potion to Dabbler."
# Close the log file # Close the log file
log_file log_file

View file

@ -273,7 +273,7 @@ py timed_script = evennia.create_script(key="Create Sticks",
# [[file:../../../projects/mud.org::*Lower Vines][Lower Vines:5]] # [[file:../../../projects/mud.org::*Lower Vines][Lower Vines:5]]
@set vines/pull_msg = "You pull the vines, but don't let go. Perhaps you could detach them if you were on |wtop|n of the |Yboulder|n?" @set vines/pull_msg = "You pull the vines, but they don't let go. Perhaps you could detach them if you were on |wtop|n of the |Yboulder|n?"
# #
@set vines/push_msg = "That doesn't seem to do much." @set vines/push_msg = "That doesn't seem to do much."
# Lower Vines:5 ends here # Lower Vines:5 ends here
@ -304,27 +304,19 @@ py timed_script = evennia.create_script(key="Create Sticks",
# Describe the climb down:
# [[file:../../../projects/mud.org::*Top of Boulder][Top of Boulder:5]]
@name climb = climb down;climb;down
# Top of Boulder:5 ends here
# And a description of the climb: # And a description of the climb:
# [[file:../../../projects/mud.org::*Top of Boulder][Top of Boulder:6]] # [[file:../../../projects/mud.org::*Top of Boulder][Top of Boulder:5]]
@desc climb = The climb seemed easy, but you're not sure you can handle the footholds going the other way around. @desc climb = The climb seemed easy, but you're not sure you can handle the footholds going the other way around.
# Top of Boulder:6 ends here # Top of Boulder:5 ends here
# And describe the journey: # And describe the journey:
# [[file:../../../projects/mud.org::*Top of Boulder][Top of Boulder:7]] # [[file:../../../projects/mud.org::*Top of Boulder][Top of Boulder:6]]
@set climb/traverse_msg = "You crawl backwards, feeling with your foot for a hold. Got it! Then another one...hoping the vines and the moss' rhizoids hold..." @set climb/traverse_msg = "You crawl backwards, feeling with your foot for a hold. Got it! Then another one...hoping the vines and the moss' rhizoids hold..."
# Top of Boulder:7 ends here # Top of Boulder:6 ends here
# Moss # Moss
# Lets make a nice spot to sit down on: # Lets make a nice spot to sit down on:
@ -966,7 +958,7 @@ py timed_script = evennia.create_script(key="Create Sticks",
# [[file:../../../projects/mud.org::*Beast][Beast:15]] # [[file:../../../projects/mud.org::*Beast][Beast:15]]
@set beast/scared_actions = "A shadow hovers at the edge of the meadow.." @set beast/scared_actions = "A tremendously large and hairy beast attempts to nervously (and almost comically) hide"
# Beast:15 ends here # Beast:15 ends here
@ -1128,6 +1120,28 @@ py timed_script = evennia.create_script(key="Create Sticks",
@detail mud = Pretty brown and sticky. @detail mud = Pretty brown and sticky.
# Mellow Marsh:15 ends here # Mellow Marsh:15 ends here
# Muddy Water
# As a future idea of making potions, we can collect /muddy water/, which needs to be turned to wine.
# [[file:../../../projects/mud.org::*Muddy Water][Muddy Water:1]]
# @teleport/quiet mp08
#
@create/drop muddy river;river;stream;water: typeclasses.drinkables.Water
#
@lock river = get:false()
#
@set river/get_err_msg = "Slippery things, those rivers. Seems you would need |gfill|n a |gbottle|n, or at least a cup to hold the muddy water."
#
@desc river = A muddy, almost stagnant river. Smells like a fecund stew of moist dirt and decomposing swamp herbage.
#
@set river/fill_name = "muddy water"
#
@set river/fill_desc = "muddy water from the marsh."
#
@set river/fill_msgs = ["$You() $conj(<< get ^ kneel >>) down, and $conj(fill) $pron(your) {2} with the muddy water."]
# Muddy Water:1 ends here
# Purple Heron # Purple Heron
# Create a puppet of the bird hunting frogs and pixies. :-D # Create a puppet of the bird hunting frogs and pixies. :-D
@ -1467,9 +1481,9 @@ py timed_script = evennia.create_script(key="Create Sticks",
# #
@set skull/get_err_msg = "It appears firmly attached to the wall where it hangs." @set skull/get_err_msg = "It appears firmly attached to the wall where it hangs."
# #
@set skull/hidden_tag = "hidden_skull" @set skull/hidden_tag = "hidden_wolf_skull"
# #
@lock skull = view:tag(hidden_skull) @lock skull = view:tag(hidden_wolf_skull)
# Horned Wolf Skull:1 ends here # Horned Wolf Skull:1 ends here
# Demon Carving # Demon Carving
@ -1485,11 +1499,9 @@ py timed_script = evennia.create_script(key="Create Sticks",
# #
@set carving/get_err_msg = "As you reach for the carving, it promptly runs away." @set carving/get_err_msg = "As you reach for the carving, it promptly runs away."
# #
@set carving/hidden_tag = "hidden_carving" @set carving/hidden_tag = "hidden_demon_carving"
# #
@set carving/hidden_tag = "hidden_carving" @lock carving = view:tag(hidden_demon_carving)
#
@lock carving = view:tag(hidden_carving)
# Demon Carving:1 ends here # Demon Carving:1 ends here
# Reed Sculpture # Reed Sculpture
@ -1507,9 +1519,9 @@ py timed_script = evennia.create_script(key="Create Sticks",
# #
@detail tie = A blue ribbon with gold embroidery that spells: B U I O @detail tie = A blue ribbon with gold embroidery that spells: B U I O
# #
@set reed/hidden_tag = "hidden_reed" @set reed/hidden_tag = "hidden_reed_sculpture"
# #
@lock reed = view:tag(hidden_reed) @lock reed = view:tag(hidden_reed_sculpture)
# Reed Sculpture:1 ends here # Reed Sculpture:1 ends here
@ -1656,83 +1668,105 @@ py bt = self.search('old lady'); bt.db.pose = 'playing with a deck of cards'
@set old lady/arrive = "45 ;; gm You hear someone in the loft up the stairs stirring in their bed. ;; 55 ;; pose looking confused ;; emote The /me wakes up and says, \"What's all this then?\" ;; 5 ;; say Who are you, dearie? ;; 10 ;; say I'd think I have intruders in my home! ;; 1 ;; emote grabs her broom and with a sweeping motion from the stairs, you find yourself flying out the door! ;; teleport {3} = Mellow Marsh ;; 3 ;; gm/#457 You hear a voice coming from the hut, \"Scat!\" ;; pose sleeping in a bed up in the loft" @set old lady/arrive = "45 ;; gm You hear someone in the loft up the stairs stirring in their bed. ;; 55 ;; pose looking confused ;; emote The /me wakes up and says, \"What's all this then?\" ;; 5 ;; say Who are you, dearie? ;; 10 ;; say I'd think I have intruders in my home! ;; 1 ;; emote grabs her broom and with a sweeping motion from the stairs, you find yourself flying out the door! ;; teleport {3} = Mellow Marsh ;; 3 ;; gm/#457 You hear a voice coming from the hut, \"Scat!\" ;; pose sleeping in a bed up in the loft"
# Trampoli the Witch:8 ends here # Trampoli the Witch:8 ends here
# The Dock # Lazy Dock
# The dock leads out into a strange sea. The break in the trees lets you see the sky. Looks like a nice place to relax. # The dock leads out into a strange sea. The break in the trees lets you see the sky. Looks like a nice place to relax.
# Return to the Forest: # Return to the Forest:
# [[file:../../../projects/mud.org::*The Dock][The Dock:1]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:1]]
@teleport mp01 @teleport mp01
# The Dock:1 ends here # Lazy Dock:1 ends here
# And tunnel to the dock: # And tunnel to the dock:
# [[file:../../../projects/mud.org::*The Dock][The Dock:2]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:2]]
@dig Lazy Dock;mp06 :typeclasses.rooms_weather.TimeWeatherRoom = south to dock;south;s,north to forest;north;n;footpath @dig Lazy Dock;mp06 :typeclasses.rooms_weather.TimeWeatherRoom = south to dock;south;s,north to forest;north;n;footpath
# The Dock:2 ends here # Lazy Dock:2 ends here
# With a mesage about leaving the trees so that I dont have to repeat that in the room description: # With a mesage about leaving the trees so that I dont have to repeat that in the room description:
# [[file:../../../projects/mud.org::*The Dock][The Dock:3]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:3]]
@set south/traverse_msg = "You follow a path down and step out from under giant trees to see the sky." @set south/traverse_msg = "You follow a path down and step out from under giant trees to see the sky."
# The Dock:3 ends here # Lazy Dock:3 ends here
# And a description: # And a description:
# [[file:../../../projects/mud.org::*The Dock][The Dock:4]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:4]]
@desc south = You see a dock on a lavender sea... Is that a comfortable-looking chair you can |gsit|n on? @desc south = You see a dock on a lavender sea... Is that a comfortable-looking chair you can |gsit|n on?
# The Dock:4 ends here # Lazy Dock:4 ends here
# And move ourselves there: # And move ourselves there:
# [[file:../../../projects/mud.org::*The Dock][The Dock:5]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:5]]
@teleport mp06 @teleport mp06
# The Dock:5 ends here # Lazy Dock:5 ends here
# And describe this. # And describe this.
# [[file:../../../projects/mud.org::*The Dock][The Dock:6]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:6]]
@desc here = The dock you stand on juts into a |Ysea|n the color of |Ylavender flowers|n. Mesmerizing and calming from the way the sound of the |Ywaves|n lap along the |Yshore|n. @desc here = The dock you stand on juts into a |Ysea|n the color of |Ylavender flowers|n. Mesmerizing and calming from the way the sound of the |Ywaves|n lap along the |Yshore|n.
Someone has set a nice |Ychair|n for viewing. Someone has set a nice |Ychair|n for viewing.
# The Dock:6 ends here # Lazy Dock:6 ends here
# And details? # And details?
# [[file:../../../projects/mud.org::*The Dock][The Dock:7]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:7]]
@detail waves = Despite the inclement weather, the waves ripple softly against the shore. Seems nice for fishing. @detail waves = Despite the inclement weather, the waves ripple softly against the shore. Seems nice for fishing.
# #
@detail lavender;flowers;flower = The water is the |wcolor|n of lavender, not actually lavender. Hrm. Could it possibly be |wlavender tea|n? @detail boat;ship = The mastless ship looks like a giant leaf. Wonder if it comes to shore?
# #
@detail shore = The roots of trees make most of the bay's shoreline. @detail lavender;flowers;flower;lavender flowers = The water is the |wcolor|n of lavender, not actually lavender. Hrm. Could it possibly be |wlavender tea|n?
# The Dock:7 ends here # Lazy Dock:7 ends here
# And describe the walk back into the forest: # And describe the walk back into the forest:
# [[file:../../../projects/mud.org::*The Dock][The Dock:8]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:8]]
@set north/traverse_msg = "You walk up a path and back into the forest of giant trees." @set north/traverse_msg = "You walk up a path and back into the forest of giant trees."
# The Dock:8 ends here # Lazy Dock:8 ends here
# And a description: # And a description:
# [[file:../../../projects/mud.org::*The Dock][The Dock:9]] # [[file:../../../projects/mud.org::*Lazy Dock][Lazy Dock:9]]
@desc north = This path leads into the forest of collosal trees. @desc north = This path leads into the forest of collosal trees.
# The Dock:9 ends here # Lazy Dock:9 ends here
# Lavender Sea
# Well get ready for making potions by allowing one to collect water from _all_ the places, like the salty sea:
# [[file:../../../projects/mud.org::*Lavender Sea][Lavender Sea:1]]
# @teleport/quiet mp06
#
@create/drop lavender sea;sea;water;bay: typeclasses.drinkables.Water
#
@desc sea = A gently waving sea. Too bad the shore doesn't respond with a greeting of its own. Is that a |Yboat|n you see sailing in the distance?
#
@lock sea = get:false()
#
@set sea/get_err_msg = "You can only hold the sea in your heart. Perhaps a bottle, or at least a cup, could hold the salty water."
#
@set sea/fill_name = "salt water"
#
@set sea/fill_desc = "salty water with a purple hue."
#
@set sea/fill_msgs = ["$You() $conj(reach) down from the dock, and $conj(fill) $pron(your) {2} with the << salty ^ lavender ^ fragrant >> water."]
# Lavender Sea:1 ends here
# Chair # Chair
# A nice chair to sit on the dock by the bay, watching the clouds as they drift away. # A nice chair to sit on the dock by the bay, watching the clouds as they drift away.
@ -2015,7 +2049,7 @@ Someone has set a nice |Ychair|n for viewing.
# [[file:../../../projects/mud.org::*Spring Water][Spring Water:1]] # [[file:../../../projects/mud.org::*Spring Water][Spring Water:1]]
# @teleport/quiet mp04 # @teleport/quiet mp04
# #
@create/drop stream;water: typeclasses.drinkables.Water @create/drop stream of spring water;stream;spring;water: typeclasses.drinkables.Water
# #
@lock stream = get:false() @lock stream = get:false()
# #
@ -2163,13 +2197,13 @@ Someone has set a nice |Ychair|n for viewing.
@teleport/quiet ring = knocker @teleport/quiet ring = knocker
# Ring:7 ends here # Ring:7 ends here
# Cozy Tea House # Cozy House
# Add the Python /special-ness/ for [[file:~/src/moss-n-puddles/typeclasses/rooms.py::class DabblersRoom(Room):][this room]]: # Add the Python /special-ness/ for [[file:~/src/moss-n-puddles/typeclasses/rooms.py::class DabblersRoom(Room):][this room]]:
# [[file:../../../projects/mud.org::*Cozy Tea House][Cozy Tea House:1]] # [[file:../../../projects/mud.org::*Cozy House][Cozy House:1]]
@dig Cozy House;mp03: typeclasses.rooms.DabblersRoom = red door;door;inside,outside;leave @dig Cozy House;mp03: typeclasses.rooms.DabblersRoom = red door;door;inside,outside;leave
# Cozy Tea House:1 ends here # Cozy House:1 ends here
# Red Door # Red Door
# The door description should match the artwork on the website: # The door description should match the artwork on the website:
@ -2461,43 +2495,29 @@ Someone has set a nice |Ychair|n for viewing.
drop ball drop ball
# Magic 8 Ball:3 ends here # Magic 8 Ball:3 ends here
# Books # Bookshelf
# We mentioned shelves of books: # Since we mentioned shelves of books, we should create a Producer that makes a random book.
# [[file:../../../projects/mud.org::*Books][Books:1]]
@detail shelves;bookshelf;bookshelves = Shelves at various angles embellish the walls of this small, cozy room. Leatherbound books weigh each shelf, while some stacks of books support other shelves. Dabbler has decorated some shelves with odd trinkets.
# Books:1 ends here
# [[file:../../../projects/mud.org::*Bookshelf][Bookshelf:1]]
# This should be an object of “books”, but looking should pull up a random list of books. @create/drop number of bookshelves;bookshelf;shelves;bookcase;books;book:typeclasses.readables.Bookshelf
# Bookshelf:1 ends here
# [[file:../../../projects/mud.org::*Books][Books:2]]
@create/drop books:typeclasses.readables.Books
# Books:2 ends here
# I start with the name, =books=, but when we look in the room, I want to see /collection/:
# [[file:../../../projects/mud.org::*Books][Books:3]]
@name books = collection of books;books
# Books:3 ends here
# With a good description: # With a good description:
# [[file:../../../projects/mud.org::*Books][Books:4]] # [[file:../../../projects/mud.org::*Bookshelf][Bookshelf:2]]
@desc books = Books of different sizes and colors. So many books. Perhaps you want to |glook|n at a single |gbook|n at random? @desc books = Shelves at various angles embellish the walls of this small, cozy room. Leatherbound books weigh down each shelf, while some stacks of books support other shelves.
# Books:4 ends here # Bookshelf:2 ends here
# Chairs # Chairs
# And [[file:~/src/moss-n-puddles/typeclasses/sittables.py::class Sittables(Sittable):][the chairs]] is a /plural/ location to sit, allowing anyone to sit down. # And [[file:~/src/moss-n-puddles/typeclasses/sittables.py::class Sittables(Sittable):][the chairs]] is a /plural/ location to sit, allowing anyone to sit down.
# [[file:../../../projects/mud.org::*Chairs][Chairs:1]] # [[file:../../../projects/mud.org::*Chairs][Chairs:1]]
@create/drop chairs:typeclasses.sittables.Sittables @create/drop couple overstuffed chairs:typeclasses.sittables.Sittables
# Chairs:1 ends here # Chairs:1 ends here
@ -2720,7 +2740,7 @@ pose gnome/default = smoking his pipe
# [[file:../../../projects/mud.org::*Stoat][Stoat:4]] # [[file:../../../projects/mud.org::*Stoat][Stoat:4]]
@set stoat/active_amount = 15 @set stoat/active_amount = 8
# Stoat:4 ends here # Stoat:4 ends here
@ -2783,7 +2803,7 @@ pose gnome/default = smoking his pipe
# [[file:../../../projects/mud.org::*Stoat][Stoat:11]] # [[file:../../../projects/mud.org::*Stoat][Stoat:11]]
@set stoat/interested_msg = "<< Currently ^ It is >> curled into a ball on {1} lap." @set stoat/interested_msg = "<< Currently ^ It is >> curled into a ball on {0} lap."
# Stoat:11 ends here # Stoat:11 ends here
@ -2801,7 +2821,7 @@ pose gnome/default = smoking his pipe
# [[file:../../../projects/mud.org::*Stoat][Stoat:13]] # [[file:../../../projects/mud.org::*Stoat][Stoat:13]]
@set stoat/interested_actions = "The << sleepy ^ wee >> beastie << on {1} lap ^ >> let's out an adorable yawn. ;; The << sleepy ^ wee >> beastie << on {1} lap ^ >> uncurls itself, stretches, and recurls again. ;; {0} pets the << sleepy ^ wee >> beastie << on |p lap ^ >> as it snuggles << close ^ >>. ;; You hear a deep purring sounds from the << sleepy ^ wee >> beastie << on {1} lap ^ >>. ;; The << sleepy ^ wee >> beastie twitches in its sleep, as if playing with dream toys." @set stoat/interested_actions = "The << sleepy ^ wee >> beastie << on {0} lap ^ >> let's out an adorable yawn. ;; The << sleepy ^ wee >> beastie << on {0} lap ^ >> uncurls itself, stretches, and recurls again. ;; {0} pets the << sleepy ^ wee >> beastie << on |p lap ^ >> as it snuggles << close ^ >>. ;; You hear a deep purring sounds from the << sleepy ^ wee >> beastie << on {0} lap ^ >>. ;; The << sleepy ^ wee >> beastie twitches in its sleep, as if playing with dream toys."
# Stoat:13 ends here # Stoat:13 ends here
@ -2810,7 +2830,7 @@ pose gnome/default = smoking his pipe
# [[file:../../../projects/mud.org::*Stoat][Stoat:14]] # [[file:../../../projects/mud.org::*Stoat][Stoat:14]]
@set stoat/friendly_msg = "<< Currently ^ It is >> curled up and purring on {1} lap." @set stoat/friendly_msg = "<< Currently ^ It is >> curled up and purring on {0} lap."
# Stoat:14 ends here # Stoat:14 ends here
@ -2819,7 +2839,7 @@ pose gnome/default = smoking his pipe
# [[file:../../../projects/mud.org::*Stoat][Stoat:15]] # [[file:../../../projects/mud.org::*Stoat][Stoat:15]]
@set stoat/pet_friendly_response = "The << wee ^ >> beastie adorably moves its head into $your() pets. ;; $You() << rub ^ pet >> the stubby but soft ears of the << wee ^ >> beastie, as it lets out a little purr. ;; The << wee ^ >> beastie rolls onto its back while $you() rub its tummy. It lets out a little purr. ;; $You() << scratch ^ massage >> the soft << back ^ rump >> of the << wee ^ >> beastie. It wriggles around trying to get the most of this attention." @set stoat/pet_friendly_response = "The << wee ^ >> beastie adorably moves its head into $your() pets. ;; $You() << $conj(rub) ^ $conj(pet) >> the stubby but soft ears of the << wee ^ >> beastie, as it lets out a little purr. ;; The << wee ^ >> beastie rolls onto its back while $you() $conj(rub) its tummy. It lets out a little purr. ;; $You() << $conj(scratch) ^ $conj(massage) >> the soft << back ^ rump >> of the << wee ^ >> beastie. It wriggles around trying to get the most of this attention."
# Stoat:15 ends here # Stoat:15 ends here
@ -2828,7 +2848,7 @@ pose gnome/default = smoking his pipe
# [[file:../../../projects/mud.org::*Stoat][Stoat:16]] # [[file:../../../projects/mud.org::*Stoat][Stoat:16]]
@set stoat/friendly_actions = "The << sleepy ^ wee >> beastie << on {1} lap ^ >> let's out an adorable yawn. ;; The << sleepy ^ wee >> beastie << on {1} lap ^ >> uncurls itself, stretches, and recurls again. ;; {0} pets the << sleepy ^ wee >> beastie << on |p lap ^ >> as it snuggles << close ^ >>. ;; You hear a deep purring sounds from the << sleepy ^ wee >> beastie << on {1} lap ^ >>. ;; The << sleepy ^ wee >> beastie twitches in its sleep, as if playing with dream toys." @set stoat/friendly_actions = "The << sleepy ^ wee >> beastie << on the lap of {0} ^ >> let's out an adorable yawn. ;; The << sleepy ^ wee >> beastie << on the lap of {0} ^ >> uncurls itself, stretches, and recurls again. ;; {0} pets the << sleepy ^ wee >> beastie << on |p lap ^ >> as it snuggles << close ^ >>. ;; You hear a deep purring sounds from the << sleepy ^ wee >> beastie << on the lap of {0} ^ >>. ;; The << sleepy ^ wee >> beastie twitches in its sleep, as if playing with dream toys."
# Stoat:16 ends here # Stoat:16 ends here
@ -2985,7 +3005,7 @@ py here.search("cabinet").do_bake()
# Sconce:1 ends here # Sconce:1 ends here
# [[file:../../../projects/mud.org::*Sconce][Sconce:2]] # [[file:../../../projects/mud.org::*Sconce][Sconce:2]]
@desc sconce = A black iron sconce holding a single lit candle. On closer examination, the bottom of this fixture appears to have a hinge? @desc sconce = A black iron sconce holding a single lit |Ycandle|n. On closer examination, the bottom of this fixture appears to have a hinge?
# Sconce:2 ends here # Sconce:2 ends here
@ -3095,67 +3115,36 @@ py here.search("cabinet").do_bake()
# Are the equipment stuff we could =use=? # Until we decide if we want to do something with the table:
# [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:3]] # [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:3]]
@detail equipment;alchemical = A |Ymortar|n and |Ypestle|n, |Yvials|n, crystal |Yphials|n, |Yjars|n, and |Ytools|n all surround a black |Ycauldron|n. @detail table = Made from a polish black wood, etched with intricate runes that shimmer faintly in the candlelight.
# Inside the Secret Room:3 ends here # Inside the Secret Room:3 ends here
# Are the equipment stuff we could =use=?
# [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:4]] # [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:4]]
@detail mortar;pestle;mortar and pestle = An obsidian mortar, its surface smooth and cool to the touch. Beside it, a pestle carved from a single piece of ancient bone, adorned with carvings of arcane symbols. @detail equipment;alchemical;alchemical equipment = A |Ymortar|n and |Ypestle|n, |Yvials|n, crystal |Yphials|n, |Yjars|n, and |Ytools|n all surround a black |Ycauldron|n.
# Inside the Secret Room:4 ends here # Inside the Secret Room:4 ends here
# [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:5]] # [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:5]]
@detail vials = Scattered across a small shelf, an array of empty glass vials. Perhaps you could fill these with potions yet to be created? @detail mortar;pestle;mortar and pestle = An obsidian mortar, its surface smooth and cool to the touch. Beside it, a pestle carved from a single piece of ancient bone, adorned with carvings of arcane symbols.
# Inside the Secret Room:5 ends here # Inside the Secret Room:5 ends here
# [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:6]] # [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:6]]
@detail phials = Delicate crystal phials, each shaped like a teardrop, attach to a wrought iron rack. Each contain vibrant liquids that swirl with colors not found in nature. Magically sealed, these phials may store volatile substances, which require special containment to prevent their magical properties from dissipating. @detail vials = Scattered across a small shelf, an array of empty glass vials. Perhaps you could fill these with potions yet to be created?
# Inside the Secret Room:6 ends here # Inside the Secret Room:6 ends here
# Can jars be a producer that returns a random jar with a “content”?
# 1. Glimmering Dust A jar filled with fine, shimmering powder that sparkles like a thousand stars.
# 2. Dragon Blood A deep red liquid that swirls with hints of gold, resembling liquid rubies.
# 3. Mandrake Root A twisted, gnarled root with a faintly green hue, nestled in a jar of dark soil.
# 4. Moonstone Crystals Iridescent stones that glow softly in the dark, casting a gentle light.
# 5. Bottled Lightning A swirling blue liquid that crackles with energy, contained within a glass jar.
# 6. Enchanted Honey Thick, golden honey that glimmers with tiny flecks of light, like captured sunlight.
# 7. Dragon Scale Powder A fine, metallic powder that shifts colors with the light, reminiscent of dragon scales.
# 8. Mermaid Tears Tiny, glistening droplets that resemble diamonds, each one capturing a moment of sorrow.
# 9. Essence of Shadow A dark, swirling liquid that seems to absorb light, creating an eerie atmosphere.
# 10. Eye of Newt Filled with many small eyeballs.
# 11. Cursed Bone Shards Jagged pieces of bone, each one etched with strange symbols and glowing faintly.
# 12. Starflower Petals Delicate, translucent petals that shimmer like the night sky, layered in a glass jar.
# 13. Whispering Seeds Tiny, dark seeds that seem to rustle softly when the jar is moved, as if alive.
# 14. Golden Sand A jar filled with fine, shimmering sand that glows warmly, reminiscent of a sunset.
# 15. Wisp of Smoke A swirling, grayish substance that drifts lazily within the confines of its jar.
# 16. Nightshade Berries Dark, glossy berries that glisten ominously, nestled in a jar of dark liquid.
# 17. Phoenix Ashes A fine, gray powder that sparkles faintly, as if containing remnants of a fiery rebirth.
# 18. Silver Thread A spool of shimmering thread that glows softly, appearing almost ethereal in nature.
# 19. Timekeeper Sand A jar filled with golden sand that flows slowly, as if measuring the passage of time.
# 20. Elven Wine A deep green liquid that sparkles with tiny bubbles.
# 21. Ghostly Essence A pale, translucent ichor that swirls with a soft glow.
# 22. Celestial Oil A shimmering oil that glows with a soft light.
# 23. Cat Shadow a swirling, inky blackness that pulses and shifts.
# 24. Toadstool Caps Vibrant mushroom caps of red, orange, and yellow, and adorned with delicate white speckles that catch the light.
# This would be funny, but I dont want a player to litter around the world with jars of crap … unless we make a janitor that sweeps the places once a day. Of course, the Jar /dropped/ here, would be deleted.
# [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:7]] # [[file:../../../projects/mud.org::*Inside the Secret Room][Inside the Secret Room:7]]
@detail jars = Hrm. Newt eyes, bat wings... interesting contents. @detail phials = Delicate crystal phials, each shaped like a teardrop, attach to a wrought iron rack. Each contain vibrant liquids that swirl with colors not found in nature. Magically sealed, these phials may store volatile substances, which require special containment to prevent their magical properties from dissipating.
# Inside the Secret Room:7 ends here # Inside the Secret Room:7 ends here
# Labels, written in elegant script, indicate their contents: "Essence of Nightshade," "Elixir of Clarity," and "Dragon's Blood."?
# Bottles same as vials?
# And tools that definitely need to /stay here/: # And tools that definitely need to /stay here/:
@ -3191,7 +3180,7 @@ py here.search("cabinet").do_bake()
# Lets do a funnier message: # Lets do a funnier message:
# [[file:../../../projects/mud.org::*Stool][Stool:4]] # [[file:../../../projects/mud.org::*Stool][Stool:4]]
@set stool/get_err_msg = "Stop try to steal everything not nailed down." @set stool/get_err_msg = "Stop trying to steal everything not nailed down."
# Stool:4 ends here # Stool:4 ends here
# Grimoire # Grimoire
@ -3277,52 +3266,44 @@ py here.search("cabinet").do_bake()
@lock cauldron = get:false() @lock cauldron = get:false()
# Cauldron:3 ends here # Cauldron:3 ends here
# Table and Shelf # Shelf of Bottles
# Until we decide if we want to do something with the table:
# [[file:../../../projects/mud.org::*Table and Shelf][Table and Shelf:1]]
@detail table = Made from a polish black wood, etched with intricate runes that shimmer faintly in the candlelight.
# Table and Shelf:1 ends here
# The table is a producer of /bottles/. # The table is a producer of /bottles/.
# [[file:../../../projects/mud.org::*Table and Shelf][Table and Shelf:2]] # [[file:../../../projects/mud.org::*Shelf of Bottles][Shelf of Bottles:1]]
@create/drop shelf of empty bottles;shelf;bottles;bottle: typeclasses.consumables.Producer @create/drop shelf of empty bottles;shelf;bottles;bottle: typeclasses.consumables.Producer
# Table and Shelf:2 ends here # Shelf of Bottles:1 ends here
# With a description: # With a description:
# [[file:../../../projects/mud.org::*Table and Shelf][Table and Shelf:3]] # [[file:../../../projects/mud.org::*Shelf of Bottles][Shelf of Bottles:2]]
@desc shelf = Cluttered with some empty brown |Ybottles|n. Perhaps you can fill these with liquid ingredients and bring them back here. @desc shelf = Cluttered with some empty brown |Ybottles|n. Perhaps you can fill these with liquid ingredients and bring them back here.
# Table and Shelf:3 ends here # Shelf of Bottles:2 ends here
# We have to have the bush describe what it /makes/: # We have to have the bush describe what it /makes/:
# [[file:../../../projects/mud.org::*Table and Shelf][Table and Shelf:4]] # [[file:../../../projects/mud.org::*Shelf of Bottles][Shelf of Bottles:3]]
@set shelf/make_name = "bottle" @set shelf/make_name = "bottle"
# #
@set shelf/make_verb = "$conj(pick up) a" @set shelf/make_verb = "$conj(pick up) a"
# Table and Shelf:4 ends here # Shelf of Bottles:3 ends here
# This one is optional as it defaults to Consumable: # This one is optional as it defaults to Consumable:
# [[file:../../../projects/mud.org::*Table and Shelf][Table and Shelf:5]] # [[file:../../../projects/mud.org::*Shelf of Bottles][Shelf of Bottles:4]]
@set shelf/make_class = "typeclasses.drinkables.Bottle" @set shelf/make_class = "typeclasses.drinkables.Bottle"
# #
@set shelf/make_desc = "A brown glass bottle. Currently empty." @set shelf/make_desc = "A brown glass bottle. Currently empty."
# #
@set shelf/make_amount = 1 @set shelf/make_amount = 1
# Table and Shelf:5 ends here # Shelf of Bottles:4 ends here
# Imp # Imp
# Every secret alchemical lab should have an Imp familiar. # Every secret alchemical lab should have an Imp familiar.
@ -3380,89 +3361,6 @@ py bt = self.search('imp'); bt.db.pose = 'sitting on an ornate perch'
@set imp/say = "1 ;; emote << nods ^ looks at you quizically ^ stares at you curiously ^ shrugs ^ investigates its fingerclaws ^ winks ^ smirks ^ raises an eyebrow ... well, if it had one, it would ^ stares at you ^ squints its eyes >>." @set imp/say = "1 ;; emote << nods ^ looks at you quizically ^ stares at you curiously ^ shrugs ^ investigates its fingerclaws ^ winks ^ smirks ^ raises an eyebrow ... well, if it had one, it would ^ stares at you ^ squints its eyes >>."
# Imp:8 ends here # Imp:8 ends here
# Trippy Potion
# After ingesting this potion, they may see hallucinations and nightmares. It would be nice if these dreams could incorporate the room state.
# Ingredients:
# - [[Pixie Dust]]
# - [[Dream Mushrooms]]
# - [[Spring Water ]]
# - [[Moonberries]]
# The moonberries grow under conifers, and I find I often have to travel to one of the islands on the Lavender Sea to collect these.
# [[file:../../../projects/mud.org::*Trippy Potion][Trippy Potion:1]]
@teleport/quiet gr02
#
@create/drop moonberries;moonberry;berry: typeclasses.consumables.Producer
#
@desc moonberries = Growing a slender vines that wrap around the trunks of the pine trees. Laden with small, blue berries, each reflecting a white cresent shape.
#
@set moonberries/make_name = "handful of moonberries"
#
@set moonberries/make_verb = "$conj(collect) a"
#
@set moonberries/make_class = "typeclasses.consumables.Edible"
#
@set moonberries/make_desc = "Blue berries with a white cresent shape."
#
@set moonberries/make_amount = 1
#
@set moonberries/make_eat_msg = "Slightly bitter. Not very good."
#
@set moonberries/make_spell_msgs = "10 ;; $You() $conj(stare) off into space, lost in thought. ;; $You() $conj(study) $pron(your) hands, utterly captivated. ;; 5 ;; $You() $conj(awaken) from a daydream with a start."
#
# And we can't see them until we are an alchemist:
@lock moonberries = view:tag(alchemist)
# Trippy Potion:1 ends here
# Other
# Well get ready by allowing one to collect water from _all_ the places, like the salty sea:
# [[file:../../../projects/mud.org::*Other][Other:1]]
@teleport/quiet mp06
#
@create/drop lavender sea;sea;water;bay: typeclasses.drinkables.Water
#
@desc sea = A gently waving sea. Too bad the shore doesn't respond with a greeting of its own.
#
@lock sea = get:false()
#
@set sea/get_err_msg = "You can only hold the sea in your heart. Perhaps a bottle, or at least a cup, could hold the salty water."
#
@set sea/fill_name = "salt water"
#
@set sea/fill_desc = "salty water with a purple hue."
#
@set sea/fill_msgs = ["$You() $conj(reach) down from the dock, and $conj(fill) $pron(your) {2} with the << salty ^ lavender ^ fragrant >> water."]
# Other:1 ends here
# And the muddy marsh:
# [[file:../../../projects/mud.org::*Other][Other:2]]
@teleport/quiet mp08
#
@create/drop river;stream;water: typeclasses.drinkables.Water
#
@lock river = get:false()
#
@set river/get_err_msg = "Slippery things, those rivers. Seems you would need |gfill|n a |gbottle|n, or at least a cup to hold the muddy water."
#
@desc river = A muddy, almost stagnant river. Smells like a fecund stew of moist dirt and decomposing swamp herbage.
#
@set river/fill_name = "muddy water"
#
@set river/fill_desc = "muddy water from the marsh."
#
@set river/fill_msgs = ["$You() $conj(<< get ^ kneel >>) down, and $conj(fill) $pron(your) {2} with the muddy water."]
# Other:2 ends here
# Bedroom # Bedroom
# A bedroom with a wardrobe that goes to another land sounds great. # A bedroom with a wardrobe that goes to another land sounds great.
@ -3491,7 +3389,7 @@ py bt = self.search('imp'); bt.db.pose = 'sitting on an ornate perch'
# [[file:../../../projects/mud.org::*Bedroom][Bedroom:3]] # [[file:../../../projects/mud.org::*Bedroom][Bedroom:3]]
@teleport/quiet mp13 @teleport/quiet mp13
# #
@desc here = Like the shadows that dance here, this oddly shaped room hugs its contents: a thick wooden framed |Ybed|n piled high with |Yblankets|n and |Ypillows|n to keep out the chill; a thick burgundy |Ycarpet|n sporting a pair of |Yslippers|n; and a |Ywardrobe|n decorated with ornate leaves and berries. @desc here = Like the shadows that dance here, this oddly shaped room hugs its contents: a thick wooden framed |Ybed|n piled high with warm |Yblankets|n and fluffy |Ypillows|n, keep out the chill; a thick burgundy |Ycarpet|n sporting a pair of |Yslippers|n; and a |Ywardrobe|n decorated with ornate leaves and berries.
# Bedroom:3 ends here # Bedroom:3 ends here
@ -3582,7 +3480,7 @@ py bt = self.search('imp'); bt.db.pose = 'sitting on an ornate perch'
# [[file:../../../projects/mud.org::*Wardrobe][Wardrobe:4]] # [[file:../../../projects/mud.org::*Wardrobe][Wardrobe:4]]
@create/drop wardrobe @create/drop wardrobe
# #
@desc wardrobe = While resting on the floor, this wardrobe scratches the ceiling. Large furniture, or perhaps a small room? Gorgeously ornate with carvings of leaves and berries. Carved above the doors, are the words, |wUKRAH|n. The latch is undone, and this can be |gopen|ned. @desc wardrobe = While resting on the floor, this wardrobe scratches the ceiling. Large furniture, or perhaps a small room? Gorgeously ornate with carvings of leaves and berries. Carved above the doors, are the words, |wUKRAH|n. The latch is undone, and can be |gopen|ned.
# Wardrobe:4 ends here # Wardrobe:4 ends here

361
world/version4.ev Normal file
View file

@ -0,0 +1,361 @@
# Jars
# Every time we look at a jar, we see something else … that we cant take. This creates ambiance without adding too much complexity?
# [[file:../../../projects/mud.org::*Jars][Jars:1]]
@tel/quiet Homey Hut
#
@create/drop assortment of jars;jars;jar: typeclasses.puzzles.Changling
# Jars:1 ends here
# Cant get them:
# [[file:../../../projects/mud.org::*Jars][Jars:2]]
@lock jars = get:false()
#
@set jars/get_err_msg = "\"Do not steal our winter provisionings,\" the horned wolf skull says. \"What are you a thief?\""
# Jars:2 ends here
# And the generate description:
# [[file:../../../projects/mud.org::*Jars][Jars:3]]
@set jars/desc_first_prefix = "<< Fascinating ^ Interesting ^ Curious >> << collection of ^ assortment of ^ >> << jars ^ contents ^ ingredients >>. You look at one << jar ^ >> with << an afixed ^ an attached >> label of << scrawling ^ scribbling ^ squiggling >> << ink ^ writing ^ letters >>,|w"
#
@set jars/desc_prefix = "You look at another << jar ^ >> with << an afixed ^ an attached >> label of << scrawling ^ scribbling ^ squiggling >> << ink ^ writing ^ letters >>,|w"
#
@set jars/desc_postfix = ""
# Jars:3 ends here
# And now for a list of the contents:
# [[file:../../../projects/mud.org::*Jars][Jars:4]]
@set jars/descs = (
"Dragon's Breath|n. A swirling mist of iridescent smoke that changes color, said to contain the essence of fire.",
"Mermaid Tears|n. Clear, crystalline droplets that shimmer with a hint of blue, believed to bring good fortune.",
"Phoenix Ashes|n. A small jar filled with fine, red and gold ash, said to have the power of rebirth.",
"Enchanted Rose Petals|n. Dried petals that change color with the phases of the moon, said to attract love.",
"Eye of Newt|n. Filled with many small eyeballs.",
"Timekeeper's Sand|n. Fine, golden sand that flows slowly, rumored to have the power to manipulate time.",
"Cursed Bone Shards|n. Jagged pieces of bone, each one etched with strange symbols and glowing faintly.",
"Enchanted Honey|n. Thick, golden honey that glimmers with tiny flecks of light, like captured sunlight.",
"Faerie Wings|n. Delicate, translucent wings that shimmer in various colors, said to grant agility.",
"Elemental Stones|n. Small, smooth stones representing earth, air, fire, and water, each with a unique glow.",
"Owlbear Hair|n. Strands of shimmering hair from various magical creatures, said to enhance spells.",
"Frosted Rose Petals|n. Dried flowers that appear to be covered in frost, said to bring winter's magic.",
"Toadstool Caps|n. Vibrant mushroom caps of red, orange, and yellow, and adorned with delicate white speckles that catch the light.",
"Glowcaps|n. Clusters of tiny, bioluminescent mushrooms that emit a soft, greenish glow.",
"Dream|n. Fluffy, cotton-like wisps gently floating, resembling miniature clouds in the jar.",
"Mandrake Root|n. A twisted, gnarled root with a faintly green hue, nestled in a jar of dark soil.",
)
# Jars:4 ends here
# Herbs
# Like the [[*Jars][Jars]], the herbs return a different response each time they are viewed.
# [[file:../../../projects/mud.org::*Herbs][Herbs:1]]
@create/drop collection of herbs;herbs;herb: typeclasses.puzzles.Changling
# Herbs:1 ends here
# While the skull protects the jars, we will have the demon stop the herbs from being pinched.
# [[file:../../../projects/mud.org::*Herbs][Herbs:2]]
@lock herbs = get:false()
#
@set herbs/get_err_msg = "On the wall, the carving comes to life, and flies next to you. \"Do not take her harvest,\" it says as it bats your hand away."
# Herbs:2 ends here
# [[file:../../../projects/mud.org::*Herbs][Herbs:3]]
@set herbs/desc_first_prefix = "<< Plenty ^ Many >> bundles around the room. One << particular ^ peculiar ^ >> << bundle ^ bouquet garni >> of "
#
@set herbs/desc_prefix = "<< Another ^ This >> << particular ^ peculiar ^ >> << bundle ^ bouquet garni >> of "
#
@set herbs/desc_postfix = " Tied with << twine ^ string ^ lace >> and << hanging from a rafter ^ hung from a nail ^ dangling from a post of a chair >>."
# Herbs:3 ends here
# And the individiaul choices are more appearance, and possibly smell, without claiming to be /worldly herbs/. Would like to add some dried red and other colored leaves to make it more fantastical.
# [[file:../../../projects/mud.org::*Herbs][Herbs:4]]
@set herbs/descs = (
"grayish-green, crinkled leaves, and has a strong, earthy aroma, like sage.",
"small, purple flowers, with that sweet, lavender scent.",
"thin, woody needles, and has a strong, pine-like fragrance, like rosemary.",
"small, white flowers with yellow centers, resembling tiny daisies.",
"tiny, greenish-brown leaves, with a robust, herbal scent, like thyme.",
"dark green leaves with a refreshing, minty aroma.",
"brown leaves, with a refreshing, minty aroma.",
"dark green and crinkled leaves, and have a sweet, peppery scent"
"brown, crinkled leaves, with a sweet, peppery, almost basil-like scent"
"grayish-green, feathery leaves, with a slightly bitter, mugwort-like aroma.",
"small, white and yellow flowers that have a feathery appearance, like yarrow.",
"dark green, almost brown leaves, with a slightly bitter aroma.",
"dark green leaves, some almost brown, with a coarse texture and earthy scent, like nettle.",
"feathery fronds, ranging from light green to brown, with a sweet, anise-like scent.",
"purple flowers (some brown), with a spiky center and a slightly sweet aroma, like echinacea.",
"bright orange to yellow flowers, with a slightly sweet, herbal scent.",
"dark green, smooth leaves, and have a strong, aromatic scent, like bay.",
"grayish-green, feathery leaves with a distinctive, bitter aroma.",
"brown and woody roots, with a strong, earthy Valerian-like smell.",
"brown, woody root with a sweet, distinct aroma, like licorice.",
)
# Herbs:4 ends here
# Sandy Shore
# Could we extend the sea from the [[file:mud.org::*The Dock][The Dock]] down a shore:
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:1]]
@teleport/quiet mp06
#
@dig Shore;mp15 :typeclasses.rooms_weather.TimeWeatherRoom = south along shore;shore;south;s,north to dock;north;n;dock
# Sandy Shore:1 ends here
# With a mesage about leaving the trees so that I dont have to repeat that in the room description:
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:2]]
@set south/traverse_msg = "Leaving the dock, you want along the soft sandy shore next to the Lavender Sea, enjoying the mesmerizing sound of the surf... until you come to a shack that blocks your stroll."
# Sandy Shore:2 ends here
# And a description:
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:3]]
@desc south = You see a shack down along the sandy shore.
# Sandy Shore:3 ends here
# And move ourselves there:
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:4]]
@teleport mp15
# Sandy Shore:4 ends here
# And describe the walk back to the dock:
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:5]]
@set north/traverse_msg = "You walk along the shore of the lavender sea back to the dock."
# Sandy Shore:5 ends here
# And a description:
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:6]]
@desc north = The sandy shore to the north ends at a dock, jutting into the lavender sea.
# Sandy Shore:6 ends here
# And describe this.
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:7]]
@desc here = Puppy-dog |Ywaves|n on a lavender |Ysea|n, snap your heels half-heartedly. Walking hard steps, punching crusted |Ysand|n, difficulty crossing land. Robust |Yshack|n squatting below a |Ypine|n, locked door holding painted |Ysign|n.
# Sandy Shore:7 ends here
# And details?
# [[file:../../../projects/mud.org::*Sandy Shore][Sandy Shore:8]]
@detail waves = Despite the inclement weather, the waves ripple gently against the shore.
#
@detail sea;lavender sea = Is that a |Yboat|n you see sailing the sea in the distance?
#
@detail boat;ship = The mastless ship looks like a giant leaf. Wonder if it comes to shore?
#
@detail shack = Standing crookedly at the edge of the sandy shore, this shack's weathered planks, bleached by the salty mist, imparts a ghostly appearance. The roof, adorned with seashells and driftwood, appears to be a patchwork of nature's treasures, inviting curious souls to uncover the secrets hidden within.
# Sandy Shore:8 ends here
# Sand
# Part of the [[Potions and their Ingredients][Alchemist Path]], we use sand as an ingredient in a potion we want to make.
# [[file:../../../projects/mud.org::*Sand][Sand:1]]
@create/drop lot of sand;sand : typeclasses.consumables.Producer
#
@desc sand = Glittery sand with small flecks of lavender-colored gems.
#
@set sand/make_name = "bag of sand"
#
@set sand/make_verb = "$conj(fill) a small"
#
@set sand/make_desc = "Small leather pouch of sand with lavender gems."
#
@lock sand = view:tag(hidden_sand)
# Sand:1 ends here
# Pine Flowers
# Part of the [[Potions and their Ingredients][Alchemist Path]], we use /pine flowers/ to create a potion TBD, and feed the stoat in Dabblers House.
# [[file:../../../projects/mud.org::*Pine Flowers][Pine Flowers:1]]
@create/drop pine tree;pine;tree;flowers;flower = typeclasses.consumables.Producer
#
@desc pine = Windswept pine leans to shade the shack, protecting it somewhat from the regular occuring rain. Interesting, that the pine has beautiful, yellow |Yflowers|n.
#
@set pine/make_class = "typeclasses.consumables.Herb"
#
@set pine/make_name = "yellow flower"
#
@set pine/make_verb = "$conj(pick) a small"
#
@set pine/make_desc = "Briny smelling flower with purple spots."
#
@lock pine = view:tag(alchemist) # We want the user to be able to "look pine" as a detail?
# Pine Flowers:1 ends here
# Sign
# We make the sign as an “object” for others to read:
# [[file:../../../projects/mud.org::*Sign][Sign:1]]
@create/drop sign = typeclasses.readables.Readable
#
@desc sign = A hand-painted sign with beautiful calligraphy reads: |wFor Rent. See Dabbler for details.|n
#
@set sign/inside = "For Rent. See Dabbler for details."
#
@lock sign = get:false()
# Sign:1 ends here
# Salty Shack
# Lets keep this pretty empty.
# [[file:../../../projects/mud.org::*Salty Shack][Salty Shack:1]]
@teleport/quiet mp15
#
@dig Salty Shack;mp16 = locked door;door;inside,door to outside;door;outside;leave;exit
# Salty Shack:1 ends here
# And described the exit:
# [[file:../../../projects/mud.org::*Salty Shack][Salty Shack:2]]
@desc door = Barnacle encrusted door with rusty irons bands and a comically large padlock. The door sports a hand-painted |Ysign|n that reads: |wFor Rent. See Dabbler for details.
#
@set door/traverse_msg = "The lock opens when you touch it, and the door opens with loud sigh. You step inside and close the door behind you."
# Salty Shack:2 ends here
# And lock the exit:
# [[file:../../../projects/mud.org::*Salty Shack][Salty Shack:3]]
@lock door = traverse:tag(open_shack_door, mp)
#
@set door/err_traverse = "The door is obviously locked."
# Salty Shack:3 ends here
# Generic description of the insides of this house:
# [[file:../../../projects/mud.org::*Salty Shack][Salty Shack:4]]
@teleport/quiet mp16
#
@desc here = The shack is curiously bare and devoid of all personality.
# Salty Shack:4 ends here
# And describe the exit:
# [[file:../../../projects/mud.org::*Salty Shack][Salty Shack:5]]
@desc door = Large wood door with iron bands.
#
@set door/traverse_msg = "You open the door and step out on the sand, closing the door behind you."
# Salty Shack:5 ends here
# Jars
# Can jars be a producer that returns a random jar with a “content”?
# Every time we look at a jar, we see something else … that we cant take. This creates ambiance without adding too much complexity?
# [[file:../../../projects/mud.org::*Jars][Jars:1]]
@tel/quiet Secret Room
#
@create/drop collection of jars;jars;jar: typeclasses.puzzles.Changling
# Jars:1 ends here
# Cant get them:
# [[file:../../../projects/mud.org::*Jars][Jars:2]]
@lock jars = get:false()
#
@set jars/get_err_msg = "The imp slaps your hand away and shakes his head. While you can take an empty |Ybottle|n, you can't take the currated ingredients. Guess you can always find your own ingredients, eh?"
# Jars:2 ends here
# And the generate description:
# [[file:../../../projects/mud.org::*Jars][Jars:3]]
@set jars/desc_first_prefix = "<< Fascinating ^ Interesting ^ Curious >> << collection of ^ assortment of ^ >> << jars ^ contents ^ ingredients >>. You look at one << jar ^ >>, << elegantly ^ hastily ^ legibly ^ >> labeled,|w"
#
@set jars/desc_prefix = "You look at another << jar ^ >>, << elegantly ^ hastily ^ legibly ^ >> labeled,|w"
#
@set jars/desc_postfix = ""
# Jars:3 ends here
# And now for a list of the contents:
# [[file:../../../projects/mud.org::*Jars][Jars:4]]
@set jars/descs = (
"Glimmering Dust|n. A jar filled with fine, shimmering powder that sparkles like a thousand stars.",
"Dragon Blood|n. A deep red liquid that swirls with hints of gold, resembling liquid rubies.",
"Crystalized Stardust|n. Tiny, sparkling crystals that twinkle like stars, believed to hold the essence of the cosmos.",
"Moonstone Crystals|n. Iridescent stones that glow softly in the dark, casting a gentle light.",
"Bottled Lightning|n. A swirling blue liquid that crackles with energy, contained within a glass jar.",
"Dragon Scale Powder|n. A fine, metallic powder that shifts colors with the light, reminiscent of dragon scales.",
"Mermaid Tears|n. Tiny, glistening droplets that resemble diamonds, each one capturing a moment of sorrow.",
"Essence of Shadow|n. A dark, swirling liquid that seems to absorb light, creating an eerie atmosphere.",
"Shadow Essence|n. A dark, swirling liquid that absorbs light, said to grant invisibility.",
"Starflower Petals|n. Delicate, translucent petals that shimmer like the night sky, layered in a glass jar.",
"Whispering Seeds|n. Tiny, dark seeds that seem to rustle softly when the jar is moved, as if alive.",
"Golden Sand|n. A jar filled with fine, shimmering sand that glows warmly, reminiscent of a sunset.",
"Wisp of Smoke|n. A swirling, grayish substance that drifts lazily within the confines of its jar.",
"Nightshade Berries|n. Dark, glossy berries that glisten ominously, nestled in a jar of dark liquid.",
"Phoenix Ashes|n. A fine, gray powder that sparkles faintly, as if containing remnants of a fiery rebirth.",
"Silver Thread|n. A spool of shimmering thread that glows softly, appearing almost ethereal in nature.",
"Timekeeper Sand|n. A jar filled with golden sand that flows slowly, as if measuring the passage of time.",
"Elven Wine|n. A deep green liquid that sparkles with tiny bubbles.",
"Ghostly Essence|n. A pale, translucent ichor that swirls with a soft glow.",
"Celestial Oil|n. A shimmering oil that glows with a soft light.",
"Cat Shadow|n. A swirling, inky blackness that pulses and shifts.",
)
# Jars:4 ends here