Page 1 of 1

Animesh

Posted: Thu Feb 20, 2020 6:34 am
by Kimm Starr
Anyone have scripts for animesh?

Re: Animesh

Posted: Mon Feb 24, 2020 8:12 pm
by Gusher Castaignede
Kimm Starr wrote:
Thu Feb 20, 2020 6:34 am
Anyone have scripts for animesh?

Try this...

Code: Select all

////--------Shows/Hides mesh when animated....

float animation_speed = 0.5;
integer total_prims;
integer link_counter;

default
{ state_entry() { total_prims = llGetNumberOfPrims(); llSetTimerEvent(animation_speed ); } timer() { link_counter++; llSetLinkAlpha(LINK_SET, 0.0, ALL_SIDES); llSetLinkAlpha( link_counter,1.0, ALL_SIDES); if( link_counter == total_prims) { link_counter = 0; } }
}

//// -------- end of script --- copy up to here.

Re: Animesh

Posted: Mon Feb 24, 2020 11:51 pm
by Kimm Starr
Gusher Castaignede wrote:
Mon Feb 24, 2020 8:12 pm
Kimm Starr wrote:
Thu Feb 20, 2020 6:34 am
Anyone have scripts for animesh?

Try this...

Code: Select all

////---------Script starts here ---- copy from here

float animation_speed = 0.5;
integer total_prims;
integer link_counter;

default
{ state_entry() { total_prims = llGetNumberOfPrims(); llSetTimerEvent(animation_speed ); } timer() { link_counter++; llSetLinkAlpha(LINK_SET, 0.0, ALL_SIDES); llSetLinkAlpha( link_counter,1.0, ALL_SIDES); if( link_counter == total_prims) { link_counter = 0; } }
}

//// -------- end of script --- copy up to here.
Thanks so much!

Re: Animesh

Posted: Sun Mar 08, 2020 4:17 pm
by Graham Mills
That script shows/hides the parts making up the animesh. As far as I'm aware animations are played using llStartObjectAnimation (see http://wiki.secondlife.com/wiki/LlStartObjectAnimation)

Thus, for example, if you have an animation called "washhands" and put it in the root prim, add the script below to the root prim, save, and the animesh avatar will wash its hands.

Code: Select all

default
{
    state_entry()
    {
        llStartObjectAnimation("washhands");
    }
}


Kimm Starr wrote:
Mon Feb 24, 2020 11:51 pm
Gusher Castaignede wrote:
Mon Feb 24, 2020 8:12 pm
Kimm Starr wrote:
Thu Feb 20, 2020 6:34 am
Anyone have scripts for animesh?

Try this...

Code: Select all

////---------Script starts here ---- copy from here

float animation_speed = 0.5;
integer total_prims;
integer link_counter;

default
{ state_entry() { total_prims = llGetNumberOfPrims(); llSetTimerEvent(animation_speed ); } timer() { link_counter++; llSetLinkAlpha(LINK_SET, 0.0, ALL_SIDES); llSetLinkAlpha( link_counter,1.0, ALL_SIDES); if( link_counter == total_prims) { link_counter = 0; } }
}

//// -------- end of script --- copy up to here.
Thanks so much!

Re: Animesh

Posted: Sun Mar 08, 2020 5:40 pm
by Gusher Castaignede
Here's another three examples.....
SOURCE: https://youtu.be/0n_sgd_1920

Code: Select all


/////-----Use in a prim as a control device to click a prim/box to control animation or if you insist on using a mesh only approach then you must right click on the mesh and choose "touch".

integer running = 0;
string anim = "";
 
default
{
    state_entry()
    {
        llOwnerSay("Touch to start the animation");
    }
 
    touch_start(integer total_number)
    {
        if(running == 1)
        {
            llStopObjectAnimation(anim);
            llOwnerSay("Stopped " + anim);
            running = 0;
        }
        else
        {
            anim = llGetInventoryName(INVENTORY_ANIMATION, 0);
            llStartObjectAnimation(anim);
            llOwnerSay("Started " + anim);
            running = 1;
        }
    }
}


This version plays randomized animations....
SOURCE: https://youtu.be/HayC32mAaE0

Code: Select all


//---Play Random Animations....

float randomized_time = 7.0; // experiment with this time
float animation_speed = 0.5;
integer total_prims;
integer link_counter;

action()
{
    llSetLinkAlpha(LINK_SET, 0.0, ALL_SIDES);
    llSetLinkAlpha( link_counter,1.0, ALL_SIDES);
}
    
default
{
    state_entry()
    {
        total_prims = llGetNumberOfPrims();
        state warmup;
    }
}

state warmup
{
    state_entry()
    {
        state trigger;   
    }
    
    changed( integer c) 
    {
        if ( c & CHANGED_LINK) 
        {
            llResetScript();
        }
    }
}
    
state trigger
{
    state_entry()
    {
       llSetTimerEvent(animation_speed);
    }
        
    timer()
    {
       link_counter++;
       action();
       if( link_counter == total_prims)
       {
           link_counter = 0;
           state wait;
       }
    }
}

state wait
{
    state_entry()
    {
        llSetTimerEvent(llFrand(randomized_time));
    }
    
    changed( integer c) 
    {
        if ( c & CHANGED_LINK) 
        {
            llResetScript();
        }
    }
     
    timer()
    {
       state warmup;
    }
}


In this example you prevent root from animating....
SOURCE: https://youtu.be/HayC32mAaE0

Code: Select all

 
////----Root Prim number is 1 in a linkset. And 2 is the number of the first child prim if we link the prims sequentially . Initial value of the link_counter to 2. so that it will ignore  number 1 ( which is the root prim) ;


float animation_speed = 0.25; // change as per your need
integer link_counter = 2; // 2 is the first childprim number in a linkset
integer total_prims;
set_alpha()
{
    llSetLinkAlpha(LINK_SET, 0.0,-1);
    llSetLinkAlpha( LINK_ROOT,1.0,-1);
    llSetLinkAlpha( link_counter,1.0, -1);
}
default
{
    state_entry()
    {
        total_prims = llGetNumberOfPrims();
        llSetLinkAlpha(LINK_SET, 1.0,-1);
        llSetTimerEvent(animation_speed );
        state forward;
    }
}
state forward
{
    timer()
    {
        link_counter++;
        set_alpha();
        if( link_counter == total_prims)
        {
            state reverse;
        }
    }
}
state reverse
{
    timer()
    {
       link_counter--;
       set_alpha();
       if( link_counter == 2)
        {
            state forward;
        }  
    }
}


Re: Animesh

Posted: Sun Mar 08, 2020 6:23 pm
by Graham Mills
Again, it depends a little on how you define an animesh script. Only the first of those scripts plays an animation, the others would work just as well on a non-animesh linkset. That's not to say that standard linkset scripts are without merit. Indeed, as far as I can tell (and I'm very new to this), they will have to do all the heavy-lifting the NPC functions have built-in.
Gusher Castaignede wrote:
Sun Mar 08, 2020 5:40 pm
Here's another three examples.....
SOURCE: https://youtu.be/0n_sgd_1920

/////-----Use in a prim as a control device to click a prim/box to control animation or if you insist on using a mesh only approach then you must right click on the mesh and choose "touch".


Re: Animesh

Posted: Sun Mar 08, 2020 7:29 pm
by Gusher Castaignede
When it refers to linkset they are animated meshes with multiple meshes versus one single binded mesh....

Re: Animesh

Posted: Sun Mar 08, 2020 8:44 pm
by Kimm Starr
Hi, Here is a simple Animesh script I came accross. Any mesh Avatar (that you can wear) can be made into animesh. Pull mesh avatar out of inventory and onto the ground, click on it to edit. Under the features tab in edit menu, check the animated mesh box. Then add this script and one or more animations. Click on the avatar and it will perform those animations.


integer DEBUG = FALSE;
float INTERVAL = 20.0; //seconds
float MOMENT = 0.5; //seconds
string STANDBY = "Now AniMesh stops. Touch me to start.";
string WORKING = "Now AniMesh starts. Touch me again to stop.";
string now_anim = "";
integer num;
integer index;

debug(string msg)
{
if (DEBUG) llOwnerSay(msg);
}

StartAnim(string anim)
{
debug("Starting " + anim);
llStartObjectAnimation(anim);
llSleep(MOMENT);
}

StopAnim(string anim)
{
debug("Stopping " + anim);
//llSleep(MOMENT);
llStopObjectAnimation(anim);
llSleep(MOMENT);
}

NextAnim()
{
string old_anim = now_anim;
if (++index >= num) index = 0;
now_anim = llGetInventoryName(INVENTORY_ANIMATION, index);
StartAnim(now_anim);
if (old_anim != "") StopAnim(old_anim);
}

StopAllAnims()
{
list anims = [];
integer length = 0;
integer index;
string anim;
anims = llGetObjectAnimationNames();
length = llGetListLength(anims);
for (index=0; index < length; index++){
anim = llList2String(anims,index);
StopAnim(anim);
}
}

lookup()
{
num = llGetInventoryNumber(INVENTORY_ANIMATION);
string s = "No animetions";
if (num == 1) s = "1 animation";
else if (num > 1) s = (string)num + " animations";
llOwnerSay(s + " found.");
}

hotstart()
{
index = -1;
if (num > 0) NextAnim();
if (num > 1) llSetTimerEvent(INTERVAL);
}

shutdown()
{
llSetTimerEvent(0);
StopAllAnims();
now_anim = "";
}

default
{
state_entry()
{
lookup();
if (num >0) llOwnerSay(STANDBY);
}

on_rez(integer param)
{
shutdown();
llResetScript();
}

touch_start(integer num)
{
if (llDetectedKey(0) != llGetOwner()) return;
lookup();
if (num == 0) return;
if (now_anim != "")
{
shutdown();
llOwnerSay(STANDBY);
}
else
{
hotstart();
llOwnerSay(WORKING);
}
}

changed(integer change)
{
if (change & CHANGED_INVENTORY)
{
lookup();
if (now_anim == "" && num > 0) llOwnerSay(STANDBY);
}
}

timer()
{
NextAnim();
}
}

Re: Animesh

Posted: Sun Mar 08, 2020 9:16 pm
by Graham Mills
The depth of my ignorance in all matters mesh knows no bounds...
Gusher Castaignede wrote:
Sun Mar 08, 2020 7:29 pm
When it refers to linkset they are animated meshes with multiple meshes versus one single binded mesh....

Re: Animesh

Posted: Mon Mar 09, 2020 4:16 pm
by Graham Mills
I've been using llSetKeyframedMotion to get animesh avatars (bots hereafter) to patrol. Some simple code below is a first attempt to get a bot to move between a set of box prims (which are required but could be made phantom and transparent).

The markers have to be named marker0, marker1, marker2, et seq and I colour face 1 green to aid orientation as the bot derives its rotation from the next marker located within 40 m by means of the llSensor function.

The tendency for the bot to effect a gradual turn can be countered by having two prims per turn, one oriented roughly as per the previous prim and the next pointing in the direction of the next prim beyond the turn.

At present the total number of markers is entered in the script and the speed can also be varied.

The bot should die if no marker can be found but it can also be killed by chatting "die" on channel 123.

A small amount of code is borrowed from a more sophisticated script by Kayaker Magic which has lots of good ideas beyond the basics shown here.
viewtopic.php?t=1155#p8672

The avatar is Ferd's Quebot
https://www.outworldz.com/Secondlife/Po ... efault.htm

Hope this is of interest. It could, of course, be extended to read locations from a notecard, thereby reducing lag.

Image

Code: Select all

integer CHAN;
integer BOTCHAN = 123;
integer MARKERMAX = 6;//total number of markers
integer gMarkCount = 0;
vector  gTarget;
rotation gAngle;
rotation gRot;
rotation gRotOld;
float SPEED = 0.5; //smaller is faster

rotation f_rotDir(vector localAxisToPointWith, vector target, vector origin)
{   
     return llRotBetween(localAxisToPointWith*ZERO_ROTATION, target-origin);
}

SFrame(vector pos,rotation rot, float seconds)
{
//From Kayaker Magic
        llSetKeyframedMotion([pos-llGetPos(),rot/llGetRot(),seconds],
            [KFM_MODE,KFM_FORWARD,KFM_DATA,KFM_TRANSLATION|KFM_ROTATION]);
}

default
{
    state_entry()
    {
        llSetRot(ZERO_ROTATION);
        gRot = ZERO_ROTATION;
        llSensor("marker"+(string)gMarkCount, "", PASSIVE, 40.0, PI);
        llStartObjectAnimation("HF-male_walk");
        CHAN = llListen(BOTCHAN, "", NULL_KEY, "");
    }
    
    timer()
    {
        if (llVecDist(llGetPos(), gTarget) < 1.0)//arrived
        {
            if (gMarkCount == MARKERMAX-1)
            {
                gMarkCount = 0;
            }
            else
            {
                gMarkCount++;
            }
            llSensor("marker"+(string)gMarkCount, "", PASSIVE, 40.0, PI);
        }
    }
        
    sensor(integer total_number)
    {    
        gTarget=llDetectedPos(0);
        llSetTimerEvent(1.0);
        gRot = llDetectedRot(0);
        float distance = llVecDist(llGetPos(), llDetectedPos(0));
        SFrame(llDetectedPos(0), gRot, distance*SPEED);
        gRotOld = gRot;
    }

    no_sensor()
    {
       llDie();
    }

    listen(integer c, string name, key id, string msg)
    {
        if ((c == 123) && (msg == "die"))
        {
            llDie();
        }
    }
}