【问题标题】:XNA Rotate and Move SpriteXNA 旋转和移动精灵
【发布时间】:2012-12-05 04:47:22
【问题描述】:
public class dgc_Spaceship : DrawableGameComponent
{

    Texture2D shipTexture;
    Rectangle spriteRectangle;
    SpriteBatch spriteBatch;
    //
    bool horizisSelected = false;
    bool rotateSelected = false;
    bool fireisSelected = false;

    SpriteFont Count;

    //Controls for ship
    dgc_TriggerHorizontal triggerHorizantal;



    Vector2 spritePosition;
    Vector2 spriteOrigin;
    Vector2 direction;


    float rotation = 0.1f;
    Random x, y;


   List<Missle> missleCollection = new List<Missle>();
   List<Asteriod> asteriodCollection = new List<Asteriod>();


    Missle missle;

    Asteriod asteriod;

    public dgc_Spaceship(Game game)
        : base(game)
    {
        // TODO: Construct any child components here


        triggerHorizantal = new dgc_TriggerHorizontal(game);
        triggerHorizantal.triggerHorizantal += new EventHandler(triggerHorizantal_Handler);
        triggerHorizantal.triggerRotate +=new EventHandler(triggerHorizantal_triggerRotate);
        triggerHorizantal.triggerFire +=new EventHandler(triggerHorizantal_triggerFire);
        Game.Components.Add(triggerHorizantal);
        missle = new Missle(game);
        asteriod = new Asteriod(game);

        for (int i = 0; i < 2; i++)
        {
            missleCollection.Add(new Missle(game));
        }


        for (int i = 0; i < 2; i++)
        {
            asteriodCollection.Add(new Asteriod(game));
        }


      }




    /// <summary>
    /// Allows the game component to perform any initialization it needs to before starting
    /// to run.  This is where it can query for any required services and load content.
    /// </summary>
    public override void Initialize()
    {
        // TODO: Add your initialization code here

        base.Initialize();
    }

    protected override void LoadContent()
    {

        spriteBatch = new SpriteBatch(GraphicsDevice);
        shipTexture = Game.Content.Load<Texture2D>(@"Sprites\spaceship");
        spritePosition = new Vector2(450,320);
        missle.LoadContent();

        Count = Game.Content.Load<SpriteFont>(@"Sprites\Count");
        //
        x = new Random();
        y = new Random();

        foreach (Asteriod display in asteriodCollection)
        {
            display.LoadContent();

            int xVec = x.Next(0, 200), yVec = y.Next(0, 200);
            display.position = new Vector2(xVec, yVec);
        }





        base.LoadContent();
    }

    /// <summary>
    /// Allows the game component to update itself.
    /// </summary>
    /// <param name="gameTime">Provides a snapshot of timing values.</param>
    public override void Update(GameTime gameTime)
    {
        // TODO: Add your update code here

        spriteRectangle = new Rectangle((int)spritePosition.X, (int)spritePosition.Y, shipTexture.Width, shipTexture.Height);

        spriteOrigin = new Vector2(spriteRectangle.Width / 2, spriteRectangle.Height / 2);

        direction = new Vector2((float)Math.Cos(rotation), (float)Math.Sin(rotation));


        if (horizisSelected)
        {
           spritePosition.X-= 0.5f;
           spritePosition.Y-= 0.5f;

        }


        if (rotateSelected)
        {               
            rotation += 0.1f;
           // missle.rotateSprite(); 
            spritePosition += direction * 20 * gameTime.ElapsedGameTime.Milliseconds;
        }

        if (fireisSelected)
        {
            missle.update();
        }



        base.Update(gameTime);
    }

    public override void Draw(GameTime gameTime)
    {

        spriteBatch.Begin();
      //  missle.draw(spriteBatch,rotation);
        spriteBatch.Draw(shipTexture,spritePosition,null,Color.White,rotation,spriteOrigin,1f,SpriteEffects.None,0);
      //  spriteBatch.DrawString(Count,asteriodCollection.Count.ToString(),new Vector2(100,100),Color.Red);
        foreach (Asteriod display in asteriodCollection)
        {
            display.Draw(spriteBatch);
        }
         spriteBatch.End();

        base.Draw(gameTime);
    }


    public void triggerHorizantal_Handler(object sender, EventArgs e)
    {
        //Do Stuff
        horizisSelected = !horizisSelected;

    }

    public void triggerHorizantal_triggerRotate(object sender, EventArgs e)
    {
        //Do Stuff
        rotateSelected = !rotateSelected;
    }

    public void triggerHorizantal_triggerFire(object sender, EventArgs e)
    {
        //Do Stuff
        fireisSelected = !fireisSelected;
    }




    }
}

我的问题:

我似乎无法弄清楚这一点。我在屏幕上有 2 个功能按钮。点击后,船顺时针旋转,另一艘船向前移动。稍微搜索一下,我就找到了带有 Math.Sin/Cos 的公式,但我认为我没有正确实现它。

我需要它做的就是将船沿旋转方向移动。

工作原理: 用户将按下旋转按钮,它将顺时针旋转船。当它处于用户想要的位置时,他们点击旋转按钮将其停止在该特定方向。

点击水平按钮,船会朝那个方向前进。

【问题讨论】:

    标签: c# xna windows-phone


    【解决方案1】:

    您的代码建议您在选择旋转时将精灵移动到所需的方向,这需要在选择水平时进行,如果选择了旋转,那么您的方向应该改变(不是每一帧)

    编辑:(最多 5 分钟)

        if (horizisSelected)
        {
           //spritePosition.X-= 0.5f;
           //spritePosition.Y-= 0.5f;
           spritePosition += direction;// * 20 * gameTime.ElapsedGameTime.Milliseconds;
    
        }
    
    
        if (rotateSelected)
        {               
            rotation += 0.1f;
           // missle.rotateSprite(); 
    
            direction = new Vector2((float)Math.Cos(rotation), (float)Math.Sin(rotation));
            //spritePosition += direction * 20 * gameTime.ElapsedGameTime.Milliseconds;
        }
    

    如果您的飞船飞走,可能是因为经过了时间(毫秒),您将不得不对此进行调试

    【讨论】:

    • 你能帮我修改一下吗?当我移动代码时,船消失了。
    • 小问题,如何提高船前进的速度
    • 通常,您的方向向量是一个归一化向量,您可以将其乘以当前速度,然后乘以经过的游戏时间,以确保无论帧速率如何,您都以恒定速率移动。跨度>
    • @Sylvia - 我相信这是他在更新中描述的“飞走”。两件事: 1 - 确保您使用 TotalMilliseconds 而不是 Milliseconds,因为 Milliseconds 只是 TimeSpan 的毫秒组件,并且 TotalMilliseconds 需要所有时间并将其转换为毫秒。 2 - 很可能你的船移动得太快了,所以它消失了就离开了屏幕。确保对向量进行归一化,使其完全不影响速度,然后将速度降低到非常低的水平,看看是否有帮助。
    • 您也可以尝试 TotalSeconds,因为它会比 TotalMilliseconds 小
    猜你喜欢
    • 1970-01-01
    • 2015-12-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多