Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles
(untagged)

XNA C# Rotation About 3 Axis

0.00/5 (No votes)
8 Sep 2013 1  
XNA - rotate model about each axis without gimbal lock

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()
{
// lets do some 90 turns and short moves with the keyboard
KeyboardState keys = Keyboard.GetState();
// only move once per key press, not constantly
if (keys.IsKeyDown(Keys.X) && !oldState.IsKeyDown(Keys.X) )
	{
	// rotate 90 degrees on X axis of the model
	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))
				{
				// move forward
				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

  • Initial version

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here