3
\$\begingroup\$

I just have started making a simple 2D board game using XNA, but I got stuck at the movement of the cursor.

This is my problem:

I have a 10x10 table on with I should use a cursor to navigate. I simply made that table with the spriteBatch.Draw() function because I couldn't do it on another way.

So here is what I did with the cursor:

public override void LoadContent()
{
    ...
    mutato.Position = new Vector2(X, Y); //X=103, Y=107;
    mutato.Sebesseg = 45;
    ...
    mutato.Initialize(content.Load<Texture2D>("cursor"),mutato.Position,mutato.Sebesseg);
    ...
}

public override void HandleInput(InputState input)
{
    if (input == null)
        throw new ArgumentNullException("input");

    // Look up inputs for the active player profile.
    int playerIndex = (int)ControllingPlayer.Value;

    KeyboardState keyboardState = input.CurrentKeyboardStates[playerIndex];

    if (input.IsPauseGame(ControllingPlayer) || gamePadDisconnected)
    {
        ScreenManager.AddScreen(new PauseMenuScreen(), ControllingPlayer);
    }
    else
    {
        // Otherwise move the player position.
        if (keyboardState.IsKeyDown(Keys.Down))
        {
             Y = (int)mutato.Position.Y + mutato.Move;
        }
        if (keyboardState.IsKeyDown(Keys.Up))
        {
            Y = (int)mutato.Position.Y - mutato.Move;
        }
        if (keyboardState.IsKeyDown(Keys.Left))
        {
              X = (int)mutato.Position.X - mutato.Move;
        }
        if (keyboardState.IsKeyDown(Keys.Right))
        {
             X = (int)mutato.Position.X + mutato.Move;
        }
    }
}

public override void Draw(GameTime gameTime)
{
    mutato.Draw(spriteBatch);
}

Here's the cursor's (mutato) class:

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

namespace Battleship.Components
{
    class Cursor
    {
        public Texture2D Cursortexture;
        public Vector2 Position;
        public int Move;

        public void Initialize(Texture2D texture, Vector2 position,int move)
        {
            Cursortexture = texture;
            Position = position;
            Move = move;
        }

        public void Update()
        {
        }

        public void Draw(SpriteBatch spriteBatch)
        {
            spriteBatch.Draw(Cursortexture, Position, Color.White);
        }
    }
}

And here is a part of the InputState class where I think I should change something:

public bool IsNewKeyPress(Keys key, PlayerIndex? controllingPlayer,
                                       out PlayerIndex playerIndex)
{
     if (controllingPlayer.HasValue)
     {
           // Read input from the specified player.
           playerIndex = controllingPlayer.Value;

           int i = (int)playerIndex;

           return (CurrentKeyboardStates[i].IsKeyDown(key) &&
                   LastKeyboardStates[i].IsKeyUp(key));
     }
}

If I leave the movement operation like this it doesn't have any sense:

X = (int)mutato.Position.X - mutato.Move;

However if I modify it to this:

X = (int)mutato.Position.X--;

it moves smoothly. Instead of this I need to move the cursor by fields (45 pixels), but I don't have any idea how to manage it.

\$\endgroup\$
4
  • \$\begingroup\$ Personally, I hate when games try to mess with my mouse. Is there a strong reason that you need to change how the mouse moves? \$\endgroup\$ Mar 27, 2012 at 19:02
  • \$\begingroup\$ i want to make my game controllable only with the keyboard. \$\endgroup\$
    – Adorjan
    Mar 28, 2012 at 6:54
  • \$\begingroup\$ That makes much more sense. Most people (including the accepted answerer) assume mouse cursor when they hear the word "cursor". \$\endgroup\$ Mar 28, 2012 at 14:42
  • \$\begingroup\$ Ah indeed I did, but that only changes the naming of variables in my case :). \$\endgroup\$
    – Roy T.
    Mar 29, 2012 at 6:22

1 Answer 1

2
\$\begingroup\$

You can represent your board with fields as a 2D array of Rectangles. Each rectangle has a position on the screen.

Let's say your field looks like this:

Rectangle[,] field;

You would then index the field using the x and y coordinates:

Rectangle someField = field[x,y];

So far so good. Now the sprite you draw as your cursor can also be seen as a rectangle. So let's have it start at the lower right corner of your field. Note that we also store the indices of the fields.

int mouseIndexX = field.GetUpperBounds(0);
int mouseIndexY = field.GetUpperBounds(1);

Rectangle mouseRect = field[mouseIndexX, mouseIndexY ];

Now you have to update your mouse code to draw the mouse sprite at the place of mouseRect. The CursorTexture will completely overlap the field. You can use Rectangle.Inflate with negative numbers to draw a smaller cursor.

spriteBatch.Draw(CursorTexture, mouseRect, null, Color.White);

And now for movement, we want to hop the mouse cursor from field to field only if we detect a new keypress:

if(IsNewKeyPress(Keys.Left, ......)
{
    // This makes sure X stays between 0 and field.GetUpperBounds
    mouseIndexX = (mouseIndexX + field.GetUpperBounds(0) - 1) % field.GetUpperBounds(0);
    mouseRect = field[mouseIndexX, mouseIndexY ];
}

The same goes for Right, Up and Down.

I hope this helps. If you don't use a Rectangle[,] to store your fields on the board you must at least have some knowledge of their position and their width and height so you should be able to figure out the code to create the mouseRect.

\$\endgroup\$
4
  • \$\begingroup\$ Thanks for your response! Actually I'm doing it with keyboard control. Can you explain me that way too ? \$\endgroup\$
    – Adorjan
    Mar 28, 2012 at 6:48
  • \$\begingroup\$ This is all for keyboard control. All I did was name the variables mouse... you can change their name to cursor... or anything else, but note that the movement happens via the IsNewKeyPress method. \$\endgroup\$
    – Roy T.
    Mar 29, 2012 at 6:23
  • \$\begingroup\$ Ahha. Well, to be honest I don't really know how to construct a 2d array, so firstly I should resolv that problem. :D If I'm right I should make a class for a field with all properties than based on it make the array. \$\endgroup\$
    – Adorjan
    Mar 29, 2012 at 17:44
  • \$\begingroup\$ You don't need a 2D array percee. You just need a way to find the location of each field given an X and Y index. \$\endgroup\$
    – Roy T.
    Mar 29, 2012 at 22:18

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .