Saturday, December 20, 2014

XNA 4.0 game programming

DirectX and OpenGL are both excellent graphics libraries. DirectX works on Microsoft platforms, whereas OpenGL is available on a much wider range of platforms. DirectX tends to be updated more often, which means it has access to the very latest graphics features. OpenGL moves slower and the latest graphics features can only be accessed through a rather unfriendly extension mechanism. OpenGL’s slow movement can be quite advantageous as the interface rarely changes and therefore code written years ago will still work with the latest OpenGL versions. Each new version of DirectX changes the interface, which breaks compatibility and requires older code to be tweaked and changed to be updated.

DirectX can be used with C# using the Managed DirectX libraries, these libraries are no longer officially supported or updated. Managed DirectX has been superseded by Microsoft’s XNA game creation library. XNA uses DirectX, but it is a much higher level framework for quickly creating and prototyping games. SlimDX is an independent C# API for DirectX, which is a good alternative to Managed DirectX.

So, are you ready to write your first game in C#? Let's start with the XNA installation. But before that, I am assuming you already have visual studio 2013 installed. Don't worry if you have the older version, you need to get a different XNA distribution. Go to https://msxna.codeplex.com/releases/view/117230 and install the following:
  1. Install DirectX
  2. Install Xna Framework 4.0 Redistribution
  3. Install Xna Game Studio 4.0 Platform Tools
  4. Install Xna Game Studio 4.0 Shared
What is XNA? XNA Game Studio 4.0 Refresh is a programming environment that allows you to use Visual Studio to create games for Windows Phone, Xbox 360, and Windows. XNA Game Studio includes the XNA Framework, a set of managed libraries designed for game development based on the Microsoft .NET Framework.  This blog is just a tutorial to get you started to write your first game.

1. Create an XNA project: Open the visual studio and create a new "Windows Game (4.0)" project under "XNA Game Studio 4.0" templates. We just simply accept the default name as WindowsGame1. If you don't see the XNA template, you have not installed the right extension. Check out the link above and make sure that you are installing the right XNA extension matching your visual studio version.

2. Create an animation object: Notice that you have two projects under the WindowsGame1 solution. WindowsGame1 project and WindowsGame1Content. Add a new C# class to WindowsGame1 project. Call it Bullet.cs. This class represents an object that will bounce around and make you excited.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;

namespace WindowsGame1
{
    class Bullet
    {
        #region Fields

        // drawing support
        Texture2D sprite;
        Rectangle myRectangle;

        // velocity information
        Vector2 velocity = new Vector2(0, 0);

        // bouncing support
        int windowWidth;
        int windowHeight;

        #endregion
        #region Constructors
        //  Constructs a bullet with random direction and speed
        public Bullet(ContentManager contentManager, string spriteName, int x, int y, int windowWidth, int windowHeight)
        {
            this.windowWidth = windowWidth;
            this.windowHeight = windowHeight;
            LoadContent(contentManager, spriteName, x, y);

            // generate random velocity
            Random rand = new Random();
            int speed = rand.Next(30);

            //rand.NextDouble() return double-precision floating point number that is greater than or equal to 0.0, and less than 1.0.
            double angle = 2 * Math.PI * rand.NextDouble();

            //Velocity vector is the position and motion of a single particle using vectors
            //For example, suppose a particle is confined to the plane and its position is given by s=(cost,sint).
            //Then it travels along the unit circle at constant speed. Its velocity vector is v=(-sint,cost).

            velocity.X = (float)Math.Cos(angle) * speed;
            velocity.Y = -1 * (float)Math.Sin(angle) * speed;
        }


        // Constructs a bullet with the given characteristics

        public Bullet(ContentManager contentManager, string spriteName, int x, int y,
            Vector2 velocity, int windowWidth, int windowHeight)
        {
            this.windowWidth = windowWidth;
            this.windowHeight = windowHeight;
            LoadContent(contentManager, spriteName, x, y);
           this.velocity = velocity;
        }
        #endregion
        #region Public methods
        // Updates the bullet's location, bouncing if necessary
        public void Update()
        {
            // move the bullet
            myRectangle.X += (int)(velocity.X);
            myRectangle.Y += (int)(velocity.Y);
            // bounce as necessary
            BounceTopBottom();
            BounceLeftRight();
        }
        // Draws the bullet
        public void Draw(SpriteBatch spriteBatch)
        {
            spriteBatch.Draw(sprite, myRectangle, Color.White);
        }
        #endregion
        #region Private methods
        // Loads the content for the bullet
        private void LoadContent(ContentManager contentManager, string spriteName,int x, int y)
        {
            // load content and set remainder of draw rectangle
            sprite = contentManager.Load<Texture2D>(spriteName);
            //Change the bullet's size by changing the last two parameters of Rectangle
            myRectangle = new Rectangle(x - sprite.Width / 2, y - sprite.Height / 2, sprite.Width/5, sprite.Height/5);
        }
        private void BounceTopBottom()
        {
            if (myRectangle.Y < 0)
            {
                // bounce off top
                myRectangle.Y = 0;
                velocity.Y *= -1;
            }
            else if ((myRectangle.Y + myRectangle.Height) > windowHeight)
            {
                // bounce off bottom
                myRectangle.Y = windowHeight - myRectangle.Height;
               velocity.Y *= -1;
            }
        }
        private void BounceLeftRight()
        {
            if (myRectangle.X < 0)
            {
                // bounce off left
                myRectangle.X = 0;
                velocity.X *= -1;
            }
            else if ((myRectangle.X + myRectangle.Width) > windowWidth)
            {
                // bounce off right
                myRectangle.X = windowWidth - myRectangle.Width;
                velocity.X *= -1;
            }
        }
        #endregion
    }
}




3. Add your content: Find a bullet png or jpg picture from internet and save it somewhere. It could be any object. It could be your own picture and then add this png or jpg picture to your WindowsGame1Conent! Let's name the png file, bullet.png.

4. Set the resolution: Go back to Game1.cs and set the resolution by adding these two lines to your Game1 constructor method.

public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
            //set resolution
            graphics.PreferredBackBufferWidth = 800;
            graphics.PreferredBackBufferHeight = 800;
        }

5. Declare your variable: Declare a private variable bullet for Class Game1

  public class Game1 : Microsoft.Xna.Framework.Game
    {
        GraphicsDeviceManager graphics;
        SpriteBatch spriteBatch;
        Bullet bullet;

6. Load your game content: Our game content is just a bullet. To load that,  add a line to LoadContent method.

protected override void LoadContent()
        {
            // Create a new SpriteBatch, which can be used to draw textures.
            spriteBatch = new SpriteBatch(GraphicsDevice);

            // TODO: use this.Content to load your game content here
            bullet = new Bullet(Content, "bullet", 300, 100, 450, 450);
        }

7. Draw your object: To draw the bullet, we will use spriteBatch object. Add three lines to your draw method.

 protected override void Draw(GameTime gameTime)
        {
            GraphicsDevice.Clear(Color.CornflowerBlue);

            // TODO: Add your drawing code here
            spriteBatch.Begin();
            bullet.Draw(spriteBatch);
            spriteBatch.End();

            base.Draw(gameTime);
        }

8. Update your object: Well, we wanted our bullet to bounce around. The update logic goes to Update method by calling the Update method of bullet object:

 protected override void Update(GameTime gameTime)
        {
            // Allows the game to exit
            if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
                this.Exit();
            // TODO: Add your update logic here
            bullet.Update();
            base.Update(gameTime);
        }

Congratulations, You just created your first animation using XNA in C#. Well, we have to create a game now so players can interact with the animation.

9. Mouse Visible: After you run the program, you will notice when you hover your mouse over anywhere on the window Game, your mouse disappears. Since we want players to interact with the window game, we will need the mouse to be visible. This can be done by setting isMouseVisible to true.

 public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
            //set resolution
            graphics.PreferredBackBufferWidth = 800
            graphics.PreferredBackBufferHeight = 800

            IsMouseVisible = true;
        }

10. Create a bullet catcher: So for our game, we try to create a new bullet catcher. This new object basically follows the mouse movement. To make it simple, find a picture of a hand and save and add as hand.jpg under WindowsGame1Content.

  public class Game1 : Microsoft.Xna.Framework.Game
    {
        GraphicsDeviceManager graphics;
        SpriteBatch spriteBatch;

        //drawing support
         Bullet bullet;
        Texture2D bulletcatcher;
        Rectangle myRectangle;

11. Load content: Let's load the bullet catcher in LoadContent method:

  protected override void LoadContent()
        {
            // Create a new SpriteBatch, which can be used to draw textures.
            spriteBatch = new SpriteBatch(GraphicsDevice);
            // TODO: use this.Content to load your game content here
            bullet = new Bullet(Content, "bullet", 300, 100, 800, 800);
            bulletcatcher = Content.Load<Texture2D>("hand");
            //start bullet catcher in the center of window
            myRectangle = new Rectangle(800 / 2 - bulletcatcher.Width / 2, 800 / 2 - bulletcatcher.Height / 2, bulletcatcher.Width/2, bulletcatcher.Height/2);
        }

12. Draw the bullet catcher:

  protected override void Draw(GameTime gameTime)
        {
            GraphicsDevice.Clear(Color.CornflowerBlue);
            // TODO: Add your drawing code here
            spriteBatch.Begin();
            bullet.Draw(spriteBatch);
            spriteBatch.Draw(bulletcatcher, myRectangle, Color.White);
            spriteBatch.End();
            base.Draw(gameTime);
        }

13. Make the bullet follow the mouse: This can done by getting the mouse state and adjust the bullet position according to mouse position.

 protected override void Update(GameTime gameTime)
        {
            // Allows the game to exit
            if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
                this.Exit();
            // TODO: Add your update logic here
            //Make the bullet catcher follow the mouse
            MouseState mouse = Mouse.GetState();
            myRectangle.X = mouse.X - bulletcatcher .Width / 2;
            myRectangle.Y = mouse.Y - bulletcatcher .Height / 2;
            bullet.Update();
            base.Update(gameTime);
        }




 
 

No comments:

Post a Comment