Table of Contents

About

This item is an animation toolbox as a HUD that can be used to start various animations. The HUD can be edited and new animations added or removed. The item is built out of one single primitive and contains just one script and several animations.

Screenshot

Scripts

///////////////////////////////////////////////////////////////////////////
//  Copyright (C) Wizardry and Steamworks 2022 - License: GNU GPLv3      //
///////////////////////////////////////////////////////////////////////////
 
///////////////////////////////////////////////////////////////////////////
//    Copyright (C) 2013 Wizardry and Steamworks - License: GNU GPLv3    //
///////////////////////////////////////////////////////////////////////////
integer wasMenuIndex = 0;
list wasDialogMenu(list input, list actions, string direction) {
    integer cut = 11-wasListCountExclude(actions, [""]);
    if(direction == ">" &&  (wasMenuIndex+1)*cut+wasMenuIndex+1 < llGetListLength(input)) {
        ++wasMenuIndex;
        jump slice;
    }
    if(direction == "<" && wasMenuIndex-1 >= 0) {
        --wasMenuIndex;
        jump slice;
    }
@slice;
    integer multiple = wasMenuIndex*cut;
    input = llList2List(input, multiple+wasMenuIndex, multiple+cut+wasMenuIndex);
    input = wasListMerge(input, actions, "");
    return input;
}
 
///////////////////////////////////////////////////////////////////////////
//    Copyright (C) 2013 Wizardry and Steamworks - License: GNU GPLv3    //
///////////////////////////////////////////////////////////////////////////
integer wasListCountExclude(list input, list exclude) {
    if(llGetListLength(input) == 0) return 0;
    if(llListFindList(exclude, (list)llList2String(input, 0)) == -1)
        return 1 + wasListCountExclude(llDeleteSubList(input, 0, 0), exclude);
    return wasListCountExclude(llDeleteSubList(input, 0, 0), exclude);
}
 
///////////////////////////////////////////////////////////////////////////
//    Copyright (C) 2013 Wizardry and Steamworks - License: GNU GPLv3    //
///////////////////////////////////////////////////////////////////////////
list wasListMerge(list l, list m, string merge) {
    if(llGetListLength(l) == 0 && llGetListLength(m) == 0) return [];
    string a = llList2String(m, 0);
    if(a != merge) return [ a ] + wasListMerge(l, llDeleteSubList(m, 0, 0), merge);
    return [ llList2String(l, 0) ] + wasListMerge(llDeleteSubList(l, 0, 0), llDeleteSubList(m, 0, 0), merge);
}
 
list menu;
integer animation;
key owner;
 
string exception;
 
default {
    state_entry() {
        owner = llGetOwner();
 
        state permissions;
    }
}
 
state permissions {
    state_entry() {
        if(owner == NULL_KEY && llGetAttached() == 0) {
            return;
        }
 
        llSetTextureAnim(
            ROTATE | LOOP,
            ALL_SIDES,
            0,
            0,
            0,
            2*PI,
            2*PI
        );
 
        llRequestPermissions(
            owner,
            PERMISSION_TRIGGER_ANIMATION
        );
    }
 
    run_time_permissions(integer perm) {
        if(!(perm & PERMISSION_TRIGGER_ANIMATION)) {
            return;
        }
 
        integer l = llGetInventoryNumber(
            INVENTORY_ANIMATION
        );
        if(l == 0) {
            exception = "no animations in inventory";
            state fault;
        }
 
        menu = [];
        integer i = 0;
        do {
            string name = llGetSubString(
                llGetInventoryName(
                    INVENTORY_ANIMATION,
                    i
                ),
                0,
                8
            );
 
            llStopAnimation(
                name
            );
 
            menu += name;
        } while(++i < l);
 
        llOwnerSay(
            (string)llGetListLength(menu) + " animation(s) have been loaded: " + llList2CSV(menu)
        );
 
        state dialog;
    }
 
    attach(key id) {
        owner = id;
    }
}
 
state dialog {
    touch_start(integer num) {
        integer channel = (integer)("0x8" + llGetSubString(llGetKey(), 0, 6));
        llListen(
            channel,
            "",
            owner,
            ""
        );
 
        llDialog(
            owner,
            "Please choose: ",
            wasDialogMenu(
                menu,
                [
                    "⟵ Back", "", "Next ⟶"
                ],
                ""
            ),
            channel
        );
    }
 
    listen(integer channel, string name, key id, string message) {
        if(message == "⟵ Back") {
            llDialog(
                id,
                "Please choose: ",
                    wasDialogMenu(
                    menu,
                    [
                        "⟵ Back", "", "Next ⟶"
                    ],
                    "<"
                ),
                channel
            );
            return;
        }
 
        if(message == "Next ⟶") {
            llDialog(
                id,
                 "Please choose: ",
                    wasDialogMenu(
                    menu,
                    [
                        "⟵ Back", "", "Next ⟶"
                    ],
                    ">"
                ),
                channel
            );
 
            return;
        }
 
        animation = llListFindList(
            menu,
            [
                message
            ]
        );
        state animate;
    }
 
    attach(key id) {
        owner = id;
    }
}
 
state animate {
    state_entry() {
        llRequestPermissions(
            owner,
            PERMISSION_TRIGGER_ANIMATION
        );
    }
 
    run_time_permissions(integer perm) {
        if(perm & PERMISSION_TRIGGER_ANIMATION) {
            llSetTextureAnim(
                ANIM_ON | ROTATE | LOOP,
                ALL_SIDES,
                0,
                0,
                0,
                2*PI,
                2*PI
            );
 
            string select = llGetInventoryName(
                INVENTORY_ANIMATION,
                animation
            );
            llStartAnimation(
                select
            );
 
            llOwnerSay("Animation \"" + select + "\" has been started.");
        }
    }
 
    touch_start(integer num) {
        llSetTextureAnim(
            ROTATE | LOOP, ALL_SIDES,
            0,
            0,
            0,
            2*PI,
            2*PI
        );
 
        string select = llGetInventoryName(
            INVENTORY_ANIMATION,
            animation
        );
        llStopAnimation(select);
 
        llOwnerSay(
            "Animation \"" + select + "\" has been stopped."
        );
        state dialog;
    }
 
    attach(key id) {
        owner = id;
    }
}
 
state fault {
    state_entry() {
        llOwnerSay("Fault occurred: " + exception);
    }
 
    changed(integer change) {
        llResetScript();
    }
 
    on_rez(integer num) {
        llResetScript();
    }
 
    attach(key id) {
        llResetScript();
    }
}