3
votes

I am trying to create a class to control the camera in OpenGL. I have three methods to change the pitch yaw and roll of the camera. The methods take a float parameter to use as the amount of rotation to add.

The code in these methods is where I need help. The rotations are stored in a Vector3. So far for the change pitch method I have:

void changePitch(float degrees)
{
    float rads = MathHelp::degreesToRadians(degrees);
    m_rotation.x += cos(m_rotation.y) * rads;
}

This is as far as I could get by myself. It kind of works, the camera looks up and down while facing up or down the z axis and not while looking down the x axis. I tried adding z rotation:

m_rotation.z += sin(m_rotation.y) * rads;

But that didn't go very well.

1
The conversion from degree to radians must be applied before it goes into the trigonometric functions. Not multiplicated with the result of sin, cos or tan.datenwolf
The angles are stored in the vector as radians.Obi-Dan
So? rads is a constant that's to be multiplied in the angle that goes into sin, not to the result of it, i.e. ``cos(m_rotation.y * rads)` – however you can not simply "add" rotations. That's simply not how it works. Concatenation of rotations is multiplicative.datenwolf
rads is the conversion of the parameter (float degrees) into a radian. This is the amount to turn by.Obi-Dan
This method would be used to change the pitch by the given amount in degrees if that makes it easier to understand.Obi-Dan

1 Answers

3
votes

Assume you have the upVector, lookAtVector and rightVector 3D vectors that point towards up, looking at direction and right of your camera. Then, to properly increment pitch you should do the computation as follows:

void changePitch(angle) {
    angle = DegreeToRadian(angle);

    // Rotate lookAtVector around the right vector
    // This is where we actually change pitch
    lookAtVector = Normalize3dVector(viewDir * cos(angle) + UpVector * sin(angle));

    // Now update the upVector
    upVector = CrossProduct(rightVector, lookAtVector);
}

In the above excerpt, names of the arbitrarily used functions are self-explanatory.