Replying to myself, but I found the solution if anybody else might run into this. Calling getRotate() on the matrix can give unexpected results if there was also a scale transform involved. The correct way is to call Matrix.decompose(..) to get to the contributing parts:
ManipMatrix.preMult(osg::Matrix::translate( -pElem->getPivotPoint() )* osg::Matrix::scale( pElem->getScale() )* osg::Matrix::rotate( pElem->getAttitude() )* osg::Matrix::translate( pElem->getPosition() ) ); osg::Vec3 s,t; osg::Quat r,so; ManipMatrix.decompose( t, r, s, so ); pElemCache->setPosition( t ); pElemCache->setAttitude( r ); pElemCache->setScale( s ); Cheers, Morne On Fri, Dec 5, 2008 at 1:08 PM, Morné Pistorius <[EMAIL PROTECTED]> wrote: > Hi all, > > I am hitting my head against a brick wall with this one. I am trying > to use osgManipulators to edit nodes in my scene. I attach a node to > a manipulator, rotate it, and then detach the node from the > manipulator and apply the manipulator's MatrixTransform to the node's > PositionAttitudeTransform (all nodes that I manipulate have a PAT as > root) so that the PAT affects its children in the same way that the > osgManipulator affected its children. Here is the code snippet: > > > NodeUpdateCallback that updates node with osgManipulator's MatrixTransform: > > virtual void operator() ( osg::Node* node, osg::NodeVisitor* nv ) > { > osgManipulator::Selection * pSelection = dynamic_cast< > osgManipulator::Selection * > ( node ); > if ( pSelection && m_Manip->m_PrevMatrix != > m_Manip->m_Dragger->getMatrix() ) > { > // Apply the transform > for ( int i = 0; i < m_Manip->m_SelectionCache->getNumChildren(); ++i ) > { > osg::PositionAttitudeTransform * pElem = dynamic_cast< > osg::PositionAttitudeTransform * > ( pSelection ->getChild(i) ); > VOSGSceneElement * pElemCache = dynamic_cast< VOSGSceneElement > * > ( m_Manip->m_SelectionCache->getChild(i) ); > > osg::Matrix ManipMatrix = pSelection->getMatrix(); > > ManipMatrix.preMult(osg::Matrix::translate( -pElem->getPivotPoint() )* > osg::Matrix::scale( pElem->getScale() )* > osg::Matrix::rotate( pElem->getAttitude() )* > osg::Matrix::translate( pElem->getPosition() ) ); > > > pElemCache->setPosition( ManipMatrix.getTrans() ); > pElemCache->setAttitude( ManipMatrix.getRotate() ); > pElemCache->setScale( ManipMatrix.getScale() ); > } > > m_Manip->m_PrevMatrix = m_Manip->m_Dragger->getMatrix(); > } > } > > In this example a VOSGSceneElement is the node that I'm trying to > manipulate and is derived from PositionAttitudeTransform. pSelection > contains a copy of this. The copy in pSelection is transformed > correctly by the manipulator. In this update callback, I'm trying to > apply the same transform from pSelection to the VOSGSceneElement in > the scene graph. > > Unfortunately this doesn't work properly, and I'm having difficulty > figuring out how to apply the correct transformation. I would be very > grateful if anybody can point me in the right direction..How do I > apply a MatrixTransform to a PositionAttitudeTransform? > > As always, thank you! > Morne > _______________________________________________ osg-users mailing list osg-users@lists.openscenegraph.org http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org