A-code undo/redo facility

If the game defines UNDO as a verb, then the undo/redo A-code mechanism gets activated for that game. The REDO verb is then defined automatically, though it can be also defined by the game explicitly as a verb. In such circumstances, defining REDO as anything other than a verb is treated as an error. REDO can be used immediately after an UNDO command, to undo some or all of the UNDO.

The general form of UNDO and REDO commands is as follows:

verb UNDO [{<number>|ALL|UNDO}]
verb REDO [{<number>|ALL}]

The default number of turns to undo or redo is one, though a specific number can be specified. ALL means just that – undo all collected turn history or undo all of the preceding UNDO. "UNDO UNDO" is equivalent to REDO ALL.

Information on the effects of an UNDO/REDO command is returned by an automatic variable UNDO.STATUS, which may but need not be explicitly defined by the game's code. The variable is considered to have four automatically declared flags:

This flag is defined but not used by the kernel. It may be used by the game's code e.g. to enable or disable use of UNDO and REDO commands.

Set if requested number of turns has been trimmed. The value of UNDO.STATUS is set to the actual number of turns undone or redone.

Set if inventory contents changed, so that the game can note the fact. There is no equivalent flag for change of location, because that can be checked by the game's code by preserving the HERE value in a local variable and then it with the value of HERE after the UNDO/REDO.

Set if the UNDO/REDO is given an illegal argument.

Undo history is saved and restored as a part of game saving and restoring. However, should the game's number of objects, locations or global variables change, the undo history of games saved by an earlier version will be quietly ignored.

Here is a simple example of using UNDO:

action undo
  local uhere
  set uhere, here       # Preserve value of HERE in a local variable
  undo arg2             # Do the UNDO!
  ifgt undo.status, 0   # Something got undone
    ifflag undo.status, undo.trim
      say "Cannot undo that many turns!"
    say "Turns undone: $\n.", undo.status
    ifne here, uhere
      say "You have relocated!"
    ifflag undo.status, undo.inv
      say "Your possessions have changed!"
  else                  # Nothing undone
    quip "Nothing happens."

Back to the documentation index
To the Mipmip home page
Feel free to leave a comment!
Mike Arnautov (27 March 2023)