Jump to content
Wulfie Reanimator

"Animated" Prim Slice

Recommended Posts

This is a small utility function I wrote for someone because it was an interesting little thing. It's fairly safeguarded to prevent "accidents."

This is intended for cubes and cylinders, or any prim type that can be properly "sliced" at the ends. Its original purpose was to create a liquid fill/drain effect. The "animation" (changing slice in a loop) is optional, and can be used to just set the prim slice value once as well.

This was the original function + example:

// link: (0 for unlinked, 1-256 for linksets) The linked prim to change.
// amount: (0.02 to 1.0) The final value of Slice End.
// animate: (TRUE or FALSE) Whether or not to simulate filling/draining or just set the new Slice.
fill(integer link, float amount, integer animate)
{
    // Limit the range
    if(amount < 0.02) amount = 0.02;
    else if(amount > 1) amount = 1;

    vector slice = llList2Vector(llGetLinkPrimitiveParams(link, [PRIM_SLICE]), 0);

    if(animate)
    {
        float difference = amount - slice.y;
        float step = difference / 16.0;

        integer i; while(++i <= 16)
        {
            llSetLinkPrimitiveParams(link, [PRIM_SLICE, <0, slice.y += step, 0>]);
        }
    }
    else llSetLinkPrimitiveParams(link, [PRIM_SLICE, <0, amount, 0>]);
}

default
{
    touch_start(integer n)
    {
        // These are examples

        // Animate to 0.0 slice (empty)
        fill(2, 0, TRUE);

        llSleep(1);

        // Animate to 1.0 slice (full)
        fill(2, 1, TRUE);

        llSleep(1);

        // Set slice to 0.5 (no animation)
        fill(2, 0.5, FALSE);

        llSleep(1);

        // Back to full
        fill(2, 1, FALSE);
    }
}

And this version includes time as a parameter, to play the effect over X seconds. It also calculates the minimum steps needed based on maximum change per loop. (0.1 in this case)

// link: (0 for unlinked, 1-256 for linksets) The linked prim to change.
// amount: (0.02 to 1.0) The final value of Slice End.
// animate: (TRUE or FALSE) Whether or not to simulate filling/draining or just set the new Slice.
// time: (0 to inf)
fill(integer link, float amount, integer animate, float time)
{
    // Sanity checks so you can't break anything.
    if(amount < 0.02) amount = 0.02;
    else if(amount > 1) amount = 1;
    if(llGetNumberOfPrims() > 0) link = 0;
    else if(link < 1) return;
    else if(link > llGetNumberOfPrims()) return;
    time = llFabs(time);

    vector slice = llList2Vector(llGetLinkPrimitiveParams(link, [PRIM_SLICE]), 0);

    if(animate)
    {
        float difference = amount - slice.y;

        float step = 1; integer steps = 0;
        while(llFabs(step) >= 0.1) { steps += 8; step = difference / (float)steps; }

        time /= steps; integer i = 0; while(++i <= steps)
        {
            llSetLinkPrimitiveParamsFast(link, [PRIM_SLICE, <0, slice.y += step, 0>]);
            llSleep(time);
        }
    }
    else llSetLinkPrimitiveParamsFast(link, [PRIM_SLICE, <0, amount, 0>]);
}

default
{
    touch_start(integer n)
    {
        fill(2, 0, TRUE, 3);

        llSleep(1);

        fill(2, 1, TRUE, 1);
    }
}

 

  • Like 3

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


×
×
  • Create New...