   quaternion 6dof camera
  After battling for 5 days the quaterions and their behavior i finally got a grip on them and whant to share some experience on how to build a 6 degree of freedom camera(descent style) using quaternions. I used theese functions for that:(If you spend some time getting accointed with quaternions you will know how to code them)createQAxisAngle - create a quaternion from axis and anglemultiplyQ  - multiply 2 quaternionsQ2M    - quaternion to matrixconjugateQ    - conjugate quaternionSome code to initialize my camera:void camera_init(){struct vector3 v = {0,0,0};cm.q = createQ(1,v); // create quaternion with w=1 to be able to multiply itcm.pos.x=0;cm.pos.y=0;cm.pos.z=10;cm.dir.x=0;cm.dir.y=0;cm.dir.z=-1;cm.up.x=0;cm.up.y=1;cm.up.z=0;cm.right.x=1;cm.right.y=0;cm.right.z=0;}//So you have some position where you setup your camera every frame. For me it looks like this (omitting projection setup):void cm_run(){// cm.q is a quaternion in cm (camera) structuredouble m[16]; // create an opengl matrixQ2M(cm.q, m);glMultMatrixd(m); // transform matrix by itQ2M(conjugateQ(cm.q),m); // then conjugate quaternion to get from// ill explain later whycm.dir.x = m[8]; // new direction vector ripped out of conjugated matrixcm.dir.y = m[9]; cm.dir.z = m[10];cm.up.x = m[4];// new up vectorcm.up.y = m[5];cm.up.z = m[6];cm.right.x = m[0]; // new right vectorcm.right.y = m[1];cm.right.z = m[2];glTranslatef(-cm.pos.x,-cm.pos.y,-cm.pos.z);And then I have functions that do pitch roll and yaw when i call them:void cm_pitch(float speed){struct quaternion c = createQAxisAngle(cm.right,speed);cm.q=multiplyQ(cm.q, c);}void cm_yaw(float speed){struct quaternion c = createQAxisAngle(cm.up,speed);cm.q=multiplyQ(cm.q, c);}inline void cm_roll(double speed){struct quaternion c = createQAxisAngle(cm.dir,speed);cm.q=multiplyQ(cm.q, c);}The theory behind this is a bit hard to explain but i'll try:We have a quaternion which expresses the orientation of our body in space.So if we want to rotate our body left we:struct vector3 v = {0,1,0}; // up vectorstruct quaternion c = createQAxisAngle(v,speed);multiplyQ(q, c);Q2M(q, matrix)glMultMatrixd(matrix);but the problem with that code is that the up vector is rotated with our body and the new up vector is rotated. If we convert our quaternion to a rotation matrix we can read the new up vector from the y column of the matrix :matrix[4], matrix[5], matrix[6]. BUT we cannot use this coordinates for the up vector in the object local space because they are from the global space. So we must cancel the rotation with conjugateQ(q) , i can't really explain now that ingenious thought i had when i draw it on paper last evening and everything was suddenly clear , so now i forgot why exactly :D. Anyway if you draw it on paper and try to visualize it it gets kind of much clearer. So you have to conjugate and then take a matrix from that, and the vectors in that matrix are the ones you need for direction/up/right. I hope it gave some hints for people so they don't have to spend a week on that problem to figure it out. If you didn't understand what i mean read this first:http://www.gamedev.net/reference/articles/article695.aspthis one is about quaternions http://www.gamedev.net/reference/articles/article1095.aspand this one is usefull for code http://www.gamedev.net/reference/articles/article1691.aspAnyway it's a pity there are no tutorials on 6dof camreas on the net (i couldnt find them in 5 days using google) so i hope someone will find this usefull.   
  I remembered what that meant: when we use conjugatedquaterion this makes the opposite rotation using our orientation quaternion and the matrix expresses the vectors in object coordinates  correspond to vectors {0,0,-1} (direction vector) , {0,1,0} and {1,0,0,} in global coordinates! so we can actully make for example an up rotation no matter what.There's also a cheap way to generate the conjugated matrix along the normal one (6 multiplications extra) in Q2M function.   