Primset script
Revision as of 00:00, 20 December 2011 by Rufus Darkfold (talk | contribs)
//primset+++ - Includes support for llGet/SetLinkPrimitiveParams, linkset resize, llLinkParticleSystem, and //llSetKeyframeMotion // Used by the primcontrol HUD. //This function typecasts a list of strings, into the types they appear to be. //Extremely useful for feeding user data into llSetPrimitiveParams //It takes a list as an input, and returns that list, with all elements correctly typecast, as output //Written by Fractured Crystal, 27 Jan 2010, Commissioned by WarKirby Magojiro, this function is Public Domain //Modified by Rufus Darkfold to keep strings like <foo> instead of discarding them entirely from the output list list_cast(list in) { list out; integer i; integer l= llGetListLength(in); for (i=0; i < l; i++) { string d= llStringTrim(llList2String(in,i),STRING_TRIM); if (d == "") out += ""; else { if (llGetSubString(d,0,0) == "<") { if (llGetSubString(d,-1,-1) == ">") { list s = llParseString2List(d,[","],[]); integer sl= llGetListLength(s); if (sl == 3) { out += (vector)d; } else if(sl == 4) { out += (rotation)d; } else out += [d]; } else out += [d]; } else if (~llSubStringIndex(d,".")) { out += (float)d; } else { integer lold = (integer)d; if ((string)lold == d) out += lold; else { key kold = (key)d; if (kold) out += [kold]; else out += [d]; } } } } //for (i = 0; i< llGetListLength(out); i++){ // llOwnerSay("Element " + (string)i + " type is " + (string)llGetListEntryType(out, i) // + " value is «" + llList2String(out,i) + "»"); //} return out; } integer dimTest( vector vr ) { return !( vr.x<0.01 || vr.y<0.01 || vr.z<0.01 || vr.x>64.0 || vr.y>64.0 || vr.z>64.0 ); } resize_linkset( vector scal ) { integer primindx; list primP; vector s = llGetScale(); integer validDim = dimTest( <scal.x*s.x,scal.y*s.y,scal.z*s.z> ); for ( primindx = 2; primindx <= llGetNumberOfPrims(); primindx++ ) { primP = llGetLinkPrimitiveParams( primindx, [PRIM_SIZE]); s = llList2Vector( primP, 0 ); validDim = validDim && dimTest( <scal.x*s.x,scal.y*s.y,scal.z*s.z> ); } if ( validDim ) { s = llGetScale(); llSetScale( <scal.x*s.x,scal.y*s.y,scal.z*s.z> ); for ( primindx = 2; primindx <= llGetNumberOfPrims(); primindx++ ) { primP = llGetLinkPrimitiveParams( primindx, [PRIM_SIZE, PRIM_POSITION]); vector primScale = llList2Vector( primP, 0 ); primScale = <primScale.x*scal.x, primScale.y*scal.y, primScale.z*scal.z>; vector primPos = llList2Vector( primP, 1 ) - llGetPos(); primPos = <primPos.x*scal.x, primPos.y*scal.y, primPos.z*scal.z>; llSetLinkPrimitiveParamsFast( primindx, [PRIM_SIZE, primScale, PRIM_POSITION, primPos/llGetRootRotation()]); } } else llOwnerSay("No resize! Out of limit sizes are not accepted"); } debugout(string msg) { llOwnerSay(msg); } integer outchan =0; reply(string msg) { llRegionSayTo(llGetOwner(), outchan, msg); if (outchan) { debugout(msg); } } integer channel = 884; list subset; integer hlis; float timeout = 300; // stop listening after 5 minutes of inactivity vector lastpos; rotation lastrot; default { timer() { if (hlis){ llOwnerSay("Deslecting " + llGetObjectName()); llListenRemove(hlis); hlis = 0; } } touch_start(integer num) { llSetTimerEvent(timeout); llResetTime(); if (!hlis) { hlis = llListen(channel, "", "", ""); llOwnerSay(llGetObjectName() + " selected. Listening on channel " + (string)channel); return; } while (num--) { integer child=llDetectedLinkNumber(num); integer j = llListFindList(subset,[child]); if (~j) { llOwnerSay("Deselecting #" + (string)child); subset = llDeleteSubList(subset, j, j); } else { llOwnerSay("Selecting #" + (string)child); subset += child; } } } listen(integer ch, string name, key id, string msg) { //llOwnerSay(msg + " from " + (string)id + " owned by " + (string)llGetObjectDetails(id, [OBJECT_OWNER])); if (llGetOwner() != id) { if (llList2Key(llGetObjectDetails(id, [OBJECT_OWNER]),0) != llGetOwner()) return; } outchan = 0; if (msg == "") { subset = []; llSetTimerEvent(0.1); // empty message = disconnect right away; return; } llSetTimerEvent(timeout); if (llGetSubString(msg, 0, 0) == "/") { // specify response channel integer endch = llSubStringIndex(msg, " "); outchan = (integer)llGetSubString(msg, 1, endch); msg = llGetSubString(msg, endch+1, -1); } if (llGetSubString(msg,0,0) == "[") { integer e = llSubStringIndex(msg, "]"); if (e > 1) subset = list_cast(llCSV2List(llGetSubString(msg, 1, e-1))); else subset = []; msg = llStringTrim(llGetSubString(msg, e+1, -1), STRING_TRIM_HEAD); if (llList2String(subset,0) == "*") { integer i; subset = []; for (i=1; i<=llGetNumberOfPrims(); i++) subset += i; } } list sub; list cmds; if (llGetSubString(msg,0,0) == "?") { cmds = list_cast(llCSV2List(llGetSubString(msg, 1, -1))); integer i; list curr; if (subset == []) // If not specified use root (or only) prim sub = [ (llGetNumberOfPrims() > 1) ]; else sub = subset; debugout(llList2CSV(cmds)); for (i = 0; i<llGetListLength(sub); i++) { if (llGetListEntryType(sub,i) == TYPE_INTEGER){ integer j = llList2Integer(sub,i); curr = llGetLinkPrimitiveParams(j, cmds); reply("[" + (string)j + "] " + llList2CSV(curr)); } else //if (llGetListEntryType(subset,i) == TYPE_STRING) { integer k; string x=llList2String(sub,i); list exp; for (k=1; k<=llGetNumberOfPrims(); k++) { if (~llListFindList(llGetLinkPrimitiveParams(k,[PRIM_NAME,PRIM_DESC]), [x])) { curr = llGetLinkPrimitiveParams(k, cmds); exp += k; reply("[" + (string)k + "] " + llList2CSV(curr)); } } debugout(x + " is " + llList2CSV(exp)); } } return; } if (llGetSubString(msg,0,0) == "$") { msg = llDeleteSubString(msg,0,0); vector v = (vector)msg; if (v == ZERO_VECTOR) { float scal=(float)msg; v = <scal,scal,scal>; } resize_linkset(v); return; } else if (llGetSubString(msg,0,0) == "%") { msg = llDeleteSubString(msg,0,0); cmds = list_cast(llCSV2List(msg)); if (subset == []) sub = [LINK_SET]; else sub = subset; debugout("ParticleSystem On " + llList2CSV(subset) +":\nCmds: "+ llDumpList2String(cmds,"; ")); integer i; for (i = 0; i<llGetListLength(sub); i++) { if (llGetListEntryType(sub,i) == TYPE_INTEGER) llLinkParticleSystem(llList2Integer(sub,i), cmds); else //if (llGetListEntryType(subset,i) == TYPE_STRING) { integer k; string x=llList2String(sub,i); list exp; for (k=llGetNumberOfPrims(); k; k--) { if (~llListFindList(llGetLinkPrimitiveParams(k,[PRIM_NAME,PRIM_DESC]),[x])) { llLinkParticleSystem(k, cmds); exp += k; } } debugout(x + " is " + llList2CSV(exp)); } } return; } else if (llGetSubString(msg,0,0) == "@") { if (subset != []) { if (!~llListFindList(subset,[llGetNumberOfPrims() > 1]) && !~llListFindList(subset,[llGetObjectName()])) { return; } } integer direction = KFM_FORWARD; msg = llDeleteSubString(msg,0,0); string pfx2 = llGetSubString(msg,0,0); if ( pfx2 == "%") { direction = KFM_PING_PONG; msg = llDeleteSubString(msg,0,0); } else if (pfx2 == "^") { direction = KFM_REVERSE; msg = llDeleteSubString(msg,0,0); } else if (pfx2 == "@") { if (msg == "@@") { llSetKeyframedMotion([], [KFM_COMMAND, KFM_CMD_STOP]); llSetPos(lastpos); llSetRot(lastrot); return; } llSetKeyframedMotion([], [KFM_COMMAND, KFM_CMD_PAUSE]); return; } else if (pfx2 == "!") { lastpos = llGetPos(); lastrot = llGetRot(); llSetKeyframedMotion([], [KFM_COMMAND, KFM_CMD_PLAY]); llSetTimerEvent(0.0); // stop the timer while animation is running return; } else if (msg == "") { llSetKeyframedMotion([], [KFM_COMMAND, KFM_CMD_STOP]); return; } lastpos = llGetPos(); lastrot = llGetRot(); cmds = list_cast(llCSV2List(msg)); llSetKeyframedMotion(cmds, [KFM_MODE, direction]); llSetTimerEvent(0.0); // stop the timer while animation is running return; } cmds = list_cast(llCSV2List(msg)); if (subset == []) sub = [LINK_SET]; else sub = subset; debugout("On " + llList2CSV(subset) +":\nCmds: "+ llDumpList2String(cmds,"; ")); integer i; for (i = 0; i<llGetListLength(sub); i++) { if (llGetListEntryType(sub,i) == TYPE_INTEGER) llSetLinkPrimitiveParamsFast(llList2Integer(sub,i), cmds); else //if (llGetListEntryType(subset,i) == TYPE_STRING) { integer k; string x=llList2String(sub,i); list exp; for (k=llGetNumberOfPrims(); k; k--) { if (~llListFindList(llGetLinkPrimitiveParams(k,[PRIM_NAME,PRIM_DESC]),[x])) { llSetLinkPrimitiveParamsFast(k, cmds); exp += k; } } debugout(x + " is " + llList2CSV(exp)); } } } }