Advanced RMS: Part 4 – Functions

By Matei of Woad Creations
created DAT9/10/03E

Often you have a piece of code that you want to use several times, perhaps with slightly different parameters. For example, you might use some code to add a “send chat” trigger in various places in your script. To do this, you can define a function, which can be called later in the script and can be passed arguments to work with or can return a result value to wherever it was called.

A function definition is of form:

<returnType> <name> ( <arg1Type> <arg1Name> = <defaultValue>, <arg2Type> <arg2Name> = <defaultValue>, … ) {
      <code>
      [ return ( <returnValue> ) ; ]
}

To call a function, use [ <variable> = ] <name> ( <arg1Value>, <arg2Value>, … );. If the function has no arguments, keep the brackets after the name but put nothing between them.

A function’s return type of the function can be void, meaning that the function doesn’t give any value back to whatever code called it, or it can be one of the variable types discussed above. If you have a non-void return type, you should have one or more return() statements so that your function returns a valid value of that type. Having no return statements for a non-void function will cause an error.

Functions can have a number of arguments, or none. Note that sometimes functions seem not to work if they have more than 8 or so arguments. If a function has no arguments, used void in the brackets after its name instead of a list of arguments. If it does have arguments, they act as local variables in that function. If a function with, say, 3 arguments is called with fewer than it has (for example, 2 only), then the first arguments specified are given the values passed, and the others are kept at their default values. This is often a useful feature.

Here is an example of several functions and how to call them:

// this function makes a message appear every few seconds to the players, using a trigger
void addMessage(string text="", int repeatTime=120) {
    id = rmCreateTrigger("message"+rmRandInt());
    // make a (random and hopefully unique) trigger name
    rmSwitchToTrigger(id);
    rmSetTriggerLoop(true);
    rmAddTriggerCondition("Timer");
    rmSetTriggerConditionParamInt("Param1", repeatTime, false);
    rmAddTriggerEffect("Message");
    rmSetTriggerEffectParamInt("Timeout", 12000, false); // message should fade after 12 seconds
    rmSetTriggerEffectParam("Text", text, false);
}

// this function returns the absolute value, |f|, of a real number f
float abs(float f=0.0) {
    if(f<0) {
        return(0-f);
    }
    else {
        return(f);
    }
}

void main(void) {
    addMessage("This map uses functions!", 70);     // makes this message appears every 70 seconds
    addMessage("Isn't it great?");                  // appears every 120 seconds (default value)
    addMessage("The absolute value of -3 is "+abs(-3)); // this time we also use abs()
    
    // ...
}

Functions are very powerful because they save you huge amounts of typing. You often have to do a similar task twice or more in an RMS; functions can let you do this elegantly and concentrate on writing your script, not copying and pasting code, and they come with the added benefit that you just have to edit one place in your code (the function definition) to fix a bug that affects many other places. Also, functions can call each other, which further increases their power and usefulness.

Back to the RMS Section