Hi Michael,

I met at least few people who were using models in different coordinate frames so your results may vary. But assuming that your model is pretty standard: where forward points toward Y+, right points toward X+ and top points toward Z+, this piece of code could work for you.


osg::Matrixd ModelPositionCallback::calculatePositionMatrix(
  const osg::EllipsoidModel* ellipsoid,
const osg::Vec3d &newPosition, // in global coords (origin in ellipsod center) const osg::Vec3d &oldPosition) // in global coords (origin in ellipsod center)
{
// Math below may fail in Polar areas ( I hope you don't care bout them now)

// First compute movement in coord system tangent to ellipsoid in oldPosition
   // Axes of this local coordinate system match world directions:
   //+X points towards east direction
   //+Y points towards north direction
   //+Z points toward  up direction
   osg::Matrixd localToWorld, worldToLocal;

ellipsoid->computeLocalToWorldTransformFromXYZ( newPosition[0],newPosition[1],newPosition[2], localToWorld );
   worldToLocal = Matrix::inverse( localToWorld );

osg::Vec3d newPosInNewPosLocalCoordSystem = osg::Vec3d( 0,0,0 ); // == newPosition * worldToLocal;
   osg::Vec3d oldPosInNewPosLocalCoordSystem = oldPosition * worldToLocal;

osg::Vec3d moveInNewPosLocalCoordSystem = newPosInNewPosLocalCoordSystem - oldPosInNewPosLocalCoordSystem;

// now the question is how your model is oriented does model nose point toward X+ or Y+ or (i hope its not Z+)?
#if 0
// compass geographical heading measured clockwise from north is (radians): double heading = atan2( moveInNewPosLocalCoordSystem[0], moveInNewPosLocalCoordSystem[1] );
#else
// but we rather need heading angle measured anticlockwise from X+ and it would be (note swapped coords ) double heading = atan2( moveInNewPosLocalCoordSystem[1], moveInNewPosLocalCoordSystem[0] );
#endif

// usually pitch in local tangent space can be computed like this (radians):
   double pitch = atan2( moveInNewPosLocalCoordSystem[2],
hypot( moveInNewPosLocalCoordSystem[0], moveInNewPosLocalCoordSystem[1] ) );

#if 1 // I recommend to start initially with 0 pitch to be on safer side at the beginig - undef it later
   pitch = 0.0;
#endif

// roll cannot be computed using odlPos and newPos only so I assume 0 degrees
   double roll = 0.0;

   // Now it all depends on your model coordinate frame:
// I am assuming your model nose points toward Y+ and its roof points toward Z+ // Above means we need first to rotate its nose around Z+ by -90 degrees from Y+ to match X+ orientation

   osg::Matrix turnRight90DegreesClockwise =
osg::Matrix::rotate( osg::DegreesToRadians( -90.0 ), osg::Vec3d( 0,0,1 ) );

   osg::Matrix rotateToMatchLocalHeading =
osg::Matrix::rotate( heading, osg::Vec3d( 0,0,1 ) );// around Z+

   osg::Matrix rotateToMatchLocalPitch =
osg::Matrix::rotate( pitch, osg::Vec3d( 1,0,0 ) ); // around X+

   osg::Matrix rotateToMatchLocalRoll =
osg::Matrix::rotate( roll, osg::Vec3d( 0,1,0 ) );// around Y+

   // So the matrix without pitch and roll would be like this:
   osg::Matrixd matrix = turnRight90DegreesClockwise *
                                    rotateToMatchLocalRoll *
                                    rotateToMatchLocalPitch *
                                    rotateToMatchLocalHeading *
                                    localToWorld;

   return matrix;
}

HTH, It comes from my head, I have not tested this. There is a chance I forgot something really important ;-) But it should be clear eanough to understand the steps.
Wojtek Lewandowski

----- Original Message ----- From: "Michael Weber" <[email protected]>
To: <[email protected]>
Sent: Thursday, October 29, 2009 2:45 PM
Subject: Re: [osg-users] Rotating models with respect toCoordinateSystemNode / EllipsoidModel


Well, my programm is pretty much like the osgsimulation example. But instead of a aircraft which flies a constant route I use a model which flies an arbitrary trajectory.

For the positioning of the model I just use makeTranslate with the new X,Y,Z coordinates, which works as expected.

Now I try to rotate my model that way that it heads towards the direction it is "flying". For the rotation I use makeRotate with the new position and the previous position (taken from here (http://forum.openscenegraph.org/viewtopic.php?p=16587#16587)).

But somehow it works not as expected. The model always looks somewhere else. So I suppose either I use the makeRotate in a wrong way or the rotation somehow depends on the position within the EllipsoidModel (maybe some conversion from world to local coordinates or vice versa?)

Any ideas?

Michael

------------------
Read this topic online here:
http://forum.openscenegraph.org/viewtopic.php?p=18856#18856





_______________________________________________
osg-users mailing list
[email protected]
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

_______________________________________________
osg-users mailing list
[email protected]
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

Reply via email to