!\------------------------------------------------------------------------------------------------------------------
    SCAVENGER HUNT - Version 0.3
    Copyright (c) 2000-2002 by Gilles Duchesne

    Written using Hugo v3.0

    This document is part of my "Scavenger Hunt" tutorial. It should be distributed as a package,
    along the following:
    SCAVHUNT1.HTM - Core & rooms
    SCAVHUNT2.HTM - Scenery objects
    SCAVHUNT3.HTM - Inventory objects (THIS FILE)
    SCAVHUNT4.HTM - NPCs
    SCAVHUNT5.HTM - Time & score
    SCAVHUNT6.HTM - Misc info, credits & hints
    SCAVHUNT7.HTM - Sounds & pictures

    The package, as a whole, can be redistributed freely. However, I'd appreciate it if the issues &
    mistakes would be reported to me rather than directly edited. Please contact me at lonecleric@bigfoot.com.

    If you think parts of this code could be reused for your own purposes, feel free to do so.
------------------------------------------------------------------------------------------------------------------\!


!This new version adds all the "inventory objects", that is, all the objects which won't have the "static"
!attribute and that the player will be able to carry around. I put them all together, near the end of the file.
!Consequently, this is the first version of the game you can actually win. Yay!

#set DEBUG                              ! include HugoFix library and grammar
#set VERBSTUBS                          ! include verb stub routines
#set NO_AUX_MATH                        ! don't need advanced math routines

#switches -ls                           ! print statistics to SAMPLE.LST
#ifset DEBUG
#switches -d
#endif

!----------------------------------------------------------------------------
! NEW GRAMMAR:
verb "read", "peruse"
    *                                                       DoVague
    * readable                                              DoRead


!Here are some new verbs I'm adding to help the player fiddle with the new objects.
verb "blow"
    *                                                       DoVague
    * object                                                DoBlow

verb "play"
    *                                                       DoVague
    * object                                                DoPlay

! I pasted this one from verblib.g, then modified it to differenciate "on" and "in"
verb "put", "place"
    *                                                       DoVague
    * multiheld "on"/"onto" "ground"/"floor"                DoPutonGround
    * multiheld "outside" xobject                           DoPutonGround
    * "down" multiheld                                      DoDrop
    * multiheld "down"                                      DoDrop
    * multiheld "in"/"into"/"inside" container              DoPutIn
    * multiheld "on"/"onto" platform                        DoPutOn
    * multiheld                                             DoDrop

! Allowing 'give up' as an action
verb "give"
    * "up"                                                  DoGiveUp

verb "bowl"
    *                                                       DoBowl

verb "count"
    *                                                       DoVague
    !"Anything" means, well, anything. Any object known by the game will be accepted, whether it's around or not.
    * anything                                              DoCount

#include "verblib.g"                    ! normal verb grammar

!----------------------------------------------------------------------------

#include "hugolib.h"                    ! standard library routines

routine init
{
    counter = -1                        ! 1 turn before turn 0

    STATUSTYPE = 1                      ! score/turns
    TEXTCOLOR = DEF_FOREGROUND
    BGCOLOR = DEF_BACKGROUND
    SL_TEXTCOLOR = DEF_SL_FOREGROUND
    SL_BGCOLOR = DEF_SL_BACKGROUND
    color TEXTCOLOR, BGCOLOR

    INDENT_SIZE = 0                    ! no indents whatsoever (doesn't fit my writing style)
    prompt = ">"

    DEFAULT_FONT = PROP_ON
    Font(DEFAULT_FONT)

    display.title_caption = "Scavenger Hunt"
    cls
    "Here you are, visiting your best friend in his new house in Cheapsville. His nice, new, empty, tediously
    boring house in a charmingly boring suburban town.\nYour friend, who always liked games of all kind and
    doesn't say no to the occasional bet, has decided to set up a challenge for you...\n"
    "A scavenger hunt.\n"
    "Here's the idea: he gives you three hours to go around the neighborhood, trying to find all the
    miscellaneous things he's listed. You're supposed to bring all these items back to his house.\n"
    
    "\n\n"
    "\BScavenger Hunt\b"
    "A Small Visit in Cheapsville"
    "Version 0.3"
    print BANNER

    player = you
    location = friendshome
    old_location = location

    move player to location         ! initialize player location
    FindLight(location)             ! whether the player can see
    DescribePlace(location)         ! the appropriate description
    location is visited
    !I make sure my "gamewon" daemon gets activated right at the beginning of the game. More on this below.
    Activate( gamewon )            ! activates the endgame daemon
}

routine main
{
    counter = counter + 1
    PrintStatusLine
    run location.each_turn
    !Those 2 calls have been here since v0.1, and yet I never commented on them. Well, so far they weren't
    !actually doing anything. I generally keep the main routine unchanged in between games. In fact, this game
    !won't have any script in it, so RunScripts won't ever do anything relevant. Accept it.
    !runevents, on the other hand, is now worthy of some attention. The purpose of this keyword (which isn't a
    !routine, BTW, but a direct call to the engine) is to call all the "events" defined for each object that is
    !currently "in scope" (usually in the same room as the PC).
    runevents
    RunScripts
    if speaking not in location     ! in case the character being spoken
        speaking = 0                ! to leaves
}

player_character you "you"
{}

!----------------------------------------------------------------------------
! ENDGAME DAEMON
! Checks if you've won the game
!----------------------------------------------------------------------------
!A daemon is an object with a special capability: it can be "activated" and "deactivated" at will, essentially
!moving in and out of scope. Therefore, instead of being called when the player is near it, the events tied to
!the daemon will be called each and every turn, or not at all.
daemon gamewon 
{}

!As the name implies, this daemon is used to check if all the winning conditions have been attained.
event in gamewon
{
    if location = friendshome
        !Special is an attribute left to the author's fancy. I'll show you how the squash can become "special"
        !in a short while.
        if squash is special
            !The FindObject routine, provided by the HugoLib, tries to reach the given object from the given
            !location. It has, however, a small bug (or a side feature, as you wish to see it): it will also
            !return true if the *player character* is able to reach the object, even if the PC is miles away
            !from that location. In the current situation, however, the PC's sure to be in the room.
            if FindObject( smalldictionary, location )
                if FindObject( sharpener, location )
                    if FindObject( pen, location )
                        if FindObject( floppydisk, location )
    {
        "\n\nWell, that's everything! Every item on the list, including the elusive racket, has been
        brought. Your friend reluctantly admits that you won the bet, and as it was agreed, promises to
        stop playing those crappy '3D action-adventure' games and to stick to IF for the whole summer."
        !***  You have won!  ***  endgame
        endflag = 1
    }
}

!Astute readers might object, at this point: "Hey, since your daemon's meant to check conditions which'll only
!happen in the friend's home, wouldn't it make more sense (and be more efficient) to put that event within the
!friendshome object, and forget about the daemon altogether?"
!Well, er, that's completely true. And I just realized that myself, while writing all those comments. I guess I
!could lie and claim it was all on purpose, just to show you how daemons work, but that's not my style. So I hope
!you'll read on with a renewed esteem for yours truly. ;-)

!----------------------------------------------------------------------------
! CL_ROOM CLASS
! Used to add generic answers to "up" and "down"
!----------------------------------------------------------------------------
room cl_room
{
    u_to
    {
        "Well, there aren't any stairs, elevators, or ladders, around, nor any wings on your back. You won't
        be able to go up."
    }
    d_to
    {
        "You can't go much lower than this."
    }
}

!----------------------------------------------------------------------------
! GENERAL SCENERY
! Objects that are used as scenery in several rooms
!----------------------------------------------------------------------------

scenery streetlight "streetlight"
{
    found_in oakstreet, intersection, schoolyard, outsidelibrary, outsidebowling
    nouns "light", "lamp", "post", "streetlight"
    adjectives "street", "lamp"
    article "a"
    long_desc
    {
        "It's a typical urban street light. You might guess that it's in working order, but it's off now
        against the morning sky. A bunch of other lights, just like this one, run along the street."
    }
}

scenery friendshouse "your friend's house"
{
    found_in oakstreet, backyard
    nouns "house", "building", "home"
    adjectives "friend's", "friend"
    long_desc
    {
        "It's a nice house. Not impressive. Just nice. It's as nice as all the other houses around. Thankfully,
        you think to yourself, they don't all look identical, like in some of those newer suburbs."
    }
    door_to
    {
        select location
            case oakstreet
                return frontdoor.door_to
            case backyard
                return backyarddoor.door_to
    }
    parse_rank 1
}

scenery cl_car
{
    found_in oakstreet, intersection, schoolyard, outsidelibrary, outsidebowling
    article "the"
    before
    {
        object
        {
            "The cars are passing by too fast - just forget it."
        }
        xobject
        {
            "The cars are passing by too fast - just forget it."
        }
    }
}
    
cl_car car "car"
{
    nouns "car"
}

cl_car cars "cars"
{
    nouns "cars"
    is plural
}

scenery grass "grass"
{
    found_in backyard, park
    nouns "grass"
    article "the"
    long_desc
    {
        "The grass seems greener here than back home. But then again, doesn't it always?"
    }
}

scenery sky "sky"
{
    found_in backyard, park, oakstreet, intersection, schoolyard, outsidelibrary, outsidebowling
    nouns "sky"
    article "the"
    long_desc
    {
        "The sky is a plain, uniform grey."
    }
}

scenery houses "houses"
{
    found_in oakstreet, intersection, schoolyard, outsidelibrary, outsidebowling
    nouns "houses", "house"
    article "the"
    long_desc
    {
        "There are several houses in the area. They are all sort of bland and nice. They're each
        significantly different, which relieves the suburban boredom a great deal."
    }
    is plural
}

scenery street "street"
{
    found_in oakstreet, intersection, schoolyard, outsidelibrary, outsidebowling
    nouns "street", "road"
    adjectives "main", "oak"
    article "the"
    long_desc
    {
        "It's a long ribbon of asphalt - nothing out of the ordinary."
    }
}

!----------------------------------------------------------------------------
! FRIEND'S HOME
!----------------------------------------------------------------------------
cl_room friendshome "At your friend's house"
{
    long_desc
    {
        "Your good friend had just begun moving into this fine, empty house. The main center of attention is
        still the desk, which tells a lot about how much still has to be moved. That won't be until the
        afternoon, however. Because of that, a puerile game of scavenger hunt seems like a good idea.
        \nThe main door leads to the east, but there's also a back door to the north, leading to the neighbor's
        backyard.
        \nA work desk has been placed in one corner. The immediate area also has a closet."
    }
    n_to {return backyarddoor.door_to}
    e_to {return frontdoor.door_to}
    out_to {return frontdoor.door_to}
    cant_go
    {
        "Unless you smashed a hole in the wall (which wouldn't be very considerate) you can't go that way."
    }
}

scenery workdesk "work desk"
{
    in friendshome
    nouns "desk"
    adjectives "work"
    article "the"
    long_desc
    {
        "The desk is quite familiar - your friend has had it for ages. It looks great, sitting there with its
        single drawer, but you wouldn't want to watch it all day."
        Perform( &DoLookIn, self )
    }
    is openable, open, container, platform
    capacity 30        ! That's for the top of the table, not the inside
    holding 0
    before
    {
        object DoMove, DoPush
        {
            "The desk might be small, but it's heavy. Since you almost threw out your back putting it there in
            the first place, you're no inclined to shove it around any more. Besides, it looks great where it
            is, and your friend agrees."
        }
        object DoOpen, DoClose
        {
            return Perform( verbroutine, drawer )
        }
        object DoLookIn
        {
            if word[2] = "in", "inside"
                return Perform( &DoLookIn, drawer )
            else
                return false    ! Means "look on" - continue normally
        }
        xobject DoPutIn        !Overrides "put in", not "put on"
        {
            return Perform( &DoPutIn, object, drawer )
        }
    }
}

scenery drawer "desk drawer"
{
    in friendshome
    nouns "drawer"
    adjectives "desk"
    article "the"
    long_desc
    {
        "The drawer, like the desk which contains it, is rather small."
        Perform( &DoLookIn, self )
    }
    is openable, not open, container
    capacity 10
    holding 0
}

scenery closet "small closet"
{
    in friendshome
    nouns "closet"
    adjectives "small", "tiny"
    article "the"
    long_desc
    {
        "This tiny closet will look much better once it's repainted, you bet. For
        the moment, it's ";
        if self is open
        {
            "open."
            Perform( &DoLookIn, self )
        }
        else
            "closed."
    }
    is openable, not open, container
    capacity 100
    holding 0
}

scenery closetdoor "closet door"
{
    in friendshome
    nouns "door"
    adjectives "closet"
    article "the"
    long_desc
    {
        "The door to this tiny closet will look much better once it's repainted, you bet. For
        the moment, it's ";
        if closet is open
            "open."
        else
            "closed."
    }
    is openable
    before
    {
        object DoOpen, DoClose
        {
            return Perform( verbroutine, closet )
        }
    }
}

scenery npc_friend "your friend"
{
    in friendshome
    nouns "friend", "man", "guy", "person"
    long_desc
    {
        "You've known him for ages. Through thick and thin, good and bad, you two always managed to keep
        in touch, and to support one another in time of need. You also share a strong interest in games
        and challenges of all kind.
        \nNoticing you staring at him, he turns toward you. \"Is there a problem?\" he asks. \"Or maybe
        you're giving up on our bet already?\""
    }
    is hidden
}

!----------------------------------------------------------------------------
! NEIGHBOR'S YARD
!----------------------------------------------------------------------------
cl_room backyard "Some neighbor's back yard"
{
    long_desc
    {
        "This back yard doesn't actually belong to your friend, even if there's a door leading to it. It's
        owned by some neighbor he hasn't even met yet. Both houses stand side by side, one to the north, the
        other to the south.
        \nYou notice a doghouse standing alongside one of the fences which surround most of the area."
    }
    s_to {return backyarddoor.door_to}
    in_to {return backyarddoor.door_to}
    se_to oakstreet
    n_to
    {
        "And just how do you plan to introduce yourself?
        \n\I\"Oh, hi there, I'm a friend of that new neighbor you haven't met, please don't mind me while I
        rummage through your belongings!\"\i
        \nUnlikely."
    }
    cant_go
    {
        "Several fences, which you hear make good neighbors, surround this area. The only passage through
        them is to the southeast."
    }
}

door backyarddoor "back yard door"
{
    between friendshome, backyard
    nouns "door"
    adjectives "back", "yard"
    article "the"
    is hidden
}

scenery cl_fence
{
    article "the"
    long_desc
    {
        "Several fences, which you hear make good neighbors, surround this area. The only passage through
        them is to the southeast."
    }
}

cl_fence fence "fence"
{
    in backyard
    nouns "fence"
}

cl_fence fences "fences"
{
    in backyard
    nouns "fences"
    is plural
}

scenery neighboryard "yard"
{
    in backyard
    nouns "yard"
    article "the"
    long_desc
    {
        "It's nice-looking, with neatly-trimmed grass everywhere."
    }
}

scenery doghouse "dog house"
{
    in backyard
    nouns "house", "doghouse"
    adjectives "dog", "red"
    article "the"
    long_desc
    {
        "The cute lil' dog house is painted bright red."
    }
    is container
    before
    {
        object DoEnter, DoLookIn
        {
            return DogDeath
        }
        xobject DoPutIn
        {
            return DogDeath
        }
    }
}

scenery neighborhouse "neighbor's house"
{
    in backyard
    nouns "house", "home", "building"
    adjectives "neighbor", "neighbor's"
    article "the"
    long_desc
    {
        "It's hard to judge the house from its back side, but it seems to be a well-maintained
        home, of roughly the same size and value as your friend's."
    }
    door_to { return backyard.n_to }
}

!----------------------------------------------------------------------------
! STREET, NEAR HOUSE
!----------------------------------------------------------------------------
cl_room oakstreet "Oak Street, near the house"
{
    long_desc
    {
        "You're now standing on the sidewalk of Oak Street. It's a quiet little street, much like every quiet
        little street you've seen in Cheapsville. Cars pass every few minutes, thrusting dust into the
        air. There's no one around; only a streetlight and a garbage bin are here to keep you company.
        \nThe street leads north toward a city park, and south to an intersection. You friend's new house
        stands to the west."
    }
    w_to {return frontdoor.door_to}
    in_to {return frontdoor.door_to}
    nw_to backyard
    n_to park
    s_to intersection
    cant_go
    {
        "You don't see anything worthwhile in that direction, and your time is precious."
    }
    before
    {
        location DoSmell
        {
            "The only thing which gets your nose's attention is the slight stench coming from the
            garbage bin."
        }
    }
}

door frontdoor "front door"
{
    between friendshome, oakstreet
    nouns "door"
    adjectives "front", "house", "main"
    article "the"
    is hidden
}

scenery dust "dust"
{
    in oakstreet
    nouns "dust"
    article "the"
    long_desc
    {
        "You're not likely to win that bet it you lose your precious time analyzing every individual spec
        of dust."
    }
}

scenery garbagebin "garbage bin"
{
    in oakstreet
    nouns "bin", "can"
    adjectives "garbage", "trash"
    article "the"
    long_desc
    {
        "This typical garbage bin has used for its intended purpose, judging by the smell. Although you expect
        to find a cheerful message along the lines of \"PLEASE KEEP OUR TOWN CLEAN\" or \"W.A.S.T.E.\", there's
        nothing like that written on it.
        \nYou notice some miscellaneous trash inside the bin."
    }
    is container
    type nothing
    capacity 30
    holding 0
    before
    {
        object DoSearch
        {
            Perform( &DoSearch, trash )
        }
    }
}

object trash "trash"
{
    in garbagebin
    nouns "trash", "garbage"
    article "some"
    long_desc
    {
        "A more-or-less homogenous heap of miscellaneous garbage. It \Icould\i hide something
        worthwhile, but you're not sure you if really want to go see for yourself."
    }
    before
    {
        object DoSearch
        {
            !At its creation, the squash object remains in the "nothing" object, at the root of the object tree.
            !It stays there until the PC searches the garbage.
            if parent( squash ) = nothing
            {
                "Setting aside your usually high standards of personal hygiene, you reach inside the
                trash. After a grotesque moment of rummaging, you pull out an old, dessicated squash. Your
                first reaction is to put it back in the bin. Once you do, however, the gears in your head start
                turning. A squash. Well, well..."
                !That's pretty straightforward - I move the squash object inside the garbage bin.
                !From this point on, looking inside the bin will let you see the squash.
                move squash to garbagebin
            }
            else
                "You're pretty sure there isn't anything else of any worth in there."
        }
        object DoGet
        {
            "You are \Unot\u going to carry that trash around."
        }
    }
}

!----------------------------------------------------------------------------
! CITY PARK
!----------------------------------------------------------------------------
cl_room park "Cheapsville City Park"
{
    long_desc
    {
        "The soft grass of what seems to be the only city park in Cheapsville welcome you. It seems nice
        enough, with trees, benches, and the usual elements of a park. However, since the weather today
        isn't that great (the sky is completely grey), the only human being around seems to be that poor
        sap operating the hot dog stand.
        \nTo the south, Oak Street reminds you that suburban civilization is only a few steps away."
    }
    s_to oakstreet
    cant_go
    {
        "A stroll in the park could be nice, but you still intend to win that little bet."
    }
    before
    {
        location DoSmell
        {
            "Hmmm... Hot dogs..."
        }
    }
}

scenery cl_tree
{
    article "the"
    long_desc
    {
        "Trees of various kinds abound in this city park."
    }
}

cl_tree tree "tree"
{
    in park
    nouns "tree"
}

cl_tree trees "trees"
{
    in park
    nouns "trees"
    is plural
}

scenery cl_bench
{
    article "the"
    long_desc
    {
        "You can see benches distributed evenly among the park."
    }
    is enterable
}

cl_bench bench "bench"
{
    in park
    nouns "bench"
}

cl_bench benches "benches"
{
    in park
    nouns "benches"
    is plural
    before
    {
        object DoEnter
        {
            return Perform( &DoEnter, bench )
        }
    }
}

scenery stand "hot dog stand"
{
    in park
    nouns "stand"
    adjectives "hot", "dog", "hotdog"
    article "the"
    long_desc
    {
        "Neat! A hot dog stand! It's a little early to have lunch, but the strong
        smell of the freshly cooked dogs tickles your nose."
    }
}

scenery npc_hotdogvendor "hot dog vendor"
{
    in park
    nouns "man", "guy", "person", "vendor", "clerk", "salesman", "sap"
    adjectives "hot", "dog", "hot-dog", "hotdog", "poor"
    article "the"
    long_desc
    {
        "Despite his greasy apron, this middle-aged man seems like a nice fellow. He
        keeps working behind his stand, apparently to make sure everything's ready
        for the potential customers."
    }
    is hidden
}

!----------------------------------------------------------------------------
! INTERSECTION
!----------------------------------------------------------------------------
cl_room intersection "Intersection of Oak & Main"
{
    long_desc
    {
        "Oak Street ends here, reaching Cheapsville's Main Street. Even though it's Monday,
        the whole place remains pretty calm. You can see why your friend picked this town -
        you can't get any quieter without living on a farm.
        \nThe most interesting building in the area is the Cheapsville City Bank, which stands
        proudly on the opposite side of Oak.
        \nMain Street runs east-west. You can also go north, back on Oak Street."
    }
    n_to oakstreet
    s_to { return bankdoor.door_to }
    in_to { return bankdoor.door_to }
    w_to schoolyard
    e_to outsidelibrary
    cant_go
    {
        "There doesn't seem to be anything interesting in that direction."
    }
}

door bankdoor "bank door"
{
    between intersection, citybank
    nouns "door"
    adjectives "bank"
    article "the"
    is hidden
}

scenery bankbuilding "bank"
{
    in intersection
    nouns "bank", "building"
    adjective "city", "bank"
    article "the"
    long_desc
    {
        "A brick building, roughly cubic in shape, with the words \"CHEAPSVILLE CITY BANK\" proudly
        painted on it."
    }
    door_to { return bankdoor.door_to }
}

!----------------------------------------------------------------------------
! BANK
!----------------------------------------------------------------------------
cl_room citybank "Cheapsville City Bank"
{
    long_desc
    {
        "Whoa! It's been ages since you saw an actual city bank. And apparently, today isn't
        your lucky day to see one: at this hour, they're closed. The windows are, anyway. And by the time
        they open, your little wager will be long over.
        \nOn one side of the open area is an ATM. On the other is the receptionist's desk, complete with
        receptionist."
    }
    n_to { return bankdoor.door_to }
    out_to { return bankdoor.door_to }
    cant_go
    {
        "Most of the bank is closed at this hour, and therefore you can't go there."
    }
}

scenery cl_bankwindow
{
    adjectives "teller", "bank", "clerk"
    article "the"
    long_desc
    {
        "There are a few - it looks like three - windows down there, meant to accomodate curmudgeonly
        customers who won't use the ATM. Of course, they're all closed right now."
    }
}

cl_bankwindow bankwindow "window"
{
    in citybank
    nouns "window"
}

cl_bankwindow bankwindows "windows"
{
    in citybank
    nouns "windows"
    is plural
}

scenery atm "ATM"
{
    in citybank
    nouns "atm", "machine"
    adjectives "atm", "cash"
    article "the"
    long_desc
    {
        "It seems the city bank managed to buy an ATM from some bigger bank, and then reprogram it
        for their own use. It seems operational, but is of no use to you, since you're not a client."
    }
}

scenery bankdesk "receptionist's desk"
{
    in citybank
    nouns "desk"
    adjectives "receptionist", "receptionist's"
    article "the"
    long_desc
    {
        "The desk is quite large, and on the side you're facing, featureless. The receptionist
        sits behind it."
    }
}

scenery npc_receptionist "bank receptionist"
{
    in citybank
    nouns "woman", "girl", "person", "receptionist", "secretary", "lady"
    adjectives "bank"
    article "the"
    long_desc
    {
        "A comely woman, probably in her late twenties. She'd look like a high profile
        businesswoman if her suit didn't look so rumpled, as if worn for a long, frantic period.
        \nShe looks deeply involved in her paperwork, although she looks up to you from time to
        time, to see if you actually want something from her."
    }
    is hidden
}

!----------------------------------------------------------------------------
! SCHOOLYARD
!----------------------------------------------------------------------------
cl_room schoolyard "School yard"
{
    long_desc
    {
        "Oh look, an elementary school! Isn't that nice? It means your friend has picked quite a good
        location to raise a family.
        \nBunches of kids are playing and laughing all around the school yard. Either it's
        recess, or they're having some special \"go play outside\" morning.
        \nThe school stands to the south, while Main Street extends both eastward & westward."
    }
    e_to intersection
    w_to
    {
        "You take a quick peek in that direction. There doesn't seem to be a lot of buildings,
        for a while at least. It might be better to stick to this part of town instead."
    }
    s_to
    {
        "Going inside the school? Well, you're a little too old to pass as a kid, even if you are playing a
        childish game, and you don't really want to scare anyone."
    }
    in_to { return s_to }
    cant_go
    {
        "There doesn't seem to be anything interesting in that direction."
    }
}

scenery yardschool "yard"
{
    in schoolyard
    nouns "yard", "asphalt"
    article "the"
    long_desc
    {
        "A vast open space, covered with asphalt."
    }
}

scenery school "school"
{
    in schoolyard
    nouns "school", "building"
    article "the"
    long_desc
    {
        "This school is bigger than the houses in the immediate area, but fits nicely into the neighborhood. It
        may very well be the only elementary school in the whole town. Apparently, it's called the \"My Dear
        Watson Elementary\"."
    }
    door_to { return schoolyard.s_to }
}

scenery npc_schoolkids "school kids"
{
    in schoolyard
    nouns "kids", "children", "boys", "girls"
    adjective "school", "young"
    article "the"
    long_desc
    {
        "Countless young children are running everywhere, playing, laughing, screaming, and doing
        the kind of things normal kids do on recess."
    }
    is hidden, plural
}

!----------------------------------------------------------------------------
! STREET, OUTSIDE LIBRARY
!----------------------------------------------------------------------------
cl_room outsidelibrary "Main Street, Outside Public Library"
{
    long_desc
    {
        "Main Street extends east and west from here. Aside from a few houses, the only building
        in the area is the public library, which lies on the north side of the street."
    }
    w_to intersection
    e_to outsidebowling
    n_to { return librarydoor.door_to }
    in_to { return librarydoor.door_to }
    cant_go
    {
        "There doesn't seem to be anything interesting in that direction."
    }
}

door librarydoor "library door"
{
    between outsidelibrary, publiclibrary
    nouns "door"
    adjectives "library"
    article "the"
    is hidden
}

scenery library "public library"
{
    in outsidelibrary
    nouns "library", "building"
    adjectives "public", "library"
    article "the"
    long_desc
    {
        "It's a smallish, unassuming building. You almost missed it, since it didn't look all that different
        from the other houses."
    }
    door_to { return librarydoor.door_to }
}

!----------------------------------------------------------------------------
! PUBLIC LIBRARY
!----------------------------------------------------------------------------
cl_room publiclibrary "Public Library"
{
    long_desc
    {
        "This isn't the largest library you've seen, of course. But it seems well furnished enough:
        novels, kids' books, biographies, dictionaries, encyclopedias, and other sorts of library materials.
        \nThe door leading outside is to the south. Near it is the librarian, sitting at her desk."
    }
    s_to { return librarydoor.door_to }
    out_to { return librarydoor.door_to }
    cant_go
    {
        "There isn't a way out in that direction."
    }
    before
    {
        location DoSmell
        {
            "The sweet aroma of old paper fills the building."
        }
    }
}

scenery cl_book
{
    adjectives "kids", "kids'"
    article "the"
    long_desc
    {
        "Lots of books of all types, on many different subjects. You'd love to look around in search of some rare
        gem you haven't read, but this obviously isn't the right moment."
    }
    is readable, openable
    before
    {
        object DoGet
        {
            "You don't have a need for any of these right now."
        }
        object DoRead, DoOpen
        {
            "Why yes, of \Ucourse\u! Read a few books. Heck, why not read \Uall\u of them! After all,
            it's not like there was this bet we intended to win. We're not in a big hurry or anything,
            \Uright\u?"
        }
    }
}

cl_book book "book"
{
    in publiclibrary
    nouns "book", "novel", "biography"
}

cl_book books "books"
{
    in publiclibrary
    nouns "books", "novels", "biographies"
    is plural
}

scenery cl_dictionary 
{
    article "the"
    long_desc
    {
        "Several dictionaries of all kind."
    }
    is readable, openable
    before
    {
        object DoGet
        {
            if parent( smalldictionary ) = nothing
            {
                "You begin to search for a small dictionary. Fortunately, and to your surprise, there are a
                few that can be borrowed from the library. That's great. Well, it is if you have a card... You
                pick up a smaller English dictionary that circulates.";
                !The Acquire routine tries to put the second object (the target) inside the first (the container).
                !Note that the key word here is "tries". If the container isn't currently able to hold the target
                !(most likely because container.holding + target.size > container.capacity), Acquire will return
                !false and the target won't move.
                if not Acquire( you, smalldictionary )
                {
                    " However, since you're carrying so much stuff already, you have no choice but to put it
                    back on the ground, at least for the time being."
                    move smalldictionary to publiclibrary
                }
                else
                    ""
                !Here, Kent wanted me to point out the existence of the "print newline" statement, which will
                !print a carriage return... but only if it's needed. That is, if the last time your printed some
                !stuff, you left a semicolumn at the end, the missing carriage return will be added. That can
                !come in handy if you're handling tons of print statements which may or may not have a CR at the
                !end. Still, in simple cases like above, I prefer my method. ;-)
            }
            else
                "You already picked one from the shelves. It should suffice."
        }
        object DoRead, DoOpen
        {
            "Why yes, of \Ucourse\u! Read a few books. Heck, why not read \Uall\u of them! After all,
            it's not like there was this bet we intended to win. We're not in a big hurry or anything,
            \Uright\u?"
        }
    }
}

cl_dictionary dictionary "dictionary"
{
    in publiclibrary
    nouns "dictionary"
    adjectives "other", "one"
}

cl_dictionary dictionaries "dictionaries"
{
    in publiclibrary
    nouns "dictionaries"
    adjectives "numerous"
    is plural
    before
    {
        object DoSearch
        {
            Perform( &DoGet, self )
        }
    }
}

scenery cl_encyclopedia
{
    article "the"
    long_desc
    {
        "Lots of reference books, on every subject you can think of."
    }
    is readable, openable
    before
    {
        object DoGet
        {
            "You don't have a need for any of these right now."
        }
        object DoRead, DoOpen
        {
            "Why yes, of \Ucourse\u! Read a few books. Heck, why not read \Uall\u of them! After all,
            it's not like there was this bet we intended to win. We're not in a big hurry or anything,
            \Uright\u?"
        }
    }
}

cl_encyclopedia encyclopedia "encyclopedia"
{
    in publiclibrary
    nouns "encyclopedia"
}

cl_encyclopedia encyclopedias "encyclopedias"
{
    in publiclibrary
    nouns "encyclopedias"
    is plural
}

scenery librariandesk "librarian's desk"
{
    in publiclibrary
    nouns "desk"
    adjectives "librarian", "librarian's", "library"
    article "the"
    long_desc
    {
        "An old wooden desk, worn by the years. It's currently occupied by the librarian herself."
    }
}

scenery npc_librarian "librarian"
{
    in publiclibrary
    nouns "woman", "lady", "librarian", "clerk"
    adjective "library", "librarian"
    article "the"
    long_desc
    {
        "Although she's probably in her mid-thirties, this librarian looks slightly older at first glance,
        due to her \I(very)\i sharp dress, her \I(nice)\i horned-rimmed glasses, and her \I(long)\i brown hair up
        tightly in a bun. When you look at her more closely, however, you can see a flash of youth in her
        \I(gorgeous)\i blue eyes. Apparently, she just likes to dress based on the Ultimate Librarian
        Archetype. Well, you're not the one who'll complain. No sir-ree... In fact, right now you're trying to
        sneak a peek of her \I(long)\i legs lying \I(elegantly)\i along the desk. You can't help but wonder if
        she circulates."
    }
    is hidden
}

!----------------------------------------------------------------------------
! STREET, OUTSIDE BOWLING ALLEY
!----------------------------------------------------------------------------
cl_room outsidebowling "Main Street, Outside Bowling Alley"
{
    long_desc
    {
        "Ah, finally! After all the niceness and cozyness of this little town, you've found a clear sign
        of modern corruption: the bowling alley. And it's already open, lucky you! The entrance
        stands to your south. You can also escape this place by following Main Street."
    }
    s_to { return bowlingdoor.door_to }
    in_to { return bowlingdoor.door_to }
    w_to outsidelibrary
    e_to
    {
        "You take a quick peek in that direction. There doesn't seem to be a lot of buildings,
        for a while at least. It might be better to stick to this part of town instead."
    }
    cant_go
    {
        "There doesn't seem to be anything interesting in that direction."
    }
}

door bowlingdoor "bowling alley door"
{
    between outsidebowling, bowlingalley
    nouns "door"
    adjectives "bowling", "alley"
    article "the"
    is hidden
}

scenery bowlingbuilding "bowling alley"
{
    in outsidebowling
    nouns "bowling", "alley", "building"
    adjectives "bowling"
    article "the"
    long_desc
    {
        "Although you're no fan of bowling alleys, at least you must commend this one for not using one
        of those tacky animated neon signs you hate so much. Then again, maybe they just lacked the
        budget."
    }
    door_to { return bowlingdoor.door_to }
}

!----------------------------------------------------------------------------
! BOWLING ALLEY
!----------------------------------------------------------------------------
cl_room bowlingalley "Bowling Alley"
{
    long_desc
    {
        "This place might be open, but it's fairly empty at this time of the day. A few enthusiastic
        bowlers are practicing for their next tournament, and that's about it.\n
        Your sharp eyes do notice something interesting, though: a door marked \"STORAGE - EMPLOYEES
        ONLY\"";
        if storagedoor is open
            ", slightly ajar."
        else
            "."
    }
    n_to { return bowlingdoor.door_to }
    out_to { return bowlingdoor.door_to }
    in_to { return storagedoor.door_to }
    cant_go
    {
        "There isn't a way out in that direction."
    }
}

door storagedoor "storage room door"
{
    between storageroom, bowlingalley
    nouns "door"
    adjectives "storage", "room", "employees"
    article "the"
    is hidden
}

scenery bowlingstuff "bowling equipment"
{
    in bowlingalley
    nouns "equipment", "lanes", "lane", "pins", "pin"
    adjective "bowling"
    article "the"
    long_desc
    {
        "Typical bowling equipment. Nothing worth spending your time on."
    }
    before
    {
        xobject DoThrowAt
        {
            if object = bowlingball
                return Bowling
        }
    }
}

scenery npc_bowlers "bowlers"
{
    in bowlingalley
    nouns "bowlers", "players", "bowler", "men"
    adjective "bowling"
    article "the"
    long_desc
    {
        "You can see, all around the place, several bowlers practicing in different alleys. Most
        of them seem to be over 40, which seems... apropriate."
    }
    is hidden, plural
}

!----------------------------------------------------------------------------
! STORAGE ROOM
!----------------------------------------------------------------------------
cl_room storageroom "Storage Room"
{
    long_desc
    {
        "This storage room would be spacy, if it wasn't completely filled with boxes and boxes
        of now-useless stuff. Only a few narrows paths allow you to walk across the room.\n
        Something in the corner of the room catches your eye almost immediately: an old IBM XT,
        sitting in all its glory on a dusty table."
    }
    out_to { return storagedoor.door_to }
    cant_go
    {
        "The room isn't \Uthat\u big. If you want to exit, just say so."
    }
}

scenery cl_box
{
    article "the"
    long_desc
    {
        "Those boxes might be filled with interesting stuff, but 1) they're tightly packed, and
        2) they're not yours."
    }
    is openable, not open
    before
    {
        object DoOpen
        {
            "Those boxes might be filled with interesting stuff, but 1) they're tightly packed, and
            2) they're not yours."
        }
    }
}

cl_box box "box"
{
    in storageroom
    nouns "box", "stuff"
}

cl_box boxes "boxes"
{
    in storageroom
    nouns "boxes"
    is plural
}

scenery computertable "table"
{
    in storageroom
    nouns "table"
    adjectives "computer", "old", "dusty"
    article "the"
    long_desc
    {
        "It's an old dusty table whose sole purpose is now to support a (possibly older) computer."
    }
}

scenery computer "IBM XT"
{
    in storageroom
    nouns "computer", "ibm", "xt", "beast", "pc"
    adjectives "ibm", "xt", "old"
    article "the"
    long_desc
    {
        "It's been quite a while since you saw once. Well, since the last flea market you've been
        to. A true antique.\n
        Your keen eye is drawn to the 5 1/4\" floppy drive right in the middle of the beast."
    }
    is container, switchable, openable, open
    before
    {
        object DoGet, DoMove
        {
            "No way! Those old computers were \Umassive\u!"
        }
        object DoSwitchOn
        {
            "Sorry pal, it looks toast."
        }
        object DoOpen, DoClose, DoLookIn
        {
            return Perform( verbroutine, floppydrive )
        }
        object DoPutIn
        {
            return Perform( &DoPutIn, object, floppydrive )
        }
    }
}

scenery floppydrive "floppy drive"
{
    in computer
    nouns "drive", "lid"
    adjectives "disk", "floppy", "drive"
    article "the"
    long_desc
    {
        "This storage unit - the only one this computer has, actually - is in front of the computer, the lid ";
        if self is open
            "open."
        else
            "closed."
    }
    is openable, not open, container
    before
    {
        object DoPutIn
        {
            "There's no need to put anything in that drive."
        }
    }
}

!----------------------------------------------------------------------------
! INVENTORY OBJECTS
!----------------------------------------------------------------------------
!Finally, here they are. Since this version is still missing numerous puzzles, several objects will just be
!"lying there", in various locations.

object money "money"
{
    in you
    nouns "money", "cash", "coins", "bills"
    article "some"
    long_desc
    {
        "You're carrying a few coins and some bills. Not much, but probably enough to
        buy a few trinkets."
    }
    before
    {
        object DoDrop, DoGive, DoPutIn
        {
            !Sleazy trick to prevent the player from spreading his money around.
            "You'd rather keep your money on yourself."
        }
        object DoCount
        {
            "You've got more than enough for the day."
        }
    }
}

object huntlist "object list"
{
    in you
    nouns "list", "note", "paper"
    adjectives "object", "item"
    article "an"
    long_desc
    {
        "It's a small paper listing all the objects you have to find to win the bet. Your
        friend and yourself made it by picking random pages in one book he had.
        \nHere's what's written on it:"
        !Many players prefer it if looking at objects with short writing on it also provides that writing directly.
        Perform( &DoRead, huntlist )
    }
    !Short descriptions are used when a non-hidden object is directly placed within a room. If you don't specify
    !a short_desc, you'll get a generic "An object list is here." comment.
    short_desc
    {
        "You see a small paper with a list of objects on them."
    }
    is readable
    size 1
    before
    {
        object DoRead
        {
            !Just an alternate way to change font styles. This code used to be mandatory, as there was a bug when
            !applying italic to a very long string, but Kent fixed that. (Yay!)
            Font( ITALIC_ON )
            "\n\UItems to find:\u\n\n* A calculator\n* A pencil sharpener\n* A dictionary
            \n* A 5 1/4\" floppy disk\n* A squash racket\n\nEvery item must be brought back to the house."
            Font( ITALIC_OFF )
        }
    }
}

object bowlingball "bowling ball"
{
    in closet
    nouns "ball"
    adjectives "bowling", "black"
    article "a"
    long_desc
    {
        "A big, black, heavy bowling ball. Your friend lent it to your a couple times
        in the past. The holes don't exactly line up with your fingers, but you can still
        get a decent grip."
    }
    short_desc
    {
        "A bowling ball sits over here."
    }
    size 30
    before
    {
        object DoPush, DoMove
        {
            "You know, this is \Unot\u how you bowl. (Just making sure.)"
        }
    }
}

object airhorn "air horn"
{
    in drawer
    nouns "horn", "can"
    adjectives "air"
    article "an"
    long_desc
    {
        "Aah, the infamous air horn. You just love when your friend brings it to the game. It
        really annoys some of your fellow fans, but what the heck.\n
        This can is about half-full. You could still a few good blows out of it."
    }
    short_desc
    {
        "There is a air horn lying on the ground."
    }
    size 10
    before
    {
        object DoBlow, DoPlay
        {
            if ( location = friendshome ) and ( parent( self ) = squash )
            {
                !This is where the "special" attribute of the squash is set. I only wanted the player to be able
                !to "bring the squash racket" in the house once, so I set the attribute and then make sure he won't
                !do it again. It's common trick to have things that only happen once.
                if squash is special
                    "No need to go through that again."
                else
                {
                    squash is special
                    "Without warning, you press the horn trigger. A resounding blast goes
                    through the house and beyond it. After a few painful seconds, you stop.\n
                    \"And just what the heck do you think...\", starts your friend.\n
                    At the same moment, you both hear a faint voice, probably coming from
                    a neighbor, screaming \"STOP THAT RACKET!\".\n
                    You smile.\n
                    \"No, wait\", your friend starts. \"You're not serious...\"\n
                    \"Well, technically, it was indeed a racket, coming from a squash, and I
                    \"brought\" it inside the house...\"\n
                    \"Dude, this isn't \"Nord & Bert\" or something. This is ridiculous!\"\n
                    You two argue for a little while, but in the end, you win. You brought a
                    squash racket in the house, and so be it."
                }
            }
            else
            {   
                !Here's a "select" statement. It checks the value of one variable and execute the matching
                !statement(s).
                select location
                    case park
                        "Yes, blowing the horn around here wouldn't probably disturb anyone... Which is
                        precisely why you don't see the purpose in doing so."
                    case bowlingalley, storageroom, publiclibrary
                        "Given your current location, you'd rather keep quiet."
                    case else
                        "You don't think it'd be reasonable to disturb all the neighborhood right now."
            }
        }
    }
}

object squash "dessicated squash"
{
    nouns "squash"
    adjectives "old", "dessicated"
    article "a"
    long_desc
    {
        "Bleh. This squash has spent a good deal of time in the garbage. It's part rotten,
        part dessicated. A piece of it was bitten off, exposing the inside.\n
        Under normal circumstances, you'd \Unever\u carry something like around. But right now..."
    }
    short_desc
    {
        "A dessicated old squash sits lumply on the ground."
    }
    is container
    capacity 10
    holding 0
    size 15
    before
    {
        object DoSmell
        {
            "You catch the beginning of a whiff, and quickly change your mind."
        }
        object DoEat
        {
            "You're not hungry not to eat it at this moment. In fact, come to think of it, you
            doubt you'll ever be hungry enough to eat \Uthis\u!"
        }
    }
}

object hotdog "hot dog"
{
    in park
    nouns "hotdog", "hot-dog", "dog", "dressing", "dressings"
    adjectives "hot"
    article "a"
    long_desc
    {
        "A reasonably large hot dog, the kind you find in ball parks. Warm, well-cooked, with
        your favorite dressings. Yummy!"
    }
    short_desc
    {
        "One hot dog was carefully placed on the ground here."
    }
    size 10
    before
    {
        object DoSmell
        {
            "Smell delicious!"
        }
        object DoEat
        {
            "This is a very tempting idea. However, the scavenger hunt should be your only
            concern for the moment. You guess that it'll still taste good went the hunt is
            over. Besides, it might always come in handy..."
        }
    }
}

object pen "pen"
{
    in citybank
    nouns "pen", "calculator"
    adjectives "calculator"
    article "a"
    long_desc
    {
        "This shiny pen bears, on one tip, a teenie-weenie built-in calculator. It doesn't work,
        of course. Most of these pen were piece of crap, as you well remember. But it's a
        calculator nevertheless, clearly valid as one of the items you seek."
    }
    short_desc
    {
        "There's a pen on the ground."
    }
    size 5
}

object sharpener "pencil sharpener"
{
    in schoolyard
    nouns "sharpener"
    adjectives "pencil"
    article "a"
    long_desc
    {
        "A small pencil shapener. Insert pencil, turn pencil, repeat if necessary. Made of light
        plastic, it probably came as a freebie with a pencil case."
    }
    short_desc
    {
        "Your keen eyes notice a small pencil sharpener."
    }
    size 3
}

object librarycard "library card"
{
    in publiclibrary
    nouns "card"
    adjectives "library"
    article "a"
    long_desc
    {
        "A small plastic card, bearing only the Cheapsville city logo and a bar code. \IA bar code?\i
        How modern!"
    }
    short_desc
    {
        "You notice a library card over here."
    }
    is readable
    size 5
    before
    {
        object DoRead
        {
            "Cheapsville's Public Library - Membership Card"
        }
    }        
}

object smalldictionary "small English dictionary"
{
    nouns "dictionary"
    adjectives "small", "english"
    article "a"
    long_desc
    {
        "A small but slightly heavy English dictionary. Based on the what you read inside the
        back cover, this one can be borrowed from the library."
    }
    short_desc
    {
        "You can see a small English dictionary here."
    }
    is readable, openable
    size 30
    parse_rank 1 ! To outrank the dictionary scenery
    before
    {
        object DoRead, DoOpen
        {
            "By the time you go through the whole dictionary, the bet will obviously be lost. Of course, by
            then you'll have tons of lovely new words to express your disappointment..."
        }
    }
}

object floppydisk "floppy disk"
{
    in floppydrive
    nouns "disk", "floppy", "diskette"
    adjectives "floppy", "5.25"
    article "a"
    long_desc
    {
        "This thing brings back countless memories. Ah, those nice old 5 1/4\" floppies. So elegant, so
        slim... so fragile, so large, so darn prone to loss of data. Good riddance."
    }
    short_desc
    {
        "There is a 5 1/4\" floppy disk over here."
    }
    size 15
}


!----------------------------------------------------------------------------
! NEW VERB ROUTINES
!----------------------------------------------------------------------------

routine DoRead
{
    ! There is no 'default response' - Reading is handled by each readable object
    return true
}

routine DoPutOn
{
    ! Because containers & platforms share the same core code, we can reuse DoPutIn
    return DoPutIn
}

routine DoBlow
{
    ! Fails by default
    "I don't see how you could blow that."
}

routine DoPlay
{
    ! Fails by default
    "Is that a game? A song? I'm afraid I'm not familiar with it..."
}

routine DoGiveUp
{
    "And mow your friend's lawn for the whole summer? NEVER!"
}

routine DoBowl
{
    if not location = bowlingalley
        "This isn't an appropriate location to play bowling."
    else
        !The Contains routine lets you know if object A is an "ancestor" of object B. It basically parses the
        !object to see if the bowling ball is a child (or a grandchild, and so on) of the bowling alley.
        !This is NOT like using FindObject, as it doesn't do anything more than looking at the object tree.
        !(Some scenery which is "found in" a room wouldn't be contained by it, for instance.)
        if not Contains( bowlingalley, bowlingball )
            "I don't see any bowling ball around here. That is, any \Bavailable\b one."
        else
            return Bowling
}

routine DoCount
{
    ! Fails by default
    "There's no need to count that."
}

routine Bowling
{
    "You pick a free lane, grab a good hold on your ball, and shoot. Looking good... Looking good... Look - DOH!
    Oh well... You never were really good at this anyway."
    return true
}

routine DogDeath
{
    "\n\n\nYou'll never be quite to remember the exact events that followed. You were told later on that
    there was some crazed pitbull sleeping quietly in the doghouse. You startled him, so he decided to rip
    one of your hands off. It didn't turn out to be a big deal -- the microsurgeon who was on call at
    Cheapsville General Hospital was able to reattach it easily, and your friend managed, with the help of his
    neighbor, to get the hand back before it had been gnawed on too severely. So much for the quiet \"small
    town\" feeling. Well, it might not be as bad as losing a limb, but...
    \n\n\B***  You have lost your bet  ***\b"
    endflag = 3
}