XNA – Camera Rotation

Posted: July 19, 2009 in C#, Game Programming, Programming, XNA
Tags: , ,

xna_logo

In this article, we will create a simple XNA program that load a 3D model, and rotating the camera around the model. In this example,  showing how to moving your camera position around the model. Camera target and camera up vector will remain same, what we need is to change camera position vector.

Untitled

First, define variables for projectionMatrix and viewMatrix

Matrix viewMatrix;
Matrix projectionMatrix;

Vector3 camPosition;
Vector3 camTarget;
Vector3 camUpVector;

float viewAngle;
float aspectRatio;
float nearPlane;
float farPlane;

Since we are using world space coordinates, this is very easy to do. Let’s first add a variable ‘angle’ to our class to store the current rotation angle. Just add this one to your variables.

private float angle = 0f;

Setting up camera

private void SetUpCamera()
{
    camPosition = new Vector3(35, 0, 0);
    camTarget = new Vector3(0, 0, 0);
    camUpVector = new Vector3(0, 1, 0);
    viewMatrix = Matrix.CreateLookAt(camPosition, camTarget, camUpVector);

    viewAngle = MathHelper.PiOver4;
    aspectRatio = graphics.GraphicsDevice.Viewport.AspectRatio;
    nearPlane = 0.5f;
    farPlane = 500.0f;
    projectionMatrix = Matrix.CreatePerspectiveFieldOfView(viewAngle, aspectRatio, nearPlane, farPlane);
}

Now, we should increase this variable with 0.05f every frame. We place it in Update method, it is called 60 times each second

protected override void Update(GameTime gameTime)
{
    if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
        this.Exit();

     angle += 0.010f;

     base.Update(gameTime);
 }

Rotating camera around Y Axis (Pitch). Rotating view matrix based on angle variable. Remember that CreateRotation method using radian.

Matrix rotationMatrix = Matrix.CreateRotationY(3 * angle);
Vector3 transformedReference = Vector3.Transform(camPosition, rotationMatrix);
Vector3 cameraLookat = camPosition + transformedReference;
viewMatrix = Matrix.CreateLookAt(transformedReference, camTarget, camUpVector);

Complete code…..

using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;
using Microsoft.Xna.Framework.Net;
using Microsoft.Xna.Framework.Storage;

namespace SimpleRotation
{
    public class Game1 : Microsoft.Xna.Framework.Game
    {
        GraphicsDeviceManager graphics;
        SpriteBatch spriteBatch;
        GraphicsDevice device;

        Model myModel;
        Matrix[] modelTransforms;

        Matrix viewMatrix;
        Matrix projectionMatrix;

        Vector3 camPosition;
        Vector3 camTarget;
        Vector3 camUpVector;

        float viewAngle;
        float aspectRatio;
        float nearPlane;
        float farPlane;

        private float angle = 0f;        

        public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
        }

        protected override void Initialize()
        {
           graphics.PreferredBackBufferWidth = 750;
           graphics.PreferredBackBufferHeight = 500;
           graphics.IsFullScreen = false;
           graphics.ApplyChanges();
           Window.Title = "Riemer's XNA Tutorials -- Series 1";        

           base.Initialize();
        }

        protected override void LoadContent()
        {
            device = graphics.GraphicsDevice;
            spriteBatch = new SpriteBatch(GraphicsDevice);

            myModel = Content.Load<Model>("p1_pencil");
            modelTransforms = new Matrix[myModel.Bones.Count];

            SetUpCamera();
        }

        private void SetUpCamera()
        {
            camPosition = new Vector3(35, 0, 0);
            camTarget = new Vector3(0, 0, 0);
            camUpVector = new Vector3(0, 1, 0);
            viewMatrix = Matrix.CreateLookAt(camPosition, camTarget, camUpVector);

            viewAngle = MathHelper.PiOver4;
            aspectRatio = graphics.GraphicsDevice.Viewport.AspectRatio;
            nearPlane = 0.5f;
            farPlane = 500.0f;
            projectionMatrix = Matrix.CreatePerspectiveFieldOfView(viewAngle, aspectRatio, nearPlane, farPlane);
        }

        protected override void UnloadContent()
        {
        }

        protected override void Update(GameTime gameTime)
        {
            if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
                this.Exit();

             angle += 0.010f;

             base.Update(gameTime);
         }

         protected override void Draw(GameTime gameTime)
         {
             device.Clear(ClearOptions.Target | ClearOptions.DepthBuffer, Color.CornflowerBlue, 1, 0);

             // setting up rotation
             Matrix rotationMatrix = Matrix.CreateRotationY(3 * angle);
             Vector3 transformedReference = Vector3.Transform(camPosition, rotationMatrix);
             Vector3 cameraLookat = camPosition + transformedReference;
             viewMatrix = Matrix.CreateLookAt(transformedReference, camTarget, camUpVector);

             //draw model
             myModel.CopyAbsoluteBoneTransformsTo(modelTransforms);
             Matrix worldMatrix2 = Matrix.CreateScale(0.01f, 0.01f, 0.01f);
             foreach (ModelMesh mesh in myModel.Meshes)
             {
                 foreach (BasicEffect effect in mesh.Effects)
                 {
                     effect.EnableDefaultLighting();
                     effect.World = modelTransforms[mesh.ParentBone.Index] * worldMatrix2;
                     effect.View = viewMatrix;
                     effect.Projection = projectionMatrix;
                 }
                 mesh.Draw();
             }          

             base.Draw(gameTime);
         }
     }
}



When you run the application, you will see that your model is spinning around its (0,0,0) point

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s