EasyDialog

From Second Life Wiki
Revision as of 20:24, 26 January 2020 by Pazako Karu (talk | contribs)
Jump to navigation Jump to search

Free to use in any context for any reason. Provided by Pazako Karu

Take on high-security dialogs the easy way! Simplifies listens and contextual information greatly into gets and sets. Each dialog uses a new listen, a new channel, and listens only to the originator of the dialog. Any use of a dialog will trigger self-clean garbage collection of old listens and values.

Example use case below.

list DIALOG_DATA;
setDialog(key id, string caption, list buttons, integer context) // Creates a listen and a dialog
{   getDialog(id); // Clean up beforehand
    if (llList2Integer(DIALOG_DATA, -3) > llGetTime()) // Clear old
    {   integer i;
        for (i = 0; i < llGetListLength(DIALOG_DATA); i++)
            llListenRemove((integer)DIALOG_DATA[i+2]);
        DIALOG_DATA = []; // If the last timed out, all are invalid
    }
    integer channel = -(integer)llFrand(DEBUG_CHANNEL);
    DIALOG_DATA += [llGetTime()+60, id, llListen(channel, llKey2Name(id), id, ""), context]; // Time, ID, Listen Handle, context
    llDialog(id, caption, buttons, channel);
}
integer getDialog(key id)
{   integer index = llListFindList(DIALOG_DATA, [id]); // Finds the dialog, if it exists
    integer context = (integer)DIALOG_DATA[index+2]; // Context that the dialog was sent in, integer
    if (~index) // If it does...
    {   llListenRemove(llList2Integer(DIALOG_DATA, index+1)); // Remove the listen
        DIALOG_DATA = llDeleteSubList(DIALOG_DATA, index-1, index+1); // Free the memory
    }
    else context = -1; // If it doesn't exist, return nothing
    return context; // Return the context
}

Example use

Context is useful for creating sub-menus without complicating the listen logic. As you can have a precheck of context, you can keep simple "Yes" and "No" answers, rather than the often-used trope of including special characters with each menu option. No additional variables or flags are necessary.

integer context_pancake = 1;
integer context_pie = 2;
default
{
    state_entry()
    {
        setDialog(llGetOwner(), "Do you like pancakes?", ["Yes", "No"], context_pancake);
    }
    listen(integer channel, key id, string message)
    {
        integer context = getDialog(id);
        if(context == context_pancake) // They like pancakes!
        {
            if (message == "Yes")
                llRegionSayTo(llGetOwner(), 0, "Glad to hear it!");
            else if (message == "No")
                setDialog(llGetOwner(), "Sorry, how about pie?", ["Yes", "No"], context_pie);
        }
        else if (context == context_pie) // They like pie!
        {
            if (message == "Yes")
                llRegionSayTo(llGetOwner(), 0, "Pie is my second favorite!");
            else if (message == "No")
                llRegionSayTo(llGetOwner(), 0, "I guess we dont have much in common :(");
        }
    }
}