Sign in to follow this  

Xna sprite movement problem

This topic is 3840 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I know i been posting a lot in the forums lately, i apologize. Im not that great at programming but i want to make a game real bad and i came across another issue. I tried looking for the answer online but failed. I want to mimic the movement of an asteriods game. I want to rotate the sprite which I did easily but how can I move the sprite straight from the angle it changed too? Anthony out

Share this post


Link to post
Share on other sites
Probably the best method is to create a Sprite class that will hold all the information for a sprite. You can start with just the texture and position, and eventually add in rotation and scale if necessary. So a simple class would be like this:


class Sprite
{
public Vector2 Position = Vector2.Zero;

public Texture2D Texture = null;

public Sprite()
{
}

public Sprite(Texture2D tex)
{
Texture = tex;
}
}



I'm not sure specifically what your question is regarding, the ship or the asteroids. There's a fun way to use inheritance to your advantage here. We can derive classes from the Sprite that way they get all those features, but then we can add more. Think of it like a tree showing animals and their ancestors and how they've evolved. So you can make things like a ShipSprite and AsteroidSprite. Since the asteroids will never change their direction, they are the simpler of the two.

Since we probably will want automation for the asteroids, we'll also add an Update method. So your asteroid class could be something like this:


class AsteroidSprite : Sprite
{
public Vector2 Velocity = Vector2.Zero;

public AsteroidSprite(Vector2 vel)
{
Velocity = vel;
}

public AsteroidSprite(Texture2D tex, Vector2 vel)
: base(tex)
{
Velocity = vel;
}

public void Update(GameTime gameTime)
{
Position += Velocity * (float)gameTime.ElapsedGameTime.TotalSeconds;
}
}



That's all. When you create the asteroid, you just set the initial velocity (which you can always change later) and possibly the texture. Obviously you're free to remove those constructors and use different ones, but this was just an example. Then when you call Update() on an AsteroidSprite it will move the position using the velocity it has.

Hopefully this will get you started in the right direction and then you can figure things out for the ShipSprite.

Share this post


Link to post
Share on other sites
thanks for the responce but i dont think you understood the question. Im not really making an asteriods clone but i want to know how the ship in the asteriods game moves like that so i can make a character that moves and rotates.

The movement I want to duplicate is when you turn with the left and right arrows they rotate the object and i did that already. but in the asteriods game when you hit the up arrow it moves the image at that angle. I dont know how to do that which is vital to what i want to do. Hopefully someone will know and help me out. Anthony out

Share this post


Link to post
Share on other sites
Gotcha.

Ok. So we'll still go with the Sprite class from above, but we'll add a few things in there for what we need.



class ShipSprite
{
//we need to make sure the ship only goes so fast
private static readonly float MaxVelocity = 50f;

public Texture2D Texture;
public Vector2 Position;
private Vector2 Velocity = Vector2.Zero;
private Vector2 Direction = new Vector2(1f, 0f);
private float Angle = 0f;

public void MoveForward()
{
Velocity += Direction;

if (Velocity.Length() > MaxVelocity)
{
Velocity.Normalize();
Velocity *= MaxVelocity;
}
}

public void MoveBackward()
{
Velocity -= Direction;

if (Velocity.Length() > MaxVelocity)
{
Velocity.Normalize();
Velocity *= MaxVelocity;
}
}

public void Update(GameTime gameTime)
{
Position += Velocity * (float)gameTime.ElapsedGameTime.TotalSeconds;
}
}



So what all did I put in and why?

The MaxVelocity variable is static and readonly (it exists as a member of the class and cannot be changed). This represents the maximum speed (in this case 50 units per second) a ship can go.

The Position, Direction, Velocity, and Angle are all pretty easy to figure out. We need to keep the Velocity because even we don't accelerate, in Asteroids the ship would continue moving even after you let go of a button.

To find the X and Y components of the direction, we will use Math.Cos and Math.Sin to find them. So when you want to rotate, we can add this method in there to handle it:


public void Rotate(float angle)
{
Angle = MathHelper.Clamp(Angle + angle, 0f, MathHelper.TwoPi); //keep things reasonable

//the Y is negative because sprite coordinates have -Y as the Up direction
Direction = new Vector2((float)Math.Cos(Angle), -(float)Math.Sin(Angle));
}



You may need to tweak the X and Y (by multiplying by a -1) for certain intervals of Angle, but that should work.

So now you just handle the input and call the correct method you need. Rotate() the ship to turn it (which also gives you the Angle for drawing it), then you use the Move methods to accelerate and deccelerate. And then just make sure you call Update each frame so that your ship continues moving.

For fun, you could also add in a drag effect where you slowly reduce the velocity on each call to update so that your ship eventually slows down a bit. But that's only if that's what you want.

Sorry this was so long, but hopefully it's useful as a starting point for you and others.

Share this post


Link to post
Share on other sites
thanks nick, yes the cos and sin math was exactly what I was missing. the draw method in xna actually does the rotation part for you. well now i can move my guy around at all angles. Thanks its apprecaited. I ran across another problem though im going to ask about soon. whew. game programming is evil LOl. Anthony out

the question in case you can answer it is I ahve a flickering and motion stutter problem when i move the character. makes me mad lol. Anthony out

Share this post


Link to post
Share on other sites

This topic is 3840 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this