Smooth camera motion

My first-person simulation uses GetAsynchKeyState to query the arrow keys. When the up arrow is pressed, my camera object’s forward() method is called, moving the camera forward a spell.

But the camera motion starts and stops too abruptly. For instance, when I start pressing the up arrow, I’m instantly at max velocity, and when I release it I stop instantaneously.

What is a good method to smooth starting and stopping of the camera? Maybe I should just use a start key that requires one keypress to get started, instead of relying on the user to hold down the key. A stop key would begin the stopping process, where the camera would decelerate until stopped.

Any ideas?

Basicaly it is just physics/math.

If you want to accelerate from a standing start, then simply use something like

if( SpeedNow < MaxSpeed) SpeedNow += AccelRate;
else if( SpeedNow > MaxSpeed) SpeedNow = MaxSpeed;

Deccelerating is just SpeedNow -= AccelRate and you make sure that it does no go below 0 (if you are trying to stop).

Another neat way is where the camera will move quickly to its desired location or orientation but will then gradually settle to a stop.

CurrentLocation += (FinalLocation - CurrentLocation) * 0.5;

The 0.5 can be replaced with anything in the range (0.0, 1.0]. The greater the number, the faster the movment. This method makes the camera move faster as the distance it has to cover increases, but slows down as the distance remaining to cover decreases. You could also use this for FinalRoll, FinalPitch, FinalYaw or anything else.

I forgot to mention that the above functions are done at every frame since they simulate acceleration/deceleration.

Yeah, I think that’s what I’ll do. I coded it up on paper and will implement when I get home. User presses start key, camera slowly accelerates to full speed. Opposite when he presses stop key.


Watch out if you plan on using floating point math like this… There are loads of opportunities for rounding errors and I’m fairly certain that adding a small amount to a floating point variable like this will cause unexpected results

Ya, that’s true. But it is trivial to place a cut off point (which is why I didn’t bother to specify one). It just depends on the developer when they want a certain value to be treated as zero (for example I would say anything less then 0.00001 is 0).

Also, if float errors are a big problem, then you could still implement it with integers.

However I am curious, what kind of things can happen if we left the above floating operation unchecked? Would it ever settle to 0.0? I guess I would have to check IEEE for the exact answer.