Welcome to the Second Life Forums Archive

These forums are CLOSED. Please visit the new forums HERE

Rotation of child around root?

Jacques Groshomme
Registered User
Join date: 16 Mar 2005
Posts: 355
01-27-2007 19:39
I'm having trouble figuring out how to rotate a child object around its root.

Say I have a two rectangular objects (say 2.0 x 0.25 x 1.0) side by side, linked. I want to rotate the child 90 degrees around the center point of the first, keeping the distance between their centerpoints the same. I'd like to use this same concept for other rotation degrees as well.

See this link for my example. The blue box represents the parent, the red represents the child.

I can wrap my head around every concept in LSL except rotation and physics. Luckily, I haven't had to deal with physics. But rotation is killing me here.
Lee Ponzu
What Would Steve Do?
Join date: 28 Jun 2006
Posts: 1,770
01-27-2007 22:02
Maybe it will help to change the way you look at the problem. It seems the same as

The center of the red is at a fixed distance from the center of the blue, and the red always faces the center of the blue.

So, given the current red position, and an angle, you compute the new position, and then rotate to face blue.


Hmmm. Now do that in quaternions 8-(
Lazink Maeterlinck
Registered User
Join date: 8 Nov 2005
Posts: 332
01-27-2007 23:35
I would suggest looking at Trig. Identies, such as Sine and Cosine, the answer you seek is in those identities :)
AJ DaSilva
woz ere
Join date: 15 Jun 2005
Posts: 1,993
01-28-2007 07:05
CODE
offsetRot(vector rotPoint, rotation rotAngle)
{
rotation newRot = llGetRot() * rotAngle;

vector currentPos = llGetPos();
vector newPos = rotPoint + ((currentPos - rotPoint) * rotAngle);

llSetPrimitiveParams([PRIM_POSITION, newPos, PRIM_ROTATION, newRot]);
}

:)
_____________________
Deanna Trollop
BZ Enterprises
Join date: 30 Jan 2006
Posts: 671
01-28-2007 07:24
Assuming un-tortured prims, this is a two-step process. To get the new position, multiply the child's initial local position by the desired rotation, in your example, 90°, or PI/2 radians, on the desired axis, which for the example below I will assume is the root prim's local Y axis:

CODE
llSetPos( llGetLocalPos() * llEuler2Rot( <0,PI_BY_TWO,0> ) );

Then do the same for rotation:
CODE
llSetLocalRot( llGetLocalRot() * llEuler2Rot( <0,PI_BY_TWO,0> ) );

Though this is an inefficient example. It's best to pre-compute the rotation offset and use it for both operations. Also, both can be done "simultaneously" within a single llSetPrimitiveParams call.


However, if your example is interpreted literally, that the prim to be rotated will be a box, you can torture it so that it's pivot is the same as the root prim's, by converting to a sphere, dimpling, then converting back to a box. Then you need only apply the rotation step described above.

[edit: Ah, crud. I tested this out in-world, but only with an axis-aligned root prim. After rotating the root prim, the whole effect falls apart.]
Jacques Groshomme
Registered User
Join date: 16 Mar 2005
Posts: 355
01-28-2007 08:11
From: AJ DaSilva
CODE
offsetRot(vector rotPoint, rotation rotAngle)
{
rotation newRot = llGetRot() * rotAngle;

vector currentPos = llGetPos();
vector newPos = rotPoint + ((currentPos - rotPoint) * rotAngle);

llSetPrimitiveParams([PRIM_POSITION, newPos, PRIM_ROTATION, newRot]);
}

:)


That works great if they're unlinked.

I need them linked but I was able to get it working by replacing

CODE

vector currentPos = llGetPos();
vector newPos = rotPoint + ((currentPos - rotPoint) * rotAngle);

with
CODE

vector newPos = llGetLocalPos() * rotAngle;

since linkset positions are relative the root. My pivot needing to be the root <0,0,0> means including it my calculation is meaningless.

I'm still not entirely sure why it works, but at least now I know to look up the magic that happens when you multiply vectors and rotations. :)

Thanks!


EDIT: OK, I've figured out the vector * rotation thing. Everything makes perfect sense now. Thanks again! :)