Introduction to Commands - ThePix/QuestJS GitHub Wiki

QuestJS is designed for parser-based games, and therefore the handling of commands is a fundamental part of the game. Even if you turn text input off, in the background the side pane or hyperlinks are still sending commands through the same system.

The Parser

When the user types a command, the text is passed to the parser to deal with. This can be found in lib/_parser.js.

The parser does some normalisation of the input text, and will then select the best command for the text by asking each command to look at the string and assign itself a score, and at the same time try to match items to the words. The command with the highest score gets selected - this is the command that best matches the text, it still may not work, but the command will decide that later.

Once it has a preferred command, it will "disambiguate" if necessary - ask the user to pick between items when the input text was ambiguous - and then run the "script" function attribute of that command, passing the list of items the command found earlier.

Commands are held in a list commands, which is set up in lib/_commands.js, but authors can also add their own custom commands.

The real work is therefore done in the commands when they assign a score and match items. This is done in a function called "matchItems", which is added automatically to every command without you doing anything. However, it does use other attributes, "regex" and "objects", that you do need to set yourself.

There is more about the parser here.

The "script" function

The script function is where the command's response is, and we can use it to do literally anything in the game world.

At this point the parser has determined what the user wants to do. The script has to first decide if that is permitted, and then, if it is, to do it.

Most scripts will start, therefore, by checking if the items the user typed are applicable. If the user typed GET HAT, and the player already has the hat, then the command is not applicable. The script function should give a message saying why and return a special value world.FAILED to let Quest know the command ended in failure. The command might also check for game state; if the player types SMASH WINDOW, and the window is already broken, again a message should be given and world.FAILED returned.

The easiest way to do this is using msgfailed, allowing you to give a message and return in one go.

  if (w.hat.loc === player.name) return failedmsg("You already have the hat!")

Once everything has been checked, the script function can make any changes to the game world (move the hat to the player, set the "broken" flag on the window). It should also tell the user what has happened, as far as the player can see.

Finally, the script function should return world.SUCCESS. This will let Quest know that time has passed in the game world and that the game world has potentially changed. Quest will run any applicable game scripts, then update the world, and finally will update the user interface (specifically the side pane).

Read More

This page takes you through how to create a simple command (if you did the tutorial, you have already seen it), whilst this page takes you through creating a considerably more complex command, in a stepwise approach. For more general instructions, see here.

To learn how a command is matched, and why one is chosen and another not, see Command matching.

There is a note on what value a command should return here, and notes about meta-commands here (meta-commands are commands about the game system, rather than the game world).

A shortcut for creating simple commands can be found here. On the other hand, for more complex commands, you might want to see the various note on this page. If you are modifying an existing command, see here.

Your command's response text (and indeed all text) should ideally be able to handle different pronouns - that is, if the player tries to pick up a man, a table or some sand, the response should not be "you cannot pick it up" every time. To learn about neutral language, see here.

In some situations, for example CLIMB, an alternative is to create a new direction, see here.