en:gamedev:documentation
Keywords: en,gamedev,documentation

# Welcome to INSTEAD

The engine for INSTEAD is written in Lua 5.1 and 5.2, therefore knowing this language is useful, although completely unnecessary. In fact, it was the express intention of the creator that new designers should be able to take on interesting projects without any need for engine-level programming.

Throughout its evolution, the engine's capabilities have widened and allowed implementation of games in various genres including arcade games and highly complex text-parsing adventures. It's even possible to launch games written for other engines. However, the original intent was custom text-based adventures, and this remains the primary focus. This is what the present documentation describes, and strengthening these foundation skills is important even if you plan to write a genre-bending game in the future, you clever child. So let's start learning INSTEAD by writing a simple text adventure!

## Adventures In Text

Most people associate a text adventure with some text printed on the screen and a few pre-defined courses of action, for example:

    You see a table in front of you. There is an apple on it. What do you do?
    	1) Take the apple
    	2) Step away from the table

Some classic games have the player type her actions literally, like this:

    You are in the kitchen. There is a table near a window.
    	PLAYER TYPES> look at the table
    There is an apple on the table.

Both of these implementations have advantages as well as drawbacks. The first approach resembles what's known as the gamebook genre and doesn't suit classic text adventures where a hero could explore a virtual world, free to move and interact with in-world objects. The second approach gives us a more realistic model, but requires more effort from the game developer and her players, making accommodation for human language with complex grammar.

The INSTEAD game engine was intended for games which combine the advantages of both approaches, at the same time attempting to avoid their drawbacks. The game world in INSTEAD is modeled in a similar fashion to the second approach in that there are places (rooms) which the protagonist can visit, and objects (including NPC characters) she can interact with. The player explores the world and can manipulate objects freely. Acting upon objects might remind her of classical graphic quests from the 1990s, yet with a greater depth of features.

Before reading this manual it's recommended you play some INSTEAD games to get an idea how each concept contained herein is implemented. However, it must be noted many old games are written with less than optimal code using deprecated constructions, so studying their code is a treacherous endeavor for the fledgling game developer. Modern structure and syntax enables you to write more laconically, simply, and clearly, so go have fun with some games then return here to pick up best practices.

## Basic Anatomy

The game window displays text and images for the room the player is standing in.

The static elements of a room are shown only once, upon entering. Clicking on the room's title will recall them.

The dynamic elements of a room are defined by its objects, including character dialogues. These are always visible to the player, yet can change based on the player's actions.

The player's inventory is represented in a separate panel that contains interactive objects the player can access throughout the game.

Player actions in the game world include:

- looking around in a room to discover new objects
- unfolding the story as it appears
- interacting with a room's objects
- using inventory objects
- following passages to other rooms

## Where To Begin

A game should have its own primary directory within your system directory, with one `main.lua` script inside the top level. Other game resources should be placed in this directory as well, and can be organized in sub-directories. This includes Lua scripts, image files, sound files, and savegame files. All references in the code must be made relative to this top level directory.

To save yourself having to search for save files elsewhere, be sure to create a sub-directory named “saves”. Your saved games will automatically be stored here.

At the beginning of the `main.lua` file a header can be defined with information tags. Each tag should start with `– &` and end with a closing `$` symbol.

The `$Name` tag contains the game title, encoded in `UTF-8 without BOM!`, which will be displayed by the interpreter when the player opens the game:

    -- $Name: The most interesting game!$

It's also recommended to specify the development version of the game:

    -- $Version: 0.5$

As well as the author(s):

    -- $Author: Non Anonymous$

If you develop your game in Windows make sure your editor supports `UTF-8 encoding without BOM!` and use it to write the code.

Since `version 1.2.0` you must define the STEAD API version after the header. It's currently `version 1.9.1` as of this writing.

    instead_version "1.9.1"

Without this line STEAD API will operate in compatibility/legacy mode. The game engine has competent backwards compatibility, but by explicitly specifying a modern API version number it's possible to use features such as snapshots, autosaved global variables, on-the-fly functions, auto-formatting, feature modules, and so on. There's no point writing new games in an old API, although such practice is common. For this reason, it's best NOT to attack game code until you've studied this manual. It will result in a better game.

Modules are included beneath the API declaration:

    require "para" --different indents
    require "dash" --replaces double hyphen sign with a large hyphen
    require "quotes" --replaces quotation marks with chevrons << >>

It's usually a good idea to define default handlers here as well:

    -- an impossible attempted action generates
    -- this response by default
    game.act = 'Does not work.';
    game.use = 'It will not help.';
    game.inv = 'Do I really need this?';

Game initialization should be defined in the init function which will be called by the engine at the very beginning. It's a good place to set the player initial state or similar early requirements for the player. However you may not need an `init` function.

    function init()
        -- set a savegame stored variable
        me()._know_truth = false;
        -- add knife to the player's inventory
        take(knife);
        -- add paper to the player's inventory
        take(paper);
    end;

The INSTEAD installation directory is where the graphic interpreter looks for available games. The Unix version also checks `~/.instead/games`. The Windows version since `0.8.7` checks `Documents_and_Settings/USER/Local_Settings/Application_Data/instead/games` but from `STEAD 1.2.0` on both Windows and Unix standalone builds looks at `./appdata/games`, if it exists.

In some INSTEAD builds (on Windows or on Linux if the project is built with gtk, etc.) it's possible to open a game from any location using the menu option “Select Game” or by hitting F4. If there's only one game in the directory it will be launched by the interpreter automatically, which is handy if you distribute your game with the engine included. Your players can simply launch INSTEAD to start their adventure.

While writing code it's strongly recommended to use indents for nested levels like in the code samples in this manual. It really helps to clarify and decreases mistakes.

Here's a basic template for your first game:

    -- $Name: My first game$
    -- $Version: 0.1$
    -- $Author: Homo codius$
    instead_version "1.9.1"
    require "para" --for decoration
    require "dash"
    require "quotes"
    require "dbg" --for debugging
    game.act = 'Um...';
    game.use = 'It does not works!';
    game.inv = 'Why?';
    function init()
        --some initialization code if needed
    end

## Debugging Basics

In the event bugs occur (they will), it's handy to run INSTEAD with the command line parameter `-debug` which will generate more informative error messages. The `-debug` parameter can also be specified in the desktop icon/shortcut properties. Right click your INSTEAD desktop icon, select Properties from the dialog menu, then type `-debug` at the end of the `Target:` field.

In Windows, debug mode opens a separate console window where errors are output. Unix uses the console where INSTEAD was launched from.

Also you can engage an internal hotkey debugger module (F7) by adding the following line after `instead_version` in the header of the `main.lua` file.

    require "dbg"

Debug mode displays the call stack, as well as allows you to quickly restart the game with Alt+R. Combining this hotkey with quicksave/quickload (F8/F9) it's possible to assess changes very efficiently with each edit you write to your code.

In your code you can force output your own custom debug messages using the `print()` method inside a function placed within an object's `act` handler:

    act = function(s)
        print ("Act is here! "..stead.deref(s));
        ...
    end;

Don't fear the previous example! After reading this manual, and with your own game on the anvil, you'll look at this code with more inspiration.

HINT: It's often useful to examine savegame files during debugging because they contain special stored game state variables.

If you're already an experienced debugger you'd probably like the ability to check your Lua syntax by parsing it with the `luac` compiler. In Unix just use the `-p` option at the command line.

On Windows you'll have to install the Lua binaries from here , then run `luac52.exe` to parse your code.

You can also run a syntax check with your initial program call, as long as you're running `version 1.9.2` or higher. Just add `-luac` to your call.

    sdl-instead -debug -luac <path/to/lua/script.lua>

# Rooms

A room is a basic game unit in which the player can exist and interact with objects. A room can represent a literal room inside a house or a massive redwood forest.

Every game must contain one variable called `main` of object type `room`. This main room is always where the game begins and where the player appears upon starting the game.

HINT: It could also be a custom start menu.

    main = room {
        nam = "The Main Room";
        dsc = [[You are in the first room of this game.]];
    }

The definition above, signified by the `=` sign, actually creates an object in the game world, a `room` simply being a special kind of object. Most things in INSTEAD are objects.

For every object there are two requisite attributes, `nam` and `dsc`, which are closed with a semicolon or a comma.

Many more attributes and handlers can come along with these two. They can receive text strings, numbers, booleans, and even functions.

The above example's `nam` attribute contains a text string that will be displayed at the top of the game window. The `nam` attribute can be used to target the object from other code. You can often refer to an object by its `nam` rather than its variable, in this case `main`, when developing more complex interactions throughout your game.

In fact, `nam` doesn't have to be output to the screen at all, to be reserved for other uses. The `disp` attribute, if present, will override it in the graphical interpreter and be displayed at the top of the player's window.

    main = room {
        nam = 'Start';

        -- displayed in the window
        disp = 'My old room, covered in dust...';
        dsc = [[I'd almost forgotten the color of the walls.]];
    }

This provides you the developer with multiple names by which you can target an object.

The `dsc` attribute contains a static description of the object, which gets displayed to the player on her first entrance. To display `dsc` again she must look at the room explicitly, or if it's your intention for `dsc` to be shown repeatedly, you can include the `forcedsc` attribute.

Either put it with your other `game` definitions at the top of the `main.lua` file.

    game.forcedsc = true;

Or inside the room's attribute list.

    main = room {
        forcedsc = true;
        nam = 'The main room';
        dsc = [[Guess what.]];
    };

However, it's not recommended to use this technique because the engine is currently optimized for classic games to which it can't apply.

You can also use `stead.need_scene()` to force display static `dsc` in current room wherever you need. Read more in the Auxiliary Methods/Functions section.

A string can be enclosed with single or double quotation marks.

    main = room {
        nam = 'The very same room';
        dsc = "Got it in one!";
    };

For long text strings it's better to use double-bracket notation.

        dsc = [[ Very loooong description... ]];

Line breaks are ignored, so you must use the `^` symbol if you want to display one on the player's screen.

        dsc = [[ First paragraph. ^^
            Second one.^^
            The third.^
            New line here:)]];

## Passing Between Rooms

Typical passages look like links at the top of the main story panel in the player's game window. These connections are defined in the `way` attribute as a list. Rooms are listed by `nam` reference (or using a variable identifier, as long the room has been defined earlier in the code). This is written the same as an `obj` list.

    main = room {
        nam = 'main room',
        dsc = 'You are in a large room.',
        obj = { 'tabl' },
        way = { 'room2' },
    };
    room2 = room {
        nam = 'hall',
        dsc = 'You are in a huge hall.',
        way = { 'main' },
    };

Two rooms are defined here. It's useful to remember that `nam` and `disp` can be written as functions to utilize dynamic room captions, which are generated on the fly, for example in a room whose `nam` shouldn't be known to the player until he enters. However, there are more appropriate tools for this purpose such as the `wroom` module discussed later.

When passing between rooms the engine calls the exit handler of the current room and the enter handler of the destination:

        hall = room {
        enter = 'You enter the hall.',
        nam = 'Hall',
        dsc = 'This is one gigantically stupendous hall.',
        way = { 'main' },
        exit = 'You leave the hall.',
    };

Like any handler, exit and enter may be defined as functions. The first parameter is the current room. The second parameter is the previous room `f` for entering, or the destination room `t` for exiting:

    hall = room {
        enter = function(s, f)
            if f == main then
    	    p 'You came from the room.';
            end
        end,
        nam = 'hall',
        dsc = 'You are in a huge hall.',
        way = { 'main' },
        exit = function(s, t)
            if t == main then
                p 'I don\'t wanna go back!'
                return false
            end
        end,
    };

As we see, the handlers can return two values, a string for graphical display and/or a boolean for changing a status. In our example the `exit` handler's function returns `false` if the player tries to go into the main room from the hall. It means she'll have to find another way, like the Barlog :). The same logic can be applied to the `enter` and `tak` handlers.

You can also return both values in a more concise way:

        -- action text followed by comma separating the status value
        return "I don't wanna go back.", false

Take into account the room pointer `here()` may not update in sync with the `enter` call! You can instead use the `left` and `entered` handlers which are triggered after the player has passed through. These handlers are recommended if you don't need to forbid passage.

Sometimes you'll want to give a passage a clever title that's distinct from the destination room's `nam`. There are several ways to implement this, but the easiest is by using the `vroom` module:

    hall = room {
        nam = 'hall';
        dsc = 'You are in the hall';
        -- the syntax for vroom is ('passage name', 'destination room')
        way = {
            vroom('To the first room', 'main')
        };
    }

    main = room {
        nam = 'main room';
        dsc = 'You are in the small room.';
        obj = { 'tabl' };
        way = { vroom('To the hall', hall) };
    };

Technically the `vroom` module returns an auxiliary `room` object with a special `enter` handler set to bounce the player into the destination room. Yippee!

Sometimes you may need to get a bit more complex by disabling and enabling passages. The engine's concept of passages assumes they are always visible even if blocked, such as a room within a house with a locked door. Therefore it's unnecessary to hide passages.

Instead you can check for a key in the player's inventory, which will be implemented in the `enter` handler of the destination room. If no key is present, a notification can alert the player and forbid her passing through. You can also create a door as a `room` object, place it inside another room, and implement unlocking it with a key, to allow the player to pass using the customary `way` list.

There are situations when you won't want a passage to be obvious to the player, or to make it appear as the result of a special event. For example a clock might be hiding a secret tunnel behind it:

    hall = room {
        nam = 'hall';
        dsc = 'You are in a huge hall.';
        obj = { 'clock' };
        way = { vroom('Behind the clock', 'behindclock'):disable() };
    };

    clock = obj {
        nam = 'clock';
        dsc = [[You see an old {clock}.]];
        act = function(s)
            --the path() method employs the enable method
            path('Behind the clock'):enable()
            p [[You discover a secret tunnel behind the clock!]];
        end;
    };

So as you can see, an initially hidden passage is created with the `vroom()` and `:disable()` methods. You can easily hide objects in lists this fashion, so `behindclock` can disappear from the room description, but it will still be available to be called later. A useful technique for hidden objects is to initialize them in a disabled state like this. The object isn't processed inside the engine until the `:enable()` method has returned it.

Semantically, you can also write these `enable/disable` methods reversed like this:

    way = { disable(vroom('In the hours, 'inclock')) };

Then inside the clock object, its act handler invokes the `path()` method, which references the 'Behind the clock' object `vroom` aliased just prior, and calls `enable()` on it. You can also write it this way:

    act = function(s)
        enable(path('Behind the clock'))
        --or, since you don't have to parenthesize solo
        -- parameters in Lua, you could also write it like this:
        -- enable(path 'Behind the clock')
        p [[You discover a secret tunnel behind the clock!]];
    end;

If the passage we want to toggle on or off is in another room, we can pass it as the second parameter of `path()`.

        path('Behind the clock', 'room312'):enable();

If you'd rather create simple passage variables, you can define them with `vroom` inside like this:

    path_clock = vroom('Behind the clock', 'behindclock');
    clock = obj {
        nam = 'clock';
        dsc = [[You see an old {clock}.]];
        act = function(s)
            path_clock:enable()
            p [[You discover a secret tunnel behind the clock!]];
        end;
    }

    hall = room {
        nam = 'hall';
        dsc = 'You are in a huge hall';
        obj = { 'clock' };
        way = { path_clock:disable() };
    };

You can also toggle a room object itself without employing `vroom`.

    inclock = room {
        nam = 'In the tunnel';
        dsc = [[It's dark here.]];
    }:disable(); --simply tacks on a disable
    -- method to the end of the room object
    -- the following three methods are also equivalent:
    -- }:disable()
    -- }; inclock:disable()
    -- }; disable(inclock)

    clock = obj {
        nam = 'clock';
        dsc = [[You see an old {clock}.]];
        act = function(s)
            -- toggles the "inclock" room to true
            inclock:enable()
            p [[You discover a secret tunnel behind the clock!]];
        end;
    };

    hall = room {
        nam = 'hall';
        dsc = 'You are in a huge hall';
        obj = { 'clock' };
        way = { 'inclock' };
    };

# Objects

Objects are what the player interacts with. Here are two examples:

    tabl = obj { --you can't name it table with an 'e' because
    -- it's a Lua keyword. Be careful with keywords and variables.
        nam = 'table',
        disp = 'Table',
        dsc = 'There\'s a {table} in the room.', -- you can escape
        -- apostrophes using \ so they
        -- won't interfere with the string

        act = 'Hm... just a table...', -- displays when
        -- object's hotlink is clicked in the dsc
    };

    salt = obj {  -- this variable can be used
    -- inside the obj list of other objects,
    -- making this object display with them

        nam = 'salt shaker'; -- name that can be
        -- used as a reference in some functions

        -- displayed in the inventory panel
        disp = 'Salt Shaker';

        -- displays a highlighted hotlink for anything within
        -- curly braces, i.e., {salt shaker}
        dsc = 'There\'s a {salt shaker}.';

        -- displays when player clicks the hotlink above
        tak = 'I took hold of the salt shaker of the table';
        -- displays when the player uses the item on another item in her inventory
        inv = 'It's the corner of the table.';
    };

Objects are represented in the inventory panel by the `nam` or the `disp` attribute, `disp` taking precedence. Also, `disp` can be set to `false` which makes the object invisible in the inventory.

Text enclosed with curly braces `{ }` inside the `dsc` attribute will be displayed as a hotlink in the graphic interpreter.

The `act` event handler must be a string, a boolean value, or a function returning one of these two.

WARNING: Some objects (table, io, string, etc…) are reserved in the Lua namespace. Be careful not to use any reserved words when choosing variable identifiers for your objects. In modern INSTEAD versions this problem is almost solved. However, you still will not be able to use variable identifiers that match INSTEAD constructors (obj, game, player, list, room, dlg, etc…)

## Adding Objects to Rooms

To include an object to a room or another object add the intended object's variable to the target room/object's obj table. For example `salt` can be bound to the `tabl` object this way:

Add references to the `obj` table to place corresponding objects at the room:

    tabl = room {
        nam = 'Table',
        dsc = 'It\'s a large kitchen table with a bowl of {salt}.',
        obj = { 'salt' },
    };

You can also use an unquoted variable identifier instead of a quoted reference, but you must define the object before defining the room in order for this to work. References have no such limitation, therefore using references is highly recommended.

Separate multiple objects within a list with commas or semicolons (standard Lua delimiters):

    obj = { 'tabl', 'apple' };

Feel free to use line breaks to make your code more readable.

    obj = {
        'tabl',
        'apple',
        'knife',
    };

You can also use functions to place objects in rooms, which will come later.

## Objects Referencing Objects

Any object may have an `obj` list. The parent object displays its `dsc` then carries out the same operation for each of its children inside `obj`. For example let's place a `bowl` on the `desk`.

    main = room {
        nam = 'A Kitchen',
        dsc = 'You walk inside.',
        -- These references can be defined after because
        -- they're housed within quotes
        obj = { 'window', 'desk' },
    };

    window = obj {
        nam = 'Window',
        dsc = [[Diffused daylight pours through a
                round porthole in the middle of the ceiling.]],
    };

    desk = obj {
        nam = 'Desk',
        dsc = [[There's a desk in the center of the room.]],
        obj = { 'bowl' },
    };

    bowl = obj {
        nam = 'Bowl',
        dsc = [[On the surface there's a metal
            bowl covered in strange engravings.]]
    };

First the player will see the room `dsc` with a large line break, then the window's `dsc`, the desk's `dsc`, and finally the bowl's `dsc` (it's the desk's child object).

Also if you move an object to another room, nested objects will be moved with it. This is part of the referencing mechanism: an `obj` table stays bound to its parent object. So be diligent about keeping track of nested objects.

## Using Objects On Objects

Players often try to use objects in their inventory on other objects. To satisfy this basic urge, the `use` handler can be invoked for the held object, and `used` for the targeted object. For example:

    knife = obj {
        nam = 'knife',
        dsc = [[There's a {knife} on the chair]],
        inv = [[It's sharp!]],
        tak = 'I took the knife!',
        use = 'You try to use the knife.',
    };
    chair = obj {
        nam = 'chair',
        dsc = 'There is a {chair} in the room.',
        act = 'Hm... Just a chair...',
        obj = { 'apple', 'knife' },

        --you monster!
        used = 'You try to hurt the chair...',
    };

If the player takes the knife and uses it on the chair, he gets the text of knife's `use` handler along with the chair's `used` handler. These two can also contain functions. The first parameter `s` refers to the object itself, and the second parameter `w` is the target object if you're defining the `use` handler, the affected object if you're defining the `used` handler.

    knife = obj {
        nam = 'knife',
        dsc = 'There is a knife on the {chair}',
        inv = 'Sharp!',
        tak = 'I took the knife!',
        use = function(s, w)
            if w ~= tabl then
                p [[I don't want to cut this.]]
                return false
            else
                p 'You incise your initials on the chair.';
            end
        end;
    };

In the example above you can only use the knife on the chair. If `use` returns false then `used` won't be invoked, and its return value is ignored. Also, if these two handlers aren't defined or they return nothing the default handler `game.use` is called.

It's your choice which one to implement in any given situation, but it's a good idea to place the handler near the object it affects. For example, a trash bin that allows the player to throw anything inside makes sense to employ the trash bin's `used` handler.

    trash = obj {
        nam = 'trash';
        dsc = [[I see a {trash bin}.]];
        act = 'It is not for me.';
        used = function(s, w)
            remove(w, me())
            p [[I do not need it anymore.]];
        end;
    }

Bugs often occur when `use` and `used` are implemented by two unintended objects the player decides to play with. For example, if the player has a knife you intend for her to use on an apple, but she decides to cut the trash bin, the knife will vanish. We'll need to rework the knife's handlers to correct this behavior. The `nouse` handler should be implemented:

    ..........................
    require "nouse"
    ..........................
    knife = obj {
        nam = 'knife',
        use = function(s, w)
            if w ~= apple then
            -- if the apple is not an action subject
                return
            end
            if w.knife then
                return "It's already skinned."
            end
            w.knife = true
            p 'I skinned the apple.'
        end;
        nouse = [[I don't want slash it.]];
    };

The `nouse` handler will be called by the engine if neither `use` or `used` returns something adequate. If `nouse` isn't called, then the `noused` handler within the affected object will searched for and called. If none of these result in an adequate return value, then the default handler `game.nouse` will be deployed.

All of these usage handlers can be functions, each with three arguments (the handler owner object, the actor object, the target object).

NOTE: The `nouse` handler actually redefines `game.use` so you must switch to its alternatives such as `game.nouse`.

It's also possible to use a scene object (placed in scene, not in inventory) on other objects. If you are going to implement this mechanism, you need to set an object or global `game.scene_use` boolean attribute `scene_use`, or build a function that returns a boolean value.

    stone = obj {
        nam = 'stone1';
        var { pushed = false };
        scene_use = true;
        dsc = [[I see the heavy {stone} on the floor.]];
        use = function(s, w)
            if w == door then
                s.pushed = true
                p [[I pushed stone to the door.]]
            else
                p [[I do not want to do a hard work!]];
            end
        end;
    }
    -- here, this object in scene can be used on other
    -- objects in scene, like the inventory item...

## The Player Object

The player is represented by the object variable `pl` of type `player`. In the engine it's represented this way:

    pl = player {
        nam = "Incognito",
        where = 'main',
        obj = { }
    };

You can target the current player object with the `me()` pointer. In most instances `me() == pl`.

The `obj` table inside `pl` represents the player's inventory. Also, if you want the player to have special qualities you can implement them in the `var` table (such as power, speed, etc.):

    pl = player {
        nam = "James";
        where = 'main';
        var { power = 100 };
        obj = { 'apple' };
        -- let's give him an apple
    };

You can even create multiple players (pl2, pl3, pl4, etc.) and alternate between them using `the change_pl()` function. It only has one parameter, which targets the player object being switched to. Using this function will change the current game location to whereever the target player is located.

### Inventory

A player's inventory exists inside the player object. The easiest way to put something there is to define its `tak` handler.

    apple = obj {
        nam = 'apple',
        dsc = 'There is an {apple} on the table.',
        inv = function(s)
            inv():del(s); --//inv()// is
            -- a pointer that you can use in the shorthand
            -- Lua syntax describes before to target the
            -- inventory of (s) which refers to apple
    	return 'I ate the apple.';
        end,
        tak = 'You took the apple.', -- same as
        -- the act handler, only it puts the
        -- target object in the inventory panel
    };

Examine the `inv` handler above. After the object has been take, the player can click it in her inventory panel. The apple is then removed from the inventory and the returned action text is displayed:

    'I ate the apple.'

It's also possible to implement taking inside the `act` handler:

    apple = obj {
        nam = 'apple';
        dsc = 'There is an {apple} on the table.';
        inv = function(s)
            remove(s, me()); -- remove(parent target, consumer)
    	-- me() is the player pointer. The effect of
            -- consuming an inventory item can be defined
    	p 'I ate the apple.'
        end;
        act = function(s)
            take(s) --take() is another method
            p 'You took that apple.';
        end;
    };

If an object doesn't have an `inv` handler then `game.inv` will be called.

You should also be aware that the term “inventory” is loosely defined in the game engine, so the inventory panel could even house abstract objects such as interactive command buttons and status meters. Go wild.

### Multiple Inventory Presets

In fact, you may use multiple characters for switching between different types of inventory. Like this:

    instead_version "2.1.0"
    pl1 = player {
        nam = '1';
        where = 'main';
    }
    pl2 = player {
        nam = '2';
        where = 'main';
    }
    inv_sw = menu {
        nam = function(s)
            return ('Inv:'.. stead.nameof(me()))
        end;
        menu = function(s)
            if me() == pl1 then
                pl2.where = here()
                change_pl(pl2)
            else
                pl1.where = here()
                change_pl(pl1)
            end
        end
    }
    apple = obj {
        nam = 'apple';
    }
    knife = obj {
        nam  = 'knife';
    }
    function init()
        change_pl 'pl1'
        place(inv_sw, pl1)
        place(inv_sw, pl2)
        place(apple, pl1)
        place(knife, pl2)
    end
    main = room {
        nam = 'room 1';
        dsc = 'room 1';
        way =  { 'r2' }
    }
    r2 = room {
        nam = 'room 2';
        dsc = 'room 2';
        way = { 'main' }
    }

## The Game Object

The game itself is represented as the object `game` of type `game`. The engine defines it as follows:

    game = game {
        codepage = "UTF-8",
        nam = "INSTEAD, version "..stead.version.." 'by Peter Kosyh",
        dsc = [[
            Commands:
                look (or just enter),
                act <on what> (or just what),
                use <what> [on what],
                go <where>,
                back,
                inv,
                way,
                obj,
                quit,
                save <fname>,
                load <fname>.
        ]],
        pl = 'p1',
        showlast = true,
        _scripts = {},
    };

As we can see, the game object holds the current player `pl` reference and some settings. At the beginning of your game you can set the text encoding to anything you want, but keep in mind it's better to just switch your editor to `UTF-8 without BOM!` encoding and work with the game engine. Changing the encoding is useful when running games written for other platforms (like URQL).

    game.codepage = "cp1251";

The game object also contains your default handlers for `act`, `inv`, `use` (It's best to always define them!).

    game.act = 'You can\'t.';
    game.inv = 'Hmm... Odd thing...';
    game.use = 'Won\'t work...';

NOTE: Don't forget that the `nouse` handler reserves the `game.use` default handler for its own peculiar needs, so if you implement `nouse` then you'll need to to include a `game.nouse` handler as a fallback for `use` to prevent bugs.

## The Timer Object

Since `version 1.1.0` of the SDL version, the game engine has incorporated a timer object.

    timer:set(ms)  --sets the timer interval in milliseconds
    timer:stop()  --stops the timer
    timer.callback(s)  --creates a callback for the timer, calling it in a fixed time interval

You can create a function that will return a stead interface command invoked after the callback's execution. For example:

    timer.callback = function(s)
        main._time = main._time + 1;
        return "look";
    end;
    timer:set(100);
    main = room {
        _time = 1,
        forcedsc = true,
        nam = 'Timer',
        dsc = function(s)
            return 'Example: '..tostring(s._time);
        end;
    };

## Lightweight Objects

Sometimes we need to fill a room with non-functional decorations to make the game world seem more diverse. Lightweight objects may be used for this purpose. For example:

    sside = room {
        nam = 'southern side',
        dsc = [[I walk to the southern wall of the building. ]],
        act = function(s, w)
            if w == "porch" then  -- this references
            -- the lightweight objects created
            -- below in the obj list
                ways():add('stolcorridor');
                p [[There's an entrance with a porch.
                   The sign on the door reads 'Canteen'.
                   I'm not hungry... Should I go in?]];
            elseif w == "people" then
                p "The people leaving look quite content.";
            end
        end;
        obj = {
               -- this is a lightweight object
               vobj("porch", "There is a small {porch} by the eastern corner."),
               --another lightweight
    	   vobj("people", [[From time to time the porch
                          door slams letting {people} in and out..]])
         },
    };

The method `vobj()` allows you to create a lightweight version of a static object. It can be interacted with by means of its parent's `act` handler which assesses the child's name. The `vobj()` method will call the `used` handler. The third parameter can call a separate object to interact with it. The `vobj()` syntax is simple:

    vobj(name, description, interactive_object)

NOTE: Lightweight objects often don't have handles to help you with interactions via inventory items, etc., so if you want the player to be able to access them you can define those behaviors within their `use` handler, via the `stead.nameof()` method, like so:

    use = function(s, w)
        if stead.nameof(w) == "humans" then
            p "You should not disturb humans."
            return
        end
    end;

One useful trick is adding `vobj()` to the room dynamically with a `place()` method:

    place(vobj("cont_button", "{Continue}"));

But this style is old-fashioned. Instead try using a `disable()` or `enable()` method within your static object descriptions, like so:

    obj = { vobj("cont_button", "{Continue}"):disable() };
    .......................................................
    exist('cont_button'):enable();  -- returns the object
    -- if it's present regardless of "able" state, then enables it

A useful permutation of `vobj()` is `vway()` which creates a reference leading to a specified room. Here's the syntax:

    vway(name, description, destination_room)

And an example implementation in an obj list:

    obj = { vway("next", "Press {here} to pass to the next room.", 'nextroom') }

If you're creating a game in the storybook genre where the gameplay consists of wandering from one link to another (which is probably a poor decision for your first game!) you should utilize the `xact()` module. It provides a simpler mechanism for creating references and also has the `xwalk` feature.

    instead_version "1.9.0"
    require "xact"

    main = room {
        nam = 'Begin';
        forcedsc = true;
        dsc = [[ Begin {xwalk(startgame)|adventure}? ]];
    }
    startgame = room {
        dsc = [[ A long time ago ...]];
    }

Using simple methods like `add()` and `del()` you can dynamically fill a room with `vway()` objects:

    objs(home):add(vway("next", "{Next}.", 'next_room'));
    -- some code here
    home.obj:del("next");
    -- home.obj is legacy style, use objs(home) instead

This behavior is due to `vobj()` and `vway()` being generic objects with predefined handlers and save methods, which allows on-the-fly creation. Knowing the engine architecture will help you implement object variants like these.

In addition to using lightweight objects for scene decoration, you can also define a static object directly in the `obj` list without a handle:

    hall = room {
        nam = 'living room';
        dsc = [[I'm in a spacious living room.]];
        obj = {
            obj {
                nam = 'table';
                dsc = [[There's a {table} in the middle.]];
                act = [[It looks like mahogany.]];
            };
        };
    }

You can also target such objects via `stead.nameof()` within the `use` handler, just like you did with `vobj()` lightweight objects:

    use = function(s, w)
        if stead.nameof(w) == 'table' then
            p [[I don't want to spoil such thing of beauty.]]
            return
        end
    end;

(NEEDS AN EXAMPLE)

You can also use a single object in multiple rooms, such as `shotgun shell` which gets duplicated as it's dropped into the player's current room each time she fires her `shotgun`. In this case the shells might merely serve as decoration without being interactive.

## Dynamically Spawning Objects

NOTE: It's recommended you study constructors before taking on this supplementary concept.

You can use the `new()` and `delete()` methods to create and remove objects dynamically. The `new()` method can accept a string argument that's written in the form of a constructor, which will of course return an object. Yay!

    -- adds a constructor definition to the code
    new ("obj { nam = 'test', act = 'test' }");

Better yet:

    -- places a new constructor in-world
    place(new [[
            function myconstructor()
            local v = {}
            v.nam = 'test object',
            v.act = 'test feedback',
            return obj(v);
        end;]]);

The constructed object will be saved every time the game is saved.

Something else to have fun with is the fact that `new()` adds a real object to the world, so you can find its variable identifier using the `deref()` method then do whatever you want with it, like delete it.

    cool_object = deref(new('myconstructor()'));
    delete(cool_object);

## Dynamically Creating References

NOTE: This is an advanced topic so there's no need for beginners to study this section in detail.

Dynamically created references can be implemented in various ways. The example below uses `vway` objects. Notice, it's most convenient to create dynamic references in the `enter` handler, but you're free to leave them wherever they fall in your code.

To add a reference you can use the `add()` method.

    objs(home):add(vway('Road', 'I noticed a {road} going into the forest...', 'forest'));

To delete a reference you can use the `del()` method.

    objs(home):del('Road');

The `srch()` method will check if the reference is present in the target room.

    if not objs(home):srch('Road') then
        objs(home):add(vway('Road', 'I noticed a {road} going into the forest...', 'forest'));
    end

If a reference is created in the current room, the previous example can be simplified.

    if not seen('Road') then
        objs():add(vway('Road', 'I noticed a {road} going into the forest...', 'forest'));
    end

Or you can manage references with `enable()` and `disable()`.

    seen('Road', home):disable();
    exist('Road', home):enable();

Creating initially disabled `vobj` and `vway` references works like this:

    obj = {vway('Road', 'I noticed a {road} going into the forest...', 'forest'):disable()},

Enabling them by their index in the `obj` table or by finding them with `srch` is similar.

    objs()[1]:enable();
    -- but better variant is
    exist 'Road':enable();

# Attributes and Handlers

Most attributes and handlers can be defined as functions. For example the `nam` attribute could just be defined as a string like so:

    nam = 'apple';

Or you could be fancy and define it as a function that returns that string, like so:

    nam = function()
        return 'apple';
    end;

Keep in mind the `nam` attribute must be defined as a string, even if you put some extra mojo inside its definition.

Strings passed to any of the `p()` methods are accumulated in an internal buffer for that specific attribute/handler. The accumulated content is passed back to the engine when the attribute/handler reaches its return. With this you can build a long text out of sequential calls to `p()/pn()/pr()`.

NOTE: The engine performs general formatting with spaces and line breaks to separate corresponding text parts. So, usually you do not need to do manual formatting. Use pxxx-functions to format a single attribute value.

The principal difference between handlers and attributes is that handlers can change the game world's state, while attributes cannot. So, if you define an attribute as a function remember an attribute's only purpose is to return a value. This is because the calling of attributes within the engine as a player roams around freely is often unpredictable and isn't bound to a specific game process, so their application within mechanisms is strongly discouraged.

Something to note about the always mechanism-friendly handler is that it cannot pause the engine to wait for an event to happen. That means you can't employ delay loops or other game delay mechanisms inside the handler itself. They're intended to change the game state and immediately return control to the game engine. The interpreter must deliver the handler's changes quickly so it can continue listening for player input. If you need to delay something use the `timer` or `cutscene` modules.

Handler functions almost always contain conditional statements when dealing with variables.

    apple = obj {
        nam = 'red apple',
        dsc = function(s)
            if not s._seen then
                p 'There is {something} on the table.';  --first entrance description
            else
                p 'There is an {apple} on the table.';  --alternate description
            end
        end;
        act = function(s)
            if s._seen then
                p 'The same apple, huh...';
            else
                s._seen = true;
                p 'Wow! It\'s an apple!';
            end
        end;
    };

The first parameter in a function `(s)` always refers to the parent object it self. When the player enters the room from this example her display will read “There's something on the table.” When the player clicks something the `_seen` variable inside the `apple` object will be set to `true`, which plays in nicely to the `dsc` function above it.

The stored variable `_seen` has an underscore at the beginning to signify it should be saved in the player's savegame file automatically. Now every time she returns to the room the game knows she's already seen the apple and will display the second description.

When an `if` statement is built without an operator `==, ⇐, ~=,…`, the variable is judged as a boolean value. Therefore, being defined as anything other than `false` means it's `true`. So for example:

    if s._seen then  --asks "Does s._seen exist and is it not false?"
        ACTION  --if the first statement is true this is performed
    else  --deduces that s._seen doesn't exist or was defined as false
        ACTION  --so this is performed instead
    end

When a numeric variable hasn't been defined and it's used in a conditional expression like the one above, the engine assumes the variable equals emptiness `nil`. You can check if a numeric variable exists with a similar code like this:

    if z == nil then
        p "Global variable z does not exist."
    end

The `nil` variable is also treated as `false` in conditional expressions:

    if not z then
        p "Variable z is not defined or false."
    end

But:

    if z == false then
        p "Variable z is false." -- z == nil will not pass this condition!!!
    end

NOTE: The `z` variable above could be undefined and so, condition `z == false` will not work, that might produce a bug in your game logic, so double check!

You can also cascade conditional statements using `then` as a delimiter, like so:

    if not z then
        if z ~= nil then
            p "Variable z equals false."
        else
            p "z is undefined! Sell your property and go hunt bugs!"
        end
    end

Take these behaviors into account when writing and debugging your game. If you have a misprint in a variable name, the expression will be evaluated as “undefined” with no error report. Your game logic will be broken and it will be difficult to find the error later.

## On-The-Fly Attribute Generation

Considering the dynamic room `dsc` in the above example is generated with a function, why not alter the `dsc` on the fly? Actually this won't work unless you define the `dsc` in the room's `var` table like this:

    button = obj {
        nam = "button";
        dsc = "There is a big red {button} on the room wall.";
        act = function (s)
            here().dsc = [[Everything changed in the room!!!]];
            pn [[The room transformed after I pressed the button.^
                 The book-case disappeared along with the table and the chest,^
                 and a strange looking device took its place.]];
        end
    };

    r12 = room {
        nam = 'room';
        var {
            dsc = [[I am in the room.]];
        };
        obj = {'button'}
    };

It's highly recommended to NOT do this. Instead, write your attributes themselves as functions, and refrain from changing their values externally. Such programming style is costly, since you're making future modifications difficult by not keeping attribute values inside the objects they describe, and your savegame files will consume much more disk space.

## Custom Attribute Lists

Standard attribute lists such as `way` or `obj` store objects in a table and manage themselves with a pre-defined set of methods, but lucky you can create lists for your own needs, and they don't have to be defined through `var` or `global`. For example:

    treasures = list { 'gold', 'silver' };

Your available list methods are:

- `add(object, [pos])` –add the object to this list, at the optional position
- `cat(b, [pos])` –insert the content of “b” (another list object) into this list at position
- `zap()` –clear this entire list
- `del(object)` –remove the object from this list, but ONLY if it's not disabled! (see next method)
- `purge(object)` –remove any object, EVEN disabled ones
- `srch(object)` –search for the object in this list. If found, return the found item and its index
- `replace(old, new)` –replace the old object with the new one
- `enable(object)` –enable the object, if found
- `disable(object)` –disable the object, if found
- `enable_all` –enable all objects in this list
- `disable_all` –disable all objects in this list

The methods `add`, `del`, `purge`, `replace`, `srch` and others can receive objects by `nam` as well as by a referenced link.

A simple example involves the system method `inv()` that references the player's inventory list, which can be quickly manipulated with a list method like so:

    inv():del('apple'),

You could even cleverly recreate the take functionality inside the `act` handler using list methods:

    knife = obj {
        nam = 'knife',
        dsc = 'There is a {knife} on the table.',
        inv = 'It\'s sharp!',
        act = function(s)
            objs():del(s);
            inv():add(s);
        end,
    };

The system method `objs()` returns the list containing all current room objects, or if given a parameter it can target any room. The corresponding method for getting the list of passages for a given room is `ways()`.

Starting in `version 0.8` the `game` object can be used as a parameter for the `add()` method. Also there's an optional second parameter that targets a specific position in the receiving list. You can now also set a list's values by index using the `set()` method. For example:

    objs():set('knife',1);

Starting in `version 0.9.1` the `enable_all()` and `disable_all()` methods work with embedded objects (objects within object), and the methods `zap()` and `cat()` became available.

Starting in `version 1.8.0` the methods `disable()` and `enable()` can be used, however…

NOTE: It's highly recommended when manipulating objects and inventory to use higher level methods such as:

    place/get/take/drop/remove/seen/have

## The Handler's Text Buffer

Sometimes we need to format output from a handler based upon a prescribed set of conditions. In such a situation the `p()` and `pn()` methods are quite useful. These two methods add formatted text to the internal buffer of the handler, which gets returned by the handler in one big chunk.

    dsc = function(s)
        p "There's a {barrel}." --this gets buffered, with whitespace
        if s._opened then
            p "Its lid is leaning against the wall."  --this gets tacked onto the first one
        end
    end;

One way to update the player with the status of some action is via `pget()` in the return.

    knife = obj {
        ...
        use = function(s, w)
    -- (w) is another object the player
    -- is using the knife to interact with
        if w == apple then
            -- so if it's an apple
            -- she says she peeled it
            p 'I peeled the apple';
            -- and the apple stays peeled
            apple._peeled = true
            return
        end
        p [[You shouldn't use a knife like that.]]
        return pget(), false;  -- false is to stop call 'used' method
    end;

## No-Output Handlers

Sometimes we need a handler doing something without producing any output.

    button = obj {
        nam = "button";
        var {
            on = false;
        };
        dsc = "There is a big red {button} on the wall.";
        act = function (s)
            s.on = true
            return true
        end;
    };

    r12 = room {
        nam = 'room';
        forcedsc = true;
        dsc = function (s)
            if not button.on then
                p [[This button hasn't been pressed.]];
            else
                p [[The button has been pressed.]];
            end
        end,
        obj = {'button'}
    };

Here the `act` handler alternates the room description, so there's no need for it to print anything itself. It's a contrived example, and you'll likely never need handlers with no output. As for the above example, you could instead print “Pressed the button.” with the `act` handler's function. Moreover, the example requires `forcedsc` mode, which breaks backward compatibility. However, such a handler could at some point be useful, so it's worthwhile to be aware of it.

You could also return only `true` from an `act` handler, which would mean an action completed successfully but didn't require any output. If you need some kind of report for the player, just don't return anything, which will display your default `game.act` text. Problem solved.

## Handler Calls Using Lua

Sometimes you need to call a handler manually. You can use the shortform Lua syntax for method calls `object:method(parameters)` if the handler `act`, `tak`, `inv`, etc., was written as a function within the target object:

    -- the function in the act handler of apple is called
    apple:act()

For more clarity here is the longform of the Lua syntax:

    -- so the shortform above simply erases the (self) parameter
    -- since it's redundant, and replaces the period with a colon
    apple.act(apple)

If the object's handler is not a function you can utilize the `stead.call()` routine to call the handler in the same manner as the interpreter does. The syntax is: stead.call(object, 'name of handler/attribute', arguments…) So, for example, to get `nam` value of the object `apple` you can do this:

    act = function(s) -- somewhere
        local r = stead.call(apple, 'nam')
        p(r)
    end

In fact, there is the `stead.nameof()` for this case, but this is just an example.

## Dynamic Events And Life Simulation

Handlers can be programmed to execute as certain player conditions are met. This technique is often used to run background processes such as life simulation. For this purpose a special event handler exists, called the `life` handler.

Any object, including rooms, can employ a `life` handler, which is called every time the game clock advances as long as the object has been added to the worldwide list of living objects (more on this in a moment). Remember, the game clock is the total number of player actions so far in the game.

Dynamic events follow this rough algorithm for each tick of the game clock:

1. The player does something in the game, which increments the game clock
2. The `life` handlers for all living objects are triggered
3. Relevant object's commence their life-like behaviors

To illustrate a simple living object, first let's give Barsik the cat some animation.

    mycat = obj {
        nam = 'Barsik',
        behaviors = {
            [1] = 'Barsik peers out of my coat.',
            [2] = 'Barsik kneads my chest. OWWW!',
            [3] = 'Barsik purrs against me.',
            [4] = 'Barsik yawns.',
            [5] = 'Barsik\'s warmth is welcome.',
            [6] = 'Barsik escapes from my coat.',
        },
        life =  function (s)
            local r = rnd(5);
            if r > 2 then
                return;  --provides a 60% chance of no behavior
            end
            r = rnd(#s.behaviors);  --the # symbol gets the last index number
               p(s.behaviors[r]);  --displays a random behavior
        end;
    };

Now that Barsik looks like a living creature, let's make it final.

    lifeon('mycat');

Okay, like you were told before, this is the part about the worldwide list of living objects. The `lifeon()` method as seen in the code above, adds Barsik the cat to this list. Don't forget to remove deceased objects from the list with `lifeoff()`, usually via the `exit` handler.

If there are a dizzying number of living objects in your game, you may want to assign priority levels. The second parameter of `lifeon()` takes a positive integer, with `1` being highest priority.

    lifeon(object_name, positive_integer);

To initialize a life simulation background process for a particular room, simply include `lifeon()` in an object's `entered` handler and `lifeoff()` in the `left` handler, then define the process in the `life` handler.

    cellar= room {
        nam = 'in the basement';
        dsc = [[It's dark down here.]];
        entered = function(s)
            lifeon(s);
        end;
        left = function(s)
            lifeoff(s);
        end;
        life = function(s)
            if rnd(10) > 8 then
                p [[I heard something rustling!]];  --scare tactics!
            end
        end;
        way = { 'upstair' };
    };

You can discern whether the player has crossed a room's border by employing the `player_moved()` method inside the `life` handler.

    flash = obj {
        nam = 'flashlight';
        var { on = false };
        life = function(s)
            if player_moved() then
                -- extinguishes the flashlight on room changes
                s.on = false
                -- let's the player know what happened
                p "My light went out..."
                   return
            end
        end;
    	...
    };

To track continuous events you can use the `time()` method, or utilize a custom counter variable. To track player location use `here()` function. Use these in conjunction with the `live()` method, which checks if an object is still living.

    dynamite = obj {
        nam = 'dynamite';
        dsc = 'BOOM!';
        var { timer = 0 };
        used = function(s, w)
            -- checks if the player uses their zippo lighter
            if w == zippo then
                if live(s) then
                    --checks redundant
                    return "It's already lit."
                else
                    -- the player lights it
                    p "I ignited the fuse."
                    -- the dynamite is added to list of living objects
                    lifeon(s)
                end
            end
        end;
        life = function(s)
            -- if it's living/lit the timer starts
            s.timer = s.timer + 1
            if s.timer == 5 then
                -- when it reaches 5 the dynamite dies
                lifeoff(s)
                if here() == where(s) then
                    -- checks if player is in the same room
                    p [[...yeah I'm dead.]]
                else
                    p [[I heard an explosion somewhere.]];
                end
            end
        end;
    };

If a `life` handler returns a string, it displays below the room's static description by default. To make the text appear above, simply return `true` as it's second value.

    life = function(s)
        return "The guardian entered the room.", true;
    end;

If you want to prevent all life processing in a particular room, add the `nolife` module to your game.

    instead_version "1.8.2" --needs to be this version or higher
    require "hideinv"
    require "nolife"
    ...
    guarddlg = dlg {
        nam = 'Guardian';
        hideinv = true;
        nolife = true;
    	...
    };

WARNING: When putting the `walk()` method inside a room's `life` handler you should take into account whether the `life` handler will affect player location. If so, any results from the handler will will be discarded at the point of player movement, then her new location's `life` handler will activate. This can get confusing, so it's best to implement `walk()` carefully.

The `life` handler is capable of removing all `act` handler text from the display, in order to let more pressing events dominate the player's focus. Imagine the player is examining a regular window in a boring room…

    window = obj {
        rainrain = false;
    	...
        act = function(s)
            s.rainrain = true;  --the variable that triggers the goblin
            return "It's probably about to rain. I wonder where my umbrella is..."
        end;
    };

Suddenly an evil goblin enters the room and runs right for her. In such a panicky situation, the window's `act` handler telling her about rain and umbrellas is useless information. The following code removes it and allows the goblin's `life` handler to take center stage.

    goblin = obj {
        ...
        life = function(s)
            if rainrain == true then
                p("A goblin's running toward me!");
                -- removes all act handlers' text from the display
                ACTION_TEXT = nil;
            end;
        end
    };

The `ACTION_TEXT` variable is unique to `life` handlers because of their clock-based routine, and allows them to change the output of all `act` handlers in the room at once. It's usually best to simply clear it with `nil`. This way the player can focus on the goblin. :O

# Methods/Functions

The game engine provides several standardized methods for returning frequently used objects (Methods are also called functions, but this manual tries to reserve the term “function” for your own code definitions, and tries to use the term “method” for anything pre-defined within the engine, simply to make it easier for young developers to discern what's being addressed in this manual).

The following terminology is used throughout this section, so refer to it as you study the methods themselves.

Common Terminology

- brackets `[ ]` – encloses optional parameters
- what – the target object (including rooms) passed as a link, reference, or variable handle
- where – the target object (including rooms) passed as a link or reference
- room – a room object passed as a link or reference
- object – an obj object, such as a table or an NPC
- passage – a value held in the way list as a link, reference, or variable handle

Methods Returning Lists

- `inv()` –returns the inventory objects list
- `objs([where])` –returns the objects list of the current room or of an object passed as the optional parameter
- `ways([room])` –returns the passages list for the current room or for one passed as the optional parameter

Methods Returning Objects

- `me()` –returns the current player object
- `here()` –returns the current room
- `where(object)` –returns a room or an object that was placed using a `put/move/drop/replace` method, or others
- `from([room])` –returns the previous current room of the player or the room visited prior to the room passed as the optional parameter
- `seen(what[, where])` –returns the object in the current or optionally targeted room, if the object is present there and is not diabled (see `exist()`)
- `exist(what[, where])` –similar to seen() but will find disabled objects
- `have(what)` –returns the object (what) if it's present in the inventory and is not disabled
- `live(what)` –returns the object (what) if it belongs to an alive object (read further in wiki)
- `path(passage[, room])` –returns the passage from the way list of the current room or one passed as the optional parameter, even if it is disabled

The methods used in the following example are usually used in conditional statements or to find objects for subsequent modification.

    exit = function(s)
        -- remember that Lua allows solo parameters to go without parentheses
        if seen 'monster' then
            p 'The monster blocks your way!'  --another solo parameter
            return false
        end
    end;
    	...
    use = function(s, w)
        if w == window and path 'Through the window':disabled() then
            -- checks whether actions on the window and
            -- its corresponding passage are currently
            -- disabled in the game

            --enables them
            path 'Through the window':enable();

            -- dramatizes with descriptive fiction. Yay!
    	p 'I broke the window!'
        end
    end;
    ...
    act = function(s)
        if have('knife') then
            p 'But I have a knife!';
            return
        end
    end;

Two useful system methods are:

- `stead.ref(reference)`
- `stead.deref(object)`

The first returns a link to the object passed by reference, the second one returns a reference to the object passed directly. This might seem confusing now, but you'll soon understand the concept of references versus objects. Here's an illustration:

    -- if apple is defined, the reference is equal to the variable itself
    stead.ref 'apple' == apple

Here's a simple example of `stead.deref()` in action:

    act = function(s)
        -- this takes the object, s,  that was passed to the
        -- function directly and returns a reference so that
        -- the print method can concatenate it with its string
        p('You clicked the object '.. stead.deref(s));
    end;

## Code Statements

A code statement is useful for defining a very short function. To save them you can assign them to a stored variable in the `global` or `var` tables. Here's an example of a short `code` function called in an `act` event handler:

        act = code [[ walk(sea) ]];

You can also redefine `code` functions on the fly, although this is usually an example of bad programming.

        var {walkwater = code [[ walk(sea) ]]; };
        ...
        s.walkwater = code [[ walk(ground) ]];

Invoked `code` statements can create objects automatically. They are also “self” variables that target the object that contains them. An `args[]` table holds all the `code` statement's arguments.

    dsc = code [[
        if not self._seen then
            p '{Something} lays on the tabe.';
        else
            p 'There is an {apple} on the table.';
        end
    ]];

NOTE: The `code` statement above is already surrounded with double brackets, so if you need to write a multi-line string literal inside a `code` statement you must use nested brackets such as `[=[ ]=]`, `[==[ ]==]`, `[===[ ]===]`, etc. The same is needed for delineating line breaks with the `^` symbol. Study the Lua syntax rules for more detail.

## Temporary Values

Sometimes you may need to create an auxiliary variable in the `var` table to store a temporary value, for example:

    kitten = obj {
        nam = 'kitten';
        var { state = 1 };  -- state variable

        --(s) refers to the entire kitten object, and
        -- this act handler function is triggered by each click
        act = function(s)
            -- increments the "state" temporary value
            -- by 1 with each click
            s.state = s.state + 1
            -- iterates until it reaches 3
            if s.state > 3 then
                 -- resets it to 1, creating a clickable looping effect
                 s.state = 1
    	end
            p [[Purrr!]]
        end;
        -- this dsc attribute function's table is related
        -- to the handler function above through the index
        dsc = function(s)
            local effects = {
                "The {kitten} is purring.",
                "The {kitten} is playing.",
                "The {kitten} is washing up.",
            };
            -- Now the index corresponding to the
            -- click loop in "act" can be printed to the player's screen
            -- s.state is a numerical index for the
            -- effects table which has 1,2,3 (a Lua index begins at 1)
            p(effects[s.state])
        end;
    }

In the `dsc` function above, a local table is created. The keyword `local` constrains the table's visibility to within the function itself, meaning nothing outside can see or use it. And `local` variables are not written in save files. You should define all auxiliary/temporary variables as `local`.

The example could also be written like this:

    dsc = function(s)
        if s.state == 1 then
            p "The {kitten} is purring."
        elseif s.state == 2 then
            p "The {kitten} is playing."
        else
            p "The {kitten} is washing up.",
        end
    end;

Or like this with an external function:

    function mprint(n, ...)
        -- temporary table for the function arguments
        local a = {...};
        -- prints the nth element of the temp table
        p(a[n])
    end;

Which can be called inside the `dsc` attribute:

    dsc = function(s)
        mprint(s.state, {
            "The {kitten} is purring.",
            "The {kitten} is playing.",
            "The {kitten} is washing up.",
        });
    end;

To simplify it all you could write it like this:

    dsc = function(s)
        p(({
            "The {kitten} is purring.",
            "The {kitten} is playing.",
            "The {kitten} is washing up.",
        })[s.state]);
    end;

## Saving Game Variables

Savegame files store the delta (change) between the initial and current game state. They can store these types of variables:

- string
- boolean
- numerical value
- link to an object
- code statement

There are three ways to create a stored variable.

1. Write the variable name with an underscore character at the beginning (which we saw in the previous section with _seen)
2. Define the variable in a “var” table inside some object
3. Define the variable in a global table

Using `var` and `global` is more intuitive so it's recommended.

Defining the global table is simple:

    global {
        -- a number stored in the savegame file
        gl_var = 1;
        -- another number
        gl_num = 1.2;
        -- a string
        gl_str = 'hello world';
        -- a boolean
        knows_truth = false;
    }

Defining a `var` table inside an object is also simple:

    main = room {
        var {
            -- this will be stored in the savegame file
            i = "a";
            z = "b";
        };
        nam = 'My first room.';
        var {
            -- also stored
            new_var = 3;
        };
        dsc = function(s)
            --(s) refers to main, so s.i refers to
            -- the variable "i" that's housed in
            -- main's var table
            p ("i == ", s.i);
            -- global elements are mapped to the
            -- global namespace. It's as if "global"
            -- and "var" tables are excluded from the
            -- object tree
            p ("gl_var == ", gl_var);
        end;

Every element inside the `var` and `global` tables must have an initial value. A system dummy object called `null` will serve as a default placeholder if you don't define a value. It can be replaced by your game code later.

## Auxiliary Methods/Functions

The game engine has a number of high-level methods that may be useful to you. You've already encountered some of them.

    -- moves the object from the current
    -- or given room to a given destination
    move(what, where_to[, where_from])

If you want to move an object from an arbitrary room you must to know its location. For implementing objects moving in a complicated fashion you could write an advanced function to track the object's location as it moves between distant rooms, or you could locate the object with the `where()` method each time, like so:

    move(mycat, here(), where(mycat))   --mycat travels with me

NOTE: You must handle the moving object with a `place()` method in order for the `where()` parameter to work.

The `movef()` method is similar to `move()` but the target object is sent to the beginning of the destination `obj` list.

The twin methods `drop()/dropf()` and `take()/takef()` act in the same way except they focus on the player's inventory.

- `drop(what[, where])` –removes the object from the player's inventory and places it at the end of the current or optionally given room's `obj` list
- `dropf(what[, where])` –drops it at the beginning of the target room's `obj` list
- `take(what[, where_from])` –removes the object from the current or optionally given room and places it at the end end of the player's inventory
- `takef(what[, where_from])` –adds the object to the beginning of the player's inventory

The four methods above can materialize objects in the target `obj` lists even if the object wasn't present in the source location. This trick is often used for filling the player inventory in the `init` function.

    function init()
         -- this knife doesn't exist anywhere,
         -- it simply materializes in the player's
         -- inventory list. Yay!
    	take('knife');
    end;

The following methods all work in a similar fashion to those above.

- `place(what[, where])` –places the object at the ending of the current (or optionally given) room
- `placef(what[, where])` –places the object at the beginning
- put(what[, where]) –OBSOLETE!
- putf(what[, where]) –OBSOLETE!
- `replace(what, what_with[, where])` –replaces the first object with the second in the current or optionally given room
- `remove(what[, where])` –removes an enabled object from its current location or an optionally given room
- `purge(what[, where_from])` –same as `remove()` but disabled objects may be removed as well

The methods above can be applied directly to rooms and objects as well.

    -- uses the me() pointer to access the
    -- 'pl' object's inventory list
    remove(apple, me())

Some methods above have variations suffixed with to which receive an additional parameter, the specific position for the object to be inserted into the target list.

- `dropto(what[, where], pos)` –since version 2.2.0
- `taketo(what[, where], pos)`
- `placeto(what[, where], pos)`

More methods include:

- `lifeon(object[, priority])` –adds the object to the dynamic “alive” objects list (explained more later). The optional parameter must be a numeric value, with `1` representing the highest priority
- `lifeoff(object)` –removes the object from the alive list
- `taken(object)` –returns true if the object has been taken (with `tak` handler or a `take()` method) and defaults to false
- `rnd(m)` –returns a random integer in the range from `1` to `m`

You will often move the player to different rooms. It's important to mention that calling `walk()` triggers a corresponding `exit/enter/left/entered` handler, which may occasionally cancel the player's movement. Continue reading to learn how to manage this situation when it arises.

Here's the basic format for `walk()` followed by an example:

- `walk(where_to)` –moves the player to the specified room

    .......................................
    act = code [[
        pn "I'm going to the next room..."
            walk(nextroom);
    ]]

Here's an example of passing a function reference to the `walk()` method:

    mycar = obj {
        nam = 'my car',
        dsc = 'In front of the cabin there is my old Toyota {pickup}.',
        act = function(s)
            walk('inmycar');
        end;
    };

NOTE: `walk()` doesn't interrupt the parent handler's execution, so you should typically place your function's return operator immediately after `walk()` like this:

    act = code [[
        pn "I'm going to the next room..."
        walk(nextroom);
        return
    ]]

To change players:

    change_pl(player)
    -- switches the game to the specified player,
    -- who has an independent inventory and location

When changing players the `exit/enter/left/entered` handlers are not triggered.

If you'd like to simulate offscreen movement for an inactive player without having to change players, you can simply change her location using the `where` attribute:

    jane.where = 'Living Room'

Here are even more auxiliary functions:

- `walkback([where_to])` –moves the current player to the previous room, or to a specified room, and the player's `from` property will not be changed
- `back([where_to])` –similar to `walkback()` except when using `back()` to move from a dialogue to a room, the room's `dsc/enter/entered` handlers will not be called, but the dialogue's `exit/left` handlers will be called
- `walkin(where_to)` –moves the player to the specified room, while the current room's `exit/left` handlers are not called
- `walkout()` –moves the player to the previous room, and its `enter/entered` handlers are not called
- `time()` –returns current game time, calculated by the number of player actions performed so far
- `cat(arg1,arg2,arg3,etc…)` –returns a concatenation of its arguments, but returns `nil` if the first argument is `nil`
- `par(arg1,arg2,arg3,etc…)` –returns a concatenation of its arguments, each delimited by the content of the first argument
- `visited([room])` –returns the number of times the current or specified room has been visited, or `nil` if never
- `visits([room])` –similar to `visited()` but returns zero instead of `nil`
- `player_moved([player])` –returns true if the player has moved this game tick, usually used for `life` handlers

In cases where `forcedsc` is incompatible with your intentions you can use the following method to maintain compatibility:

- `stead.need_scene([room])` –makes the engine show the room's static `dsc` during the next game tick
- `stead.nameof(object)` –returns the object's `nam` attribute
- `stead.dispof(object)` –returns the object's `disp` attribute, or `nam` if `disp` is empty
- `disabled(object)` –returns true if the object is disabled
- `stead.call(link, attribute_handler_string_name, parameters)` –calls the handler, or returns the attribute value (this method is explained further later)
- `instead_gamepath()` –returns the full path of the game directory
- `instead_savepath()` –returns the full path of the saved game files directory

### Text Formatting

You can accomplish simple text formatting with the following methods:

- `txtmiddle()` –aligns text at the middle of the screen on both axes (this is the default setting)
- `txtc()` –longitudinally aligns text in a central column on the screen
- `txtr()` –longitudinally aligns text to the right side of the screen
- `txtl()` –longitudinally aligns text to the left side of the screen
- `txttop()` –latitudinally pushes text to the top of the screen
- `txtbottom()` –latitudinally pushes text to the bottom of the screen

For example:

    main = room {
        nam = 'Intro',
        dsc = txtc('Welcome!'),
    };

You can define a special text style with these methods:

- `txtb()` –boldface
- `txtem()` –embossed
- `txtu()` –underlined
- `txtst()` –strikethrough

For example:

    main = room {
        nam = 'Intro',
        -- only boldfaces the word "main"
        dsc = 'You are in the room: '..txtb('main')..'.',
    };

Since `version 1.1.0` you can create unwrapped strings using the `txtnb()` method.

    main = room {
        nam = 'Intro',
        dsc = 'You are in the room '..txtnb('main')..'.',
    };

## Constructors and Inheritance

WARNING: If you're writing your first game you should make it simple, that is to say the information in this section of the manual is not important. Moreover, 90% of the games written for INSTEAD don't use anything in this section! That's not to say it's not a good section.

The idea of constructors should come to mind once your (second/third/tenth) game has a lot of similar objects. You might say to yourself, “I really would love to simplify this code…” Constructors are a method for automating common pieces of code. In fact the `obj`, `room`, and `dlg` handlers are constructors themselves.

When you write something as an `obj` a constructor method calls `obj` as a parameter which passes the table `{nam = 'name'}`.

    apple = obj {
        nam = 'apple';
        dsc = "It's a nice apple.";
    };

Say you need a window in your game. Realizing that real windows can be broken, you can write a constructor that will manifest all windows with this realistic behavior, saving yourself from ever having to code it again.

    -- first create a variable as a function
    window = function (v)
        -- pass itself in as true
        v.window = true
        -- assess whether nam is empty
        if v.nam == nil then
            -- if so, fill it with this generic title
            v.nam = 'window'
        end
        -- assess whether dsc is empty
        if v.dsc == nil then
            -- if so, fill it with this phrase
            v.dsc = 'There is a {window}'
        end
        -- function to define the default act handler
        -- regardless of whether it's empty
        v.act = function (s)
            -- assess whether the act handler's _broken variable is set to true
            if s._broken then
                -- if so display this phrase when the player clicks the window
                p [[broken window.]]
    	else
                p [[dark outside.]]  --otherwise display this
    	end
        end;
        -- assess whether the used handler is empty
        if v.used == nil then
            -- function to autofill the used handler
            v.used = function (s, w)
                -- assess whether the second parameter (parent self?)
                if w == hammer then
                    if s._broken then
                        p [[Window already broken.]]
                    else
                        p [[I broke the window.]]
                        s._broken = true;
                    end
                end
            end;
        end
        return obj (v)
    end;

This constructor fills in some of its attributes and handlers itself, but still allows the player's game and your own extraneous code to override some of them. At the end it calls for the manifestation of the object with finalized parameters and returns the custom window object.

    win1 = window {
        -- overrides only the dsc attribute, while all others auto-fill
        dsc = "In the eastern wall is {window frame}.";
    };

Since windows are usually static objects, you can could put it directly into the `obj` handler for your room instead.

    obj = {
        window {
            dsc = 'In the east wall is a {window frame}.';
        }
    };

If you want to use a more conventional constructor syntax, as a function that takes several parameters instead of a table it's perfectly workable. In fact, `vroom()`, `vobj()`, and `vway()` follow this paradigm.

    window = function (nam, dsc)
        -- creates an empty table inside function
        local v = {}
        v.window = true  -- begins to fill the table
        v.nam = 'window'
        -- checks if the given window being passed in already has a dsc
        if dsc == nil then
            v.dsc = 'There is a {window}.'
        end
        v.act = function (s)
            if s._broken then
                p [[broken window.]]
            else
                p [[dark outside.]]
            end
        end
        v.used = function (s, w)
            if w == hammer then
                if s._broken then
                    p [[Window already broken.]]
                 else
                    p [[I broke the window.]]
                    s._broken = true;
                 end
            end
        end
        -- sends the local window settings out
        -- into the world as a constructed (pre-filled) object
        return obj(v)
    end;

A call to this constructor will look different than the table-based calls.

    obj = {window ('Window', 'In the east wall is {box}.')}

In fact, both approaches are useful in different scenarios. If the constructed object might be assigned new or optional attributes later, it's easier to define the constructor as a function of the host table, the same as `obj`, `room`, and `dlg` are. Otherwise, if the object is sure to be hands-off later, you can use define it as a function itself.

You might need to add new variables to your constructor. In the example above we created the stored variable `_broken` prefixed with an underscore because stored variables can be created on-the-fly. But if you need unstored variables you can use `stead.add_var()` instead. The syntax is shown below.

    stead.add_var(constructor, {variable = value})

Here's the previous example with an unstored variable.

    window = function (v)
        -- adds the "broken" with a value to your constructor
        stead.add_var (v, {broken = false})
        v.window = true
        ...
    end;

If you need to add a `global` variable it can be done on-the-fly just like stored variables.

    -- no need for parentheses since it's only one parameter
    stead.add_var {global_var = 1}

Now that we understand how to build constructors, let's think about the concept of inheritance. It's employed in the examples above, at least it will be since there's no other reason to have constructors. They call another constructor window `obj`, thereby obtaining all the properties of a regular object. Also, window defines a variable attribute window, to the game, we can understand that we are dealing with a window. For example:

    use = function (s, w)
        if w.window then
            p [[I point my flashlight at the window.]]
            return
        end
    end;

To illustrate the mechanism, create a class of objects called `treasure`.

    global {score = 0}
    treasure = function()
        local v = {}
        v.nam = 'treasure'
        v.treasure = true
        v._points = 100
        v.dsc = function (s)
            p ('There are {', stead.dispof (s), '}.')
        end;
        v.inv = function (s)
            p ('same', stead.dispof (s), '.');
        end;
        v.tak = function (s)
            -- Increase the account
            score = score + s.points;
            p [[With trembling hands I took the treasure.]];
        end
        return obj (v)
    end;

Now, based on our `treasure` constructor we can define any specific kind of treasure for our world. How about gold, diamond and a treasure chest?

    gold = function(dsc)
        local v = treasure ();
        v.nam = 'gold';
        v.gold = true;
        v.points = 50;
        v.dsc = dsc;
        return v
    end;
    diamond = function(dsc)
        local v = treasure ();
        v.nam = 'diamond';
        v.diamond = true;
        v.points = 200;
        v.dsc = dsc;
        return v
    end;
    chest = function(dsc)
        local v = treasure ();
        v.nam = 'chest';
        v.chest = true
        v.points = 1000;
        v.dsc = dsc;
        return v
    end;

To put them in the game, just define a variable with them, and as you should be able to tell the inherited aspects from `treasure()` fall into `diamond()`, `gold()`, and `chest()`. Cool huh?

    diamond1 = diamond("I see a glittering {sparkle in the mud}...");
    diamond2 = diamond();  --fills in with the default dsc
    gold1 = gold("In the corner, a bit of yellow {shimmers}.");
    cave = room {
        nam = 'cave';
        obj = {
            'diamond1',
            'gold1',
            chest ("A heavy steel {chest}!")
        };
    }

When writing constructors sometimes you'll want to run a handler or a method from within. Simply use this system method to access it:

    stead.call(object, method/handler, parameters)

You could modify the window constructor you created earlier (example to show syntax, rather than a purposeful modification).

    window = function (nam, dsc, customHandler)
        local v = {} --creates an empty table
        v.window = true  --fills the table
        v.nam = 'window'
        v.newHandler = function(s)
            -- custom event handler that returns a string
            p("It looks to be antique glass.")
        end;
        if dsc == nil then
           v.dsc = [[There's a blurry plate glass {window}]]
        end
        v.act = function(s)
            if s._broken then
                p [[It's broken.]]
            end
            -- calls the custom 'newHandler' and places its result in r
            local r = stead.call(s, 'newHandler')
            if r then
                p(r)
            else
                p [[It's so dark outside.]]
            end
        end;
    ...
    end;

WARNING: The following section is merely to prevent frustrating misunderstandings with the nature of constructors. This is the fact that it's impossible to save objects created on-the-fly without giving them a variable identifier. To do so requires much deeper engine manipulation than should be necessary for the scope of this engine.

For example, you could try to create a custom version of `vway()`, calling it `xway()`. When clicked, an `xway()` object executes `xwalk()`, like so:

    function xway(name, dsc, w)
    -- you can't pass the variable handle itself
        return obj {
            nam = name;
            dsc = dsc;
            act = function (s)
                walk (s.where)
            end;
    	where = w;
         };
    end

When you attempt to implement this in real code it will be impossible to save any object it constructs because there's no variable identifier.

    -- creates an handle-less object
    place(xway('the cave', '{In the cave}', 'cave'));

The engine then won't be able to save the object. This is because generally speaking, INSTEAD is only able to save objects that have identifiers. Objects that only have descriptors are created by explicitly assigning them in a global context such as `(apple = obj {…})` or by creating them within lists such as `obj` and `way` where they're indexed and stored. (Also you can use the inadvisable `new()` system method described below).

Nevertheless, there is a way to store these objects, but it isn't useful for writing games. It's intended for the development of modules and extensions of the engine. If you're an average storytelling game designer, you can safely skip the following explanation. In fact, it's the wish of the creator of INSTEAD that designers never need to deal with the engine on this level.

So, to save a variable in a very unfriendly and non-game-code kind of way you can do this:

    function xway (name, dsc, w)
        return obj {
            nam = name;
            dsc = dsc;
            act = function(s)
                walk (s.where)
            end;
            where = w;
            save = function(self, name, h, need)
                -- self == the current object
                -- name == the intended handle of the variable
                -- h == file descriptor for savegame
                -- need == a sign that it is creating an object,
                -- the save file is to create an object at startup
                local dsc = self.dsc;  --startup
                local w = stead.deref(self.where);
                if need then
                    -- in the case of creation,
                    -- we write the string to call the constructor
                    h: write (stead.string.format(
                        "% s = xway (%s,%s,%s); \ n",
                        name,
                        -- Formation of lines
                        stead.tostring (self.nam),
                        stead.tostring (dsc),
                        stead.tostring (w)));
                end
                stead.savemembers (h, self, name, false);
                -- keep all other variables such as object,
                -- the state of the on / off, etc. false
                -- in last position.
                -- this will mean they'll be transferred to
                -- the save-nested objects as the 'need' parameter
            end
        };
    end;

# Dialogues

Character dialogues are actually room objects of type `dlg` which contain a `phr` object list. There are two types of dialogues: extended and simple. Both share the same behavior, but simple dialogues are deprecated and therefore not recommended for use.

When the player enters a dialogue she will see a list of phrases. When she clicks a phrase it triggers a reaction. By default, clicked phrases become hidden. When all of them have disappeared the dialogue returns the player to the previous room. Often you may want to include permanent phrases like 'End this dialogue.' or 'Ask one more time.' to prevent the dialogue from escaping to the previous room.

Dialogues are entered in the same way as rooms:

    cook = obj {
        nam = 'cook';
        dsc = 'I see a {cook}.';
        act = function()
            return walkin 'cookdlg'
        end;
    };

It's recommended to use `walkin()` instead of `walk()` because the current room's `exit/left` handlers won't be activated. Also, the person we want to talk to is usually in the same room with the player, so we don't want to officially leave.

You can enter a dialogue from another one, implementing hierarchical branches. You can return to the previous branch with a `back()` call. Extended dialogues implement hierarchical branches much better than simple dialogues.

The engine prevents entering a dialogue with no phrases because it will be exited automatically. Take this into account while debugging your games.

NOTE: It's highly recommended to use the `hideinv` handler when implementing dialogue into your game. Dialogues will look better if inventory items aren't affecting phrases, and you will prevent unexpected conversation bugs. Add it by putting this at the top of the `main.lua` file:

    require "hideinv"

Then declare it as true inside your dialogues like this:

    guarddlg = dlg {
        nam = 'guard';
        hideinv = true;
        phr = {
            {...};
            {...};
        };
    }

The most common mistake is incorrectly calling a dialogue from the `inv` handler without hiding the inventory itself from the dialogue. For example, when building a mobile phone inside your game, you would expect the player to click the phone inside her inventory which would trigger a dialogue. As you know from above, escaping dialogues is usually done through a `back()` call, but if the inventory isn't hidden and the player clicks the mobile phone in the inventory one more time, we run into the same dialogue again! The `back()` call will put the player in the previous instance of the `dlg` “room” instead of the actual room she's supposed to be standing in. Of course you can avoid such situations by doing the following:

    phone = obj {
        nam = 'mobile';
        -- when the player clicks on
        -- her mobile phone in her inventory
        inv = function(s)
            if here() ~= phone_dlg then
                -- this line checks if the current room
                -- is the actual room she's in, not the dlg "room"
                -- if she's not in the dlg, it makes her walk into the dlg
                walkin(phone_dlg)
                return
            end
            -- this relates the situation to the player :)
            p "I am already holding the mobile."
        end;
    };

## Extended Syntax

Since `version 1.7.0` a more powerful dialogue syntax has been supported, known as extended dialogues. Unlike the earlier format, now phrases are defined in a phrase table:

    cookdlg = dlg {
        nam = 'in the kitchen';
        hideinv = true;
        entered = [[I notice the round face of the
                  cook under her white hat. Her eyelids are sagging...]];
        phr = {
            { always = true,
                "Some of those greens, please. And beans too.",
                "Mmmmkay."};
            { always = true,
                "Fried potatoes please.",
                "Of course."};
            { always = true,
                "Two bowls of garlic soup.",
                "My favorite..." };
            { always = true, "Something light, please. I've got an ulcer.",
                "No soup for you!" };
            { always = true, "Thank you, I don't want anything.",
                "Get out of the line.",
                [[back()]] };
        };
    };

If the dialogue's `dsc` attribute isn't defined, it will automatically call the last reply from the player's interactions. The player will see it after clicking the room's caption. Because of this pleasing behavior it's better to put any necessary static description of the `dlg` into its `entered` handler, as was done in the above example.

Phrases are written with the following syntax:

    phr = {
        [index or tag=TAG],
        [false if disabled],
        [always = true],
        "Question",
        "Reply",
        [[reaction code]]
    };

Each phrase is presented to the player as its “Question” value. The “Reply” value is displayed after it's been clicked. The phrase then becomes disabled (changing its second value to `false`), and the reaction code is invoked (if present). The reaction code may contain any Lua code.

The game engine provides the following methods to use on phrases:

- `pon(indexes or tags)` – unhides phrases
- `poff(indexes or tags)` – hides phrases
- `prem(indexes or tags)` – removes/blocks phrases, and they CANNOT be re-enabled with `pon()`
- `pseen(indexes or tags)` – returns true if all targeted phrases are visible
- `punseen(indexes or tags)` – returns true if all targeted phrases are hidden

If called with no arguments, these methods are applied to the current phrase, wherever the code is called from.

To manipulate phrases in a different dialogue, you can use the following syntax:

    dialogue:method()

For example, if the `guard_dlg` exists somewhere outside the current room, you can target it like this:

    guard_dlg:pon('show_card')

You will probably find it quite useful at times to disable a phrase initially, then enable it later, like so:

    cookdlg = dlg {
        nam = 'in the kitchen';
        hideinv = true;
        entered = [[I see a fat face of a lady-cook wearing a white hat. She looks tired...]];
        phr = {
            -- this phrase is initially disabled
            { 1, false, always = true, [[I love those!]], [[Everyone does.]] };
            -- once the player finds out there are
            -- french rolls on the shelf the first phrase is enabled
            { [[What's on the shelf?]], [[French rolls.]], [[pon(1)]] };
            { always = true, "Some greens, please.", "Good."};
            { always = true, "Fried potatoes, please!", "Eat now!"};
            { always = true, "Thanks, but I'm not hungry.", "As you wish.", [[back()]] };
        };
    };

If you'll never need to manipulate a certain phrase, you can drop its first field entirely:

        { "Question?", "Reply!" };

To manipulate phrases you can target them by index:

    { 2, "Question?", "Reply!" };

However for complex dialogues, tags are more suitable:

    { tag='exit', "I'm leaving!", [[back()]] };

A tag is simply a string label. As explained earlier, you can pass phrases by index or tag to the `pon/poff/pseen/punseen` methods. You can also assign a tag to an indexed phrase.

NOTE: If multiple phrases have the same tag, the method's action will be applied to all of them.

Also be aware that:

- `pseen()` will return true if at least one of its targeted phrases that has the plural tag is visible
- `punseen()` will return true if at least one of its targeted phrases that has the plural tag is hidden

If a phrase contains `always=true` it won't be automatically hidden after being clicked by the player.

    { tag='exit', always=true, "Ok, I'm leaving!", [[back()]] }

If you want to implement reaction code without returning any text after the player clicks the phrase, you can use one of the following examples:

    -- put "nil" in the Reply field
    { tag='exit', always=true, "Ok, I'm leaving!", nil, [[back()]] }
    -- which will return nil simply omit the Reply field,
    { tag='exit', always=true, "Ok, I'm leaving!", code = [[back()]] }

You can also define questions and replies as functions or code:

    -- this phrase unhides the next
    { tag='exit', code[[p"I'm leaving."]], code[[p"Please stay."; pon'really']] },
    -- this phrase is hidden by default
    { tag='really', false, always=true, "No, I'm really leaving!", function() back() end }

For complex branching dialogues you can group phrases, which essentially removes the need for massively convoluted `pon/poff` crossovers between numerous `dlg` objects. Phrase groups are displayed to the player as a new dialogue screen.

Each phrase group must be separated by a phrase with no reaction code. The simplest implementation is using curly braces `{ }` but you can use anything to separate your groups, even a tag which allows you to target switching between branches, like so:

    --First Phrase Group
    { 'Tell me about the weather.',
      'Does I look like I keep up with the weather?',
      [[psub 'weather']]
    },
    { always=true, [[Goodbye.]], code = [[back()]] },
    -- this is the delimiter, essentially serving as
    -- a targetable nametag leading into the following branch
    { tag = 'weather' },
    -- Second Phrase Group
    { 'Do you know the current temperature?', 'Maybe... 25 Celsius.' },
    { 'What the humidity like?', 'Definitely eighty percent. You can bet on it.' },

Only one group can be visible to the player at a time. Upon entering the sample dialogue above, the player sees two phrases to choose from. The first phrase's code pushes her down to the phrase with the tag `weather`, which is empty, so it basically falls out of the way and the second phrase group takes over. After both questions in the second group are asked, the player is pushed back to the initial branch, where the only visible phrase left is 'Goodbye.'

Branch switching is implemented with the following methods:

- `psub('branch')` –pushes the player into the target branch, or the following sub-group by default, and adds a return behavior, such that after all branch phrases are disabled or `pret()` is invoked (this method is explained later), the player will automagically return to the caller branch. Nifty!
- `pjump('branch')` –makes an unconditional jump to the target branch, or the following sub-group by default, and adds a return behavior like psub() does
- `pstart('branch')` –makes an unconditional jump, and erases the `psub()` call stack, preventing the return behavior

To get the current branch's index use this method:

    dialogue_nam:current()

To get its tag use this:

    dialogue_nam:curtag()

You can apply the two methods above to external dialogues as well, like so:

    shop_dlg:pstart(1)

A branch's active/inactive status as well as the number of visible phrases remaining. Simply use the following methods, both of which accept the index/tag of the leading phrase in the target branch as their argument. If no argument is supplied, the current group is processed:

    -- returns true if the group contains no active phrases
    dialogue_nam:empty([t])
    -- returns the number of visible phrases, 0 if empty
    dialogue_nam:visible([t])

You can get fancy with how branches are displayed to the player by including a Question field in the target, which becomes a static caption for the entire group:

    { 'Tell me about the weather.', code = [[psub'weather']] },
    { always=true, [[Goodbye.]], code = [[back()]] },
    { },
    -- plays the role of branch caption
    { tag = 'weather', 'Okay, what are you interested in?'},
    { 'What is the temperature?', '25 degrees Celsius.' },
    { 'What about the humidity?', '80%.' },

This caption question can also be a function, allowing you to invoke code as branches switch.

    { 'Tell me about the weather.', code = [[psub'weather']] },
    { always=true, [[Goodbye.]], code = [[back()]] },
    { },
    { tag = 'weather', function()
        p 'Ok, what exactly?';
        weather_asked = true;
    end },
    { 'What\'s the temperature?', '25 degrees Celsius...' },
    { 'Do you know the humidity?', '80%!' },

The caption phrase can additionally contain an empty method, which will be called after all phrases in the branch are hidden:

    { 'Tell me about the weather.', code = [[psub'weather']] },
    { always=true, [[Bye!]], code = [[back()]] },
    { },
    { tag = 'weather',
      'What do you?',
       empty = code [[p'Enough talking about the weather!';
       pret()]] },
    { 'Temperature?', '25 C!' },
    { 'Humidity?', '80%' },

Despite being included in the above empty method, the default action for empty is `pret()`. However, if you choose to redefine empty with some other method you must call `pret()` explicitly when needed from then on.

If you want to see a full branching dialogue.. in Russian, check out the following link to the GitHub repository: Example Dialogue

## Deprecated Syntax

WARNING: The following examples utilize deprecated syntax, and are included in this documentation for the sake of potentially helping you sort your way through obsolete code in old games. Some concepts are shared with Extended dialogues, but it's still important to follow the Extended rules for modern development.

Here's a dialogue written in the deprecated syntax:

    food = obj {
        nam = 'meal',
        inv = function (s)
            remove('food', inv());
    	p "I'm eating.";
        end;
    };
    gotfood = function(w)
        take 'food';
        -- this is a savegame stored variable
        food._num = w;
        back();
    end;

    povardlg = dlg {
        nam = 'In the kitchen';
        dsc = [[I notice the round face of the cook under
            a big white hat. She looks really, really tired.]];
        obj = {
            [1] = phr("Some greens, please.", "Enjoy...", [[pon(); gotfood(1);]]),
            [2] = phr("Fried potatoes now!", "Bon appetit, ya filthy animal...",
               [[pon(); gotfood(2);]]),
            [3] = phr("Two bowls of garlic soup", "That's my favorite too!",
               [[pon(); gotfood(3);]]),
            [4] = phr("Something light, please. I've got an ulcer...", "Porridge for you then.",
               [[pon(); gotfood(4);]]),
        };
    };

The player chooses her meal, she receives it and the `nam` is stored in `food._num`, then returns back to the room where she began the dialogue. Reactions can contain any Lua code, but usually it's phrase management logic.

NOTE: The `pon/poff/prem/pseen/punseen` methods only work with indexes here. Deprecated dialogues CANNOT employ tags.

To pass from one deprecated dialogue to another, you would hide phrases while initializing the dialogue then unhide them later through the conditional `_phr` variable and `pon/poff/prem` methods, like so:

    facectrl = dlg {
        nam = 'face control';
        dsc = 'I see the unpleasant and unfriendly face of the fat security guy.';
        obj = {
            [1] = phr("I've come to listen to the lecture of Belin...",
                [["I don't know you, -- the guard grins
                -- and I was told to only let decent people in."]],
                [[pon(2);]]),
            [2] = _phr("I have the invitation right here!",
                [["I see. Now look at that mirror there.
                I suppose you may not have one in your home.
                You've come to listen to Belin. Be-lin!
                The right hand of... - the guard pauses for a second -
                get out of here!"]],
                [[pon(3,4)]]),
            [3] = _phr("I'm gonna kick you in your fat face!",
                [["Well, let's see it." - powerful hands push me
                into the corridor, but I feel lucky to remain in one piece...]],
                [[poff(4)]]),
            [4] = _phr("You boar! I told you I have an invitation!",
                [["Do you?" - the guard's eyes turn red -
                a hard knock sends me out - it could be worse...]],
                [[poff(3)]]),
        };
        exit = function(s,w)
            s:pon(1);
        end;
    };

NOTE: Again, do not write dialogues like this! Extended dialogues are much easier and better.

For style/aesthetic purposes you can define the prefix placed in front of every phrase, which is its numerical index by default:

    stead.phrase_prefix = '--'
    stead.phrase_prefix = '+'
    stead.phrase_prefix = ':)'

Each of these causes all phrases to be prefixed by the given string instead of their index number. This constant (stead.phrase_prefix) is not variable and so it must be defined early in game. Or you can set it in `init()` function.

NOTE: The string value isn't stored in the player's savegame file, so the game has to define it explicitly for each playthrough. Be aware of this.

# Extra Features

## Graphics

The game's graphic interpreter (the part that displays things onscreen) will treat a room's `pic` attribute as a path to an image that should be displayed in the viewer.

    home = room {
        pic = 'gfx/home.png',
        nam = 'at home',
        dsc = "I'm at home",
    };

Of course, `pic` can also be a function. If the current room has no `pic` attribute defined, the `game.pic` attribute is assessed instead. If it's also undefined, no image will be displayed.

From `version 0.9.2` you can use animated gif files, and graphics can be embedded everywhere, including within the text itself and inside the inventory panel useing the `img()` method.

    knife = obj {
        -- the nam will be a concatenation of the two
        nam = 'Knife'..img('img/knife.png'),
    }

In the current version you're free to use the `disp` attribute instead of the `nam` attribute.

    knife = obj {
        nam = 'Knife';
        ...
        disp = 'Knife'..img('img/knife.png'),
    }

Starting with `version 1.3.0` text flow around images is supported. Use the `imgl()` and `imgr()` methods, which insert the image at the left or right border respectively. To add open space around the image use the `pad:` prefix.

NOTE: The text flow images (imgl and imgr) cannot be a link.

Notice the abbreviated versions below and how they affect more than one side.

    -- the image is padded on top 0px, right 16px, bottom 16px, left 4px
    imgl('pad:0 16 16 4, picture.png')

    -- the image is padded on top 0px, right 16px, bottom 0px, left 16px
    imgr('pad:0 16, picture.png')

    -- the image is padded on all sides with 16px
    imgl('pad:16, picture.png')

A clever use of the `img()` method is to create blank areas and border boxes.

    dsc = img 'blank:32x32'..[[Line with blank image.]];
    dsc = img 'box:32x32,red,128'..[[Line with red semi-transparent square.]];

Starting with `version 1.0.0` the interpreter can compose images from a base image and an overlay.

    pic = 'gfx/mycat.png;gfx/milk.png@120,25;gfx/fish.png@32,32'

## Sound and Music

The interpreter cycles music that's been called with the `set_music()` method, which is often implemented in the `enter` handler.

    street = room {
        pic = 'gfx/street.png',
        enter = function()
            set_music('mus/rain.ogg');
        end,
        nam = 'on the street',
        dsc = 'It is raining outside.',
    };

The `get_music()` method returns the name of the current track.

Starting with `version 0.7.7` the `set_music()` function can receive an additional parameter for the number of loops you wish it to play.

You can ask for the current loop position with the `get_music_loop()` method. If -1 is returned it means the current track is finished looping.

From `version 0.9.2` the `set_sound()` method will play a sound file.

The `get_sound()` method returns the filename of the sound that's queued to be played.

Starting with `version 1.0.0` you can simply call `stop_music()` to end the track being played.

From `version 1.0.0` you can use the `is_music()` method to check if music is playing or not.

## Themes

The SDL version's graphic interpreter has a fancy theme subsystem. It accesses your game's `theme` directory which must house a `theme.ini` file. It must also include a `default` theme. This is always the first to load. All other themes inherit from it and can partially or completely override its parameters.

Themes can be selected by the player in the settings menu, but your game can initially inject its own theme which will override all others by as much as you choose. To do this, place a duplicate of the `theme.ini` file within the game directory, where `main.lua` resides. The player can always override your theme if she wants. If she does, the interpreter will issue a warning that she's overruling the godlike developer's creative intentions. ;)

You can include comments with tags inside the theme header. Currently there's only one tag available. Here's a sample theme to show the basic format to follow:

    ; $Name:New theme$
    ; modified "book" theme
    include = book
    scr.gfx.h = 500

The interpreter searches for the player's own themes in her installation's `themes` directory. The Unix version also checks `~/.instead/themes/` and since `version 0.8.7` the Windows version checks `Documents and Settings/USER/Local Settings/Application Data/instead/themes`

The `theme.ini` file has a very simple syntax:

    <parameter> = <value>; comment

A value can be a string, a number, or a color. Certain colors can be called with a `string`, such as `yellow`, `green`, and `violet`, but other colors must be written in `#RGB` format, where `R`, `G`, and `B` are replaced with hexadecimal values.

Parameters

`scr.w` –game window width in pixels

`scr.h` –game window height in pixels

`scr.col.bg` –background color of the entire game window

`scr.gfx.bg` –directory path to the static background picture, gifs are not enabled

`scr.gfx.mode` –sets the layout mode for room pictures as float, embedded, or fixed

- `float` – the picture will be centered within `scr.gfx.x`, `scr.gfx.y` and downscaled to fit inside `scr.gfx.w`, `scr.gfx.h`
- `embedded` – the picture is made part of the main story panel, and `scr.gfx.x`, `scr.gfx.y`, and `scr.gfx.w` are ignored so that it can scroll with the text
- `fixed` – same as embedded, except it doesn't scroll with the text

`scr.gfx.x`, `scr.gfx.y`, `scr.gfx.w`, `scr.gfx.h` –X/Y coordinates, width, and height of room pictures, adjusted by layout mode

`scr.gfx.scalable = [0|1|2|4|5|6]`

- 0 - Unscalable
- 1 - Scalable
- 2 - Fold-Scalable

Added in `Version 2.2.0`

- 4 - Fully Scalable (with Unscalable Fonts)
- 5 - Scalable, with Unscalable Fonts
- 6 - Fold-Scalable, with Unscalable Fonts

`win.gfx.h` –synonymous with `scr.gfx.h` (for compatibility)

`win.x`, `win.y`, `win.w`, `win.h` –X/Y coordinates, width, and height of the main text area only, excluding the scrollbar width, and the text will be pushed by a fixed or embedded room picture

`win.fnt.name` –path to a font file

`win.fnt.size` –font size for the main text area

`win.fnt.height` –line height for the main text area, as a float number, 1.0 by default

`win.align = left/center/right/justify` – alignment of text in the story panel's text area

`win.gfx.up`, `win.gfx.down` –paths to the pictures of up/down scroll handles for the main story panel

`scr.gfx.pad` –sets padding for all scrollbars and menu edges

`win.up.x`, `win.up.y`, `win.down.x`, `win.down.y` –coordinates for scroll handles, literal position or -1 for invisible

`win.col.fg` –font color for the main story panel

`win.col.link` –color of clickable words in the main story panel

`win.col.alink` –hover-over color for clickable words in the main story panel

`win.scroll.mode = [0|1|2|3]` – the scrolling area on the scene

- 0 - No auto-scroll
- 1 - Scroll to change the text only
- 2 - Only scroll if area not visible
- 3 - Always in the end

`inv.x`, `inv.y`, `inv.w`, `inv.h` –X/Y coordinates, width, and height of the inventory panel

`inv.mode` –`horizontal` or `vertical` inventory stacking mode –in vertical mode only 1 object fits per row, in horizontal multiple objects can fit –you must reposition and resize the panel to make good use of `horizontal` mode

`inv.col.fg` –text color for the inventory panel

`inv.col.link` –color for clickable words inventory panel

`inv.col.alink` –hover-over color for clickable words in the inventory panel

`inv.fnt.name` –path to a font file for the inventory panel

`inv.fnt.size` –font size for the inventory panel

`inv.fnt.height` –line height for the inventory panel, as a float number, 1.0 by default

`inv.gfx.up`, `inv.gfx.down` –paths to the pictures for the inventory panel's up/down scroll handles

`inv.up.x`, `inv.up.y`, `inv.down.x`, `inv.down.y` –coordinates of scroll handles, literal position or -1 for invisible

`menu.col.bg` –background color for menus

`menu.col.fg` –text color for menus

`menu.col.link` –color for clickable menu items

`menu.col.alink` –hover-over color for clickable menu items

`menu.col.alpha` –transparency for menus as an alpha value, from 0-255

`menu.col.border` –border color for menus

`menu.bw` –border width for menus

`menu.fnt.name` –paths to font files for menus

`menu.fnt.size` –font size for menus

`menu.fnt.height` –line height for menus, as a float number, 1.0 by default

`menu.gfx.button` –path to the menu icon picture file

`menu.button.x`, `menu.button.y` –coordinates for the button location on the main screen

`snd.click` –path to a click sound file

`include` –path of a theme file to serve as filler for missing parameters, no extension or = sign needed

For example, this will build your custom parameters over the Book theme that comes included with Instead:

    include book

The following parameters have been available since `version 0.8.9` of the engine:

`scr.gfx.cursor.x` –X coordinate of the center of the cursor

`scr.gfx.cursor.y` –Y coordinate of the center of the cursor

`scr.gfx.cursor.normal` –directory path to the cursor's picture file

`scr.gfx.cursor.use` –path to a picture file for the cursor's `use` indicator

`scr.gfx.use` –path to a picture file for the room's `use` indicator

## Extending The Engine With Modules

Starting with `version 1.2.0` you can employ feature extension modules via the `require` method. Modules must be manually added to your `main.lua` file, usually near the top.

    ...
    require "para"
    require "dbg"

These are the currently available modules:

- `dash` — prints middle dash instead of a normal one
- `hotkeys` — you can set hotkeys
- `quotes` — prints curly quotes (« and ») instead of boring ones
- `dbg` –enables the debugging module (F7), which outputs to an external console
- `hideinv` –hides inventory interactions from clicks inside the story text area
- `walk` –enables an improved implementation of passages
- `xact` –permits multiple references to objects, improving hotlinks
- `input` –enables keyboard input, allowing you to implement simple text entry fields
- `kbd` –not as low-level as the `input` module
- `timer` –provides a timer
- `click` –enables mouse clicks on images to be captured
- `vars` –enables definition of variables
- `prefs` –enables savegame preferences and achievements
- `snapshots` –enables snapshots
- `sprites` –enables sprites
- `format` –allows you to format output; by default all settings are disabled
- `sound`
- `object` –enables improved objects
- `theme` –enables theme manipulation on-the-fly
- `para` –adds indentation to paragraphs

If the engine is higher than `version 1.2.0` the 'vars', `object`, and `walk` modules are automatically activated.

To illustrate the use of modules in code, let's take a look at the `prefs` module. A special object variable called `counter` is part of this engine extension. It can store game variables such as player progress or number of attempts.

    require "prefs"
    ...
    prefs.counter = 0  --number of times the player has attempted a room
    ...
    exit = function(s)
        -- the number of exits is incremented
        prefs.counter = prefs.counter + 1
        -- saves the counter inside the prefs object
        prefs:store()
    end;
    ...
    enter = function(s)
        -- retrieves the counter and displays it
        return 'You passed the game '..prefs.counter..' times';
    end;

    ...

    act = function(s)
        -- clears the prefs object
        prefs:purge()
        return "Preferences has been cleared"
    end;

## Real-Time Keyboard Input

WARNING: The following examples utilize deprecated syntax, and are included in this documentation for the sake of potentially helping you sort your way through obsolete code in old games. Please, use module `kbd` to handle keyboard. Also, there is a module `keyboard` to make possible the player text input.

Since `version 1.1.0` the SDL version has supported real-time keyboard input. This can be activated via the `input` object.

    input.key(s, pressed, key)

The first argument references the keyboard handler's self. The second argument accesses the engine's press and release events. The third argument receives the name of the specific key being activated.

The input object's `key` handler can also return an engine interface command, in which case the interpreter won't handle it, which is useful for behind-the-scenes effects. For example:

    input.key = function(s, pr, key)
        if not pr or key == "escape" then  --checks if the Escape key was activated
            return  --exits the current typing area??
        elseif key == 'space' then  --checks if the Spacebar was activated
            key = ' '   --outputs an empty space through the key handler
        elseif key == 'return' then  --checks if the Enter key was activated
            key = '^';  --outputs a line break through the key handler
        end
        if key:len() > 1 then   --checks if the
            return
        end
        main._txt = main._txt:gsub('_$','');
        main._txt = main._txt..key..'_';
        return "look";
    end;
    main = room {
        _txt = '_',
        forcedsc = true,
        nam = 'Keyboard',
        dsc = function(s)
            return 'Example: '..tostring(s._txt);
        end;
    };

## Real-Time Mouse Input

You may use `click` module to handle mouse click events. Module will call here().click or game.click method with coordinates (x, y) of click in parameters. 0,0 is the left top corner. You can get even background clicks, just define:

    click.bg = true;

So, the method will called in this case with those parameters:

    game.click(s, x, y, px, py)

Where x, y is the coordinates of whole window and px,py - coordinates in image (if image was clicked).

If you need to get press and release events, you may define:

    click.press = true;

In such case the parameters are:

    game.click(s, press, x, y, px, py)

Where press is boolean.

If you need to get button number, please, define:

    click.button = true

And get the button number as the 3d parameter.

Here is the example of the module usage:

    -- $Name: Tets module -- click$
    -- $Version: 0.1$
    -- $Author: instead$

    instead_version "1.8.0"

    -- use module
    require "click"

    -- define game.click
    game.click = function(s, x, y) -- this is global method,
    -- will called if not here().click defined
        p ("You are clicked at: ", x, ", ", y);
    end

    main = room {   nam = 'Forest',
        forcedsc = true,
        pic = 'house.png',
        dsc = [[ You are seeing a house. Door is open. ]],
        -- define own click method in this scene
        click = function(s, x, y)
            -- is this the door area?
            if x > 80 and x < 200 and y > 225 and y < 325 then
                walk('house');
            else
                return 'This is not the door.';
            end;
        end,
    };

    house = room {  nam = 'Дом',
        forcedsc = true,
        pic = 'door.png',
        dsc = [[ You are inside the house.]],
    };

# Neat Ideas/Examples

## In-Game Walkman

To implement a personal music device for the player to control you must create it as an “alive” object. First create a tracklist in the `tracks` handler.

    --might be an attribute... not sure
    tracks = {"mus/astro2.mod", "mus/aws_chas.xm", "mus/dmageofd.xm", "mus/doomsday.s3m"}

Then create a living, breathing Walkman object to entertain your players. ;)

    mplayer = obj {
    	nam = 'media player',
    	life = function(s)
    			local n = get_music();
    			local v = get_music_loop();
    			if not n or not v then
    				set_music(tracks[2], 1);
    			elseif v == -1 then
    				local n = get_music();
    				while get_music() == n do
    					n = tracks[rnd(4)]
    				end
    			set_music(n, 1);
    			end
    		end;
    	};
    lifeon('mplayer');

You can even use `get_music_loop()` and `get_music()` to remember the last track and let the player restore it.

    function save_music(s)
    		s._oldMusic = get_music();
    		s._oldMusicLoop = get_music_loop();
    	end;
    function restore_music(s)
    		set_music(s._oldMusic, s._oldMusicLoop);
    	end;
    ...
    enter = function(s)
    		save_music(s);
    	end;
    exit = function(s)
    		restore_music(s);
    	end;
    ...

Since `version 0.8.5` the `save_music()` and `restore_music()` methods have been permanently included in the game library.

## Teleportation Hack

If your player lost their horse or they need something else to appear next to them, one way to materialize that object is to implement the `lifeon()` method as a teleporter, controlled by the object's `life` handler. This will materialize the object at the player's current location, technically just bringing it to life again. But you get the idea.

    horse = obj {
    	nam = 'horse',
    	dsc = 'A {horse} is next to me.',
    	life = function(s)
    			if not seen('horse') then
    				move('horse', here(), s.__where);
    				s.__where = pl.where;
    			end
    		end,
    };
    function init()
    		lifeon('horse');
    	end;

## Custom Menus Within Items

Menus are a great feature to add to your world. You can add them to an object by incorporating the following `menu` constructor into your code. It's activated by the player with a single mouse click. If it has no return string, the state of game will not change. For example, here's a simple implementation of a pocket housed inside the inventory.

    pocket = menu {
        var { state = false };
        nam = function(s)
            if s.state then
                return txtu('pocket');
            end
            return 'pocket';
        end;
        gen = function(s)
          -- this is our custom function -- pocket generator
            if s.state then
                s:enable_all();
            else
                s:disable_all();
            end
        end;
        menu = function(s)
            s.state = not s.state
    	s:gen(); -- generate pocket
        end;
    };
    knife = obj {
    	nam = 'knife',
    	inv = 'This is knife',
    };
    function init()
        inv():add(pocket);
        place(knife, pocket);
        pocket:gen();
    end;
    main = room {
        nam = 'test',
    };

Another cool implementation of menus is to place an unclickable text readout of the player's status within the inventory panel.

    global {
    	life = 10;
    	power = 10;
    }
    status = stat { -- create status object
        nam = 'my status';
        disp = function(s)
            p ('Life: ', life, 'Power: ', power)
        end;
    };
    function init()
        take 'status';
    end;

# Preparing Your Game For Release

## Splitting Your Game Into Files

Split your game into multiple files to make it easier to manage. You can use the `dofile()` method to insert your separated source code files into the game. You must use `dofile()` in a global context, so load all of them while parsing `main.lua` at the opening of the game.

    ...somewhere inside main.lua...
    dofile "episode1.lua"
    dofile "npc.lau"
    dofile "start.lua"

Dynamically including files gives you the ability to redefine objects and rooms as the game progresses. Nifty! Just use the `gamefile()` method.

    act = code [[ gamefile("episode2.lua"); ]]

You can also clear the game stack of old files, leaving you with a brand new game without the player needing to load anything herself. This is quite useful for multi-part stories where locations need to be revisited in a brand new light. Just put `true` as a second parameter for the `gamefile()` method.

    act = code [[ gamefile("episode3.lua", true); ]]

## Encoding Your Game's Source

Since `version 0.9.3`, if you want to hide your source code you can encode it from the command line as follows:

    sdl-instead -encode <lua file> [encoded file]

Then to load your encoded file from Lua use:

    doencfile()

It's necessary to keep `main.lua` as a plain text file for this, so the recommended scheme is:

    game is a encoded game.lua ):
    main.lua
    -- $Name: My closed source game!$
    doencfile("game");

WARNING: Do NOT use the luac compiler for encoding, as it produces platform-dependent code! For regular game compilation it's quite useful for hunting down bugs, but not for encoding.

## Packaging Your Game

Since `version 1.4.0` you're able to package all your game's resources including graphics, sounds, themes, etc., into one fancy `.idf` file. Just put your resource directories all into a single directory called `data` and from the command line run:

    instead -idf <path_to_your_parent_data_directory>

A file called `data.idf` will be created. Put this into your game's top level directory along with the code files and remove the original resource files.

You can also pack your entire game into one `.idf` file like so:

    instead -idf <path_to_game_directory>

A game stored in `.idf` format can be run like any other game within INSTEAD, or straight from the command line with:

    instead game.idf

# Appendix

## STEAD Interface Commands

## Pre-Defined Methods

## Pre-Defined Objects

# Credits

Translation from Russian by Vopros

English Localization and Technical Editing by Ryan Joseph