Jump to content

Help tracking targets with child prims (rotations only)


Fenix Eldritch
 Share

You are about to reply to a thread that has been inactive for 4692 days.

Please take a moment to consider if this thread is worth bumping.

Recommended Posts

I'm building a model ship to have rotating turrets. The idea is that when directed to "fire" on a target, the (child prim) turret would swivel around its z-axis only to face the target. Since the model will be physical and thus moving around, I need to ensure only the local z axis of the child prim changes... I've almost got it, but one last thing is tripping me up. I could use an extra set of eyes for any suggestions...

sensor(integer num_detected)
    {   //cause the child prim's forward (+X) axis to face target
        vector targetOffset = llDetectedPos(0) - llGetPos();        //target_pos - child_global_pos
        targetOffset.z = 0.0;                                       //don't care about z coordinates here
        rotation targetRot = (llRotBetween( <1.0,0.0,0.0>, llVecNorm(targetOffset) ) )*llGetRootRotation();

        llSetLinkPrimitiveParamsFast( LINK_THIS, [PRIM_ROT_LOCAL, targetRot] );
    }

 I think the problem is that last part of the calculation of targetRot.... if I don't multiply by the root rotation of the object, the child prim won't track the target accurately... it seems as the root's z rotation gets close to 180, the resulting rotation of the child turret becomes inverted.... but it still stays "upright" relative to the base.

Now if I DO multiply by the root rotation, the turret correctly tracks the target... but it no longer stays "locked" to only swiveling about its local z axis. The child prim will now always stay "upright" relative to the global frame.

(I hope I'm getting the terms right)

Link to comment
Share on other sites

llRotBetween is tricky in some cases
May I suggest you use llAxes2Rot which has a more firm grip on things

Something along this line:

sensor(integer num_detected)
{   //cause the child prim's forward (+X) axis to face target
    vector targetOffset = llDetectedPos(0) - llGetPos();        //target_pos - child_global_pos
    targetOffset.z = 0.0;                                       //don't care about z coordinates here
    rotation targetRot = llAxes2Rot( targetOffset, llRot2Up(llGetRot())%llVecNorm(targetOffset), llRot2Up(llGetRot()))/llGetRootRotation();

    llSetLinkPrimitiveParamsFast( LINK_THIS, [PRIM_ROT_LOCAL, targetRot] );
}

 

 

 

Link to comment
Share on other sites

Thanks for your response Dora!

I spent all day playing with your code. While trying to understand how the llAxes2Rot worked,  I stumbled across your wiki page further explaining it: llAxes2Rot right and wrong and the example function calls you had Vec2RotHor() really helped me understand! From that I was able to cobble this new routuine together:

vector targetOffset = llVecNorm( llDetectedPos(0) - llGetPos() );   //normalized direction to target from turret primvector UP = llVecNorm(llRot2Up(llGetRootRotation()));               //normalized direction of "Up" for the entire shipvector LEFT = llVecNorm(UP % targetOffset);     //calculate left direction by taking cross product of up and fwd directionstargetOffset = llVecNorm(LEFT % UP);            //recalculate fwd to confine  it to the horizontal plane (relative to the ship)rotation targetRot = llAxes2Rot(targetOffset, LEFT, UP) / llGetRootRotation();  //calculate final rotation using fwd,left,up...llSetLinkPrimitiveParamsFast( LINK_THIS, [PRIM_ROT_LOCAL, targetRot] );

 And it works! No mater the orientation of the ship, the turret child prim will accurately swivel to track a target while staying confined to its local z axis. Thank you!

I just have one more question.... why must we divide the rotation by the root prim's rotation? I don't quite understand why that makes it work...

 

Link to comment
Share on other sites

I am glad it helped you:smileyhappy: llAxes2Rot() is strong and demanding.


Fenix Eldritch wrote:

I just have one more question.... why must we divide the rotation by the root prim's rotation? I don't quite understand why that makes it work...

It is in order to transform the global rotation into a local rotation you can use with PRIM_ROT_LOCAL.
There probably is a few more ways to do it, but if this works it is fine with me:smileywink:

Link to comment
Share on other sites

You are about to reply to a thread that has been inactive for 4692 days.

Please take a moment to consider if this thread is worth bumping.

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now
 Share

×
×
  • Create New...