Introduction
XNA is a great platform for hobby graphics programming. I wanted a ship to move through space and rotate independently about each axis. This is simple once you know how, but my first few attempts did not work.
Background
I wanted to have a ship move through space and be able to use a separate control to rotate on each axis: x,y, z. My first attempt worked fine for one axis at a time, but once I rotate about one axis, the other axis got rotated and then I was rotating about some random axis. And I ran into gimbal lock: the math would stop working if I was vertical or tried to rotate too far one way.
A bit of research told me that the answer is matrices. Don't try to do the math by hand with trigonometry, use the built in XNA functions that handle model rotations. It took a bit of fiddling about, but here is the surprisingly simple control code:
protected void UpdateInput()
{
KeyboardState keys = Keyboard.GetState();
if (keys.IsKeyDown(Keys.X) && !oldState.IsKeyDown(Keys.X) )
{
modelRotation *= Matrix.CreateFromAxisAngle(modelRotation.Left, MathHelper.PiOver2);
}
else
{
if (keys.IsKeyDown(Keys.Y) && !oldState.IsKeyDown(Keys.Y) )
{
modelRotation *= Matrix.CreateFromAxisAngle(modelRotation.Up,
MathHelper.PiOver2);
}
else
{
if (keys.IsKeyDown(Keys.Z) && !oldState.IsKeyDown(Keys.Z))
{
modelRotation *= Matrix.CreateFromAxisAngle
(modelRotation.Forward, MathHelper.PiOver2);
}
else
{
if (keys.IsKeyDown(Keys.B) && !oldState.IsKeyDown(Keys.B))
{
modelPosition += modelRotation.Forward * 500;
}
else
{
if (keys.IsKeyDown(Keys.D0) && !oldState.IsKeyDown(Keys.D0))
{
modelPosition = Vector3.Zero;
modelRotation = Matrix.Identity;
}
}
}
}
}
oldState = keys;
}
Using the Code
This code can be easily updated to support smooth movement. Right now it makes the model jump, with each key press, but it shows the basic technique.
Points of Interest
XNA has lots of built in functions that make doing directX very simple. If you want to play with graphics, or learn it in a higher level platform, XNA is the way to go.
History