En effet, je vais essayer d'être plus claire en ce qui concerne la matrice de rotation qui est le résultat des produits des matrice de rotation en X,Y et Z comme l'a expliqué très justement Hawk. Je vais te donner une fonction que j'ai faite pour passer d'une matrice de rotation à un vecteur cartésien (c'est à dire composé de x, y, z, Rx, Ry et Rz):
/**
@brief Convert the matrix to point.
@param l_Convention Represent the convention of the point.
@return The resulting point .
*/
GPoint GMatrix::toPoint(GPoint::Convention l_Convention) const
{
GPoint Point;
switch(l_Convention)
{
case GPoint::BRYANT:
Point.Rx = atan2( at(3,2) , at(3,3));
Point.Ry = atan2(-at(3,1) , sqrt(at(1,1)*at(1,1) + at(2,1)*at(2,1)));
Point.Rz = atan2( at(2,1) , at(1,1));
if((Point.Ry <= PI/2.0+0.0001)&&(Point.Ry >= PI/2.0-0.0001)) {Point.Rx=0.0;Point.Rz = -atan2( at(1,2) , at(2,2));}
if((Point.Ry >= -PI/2.0-0.0001)&&(Point.Ry <= -PI/2.0+0.0001)) {Point.Rx=0.0;Point.Rz = atan2(-at(1,2) , at(2,2));}
Point.X = at(1,4);
Point.Y = at(2,4);
Point.Z = at(3,4);
break;
case GPoint::EULER_XYZ:
Point.Rx = atan2(-at(2,3) , at(3,3));
Point.Ry = atan2( at(1,3) , sqrt(at(3,3)*at(3,3) + (-at(2,3))*(-at(2,3))));
Point.Rz = atan2(-at(1,2) , at(1,1));
if((Point.Ry <= PI/2.0+0.0001)&&(Point.Ry >= PI/2.0-0.0001)) {Point.Rx=0.0;Point.Rz = atan2( at(3,2) , at(2,2));}
if((Point.Ry >= -PI/2.0-0.0001)&&(Point.Ry <= -PI/2.0+0.0001)) {Point.Rx=0.0;Point.Rz = atan2( -at(3,2) , at(2,2));}
Point.X = at(1,4);
Point.Y = at(2,4);
Point.Z = at(3,4);
break;
case GPoint::EULER_ZYX:
Point.Rx = atan2( at(3,2) , at(3,3));
Point.Ry = atan2(-at(3,1) , sqrt(at(1,1)*at(1,1) + at(2,1)*at(2,1)));
Point.Rz = atan2( at(2,1) , at(1,1));
if((Point.Ry <= PI/2.0+0.0001)&&(Point.Ry >= PI/2.0-0.0001)) {Point.Rx=0.0;Point.Rz = -atan2( at(1,2) , at(2,2));}
if((Point.Ry >= -PI/2.0-0.0001)&&(Point.Ry <= -PI/2.0+0.0001)) {Point.Rx=0.0;Point.Rz = atan2( -at(1,2) , at(2,2));}
Point.X = at(1,4);
Point.Y = at(2,4);
Point.Z = at(3,4);
break;
case GPoint::THIRD_COLUMN:
Point.Rx = at(3,2);
Point.Ry = at(1,3);
Point.Rz = at(2,1);
Point.X = at(1,4);
Point.Y = at(2,4);
Point.Z = at(3,4);
break;
case GPoint::RPY:
Point.Rx = atan2( at(2,1) , at(1,1));
Point.Ry = atan2(-at(3,1) , sqrt(at(1,1)*at(1,1) + at(2,1)*at(2,1)));
Point.Rz = atan2( at(3,2) , at(3,3));
if((Point.Ry <= PI/2.0+0.0001)&&(Point.Ry >= PI/2.0-0.0001)) {Point.Rx=0.0;Point.Rz = atan2( at(1,2) , at(2,2));}
if((Point.Ry >= -PI/2.0-0.0001)&&(Point.Ry <= -PI/2.0+0.0001)) {Point.Rx=0.0;Point.Rz = atan2(-at(1,2) , at(2,2));}
Point.X = at(1,4);
Point.Y = at(2,4);
Point.Z = at(3,4);
break;
}
Point.setConvention(l_Convention);
return Point;
}
Tous les at(i,j) sont équivalant à une matrice (double** at) si tu veux. Tu n'as qu'a reprendre les formules. Les "if" sont là pour gérer les singularités. Toutes ses conversions suivent les normes Euleriennes. RPY signifie Roll Pitch Yaw.
Et voilà, j'espère que ça t'aidera.