Myriad's Bam Module (Goes In The Hud)
updated February 10 2012

This is the adventure quest script. It goes into the HUD so that the player receives the necessary info and such to pursue any quests or adventures that you set up.

// Myriad Lite Module BAM v0.0.0 20110908
// The Myriad RPG System was designed, written, and illustrated by Ashok Desai
// Myriad RPG licensed under the Creative Commons Attribution 2.0 UK: England and Wales
// http://creativecommons.org/licenses/by/2.0/uk/
// Myriad Lite software Copyright (c) 2011 by Allen Kerensky (OSG/SL)
// Baroun's Adventure Machine Copyright (c) 2008-2011 by Baroun Tardis (SL)
// Myriad Lite and Baroun's Adventure Machine licensed under the
// Creative Commons Attribution-Share Alike-Non-Commercial 3.0 Unported
// http://creativecommons.org/licenses/by-nc-sa/3.0/

// CONSTANTS - DO NOT CHANGE DURING RUN
string VERSION = "0.0.0"; // Allen Kerensky's script version
string VERSIONDATE = "20110908"; // Allen Kerensky's script yyyymmdd
string CHAN_PREFIX = "0x"; // channel prefix for calculating dynamic channels
string DIV = "|"; // message field divider
string API_OFFERADV = "OfferAdv"; // Offer an adventure to HUD wearer
string API_ACCEPTADV = "AcceptAdv"; // Offer accepted player is on an adventure
string API_INADV_QUERY = "InAdv?"; // Ask a player HUD if the player is in an adventure - InAdv?
string API_INADV_RESPONSE = "InAdv"; // In Adventure Response Yes: InAdv | String AdventureName  No: InAdv | NONE
string API_TASKIP_QUERY = "TaskIP?"; 
string API_TASKIP_RESPONSE = "TaskIP"; // Task In Progress Reply current task in progress: TaskIP | AdventureGoal
string API_TASKCP_QUERY = "TaskCP?"; // Task Complete Query
string API_TASKCP_RESPONSE = "TaskCP"; // Task Complete Reply
string API_DONETASK = "DoneTask"; // Task Done - player achieved current goal NPC sends: DoneTask | GoalText | TaskDone Text | PlayerUUID
string API_DONEADV = "DoneAdv"; // Done Adventure reply
string API_NONE = "NONE";
string API_ADDTASK = "AddTask"; // Add a task to the Player HUD - AddTask | TaskNumber | String Describing Task
string API_ADDHINT = "AddHint"; // Add a hint for a task to the Player HUD - AddHint | TaskNumber | String Hint
string MSG_NO_ADVENTURE = "Looking for adventure...";
string MSG_CURRENT_ADVENTURE = "Adventure: ";
string MSG_CURRENT_GOAL = "Overall Goal: ";
string MSG_CURRENT_TASK = "Current Task: ";
string MSG_CURRENT_HINT = "Current Hint: ";

// RUNTIME GLOBALS - CAN CHANGE DURING RUN
integer CHANOBJBAM; // channel of thing we're talking to
string  STATUSMSG; // scratch space to build status messages
integer STATUS_FLAG; // show status as HUD hover text

// Adventure-Specific Configuration
// Task numbers are (AdvNum*100)+task, so they don't overlap between adventures
string  ADVNAME="NONE"; // Adventure Name
string  ADVTEXT; // brief description
// Current Task-specific info
string  ADVTASKTODO; // task name of the next task handed out
integer ADVTASKTDNUM; // task number of the next task handed out
string  ADVTASKTODOHINT; // Hint text for the next task handed out
// Previous Task-specific info
list    ADVTASKDONE; // Tasks which are complete   (name of task)
list    ADVTCOMP; // completed task numbers (list of numbers)

// SETUP - begin bringing the HUD online
SETUP() {
    llSetText("",<0,0,0>,0); // clear any previous hovertext
    if ( llGetAttached() >= 31 && llGetAttached() <= 38 ) { // are we attached to a HUD slot?
        STATUS_FLAG = TRUE; // turn on HUD hovertext
    } else {
        STATUS_FLAG = FALSE; // turn off body attached hovertext
    } 
    STATUS();        
}

// RESET - shut down running animations then reset the script to reload character sheet
RESET() {
    llResetScript(); // now reset
}

// GLOBAL STATUS() - update adventure data on HUD
STATUS() {
    if ( ADVNAME == "NONE" ) { // is player in an adventure?
        STATUSMSG = MSG_NO_ADVENTURE; // nope
    } else { // yep, build the status
        STATUSMSG = MSG_CURRENT_ADVENTURE + ADVNAME + "\n" +
                    MSG_CURRENT_GOAL + ADVTEXT + "\n" +
                    MSG_CURRENT_TASK + ADVTASKTODO + "\n" +
                    MSG_CURRENT_HINT + ADVTASKTODOHINT;
    }
    if ( STATUS_FLAG == FALSE ) { // if attached to body, use chat output
        llOwnerSay(STATUSMSG);
    } else { // attached to HUD slot, use hovertext
        llSetText(STATUSMSG,<1,1,1>,1.0);
    }
}

// DEFAULT STATE - load character sheet
default {

    // STATE ENTRY - called on Reset
    state_entry() {
        SETUP(); // show credits and start character sheet load
    }

    // ON_REZ - logged in with meter, or worn from inventory while running
    on_rez(integer rezparam) {
        RESET(); // a reset to reload character
    }

    // ATTACH - logged in with meter or worn from inventory/ground while running
    attach(key id) {
        RESET(); // a reset to reload character
    }

    // TOUCH_START - touch HUD for adventure update
    touch_start(integer total_number) {
        STATUS();
    }

    // LINK MESSAGE - commands to and from other prims in HUD
    link_message(integer sender,integer channel,string message, key speakerid) {
        if ( message == "BAMSTATUS" ) { STATUS(); return;} // show status when specifically requested
        if ( message == "MODULERESET" ) { RESET(); return;} // HUD reset so reset module too
        // calculate BAM dynamic channel of item/player talking to us
        CHANOBJBAM = (integer)(CHAN_PREFIX + llGetSubString((string)speakerid,-7,-1));

        // break down the commands and messages into units we can work with
        list fields = llParseString2List(message,[DIV],[]); // break into list of fields based on DIVider
        string command = llList2String(fields,0); // assume the first field is a Myriad Lite command
        string data1   = llList2String(fields,1);
        string data2   = llList2String(fields,2);
        string data3   = llList2String(fields,3);

        // We're asked what adventure we're in
        if ( command == API_INADV_QUERY ) {
            llSay(CHANOBJBAM,API_INADV_RESPONSE + DIV + ADVNAME); // reply with In Adventure and Adventure Name
            STATUS();
            return; // command done, return early
        }

        // We're asked our current task in progress
        if ( command == API_TASKIP_QUERY ) { // what task in progress?
            // respond with task in progress
            llSay(CHANOBJBAM, API_TASKIP_RESPONSE + DIV + (string)ADVTASKTDNUM); // Reply with current task in progress and number
            STATUS();
            return; // command done, return early
        }

        // Get list of completed tasks
        if ( command == API_TASKCP_QUERY ) { // what tasks complete?
            llSay(CHANOBJBAM, API_TASKCP_RESPONSE + DIV + llList2CSV(ADVTCOMP)); // reply with current task complete list as CSV
            STATUS();
            return; // command done, return early
        }

        // player is offered an adventure
        if ( command == API_OFFERADV ) { // want adventure?
            // FIXME need to add dialog box to accept/decline later
            ADVNAME=data1; // name of the adventure
            ADVTEXT=data2; // description of the adventure
            ADVTCOMP=[]; // clear the completed task list and start new one
            ADVTASKTODO=""; // clear the next task name
            ADVTASKTDNUM=0; // clear the next task number
            llSay(CHANOBJBAM, API_ACCEPTADV + DIV +data1); // accept the adventure
            STATUS();
            return; // command done, return early
        }

        // add the next task to complete
        if ( command == API_ADDTASK ) { // add a task
            ADVTASKTDNUM=(integer)data1; // next task number
            ADVTASKTODO=data2; // next task name
            llOwnerSay(ADVTASKTODO); // tell player the next task name
            STATUS();
            return; // command done, return early
        }

        // add a hint for the next task to complete
        if( ( command == API_ADDHINT ) && ( (integer)data1 == ADVTASKTDNUM) ) {
            ADVTASKTODOHINT=data2; // next task hint
            llOwnerSay(ADVTASKTODOHINT); // tell that player the next task hint
            STATUS();
            return; // command done, return early
        }

        // is player done with this task of the adventure?
        if ( ( command == API_DONETASK ) && ( (integer)data1 == ADVTASKTDNUM) ) {
            ADVTCOMP = [(integer)data1] + ADVTCOMP; // add this task number to completed list
            ADVTASKTDNUM=0; // clear out the task number we're working on since its done now
            ADVTASKTODO=""; // clear out the task name
            ADVTASKTODOHINT=""; // clear out the task hint
            llOwnerSay(data2); // tell player task is complete
            if ( data3 != "" ) llPlaySound(data3,0.5); // play sound if one was defined
            STATUS();
            return; // command done, return early
        }

        // is player done with the entire adventure?
        if ( ( command == API_DONEADV ) && ( data1 == ADVNAME ) ) {
            ADVTCOMP = []; // clear out adventure tasks - we're done
            ADVTASKTDNUM=0; // clear out next task number
            ADVTASKTODO=""; // clear out name of next task
            ADVTASKTODOHINT=""; // clear out next task hint
            ADVNAME="NONE"; // set current adventure name to none
            ADVTEXT="Looking for adventure..."; // set the current adventure name to 
            llOwnerSay(data2); // tell player adventure is complete
            if ( data3 != "" ) llPlaySound(data3,0.5); // play sound if one was defined
            STATUS();
            return; // command done, return early
        }            
    } // end listen
} // end state running
// END
Creative Commons License
This work by