c# - XNA C# 2D 平铺引擎

标签 c# .net xna

我决定尝试使用 Xna 框架制作一款地下城爬行游戏。我是一名计算机科学专业的学生,​​对c#和.net框架非常熟悉。我对引擎开发的不同部分有一些疑问。

  1. 加载 map

我有一个图 block 类,用于存储图 block 的 Vector2 位置、2dtexture 和尺寸。我有另一个名为tilemap 的类,它有一个按位置索引的图 block 列表。我正在读取一个文本文件,该文件采用上面的数字格式,该文件将数字与图 block 列表中的索引相匹配,并创建一个具有正确纹理和位置的新图 block ,并将其存储到另一个图 block 列表中。

public List<Tile> tiles = new List<Tile>(); // List of tiles that I have added to the game
public List<TileRow> testTiles = new List<TileRow>(); // Tilerow contains a list of tiles along the x axis along with there vector2 position.

读取并存储 map 图 block 。

    using (StreamReader stream = new StreamReader("TextFile1.txt"))
                {
                    while (stream.EndOfStream != true)
                    {
                        line = stream.ReadLine().Trim(' ');
                        lineArray = line.Split(' ');
                        TileRow tileRow = new TileRow();
                        for (int x = 0; x < lineArray.Length; x++)
                        {  
        tileXCo = x * tiles[int.Parse(lineArray[x])].width;
        tileYCo =  yCo * tiles[int.Parse(lineArray[x])].height;
        tileRow.tileList.Add(new Tile(tiles[int.Parse(lineArray[x])].titleTexture, new Vector2(tileXCo,tileYCo)));
                        }
                        testTiles.Add(tileRow);
                        yCo++;
                    }
                }

用于绘制 map 。

 public void Draw(SpriteBatch spriteBatch, GameTime gameTime)
        {
            foreach (TileRow tes in testTiles)
            {
                foreach (Tile t in tes.tileList)
                {
                    spriteBatch.Draw(t.titleTexture, t.position, Color.White);
                }
            }
        }

问题: 这是我应该这样做的正确方法,还是应该存储引用我的图 block 列表的列表?

我将如何处理多层 map ?

  1. 碰撞检测

目前,我有一个方法,它循环遍历 testTiles 列表中存储的每个图 block ,并检查其尺寸是否与玩家尺寸相交,然后返回所有图 block 的列表。我有一个名为 CollisionTile 的图 block 类的派生类,当玩家和该矩形相交时,它会触发碰撞。 (公共(public)类 CollisionTile :平铺)

public List<Tile> playerArrayPosition(TileMap tileMap)
        {  
            List<Tile> list = new List<Tile>();
            foreach (TileRow test in tileMap.testTiles)
            {
                foreach (Tile t in test.tileList)
                {
                    Rectangle rectangle = new Rectangle((int)tempPosition.X, (int)tempPosition.Y, (int)playerImage.Width / 4, (int)playerImage.Height / 4);
                    Rectangle rectangle2 = new Rectangle((int)t.position.X, (int)t.position.Y, t.width, t.height);
                    if (rectangle.Intersects(rectangle2))
                    {
                        list.Add(t);
                    }
                }
            }
            return list;
        }

是的,我很确定这不是检查图 block 碰撞的正确方法。任何帮助都会很棒。

很抱歉这篇文章很长,如果有任何帮助,我们将不胜感激。

最佳答案

你是对的。这是一种非常低效的绘制和检查图 block 碰撞的方法。您应该查看的是 Quadtree数据结构。

四叉树将以允许您使用矩形查询世界的方式存储您的图 block ,并且您的四叉树将返回该矩形内包含的所有图 block 。

List<Tiles> tiles = Quadtree.GetObjects(rectangle);

这允许您仅选择需要处理的图 block 。例如,在绘制图 block 时,您可以指定视口(viewport)大小的矩形,并且只会绘制这些图 block (剔除)。

另一个例子是,您可以使用玩家的矩形查询世界,并且仅检查为世界的该部分返回的图 block 上的碰撞。

为了加载图 block ,您可能需要考虑加载到二维数组中,而不是列表中。这将允许您根据其位置获取图 block ,而不是在两个列表之间交叉引用它。

Tile[,] tiles = new Tile[,]
Tile tile = tiles[x,y];

此外,在这种情况下,数组数据结构比使用列表更有效。

关于c# - XNA C# 2D 平铺引擎,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17174874/

相关文章:

C#,多个 == 运算符重载,没有模糊的 null 检查

c# - 服务器响应 .net 上的重复条目

.NET Core 未在 Windows 2008 Server R2 中运行

c# - 我可以从我的 Windows 10 UWP 应用程序引用 .NetStandard 库吗?

c# - 单点触控 'Func' 代表?

c# - WIF: "ID1014: The signature is not valid. The data may have been tampered with"使用非商店证书时出错

c# - 数据表是否为空

c# - 确定哪个 .net 程序集加载了另一个

c# - 委托(delegate)细节

c# - 我如何在 XNA 中找到旋转变换的 2D 坐标?