绘制等距瓷砖地图

发布于 2024-10-09 05:12:41 字数 3665 浏览 0 评论 0原文

我一直在使用 C# / XNA Game Studio 绘制等距地图,虽然我已经取得了很大的进展,但它看起来不太正确,我想知道是否有人可以提供帮助。

下面是我绘制地图的代码:

public void Draw(SpriteBatch theBatch, int drawX, int drawY)
    {

        if ((drawY % 2 == 0))
            theBatch.Draw(tileTexture, new Rectangle((drawX * width), (drawY * length / 2), width, length), Color.White);
        else
            theBatch.Draw(tileTexture, new Rectangle(((drawX * width) + (width / 2)), (drawY * length / 2), width, length), Color.White);
    }

该方法中的代码就像在嵌套的 for 循环中一样,从左到右、从上到下绘制。当 y 值为奇数时,该行会移动以适应,但看起来有点不对劲。

这是 8x5 地图的生成输出:

http://imgur.com/xpDRU.png

如您所见,它看起来不太正确,我不确定它是否与我的代码中的数学有关,或者是否与所有内容绘制的顺序有关。我对 C# 非常陌生,并且使用精灵,因此任何帮助将不胜感激。

因为它可能会有所帮助,所以这里是绘制地图的代码的其他相关部分。

整个 Tile 类:

public class Tile
{
    // Dimension variables
    int height;
    int width;
    int length;

    String type;
    Texture2D tileTexture;
    Vector2 coordinates;

    /// 
    /// Tile Constructor
    /// 
    public Tile(ContentManager theContent, String theType, Vector2 theCoordinates)
    {
        width = 68;
        length = 46;

        type = theType;
        coordinates = theCoordinates;

        // Sets the right texture to the texture ref
        if (theType == "grass")
            tileTexture = theContent.Load<Texture2D>(@"Tiles\iso_grass");
    }

    /// 
    ///  Draws the tile at the given location
    /// 
    public void Draw(SpriteBatch theBatch, int drawX, int drawY)
    {

        if ((drawY % 2 == 0))
            theBatch.Draw(tileTexture, new Rectangle((drawX * width), (drawY * length / 2), width, length), Color.White);
        else
            theBatch.Draw(tileTexture, new Rectangle(((drawX * width) + (width / 2)), (drawY * length / 2), width, length), Color.White);
    }


}

TileRow 类,包含一行图块。

public class TileRow
{
        public List<Tile> Row = new List<Tile>();
        public int rowLength;

        public TileRow(int theLength, int yIndex, ContentManager theContent)
        {
            rowLength = theLength;
            Tile thisTile;

            // Here the tiles are created and added to the row
            for (int x = 0; x < rowLength; x++)
            {
                thisTile = new Tile(theContent, "grass", new Vector2(x, yIndex));
                Row.Add(thisTile);
            }
        }

        /// 
        /// Draw -- invokes the draw method of each tile in the row
        /// 
        public void DrawRow(SpriteBatch theBatch, int currentY)
        {
            for (int x = 0; x < rowLength; x++)
            {
                Row[x].Draw(theBatch, currentY, x);
            }
        }
    }
}

和 MapStruct 类,它保存所有行

public class MapStruct
{

    public List<TileRow> allRows = new List<TileRow>();
    int depth;

    // Constructor
    public MapStruct(ContentManager theContent, int theDepth, int rowLength)
    {
        depth = theDepth;
        TileRow thisRow;

        // Here we make a row of tiles for each level of depth
        for (int y = 0; y < depth; y++)
        {
            thisRow = new TileRow(rowLength, depth, theContent);
            allRows.Add(thisRow);
        }
    }

    ///
    /// Draw - this method invokes the draw method in each tile row, which then draws each tile
    ///
    public void DrawMap(SpriteBatch theBatch)
    {
        for (int y = 0; y < depth; y++)
        {
            allRows[y].DrawRow(theBatch, y);
        }
    }
}

对于如何解决此问题的任何帮助,以及如何改进代码的建议,将不胜感激!

I've been working on drawing an isometric map with C# / XNA Game Studio, and while I've gotten pretty far it doesn't look quite right and I was wondering if anybody can help.

Here's the code I have for drawing the map:

public void Draw(SpriteBatch theBatch, int drawX, int drawY)
    {

        if ((drawY % 2 == 0))
            theBatch.Draw(tileTexture, new Rectangle((drawX * width), (drawY * length / 2), width, length), Color.White);
        else
            theBatch.Draw(tileTexture, new Rectangle(((drawX * width) + (width / 2)), (drawY * length / 2), width, length), Color.White);
    }

The code within this method acts as if it were inside a nested for loop, drawing left to right, top to bottom. When the y-value is odd, the row is shifted over to fit, however it looks a bit off.

This is the produced output for an 8x5 map:

http://imgur.com/xpDRU.png

As you can see, it doesn't quite look right, and I'm not sure if its an issue with the math in my code, or if it has to do with the order everything is being drawn in. I'm very new to C# and working with sprites, so any help would be greatly appreciated.

Because it might be helpful, here is the other relevant parts of code which draw the map.

The entire Tile Class:

public class Tile
{
    // Dimension variables
    int height;
    int width;
    int length;

    String type;
    Texture2D tileTexture;
    Vector2 coordinates;

    /// 
    /// Tile Constructor
    /// 
    public Tile(ContentManager theContent, String theType, Vector2 theCoordinates)
    {
        width = 68;
        length = 46;

        type = theType;
        coordinates = theCoordinates;

        // Sets the right texture to the texture ref
        if (theType == "grass")
            tileTexture = theContent.Load<Texture2D>(@"Tiles\iso_grass");
    }

    /// 
    ///  Draws the tile at the given location
    /// 
    public void Draw(SpriteBatch theBatch, int drawX, int drawY)
    {

        if ((drawY % 2 == 0))
            theBatch.Draw(tileTexture, new Rectangle((drawX * width), (drawY * length / 2), width, length), Color.White);
        else
            theBatch.Draw(tileTexture, new Rectangle(((drawX * width) + (width / 2)), (drawY * length / 2), width, length), Color.White);
    }


}

The TileRow class, which holds one row of tiles.

public class TileRow
{
        public List<Tile> Row = new List<Tile>();
        public int rowLength;

        public TileRow(int theLength, int yIndex, ContentManager theContent)
        {
            rowLength = theLength;
            Tile thisTile;

            // Here the tiles are created and added to the row
            for (int x = 0; x < rowLength; x++)
            {
                thisTile = new Tile(theContent, "grass", new Vector2(x, yIndex));
                Row.Add(thisTile);
            }
        }

        /// 
        /// Draw -- invokes the draw method of each tile in the row
        /// 
        public void DrawRow(SpriteBatch theBatch, int currentY)
        {
            for (int x = 0; x < rowLength; x++)
            {
                Row[x].Draw(theBatch, currentY, x);
            }
        }
    }
}

and the MapStruct class, which holds all the rows

public class MapStruct
{

    public List<TileRow> allRows = new List<TileRow>();
    int depth;

    // Constructor
    public MapStruct(ContentManager theContent, int theDepth, int rowLength)
    {
        depth = theDepth;
        TileRow thisRow;

        // Here we make a row of tiles for each level of depth
        for (int y = 0; y < depth; y++)
        {
            thisRow = new TileRow(rowLength, depth, theContent);
            allRows.Add(thisRow);
        }
    }

    ///
    /// Draw - this method invokes the draw method in each tile row, which then draws each tile
    ///
    public void DrawMap(SpriteBatch theBatch)
    {
        for (int y = 0; y < depth; y++)
        {
            allRows[y].DrawRow(theBatch, y);
        }
    }
}

Any help on how I could fix this issue, as well as advice on how I could improve my code would be greatly appreciated!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

黑寡妇 2024-10-16 05:12:41

看起来你的循环给每一行的 Y 添加了一点点。
我在你的 Tile 函数中找到了这个变量。

length = 46;

我没有检查过,但我相信“长度”是瓷砖的高度?如果是这样,请尝试稍微调整一下。也许,您忘记减去瓷砖的高度。因此,如果图块的边长约为 6 个像素,则偏移量 pr 的长度。行只有 40。

还要记住从上到下绘制,因为最接近相机的图块必须最后绘制,以产生深度错觉。

Looks like your loop adds a little to much to the Y on each row.
I found this variable in your Tile function.

length = 46;

I havent checked, but I believe "length" is the height of the tile? if so, try ajusting it a bit. Perhaps, you've forgotten to minus the height of the tile. So if the side of the tile is like 6 pixels, then the length for offset pr. row is only 40.

Also remember to plot from top and down, since the tiles nearest camera has to be plotted last, to make the depth illusion.

我偏爱纯白色 2024-10-16 05:12:41

我相信 BerggreenDK 是对的,但你的评论让人觉得你误解了他的答案。您的图块需要以仅包括绿色表面区域“屏幕高度”的 Y 偏移量绘制。因此,绘制完整的图块大小,但将行偏移长度 - 5(其中 10 是估计偏移量,5 是偏移量的一半,因为每行应仅偏移距离的一半)。

theBatch.Draw(tileTexture, new Rectangle((drawX * width), (drawY * (length) / 2), width, length - 5), Color.White);

...如果我的参数正确的话。

另外,行需要从后到前绘制,但它们似乎是从左到右绘制的?我不知道 XNA,所以无法显示代码来解决这个问题...当我仔细观察时,“较远”的一行中的一些图块被“较近”的图块过度绘制了。我不知道 XNA,也不知道绘图顺序是如何确定的,所以无法提供解决方案......

I beleive BerggreenDK is right, but your comment make it seem you misunderstood his answer. Your tiles need to be drawn at an Y offset that only includes the green surface areas "screen height". So, draw the full tile size, but offset the rows with length - 5 (Where 10 is the estimated offset and 5 is half that, as each row should be offset by only half the distance).

theBatch.Draw(tileTexture, new Rectangle((drawX * width), (drawY * (length) / 2), width, length - 5), Color.White);

...if I got the parameters right.

Also, the rows need to be drawn from back to front, but they seem to be drawn from left to right? I don't know XNA, so can't show code to fix that...when I look closely some tiles in a row "further away" is over-drawn by a tile "closer". I don't know XNA and don't get how the drawing order is determined, so can't offer a fix for that...

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文