1
Developer's documentation, appendix A: Results
	Matti Niemenmaa, 2007-11-05

1
This is the first appendix in the developer documentation, explaining how
results work and can be written. Like all developer documentation, this is
meant to be read in order, which is why keywords like "part-1" are provided,
but a text editor is best.

2
10
___Part-1___
A *result* is simply a *boolean expression* followed by a number of
*consequences*. The precise syntax is as follows (whitespace is ignored):

boolean expression {
message
[consequence;]
}

Where:
- boolean expression is as explained below,
- message is a string delimited by quotation marks: note that escape characters
  are not parsed: you cannot have a message contain a quotation mark,
- consequence is any of those listed in _part-2_ (unless explicitly disallowed
  in the result type: see spell and entity documentation for details of what is
  allowed).

A boolean expression is an expression written in prefix notation, with strings
as operands and the logical operators & (and), | (or), and ! (not) as
operators. The strings represent spell names.

An example expression is of the form (& A | B ! C), which may be more clearly
written as (& A (| B !C)): true if spell A is cast, and either spell B is cast
or spell C is not cast.

As you may have noticed from the example above, brackets are completely
superfluous, but may be wrapped around sub-expressions at will. The entire
expression must always be enclosed in brackets, however.

A substitute for an expression is the expression (default), which is always
true. Most, but not all, results require that a default expression is provided.

The complete grammar for a boolean expression can be expressed suchly in an
EBNF:

wholething    :: "(" bool-expr ")"
               | "(default)"
bool-expr     :: spell-name
               | operator-expr
operator-expr :: and-expr
               | or-expr
               | not-expr
&-expr        :: "&" sub-expr sub-expr
|-expr        :: "|" sub-expr sub-expr
!-expr        :: "!" sub-expr
sub-expr      :: bool-expr
               | "(" operator-expr ")"

Results are always checked in the order in which they are written. If the first
result has a boolean expression of (default), the other cases will never occur.

2
___Part-2___
A *consequence* is always followed by a semicolon in the result. What follows
is a complete list of possible consequences, with the meaning explained after a
hyphen:
- fail          - if spell, don't place effect; if motion, assume default state
- counter <str> - counter the spell <str>
- active <str>  - spell only: while active, display the message <str>
- expire <str>  - spell only: when expires, display the message <str>
- sanity <byte> - modify player's sanity by <byte>
- leave         - motion only: remove entity
- gameover      - end game if player is in the same room
- realgameover  - end game always

<str> indicates that the consequence must be followed by a string, for instance
'counter "foo";', and <byte> indicates that the consequence must be followed by
an integer in the interval [-128, 128).
