Thanks for the posts and ideas. I already know how to get the final values for position, linear velocity, linear acceleration, and Euler angle.
I have been researching quaternions some more. if it’s even possible I would like to know the instant angular velocity and angular acceleration which I tried to find in the code below. If it’s not possible to find the instant value I am confused as to what should be a vector and what should be a quaternion in your post above.
If it matters I am trying to use instant quaternions. I had problems with oscillating after a perfect collision using just the original and resulting vectors (I have not tried it with quaternions though).
The C code below is as close as I can get to the real motion engine:
void rotateShapeX(mat4 *m, quat *q, vec3 *angleRadians, vec3 *angularVelocity, vec3 *angularAcceleration)
{
*angularVelocity = GEAddVectors(*angularVelocity, GEMultiplyVectorAndScalar(*angularAcceleration, globalTimeStep));
*angleRadians = GEAddVectors(*angleRadians, GEMultiplyVectorAndScalar(*angularVelocity, globalTimeStep));
*q = GEQuaternionFromAxisAndAngle(*angularVelocity, angleRadians->x);
*m = GEMultiplyMat4(GEMat4FromRotate(angleRadians->x, 1.0, 0.0, 0.0), *m);
}
void rotateShapeZ(mat4 *m, quat *q, vec3 *angleRadians, vec3 *angularVelocity, vec3 *angularAcceleration)
{
*angularVelocity = GEAddVectors(*angularVelocity, GEMultiplyVectorAndScalar(*angularAcceleration, globalTimeStep));
*angleRadians = GEAddVectors(*angleRadians, GEMultiplyVectorAndScalar(*angularVelocity, globalTimeStep));
*q = GEQuaternionFromAxisAndAngle(*angularVelocity, angleRadians->z);
*m = GEMultiplyMat4(GEMat4FromRotate(angleRadians->z, 0.0, 0.0, 1.0), *m);
}
void shape(void)
{
mat4 rotateMatrix, rotateMatrix1, rotateMatrix2, rotateMatrix3;
rotateMatrix = rotateMatrix1 = rotateMatrix2 = rotateMatrix3 = GEIdentityMat4();
// These will be static once it works
vec3 angularVelocityVector1 = GERadiansFromDegreesVector(GESetVector(20.0, 0.0, 0.0));
vec3 angularVelocityVector2 = GERadiansFromDegreesVector(GESetVector(0.0, 0.0, 20.0));
vec3 angularVelocityVector3 = GERadiansFromDegreesVector(GESetVector(20.0, 0.0, 0.0));
// This is here so I can test only the angular velocity
vec3 angularAccelerationVector = GESetVector(0.0, 0.0, 0.0);
static vec3 angleEulerRadians, angleEulerRadians1, angleEulerRadians2, angleEulerRadians3;
static quat quaternion, quaternion1, quaternion2, quaternion3;
static char initialze = 0;
if (initialze == 0)
{
angleEulerRadians = angleEulerRadians1 = angleEulerRadians2 = angleEulerRadians3 = GESetVector(0.0, 0.0, 0.0);
quaternion = GESetQuaternion(0.0, 0.0, 0.0, 1.0);
initialze = 1;
}
// Rotate
rotateShapeX(&rotateMatrix1, &quaternion1, &angleEulerRadians1, &angularVelocityVector1, &angularAccelerationVector);
rotateShapeZ(&rotateMatrix2, &quaternion2, &angleEulerRadians2, &angularVelocityVector2, &angularAccelerationVector);
rotateShapeX(&rotateMatrix3, &quaternion3, &angleEulerRadians3, &angularVelocityVector3, &angularAccelerationVector);
// Multiply matrices (works)
rotateMatrix = GEMultiplyMat4(rotateMatrix1, rotateMatrix);
rotateMatrix = GEMultiplyMat4(rotateMatrix2, rotateMatrix);
rotateMatrix = GEMultiplyMat4(rotateMatrix3, rotateMatrix);
// Multiply Quaternions? (does not work)
quaternion = GETransformQuaternions(quaternion, quaternion1);
quaternion = GETransformQuaternions(quaternion, quaternion2);
quaternion = GETransformQuaternions(quaternion, quaternion3);
vec3 angularVelocityVector = GEAxisFromQuaternion(quaternion);
// Not sure if this is correct but I took out multipling globalTimeStep since it is already used in rotateShape*();
angularVelocityVector = GEAddVectors(angularVelocityVector, angularAccelerationVector);
angleEulerRadians = GEAddVectors(angleEulerRadians, angularVelocityVector);
glColor3f(0.0, 1.0, 1.0);
glPushMatrix();
glTranslatef( 2.0, 0.0, 0.0);
// This spins really fast
glMultMatrixf(GEMat4FromEulerAngle(angleEulerRadians).array);
glutWireSphere(2.0, 7.0, 7.0);
glPopMatrix();
glColor3f(1.0, 0.0, 0.0);
glPushMatrix();
glTranslatef(-2.0, 0.0, 0.0);
glMultMatrixf(rotateMatrix.array); // (Works)
glutWireSphere(2.0, 7.0, 7.0);
glPopMatrix();
}