Custom Text Processor Directives - ThePix/QuestJS GitHub Wiki

You can add your own text processor directives using the tp.addDirective function. This needs a name and a function. The function should take a string array as a parameter (the input text, split on colons) and the parameters you passed to msg, and return a string.

Here is an example:

  tp.addDirective("fancy", function(arr, params) {
    return '<span style="font-family:Montserrat">' + arr.join(":") + "</span>"; 
  });

Note that the parameter arr is joined with colons, as this is how it was broken up. You may want to use the first one to set a value, as in this example:

  tp.addDirective("fancy2", function(arr, params) {
    const font = arr.shift();
    return '<span style="font-family:' + font + '">' + arr.join(":") + "</span>"; 
  });

This example looks at an attribute on the player; if true, the second section is shown, otherwise the third is.

tp.addDirective("lore", function(arr, params) {
  return player.status === 'Lore' ? arr[0] : arr[1]
});

This example is similar, but calls a function.

tp.addDirective("cloakHere", function(arr, params) {
  return cloakHere() ? arr[0] : arr[1]
});

You can use this to do anything. It could just insert a standard piece of text, similar to a macro. This is currently the way to do the equivalent of "eval" in the Quest 5 text processor (JavaScript can handle eval but it is considered insecure, so I am trying to avoid it).

  tp.addDirective("title", function(arr, params) {
    return settings.title; 
  });

Custom directives offer a way to keep location and item descriptions as strings, but still dynamic. The "examine" attribute could then be as simple as:

  examine:"The hourglass has two connected glass bulbs.{hourglass}"

All the complicated stuff, in this case how much time has passed in effect, is done in the text processor directive.

tp.addDirective("hourglass", function(arr, params) {
  return "The upper bulb is about " + Math.round(this.state) + "% full."
}

Whether this is actually easier is debatable...

Extended "once"

The standard text processor has a "once" command that ensures a section of text is only seen one time, but is limited to be used in just one string. What if you want the text to be only seen once, but it could be embedded in several strings? Let us suppose a section of your game has some introductory text, but the player might first arrive in any of four different locations. One way to handle this is with a custom directive.

Here is an example. We need to save a flag on one of the rooms, it does not matter which. If the flag is already true, just return an empty string. Otherwise, set the flag, and return the introductory text.

tp.addDirective("greenhouseIntro", function(arr, params) {
  if (w.greenhouse_west.seenFlag) return ''
  w.greenhouse_west.seenFlag = true
  return 'Just for a moment, you think you are outside - all you can see is trees, bushes and plants. But no, above there is a roof, and walls can be seen all around you; this is a greenhouse. '
})

Each description then needs the directive at the start:

  desc:"{greenhouseIntro}You are stood on a catwalk that skirts the north side of the great greenhouse. Even from here, the huge oak tree towers over you.",

It is bad practice to put anything important in text that will only be seen once, as users can miss it, and then have no opportunity to see it again.

Honorifics

Here is a "title" text processor that will give the contents of the NPC's "title attribute, or just "Mr" of "Ms" if not set. It illustrates how to use paramters, using the in-built "_findObject" function. It also tests that the found object is an NPC.

tp.addDirective("title", function(arr, params) {
  const npc = tp._findObject(arr[0], params, arr)
  if (!npc) errormsg("Failed to find object '" + name + "' in text processor 'title' (" + params.tpOriginalString + ")")
  if (npc.title) return npc.title
  return npc.isFemale ? 'Ms' : 'Mr'
})

We can use a text processor inside a text processor! This example gives the title and the name, using the above function and the built-in "nameFunction".

tp.text_processors.tnm = function(arr, params) {
 return tp.text_processors.title(arr, params) + ' ' + tp.nameFunction(arr, params, false) 
}

The parameters

In addition to any parameters you send, params will also contain:

  • tpOriginalString: The original string
  • tpFirstTime: Will be true the first time this string has been done.
⚠️ **GitHub.com Fallback** ⚠️