【问题标题】:xna draw spritebatch only oncexna 仅绘制一次 spritebatch
【发布时间】:2014-01-12 12:32:30
【问题描述】:

我是 xna 编程的新手,我需要一些帮助...

我构建了一个 2D 游戏,具有静态背景 在我当前的屏幕中,有背景图像,左侧有 4 个大图像,我需要在右侧绘制 16 个小图像(或多或少 50x50)

所以这是我更新左侧16张图片位置的方法 更新只调用一次

private void letterLblsLocation() 
    {
        if (letterLbls.Count != 0)
        {
            letterlblposition = new Vector2(0f, 0f);
            lblvector = new Vector2(0f, 0f);
            int col = 1;
            int lblsize = ScreenManager.GraphicsDevice.Viewport.Height / 15;
            for (int lbl = 0; lbl < letterLbls.Count; lbl++)
            {
                letterlblposition.X = ScreenManager.GraphicsDevice.Viewport.Width - (col * lblsize);
                letterlblposition.Y += 5 + lblsize;
                if (letterlblposition.Y > ScreenManager.GraphicsDevice.Viewport.Height - lblsize)
                {

                    col = col + 3;
                    letterlblposition.Y = 5 + lblsize;
                }
                recsOnRight.Add(new Rectangle((int)letterlblposition.X, (int)letterlblposition.Y, lblsize, lblsize));

                lblvector.X = recsOnRight[lbl].X + 5;
                lblvector.Y = recsOnRight[lbl].Y;
                letterLbls[lbl].Position = lblvector;
            }
        }
    }

这是我的更新方法

public override void Update(GameTime gameTime, bool otherScreenHasFocus,bool coveredByOtherScreen)
    {
        base.Update(gameTime, otherScreenHasFocus, false);



        // Gradually fade in or out depending on whether we are covered by the pause screen.
        if (coveredByOtherScreen)
            pauseAlpha = Math.Min(pauseAlpha + 1f / 32, 1);
        else
            pauseAlpha = Math.Max(pauseAlpha - 1f / 32, 0);

        if (IsActive)
        {
            if(questionNeeded)
            {
                ChooseWord();
                ChooseLettersOnRight();
                LabelsWithLetters();
                letterLblsLocation();
            }


        }
    }

这是我的 Draw 方法

public override void Draw(GameTime gameTime)
    {

        spriteBatch.Begin();
        spriteBatch.Draw(background, new Rectangle(0, 0, ScreenManager.GraphicsDevice.Viewport.Width, ScreenManager.GraphicsDevice.Viewport.Height), Color.White);
        if (!questionNeeded)
        {
            for (int i = 0; i < 16; i++)
            {
                if (i < 4)
                {
                    Texture2D helpTexture = questionToDisplay.pic[i];
                    Rectangle helpRect = questionToDisplay.picRecs[i];
                    spriteBatch.Draw(helpTexture, helpRect, Color.White);
                }
                spriteBatch.Draw(labelSquare, recsOnRight[i], Color.White);
                }
            }

        spriteBatch.End();

现在我的问题是,当我尝试在右侧绘制 16 个 spritebatch 时,游戏变慢了 有没有办法只绘制一次 16 张图片,然后仅在玩家点击其中一张时重新绘制它们? 或者一种合并它们以绘制一个大图像而不是 16 个小图像的方法? 或者由于我在这里的经验很少,所以这段代码中是否有什么必须更改的内容,导致我在绘制这张照片时游戏运行缓慢?

提前致谢

【问题讨论】:

  • 16 个精灵甚至不应该有明显的性能影响。除非他们的分辨率非常高。你确定问题是由绘制代码引起的吗?
  • Nico,如果我删除了这个 for 循环,那么速度会再次恢复正常......所以这就是为什么认为问题出在 Draw 中,至于分辨率我尝试加载的图片有一个简单的蓝色方块 100x100 像素

标签: c# xna


【解决方案1】:

在 Draw 调用期间,您正在初始化 Graphics Device、SpriteBatch、SpriteFont 和 Textures。这真的很糟糕。

将这些初始化移动到 Draw 函数之外的 LoadContent() 函数中,并且只初始化一次。

【讨论】:

  • 好的,我把它们移到了 LoadContent()...事实上,有一个小的改进(谢谢)但是速度仍然很慢
【解决方案2】:

我刚刚从 draw 方法中删除了 for 循环,然后调用 spriteBatch.Draw 16 次,每个精灵一个。 是的,显然这不是最好的解决方案,但它有效并且速度再次恢复正常。 此外,正如 Jon 提到的,我将所有初始化从 Draw 或 Update 中移出,它们确实使代码更快。

【讨论】:

    【解决方案3】:

    您的代码 sn-p 中没有任何地方可以大大降低应用程序的速度。尝试使用秒表测试 Draw 和 Update 方法。使用 fps 60(默认情况下),总共不应超过 1/60 秒。尝试本地化降低游戏速度的具体部分。

    仅在不正确的情况下绘制图像怎么办。 XNA 不是 WinForms,并且 Draw() 调用每一帧,你应该清除屏幕并重新绘制你想要显示给玩家的所有内容。游戏循环很简单:一次调用 Initialize() 和 LoadContent,然后在“无尽”的 cicle 中以一定的频率调用 Update 和 Draw,最后调用一次 UnloadContent。

    如果您想在点击后更改图像,您需要有两个图像 - 单击和未单击,以及一些变量来保持每个图像的状态。您在 Update 方法中检查鼠标/键盘输入,更改变量状态并在 Draw 方法中决定将什么图像传递给 spritebatch.Draw() 调用。此外,如果您有一些由许多精灵组成的复杂场景,您可以在每次更新后仅将其绘制为渲染目标一次,然后将其绘制为一个实体纹理('lot' 表示 100 秒,就像在泰拉瑞亚中一样,但不是 16 个蓝色矩形) .

    【讨论】:

    • 问题是我确实尝试将慢速部分本地化。这就是我提到 for 循环的原因。我仍然不知道为什么使用 for 循环程序很慢,如果我编写相同的方法调用 16 次它工作正常。但是我以我在下面的回答中描述的方式克服了它。
    猜你喜欢
    • 1970-01-01
    • 2011-08-10
    • 2016-01-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多