Don't click here unless you want to be banned.

LSL Wiki : SableTill

HomePage :: PageIndex :: RecentChanges :: RecentlyCommented :: UserSettings :: You are crawl338.us.archive.org

Speed tests

++x vs x=x+1 vs x++

default
{
    state_entry()
    {
        while(TRUE) {
            integer iter=20000;
            integer time = llGetUnixTime();
            llOwnerSay("++x "+(string)iter);
            integer x=0;
            for(x=0;x<iter;++x) {
            }
            llOwnerSay((string)(llGetUnixTime()-time));        
    
            time = llGetUnixTime();
            llOwnerSay("x=x+1 "+(string)iter);
            x=0;
            for(x=0;x<iter;x=x+1) {
            }
            llOwnerSay((string)(llGetUnixTime()-time));        
    
            time = llGetUnixTime();
            llOwnerSay("x++ "+(string)iter);
            x=0;
            for(x=0;x<iter;x++) {
            }
            llOwnerSay((string)(llGetUnixTime()-time));        
        }
    }
}



Results
[4:24]  Object: ++x 20000
[4:26]  Object: 76
[4:26]  Object: x=x+1 20000
[4:27]  Object: 76
[4:27]  Object: x++ 20000
[4:28]  Object: 94
[4:28]  Object: ++x 20000
[4:30]  Object: 79
[4:30]  Object: x=x+1 20000
[4:31]  Object: 77
[4:31]  Object: x++ 20000
[4:33]  Object: 94

Conclusion
++x is the same as x=x+1, but x++ is slower unless you need that pre-incremented value.





Artificial Life
Lame swarming script

ChangeLog
2006-08-04
Lots of bugfixes
Added a LagMonitor which causes fish to die on lag spikes
Added a predator mode.
2006-08-06
Improved the bootstrap.
Fixed some bugs in the predator mode.

Instructions for usage:
Create a notecard and put the stuff from FishNote into it. Copy each of the other boxes below and save the text in a script with the same name as the title here.
Create a prim, just a random plywood box is fine. First place the notecard inside. Every other script reads this notecard so it needs to be there first. Then place the Init script in, it sets a few values including the object name which every other script uses so it's helpful to put it in first. Then transfer all the other scripts in any order.

It's perfectly fine to leave certain scripts out. For example if you want your fish to float away on their own then leave out NearOwner. If you don't want the text to appear above each fish then leave out the Stats script.

One useful thing to do is to make a container, put a temp-on-rez fish inside it. Then write a little script to llRezObject the fish on a timer. If you make one once every 10 seconds you'll end up with about 6 in the swarm if you make it rez once per second you'll end up with 60 and the sim might start to strain a little. If you set your objects to be temp-on-rez then you can set the lifetime to something ridiculous like 600 since the simulator deletes temporary objects over about 60 seconds old.

The Repel and Attract functions work based on Object name so you can set up two swarms or make new fish ignore the old ones by changing the name parameter in the FishNote notecard.

If you can't get any of this to work just contact me in game and I may be able to transfer all the scripts to you or at the very least help you get it working.


FishNote
fishname=Fish 4.0
predname=Pred 4.1
heartbeat=0.5
friction=0.6
maxpush=2.0
lifespan=600
quiet=true
phantom=false
temp=false







Attract
//default values
float maxpush=3;
float heartbeat=1;
integer quiet=TRUE;
string fishname="Fish 4.0";

string scriptname;
float scan_dist=0.5;

default {
    state_entry() {
        scriptname = llGetScriptName();         
    }
    
    //mostly used to receive initialised parameters.
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":", "="], []);
        if(llList2String(cmd, 0) == "PARAM") {
            //llOwnerSay(str+":"+llList2String(cmd, 1)+":"+llList2String(cmd, 2));
            if(llList2String(cmd, 1)== "maxpush") {
                maxpush = llList2Float(cmd, 2);
                return;                
            }
            if(llList2String(cmd, 1)== "heartbeat") {
                heartbeat = llList2Float(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "quiet") {
                quiet = llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "fishname") {
                fishname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "EOF") {
                if(!quiet) {       
                    llOwnerSay(scriptname+":"+"heartbeat="+(string)heartbeat);
                    llOwnerSay(scriptname+":"+"maxPush="+(string)maxpush);
                    llOwnerSay(scriptname+":"+"quiet="+(string)quiet);        
                    llOwnerSay(scriptname+":"+"fishname="+(string)fishname);                            
                }
                
                if(llGetAttached()!=0) {
                    return;
                }
                state run;
            }
            
        }
    }
}

state run
{
    state_entry()
    {
        llSetTimerEvent(heartbeat);
    }
    
    timer() {
        //benefit of this over SensorRepeat is we get objectname every time
        //since it has a tendency to change around.
        llSensor(fishname, NULL_KEY, ACTIVE | PASSIVE, scan_dist, PI);        
    }
            
    sensor(integer num_detected) {
        //new magic idea, get the average vector of all detected items
        //push away from that!
        integer count=0;
        vector target=<0,0,0>;
        for(count=0;count<num_detected;++count) {
            target+=llDetectedPos(count);
        }
        target/=num_detected;
        
        
        //theoretically 0 should be the nearest
        vector push = -((llGetPos()-target));
        //3, it's the magic number.
        push/=3;
        
        //limit to maxPush in power
        if(llVecMag(push)>maxpush) {
            if(!quiet)
                llOwnerSay(scriptname + "Warning! Pushing "+(string)push);
            push = push*maxpush/llVecMag(push);
        }
        //pass message to stats module        
        llMessageLinked(LINK_SET, (integer)(llVecMag(push)*1000), "STATS:"+scriptname, NULL_KEY);  

        push*=llGetMass();
        llApplyImpulse(push, FALSE);                        
    }
    
    //should send a message when attract is 0
    no_sensor() {
        //we may not be scanning far enough.
        if(scan_dist<64)
            scan_dist*=2;
        llMessageLinked(LINK_SET, -(integer)scan_dist, "STATS:"+scriptname, NULL_KEY);
    }

    
}




CardReader
//-------------------------------------------
// SampleSettingsReader.lsl
// Written by Konigmann Lippmann
// Thanks to Apotheus Silverman for his MultiItem Vendor...
// It seems like everything I write is based on it in one way or another.


// Globals
integer iNotecardIndex;
integer iNotecardCount;
integer iNoteCardLine;
key kCurrentDataRequest;
string sSettingsNotecard;


default
{
    state_entry()
    {
        //llOwnerSay(llGetScriptName() +":"+"entry");
        integer iii;
    
        iNotecardCount = llGetInventoryNumber( INVENTORY_NOTECARD );
        iNotecardIndex = 0;
        if( iNotecardCount > iNotecardIndex )
        {
            sSettingsNotecard = llGetInventoryName( INVENTORY_NOTECARD, iNotecardIndex );
            iNoteCardLine = 0;
            kCurrentDataRequest = llGetNotecardLine( sSettingsNotecard, iNoteCardLine );
            iNotecardIndex++;
        }
        if( iNotecardIndex == 0 )
        {
            llOwnerSay("Using Default Values." );
        }
    }

    dataserver( key kQuery, string sData )
    {
        list lSetting;

        kCurrentDataRequest = "";
        if( sData != EOF )
        {
            //llOwnerSay(llGetScriptName() +":"+sData);
            llMessageLinked(LINK_SET, 0, "PARAM:"+sData, NULL_KEY);
            kCurrentDataRequest = llGetNotecardLine( sSettingsNotecard, ++iNoteCardLine );
        }
        else
        {
            iNotecardIndex++;
            if( iNotecardIndex < llGetInventoryNumber( INVENTORY_NOTECARD ) )
            {
                sSettingsNotecard = llGetInventoryName( INVENTORY_NOTECARD, iNotecardIndex );

                iNoteCardLine = 0;
                llGetNotecardLine( sSettingsNotecard, iNoteCardLine );
            }
            else
            {
                llMessageLinked(LINK_SET, 0, "PARAM:EOF", NULL_KEY);
            }
        }
    }
}





Flee
//default values
float heartbeat=1;
//sometimes things go weird and want to push the object a million miles away
//this restricts that to an upper limit.
float maxpush=1;
integer quiet=TRUE;
string predname;

string scriptname;
float maxCubed;
float scan_dist=0.5;

default {
    state_entry() {
        scriptname = llGetScriptName();         
    }
    
    //mostly used to receive initialised parameters.
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":", "="], []);
        if(llList2String(cmd, 0) == "PARAM") {
            //llOwnerSay(str+":"+llList2String(cmd, 1)+":"+llList2String(cmd, 2));
            if(llList2String(cmd, 1)== "maxpush") {
                maxpush = llList2Float(cmd, 2);
                return;                
            }
            if(llList2String(cmd, 1)== "heartbeat") {
                heartbeat = llList2Float(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "quiet") {
                quiet = llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "predname") {
                predname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "EOF") {
                if(!quiet) {       
                    llOwnerSay(scriptname+":"+"heartbeat="+(string)heartbeat);
                    llOwnerSay(scriptname+":"+"maxPush="+(string)maxpush);
                    llOwnerSay(scriptname+":"+"quiet="+(string)quiet);        
                    llOwnerSay(scriptname+":"+"predname="+(string)predname);                            
                }

                if(llGetObjectName()==predname) {
                    return;
                }
                
                if(llGetAttached()!=0) {
                    return;
                }

                maxpush*=3;
                maxCubed = llPow(maxpush, (1.0/3.0));
                                                
                state run;
            }
        }
    }
}


state run
{
    state_entry() {
        llSetTimerEvent(heartbeat);
    }

    timer() {
        llSensor(predname, NULL_KEY, ACTIVE | PASSIVE, scan_dist, PI);        
    }

    sensor(integer num_detected) {
        //theoretically 0 should be the nearest
        vector push = ((llGetPos()-llDetectedPos(0)));
        //for some reason it sometimes shoots off in random directions, apply this limiter
        if(llVecMag(push)>maxpush) {
            if(!quiet)
                llOwnerSay(llGetScriptName() + " Warning! Pushing "+(string)push);
            push=push*maxpush/llVecMag(push);
        }

        if(llVecMag(push) > llVecMag(<maxCubed, maxCubed, maxCubed>)) {
            push=<0,0,0>;
        } else {
            float newMag = maxpush - llVecMag(push);
            push=push*newMag/llVecMag(push);
        }
        
        
        //this message goes to stats module which sets text  
        llMessageLinked(LINK_SET, ((integer)(llVecMag(push)*1000)), "STATS:"+scriptname, NULL_KEY);  
        
        push *= llGetMass();
        llApplyImpulse(push, FALSE);
              
    }
    
    //should send a message when attract is 0
    no_sensor() {
        //we may not be scanning far enough.
        if(scan_dist<64)
            scan_dist*=2;
        llMessageLinked(LINK_SET, -1, "STATS:"+scriptname, NULL_KEY);          
    }
}





Friction
//default values
float friction = 0.3;
//we apply a little friction once per heartbeat seconds
float heartbeat=1;
//sometimes things go weird and want to push the object a million miles away
//this restricts that to an upper limit.
float maxpush=1;
integer quiet=TRUE;
string fishname;
string predname;

string scriptname;

default {
    state_entry() {
        scriptname = llGetScriptName();         
    }
    
    //mostly used to receive initialised parameters.
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":", "="], []);
        if(llList2String(cmd, 0) == "PARAM") {
            if(llList2String(cmd, 1)== "maxpush") {
                maxpush = llList2Float(cmd, 2);
                return;                
            }
            if(llList2String(cmd, 1)== "heartbeat") {
                heartbeat = llList2Float(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "quiet") {
                quiet = llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "fishname") {
                fishname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "predname") {
                predname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "friction") {
                friction = llList2Float(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "EOF") {
                if(!quiet) {       
                    llOwnerSay(scriptname+":"+"heartbeat="+(string)heartbeat);
                    llOwnerSay(scriptname+":"+"maxPush="+(string)maxpush);
                    llOwnerSay(scriptname+":"+"quiet="+(string)quiet);        
                    llOwnerSay(scriptname+":"+"friction="+(string)friction);                              }
                
                //no real harm in running this while attached really.
                if(llGetAttached()!=0) {
                    return;
                }
                state run;
            }
        }
    }
}



state run
{
    state_entry()
    {
        scriptname = llGetScriptName();
        
        llSetTimerEvent(heartbeat);
    }

    timer() {
        //calculate friction to apply
        vector push = -llGetVel() * friction;
        //apply upper limit
        if(llVecMag(push)>maxpush) {
            push=maxpush*push/llVecMag(push);
            if(!quiet)
                llOwnerSay(llGetScriptName() + " Warning! Pushing "+(string)push);
        }
        //this message goes to stats module which sets text  
        llMessageLinked(LINK_SET, ((integer)(llVecMag(push)*1000)), "STATS:"+scriptname, NULL_KEY);
        push*=llGetMass(); 
        
        llApplyImpulse(push, FALSE);
        

     }
}










Init
string fishname = "Fish";
string predname = "Predator";
integer lifespan=360;
integer phantom=TRUE;
integer temp=TRUE;
integer quiet;

string scriptname;

default {
    state_entry() {
        scriptname == llGetScriptName();

        llResetOtherScript("CardReader");        
    }
    
    //mostly used to receive initialised parameters.
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":", "="], []);
        if(llList2String(cmd, 0) == "PARAM") {
            //llOwnerSay(str+":"+llList2String(cmd, 1)+":"+llList2String(cmd, 2));
            if(llList2String(cmd, 1)== "quiet") {
                quiet = llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "lifespan") {
                lifespan= llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "fishname") {
                fishname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "predname") {
                predname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "EOF") {
                if(!quiet) {       
                    llOwnerSay(scriptname+":"+"quiet="+(string)quiet);        
                    llOwnerSay(scriptname+":"+"fishname="+(string)fishname);                            
                    llOwnerSay(scriptname+":"+"predname="+(string)predname);                            
                    llOwnerSay(scriptname+":"+"lifespan="+(string)lifespan);            
                    llOwnerSay(scriptname+":"+"phantom="+(string)phantom);                    
                    llOwnerSay(scriptname+":"+"temp="+(string)temp);                                        
                }

                state run;
            }
            
        }
    }
}


state run
{
    on_rez(integer huh) {
        llResetScript();
    }
    state_entry()
    {
        if(llFrand(1) < 0.9) {
            llSetColor(<1, 1, 1>, ALL_SIDES);            
            llSetObjectName(fishname);
        } else {
            llSetColor(<1, 0, 0>, ALL_SIDES);
            llSetObjectName(predname);            
        }
        //Setting the buoyancy to 1 cancels out the gravity.  The object will now float.
        llSetBuoyancy(1);

        //allow rotation on any axis
        llSetStatus(STATUS_ROTATE_X,TRUE);
        llSetStatus(STATUS_ROTATE_Y,TRUE);
        llSetStatus(STATUS_ROTATE_Z,TRUE);        

        //phantom is handy for some reason
        llSetStatus(STATUS_PHANTOM,phantom);
        
        //physics is annoying
        llSetStatus(STATUS_PHYSICS,TRUE);
        
        llSetText("", <0,0,0>, 0);
        
        llSetTimerEvent(lifespan);

        llSetPrimitiveParams([PRIM_TEMP_ON_REZ, temp]);
        
        //boot strap is pain!
        //here we will reset all other scripts
        //if init is restarting then every other damn thing can restart too.
        //this means we run cardReader twice, annoying.
        integer max = llGetInventoryNumber(INVENTORY_SCRIPT);
        integer count;
        string me = llGetScriptName();
        for(count=0;count<max;++count) {
            string other = llGetInventoryName(INVENTORY_SCRIPT, count);
            if(other!=me && other !="CardReader") {
                llResetOtherScript(other);
            }
        }
        llResetOtherScript("CardReader");  
        if(llGetObjectName() == predname) {
           vector push = <llFrand(2), llFrand(2), llFrand(2)>;
            push*=llGetMass();
            llApplyImpulse(push, FALSE);                        
        }
                    
    }
    
    changed(integer change) {
        if(change & CHANGED_INVENTORY) {
            llResetScript();
        }
    }

    timer() {
        llDie();
    }
}





LagMonitor
string giv(integer type,integer i) {
    return llGetInventoryName(type,i);
}
default
{
    state_entry()
    {
        //stupid to check too often since that in itself causes lag.
        llSetTimerEvent(10);
    }

    timer() {
        if(llGetRegionTimeDilation() < 0.65) {
            llDie();
        }
        if(llGetRegionFPS() < 35) {
            llDie();
        }
    }
}




NearOwner

//default values
float maxpush=3;
float heartbeat=1;
integer quiet=TRUE;
string predname;
string fishname;

string scriptname;
float scan_dist=0.5;

default {
    state_entry() {
        scriptname = llGetScriptName();         
    }
    
    //mostly used to receive initialised parameters.
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":", "="], []);
        if(llList2String(cmd, 0) == "PARAM") {
            //llOwnerSay(str+":"+llList2String(cmd, 1)+":"+llList2String(cmd, 2));
            if(llList2String(cmd, 1)== "maxpush") {
                maxpush = llList2Float(cmd, 2);
                return;                
            }
            if(llList2String(cmd, 1)== "heartbeat") {
                heartbeat = llList2Float(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "quiet") {
                quiet = llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "predname") {
                predname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "fishname") {
                fishname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "EOF") {
                if(!quiet) {       
                    llOwnerSay(scriptname+":"+"heartbeat="+(string)heartbeat);
                    llOwnerSay(scriptname+":"+"maxPush="+(string)maxpush);
                    llOwnerSay(scriptname+":"+"quiet="+(string)quiet);        
                    llOwnerSay(scriptname+":"+"predname="+(string)predname);                        
                    llOwnerSay(scriptname+":"+"fishname="+(string)fishname);                                                     }
                
                if(llGetAttached()!=0) {
                    return;
                }
                if(llGetObjectName() == predname) {
                    return;
                }
    
                state run;
            }
        }
    }
}

state run
{
    state_entry()
    {
        llSetTimerEvent(heartbeat);
    }
    
    timer() {
        llSensor("", llGetOwner(), AGENT, scan_dist, PI);        
    }

    sensor(integer num_detected) {
        //slightly prefer to float around above my head
        vector push = -((llGetPos()-llDetectedPos(0)-<0,0,2>));
        //3, it's the magic number.
        push/=3;
        
        if(llVecMag(push)>maxpush) {
            push = push*maxpush/llVecMag(push);
            if(!quiet)
                llOwnerSay(scriptname + "Warning! Pushing "+(string)push);
        }
        llMessageLinked(LINK_SET, (integer)(llVecMag(push)*1000), "STATS:"+scriptname, NULL_KEY);    
        
        push*=llGetMass();
        llApplyImpulse(push, FALSE);                        
        
        llLookAt(llGetPos()+push, 1, 1);    
    }
    
    //if owner cannot be detected then die
    no_sensor() {
        //we may not be scanning far enough.
        if(scan_dist<64)
            scan_dist*=2;
        llMessageLinked(LINK_SET, -(integer)scan_dist, "STATS:"+scriptname, NULL_KEY);
    }

}








Repel
//default values
float heartbeat=1;
//sometimes things go weird and want to push the object a million miles away
//this restricts that to an upper limit.
float maxpush=1;
integer quiet=TRUE;
string predname;
string fishname;

string scriptname;
float maxCubed;
float scan_dist=.5;

default {
    state_entry() {
        scriptname = llGetScriptName();         
    }
    
    //mostly used to receive initialised parameters.
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":", "="], []);
        if(llList2String(cmd, 0) == "PARAM") {
            //llOwnerSay(str+":"+llList2String(cmd, 1)+":"+llList2String(cmd, 2));
            if(llList2String(cmd, 1)== "maxpush") {
                maxpush = llList2Float(cmd, 2);
                return;                
            }
            if(llList2String(cmd, 1)== "heartbeat") {
                heartbeat = llList2Float(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "quiet") {
                quiet = llList2Integer(cmd, 2);                
                return;                
            }
            if(llList2String(cmd, 1)== "fishname") {
                fishname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "predname") {
                predname = llList2String(cmd, 2);                
                return;
            }
            if(llList2String(cmd, 1)== "EOF") {
                if(!quiet) {       
                    llOwnerSay(scriptname+":"+"heartbeat="+(string)heartbeat);
                    llOwnerSay(scriptname+":"+"maxPush="+(string)maxpush);
                    llOwnerSay(scriptname+":"+"quiet="+(string)quiet);        
                    llOwnerSay(scriptname+":"+"fishname="+(string)fishname);                            
                    llOwnerSay(scriptname+":"+"fishname="+(string)predname);                                                
                }
                
                if(llGetAttached()!=0) {
                    return;
                }
                if(llGetObjectName() == predname) {
                    return;
                }
                maxCubed = llPow(maxpush, (1.0/3.0));
                    
                state run;
            }
            
        }
    }
}


state run
{
    state_entry() {
    
        llSetTimerEvent(heartbeat);
    }
    
    timer() {
        //benefit of this over SensorRepeat is we get objectname every time
        //since it has a tendency to change around.
        llSensor(llGetObjectName(), NULL_KEY, ACTIVE | PASSIVE, scan_dist, PI);        
    }

    sensor(integer num_detected) {
        //new magic idea, get the average vector of all detected items
        //push away from that!
        integer count=0;
        vector target=<0,0,0>;
        for(count=0;count<num_detected;++count) {
            target+=llDetectedPos(count);
        }
        target/=num_detected;
        
        //theoretically 0 should be the nearest
        vector push = ((llGetPos()-target));

        //for some reason it sometimes shoots off in random directions, apply this limiter
        if(llVecMag(push)>maxpush) {
            if(!quiet)
                llOwnerSay(llGetScriptName() + " Warning! Pushing "+(string)push);
            push=push*maxpush/llVecMag(push);
        }
        if(llVecMag(push) > llVecMag(<maxCubed, maxCubed, maxCubed>)) {
            push=<0,0,0>;
        } else {
            float newMag = maxpush - llVecMag(push);
            push=push*newMag/llVecMag(push);
        }
        
        
        //this message goes to stats module which sets text  
        llMessageLinked(LINK_SET, ((integer)(llVecMag(push)*1000)), "STATS:"+scriptname, NULL_KEY);  
        
        push *= -llGetMass();
        llApplyImpulse(push, FALSE);
              
    }
    
    //should send a message when attract is 0
    no_sensor() {
        if(scan_dist<64)
            scan_dist*=2;
        llMessageLinked(LINK_SET, -(integer)scan_dist, "STATS:"+scriptname, NULL_KEY);          
    }    
}











Stats
//map of strings to floats, or more precisely strided list.
list map;

set_text() {
    integer size = llGetListLength(map);
    integer count;
    string text="";
    for(count=0; count<size; count+=2) {
        text+=llList2String(map, count)+":"+llList2String(map, count+1)+"\n";
    }
    llSetText(text, <0,0,0>, 1);
}

//will accept link messages from all the other scripts and publish the details as settext
default
{
    state_entry()
    {
    }

    //str will be script name.
    //num will be value multiplied by 1000
    link_message(integer sender_num, integer num, string str, key id) {
        list cmd = llParseString2List(str, [":"], []);
        if(llList2String(cmd, 0) == "STATS") {
            if(llStringLength(str)==0) {
                llOwnerSay("Alert:"+str);    
            }
            str = llList2String(cmd, 1);
            integer index = llListFindList(map, [str]);
            if(index==-1) {
                map+=[str, num];
            } else {
                map = llListReplaceList(map, [num], index+1, index+1);
            }
            set_text();
        }
    }
    
    

}
There is one comment on this page. [Display comments/form]