RB §6.1. Designing New Commands

Quite a bit of interactive fiction design involves the creation of custom commands to expand on the library's existing set. There is more to know than we can review in this section; instead, this is to serve as an overview of the process, with hints about where in Writing with Inform we might find more technical details.

Before we even start to write our source text, we should think about the following things:

(1) What words will the player use to make this new action happen?
(2) What will the action change about the world model?
(3) What circumstances might make the new action go wrong or produce silly outcomes?

To take these one one by one:

(1) We may have a general idea of the phrasing we want the player to use -- say we want to add an SHOOT command which allows the player to fire a gun at something. (This is an intentionally tricky choice of verb, because it shows off so many possibilities.) So we might decide the base form of the action will be

SHOOT THE PISTOL AT HENRY

So now we're going to need an action that applies to two objects -- the pistol as the noun, and Henry as the second noun. The problem is, though, that there are lots of other ways that the player could reasonably formulate the command, some of which leave out information:

SHOOT HENRY
SHOOT PISTOL
FIRE PISTOL
SHOOT AT HENRY
SHOOT AT HENRY WITH GUN

To avoid frustrating the player, we should make a guess about what the player means whenever we're sure that guess will be reliable (we might, for instance, have only one gun in the story, so we know that SHOOT HENRY will always mean SHOOT HENRY WITH PISTOL), but ask the player for clarification whenever there might be ambiguity (SHOOT PISTOL gives no clue about the target, nor can we safely guess, so we want Inform to ask "What do you want to shoot the pistol at?"). The next section goes into more detail about how to handle these variations.

Conversely, there are cases where the player is offering too much information for the command we've defined - say we have a BURN command which doesn't look for a specified fire source, but the player is trying to BURN BOX WITH MATCH. We probably don't want to throw away the extraneous information as though it had never been typed, because the player might have typed something quite specific. BURN BOX WITH ACID, say, should not be cavalierly reinterpreted as BURN BOX (with a fire source). Instead, we want to give the player a bit of gentle guidance, perhaps using "Understand as a mistake", as in

Understand "burn [something] with [text]" as a mistake ("Your choice of lighter isn't important in this story: BURN SOMETHING will suffice.")

Finally, there are some cases where we want to understand a phrase to mean a specific form of a more general action. For instance, we might want TURN DOWN THE MUSIC to mean the same thing as SET VOLUME KNOB TO 1. In this case, we may want to make a sort of dummy action which converts into the main action, as in

Understand "turn down volume" or "turn down music" or "turn down the volume" or "turn down the music" as lowering the volume. Lowering the volume is an action applying to nothing.

Instead of lowering the volume, try setting the volume knob to 1.

More about this can be found later in this chapter, under Remembering, Converting and Combining Actions.

Sometimes these kinds of details can be caught in play-testing, but it's a good idea to think about them specifically and in advance rather than leaving them to our beta-testers to sort out.

(2) To generalize very broadly, there are two possible kinds of command in IF: those that only exist to give the player new information (like EXAMINE, INVENTORY, LOOK, TASTE), and those that change the world model (like TAKE FISH, OPEN DOOR, UNLOCK GATE WITH BLUE KEY). The Inform library has some commands that really do none of these things by default - commands like JUMP that do nothing interesting at all most of the time - but those exist as hooks, in case there is ever something important for them to do.

Commands that ask for information are usually easier to implement. Very often we're looking to offer the player a new kind of information about specific objects, and these can be handled by adding new text properties, as in

A thing has some text called the sacred emanation.

Carry out perceiving something:
    say "[sacred emanation of the noun][paragraph break]".

Commands that affect the world model, on the other hand, can range from simple to very complex indeed. Sometimes we need to do nothing more than add an attribute to an object, like

A thing can be folded or flat. A thing is usually flat.

so that our FOLD command can change the object into its folded form. At other times, we need quite intricate rules to account for a subtle multi-stage process - how fire is burning and spreading to objects, say, or how a conversation is progressing. Other parts of the Recipe Book offer solutions to some of these challenges.

(Strictly, we might count a third kind of command: the kind that controls the story itself. The Advanced Actions chapter discusses how to add actions out of world, as these are called, but the difficult ones are already built into Inform - saving, restoring, restarting, undoing a turn, and so on. Mostly when we need to add new actions out of world, they will be help or hint systems of some kind. More about these can be found in the Helping and Hinting section of the Recipe Book, under Out of World Actions and Effects.)

(3) Most commands that change the world require certain preconditions: the player needs to be holding the gun before he can fire it; the gun must be loaded with ammunition; if we're being especially detailed in our simulation, the safety must be off.

Often, there are also subtler details about how the command should interact with special items. For any new command we create, it's worth asking: should anything special happen if the player performs this action...

On himself?
On another living character?
On an object he (or another character) is carrying or wearing?
On an object he (or another character) is inside or on?
On a door?
On an object that is impossible to move (defined as "scenery" or "fixed in place")?
On an intangible object (such as a beam of sunlight)?
On an object far away (such as the sun)?
On an object that is part of something else (such as a doorknob)?
On an object that itself has parts (such as a desk with drawers)?
If there are two objects required by the action, can both the noun and the second noun be the same thing?

For instance, we might have written code so that if the gun is fired at anything but a person or a fragile object, the default response is "The bullet bounces harmlessly off [the second noun]." Our checklist would remind us to write special cases to prevent

SHOOT GUN AT MY SHOE (while he's wearing it)
SHOOT GUN AT ME
SHOOT GUN AT GUN

and so on. Actions that destroy objects are especially tricky, because there are many things that aren't safe to destroy without carefully adjusting the world model. (What happens if we burn a door connecting two rooms? a wooden desk with a drawer containing an asbestos vest? the armchair Cousin Fred is sitting on?)

RB §6.2. Writing New Commands

Once we've considered all the design issues pertaining to a new action, we're ready to start writing the source text. First we need to give the player a way to issue the command:

Understand "smile" as smiling.
Understand "fold [something]" as folding.
Understand "shoot [something preferably held] at [something]" as shooting it with.
Understand "wrap [something preferably held] in [something preferably held]" as wrapping it in.

(Note how "it" stands in for the first item when we have an action requiring two objects.) The things that go in square brackets are called "tokens": they are blank spaces for the player to fill in with story objects. The different kinds of tokens are explained in the chapter on Understanding.

We can add synonyms with

Understand the command "grin" as "smile".

and we can create reversed versions of commands with

Understand "shoot [something] with [something preferably held]" as shooting it with (with nouns reversed).

These variations are also covered in the Understanding chapter. If the action needs to work on things that aren't within the player's sight or reach in the normal way, we may need to use an [any thing] token (see the Understanding chapter), as in

Understand "contemplate [any thing]" as considering.

We may also need to modify reach or light levels (see Changing reachability and Changing visibility in the Advanced Actions chapter), or rely on the Deciding the scope of... activity.

As for guessing the player's intention when he isn't clear, we may want to consult the Does the player mean rules (to help Inform make guesses between multiple possible targets) and the activities Supplying a missing noun and Supplying a missing second noun (to help Inform guess an appropriate item when the player leaves something entirely out of his command). For instance, if the player typed SHOOT HENRY, it is the supplying a missing noun/second noun activity that would allow us to make Inform draw the obvious conclusion that he shoots Henry with the pistol in his hand. The Does the player mean rules are discussed in the chapter on Advanced Actions; the activities in the Activities chapter.

Next we need to define our new action, as in

Smiling is an action applying to nothing.
Folding is an action applying to one thing.
Wrapping it in is an action applying to two carried things.

In cases where we're using an "[any thing]" token to let the player affect objects that aren't normally visible or reachable, we'll need to define the action to apply to visible objects. This tells Inform that the player doesn't have to be able to touch the object for it to work. So for instance

Considering is an action applying to one visible thing.

For more on this topic, see Visible vs. touchable vs. carried in the Advanced Actions chapter.

The next step is to create rules for Inform to follow when the action happens. These can be check rules (which make sure that the conditions for the action to occur are fulfilled); carry out rules (which perform the action); and report rules (which describe the results of the action to the player). Any new action should have at least a report rule to let the player know what has happened (if anything), and a carry out rule if there are any ramifications for the world model. For instance:

Carry out folding:
    now the noun is swan-like.

Report folding:
    say "You deftly fold [the noun] into the shape of a swan."

It's important to remember that report rules may be describing something whose name is plural, such as papers or shoes, and write our text so that it sounds right either way; see the chapter on Adaptive Text and Responses.

More about defining actions and creating carry out and report rules may be found in the chapter on Advanced Actions.

Meanwhile, the check rules give us a chance to provide sensible restrictions on how the command works, as in

Check folding:
    if the noun is not a napkin:
        say "[The noun] won't bend." instead.

Check shooting something with the noun:
    say "[The noun] is incapable of aiming at itself." instead.

Check burning something which contains the player:
    say "You're not quite desperate enough to make a funeral pyre for yourself just yet." instead.

The chapter on Advanced Actions explains how check rules work. In the special case where we want the player to take things automatically before using them, we may want to define the action to work only on carried objects, as in

Wrapping it in is an action applying to two carried things.

The activity Implicitly taking something (documented in the Activities chapter) allows us to modify what should happen during this process.

Lastly, a word or two about trouble-shooting. If a newly created command seems not to be working, we can discover what action Inform is really generating with the ACTIONS testing command, as in

>actions
Actions listing on.

>i
[taking inventory]
You are carrying nothing.

[taking inventory - succeeded]

If the desired command is not happening, we may need to review our understand lines. A common problem is that our new action conflicts with one already defined by default. In that case, we may want to check the Actions index and see whether there are already-defined actions which might conflict with it. If so, we may need to redefine a command with a line like

Understand the command "stand" as something new.

If that's not enough, we can get a comprehensive view of everything that happens during an action with RULES: this will list all the check, carry out, and report rules that Inform is using to perform the command.

See also

Memory and Knowledge for more about the any token and the concept of scope to control what the player may refer to in a command

RB §6.3. Modifying Existing Commands

Much of the rest of this chapter discusses the behavior of specific commands in Inform's command library, and how we might change and build on these. This section is instead an overview of the general principles: where and how can one intervene?

Whenever we are dealing with actions, the Actions Index is likely to be useful: it lists all the actions currently implemented, whether in our own source or in extensions or the Standard Rules, and lists the rules pertaining to each.

The lightest and easiest way to change behavior is with an Instead rule:

Instead of eating the apple:
    say "It turns out to be made of beeswax, so that's a non-starter."

Instead of tasting an edible thing:
    say "It's delicious!"
    rule succeeds.

The addition of "rule succeeds" tells Inform that the instead action was a success rather than a failure; this is not usually very important with the player's own actions, but can be useful for actions performed by other characters, so that a successfully replaced action is not followed by the disconcerting line

Clark is unable to do that.

Before and After offer alternative easy forms of modification; the Basic Actions chapter explains all three.

Changing the way an action works in all cases is usually better addressed by changing the main rulebook, rather than with one (or many) instead rules. We may add new check, carry out, and report rules to existing action rulebooks. The Advanced Actions chapter describes these, and ends with some guidelines on when to use before, instead, and after, and when to use check, carry out, and report.

Similarly, we may delete, move, or replace rules that are already present (see the chapter on Rulebooks). This is handy if we decide that an action has restrictions that we dislike and want to abolish. If the restriction we need to change is part of the accessibility rules - those which check whether the player can take, see, and touch items - we may need to look at Changing reachability or Changing visibility in the Advanced Actions chapter (to revise what is allowed), at Deciding the scope of something in the Activities chapter (to influence what can be seen when).

If, for instance, the player character is a burly fellow who can lift any other character he likes:

The can't take other people rule is not listed in any rulebook.

...and rip knobs off doors:

The can't take component parts rule is not listed in the check taking rulebook.

...and commit petty theft:

The new can't take people's possessions rule is listed instead of the can't take people's possessions rule in the check taking rulebook.

This is the new can't take people's possessions rule:
    if someone (called the owner) carries the noun:
        say "(first waiting until [the owner] is distracted)";

The right approach to use also depends a bit on how systematic a change we anticipate. We may find that instead rules become cumbersome when we want to specify behavior for a very large number of objects. It's fine to have

Instead of tasting the arsenic:
    say "You'll live to regret this very very shortly.";
    end the story.

but a bit more tedious to have to write

Instead of tasting the peppermint: ...
Instead of tasting the plate: ...
Instead of tasting the banister: ...
Instead of tasting the donkey: ...
(etc.)

in a story in which most items have unique flavor descriptions. In that situation, it may be more sensible to overhaul the design of the action: create a new text property for things, and revise "tasting" so that it now consults this property:

The block tasting rule is not listed in any rulebook.

A thing has some text called the flavor. The flavor of a thing is usually "Nothing special."

Report tasting something:
    if the flavor of the noun is "Nothing special.":
        say "You taste nothing unexpected." instead;
    otherwise:
        say "[the flavor of the noun][paragraph break]" instead.

Report someone tasting something:
    say "[The actor] licks [the noun]."

Finally and most sweepingly, we can rip out whole passages of the Standard Rules and replace them - or not. This is a drastic measure and rarely necessary (or so we hope); but see the Extensions chapter for ways to replace sections of existing source, or even revise the Inform 6 template files on which Inform depends. By these means almost anything can be changed. We can throw out a whole range of existing commands and start from scratch, for instance, if we want Inform to know about a completely new and different command set.

See also

Magic (Breaking the Laws of Physics) for a hat that lets the player walk through closed doors, and an NPC able to reach through solid containers

Examples

214. Slogar's Revenge ★★★

Under most circumstances, locking and unlocking require the player to be carrying the key he uses to unlock something. This makes sense -- unless the key is on a keychain, or on a chain around his neck, for instance. So here we explore one way to circumstantially override the carrying requirements, while still making sure that the player cannot unlock the door if the unlocking tool is nowhere in sight.

In essence, we are rewriting the carrying requirements rule with a different one of our own devising, and swapping it in only at those moments when it is correct to do so.

paste.png "Slogar's Revenge"

Section 1 - Procedure

The amulet carrying rule substitutes for the carrying requirements rule when locking something with the Amulet of Tumblers.

The amulet carrying rule substitutes for the carrying requirements rule when unlocking something with the Amulet of Tumblers.

We can now replace the usual behavior of the carrying requirements rule (to check whether the player is carrying something and, if not, to generate an implicit take) with a similar rule of our own; note that "if the player has the second noun" is a more compact way to write "if the player carries the second noun or the player wears the second noun":

This is the amulet carrying rule:
    if the player has the second noun:
        continue the action;
    say "(first picking up the amulet)[command clarification break]";
    try silently taking the second noun;
    if the player is not carrying the second noun:
        stop the action;

Section 2 - Scenario

The Daunting Dungeon is a room.

West of the Daunting Dungeon is the Disturbing Door. The Disturbing Door is a door. West of the Disturbing Door is the Fallow Field.

The Disturbing Door is closed and locked.

The player wears the Amulet of Tumblers. The Amulet of Tumblers unlocks the Disturbing Door.

Test me with "unlock disturbing door with amulet / open door / west / remove amulet / close door / lock disturbing door with amulet / drop amulet / unlock disturbing door with amulet".

For a more systematic handling of the keychain problem (and a number of other refinements to the behavior of doors), see the Locksmith extension included with Inform.

RB §6.4. Looking

Looking is quite a complicated command, since the production of a room description takes many steps. A detailed description of this process may be found in the Room Descriptions section.

By convention, a player sees full descriptions of rooms he enters more than once, but may type BRIEF in order to see shorter descriptions, and SUPERBRIEF tells the story never to print room descriptions at all. VERBOSE restores the default behavior.

These conventions are not always appropriate, however, especially in works where experiencing a changing environment is essential. The use option

Use brief room descriptions.

changes the default behavior so that rooms are not always described fully to the player. Verbosity demonstrates how this works.

The player always has the option of turning room descriptions to BRIEF or SUPERBRIEF mode. Verbosity 2 demonstrates how we might remove the player's ability to change the default behavior.

See also

Room Descriptions for a detailed description of how Inform creates room descriptions and how to change the results
Going, Pushing Things in Directions for ways to change just those room descriptions that are shown as the result of the player's movement
Memory and Knowledge for ways to change the room description in response to the player character's knowledge at any given stage of play

Examples

2. Verbosity 1

By default, the description of a room is printed every time the player enters a room.

On a device with very limited screen space, however, we might wish to supplant that behavior with "brief" descriptions. In Brief mode, Inform prints room descriptions only when the player enters that room for the first time. Afterwards, the text is skipped, for brevity, though the player can see it again at any time by typing LOOK.

As we saw in the previous chapter, we can set "use options" to control certain aspects of the player's experience. One of the use options is the option to

Use brief room descriptions.

which changes the defaults so that the description of a room is printed only the first time the player enters.

paste.png "Verbosity"

Use brief room descriptions.

The Wilkie Memorial Research Wing is a room. "The research wing was built onto the science building in 1967, when the college's finances were good but its aesthetic standards at a local minimum. A dull brown corridor recedes both north and south; drab olive doors open onto the laboratories of individual faculty members. The twitchy fluorescent lighting makes the whole thing flicker, as though it might wink out of existence at any moment.

The Men's Restroom is immediately west of this point."

The Men's Restroom is west of the Research Wing. "Well, yes, you really shouldn't be in here. But the nearest women's room is on the other side of the building, and at this hour you have the labs mostly to yourself. All the same, you try not to read any of the things scrawled over the urinals which might have been intended in confidence."

Test me with "west / east".

If we type "test me" during play, these commands will be carried out automatically, and we can see that when we return to the Research Wing, the description is not given a second time.

Some notes: the player can also turn full-length descriptions on or off with the commands "verbose" and "brief", or set a minimal-description setting with the command "superbrief". This power still belongs to the player even if we have set the use option to show brief room descriptions by default.

Moreover, we can ourselves check what the state of the descriptions is, with

if set to sometimes abbreviated room descriptions: ...
if set to unabbreviated room descriptions: ...
if set to abbreviated room descriptions: ...

Finally, it is possible to exercise more precise control over what the player sees on his first and subsequent visits to a room; see the next example for details.

395. Verbosity 2

Suppose that we want the player always to see full room descriptions, even if he tries to reset the defaults -- perhaps because there is vital information there which he will miss if he turns off full-length room descriptions.

To do this, we might want to remove the standard behavior of the three actions associated with BRIEF, SUPERBRIEF, and VERBOSE, replacing them with explanatory messages about how the game behaves. We cannot use Instead to override these actions, because Instead rules do not apply to actions out of world. Instead, we will want to remove and replace the carry out rules.

We can do this easily by going to the Actions Index, looking up the detail panel for, say, "preferring abbreviated room descriptions", and click the "unlist" button to paste in the sentence that will remove this rule from the rulebook.

Let's remove all three of the carry out rules and substitute our own:

paste.png "Verbosity 2"

Section 1 - Procedure

The prefer unabbreviated room descriptions rule is not listed in the carry out preferring unabbreviated room descriptions rulebook.

The prefer sometimes abbreviated room descriptions rule is not listed in the carry out preferring sometimes abbreviated room descriptions rulebook.

The prefer abbreviated room descriptions rule is not listed in the carry out preferring abbreviated room descriptions rulebook.

Carry out preferring unabbreviated room descriptions:
    say "[story title] always provides full-length descriptions for your reading pleasure."

Carry out preferring sometimes abbreviated room descriptions:
    say "For your playing protection, [story title] provides only full-length room descriptions."

Carry out preferring abbreviated room descriptions:
    try preferring sometimes abbreviated room descriptions instead.

The standard report preferring abbreviated room descriptions rule is not listed in the report preferring abbreviated room descriptions rulebook.

The standard report preferring unabbreviated room descriptions rule is not listed in the report preferring unabbreviated room descriptions rulebook.

The standard report preferring sometimes abbreviated room descriptions rule is not listed in the report preferring sometimes abbreviated room descriptions rulebook.

Use full-length room descriptions.

Section 2 - Scenario

The Wilkie Memorial Research Wing is a room. "The research wing was built onto the science building in 1967, when the college's finances were good but its aesthetic standards at a local minimum. A dull brown corridor recedes both north and south; drab olive doors open onto the laboratories of individual faculty members. The twitchy fluorescent lighting makes the whole thing flicker, as though it might wink out of existence at any moment.

The Men's Restroom is immediately west of this point."

The Men's Restroom is west of the Research Wing. "Well, yes, you really shouldn't be in here. But the nearest women's room is on the other side of the building, and at this hour you have the labs mostly to yourself. All the same, you try not to read any of the things scrawled over the urinals which might have been intended in confidence."

Test me with "west / east / brief / w / e / superbrief / w / e / verbose".

RB §6.5. Examining

By default, examining an object shows its description, and - for devices - tells us whether the object is switched on or switched off.

This kind of additional information is not always what we want, so if we have a device whose on/off status we want to conceal, we may write

The examine described devices rule is not listed in any rulebook.

On the other hand, there are times when we may want to add a similar line or two to the descriptions of other kinds of objects. Crusoe ★★★ allows us to append an "It is charred." sentence to the end of descriptions of things we have burned in the fire. Since it works by introducing a "printing the description" activity, Crusoe is also a good example to start from if we want to introduce more complex, flexible descriptions of items throughout our story.

Odin rewrites the "You see nothing special..." line with other text of our own, for items that otherwise do not have a description.

Finally, we may want to look at multiple things at once. The Left Hand of Autumn ★★★ demonstrates how we might provide a different response for EXAMINE PAINTINGS than for examining each individually; Beekeeper's Apprentice ★★ provides a SEARCH command that will show the descriptions of all the scenery in the current location.

See also

Actions on Multiple Objects for an alternative EXAMINE ALL command

Examples

44. Odin

In recent years there has been a strong trend towards providing unique descriptions for all implemented objects. Often this is a good idea, but there are also contexts in which we may want to discourage the player from looking too closely at some things and concentrate his attention on just a few interesting ones.

The trick here is that leaving items completely undescribed leads to rather dull exchanges like this:

>x table
You see nothing special about the table.

...which can leave the player with the impression that the author was simply too lazy to describe everything. So it can be a good idea to replace that default message with a different one more appropriate to the game. For instance:

paste.png "Odin"

The House of a Mortal Farmer is a room. "Having two separate rooms, this house testifies to considerable wealth and success at agriculture."

The Bedroom is inside from the House.

A chair is a kind of supporter. A chair is always enterable.

In the House are a table, two chairs, a basket, and a hearth. On the table is a loaf of bread.

The description of a thing is usually "You give [the noun] a glance, but it is plainly beneath your attention."

Because the description is attached to a whole kind ("thing"), it is really a blanket instruction about many objects at once. More specific instructions always override less specific ones, so we can easily make exceptions. For instance, the following will work correctly:

The infant is a man in the basket. The description of the infant is "So strong and fat that you wonder whether one of your fellow gods is acquainted with the mistress of the house-- but it's no concern of yours, of course."

Test me with "x table / x chair / x infant".

68. Beekeeper's Apprentice ★★

We have to create a suitable action and say what it does, and to repeat what we do through all the scenery items. That needs material from subsequent chapters, but is quite ordinary Inform all the same:

paste.png "Beekeeper's Apprentice"

Studying the vicinity is an action applying to nothing.

Report studying the vicinity:
    if the location does not contain something which is scenery:
        say "There's little of interest in the [location]." instead;
    repeat with point of interest running through scenery in the location:
        say "[point of interest]: [run paragraph on]";
        try examining the point of interest.

Understand "search" as studying the vicinity.

The Yard is a room.

The hive and the honey are scenery things in the Yard. The description of the hive is "The honeycombed hive is all around you, thrumming with life." The description of the honey is "Wax-sealed honey has been cached in many of the hexagonal nurseries."

Test me with "search".

The reason for this example is to show the use of saying "[run paragraph on]". It means we have output such as:

>search
hive: The honeycombed hive is all around you, thrumming with life.

honey: Wax-sealed honey has been cached in many of the hexagonal nurseries.

Without the running on, the prompts "hive:" and "honey:" would be separated from the descriptions following them, which would look a little odd.

295. The Left Hand of Autumn ★★★

Suppose that we have a game in which groups of objects can have meaning apart from their individual significance -- perhaps there are spells that can only be cast by collecting just the right items in the same place.

In this case, one of the things the player might like to be able to do is look at several items together and get a special response, different from looking at the items individually.

To make this happen, we need to do several things:

(1) we need to create a version of the EXAMINE command that can apply to multiple objects at once.
(2) we need to correct the way Inform normally deals with multiple-object commands, because we want our group description to print only one time, and we want to avoid stubs such as "pear: ... apple: ..." before or after the group description.
(3) we need to define a way for Inform to identify interesting groups and describe them.

paste.png "The Left Hand of Autumn"

Section 1 - Procedure

Understand "examine [things]" or "look at [things]" as multiply-examining. Multiply-examining is an action applying to one thing.

Understand "examine [things inside] in/on [something]" or "look at [things inside] in/on [something]" as multiply-examining it from. Multiply-examining it from is an action applying to two things.

Group-description-complete is a truth state that varies.

Carry out multiply-examining it from:
    try multiply-examining the noun instead.

Check multiply-examining when group-description-complete is true:
    stop the action.

Carry out multiply-examining:
    let L be the list of matched things;
    if the number of entries in L is 0, try examining the noun instead;
    if the number of entries in L is 1, try examining entry 1 of L instead;
    describe L;
    say line break;
    now group-description-complete is true.

Before reading a command:
    now group-description-complete is false.

Now for step 2, overriding Inform's usual output of names of objects:

The silently announce items from multiple object lists rule is listed instead of the announce items from multiple object lists rule in the action-processing rules.

This is the silently announce items from multiple object lists rule:
    unless multiply-examining or multiply-examining something from something:
        if the current item from the multiple object list is not nothing, say "[current item from the multiple object list]: [run paragraph on]".

Definition: a thing is matched if it is listed in the multiple object list.

We'll save our "to describe" phrase until Section 2, when we can give the game specific instructions about how to report different lists of objects.

Now, the player might also want to be able to refer to a group of item by some kind of group name, so let's add the option of creating a Table of Collective Names which will interpret these:

After reading a command:
    repeat through the Table of Collective Names:
        let N be "[the player's command]";
        let Y be relevant list entry;
        while N matches the regular expression "[name-text entry]":
            replace the regular expression "(.*)[name-text entry](.*)" in N with "\1[Y]\2";
        change the text of the player's command to N.

Report taking something:
    say "You pick up [the noun]." instead.

And as a bit of polish, because we'd like SEARCH TABLE to have the same effect as EXAMINE ALL ON TABLE:

Understand "look on [something]" as searching.

Instead of searching something which supports at least two things:
    let L be the list of things supported by the noun;
    describe L.
Instead of searching something which contains at least two things:
    let L be the list of things contained by the noun;
    describe L.

Section 2 - Scenario

Eight-Walled Chamber is a room. "A perfectly octagonal room whose walls are tinted in various hues."

The display table is a supporter in the Chamber. A twig of rowan wood is on the table.

The player carries an apple and a pear.

A glove is a kind of thing. A glove is always wearable. Understand "glove" as a glove. The player carries a left glove and a right glove. The left glove and the right glove are gloves.

Now we define a few actual lists of items:

Fruit list is a list of objects which varies. Fruit list is { apple, pear }.
Glove list is a list of objects which varies. Glove list is { right glove, left glove }.
Arcane list is a list of objects which varies. Arcane list is { left glove, twig, pear }.

To describe (L - a list of objects):
    sort L;
    if L is fruit list:
        say "Just a couple of fruits.";
    otherwise if L is glove list:
        say "It's a matched pair of fuzzy blue gloves.";
    otherwise if L is arcane list:
        say "To anyone else it might look like a random collection of objects, but these three things -- [L with definite articles] -- constitute a mystic key known as the Left Hand of Autumn. They practically hum with power.";
    otherwise:
        say "You see [L with indefinite articles]."

When play begins:
    sort fruit list;
    sort glove list;
    sort the arcane list.

We sort the lists so that regardless of how we change the rest of the code (and the order in which objects are coded), the resulting list will always be in sorted order and ready to compare with the list of items the player wants to look at. And thanks to the "Reading a command" code we wrote earlier, we can also teach the game to understand the player's references to "the left hand of autumn" as a specific collection of items.

Table of Collective Names

name-text

relevant list

"left hand of autumn"

"[arcane list]"

"gloves"

"[glove list]"

"pair of gloves"

"[glove list]"

Test me with "x apple and pear / x left and right / put pear on table / put left glove on table / x all on table / put all on table / examine all on table / get apple, twig, pear / x all on table / search table".

337. Crusoe ★★★

Suppose we want to add rules so that any time we examine a charred object (and most of our objects can be charred), a line about the charring is appended to the end of the object description. We could use "after examining...", but perhaps we would prefer for the sentence about the charring not to appear in its own paragraph.

This is an ideal occasion for a new activity. We look at the action index for "examining" to identify the rule that causes the old behavior (in this case, the "standard examining rule"); replace this with a new rule that calls our activity; and write our "printing the description" activity in such a way that it uses an object's description without forcing a paragraph return afterward.

Then we will use "after printing the description" to add our line about charring, and make sure that the paragraph return does occur before the prompt.

So:

paste.png "Crusoe"

Section 1 - Creating our New Activity

The fancy examining rule is listed instead of the standard examining rule in the carry out examining rules.

This instruction replaces a normal piece of the examine action, the standard examining rule, with another one of our own devising. (The replacement of the standard examining rule will be explained in more detail in the chapter on rulebooks.)

Printing the description of something is an activity.

This is the fancy examining rule:
    carry out the printing the description activity with the noun;
    rule succeeds.

All we have done here is enclose what is usually just a rule inside an activity. This means that we can now write before and after rules for the activity, and also add special instructions like "Rule for printing the name of something while printing the description of something" -- this may not be likely to arise often, but Inform now has the concept of "printing the description of something" as a separate context of action. Next we add the modification that lets us append to the description without a new line:

Rule for printing the description of something (called item):
    if the description of the item is not "":
        say "[description of item] [run paragraph on]";
    otherwise:
        say "You see nothing special about [the item]. [run paragraph on]".

"run paragraph on" here will mean that we do not get a paragraph break following the description, even if it ends with a period. We also insert a space, so that our follow-on comments will be properly punctuated.

After printing the description of something charred:
    say "It is charred." instead.

The instead at the end of this line stops Inform for going on with any other "after printing the description of..." rules.

The standard library also has rules for printing additional text about containers and supporters with visible contents, and devices that are switched on; with this current system, we could add those as "after printing the description" rules as well, building up a complete paragraph if we wanted. But for simplicity we won't exemplify all of that here. The effects would be much the same as with the "charred" line.

Now, because we want to make sure that we always do get a paragraph break after our description, we add this rule last after all the other rules. "Last" and "first" rules are covered in more detail in the chapter on rulebooks.

Last after printing the description of something:
    say paragraph break.

Section 2 - The Scenario

The Desert Isle is a room. "A pale expanse of sand, here and there developing into hillocks of grass, and a small clump of palms. The water is shallow here, and there are other islands within swimming distance -- or even wading distance, perhaps -- but none of them is any larger than your island, so it doesn't seem worth the trouble of visiting.

A few hundred feet out, the water turns darker blue, the sea floor drops away, and there is nothing to be seen all the way down to the horizon, except a couple of fluffy clouds, and an occasional bird.

The remains of your fire smolder in the stone-lined pit."

A thing can be charred or whole. A thing is usually whole. Instead of burning something: say "You hold [the noun] to the fire until it flares and chars."; now the noun is charred.

The player carries a stick. The description of the stick is "A strip of palm from the woodiest part of the leaf, about a foot and a half long."

The player carries a glass bottle and a piece of paper. The description of the paper is "A single blank sheet." In the glass bottle is a grain of sand. The glass bottle is openable and open. Instead of burning the glass bottle: say "You hold the bottle to the flame, but it grows uncomfortably warm."

Instead of burning the grain of sand: say "You drop the grain into the fire pit, where it becomes indistinguishable from all the others."; now the grain of sand is nowhere. Instead of dropping the grain of sand: now the grain of sand is nowhere; say "You return the grain of sand to its brethren."

The player's description is handled in an unusual way, and this will produce a space paragraph break there where it should not. Instead, therefore, we will add an instead for examining the player (probably a good idea anyway):

Instead of examining the player:
    say "You are sunburned and there is sand in cracks you didn't know existed."

Test me with "i / x stick / x bottle / x sand / x paper / x me / burn stick / x stick / burn paper / x paper".

The "printing a description" activity may be useful for other games, and can be imported just by lifting section 1.

RB §6.6. Looking Under and Hiding

Finding hidden objects is a classic puzzle in IF. Beachfront provides the most basic example, an object that becomes visible only when we have searched the papers on a cluttered desk. Beneath the Surface takes this further, giving all large furnishings the ability to conceal items, and allowing the player to put things underneath other things, as well as find them. Flashlight adds an extra twist to the puzzle by requiring that the player have a flashlight to shine under a bulky object in order to find what lies underneath.

Looking inside an object is generally handled by the searching action, and we could extend that to allow the player to search multiple or complex objects. Matreshka turns the puzzle on its head by allowing the player to search a whole room systematically with only a single command.

See also

Kitchen and Bathroom for the related case of needing to look in a mirror

Examples

98. Beachfront

Suppose we have our player, a detective, searching for evidence; we don't want him to be able to use this evidence until he has performed the action that reveals it, but after that it should be visible in the room when he looks.

A simple way to do this is to start the object -- an envelope, in this scenario -- out of play, and only move it into the location when the player looks for it:

paste.png "Beachfront"

The Stuffy Office is a room. "The windows are closed, making the sultry air even more unbearable. A narrow slice of Caribbean blue is visible between the scuba gear rental shop and the recreated 17th century pirate tavern.

The office is cheerfully furnished with wicker chairs and white curtains, but the tropical decorating scheme stopped at the desk, which is heavy oak and absolutely covered with papers."

The heavy oak desk is a supporter in the stuffy office. It is scenery. Understand "paperwork" as the desk.

The creamy envelope is an openable container. The description is "There is no return address on the outside of the envelope, just the address of the Doctor's office -- but the legs of the capital A are rubbed down in a characteristic way, and the top of every R is open. There's no question that it comes from the same typewriter as the blackmail note." In the envelope is a letter. The envelope can be found or lost. The envelope is lost.

Instead of searching the desk when the envelope is lost:
    now the envelope is found;
    say "You rifle through the piles of bills and notices; invitations to conventions; advertisements for high-end prescription drugs; pink carbon sheets bearing patients['] names and medical identification numbers in spidery, elderly handwriting. Almost at the bottom of the heap, you find what you were looking for: a creamy envelope with the address typed.";
    move the envelope to the desk.

Here we've changed the property of the envelope to keep track of the fact that it has been found, so that if the player tries again, he won't find anything more.

Instead of searching the desk:
    say "Further investigation of the desk reveals nothing else suspicious."

Notice that we have two rules that apply to "searching the desk", but one of them has a more specific set of parameters ("when the envelope is lost"). This means that Inform will consult that rule first and use it if it applies; it will only carry out our plain vanilla "instead of searching the desk" rule when the more restricted rule is not relevant.

Test me with "x envelope / x desk / search desk / look / get envelope / x envelope".

173. Matreshka

paste.png "Matreshka"

Ransacking is an action applying to one thing.

Check ransacking:
    if the noun is not the location, say "You can hardly search [the noun] from here." instead.

Carry out ransacking:
    while the player can see a closed openable unlocked container (called target):
        say "[target]: [run paragraph on]";
        try opening the target.

Report ransacking:
    say "You can see nothing further worth searching."

The Russian Gift Shop is a room. In the Russian Gift Shop is a large wooden doll. It is closed and openable. In the large wooden doll is a medium wooden doll. It is closed and openable. In the medium wooden doll is a small wooden doll. It is closed and openable. In the small wooden doll is a tiny solid wooden doll.

And now we need to borrow from a later chapter for the command that will make this work:

Understand "search [any visited room]" as ransacking.

Test me with "search gift shop".

218. Flashlight

paste.png "Flashlight"

The Schoolhouse is a room. "Though normally comfortable, the room is dark and menacing during the storm; rain sheets on the windows, and you can barely see the flash of the lighthouse only a few miles away."

The cabinet is a fixed in place openable container in the Schoolhouse. The hurricane lantern is a thing in the Schoolhouse. "A hurricane lantern hangs from a peg." The lantern is lit.

Visibility rule when looking under something:
    if the player is carrying a lit thing (called lamp):
        say "You shine [the lamp] under [the noun]...";
        there is sufficient light;
    there is insufficient light.

There is a marble. The marble can be found or lost. The marble is lost.

Instead of looking under the cabinet when the marble is lost:
    move the marble to the player;
    now the marble is found;
    say "Billy's lost marble! So that's where it got to!"

Test me with "look under cabinet / get lantern / look under cabinet".

Because visibility is checked before instead rules, this discovery will (correctly) occur only when the player does have enough light.

231. Beneath the Surface

The standard world model provides for the idea of containers and supporters, but this is not the only way that objects can relate to one another in the real world. Here we try adding the idea of concealment beneath another object:

paste.png "Beneath the Surface"

Section 1 - In Which our Terms are Defined

Underlying relates various things to one thing. The verb to underlie means the underlying relation. The verb to be under means the underlying relation. The verb to be beneath means the underlying relation.

Instead of looking under a thing which is underlaid by something (called the lost object):
    say "You find [the list of things which underlie the noun]!";
    now every thing which underlies the noun is carried by the player;
    now every thing which underlies the noun does not underlie the noun.

Hiding it under is an action applying to one carried thing and one thing. Understand "put [something preferably held] under [something]" as hiding it under. Understand "hide [something preferably held] under [something]" as hiding it under. Understand the commands "shove" and "conceal" and "stick" as "hide".

Check hiding it under:
    if the second noun is not fixed in place, say "[The second noun] wouldn't be a very effective place of concealment." instead.

Carry out hiding it under:
    now the noun is nowhere;
    now the noun underlies the second noun.

Report hiding it under:
    say "You shove [the noun] out of sight beneath [the second noun]."

Section 2 - In Which They are Put To Use

The Room of Hidden Objects is a room. It contains a sofa, an easy chair, and a rug. The sofa supports a lime-green pillow and an innocent-looking Chinese finger toy. The rug is fixed in place. The chair is a supporter.

A treasure map underlies the easy chair. A skeleton is beneath the sofa. A blueprint of Atlantis, a lexicon of Linear A, and the key to Jimmy Hoffa's Mausoleum are under the rug.

Test me with "look under the sofa / look under the rug / look under the easy chair / hide lexicon under rug".

RB §6.7. Inventory

Occasionally we would like to change the way the name of something is printed as part of our inventory, and we can do this with a printing the name rule such as

Rule for printing the name of the dead rat while taking inventory:
    say "dead rat (at arm's length)"

There are also several possibilities for redesigning the inventory list as a whole. Persephone ★★★ shows how to divide an inventory list into two parts, a "You are carrying: " section and a "You are wearing: " section. Equipment List ★★ goes further, and shows how we might use Inform's specialized listing functions to create a variety of differently formatted inventories.

Sometimes the way Inform by default lists properties such as "(closed)" or "(open but empty)" isn't quite what we want. Oyster Wide Shut offers a flexible alternative to the standard behavior, allowing finer control over which properties are listed and how they are described.

Trying Taking Manhattan ★★★ replaces the inventory behavior for other characters: instead of silently looking through their possessions (but not describing them to the player), they now describe to the player what they're carrying and wearing.

Examples

425. Oyster Wide Shut

As we've seen in earlier examples such as "Equipment List", it is possible to vary the way Inform creates inventory listings in general (to create lists that look more like paragraphs of prose, lists divided between what the player is wearing and what he isn't, and so on). We can also use activities to alter the printing of specific objects' names and contents, as with the "omit contents in listing" feature after printing the name of something.

We may find, however, that we would like a great deal more control over Inform's printing of inventory details, not just as a special effect for a few items, but throughout the game.

We start by turning off Inform's native property writer:

paste.png "Oyster Wide Shut"

Section 1 - Procedure

The print standard inventory rule is not listed in any rulebook.

Carry out taking inventory (this is the new print inventory rule):
    say "You are carrying: [line break]";
    list the contents of the player, with newlines, indented, including contents, with extra indentation.

This is very much like the library's standard behavior, but with the exception that "giving inventory information" or even "giving brief inventory information" are omitted. Here's how we supplant it:

After printing the name of something (called target) while taking inventory:
    follow the property-aggregation rules for the target.

Now, our property-aggregation rulebook is going to look at a given object and decide on a list of features that should be mentioned in inventory. We'll start by producing something quite similar to Inform's default behavior:

The property-aggregation rules are an object-based rulebook.
The property-aggregation rulebook has a list of text called the tagline.

A first property-aggregation rule for an openable open thing (this is the mention open openables rule):
    add "open" to the tagline.

A first property-aggregation rule for an openable closed thing (this is the mention closed openables rule):
    add "closed" to the tagline.

A property-aggregation rule for a closed transparent container which contains nothing (this is the mention empty transparent containers rule):
    add "empty" to the tagline.

A property-aggregation rule for an open container which contains nothing (this is the mention empty open containers rule):
    add "empty" to the tagline.

A property-aggregation rule for a lit thing (this is the mention lit objects rule):
    add "providing light" to the tagline.

A property-aggregation rule for a thing worn by the player (this is the mention worn objects rule):
    add "being worn" to the tagline.

The last property-aggregation rule (this is the print aggregated properties rule):
    if the number of entries in the tagline is greater than 0:
        say " ([tagline])";
        rule succeeds;
    rule fails.

Notice that we don't need to write any rules about how to print that list of text: because Inform is printing out a list, it will automatically insert commas, spaces, and the word "and" where appropriate; and it will automatically follow the "use serial comma" option, if we have it set.

Now we're free to meddle. Let's give the player a bunch of possessions that will be listed in interesting ways in inventory:

Section 2 - Scenario

The Curved Beach is a room. "White sand stretches away both northeast and northwest, enclosing this attractive little bay. Gentle waves lap at the beach."

The player carries a glowing plastic sack. The glowing plastic sack is lit and transparent and openable and open. It contains a rock. It is wearable.

The player wears a flashlight lanyard. The flashlight lanyard is a device.

Carry out switching on the lanyard: now the noun is lit.
Carry out switching off the lanyard: now the noun is unlit.

The player carries an oyster. The oyster contains a pearl. The oyster is openable.

Now suppose that we don't want the oyster to say "closed" when it's closed. Instead, we'd like it to say "clamped shut". As this is the only property the oyster will ever have, we can simply override his whole property-aggregation rulebook:

A property-aggregation rule for the oyster:
    if the oyster is closed:
        say " (clamped shut)";
    rule succeeds.

That's fine for the oyster because "clamped shut" is the only property he'll ever have. What if we'd like instead just to revise the way the sack (and only the sack) gets described as providing light?

The sacklight rule is listed after the mention lit objects rule in the property-aggregation rules.

A property-aggregation rule for the plastic sack (this is the sacklight rule):
    if "providing light" is listed in the tagline:
        remove "providing light" from the tagline;
        add "gently glowing" to the tagline.

Now the flashlight (and any other regular light sources we might add to the game) will be described as "providing light", but the sack will only be said to be gently glowing -- a bit more appropriate for its rather fainter gleam.

We might also wish to add a systematic feature across the board to include a new property in the inventory list? Let's say the player can enchant his possessions, and enchanted possessions should thereafter be listed accordingly:

A thing can be magical or non-magical. A thing is usually non-magical.

Understand "enchant [something]" as enchanting. Enchanting is an action applying to one thing.

Carry out enchanting something:
    now the noun is magical.

Report enchanting something:
    say "Ding! You turn [the noun] magical."

A property-aggregation rule for a magical thing:
    add "enchanted" to the tagline.

Test me with "i / close oyster / i / turn on flashlight / i / take off flashlight / i / turn off flashlight / i / close sack / i / open sack / i / take all from sack / i / close sack / i / wear sack / i / enchant sack / i / open sack / put all in sack / i / close sack / i".

Further variations are possible as well: if we used a "before printing the name..." rather than an "after printing the name..." rule, we could automatically generate lines like "an open and empty phosphorescent plastic sack", removing some of the artificiality of the parentheses.

Or we could add more logic to the rules about which properties are mentioned, so that some features of objects were mentioned in inventory only if the player was wearing the correct detection device, like so:

paste.png The player wears enchantment-detecting goggles.

A property-aggregation rule for a magical thing:
    if the player is wearing the goggles:
        add "enchanted" to the tagline.

177. Equipment List ★★

Most of the phrase options above are relatively self-explanatory; a few are less so. Here is an overview:

"With newlines" tells Inform to put a new line before each listed object. Indented tells it to indent contents of objects, when listing these.

"Giving inventory information" means to append information such as (closed) or (being worn) to objects.

"As a sentence" means to put "and" before the last object and commas between them; this is usually not used in conjunction with newline listing. "As a sentence" obeys whatever conventions about the use of the serial comma we may have established with the "Use serial comma" option.

"Including contents" means to list the contents of open or transparent containers and all supporters, whereas including all contents means to list the contents of all containers, even opaque closed ones.

"Tersely", perhaps unexpectedly, puts parentheses around objects listed as the contents of other objects.

"Giving brief inventory information" omits most of the inventory tags, such as "(open)" and "(worn)", but does list "(closed)" for closed containers which might not otherwise be obviously openable.

"Using the definite article" means prefixing objects with "the", if applicable, rather than "a".

"Listing marked items only" means including only objects that have already been declared "marked for listing".

"Prefacing with is-are" means that Inform will write "is" before the list if it contains only one item, and "are" if the list contains more than one.

"Not listing concealed items" means to omit from the list anything which is scenery.

Finally, "with extra indentation" means that the whole list should be indented slightly, in emulation of the default inventory listing.

With this information, we can try rewriting the inventory behavior to emulate the standard or to explore alternate versions:

paste.png "Equipment List"

The Watery Room is a room. The player carries a snorkel and a waterproof sack. The waterproof sack contains an undersea map, a diving guide, a cup, and 500 Argentine pesos. The cup contains a worm. The player wears a swimsuit and a pair of flippers. The sack is openable and open.

Inventory listing style is a kind of value. The inventory listing styles are tall, wide, curt, minimal, divided tall, and divided wide. Current inventory listing style is an inventory listing style that varies.

Understand "inventory [inventory listing style]" as requesting styled inventory. Requesting styled inventory is an action applying to an inventory listing style. It is an action out of world.

Carry out requesting styled inventory:
    now current inventory listing style is the inventory listing style understood.

Report requesting styled inventory:
    say "Inventory listing is now set to [current inventory listing style]."

We begin by emulating the standard inventory listing style:

Instead of taking inventory when current inventory listing style is tall:
    if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
    say "You are carrying: [line break]";
    list the contents of the player, with newlines, indented, giving inventory information, including contents, with extra indentation.

Here we offer the alternative of listing everything together as a paragraph:

Instead of taking inventory when current inventory listing style is wide:
    if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
    say "You are carrying ";
    list the contents of the player, giving inventory information, as a sentence, including contents;
    say "."

This may be unsatisfactory, however. Items that are inside other items are not set off from those merely carried by the player. One way around this is to use terse listing, giving such descriptions as "a waterproof sack (in which are an undersea map, a diving guide, a cup (in which is a worm) and a 500 Argentine pesos)" as opposed to the more confusing " a waterproof sack (open), inside which are an undersea map, a diving guide, a cup, inside which is a worm and a 500 Argentine pesos".

Instead of taking inventory when current inventory listing style is curt:
    if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
    say "You are carrying ";
    list the contents of the player, tersely, giving brief inventory information, as a sentence, including contents;
    say "."

If, using the above style, we close the sack, we will still get "(closed)" after the sack's listing. The following minimalist listing style abolishes even that nicety:

Instead of taking inventory when current inventory listing style is minimal:
    if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
    say "You are carrying ";
    list the contents of the player, tersely, as a sentence, including contents;
    say "."

If we want to list worn things separately from carried things, we have occasion to put "listing marked items only" to work:

Instead of taking inventory when the current inventory listing style is divided wide:
    if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
    say "You are wearing ";
    now all things enclosed by the player are unmarked for listing;
    now all things worn by the player are marked for listing;
    if no things worn by the player are marked for listing, say "nothing";
    otherwise list the contents of the player, as a sentence, listing marked items only;
    say ".[paragraph break]";
    say "You are carrying ";
    now all things carried by the player are marked for listing;
    now all things worn by the player are unmarked for listing;
    if no things carried by the player are marked for listing, say "nothing";
    otherwise list the contents of the player, as a sentence, tersely, giving brief inventory information, listing marked items only;
    say ".[paragraph break]".

And similarly for a tall divided inventory:

Instead of taking inventory when the current inventory listing style is divided tall:
    if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
    if the player carries something:
        now all things enclosed by the player are unmarked for listing;
        now all things carried by the player are marked for listing;
        say "You are carrying: [line break]";
        list the contents of the player, with newlines, indented, giving inventory information, including contents, with extra indentation, listing marked items only;
    if the player wears something:
        now all things enclosed by the player are unmarked for listing;
        now all things worn by the player are marked for listing;
        say "You are wearing: [line break]";
        list the contents of the player, with newlines, indented, including contents, with extra indentation, listing marked items only.

Test me with "i / inventory wide / i / inventory curt / i / close sack / i / open sack / inventory minimal / i / close sack / i / open sack / inventory divided wide / i / inventory divided tall / i / drop all / i / take all / take off swimsuit / take off flippers / i / i divided wide / i / wear swimsuit / drop all / i".

64. Persephone ★★★

If we wanted, we might replace the rule for taking inventory as follows:

paste.png "Persephone"

Instead of taking inventory:
    say "[if the player carries something][We]['re] carrying [a list of things carried by the player][otherwise][We]['re] empty-handed";
    say "[if the player wears something]. [We]['re] wearing [a list of things worn by the player][end if]."

The Fancy Party is a room. The player carries a sword, a strawberry stem, and 20 credits worth of platinum. The player wears a sash indicating lordhood.

Test me with "i / take off sash / i / drop all / i".

204. Trying Taking Manhattan ★★★

Inform has built-in commands for other people, and sometimes we may want to adjust the way these work without completely disabling and replacing the command. Suppose, for instance, that instead of

Kermit the Frog looks through his possessions.

we'd like someone taking inventory to report what he's got, thus:

Kermit the Frog says, "I seem to be carrying a microphone and wearing a hat and a trenchcoat."

To do this, we could replace the built-in report rule with a different one.

paste.png "Trying Taking Manhattan"

The loud inventory rule is listed instead of the report other people taking inventory rule in the report taking inventory rules.

This is the loud inventory rule:
    unless the player is the person asked:
        say "[The person asked] says, 'I seem to be carrying [a list of things carried by the person asked][if the person asked is wearing something] and wearing [a list of things worn by the person asked][end if].'"

Persuasion rule for asking someone to try doing something: persuasion succeeds.

Grand Central Station is a room. "Here you are in New York, New York. Any minute now someone is going to burst into song."

Kermit the Frog is a man in Grand Central Station. "Kermit the Frog stands nearby, enjoying being green." Kermit is wearing a hat and a trenchcoat. He is carrying a microphone.

Test me with "inventory / kermit, inventory".

RB §6.8. Taking, Dropping, Inserting and Putting

We may want to change the default refusal message when the player tries to pick up scenery: Replanting demonstrates this case simply.

Removal modifies responses to successful TAKE commands, with the effect that when the player picks up an item, he gets a response such as "You take the book from the shelf."

Croft ★★★ modifies the DROP command, so that objects dropped on specific surfaces get reported in a special way. Celadon allows the player to drop even objects he is carrying indirectly, for instance on a tray or in a sack.

Morning After introduces a simple rule that changes the behavior of the whole story: whenever the player takes an item he hasn't already looked at, he automatically examines it. This picks up the pace of exploration passages where the player is likely to be collecting a large number of objects.

By default, when the player tries to put or insert an item that he isn't holding, Inform prints a refusal message; Democratic Process ★★★ and Sand ★★★★ offer ways instead to have the player first pick up the relevant items. (The former applies to single items the player is trying to place; the latter expands coverage to work even if the player uses a command affecting multiple objects.)

Taking also happens as a result of other commands. Such takes can be made unnecessary by turning off the "carrying requirements rule" under particular circumstances, or presented differently using the implicitly taking activity.

Examples

16. Replanting

By default, "TAKE OAK" in the example above will produce the response "That's hardly portable." This is fine under many circumstances, but also a bit generic, so we might want to override it for a specific game.

paste.png "Replanting"

The Orchard is a room. "Within this quadrille of pear trees, a single gnarled old oak remains as a memory of centuries past." The gnarled old oak tree is scenery in the Orchard.

Instead of taking some scenery: say "You lack the hulk-like strength."

Test me with "take oak".

Here we've used an "instead" rule; we will learn more about these in the section on actions. This allows us to define our own results for taking an object.

Note: "scenery" is a property of an object (about which we will hear more later). So when we use it in rules, we can talk about "some scenery", "something that is scenery", or even "a scenery thing" -- the last one doesn't sound much like English, but is a more plausible construction with other adjectives.

90. Morning After

Suppose we want to make the player's life slightly easier by examining everything he picks up, if he hasn't already examined it.

paste.png "Morning After"

A thing can be examined or unexamined.

After taking something unexamined:
    say "Taken. [run paragraph on]";
    try examining the noun.

Carry out examining something:
    now the noun is examined.

Carry out rules are explained in more detail in the chapter on advanced action handling. For now, it may be enough to know that what we put into this carry out rule for examining will happen any time anything is examined, but that it will not interfere with the rest of the predefined behavior of the action. The player will still see the object description and so on, as usual.

The Red Door Saloon is a room. "This old place is in pretty bad shape since the mine shut down. Now there's not much to see but the pair of deep gouges in the floorboards where they dragged away the Sheriff's corpse with the spurs still on."

Jed is a man in the Red Door Saloon. "At 8:30 AM the only person around is old Jed, collecting his hangover cure."

The pistol is a thing in the Red Door Saloon. The description of the pistol is "It ain't too accurate, but for two dollars you can't expect much."

The hangover cure is a thing in the Red Door Saloon. The description of the hangover cure is "Two yellow egg-yolks unbroken in a red-brown liquid. Yep."

Test me with "x pistol / get all".

200. Removal

Suppose that we want to change the reporting of "take" so that the player is always told something like "You take the book from the shelf." or "You pick up the toy from the ground." In order to generate these reports, we will need to know where the object started, even though by the time we are printing the output, the object will have moved.

paste.png "Removal"

The Pharmacy is a room. A desk and a trash can are in the Pharmacy. The pill-counter, a prescription, and a computer are on the desk. The computer is fixed in place. The pill-counter contains some Vicodin. The trash can contains an empty box.

The taking action has an object called previous locale (matched as "from").

The previous locale could in theory be either a thing or a room, so we make it "an object" -- that is, the most generic possible kind, to which both things and rooms belong. Now we record what the previous locale is at the beginning of each taking action:

Setting action variables for taking:
    now previous locale is the holder of the noun.

Report taking something from the location:
    say "You pick up [the noun] from the ground." instead.

Report taking something:
    say "You take [the noun] from [the previous locale]." instead.

Test me with "get all".

224. Celadon

By default, Inform only lets the player drop those things which he is carrying -- that is, those directly in his possession. Things inside satchels or on portable trays have to be taken first.

If we want to change this behavior, we might add a dropping rule that distinguishes between carrying and mere enclosure (introduced back in "The location of something" in the chapter on Things):

paste.png "Celadon"

The Tea Room is a room. The player carries a black lacquer tray. The lacquer tray is portable. On the lacquer tray are a celadon teapot and a napkin.

Before dropping something:
    if the player does not carry the noun and the player encloses the noun:
        say "(first taking [the noun] from [the holder of the noun])[command clarification break]";
        silently try taking the noun;
        if the player does not carry the noun, stop the action.

Instead of taking the napkin:
    say "It seems to be stuck to the tray, possibly by an underlying wad of gum."

Test me with "i / drop teapot / i / look / drop teapot / drop napkin / i / drop tray".

86. Democratic Process ★★★

"Stop" and "Continue" are most useful when we need to write rules that will have to stop the action some of the time but at other times let it pass; so for instance:

paste.png "Democratic Process"

Before inserting something which is not carried by the player into something:
    if the noun is in the second noun, say "Already done." instead;
    say "(first taking [the noun])[line break]";
    silently try taking the noun;
    if the player is not holding the noun, stop the action.

Before putting something which is not carried by the player on something:
    if the noun is on the second noun, say "Already done." instead;
    say "(first taking [the noun])[line break]";
    silently try taking the noun;
    if the player is not holding the noun, stop the action.

The Assembly Room is a room. "On most days, this room is used for elementary school assemblies; at the moment, it serves as a voting place." The ballot is on the desk. The desk is in the Assembly Room.

The machine is a container in the Assembly Room. "On the ballot machine is a sign which reads 'PUT BALLOTS IN ME :)'." Understand "ballot machine" as the machine.

Test me with "put ballot in machine".

202. Croft ★★★

Suppose that we have a design in which the player spends lots of time on enterable supporters, and in which we want to report certain actions -- dropping things onto those supporters, or leaping from one to another -- in a new way. We might begin by adding some action variables to help us keep track of the situation:

paste.png "Croft"

The dropping action has an object called the container dropped into (matched as "into").

The dropping action has an object called the supporter dropped onto (matched as "onto").

Rule for setting action variables for dropping:
    if the actor is in a container (called C), now the container dropped into is C;
    if the actor is on a supporter (called C), now the supporter dropped onto is C.

Report dropping a heavy thing onto a metallic thing:
    say "You drop [the noun], and [the supporter dropped onto] clangs protestingly." instead.

Report someone dropping a heavy thing onto a metallic thing:
    say "[The actor] drops [the noun] onto [the supporter dropped onto], which clangs protestingly." instead.

A thing can be heavy or light. A thing can be metallic or ordinary. A thing is usually ordinary. A thing is usually light.

The Ancient Cambodian Temple is a room. "A vast space built for ancient and forgotten rituals. The stone floor crawls with vermin. Well above the floor, and separated by some feet, are twin platforms built into the wall: the one carved of jointed wood, the other of sheets of graven bronze."

A platform is a kind of supporter. A platform is always enterable. A platform is usually scenery.

The bronze platform is a metallic platform in the Temple. Lara is a woman. She is on the bronze platform. She wears safari pants and a tank top. She carries a gun and a map. The gun is heavy.

The wood platform is an ordinary platform in the Temple. The player is on the wood platform. The player carries a rope, an Ancient Cambodian/English Phrasebook, a pickaxe, and a precious idol. The idol and the pickaxe are heavy.

Persuasion rule: persuasion succeeds.

The entering action has an object called the place left (matched as "from").
    Check entering a platform from a platform:
        if actor is the player, say "You leap into midair to cross the distance...";
    otherwise say "[The actor] leaps gracefully across the distance...";
    move the actor to the holder of the noun, without printing a room description.

Because this rule occurs before the "implicitly pass through other barriers rule", that rule will not occur when we move from platform to platform; we'll use our own custom rule instead.

Rule for setting action variables for entering:
    now the place left is the holder of the actor.

Report entering a platform from a platform:
    say "You land in a cat-like crouch on [the noun]." instead.

Report Lara entering a platform from a platform:
    say "Lara lands soundlessly on [the noun][if the noun supports the player] beside you[end if]." instead.

Report entering a platform from the location:
    say "You jump, catch the edge of [the noun] in your hands, and -- exerting considerable upper-body strength -- pull yourself up onto it." instead.

Report Lara entering a platform from a location:
    say "Lara jumps, catches the edge of [the noun], and is standing upright on it, all in less time than it takes to tell."

Instead of examining a person who is not the player:
    say "[The noun] carries [list of things carried by the noun] and wears [list of things worn by the noun]."

Instead of climbing a platform, try entering the noun.

Test me with "Lara, drop map / lara, drop gun / drop idol / enter bronze platform / drop pickaxe / get off / climb wood".

379. Lollipop Guild ★★★

As mentioned in this section, the "implicitly taking" activity does not allow us to skip an implicit take entirely. In order to do this, we need to borrow from the chapter on Rulebooks and tell Inform that one of the rules normally built in to the Standard Rules does nothing in certain circumstances:

paste.png "Lollipop Guild"

The carrying requirements rule does nothing when showing something to the guardian.
The can't show what you haven't got rule does nothing when showing something to the guardian.
The block showing rule does nothing.

Candyland is a room. "A fizzing, popping wonderland of sugary delights. A path tiled with butterscotch sweets leads to the horizon."

The butterscotch path is scenery in Candyland.

The player carries a basket. In the basket are a licorice gumdrop and a can of tuna. The gumdrop is edible. The description of the gumdrop is "Covered all over with grains of sugar." The can of tuna is edible. The description of the can of tuna is "A rare import in this place."

The giant lollipop is a fixed in place edible thing in Candyland. "Growing right next to the path, on a trunk of white paper, is a giant lollipop colored green and red and white." The description of the lollipop is "If you were very blind, like Aunt Myrtle, you might mistake it for a young sapling just planted: the lollipop is just that leafy shade of green, with swirls of white and red that might be branches or flowers."

The guardian is a man in Candyland. "Right beside you is a guardian in a mint-colored uniform." The description of the guardian is "A killjoy wielding a gigantic toothbrush." The guardian carries a gigantic toothbrush. The description of the toothbrush is "Bristles as long as your hand. Firm bristles, too, not those soft ones. The guardian doesn't care about your tender gums."

A thing can be sweet. The butterscotch path, the lollipop, and the gumdrop are sweet.

Carry out showing a sweet thing to the guardian:
    say "The guardian shrieks! You don't understand its language, but from its ululations you understand the idea of decay. There may have been a bit in there about a root canal." instead.

Carry out showing something to the guardian:
    say "The guardian nods approvingly at the unsweetened [noun]." instead.

Report eating a sweet thing in the presence of the guardian:
    say "The guardian looks mournful, but unholsters his tube of paste and begins applying it to the toothbrush, as though to say that he really did not want to have to do this...";
    end the story saying "Everything goes minty" instead.

Report eating something:
    say "You consume [the noun] with gusto." instead.

Test me with "x guardian / x toothbrush / show gumdrop to guardian / show path to guardian / show tuna to guardian / look / eat gumdrop".

Note that because we only deactivate the carrying requirements rule for showing purposes, the player still takes the gumdrop before eating it.

87. Sand ★★★★

The above example does not quite work when we want the player to be allowed to take multiple objects at once before putting them somewhere: we also need to add a couple of "understand" rules borrowed from many chapters later. While the reasons may not be immediately clear, we include the demonstration here for the sake of thoroughness:

paste.png "Sand"

Before inserting something which is not carried by the player into something:
    if the noun is in the second noun, say "Already done." instead;
    say "(first taking [the noun]) ";
    silently try taking the noun;
    if the player is not holding the noun, stop the action.

Before putting something which is not carried by the player on something:
    if the noun is on the second noun, say "Already done." instead;
    say "(first taking [the noun])[line break]";
    silently try taking the noun;
    if the player is not holding the noun, stop the action.

Understand "put [things] in [something]" as inserting it into. Understand "put [things] on [something]" as putting it on.

The Closet is a room.

A lentil is a kind of thing. A black-eyed pea is a kind of thing. The closet contains 3 lentils. The Closet contains 14 black-eyed peas. The round tin is a container in the closet. The round tin contains 17 lentils. The square tin is a container in the Closet. The square tin contains 20 black-eyed peas.

Sorting is a scene. Sorting begins when play begins. Sorting ends when all the lentils are in the round tin and all the black-eyed peas are in the square tin. When Sorting ends, end the story finally.

When play begins: say "Thanks to your cruel stepmother, you're not going anywhere until the lentils and peas are sorted."

Test me with "put peas in square tin / put lentils in round tin".

RB §6.9. Going, Pushing Things in Directions

Going is the most complex of actions after looking (or perhaps including looking): the success of every movement depends on the direction the player goes; the room he starts from; the room he intends to reach; whether there are any doors intervening (and, if so, whether these are closed or locked); whether he is traveling by vehicle; and whether he is pushing anything in front of him. When he gets there, the description he sees is itself generated by a looking command.

Pushing something in a direction is really a sort of going. The command >PUSH WHEELBARROW WEST first checks certain qualifying rules: by default, only things defined as pushable between rooms may be pushed, and they may be pushed only in horizontal directions (not UP or DOWN) -- though these rules can be overridden, as we see in Zorb ★★★. If the player's pushing attempt passes these criteria, the action is translated automatically into a going action, with all the usual checks about whether that direction leads anywhere, whether a door is in the way, and so on. The converted action afterward can be caught with such rules as

Instead of going to the Alpine Meadow with the wheelbarrow:
    say "You don't want to crush the delicate blooms."

Instead of going north with the handcart:
    say "The headwind is so stiff that you are unable to make much northerly progress at all while encumbered by the handcart."

Since the two actions are internally being handled as one, both are discussed here.

It is very common for players to make a mistake and type the wrong direction command, or even to misunderstand the room description and not recognize all the possible exits. Bumping into Walls ★★★ helpfully adds a facility so that when the player tries to go in the wrong direction, the story lists the correct possibilities, as in

From here, the viable exits are to the south, the east and the west.

Assuming that travel succeeds, another useful technique is to provide some sense of the journey between locations, especially if they are remote from one another or the player has to do something unusual to get from one to the other. Up and Up ★★ adds a short description of travel when we approach a new room, before the room description is printed; Veronica, conversely, adds a comment when the player leaves a region of the map. The Second Oldest Problem intervenes and kills a player who tries to travel from one dark room to another. Mattress King embellishes the description that automatically results from PUSH MATTRESS WEST, adding a line that describes the player pushing the object before describing the new room approached.

We may also want to add a brief comment when we arrive in a new room, after the room description is printed. One trivial way to do this is to append the line to the room's main description, conditionally, like this:

The Hammock Emporium is a room. "This is Cousin Ed's shop, the big dream he left accounting to pursue. You can't help gawking at the Luxury Leather Space Hammock, made of genuine red buffalo skins[if unvisited]. [paragraph break]So this is why Grampa makes all those 'lying down on the job' jokes every Thanksgiving[end if].".

But often we want our first-glance comment to come after some items in the room are described; and for this effect, we would use the "first look rule" defined in Saint Eligius.

If these methods are not enough, the looking action has an action-specific variable called "the room-describing action", which records whether this particular instance of looking comes about because the player typed LOOK or because the player traveled to a new location. We can consult this variable if we want to make looking work differently after going, as for instance here:

Check looking when the room-describing action is the going action:
    say "You are temporarily too blinded to see." instead.

Another category of examples treat how we handle the movement commands themselves. The eight compass directions, with UP and DOWN, IN and OUT, are used as standard in most interactive fiction, but they are not the only possible way of navigating, and strike many newcomers to the genre as counter-intuitive, since when strolling around in real life most of us rarely think about our travel in terms of compass orientation. Misadventure allows the player to GO TO a named room, instead, and calculates the best route to reach the destination; Safari Guide ★★ builds on this by letting the player make the whole trip in a single move, automatically opening any doors that stand in his way en route.

In the same spirit of interpreting the player's intentions sensibly, Provenance Unknown ★★★ modifies the pushing command so that if the player pushes the top object in a stack of objects towards a direction, Inform attempts to move the bottom item instead. This is convenient if, for instance, we have a heavy television on a movable cart and want PUSH TELEVISION WEST to work just as well as PUSH CART WEST.

We also sometimes want to respond sensibly to terse movement commands or ones that rely on some knowledge of where the player has already been. Polarity ★★★ provides a GO BACK command, allowing the player to retreat in the direction from which he came, while Minimal Movement understands LEAVE, GO, and so on as OUT, in the absence of other information. Owen's Law ★★★ takes this further, calculating from the best routes on a map how to make OUT mean "move towards the exit of this indoor room", and IN mean "proceed further into the interior". Wonderland ★★ assigns altitudes to all rooms and works out the local best meaning of UP and DOWN accordingly.

See also

Map for how to create other kinds of new direction
Varying What Is Read for further divisions of the standard compass, such as north-northwest
Ships, Trains and Elevators for ship-board directions
Bicycles, Cars and Boats for common vehicles in which to travel the map

Examples

100. Veronica

Suppose that we want to have something happen when the player leaves a region we've defined. "Instead of going from (the region)..." will not suffice for this, because this rule will be invoked every time the player successfully leaves a room within the region, whether or not he is going to a room that is also in the same region.

Instead we need a rule that is a bit more specific, like this:

paste.png "Veronica"

Neptune is a region.

Tijuana is a room.

High School is north of Tijuana. It is in Neptune.

Detective Offices is west of High School. It is in Neptune.

The player is in High School.

Instead of going from Neptune to a room which is not in Neptune:
    say "It's a bad time to leave Neptune."

Test me with "s / w / e".

105. Mattress King

By default, when the player pushes something a direction, Inform checks to make sure that the object is pushable between rooms. If not, it blocks the action; if so, it carries out a normal going action with the pushed object taken along.

Also by default, this action produces only a description of the new room that we've traveled into. But suppose we would like to print a short message describing the pushing action first:

paste.png "Mattress King"

Monica's Bedroom is a room. The Living Room is south of Monica's Bedroom. Rachel's Bedroom is south of the Living Room.

After going a direction (called way-pushed) with something (called the thing-pushed):
    say "You push [the thing-pushed] [way-pushed] to [the location].";
    continue the action.

The race car bed is an enterable supporter in Monica's Bedroom. It is pushable between rooms.

Test me with "push bed south".

198. The Second Oldest Problem

Text in this example is drawn from Will Crowther's original 1976 FORTRAN implementation of ADVENTURE, the founding work of the genre, whose source code was rediscovered by Dennis G. Jerz in 2007. Note the capitals: the program ran on an early computer without lower case lettering. They look a little mimsy now, but picture them glowing green on an old-style cathode ray tube monitor in a darkened room late at night.

The problem alluded to is that the player is forbidden to walk between two dark rooms, so that he must always have light to see by from at least one end of any movement. Writing source text to achieve this is tricky to get right in every case, because the determination of light is hard to do. Here we interleave the necessary rules into the existing "going" action, using a new action variable to record the number of ends which are dark as experienced by the player, which might be 0, 1 or 2:

paste.png "THE SECOND OLDEST PROBLEM"

The going action has a number called the dark terminus count.
Setting action variables for going:
    now the dark terminus count is 0;
    if in darkness, increment the dark terminus count.
The last carry out going rule:
    if in darkness, increment the dark terminus count;
    if the dark terminus count is 2, end the story saying "YOU FELL INTO A PIT AND BROKE EVERY BONE IN YOUR BODY!" instead.

And now three early rooms to try this out.

COBBLE CRAWL is a room. "YOU ARE CRAWLING OVER COBBLES IN A LOW PASSAGE. THERE IS A DIM LIGHT AT THE EAST END OF THE PASSAGE."

DEBRIS ROOM is west of COBBLE CRAWL. "YOU ARE IN A DEBRIS ROOM, FILLED WITH STUFF WASHED IN FROM THE SURFACE. A LOW WIDE PASSAGE WITH COBBLES BECOMES PLUGGED WITH MUD AND DEBRIS HERE,BUT AN AWKWARD CANYON LEADS UPWARD AND WEST."

AWKWARD CANYON is west of DEBRIS ROOM. "YOU ARE IN AN AWKWARD SLOPING EAST/WEST CANYON."

DEBRIS ROOM and AWKWARD CANYON are dark.

Rule for printing the name of a dark room: say "DARKNESS" instead.
Rule for printing the description of a dark room: say "IT IS NOW PITCH BLACK. IF YOU PROCEED YOU WILL LIKELY FALL INTO A PIT." instead.

Test me with "w / e / w / w".

This is only the second oldest problem in the IF literature: the earliest puzzle is unlocking the steel grate which bars entrance to the cave.

306. Misadventure

The original Adventure allowed the player to type the names of rooms in order to move to them, and it is now not too difficult for us to do the same. Adventure restricted this option to adjacent rooms, but we might want to be a bit more flexible, so we will accept any room:

paste.png "Misadventure"

Plover Room is a room. "You're in a small chamber lit by an eerie green light. An extremely narrow tunnel exits to the west. A dark corridor leads northeast."

The Dark Corridor is northeast of Plover Room. Plover Room is south of the Dark Corridor. The printed name of the Dark Corridor is "Dark Room". The description of the Dark Corridor is "You're in the dark-room. A corridor leading south is the only exit."

The Alcove is west of Plover Room. "You are in an alcove. A small northwest path seems to widen after a short distance. An extremely tight tunnel leads east. It looks like a very tight squeeze. An eerie light can be seen at the other end."

Northwest of the Alcove is the Misty Cavern. The description of Misty Cavern is "You are following a wide path around the outer edge of a large cavern. Far below, through a heavy white mist, strange splashing noises can be heard. The mist rises up through a fissure in the ceiling. The path exits to the south and west." West of Misty Cavern is the Alcove.

Understand "[any room]" as going by name. Understand "go to [any room]" as going by name.

Going by name is an action applying to one thing.

We should reject movement to the player's current location, or to anywhere he hasn't been and can't see:

Check going by name:
    if the noun is the location, say "You're already in [the location]." instead;
    if the noun is not adjacent and the noun is unvisited, say "That noun did not make sense in this context." instead.

The assumption here is that the player does know the names of the rooms adjacent to his current location, even if he hasn't been there yet.

Now for the travel itself. The simplest way to ensure that the usual movement rules will still apply is to convert GO BY NAME into a GO action, and here the best route comes to our aid:

Carry out going by name:
    let aim be the best route from the location to the noun, using doors;
    if aim is not a direction, say "You can't think how to get there from here." instead;
    say "(heading [aim])[command clarification break]";
    try going aim;
    if the location is not the noun, say "You'll have to stop here."

This will allow the player to travel toward rooms he has already visited even if they are several moves away.

Finally, so that the player can also use the names of doors as commands:

Understand "[door]" as entering.

And in keeping with the original, we might add to our scenario a rule or two about restrictions on movement, just to test that it's all working right:

The player carries a plover egg and a platinum pyramid. The description of the egg is "Plover's eggs, by the way, are quite large." The printed name of the egg is "emerald the size of a plover's egg". Understand "emerald" as the egg. The description of the pyramid is "The platinum pyramid is 8 inches on a side!"

Instead of going to the Plover Room from the Alcove when the player carries something which is not the plover egg:
    say "Something you're carrying won't fit through the tunnel with you. You'd best take inventory and drop something."

Test me with "go to misty cavern / go to dark corridor / go to plover room / go to alcove / go to dark corridor / drop pyramid / go to dark corridor / g / go to alcove / g / go to misty cavern".

372. Minimal Movement

Sometimes it would be nice to respond a little more sensitively to a vague command such as "leave" -- converting it, perhaps, to a "go out" command.

paste.png "Minimal Movement"

The Doll-like House is a room. The Postage-Stamp-Sized Garden is outside from the House.

Rule for supplying a missing noun while going:
    now noun is outside.

This particular situation is very slightly complicated by the existing rules about vague movement, but fortunately we can easily turn those off.

The block vaguely going rule is not listed in the for supplying a missing noun rules.

Test me with "go".

394. Saint Eligius

A not-infrequent desire in IF is to provide a few lines of comment when the player first enters a new room, after the objects are described but before anything else (such as an every turn rule) can fire. The cleanest, most systematic solution is to add a rule to the carry out looking rulebook, so:

paste.png "Saint Eligius"

The first look rule is listed after the room description paragraphs about objects rule in the carry out looking rules. A room can be commented or uncommented. A room is usually uncommented.

This is the first look rule:
    if the location is uncommented, carry out the gawking at activity with the location.

Gawking at something is an activity.

Rule for gawking at the Diamond Market:
    say "Your throat closes and your eyes begin to sting. You have long disdained pomp and luxury, and railed against the oppression that brings such wealth to some men at the cost of the lives of others; you were not prepared for the magnificence."

After gawking at a room (called the target): now the target is commented.

And now the scene itself:

The Cobbled Alley is a room. "The Alley has never been made into a proper street: the buildings on either side are simply too important to tear down. For all that, there isn't much sign of the magnificence nearby. The entrance you seek is set below street level, four grimy steps down to a half-basement."

After going to Diamond Market:
    say "You descend the steps quickly and step into the small foyer, allowing yourself to be searched for weapons, before going on to...";
    continue the action.

Diamond Market is down from Cobbled Alley. "The roof is vaulted and painted in allegorical images representing Plenty, the Riches of the Earth, and Saint Eligius, patron of goldsmiths and jewelers.

Under their watchful eye, dozens of men in sober black robes sit; and on the tables before them are rubies, emeralds, sapphires from oversea, but most of all diamonds, both raw and cut."

The burly guard is a man in Diamond Market. "A burly guard patrols quite close to you, but even he is more sumptuously dressed than the average burly guard, and his buttons shine."

Test me with "d / look".

6. Up and Up ★★

Sometimes when a player moves from one room to another, we want to imply that a considerable amount of time elapses, or that something interesting occurs on the way. In that case, we might want to print more than just the room description itself. Here is how we might define a couple of rooms that are far apart:

paste.png "Up and Up"

The Plain of the Skull is below the Endless Tower. The description of the Plain of the Skull is "A vast and trackless plain, enlivened only by the bones of those who have previously tried and failed to cross. Above you is the Endless Tower, which rises half-way to the moon."

The description of the Endless Tower is "From up here the Plain of the Skull seems only a small bald patch: the world is round and most of it is covered with trees. Far off to the southwest is a shimmering surface that might be water; but there are no signs of cities or civilizations, only the lizard-skeletons."

And now we borrow from the instructions on Actions to create our actual message. "Before..." introduces a rule that occurs when the player tries to do something; in this case, we will make a Before rule for going to the tower.

Before going to the Endless Tower:
    say "You climb... and climb... and climb... The sun sets. The moon rises. The wind begins to blow. You continue to climb..."

The player carries a bit of harness. The description of the harness is "A strip of worked leather and a loop of metal, scavenged from one of the skeletons on the plain. Without it, you might think your entire quest was in vain."

Test me with "look / up".

256. Wonderland ★★

Suppose we have a landscape with a great deal of up and down variation, where GO UP and GO DOWN will be significant almost everywhere, and specifying them all individually a tremendous pain:

paste.png "Wonderland"

An altitude is a kind of value. 1000 feet specifies an altitude. A room has an altitude.

Definition: a room is low if its altitude is 3000 feet or less. Definition: a room is high if its altitude is 5000 feet or more.

Instead of going down:
    if an adjacent room is lower than the location:
        let the valley be the lowest adjacent room;
        let the way be the best route from the location to the valley;
        say "(that is, [way])[paragraph break]";
        try going the way;
    otherwise:
        say "You're in a local valley: there's no down from here."

Instead of going up:
    if an adjacent room is higher than the location:
        let the peak be the highest adjacent room;
        let the way be the best route from the location to the peak;
        say "(that is, [way])[paragraph break]";
        try going the way;
    otherwise:
        say "You're on a local peak."

Paradise is a room. Paradise has altitude 5400 feet. "A handsome parking lot, a picnic ground, and the Henry M. Jackson Memorial Visitor Center. The latter offers, for serious climbers, a hot shower; for nature enthusiasts, an interpretive museum; and for car-trippers, a gift shop selling canned slugs. All of which is a largely unsuccessful distraction from the peak of Mt. Rainier beyond."

Cougar Rock is southwest of Paradise. The altitude of Cougar Rock is 3180 feet. "Numerous individual campsites and (on the road inventively labeled 'F') a handful of larger campgrounds suitable for church groups and family reunions."

Longmire is southwest of Cougar Rock. It has altitude 2760 feet. "A tiny town: it has to offer a few groceries, a post office, and a lodge for people who do not care to camp, all built in a rustic Park Service way."

Panorama Point is north of Paradise. It has altitude 6800 feet. Camp Muir is north of Panorama Point. It has altitude 10188 feet. Columbia Crest is northwest of Camp Muir. It has altitude 14410 feet. St Andrews Rock is west of Columbia Crest. It has altitude 10992 feet. Camp Schuman is northeast of Columbia Crest. It has altitude 9510 feet.

Since Mount Rainier National Park runs to over 235,000 acres, we will omit the rest of the locations, but it does seem fair to give a little more credit to anyone who makes the summit:

Instead of going up in the highest room:
    say "You're standing at the summit of Mt. Rainier, the highest point in the state of Washington. There is no up."

Test me with "up / up / up / down / down / up / up".

307. Safari Guide ★★

The foregoing example moves the player one location towards his destination, and requires that rooms have been visited before. But suppose we wanted to be a bit more lenient about movement, and let the player make as many steps as necessary per turn. We will also show consideration about doors, using the "Locksmith" extension supplied with Inform. (Now every time the code attempts opening a door, unlocking rules will also be invoked.)

paste.png "Safari Guide"

Include Locksmith by Emily Short.

The Monkey House is a room. The African Grasslands Exhibit is north of the Monkey House. The bird door is north of the African Grasslands Exhibit and south of the Aviary. The Ostrich Enclosure is west of the Aviary. The bird door is a door. It is closed, lockable, and locked. The silver key is a passkey. It unlocks the bird door. The player carries the silver key.

Understand "go to [any room]" as going by name. Understand "[any room]" as going by name. Understand "[door]" as entering.

Going by name is an action applying to one thing.

Check going by name:
    if the noun is the location, say "You're already in [the location]." instead.

Carry out going by name:
    while the player is not in the noun:
        let heading be the best route from the location to the noun, using even locked doors;
        if heading is not a direction, say "You can't think how to get there from here." instead;
        let destination be the room heading from the location;
        say "(heading [heading])[command clarification break]";
        try going heading;
        if the player is not in the destination, rule fails.

Test me with "go to aviary / go to ostrich enclosure / african grasslands".

Notice that we continue the movement until one of two things happens: either the player reaches the room that is his destination, or the going attempt doesn't work. In the latter case we stop the action in order to avoid hanging the game up in a loop. This event might occur when the player runs into a locked door, for instance.

102. Polarity ★★★

The main trick of this is always to record where the player has gone when he has just moved.

paste.png "Polarity"

The former location is a room that varies.

Here we record where the player has been before moving him; by calling this the "first carry out going rule", we make sure that this rule is followed during the going action before any other pieces of the movement occur. For more detail, see the chapters on advanced actions and on rules.

First carry out going rule:
    now the former location is the location.

Understand "go back" as retreating. Understand "back" or "return" or "retreat" as retreating.

Retreating is an action applying to nothing.

Carry out retreating:
    let way be the best route from the location to the former location, using doors;
    if way is a direction, try going way;
    otherwise say "You can't see an open way back."

And to deal with the case where the player has not yet moved:

When play begins: now the former location is the Dome.

Instead of retreating when the former location is the location: say "You haven't gone anywhere yet."

Dome is a room. North of Dome is North Chapel. South of the Dome is South Chapel. West of the Dome is Western End. Quiet Corner is northwest of the Dome, north of Western End, and west of North Chapel. Loud Corner is east of North Chapel, northeast of Dome, and north of Eastern End. Eastern End is north of Dim Corner and east of Dome. Dim Corner is southeast of Dome and east of South Chapel. Ruined Corner is southwest of Dome, west of South Chapel, and south of Western End.

The church door is east of Eastern End and west of the Courtyard. The church door is a door.

Test me with "back / n / go back / e / open door / go through door / go back".

103. Bumping into Walls ★★★

paste.png "Bumping into Walls"

First we add an instruction to determine which ways lead to other rooms.

Definition: a direction (called thataway) is viable if the room thataway from the location is a room.

Now we build in the instruction for what Inform should say if the player tries to head in a direction that leads nowhere:

Instead of going nowhere:
    let count of exits be the number of viable directions;
    if the count of exits is 0, say "You appear to be trapped in here." instead;
    if the count of exits is 1, say "From here, the only way out is [list of viable directions].";
    otherwise say "From here, the viable exits are [list of viable directions]."

There is no theoretical reason why we have to define "count of exits" here: we could, if we wanted, just say "if the number of viable directions is 0", "if the number of viable directions is 1", and so on. However, each calculation of a "viable direction" takes a bit of computing power, so there is some slight savings in not requiring the game to count viable directions more than once in this routine.

Dome is a room. North of Dome is North Chapel. South of the Dome is South Chapel. West of the Dome is Western End. Quiet Corner is northwest of the Dome, north of Western End, and west of North Chapel. Loud Corner is east of North Chapel, northeast of Dome, and north of Eastern End. Eastern End is north of Dim Corner and east of Dome. Dim Corner is southeast of Dome and east of South Chapel. Ruined Corner is southwest of Dome, west of South Chapel, and south of Western End.

The Crypt is below the dome.

The church door is east of Eastern End and west of the Courtyard. The church door is a door.

Test me with "u / n / n / e / n / s / u / open door / e / n".

107. Zorb ★★★

There are two aspects of Inform's handling of pushable objects that are particularly prime for modification. One is that we may want to change the language used to refuse the pushing of unpushable objects.

Second, Inform by default assumes that it is impossible to push objects in up or down directions. This makes lots of sense if the player is trying to push a wheelbarrow up a ladder; it makes less sense if instead we're pushing a ball up a slope.

We solve both problems with some syntax borrowed from the chapter on rulebooks: in the first case, we replace the old rule with a new one with more friendly phrasing; in the second, we remove the rule entirely. More about how to do this is described in the rulebooks chapter; and in general we can find out what rules contribute to any given action by looking at the Actions index. In this case, the action is "pushing it to", which has its own set of prerequisites (called check rules) that make sure the object can safely be pushed, before turning processing over to the going action.

paste.png "Zorb"

Section 1 - Procedure

The new can't push unpushable things rule is listed instead of the can't push unpushable things rule in the check pushing it to rules.

This is the new can't push unpushable things rule:
    if the noun is not pushable between rooms:
        say "[The noun] [are] not amenable to being pushed from place to place." instead.

The can't push vertically rule is not listed in any rulebook.

And now to provide a scenario where the player can push something up and down a hillside. Most of the rest of the example is there for local color and to provide a way to demonstrate these rule adjustments:

Section 2 - Scenario

The Steep Hill is a room. The Crest is above Steep Hill. The Valley is below Steep Hill.

The flat rock is a fixed in place thing in the Steep Hill.

The Zorb is a transparent open enterable container in the Steep Hill. "[if the player props the Zorb]The Zorb rests here, kept from further rolling by your support[otherwise]The Zorb is here[end if].". It is pushable between rooms. The description of the Zorb is "A giant plastic inflatable ball, like a hamster ball for humans[if someone is in the Zorb]. Inside [is-are list of people in the Zorb][end if]."

Lucy is a woman in the Zorb.

Carry out going with the Zorb when the Zorb contains Lucy:
    say "Lucy whoops delightedly as she rides along in the Zorb."

Every turn when the Zorb is not in the Valley and the player does not prop the Zorb:
    let next room be the room down from the location of the Zorb;
    if the player is not in the Zorb and the player can see the Zorb:
        say "The Zorb succumbs to gravity and rolls down toward [the next room].";
    move the Zorb to the next room;
    if the player is in the Zorb:
        say "The Zorb rolls you down the hill!";
        try looking;
    otherwise if the player can see the Zorb:
        say "The Zorb rolls ponderously but inevitably into the vicinity.";

Propping relates one person to one thing. The verb to prop means the propping relation.

Carry out going with the Zorb:
    now the player props the Zorb.

Before doing something when the action requires a touchable noun:
    if the noun is not the Zorb, now the player does not prop the Zorb.

Check waving hands when the player is propping something (called casualty):
    try the player releasing the casualty.

Carry out entering the Zorb:
    now the player does not prop the Zorb.

Understand "let go of [something]" or "let [something] go" or "release [something]" or "free [something]" as releasing. Releasing is an action applying to one thing.

Check releasing:
    if the player carries the noun:
        try dropping the noun instead.

Check releasing:
    if the player does not prop the noun:
        say "You are not supporting [the noun]." instead.

Carry out releasing:
    now the player does not prop the noun.

Report releasing:
    say "You let go of [the noun]."

Test me with "d / push zorb up / look / push zorb up / wave / d / d / push zorb up / release zorb / d / push zorb up / touch rock / push the flat rock south".

108. Provenance Unknown ★★★

Suppose we have a series of items that might be stacked on top of one another -- say a heavy television on a rolling cart, and we want the player to be able to move the cart with PUSH TELEVISION EAST just as well as with PUSH CART EAST.

This takes a little redirection, using a setting action variables rule. This is not a kind of rule we've encountered yet, and in fact we won't meet it until the Advanced Actions chapter; it is included here for the convenience of authors who want to modify the effect of pushing without reading that far ahead:

paste.png "Provenance Unknown"

Setting action variables for pushing something to:
    if the noun is enclosed by a pushable between rooms thing (called the pushed item) which is in the location:
        now the noun is the pushed item instead.

This rule says that any time we push an object that is on top of a stack of pushable objects, we should transfer the action to the item at the bottom of the stack.

The rest is merely a test case.

The heavy golden idol is on a roller board. The roller board is on a hovercraft.

The hovercraft, the tea trolley, and the skateboard are pushable between rooms.

The hovercraft is in Zeta Proximan Dig Field.

Zeta Proximan Dig Field is a room. "During the day, the field is massed with sweating native workers, overseers, and officials from central command. Now the spades, trowels, brushes, metal detectors, ground probes, plumb lines, and sighting tripods have been laid aside.

All that remains are the trenches and the fine grey dust that blows slowly across them; the moonlight; and the just-emerging outlines of an ancient and alien wall."

The Hover-Road is west of the Dig Field. "A long road hastily laid down, stretching east to west, from the dig site toward the safety of the city."

When play begins:
    say "You have, at last, loaded your illicit cargo without setting off any of the many and sensitive alarms set here; now it remains only to sneak out of the area, under the light of Zeta Proxima's lone green moon."

Test me with "push idol west / look / push roller board east / look".

179. Owen's Law ★★★

Suppose we want the game to interpret "GO OUT" as "move towards an outdoors room, or towards a room with more exits than the current room", while "GO IN" means "move toward a room with fewer exits, or towards an indoors room". Thus going in repeatedly within a building would lead towards dead-ends, while going out repeatedly would lead towards the center of the building and then towards an exit to the outside world.

We start by encoding these rules as definitions:

paste.png "Owen's Law"

A room can be indoors or outdoors. A room is usually indoors.

Definition: a room is outward:
    if it is not adjacent, no;
    if it is indoors and the location is outdoors, no;
    if it is outdoors and the location is indoors, yes;
    if the number of rooms adjacent to it is greater than the number of rooms adjacent to the location, yes;
    otherwise no.

Definition: a room is inward:
    if it is not adjacent, no;
    if it is outdoors and the location is indoors, no;
    if it is indoors and the location is outdoors, yes;
    if the number of rooms adjacent to it is less than the number of rooms adjacent to the location, yes;
    otherwise no.

Instead of going nowhere when the noun is outside: try exiting.

Instead of exiting when the player is in a room:
    if at least one room is outward:
        let the destination be a random outward room;
        let the way be the best route from the location to the destination;
        say "(that is, [way])[command clarification break]";
        try going the way instead;
    otherwise:
        say "It's not entirely obvious which way you mean. ";
        carry out the listing available exits activity.

Instead of going inside when the room inside from the location is not a room and at least one room is inward:
    if more than one room is inward:
        carry out the listing available exits activity;
    otherwise:
        let the destination be a random inward room;
        let the way be the best route from the location to the destination;
        say "(that is, [way])[command clarification break]";
        try going the way instead.

Instead of going nowhere:
    carry out the listing available exits activity.

This "listing available exits" is a refinement borrowed from a future chapter, which allows us to specify special listing and printing rules:

Listing available exits is an activity.

Rule for listing available exits:
    if going inside and an adjacent room is inward:
        say "From here 'in' could reasonably mean [a list of adjacent inward rooms].";
        rule succeeds;
    if exiting and an adjacent room is outward:
        say "From here 'out' could reasonably mean [a list of outward adjacent rooms].";
        rule succeeds;
    say "From here you can go [a list of adjacent rooms]."

Before printing the name of a room (called the target) while listing available exits:
    let aim be the best route from the location to the target;
    say "[aim] to the ".

Rule for printing the name of an unvisited room which is not the location:
    say "unknown location".

Dune is an outdoors room. "Hundreds of feet of dune stretch west to the beach, crisscrossed with dune-buggy tracks and the footprints of birds. To the east is a low-lying, boxy concrete installation."

Ocean Shores Military Installation is east of the Dune. It is an outdoors room. "The World War II emplacements, built in case of Japanese invasion, have never been destroyed, though with all the weapons and furnishings gone it is difficult to make much sense of the original structure. A doorway leads west into concrete-lined darkness; a rusty but reliable ladder ascends to a walkway overlooking the sea."

Walkway is above Ocean Shores Military Installation. "From here you have a long view of the dunes and the Pacific Ocean, complete with the rotting hull of a long-stranded vessel."

Dark Echoing Room is inside from Ocean Shores Military Installation. Dank Dripping Room is east of Dark Echoing Room. Narrow Room is south of Dark Echoing Room. Small Sealed Chamber is north of Dark Echoing Room. Room Smelling of Animal Urine is north of Dank Dripping Room. The description of a room is usually "It is dark in here, and feels unsafe."

Test me with "e / u / d / in / s / out / n / out / e / in / out / out / out".

RB §6.10. Entering and Exiting, Sitting and Standing

Under ordinary circumstances, Inform does not keep track of the player's posture, nor of his exact location in a room. Lies implements a room in which the player can lie in different positions on the floor, getting different views as a result.

Our other examples are all modifications of the way Inform handles player movement to make better default guesses at what he wants to do: Anchorite adds a GET DOWN and DOWN command that work when the player is on a supporter, to accompany GET UP, GET OFF, and GET OUT (already understood). Get Axe makes the player get out of a portable container before attempting to lift it - a consideration that comes up relatively rarely, but that might pertain to inflatable rafts, beanbag chairs, and other lightweight but capacious pieces of furniture.

See also

Position Within Rooms for a box the player can push around the room and stand on in different locations
The Human Body for letting the player sit, stand, or lie down systematically on furniture or on the floor
Furniture for various objects on which the player can sit or stand

Examples

206. Get Axe

We could now re-write the check rules so that any time someone (the player or someone else) tries to pick up a container which he is in, he will first get out:

paste.png "GET AXE"

This is the clever can't take what you're inside rule:
    if the person asked is in the noun, try the person asked exiting;
    if the person asked is in the noun, rule fails.

The clever can't take what you're inside rule is listed instead of the can't take what you're inside rule in the check taking rules.

Attic is a room. The unused coffin is in the Attic. The coffin is enterable and openable and open. Raskolnikov is a man in the coffin.

Persuasion rule for asking Raskolnikov to try doing something:
    persuasion succeeds.

Test me with "raskolnikov, get coffin".

289. Anchorite

With GET DOWN, we can replace the whole command, which will not interfere with the normal function of the TAKE verb, or allow the player to attempt to GET any other directions:

paste.png "Anchorite"

The Solitary Place is a room. "A glittering, shimmering desert without either locusts or honey." The pillar is an enterable supporter in the Solitary Place. "The broken pillar is short enough to climb and sit on." The description of the pillar is "Once it was a monument: a long frieze of battles and lion-hunts spirals up the side, in honor of an earthly king." The player is on the pillar.

Understand "get down" as exiting.

This doesn't cover the case where the player just types "DOWN", and we don't want to preempt the normal operation of the GO action here. So instead of writing a new understand instruction, we might catch this one at the action-processing level:

Instead of going down when the player is on a supporter:
    try exiting.

Test me with "down / enter pillar / get down / down / get down".

310. Lies

To set the scene, and make new actions to provide for two of these ways:

paste.png "Lies"

The Laundry is a room. "An old Limehouse haunt, the Chinese laundry used by the down-trodden wives of the Tong of the Black Scorpion." The vast marble sink is here. "There is nothing obviously oriental about the vast marble sink, which is large enough to lie down inside. A wooden-rack floor, equipped for easy drainage, turns out also to be equipped for snagging the shoes of passers-by." The sink is an enterable container, fixed in place.

Lying down is an action applying to nothing. Report lying down: say "You lie down for a while in the middle of the Laundry, wondering about the point of existence, then get up again."

Lying near is an action applying to one thing. Report lying near: say "You lie down next to [the noun] for a while, mumbling to yourself."

Instead of lying near the sink, say "Lying down close to the cool butcher's marble slabs of the sink, your attention is caught by the sight of coolie shoes through a floor-level grille for ventilation. The game is afoot!"

So far, so good. Now for the grammar, where we create two new tokens: one for each of two groups of alternative prepositions.

Understand "beneath/under/by/near/beside/alongside/against" or "next to" or "in front of" as "[beside]".

Understand "on/in/inside" or "on top of" as "[within]".

Understand "lie down" as lying down.

Understand "lie down [within] [something]" as entering.

Understand "lie [beside] [something]" or "lie down [beside] [something]" as lying near.

Test me with "lie down / lie down on top of the sink / get out / lie down inside the sink / get out / lie down in front of the sink".

RB §6.11. Waiting, Sleeping

The standard WAIT command makes time pass at the same rate that it would anyway - one minute per turn. In a story where events happen at specific times of day, though, we might want to give the player more control. Nine AM Appointment shows how to give the player a WAIT 10 MINUTES command, while Delayed Gratification ★★ lets him WAIT UNTIL a specific time of day.

Ordinarily, Inform also refuses to allow the player to SLEEP and WAKE UP: the commands exist, but have no effect. Change of Basis ★★ lets the player put himself into a sleep state in which he cannot do anything. A somewhat more interesting expansion on this idea would be to let the player sleep and have dreams; there are no examples specifically of dream states, but we might consult the examples on scenes about how to disrupt one environment and move the player to another, entirely new one.

See also

Scene Changes for ways to move the player to a new environment such as a dream state

Examples

388. Nine AM Appointment

If there's some reason the player needs to be at a specific place and time, we might want to allow him to wait a number of minutes at once.

paste.png "Nine AM Appointment"

Waiting more is an action applying to one number.

Understand "wait [a time period]" or "wait for [a time period]" or "wait for a/an [a time period]" or "wait a/an [a time period]" as waiting more.

Carry out waiting more:
    let the target time be the time of day plus the time understood;
    decrease the target time by one minute;
    while the time of day is not the target time:
        follow the turn sequence rules.

The one nuance here is that after our wait command occurs, the turn sequence rules will occur one more time. So we need to subtract one minute from the parsed time to make the turn end on the desired number of minutes.

Report waiting more:
    say "It is now [time of day + 1 minute]."

And if we want to ensure that the player doesn't (accidentally or intentionally) put the interpreter through a really long loop, we could put an upper limit on his patience:

Check waiting more:
    if the time understood is greater than one hour, say "You really haven't got that kind of patience." instead.

The Specialist's Office is a room. The secretary is a woman in the Office. Instead of asking the secretary about "[appointment]", say "'Hang on just five more minutes,' she says, in a distracted manner."

Understand "appointment" or "specialist" or "doctor" as "[appointment]".

At 9:45 AM: say "At [the time of day in words], secretary glances at you and gives a reassuring smile."

Test me with "ask secretary about appointment / wait five minutes / g / g / wait 61 minutes / wait for half an hour / wait for a quarter of an hour / wait for an hour".

47. Change of Basis ★★

Suppose we want to allow the player to go to sleep some of the time:

paste.png "Change of Basis"

A person is either awake or asleep. A person is usually awake.

The important thing to note here is that it does not work to say "the player is either asleep or awake". This is because the player is not necessarily one specific person or thing during the game: the identity of the player can be changed, as we will see later.

So if we want to make rules about the properties of the player, we should attach these rules to the "person" kind.

Linear Algebra Class is a room. "The blackboard is covered with square arrangements of numbers. These are supposed to convey something to you, but mostly you're finding them soporific."

Now a few rules about changing from one state to the other:

Instead of sleeping: now the player is asleep; say "You drop off."

Instead of doing something other than waking up, waiting or sleeping when the player is asleep:
    say "Ssh! You're sleeping!"

Instead of sleeping when the player is asleep:
    say "Zzzz."

Instead of waking up when the player is asleep:
    now the player is awake;
    say "You come to suddenly, wiping drool from your lips."

Instead of doing something other than looking or sleeping when the player is awake:
    say "You'd really rather just sleep through this."

Test me with "wake up / sleep / look / z / sleep / wake up / look".

389. Delayed Gratification ★★

paste.png "Delayed Gratification"

Hanging around until is an action applying to one time.

Check hanging around until:
    if the time of day is the time understood, say "It is [time understood] now!" instead;
    if the time of day is after the time understood, say "It is too late for that now." instead.

Carry out hanging around until:
    while the time of day is before the time understood:
        follow the turn sequence rules.

Report hanging around until:
    say "You yawn until [time understood]."

Understand "wait until [time]" as hanging around until.

The Empty Field is a room. "It's an ordinary empty field. Nothing to see here at all-- yet. Wait until 11:45 PM, though."

At 11:45 PM:
    say "Suddenly the air is filled with light and the sounds of an approaching band. Over the crest of the hill comes a parade of singing, stomping, hooting people: and not just people, but dogs, horses, elephants, giraffes... There are banners, and candles, and a flag that glows eerie-green in the dark; there is a float shaped like an enormous turtle, its shell covered with winking green lights; there is an old man dressed as a skeleton, carried in a litter, his neck garlanded with dried chiles. There are small girls throwing rose petals from a basket, and grown women half-naked carrying the emblems of Bacchic revelry, and two little boys each with a silver basin of clear water. All these go by in procession, and you join on at the end.";
    end the story finally.

Test me with "look / z / z / wait until 11:45 PM".

RB §6.12. Other Built-In Actions

Many other actions are themselves very simply implemented and provide only a shell for us to expand on according to the needs of a particular story. Many of these are discussed at more length in sections on various kinds of props and objects; in particular:

See also

Modifying Existing Commands for ways to override automatic takes or restrictions on what the player must be able to hold or touch
Sounds for LISTEN
Barter and Exchange for GIVE and SHOW
Combat and Death for ATTACK
Saying Simple Things for ASK, TELL, and ANSWER
Food for TASTE and EAT
Liquids for DRINK
Clothing for WEAR and TAKE OFF
Bags, Bottles, Boxes and Safes for OPEN, CLOSE, LOCK, and UNLOCK as applied to containers
Doors, Staircases, and Bridges for OPEN, CLOSE, LOCK, and UNLOCK as applied to doors
Furniture for things the player can ENTER and GET OUT of
Money for BUY
Fire for BURN

RB §6.13. Magic Words

Many fantasy games incorporate the idea of magic words that can be spoken. In implementing these, we want to be a bit flexible and accept a range of input regardless of whether the player explicitly speaks the command aloud: XYZZY, SAY XYZZY, or perhaps even CAST XYZZY. The inventively named Xyzzy demonstrates how we might define such a command.

If we want to go even further and to allow the player also to use quotation marks, as in SAY "XYZZY", we may want to include Punctuation Removal by Emily Short, which allows for quotation marks to be stripped out of the player's input before it is understood.

Examples

286. XYZZY

We have seen before how to define a new action from scratch, but we may want to review here, using a simple command that requires no objects.

paste.png "XYZZY"

Understand "xyzzy" or "say xyzzy" or "cast xyzzy" as casting xyzzy.

Casting xyzzy is an action applying to nothing.

Check casting xyzzy:
    if the player does not wear the amulet of elocution, say "You are unable to articulate the second 'z' separately from the first, and the spell fails in a disdainful puff. Must be Parisian magic." instead;
    if the player has the plate, say "The plate of cheeses twitches uncomfortably, aware that it should be doing something, but not sure what." instead.

Carry out casting xyzzy:
    move the plate to the player.

Report casting xyzzy:
    say "Under the influence of the Amulet of Elocution, you pronounce this as Xhi-zee. And lo, from nowhere, a [plate] appears!"

The amulet of elocution is a wearable thing. It is carried by the player. The description is "A heavy gold ring on a chain. If heated in an ordinary house fire, it glows with the words, 'Moses Supposes His Toeses Are Roses.'"

The plate is a portable supporter. On the plate is a very ripe ooze. Instead of smelling the ooze, say "It smells like socks. This is going to be wonderful." The ooze is edible. The printed name of the plate is "plate[if the plate supports the ooze] of cheese[end if]". The description of the ooze is "Definitely genuinely cheese." Understand "cheese" as the ooze.

Instead of eating the ooze: now the ooze is nowhere; say "You are transported..."; move the player to Paradise.

The Cheez Factory is a room. "All around you are squares of pressed orange polymer, or possibly cheez. Your only hope is the magic word your uncle taught you: XYZZY." The squares of pressed orange polymer are scenery in the Factory. The description is "You see nothing special about the squares of pressed orange polymer. Nothing special at all." Understand "square" or "cheez" as the squares.

Paradise is a room. The description is "Well, it might just be one of the posh upper rings of purgatory, if you're entirely honest with yourself."

Test me with "x squares / x amulet / x cheese / xyzzy / wear amulet / xyzzy / x ooze / smell ooze / eat ooze".

XYZZY is a magic word from the original Adventure, and many other games respond to it with some sort of amusing message.

RB §6.14. Remembering, Converting and Combining Actions

Sometimes we want Inform to apply a player's action to a different target than the one specified: for instance, directing all (or almost all) commands from the doorknob to the door of which it is a part. Fine Laid demonstrates how to do this. Along the same lines, Lucy shows how to direct a player's conversation action to apply to a new conversation topic.

We can also record a series of actions performed by the player or by another character.

Cactus Will Outlive Us All demonstrates characters each of whom reacts to a very specific provocation; I Didn't Come All The Way From Great Portland Street implements a game show in which the player is not allowed ever to repeat an action he has already performed; and Leopard-skin implements a maze which the player can escape only by performing a specific sequence of actions.

Anteaters ★★ provides a peculiar gizmo that can remember actions performed in its presence and force the player to reiterate them.

Examples

89. Fine Laid

Sometimes it is useful to direct all -- or almost all -- actions from one object to another. For the sake of argument, say we have a sheet of paper with writing on it, and (because we're very meticulous) we want to let the player examine the writing and get a customized response, different from when he just examines the sheet of paper. But for all other purposes -- say, TAKE or TASTE -- we want the two objects to be treated as one.

Here, we approach the problem by changing the noun and/or the second noun of the current action, then issuing a new command to "try the current action". Because we've changed the noun and second noun, the "current action" at this point is different from the one generated originally by the player's command.

paste.png "Fine Laid"

High Street Stationer is a room.

The sheet of paper is a thing in High Street Stationer. The writing is part of the sheet of paper.

The description of the sheet of paper is "A beautiful sheet of heavy cream paper." The description of the writing is "Delicate and spidery."

Instead of tasting the sheet of paper, say "You might need more fiber in your diet, but this isn't the way.".

Before doing something other than examining when the current action involves the writing:
    if the writing is the noun, now the noun is the sheet of paper;
    if the writing is the second noun, now the second noun is the sheet of paper;
    try the current action instead.

Test me with "examine sheet of paper / examine writing / get writing / taste writing".

91. Lucy

Occasionally we will want to replace the player's question topic with another of our own devising. We can do this in the simplest possible case like so:

paste.png "Lucy"

The International Boardgame Championship is a room. Lucy is a woman in the Championship.

Instead of asking Lucy about "checkers":
    try asking Lucy about "games".

Instead of asking Lucy about "games",
    say "'I don't like games,' she sniffs."

Test me with "ask lucy about checkers / ask lucy about games".

Note that this syntax did not work in older versions of Inform; it is now safe.

219. Cactus Will Outlive Us All

paste.png "Cactus Will Outlive Us All"

Death Valley is a room. Luckless Luke and Dead-Eye Pete are men in the Valley. A cactus is in the Valley. Persuasion rule: persuasion succeeds.

A person has an action called death knell. The death knell of Luckless Luke is pulling the cactus. The death knell of Dead-Eye Pete is Luke trying dropping the cactus.

Before an actor doing something:
    repeat with the victim running through people in the location:
        let the DK be the death knell of the victim;
        if the DK is not waiting and the current action is the DK:
            say "It looks as if [the DK] was the death knell for [the victim], who looks startled, then nonexistent.";
            now the victim is nowhere.

If we leave it at that, then pulling the cactus will kill Luckless Luke but then say "Nothing obvious happens.", which seems like a bit of an anti-climax. So we add a special case response for that one:

After pulling the cactus when Luckless Luke was in the location:
    say "That's a real shame."

Test me with "get cactus / drop cactus / luke, get cactus / luke, drop cactus / pull cactus / look".

430. Leopard-skin

Suppose (as in Infocom's Leather Goddesses of Phobos) that we have a maze that the player can escape only by performing the correct sequence of actions in the correct order. One way to do this would be to keep a list of the player's most recent actions, and see whether these match up with the combination we have established as the maze's solution.

For instance:

paste.png "Leopard-skin"

The Fur-Lined Maze is a room. "This seemingly endless sequence of rooms is decorated in a tasteful selection of exotic furs and gilded fixtures."

Clapping is an action applying to nothing. Understand "clap" as clapping.
Kweepaing is an action applying to nothing. Understand "kweepa" as kweepaing.

Carry out clapping:
    say "You clap."

Carry out kweepaing:
    say "You holler 'KWEEPA!' triumphantly."

The maze-sequence is a list of stored actions that varies.

When play begins:
    add jumping to the maze-sequence;
    add clapping to the maze-sequence;
    add kweepaing to the maze-sequence.

The attempted-sequence is a list of stored actions that varies.

Every turn when the player is in the Fur-Lined Maze:
    truncate the attempted-sequence to the last two entries;
    add the current action to the attempted-sequence;
    if the attempted-sequence is the maze-sequence:
        say "That does it! You are instantly transported from the maze!";
        end the story finally.

Test me with "hop / clap / clap / hop / kweepa / hop / clap / kweepa".

432. I Didn't Come All The Way From Great Portland Street

There is very little to this, in fact. The tricky rule to enforce is Repetition: the player is forbidden to repeat any previously tried action. We keep track of this by keeping a set of past actions, which for want of a better term is called the "tally". All we need to do is:

if the current action is listed in the tally, challenge for "Repetition of [the current action]!";
otherwise add the current action to the tally.

Note that the tally can never contain duplicates, and that when, at the end of the round, we print it out, we sort it first - this makes a more natural-looking sentence. (Sorting a list of actions uses the natural order for actions: compare the sequence on the Actions page of the Index.) The full text, then, is:

paste.png "I Didn't Come All The Way From Great Portland Street"

The Paris Theatre is a room. An instrument is a kind of thing. The violin, the tuba, the xylophone and the triangle are instruments. The violin is inside the case. The tuba, the xylophone, the radish, the case, the bust of Nicholas Parsons, the purple felt hat and the triangle are in the Paris Theatre.

The Round is a scene. The Round begins when play begins. The Round ends when the turn count is 10.

The tally is a list of stored actions that varies.

When the Round begins:
    say "'And the subject on the card is... musical instruments. Will you carry out for us something to do with that, please, for ten turns starting - now!'"

When the Round ends:
    sort the tally;
    say "Phweeep![paragraph break]'So, when the whistle goes ten turns are up, you get a point for acting when the whistle blows, and in that round you entertained us by [the tally], and you also get a bonus point for keeping going until the whistle went.'";
    end the story finally.

To challenge for (infraction - text):
    say "Bzzzzt! 'And [one of]Clement Freud[or]Derek Nimmo[or]Kenneth Williams[or]Peter Jones[at random] has challenged.'[paragraph break]'[infraction]'[paragraph break]'Well, as it's your first time playing the game, and the audience was enjoying your contribution so much, I will disallow the challenge, you have [10 minus the turn count] turn[s] left on musical instruments, starting... now!"

Before doing something:
    if the current action is listed in the tally, challenge for "Repetition of [the current action]!" instead;
    otherwise add the current action to the tally;
    if waiting, challenge for "Hesitation!" instead;
    if not looking and not waiting and the noun is not an instrument and the second noun is not an instrument, challenge for "Deviation!" instead.

Test me with "look / wait / examine bust / take tuba / get triangle / hit xylophone / get tuba / examine tuba / get violin".

(The Paris Theatre in Lower Regent Street, London, was for many years the home of BBC radio panel games.)

222. Anteaters ★★

paste.png "Anteaters"

A book is a kind of thing. Understand "book" as a book. A book has a table name called the contents.

Report consulting a book about:
    say "You flip through [the noun], but find no reference to [the topic understood]." instead.

Instead of consulting a book about a topic listed in the contents of the noun:
    say "[reply entry][paragraph break]".

The Guide to Desert Fauna is a book. The contents of the Guide is the Table of Critters.

Table of Critters

topic

reply

"spines"

"You flip through the Guide for a while and eventually realise that spines are flora, not fauna."

"anteater colonies"

"The giant anteater, which grows to six feet in size and can kill a jaguar, is a solitary animal, found in many habitats, including grasslands, deciduous forests and rainforests. It does not form colonies. That's ants. They're actually quite easy to tell apart."

Death Valley is a room. The Guide is in the Valley.

The gizmo is in Death Valley. The gizmo has an action called idea. The description of the gizmo is "The gizmo is hard to describe, but it projects an idea of [idea]."

Before when the player carries the gizmo and the idea of the gizmo is waiting:
    say "[The gizmo] eagerly soaks up the whole idea of [the current action].";
    now the idea of the gizmo is the current action.

After dropping the gizmo:
    say "The percussion of the fall seems to have shaken the gizmo's idea loose! There's nothing for it now but [idea of the gizmo].";
    try the idea of the gizmo;
    now the idea of the gizmo is waiting.

Test me with "get guide / look up spines in guide / x gizmo / get gizmo / i / x gizmo / drop gizmo / get gizmo / look up anteater colonies in guide / x gizmo / drop gizmo".

RB §6.15. Actions on Multiple Objects

Inform allows a handful of actions - TAKE, DROP, PUT, INSERT - to apply to more than one item at a time, so that the player can move things around easily.

The general principle is that multiple objects are allowed if the actions are likely to be successful but not interesting most of the time, and if they're things that the player could plausibly do all at once. For most actions, the use of ALL would seem weirdly indiscriminate: EAT ALL, say, describes very implausible behavior, and EXAMINE ALL would likely generate a screenful of text at once.

But this is all under our control. To create an action that uses multiples, or to allow the use of multiple objects with an already-existing action, we need to create an understand statement that uses the "[things]" token (note the plural). For instance:

Understand "give [things] to [someone]" as giving it to.

This would let the existing give action apply to multiple objects, in just the same way that "take" does. Shawn's Bad Day demonstrates how we might allow EXAMINE ALL to print descriptions of every visible item.

Alternatively, we could generate a new action:

Understand "give [things] to [someone]" as multiply-giving it to. Multiply-giving it to is an action applying to one carried thing and one thing.

(In theory the language here should perhaps be "several carried things" -- but Inform is still going to process multiply-giving item by item, unless we redirect it. More about this in a moment.)

When handling an action that uses the "[things]" token, the parser makes a list of every item to which it is going to apply the action: this is called the multiple objects list. The multiple objects list can be the result of a vague request (GET ALL) or a specific one involving identical multiples (GET PENNIES, GET THREE APPLES) or a very specific one involving unique, named nouns (GET GERBIL, APPLE, AND POMEGRANATE).

We can manipulate what Inform includes in "ALL" in sentences like TAKE ALL with the "deciding whether all includes..." activity; for instance

Rule for deciding whether all includes scenery: it does not.

prevents TAKE ALL from applying to things that can't be moved anyway, avoiding lots of lines like

tree: That's hardly portable.
swing set: That's hardly portable.

A slightly tedious technical note: the multiple objects list is not strictly a list in the standard Inform sense, because it is used so frequently in parsing that it would be cumbersome to handle it with the more flexible but less efficient structure used for lists. However, if we want to manipulate the multiple objects list as though it were an ordinary list -- that is, sort it, rotate it, truncate it, remove entries from it, etc -- we may do so by creating a list like this:

let L be the multiple object list.

and later after making L conform to our desires:

alter the multiple object list to L.

Inform next repeatedly runs the action rulebook for the action generated, using each item from the multiple object list as "noun" in turn (or as "second noun", if that's where the [things] token appeared in the understand line). Since it is possible to alter the multiple object list before the "generate action rule" portion of the turn sequence consults the rulebooks, we can also affect the order in which the player's matched objects are handled; see Formicidae ★★. We should not attempt to change the multiple object list after this point, because this is likely to introduce bugs.

Each time Inform tries the action on a new noun, it prefixes the action-attempt with the name of the item it's currently working on. This is where we get such output as "frog eyeballs:" and "newt toes:" in long lists like

frog eyeballs: Taken.
newt toes: Taken.

These names are generated by the "announce items from multiple object lists rule" in the action-handling rules; Escape from the Seraglio ★★ shows how to alter them. In the context of this rule, the thing we are currently printing the name of can be called "the current item from the multiple object list".

Suppressing names of objects entirely, while occasionally tempting, may have unintended consequences, especially if some of the attempted actions are prevented by check rules that themselves print things. It is safest to suppress the multiple object names in the case where we already know that the action will succeed wherever it is attempted (more often for observational actions like examining than for manipulative actions like taking, or where we mean to completely override default handling).

Given that our hypothetical "multiply-giving" applies to each given object in turn, it might seem to be useless to create "multiply-giving" as an action different from "giving" -- but the convenience is that manipulating the multiple object list makes it possible to group behavior artificially. The trick here is that, on the first pass of the multiply-giving rulebook, we look at the entire multiple object list, perform actions, print output, and set a flag saying that the action has been handled. The flag tells Inform not to do or print anything for any of the subsequent passes through that action rulebook; thus we artificially create a situation where, instead of performing an action on each object in turn, Inform acts once on the entire group. That allows us to assess the cumulative qualities of the group and have the action respond differently than it might when assessing each item individually.

The Facts Were These ★★ demonstrates how we might write an action for GIVE THREE DOLLARS TO MAN or GIVE PIE AND HAT TO MAN where the man would only accept the collective gift when its total proved satisfactory.

Western Art History 305 ★★ demonstrates how we might allow EXAMINE, which doesn't normally permit multiple objects, to take them, but to give vaguer responses to a mass examination than an individual one.

See also

Examining for groups of objects that have a collective description different from their individual descriptions, and for commands that search multiple things at once
Dispensers and Supplies of Small Objects for ways to let the player pick up a number of identical items from a dispenser or supply

Examples

294. Shawn's Bad Day

We can add the handling of multiple objects to an existing action simply by adding in a line of grammar using "[things]". In response, Inform will consider every object accepted by the token, and perform the action once for each of those objects. Thus:

paste.png "Shawn's Bad Day"

The Treasury is a room. The vault is a lockable locked closed openable container in the Treasury. It is fixed in place. "A massive vault fills up one wall." The description is "The vault's system includes [a list of things which are part of the vault]."

A little green light, a little blue light, a little red light, a thin black pane of glass, a laser beam, a retinal scanner, a thumbprint ID plate, a dial, and a large lever are part of the vault.

The security guard is a man in the Treasury. The description is "His name is Shawn, and he doesn't look happy."

The description of the green light is "Off." The description of the blue light is "Tranquilly on." The description of the red light is "Angrily flashing."

Understand "examine [things]" as examining.

Test me with "examine all".

327. Western Art History 305 ★★

In a gallery, there are many individual things to look at, but you can also get a general impression by just examining them as a collection.

First, we'll make a kind for the paintings exhibited in the gallery, and then we'll also make a special object to represent all of them as a mass:

paste.png "Western Art History 305"

A painting is a kind of thing. A painting is usually fixed in place. Understand "painting" as a painting. Understand "paintings" as the plural of painting.

The painting-collective is a thing. The printed name of the painting-collective is "paintings". The description of the painting-collective is "There's [a list of visible paintings]."

We could if we wanted tweak the description to be different in style in different rooms of the gallery, but this will do for now. Next we need to make it possible to type something like EXAMINE PAINTINGS, which normally wouldn't work because the Standard Rules don't tell Inform to recognise multiple objects with the EXAMINE command (unlike, say, DROP or TAKE). This is easy:

Understand "examine [things]" as examining.

Now to make use of the special object. If the player types EXAMINE PAINTINGS, the multiple object list will become a list of the visible paintings. The following rule looks at this list: if it contains more than one painting, it replaces them with the painting-collective instead. Now there's only one examining action, so we get a reply like "There's an abstract painting, a pointilist painting and a French academic painting." instead of a list of descriptions of each in turn.

A multiple action processing rule when the current action is examining (this is the examine kinds rule):
    let L be the multiple object list;
    let F be L;
    let the painting count be 0;
    repeat with item running through L:
        if the item is a painting:
            increment the painting count;
            remove the item from F;
    if the painting count is greater than one:
        add the painting-collective to F;
        alter the multiple object list to F.

And now some art to try this out on:

Gallery is a room. "Various paintings hang on the walls of this gallery, awaiting critical attention. A side chamber to the north contains smaller works."

The abstract painting, the pointilist painting, and the French academic painting are paintings in the Gallery.

North of the Gallery is the Side Chamber. A handsome miniature is a painting in the Side Chamber. The description of the handsome miniature is "The miniature depicts a uniformed soldier of the late 18th century, with braid on his shoulders and a curl in his beard."

The player carries a small notebook. The description of the notebook is "It contains the notes you've taken so far towards a paper for Western Art History 305. So far you're still feeling a bit uninspired."

Test me with "x paintings / x all / n / x paintings / x all".

328. The Best Till Last ★★

If a single command asks to do many things, some dull and some exciting, we may want to save the good ones for the end.

paste.png "The Best Till Last"

The Funky Ignition Lounge is a room. "This is where all evenings end." The stick of gelignite, the solid magnesium footstool, the vetiver candle, and the vodka bottle are here.

The burn description of the vetiver candle is "It burns right down, expensively but gothically."

The player carries an inexpensive firework. The description of the firework is "It is a cardboard tube with red and green stripes along the outside, and a fuse sticking out of the end." The burn description of the firework is "It ignites gloriously! You take a few hasty steps back in order to avoid burning yourself, and not a moment too soon. Red and green sparks fly out of the tube, and there's a whistling noise punctuated by several loud cracks."

The player carries a lighter. The description of the lighter is "You don't smoke, but you like to have access to flame now and then anyway."

Burning it with is an action applying to one thing and one carried thing.

Understand "burn [things] with [something preferably held]" as burning it with.

The block burning rule is not listed in any rulebook.

A thing has some text called the burn description.

Check burning something:
    if the player carries the lighter:
        try burning the noun with the lighter;
    else:
        try burning the noun with the noun.

Check burning something with something when the second noun is not the lighter:
    say "Your trusty lighter is the best flame source available to you." instead.

Check burning something with something:
    if the burn description of the noun is "":
        say "Best not." instead.

Carry out burning something with something:
    remove the noun from play.

Report burning something with something:
    say "[burn description of the noun][line break]".

A multiple action processing rule when the action name part of the current action is the burning it with action (this is the orderly burn rule):
    let L be the multiple object list;
    let dull list be a list of objects;
    let fun list be a list of objects;
    repeat with item running through L:
        if the burn description of the item is "":
            add item to dull list;
        else:
            add item to fun list;
    let F be the dull list;
    add fun list to F;
    alter the multiple object list to F.

Test me with "burn all with lighter".

411. Escape from the Seraglio ★★

paste.png "Escape from the Seraglio"

Section 1 - Special Announcement Rules

The number of takes this turn is a number that varies. Every turn: now the number of takes this turn is 0.

The friskily announce items from multiple object lists rule is listed instead of the announce items from multiple object lists rule in the action-processing rules.

This is the friskily announce items from multiple object lists rule:
    if taking:
        if the current item from the multiple object list is not nothing:
            increment the number of takes this turn;
            say "[if number of takes this turn is 1]First [otherwise if the number of takes this turn is 2]And then [otherwise if the number of takes this turn is 3]And I suppose also [otherwise if the number of takes this turn is 7]And on we wearily go with [otherwise if the number of takes this turn is 9]Oh, and not forgetting [otherwise]And [end if][the current item from the multiple object list]: [run paragraph on]";
    otherwise:
        if the current item from the multiple object list is not nothing, say "[current item from the multiple object list]: [run paragraph on]".

Rule for deciding whether all includes the person asked: it does not.
Rule for deciding whether all includes a person when taking: it does not.

Section 2 - The Scenario

The Palm Chamber is a room. Sarissa is a woman in the Palm Chamber.

The Palm Chamber contains a bottle of ink, a quill pen, a tangerine, a bunch of grapes, a length of silken rope, some perfume, a cake of incense, a fitted leather bodice, a sapphire anklet, an illustrated novel, a whip, and a heavy iron key.

A persuasion rule for asking Sarissa to try taking the key:
    say "Sarissa nervously demurs, knowing that it is forbidden.";
    persuasion fails.

A persuasion rule: persuasion succeeds.

Test me with "take all / drop all / sarissa, take all".

428. Formicidae ★★

Suppose we have an item that produces an interesting result the first time the player lifts it -- a rock with dangerous ants revealed underneath. The effect of the surprise is a little weakened, though, if the player sees that response as the result of a TAKE ALL, when it might be printed like this:

>[3] get all
tent peg: Taken.
water flask: Taken.
trading permit: Taken.
innocent-looking rock: You reach for the rock and turn it over to reveal a thriving colony of flesh-eating ants. Needless to say, you drop the rock and jump back with a decidedly effeminate scream. They can probably hear you all the way back in the base camp.
rusty nail: Taken.

[Your score has just gone down by two points.]

The calm response to "rusty nail" looks odd now, and the score change is disconnected from the event that caused it.

To manage this, we might institute a system so that interesting objects are handled last in their list, like so:

paste.png "Formicidae"

Use scoring.

Section 1 - Procedure

The magic rule is listed before the generate action rule in the turn sequence rules.

A thing has a number called dramatic potential.

This is the magic rule:
    let L be the multiple object list;
    if the number of entries in L is greater than 1:
        sort L in dramatic potential order;
        alter the multiple object list to L.

Section 2 - Scenario

The Foothills is a room. "The land has become hilly; though the soil is still mostly coarse yellow sand, clumps of grass are able to grow in the shadier places. Deep wagon ruts running from the southwest towards the mountains in the northeast show where generations of caravans have already passed."

The water flask, the tent peg, and the trading permit are things in Foothills.

The rock is a thing in Foothills. Before printing the name of the rock when the rock is not handled: say "innocent-looking ". The dramatic potential of the rock is 10.

The rusty nail is a thing in Foothills.

The ant colony is a fixed in place thing. "A busy group of ants are crawling to and fro in the unaccustomed sun." Rule for deciding whether all includes the ant colony while taking: it does not.

Instead of taking the rock when the rock is handled:
    say "It might still have a stray ant or two on it."

After taking the rock:
    now the rock is handled;
    move ant colony to the location;
    move the rock to the location;
    say "You reach for the rock and turn it over to reveal a thriving colony of flesh-eating ants. Needless to say, you drop the rock and jump back with a decidedly effeminate scream. They can probably hear you all the way back in the base camp.";
    decrease score by 2.

Test me with "get peg / drop peg / get all / get rock".

Note that while one could also manipulate the object list to add or remove items at this stage, there's a simpler way to control what Inform considers "ALL" to mean in commands: see the activity "Deciding whether all includes" in the activities chapter.

431. The Facts Were These ★★

Occasionally it happens that we want to process an action on multiple items differently than we would if the player had just typed each of the individual actions separately. In this example, the reason is that we can only successfully GIVE items when their combined value passes a certain threshold amount; otherwise the recipient will reject them.

This works as an implementation of money, if we give value only to cash objects (though several other implementations of cash are available, most of which are simpler and more efficient). We could also imagine a mechanic like this being used for a bargaining or auction game as well, given a society that deals in objects rather than credits.

In order to consider all the items in the gift at once, we create an action that applies to multiple objects, but will in fact test the whole object collection during the first pass and print a definitive answer to whether the action succeeded. All subsequent times the game consults the rulebook will be stopped at the very beginning. No further processing will occur or output be printed.

paste.png "The Facts Were These"

Section 1 - Procedure

We start by creating the idea that everything in the game has a monetary value:

A price is a kind of value. $10 specifies a price. A thing has a price.

Understand "give [things preferably held] to [someone]" as multiply-giving it to. Understand "give [things] to [someone]" as multiply-giving it to. Multiply-giving it to is an action applying to two things.

A subtlety here: we say "things preferably held" to prefer items that the player is holding (so if the player has two dollars in hand and a third lies on the ground, he will use just the two he has).

The second grammar line allows Inform to match things that aren't held if it can't make up the list from things that are. If all three dollars are on the ground, the player can pick them up before spending them.

We do not, however, make multiply-giving apply to a "carried" item, because that will generate implicit takes of those items in a way that will mess up our action reporting. Instead, we're going to build the implicit takes into the system in a different way, one that permits us to collate the reports more attractively and print a short, one-sentence list of anything that the player had to pick up.

A thing can be given or ungiven. A thing is usually ungiven.

This is for record-keeping purposes so that we can print an attractive list of what was given at the end of the turn.

First check multiply-giving it to:
    if already gave at the office is true:
        stop the action.

Already gave at the office is a truth state that varies.

"Already gave at the office" is the perhaps-excessively-named flag that keeps track of whether we've already done this action once.

Check multiply-giving something to the player:
        now already gave at the office is true;
        say "You can hardly bribe yourself.[paragraph break]" instead;

The following rule is longish because it processes the entire list at once, generating implicit takes if necessary (but processing those implicit takes silently according to its own special rule, so that the output can be managed attractively). We are also, at the same time, calculating the total value of the player's offer.

Check multiply-giving it to:
    let L be the multiple object list;
    let bribe-price be $0;
    repeat with item running through L:
        if the player does not carry the item:
            abide by the ungivability rules for the item;
            carry out the implicitly taking activity with the item;
            if the player does not carry the item:
                now already gave at the office is true;
                say "You can't include [the item] in your bribe, since you're not holding [them]![paragraph break]" instead;
        increase bribe-price by the price of item;
    if the number of entries in the recently-collected list is greater than 0:
        repeat with item running through the recently-collected list:
            now item is marked for listing;
        say "You pick up [the list of marked for listing things] and make your offer. [run paragraph on]";
        now everything is unmarked for listing;
    if the bribe-price is less than the price of the second noun:
        now already gave at the office is true;
        say "[The second noun] angrily rejects your piffling bribe.[paragraph break]" instead.

The bit about making some items "marked for listing", above, rather than printing the list directly, is that using the "[the list of....]" syntax guarantees that Inform will respect grouping rules in writing its description. For instance, if the player has automatically taken all three dollars, the output will say "the three dollars" instead of "the dollar, the dollar, and the dollar."

Carry out multiply-giving it to:
    let L be the multiple object list;
    repeat with item running through L:
        now the second noun carries the item;
        now the item is given;
    now already gave at the office is true;

Report multiply-giving it to:
    say "[The second noun] rather shamefacedly tucks [the list of given things] away into a pocket.[paragraph break]".

Now we create our own variation of implicitly taking in order to customize the output for the multiply-giving action. The "ungivability rules" should disallow any object that the player absolutely cannot take, because we want "carry out the implicitly taking activity" to succeed every time -- and therefore not print out any less-attractive results from implicit takes that don't succeed. Otherwise, the player's GIVE TREE AND DOG TO ATTENDANT might produce the reply "That's fixed in place" -- without specifying which object is fixed in place.

Because of the way this works, we will want to be careful: if we have any "instead of taking..." rules for special objects in the game, we should be sure to mirror those with an ungivability rule to print something more suitable in the case that the player tries taking that object as part of the multiple giving action.

The ungivability rules are an object-based rulebook.

An ungivability rule for a person:
    now already gave at the office is true;
    say "Slavery is illegal.[paragraph break]" instead.

An ungivability rule for something (called the item) which is enclosed by someone who is not the player:
    now already gave at the office is true;
    say "[The item] [aren't] yours to give.[paragraph break]" instead.

An ungivability rule for something which encloses the player:
    now already gave at the office is true;
    say "You don't want to end up as part of the gift.[paragraph break]" instead;

An ungivability rule for something (called the item) which is part of something:
    now already gave at the office is true;
    say "[The item] [are] attached to [a random thing which incorporates the item][paragraph break]" instead.

An ungivability rule for something (called the item) which is scenery:
    now already gave at the office is true;
    say "[The item] [are] unremovable.[paragraph break]" instead.

An ungivability rule for something (called the item) which is fixed in place:
    now already gave at the office is true;
    say "[The item] [are] fixed in place.[paragraph break]" instead.

An ungivability rule for a direction (called the item):
    now already gave at the office is true;
    say "[The item] [are] not susceptible to giving.[paragraph break]" instead.

Rule for implicitly taking something (called target) while multiply-giving:
    silently try taking the target;
    if the player carries the target:
        add the target to the recently-collected list.

The recently-collected list is a list of objects that varies.

And since we don't want to list the individual objects separately:

The selectively announce items from multiple object lists rule is listed instead of the announce items from multiple object lists rule in the action-processing rules.

This is the selectively announce items from multiple object lists rule:
    if multiply-giving:
        do nothing;
    otherwise:
        if the current item from the multiple object list is not nothing:
            say "[current item from the multiple object list]: [run paragraph on]".

And now, since this ought to work symmetrically if the player provides just one high-value item:

Check giving something to someone:
    if the price of the noun is less than the price of the second noun:
        say "[The second noun] angrily rejects your piffling bribe." instead.

As we've seen elsewhere, the giving action by default returns a refusal, but is also written to start working if we remove the blockage. So we do that here, and revise the report rule to match the report rule we have for multiple giving.

The block giving rule is not listed in any rulebook.

The new report giving rule is listed instead of the standard report giving rule in the report giving it to rules.

This is the new report giving rule:
    say "[The second noun] rather shamefacedly tucks [the noun] away into a pocket."

After each instance of the multiply-giving action, we need to clear the variables we used to track its state. We could do this in "Before reading a command", but that's unsafe because the player might type GIVE PIE AND CAP TO ATTENDANT. GIVE DOLLARS TO ATTENDANT. all on a single line, and we would like to be able to clear the variables between one action and the next. The correct place to attach this behavior is immediately before the generate action rule, thus:

The before-generation rule is listed before the generate action rule in the turn sequence rules.

This is the before-generation rule:
    now every thing is ungiven;
    now already gave at the office is false;
    truncate the recently-collected list to 0 entries.

Section 2 - Scenario

The Morgue Office is a room. "This is not the Morgue itself; this is only its outer office. The familiar room full of silver drawers and cold air lies beyond."

The Morgue Attendant is a man in the Morgue Office. "The Attendant has seen you come through a number of times, and is becoming suspicious of your abiding interest in dead people." The description is "The Morgue Attendant is fifty-four years, six months, five days, and three minutes old." The price of the Morgue Attendant is $3.

A dollar is a kind of thing. The player carries three dollars. The price of a dollar is always $1.

The player carries a miniature rhubarb pie. The price of the miniature rhubarb pie is $5.

The player carries a knitted cap. The price of the knitted cap is $2.

Test me with "test dollars / purloin three dollars / test multi-line / purloin three dollars / purloin pie / purloin cap / test specificity / purloin three dollars / test largesse / test mixed-gift".

Test multi-line with "give dollar and pie to attendant. give dollars and cap to attendant".

Test dollars with "drop all / give dollar to Morgue Attendant / give dollars to Morgue Attendant / get dollars / give dollars to morgue attendant / purloin three dollars / drop dollars / give dollars to Morgue Attendant".

Test specificity with "give three dollars to Morgue Attendant".

Test largesse with "give pie to Morgue Attendant".

Test mixed-gift with "give dollar and cap to Morgue Attendant / get cap / give dollar and cap to morgue attendant / give me and dollar to attendant".

PURLOIN, used in the tests here, is a special debugging command that allows the player to acquire objects that wouldn't otherwise be possible to take. It is only active in non-release versions of the story. For more about debugging commands, see the chapter on Testing and Debugging.

RB §6.16. Alternate Default Messages

Often we will want to replace the text produced by Inform by default: this includes quite a wide range of text, much of which either describes the success of a command or explains why the action failed.

Inform provides the Responses system to enable default messages like "You can't go that way" to be changed, and this is capable of making large-scale changes. This is especially useful if we want to give the viewpoint character a distinctive voice and set of mannerisms.

RB §6.17. Clarification and Correction

Some commands and some objects raise special challenges when it comes to working out the player's intention.

Sometimes this can be done with good rules about the assumptions Inform should make. Alpaca Farm demonstrates a USE command, always a challenge because USE can mean very different actions with different items.

There are also times when we need to ask the player for more information. Apples demonstrates how sensibly to use properties to disambiguate between similar objects, while Walls and Noses ★★★ rephrases the disambiguation question when special objects are involved: examining one of the walls of the room will make the story ask "In which direction?" and EXAMINE NOSE will lead to "Whose nose do you mean, Frederica's, Betty's, Wilma's or your own?"

At other times, the player types something that is wrong in a predictable way: for instance, we might want to remove all the "with..." phrases from commands like

HIT DOOR WITH FIST
KICK DRAGON WITH FOOT
LOOK WEST WITH EYES

and merely parse the remainder of the command. (That last command may be unlikely, but novice players do quite often type commands that refer unnecessarily to body parts.) Cave-troll ★★★ demonstrates how.

WXPQ demonstrates how to modify the error message the parser gives in response to a command it doesn't understand; this particular example focuses on the "That noun doesn't make sense in this context" message that arises from using the "[any thing]" or "[any room]" tokens, but the techniques could be adapted to handling other parser errors as well.

For catching typing errors, Cedric Knight's extension Mistype may also be of use: it provides an automatic typo-correction function that the player can turn on or off.

Examples

290. Alpaca Farm

This example takes the ordering of grammar lines to its logical extreme, sorting the player's input into different categories depending on the kind and condition of the objects mentioned.

paste.png "Alpaca Farm"

Understand "use [an edible thing]" as eating.

Understand "use [a wearable thing]" as wearing.

Understand "use [a closed openable container]" as opening. Understand "use [an open openable container]" as closing.

Understand "use [something preferably held] on [a locked lockable thing]" as unlocking it with (with nouns reversed). Understand "use [something preferably held] on [an unlocked lockable thing]" as locking it with (with nouns reversed).

Understand "use [a switched off device]" as switching on.

Understand "use [something]" as using. Using is an action applying to one thing. Carry out using: say "You will have to be more specific about your intentions."

Understand "use [a door]" as opening. Understand "use [an open door]" as entering.

The Llama Pen is a room. North of the Pen is the gate. The gate is a door. North of the gate is the Rocky Path. The brown llama is an animal in the Llama Pen.

Appearance is a kind of value. The appearances are muddy, scruffy, fluffy, and dapper. The brown llama has an appearance. The brown llama is muddy. Before printing the name of the brown llama, say "[appearance] ". Before printing the name of the brown llama while grooming: say "now-[if appearance of the brown llama is less than dapper]merely-[end if]".

A grooming tool is a kind of thing. Understand "use [a grooming tool] on [something]" as grooming it with (with nouns reversed). Grooming it with is an action applying to two things. Understand "groom [something] with [something]" as grooming it with.

Carry out grooming it with:
    if the appearance of the noun is less than dapper, now the appearance of the noun is the appearance after the appearance of the noun.

Report grooming it with:
    say "You attend diligently to the appearance and hygiene of [the noun]."

Instead of using a grooming tool in the presence of the brown llama:
    try grooming the brown llama with the noun.

The player carries some nail nippers, a slicker brush, and an apple. The apple is edible. The brush and the nippers are grooming tools. The player wears a sombrero.

The description of the nail nippers is "Ten inches long, to give you the necessary leverage to cut tough llama toenails. It still helps to soften them up by making the llama stand in a bucket of water first, though."

The description of the slicker brush is "Fine, angled soft bristles set into a broad back, perfect for removing mud from the coat of a long-woolled llama."

The industrial-strength blower is a fixed in place device in the Llama Pen. "Attached to the nearest wall, on its own movable boom, is an industrial-strength blower for doing llama hair."

Understand "use [switched off blower]" as switching on. Understand "use [switched on blower] on [brown llama]" as grooming it with (with nouns reversed). Instead of using the blower in the presence of the brown llama, try grooming the brown llama with the blower.

Test me with "use gate / use blower / use nippers / use brush / use apple / remove sombrero / use sombrero".

Whether we actually want a USE action is a subject of some theoretical debate in the IF community. On the one hand, it helps avoid guess-the-verb problems where the player cannot figure out what term to use in order to express a fairly simple idea. On the other, it encourages the player to think that all items have one and exactly one use, rather than getting him to consider the range of possibilities that arise from having a complex vocabulary.

369. Apples

Inform by default detects whether two objects can be disambiguated by any vocabulary available to the player. If so, it asks a question; if not, it picks one of the identical objects at random.

Generally this produces good behavior. Occasionally, though, two objects have some distinguishing characteristic that doesn't appear in the object name. For instance, suppose we've created a class of apples that can be told apart depending on whether they've been bitten or not:

An apple is a kind of thing. Consumption is a kind of value. The consumptions are pristine and bitten. An apple has a consumption. The description of an apple is "It is [consumption]."

Understand the consumption property as describing an apple.

The player can meaningfully type

>EAT BITTEN APPLE

or

>EAT PRISTINE APPLE

but if he types

>EAT APPLE

Inform will, annoyingly, ask

Which do you mean, an apple or the apple?

This gives the player no indication of why Inform is making a distinction. So here we add a special "printing the name" rule to get around that situation:

paste.png "Apples"

Orchard is a room.

An apple is a kind of thing. Consumption is a kind of value. The consumptions are pristine and bitten. An apple has a consumption. The description of an apple is "It is [consumption]."

Understand the consumption property as describing an apple.

Before printing the name of an apple while asking which do you mean: say "[consumption] ". Before printing the plural name of an apple while asking which do you mean: say "[consumption] ".

The player carries three apples.

Instead of eating a pristine apple (called the fruit):
    say "You take a satisfying bite.";
    now the fruit is bitten.

Instead of eating a bitten apple (called the fruit):
    say "You consume the apple entirely.";
    now the fruit is nowhere.

Inform will also separate the bitten from the pristine apples in inventory listings and room descriptions, even though it's not clear why; we can improve on that behavior thus:

Before listing contents: group apples together.

Rule for grouping together an apple (called target):
    let source be the holder of the target;
    say "[number of apples held by the source in words] apple[s], some bitten".

Before printing the plural name of an apple (called target):
    let source be the holder of the target;
    if every apple held by the source is bitten, say "bitten ";
    if every apple held by the source is pristine, say "pristine ".

Test me with "i / eat apple / i / eat apple / pristine / i / eat apple / pristine / i".

380. WXPQ

The parser error "That noun did not make sense in this context" arises instead of "You can't see any such thing" when the player uses a command that could apply to any item in the game -- that is, a command such as

Understand "go to [any room]" as going directly to.
Understand "talk about [any subject]" as discussing.

...and so on. The idea here is that "You can't see any such thing" isn't a sensible rejoinder when the player doesn't really need to be able to see the object.

Nonetheless, "That noun did not make sense..." is itself a fairly dry and uninformative response, and we may want to override it to something more appropriate for the specific kind of context in which it might appear. For instance:

paste.png "WXPQ"

WXPQ Studio is a room. "After about 2 AM, no one is listening anyway, so you can more or less make up whatever you like to fill the airwaves."

John F Kennedy, Elvis, Ralph Nader, Tony Blair, and single-origin chocolate are things.

Understand "talk about [any thing]" or "discuss [any thing]" as discussing. Discussing is an action applying to one visible thing.

Carry out discussing:
    say "You babble for a while about your [one of]interest in[or]hatred of[or]passionate devotion to[or]conspiracy theory concerning[or]mother's secret love affair with[as decreasingly likely outcomes] [the noun]."

Rule for printing a parser error when the latest parser error is the noun did not make sense in that context error:
    say "For once, you're at a loss for anything to say."

Test me with "discuss Elvis / discuss Kennedy / discuss chocolate / discuss narratology vs ludology debate".

Note that this solution works as simply as it does because we only have one command in the game that can apply to an "[any]" token. If we had several, we'd need to distinguish between the parser error attached to "discuss" and the parser error attached to "go to" (for instance). In that case, we might instead write something like

Rule for printing a parser error when the latest parser error is the noun did not make sense in that context error:
if the player's command includes "go":
    say "There's no such place you know how to get to.";
otherwise:
    say "For once, you're at a loss for anything to say."

370. Walls and Noses ★★★

Suppose we want our game to respond to "EXAMINE WALL" with "In which direction?", and to "EXAMINE NOSE" with "Whose nose do you mean, Frederica's, Betty's, Wilma's or your own?"

For the case of EXAMINE WALL, we need a way to determine whether every item being disambiguated is a direction. We'll start by making a "matched" adjective which will identify items being disambiguated:

paste.png "Walls and Noses"

Eight-Walled Chamber is a room. "A perfectly octagonal room whose walls are tinted in various hues."

Understand "wall" as a direction.

Definition: a direction is matched if it fits the parse list.
Definition: a room is matched if it fits the parse list.
Definition: a thing is matched if it fits the parse list.

Rule for asking which do you mean when everything matched is direction:
    say "In which direction?"

Checking the parse list requires a bit of behind-the-scenes work with Inform 6. Fortunately, you don't have to understand this entirely in order to use the rest of the example:

To decide whether (N - an object) fits the parse list:
    (- (FindInParseList({N})) -)

Include (-
[ FindInParseList obj i k marker;
    marker = 0;
    for (i=1 : i<=number_of_classes : i++) {
    while (((match_classes-->marker) ~= i) && ((match_classes-->marker) ~= -i)) marker++;
    k = match_list-->marker;
    if (k==obj) rtrue;
    }
    rfalse;
];
-)

Now that we've defined our "matched" adjective, we can use it for other purposes as well -- even generating our own lists. Our second challenge was to respond to EXAMINE NOSE with "Whose nose do you mean, Frederica's, Betty's, Wilma's or your own?"

Here we need to change the way the question is worded (not "which do you mean" but "whose nose do you mean"). We also have to the names of the noses as they're printed in this particular context, so that they don't repeat the word "nose" over and over. And -- as a point of good English style -- we also want "your own" nose always to be last on the list.

For this purpose we may want to use the built-in "Complex Listing" extension, which allows us to print specially ordered lists. So:

Include Complex Listing by Emily Short.

Wilma, Betty, and Frederica are women in the Eight-Walled Chamber. Understand "lady" or "woman" as a woman. A nose is a kind of thing. A nose is part of every person.

Rule for asking which do you mean when everything matched is a nose:
    prepare a list of matched things;
    if your nose is an output listed in the Table of Scored Listing:
        choose row with an output of your nose in the Table of Scored Listing;
        now the assigned score entry is -1;
    say "Whose nose do you mean, [the prepared list delimited in disjunctive style]?"

Rule for printing the name of a nose (called target) while asking which do you mean :
    if everything matched is a nose:
        if the target is part of a person (called owner):
            if the owner is the player, say "your own";
            otherwise say "[the owner][apostrophe]s";
    otherwise:
        make no decision.

Understand "own" or "mine" as your nose.

Test me with "x wall / north / x nose / mine".

424. Cave-troll ★★★

Novice players of interactive fiction, unfamiliar with its conventions, will often try to add extra phrases to a command that the game cannot properly parse: HIT DOOR WITH FIST, for instance, instead of HIT DOOR.

While we can deal with some of these instances by expanding our range of actions, at some point it becomes impossible to account for all the possible prepositional phrases that the player might want to tack on. So what do we do if we want to handle those appended bits of text sensibly?

We could go through and remove any piece of text containing "with ..." from the end of a player's command; the problem with that is that it overzealously lops off the ends of valid commands like UNLOCK DOOR WITH KEY, as well. So clearly we don't want to do this as part of the "After reading a command..." stage.

A better time to cut off the offending text is right before issuing a parser error. At that point, Inform has already determined that it definitely cannot parse the instruction as given, so we know that there's something wrong with it.

The next problem, though, is that after we've edited the player's text we want to feed the corrected version back to Inform and try once more to interpret it.

This is where we have a valid reason to write a new "rule for reading a command". We will tell Inform that when we have just corrected the player's input to something new, it should not ask for a new command (by printing a prompt and waiting for another line of input); it should instead paste our stored corrected command back into "the player's command" and proceed as though that new text had just been typed.

Thanks to John Clemens for the specifics of the implementation.

paste.png "Cave-troll" by JDC

Section 1 - The Mechanism

The last command is a text that varies.

The parser error flag is a truth state that varies. The parser error flag is false.

Rule for printing a parser error when the latest parser error is the only understood as far as error and the player's command matches the text "with":
    now the last command is the player's command;
    now the parser error flag is true;
    let n be "[the player's command]";
    replace the regular expression ".* with (.*)" in n with "with \1";
    say "(ignoring the unnecessary words '[n]')[line break]";
    replace the regular expression "with .*" in the last command with "".

Rule for reading a command when the parser error flag is true:
    now the parser error flag is false;
    change the text of the player's command to the last command.

Section 2 - The Scenario

The Cave is a room.

The troll is a man in the cave.

The player carries a sword.

The chest is a locked lockable container in the cave.

Test me with "attack troll with sword / unlock chest with sword / attack troll as a test".

A caveat about using this method in a larger game: "parser error flag" will not automatically control the behavior of any rules we might have written for Before reading a command... or After reading a command..., so they may now fire at inappropriate times. It is a good idea to check for parser error flag in those rules as well.

RB §6.18. Alternatives To Standard Parsing

Very occasionally, for out-of-the-ordinary games, we want to make major changes to the way that Inform ordinarily understands commands.

Cloves ★★ shows how we might read adverbs in the player's command: adverbs are challenging because they can legitimately appear anywhere in a command structure, so must be found and accounted for before the rest of the command is understood.

Fragment of a Greek Tragedy ★★ goes further, substituting a keyword-recognition parser for the usual structure of commands and objects.

Less drastically, menus of numbered options can temporarily replace or augment standard commands. Down in Oodville ★★ demonstrates how to add a list of transporter destinations from which the player may choose by numeral.

See also

Traits Determined By the Player for ways to ask the player a question at the beginning of play
Saying Simple Things for a way to ask the player a yes-no question any time during play

Examples

304. Down in Oodville ★★

Now and then in IF there is a situation where we need to ask the player for a numbered choice rather than an ordinary action command. What's more, that numbered choice might change during the game, so we don't want to just hard-wire the meanings of "1", "2", and "3" whenever the player types them.

A better trick is to keep a list or table (we'll use a table here because it involves slightly less overhead) recording what the player's numerical choices currently mean. Then every time the player selects a number, the table is consulted, and if the number corresponds to something, the player's choice is acted on.

In our example, we'll have a transporter pad that can take the player to any room in the game that he's already visited. (Just for the sake of example, we'll start him off with a few pre-visited rooms.)

paste.png "Down in Oodville"

Section 1 - Method

Understand "[number]" as selecting.

Selecting is an action applying to one number.

Check selecting: [assuming we don't want to be able to transport from just anywhere]
    if the player is not on the transporter pad:
        say "You can transport only from the transporter pad. From other places than the transporter room, you can HOME to your base ship, but not leap sideways to other locations.";
        empty the transport options instead.

Check selecting:
    if the number understood is greater than the number of filled rows in the Table of Transport Options or the number understood is less than one:
        say "[The number understood] is not a valid option. ";
        list the transport options instead.

Carry out selecting:
    let N be the number understood; [not actually a necessary step, but it makes the next line easier to understand]
    choose row N in the Table of Transport Options;
    if the transport entry is a room:
        move the player to the transport entry;
    otherwise:
        say "*** BUG: Improperly filled table of transport options ***" [It should not be possible for this to occur, but we add an error message for it so that, if it ever does, we will know what is causing the programming error in our code]

To list the transport options:
    let N be 1;
    say "From here you could choose to go to: [line break]";
    repeat through the Table of Transport Options:
        say " [N]: [transport entry][line break]";
        increment N.

To empty the transport options:
    repeat through the Table of Transport Options:
        blank out the whole row; [first we empty the table]

To load the transport options:
    repeat with interesting room running through visited rooms which are not the Transporter Room:
        choose a blank row in the Table of Transport Options;
        now the transport entry is the interesting room.

Table of Transport Options
transport
an object
with 3 blank rows. [In the current scenario, the number of blank rows need never be greater than the number of rooms in the game, minus the transport room itself.]

Understand "home" as homing. Homing is an action applying to nothing.

Check homing:
    if the player is in the Transporter Room:
        say "You're already here!" instead.

Carry out homing:
    move the player to the transporter room.

Section 2 - Scenario

The Transporter Room is a room.

Oodville is a visited room.

Midnight is a visited room. The Diamond City is west of Midnight.

The transporter pad is an enterable supporter in the Transporter Room. "The transporter pad in the middle of the floor is currently dull blue: powered but unoccupied."

After entering the transporter pad:
    say "The transporter beeps and glows amber as you step onto its surface. A moment later a hologram displays your options. [run paragraph on]";
    empty the transport options;
    load the transport options;
    list the transport options.

Test me with "get on pad / 0 / -1 / 8 / 2 / look / w / home / get on pad / get off pad / 3".

If we wanted to replace the regular command structure entirely with numbered menus, or use menus to hold conversation options, we could: several Inform extensions provide these functions.

373. Cloves ★★

It has sometimes been suggested that IF should allow for the player to use adverbs, so that doing something "carefully" will have a different effect from doing it "quickly". There are several inherent challenges here: it's a good idea to make very sure the player knows all his adverb options, and the list of possibilities should probably not be too long.

Another trick is that adverbs complicate understanding commands, because they can occur anywhere: one might type >GO WEST CAREFULLY or >CAREFULLY GO WEST, and ideally the game should understand both. After reading a command is the best point to do this sort of thing, because we can find adverbs, interpret them, and remove them from the command stream. So:

paste.png "Cloves"

Manner is a kind of value. The manners are insouciantly, sheepishly, and defiantly.

Now we have, automatically, a value called manner understood to be used whenever parsing manners, and we can use this even during the "after reading a command" stage, so:

After reading a command:
    if the player's command includes "[manner]":
        cut the matched text;
    otherwise:
        say "But how, my dear boy, how? You simply can't do something without a pose. Thus far you have mastered doing things [list of manners].";
        reject the player's command.

When play begins:
    now the left hand status line is "Behaving [manner understood]";
    now the right hand status line is "[location]";
    now the manner understood is insouciantly.

The Poseur Club is a room. "Lady Mary is laid out on a sofa, her wrists bandaged importantly[if the manner understood is insouciantly] -- and she looks all the more depressed by your indifference to her state[end if]; Salvatore is at the gaming table, clutching his hair with both hands[if the manner understood is defiantly] -- though he looks up long enough to snarl in response to that expression of yours[end if]; Frackenbush is muttering lines from another of his works in progress, as though poetry has nearly made him mad[if the manner understood is sheepishly]. But he spares you a reassuring smile. He's not a bad fellow, Frackenbush[end if].

The usual people, in short."

Instead of doing something other than waiting or looking:
    say "Dear. No. That would smack of effort."

Instead of waiting when the manner understood is sheepishly:
    say "You scuff your foot against the ground for a moment, and allow a seemly blush to creep over your cheek. It's quite effective, you are sure, though you can't look up and see how it is going."

Instead of waiting when the manner understood is insouciantly:
    say "Thrusting your hands into your pockets, you whistle a jaunty tune.

'Do shut up,' says a Melancholy Poseur from over by the window."

Instead of waiting when the manner understood is defiantly:
    say "You raise your chin and give a pointed glance around the room as though to say that you are waiting for someone; you are unembarrassed about waiting for her; you have by no means been stood up; and the first person to comment will receive a poke in the eye."

Before looking when the manner understood is sheepishly:
    say "You gaze up from under your brows..."

Before looking when the manner understood is defiantly:
    say "You cast a withering gaze over the room."

Before looking when the manner understood is insouciantly:
    if turn count > 1,
        say "You turn an eye to your surroundings, looking faintly-- just faintly-- amused."

Test me with "wait / wait insouciantly / sheepishly look / defiantly look / look insouciantly".

The qualification about turn count is to prevent this before message from occurring when the player first looks around the room (automatically) at the start of play.

Note that to test this example, one must type INSOUCIANTLY TEST ME, and not simply TEST ME: a poseur's work is never done.

375. Fragment of a Greek Tragedy ★★

Apologies to the shade of A. E. Housman.

paste.png "Fragment of a Greek Tragedy"

Understand "restart/restore/save/quit" as "[meta-command]".

After reading a command:
    if the player's command matches "[meta-command]", make no decision;
    say line break;
    repeat through Table of Current Topics:
        if the player's command includes topic entry:
            say "CHORUS: [reply entry][paragraph break]";
            follow the advance time rule;
            rule succeeds;
    say "[italic type] Pause.[roman type][line break]";
    follow the advance time rule;
    rule succeeds.

Table of Current Topics

topic

reply

"journey/trip/travel/came/arrived"

"Sailing on horseback, or with feet for oars?"

"horseback/legs/feet/oars"

"Beneath a shining or a rainy Zeus?"

"shining/rainy/weather/zeus"

"Mud's sister, not herself, adorns thy boots."

This would be a bit bare if we didn't provide the player with some sort of context at the outset, so let's put some remarks before the first command prompt:

Before reading a command while the turn count is 1:
    say "CHORUS: O suitably-attired-in-leather-boots
    Head of a traveller, wherefore seeking whom
    Whence by what way how purposed art thou come
    To this well-nightingaled vicinity?
    My object in inquiring is to know.
    But if you happen to be deaf and dumb
    And do not understand a word I say,
    Then wave your hand, to signify as much."

This "turn count" condition is why it was useful to follow the advance time rule in "after reading a command": the game (or drama, if you like) will continue to count moves elapsed even though the rest of Inform's command parsing and world model is being ignored. In a longer and more ambitious implementation of this idea, we might want to allow scenes to govern the behavior and responses of the Chorus.

And then to give the whole exchange a play's format:

The Stage is a room.

The room description heading rule is not listed in the carry out looking rules.

When play begins:
    now the command prompt is "YOU: ";
    now left hand status line is "Fragment of a Greek Tragedy";
    now right hand status line is "A. E. Housman".

(Because this example manipulates commands outside of the normal parser, the mechanism for TEST will not work here. Try typing commands such as: TELL CHORUS ABOUT JOURNEY / TELL CHORUS ABOUT FEET / TELL CHORUS ABOUT SHROPSHIRE / TELL CHORUS ABOUT ZEUS)