Domanda

so I'm working on a 2D castle defense style game for a class I'm taking and I'm having difficulties trying to get the arrows that the player fires to rotate properly as they fly in their parabolic arc. I'm sure many of you have played similar games before, but here is a link, for example's sake, of exactly what I'm trying to accomplish.

http://www.lostvectors.com/prelude/

I currently have an arrow class:

public class Arrow
    {
        public Texture2D arrowSprite;
        public double Xvelocity;
        public double Yvelocity;
        public int currentXpos;
        public int currentYpos;
        public int oldXpos;
        public int oldYpos;
        public float currentAngle;
        public float oldAngle;

        public Arrow() 
        {
            arrowSprite = WindowsGame1.Game1.arrow;
            Xvelocity = 10;
            Yvelocity = 10;
            currentXpos = 850;
            currentYpos = 200;
        }
    }

Note: The initial values I have set are just in place until I can get the animation to work correctly. I will have the values set based on user input once I have this problem solved.

I have the following code in my update method to update the arrows:

foreach (Player.Arrow arrow in onscreenArrows)
            {
                arrow.oldXpos = arrow.currentXpos;
                arrow.oldYpos = arrow.currentYpos;
                arrow.currentXpos -= Convert.ToInt32(arrow.Xvelocity);
                arrow.currentYpos -= Convert.ToInt32(arrow.Yvelocity);
                arrow.oldAngle = arrow.currentAngle;
                arrow.currentAngle = Convert.ToSingle(Math.Atan(arrow.Yvelocity/arrow.Xvelocity) * 180 / Math.PI);
                arrow.Yvelocity -= 1;
            }

and this snippet in my draw method:

foreach (Player.Arrow arrow in onscreenArrows)
        {
            spriteBatch.Draw(arrow.arrowSprite, new Vector2(arrow.currentXpos, arrow.currentYpos), null, Color.White, arrow.currentAngle - arrow.oldAngle, new Vector2(0, 4), 1.0f, SpriteEffects.None, 0);
        }

To clarify, the arrows are being fired from the right side of the screen and are traveling left. I apologize for my extremely messy code. I'm still very new to game programming and I've just been trying to get the animation to work properly before doing anything else. Any advice would be very helpful and greatly appreciated, thanks!!

È stato utile?

Soluzione

Your code actually looks pretty good. The only mistake I can see is that you are passing the spriteBatch.Draw function the rotation as:

arrow.currentAngle - arrow.oldAngle

The rotation given to SpriteBatch.Draw is the absolute rotation (MSDN) and so you should just pass it arrow.currentAngle

To be clear, you are currently passing it the change in angle (delta, or relative angle) from the last frame, when it has no memory of the last frame. You should just give it the angle to draw at.

Update Missed a few problems on your math.

  1. Math.Atan returns a radian, and spriteBatch.Draw expects a radian, so you don't need to do the conversion between degrees and radians (in fact, that is probably why you see it jumping around wildly).

  2. Your math gets the correct angle if you were travelling right. To get it travelling left, take 180 degrees and subtract the calculated angle.

With those improvements, your code becomes:

arrow.currentAngle = Math.Pi - Math.Atan(arrow.Yvelocity/arrow.Xvelocity);

Let me know how it goes!

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top