您不能简单地使用相同的墙壁和地板绘图代码,因为墙壁和地板不在同一平面上:地板是平的(水平的),而墙壁是垂直的.所以你必须以不同的方式绘制它们.
您在地板工具箱中的x和y坐标就瓷砖的位置而言意味着“左/右”和“前/后”.对于砖块,左侧和右侧仍然有意义,但我们想要向上和向下替换向上和向下以反映垂直方向.所以我们的“y”有了新的含义.
现在,在数学中,y轴通常指向上方,而在2D计算机图形中指向下方.您可以选择 – 下面的代码假设它指向上方,因此y = 0表示“在楼层”.
所以让我们开始考虑订单.您发布的示例砖是用于墙(左上端)的墙.由于砖的黑色部分(墙的深度),我们必须确保我们首先绘制更右边的砖块,以便左侧的黑色深度将被更接近的砖块覆盖.同样的论点适用于墙顶部的黑色,我们必须首先绘制下部砖.
如果我们坚持前面讨论的x方向和y方向(x从左到右,y从下到上),这意味着我们必须在负方向上运行两个for循环:
for (int y = 3; y >= 0; y--) {
for (int x = 5; x >= 0; x--) {
...
}
}
现在的主要问题是,我们必须相对于其他砖块来抵消每块砖的绘制.让我们一个一个方向,从x方向开始.
让我们想象两块砖彼此相邻:
两者的左边有黑色深度部分可见,但右边的部分不应显示.因此,我们不能简单地将正确的图像偏移到PNG的整个宽度.实际上,假设砖块与地砖对齐,墙壁实际前部的宽度应与瓷砖宽度的一半相同.
int xCo = x * tileWidth / 2;
左边的黑墙深度不应该被忽略,因为我们可能想要将每个砖稍微向左偏移,以便墙的前角的x坐标与地砖对齐,而不是x-后角的坐标.
现在,每块砖的y坐标有点棘手,因为它不仅取决于砖块,还取决于x坐标:越靠右,我们应该绘制得越高.但是让我们暂时忽略x方向并尝试简单地绘制一列砖块:
同样,两块砖的y坐标之间的差值不是PNG的整个高度.与左/右情况不同,我们假设砖块与瓷砖对齐,允许我们使用tileWidth作为delta-x,砖块可以具有任意高度.但我们仍然可以从图像高度计算出实际的砖块高度,因为我们知道左侧的深度和顶部的深度必须对齐.
如果我们看一下砖PNG右上角的小透明三角形,我们注意到它的宽度和高度的比例必须与地砖的宽度和高度的比率相同.这允许我们从上面计算的xoffset计算yoffset,并使用它来推断砖的实际高度:
int yoffset = xoffset * tileHeight / tileWidth;
int wallHeight = wallHeight() - tileHeight / 2 - yoffset;
请注意,这仅在PNG边界处没有空白空间的情况下才起作用,并且由于舍入错误可能仍然会失败.因此,如果需要,您可以在此处添加Math.ceil()(或简称为1).
所以对于简单的列,我们现在很好:我们可以简单地将y变量与上面的wallHeight相乘.但如前所述,砖的x位置也会影响y像素坐标.如果我们再看两张相邻的砖块再看第一张照片,我们需要将右边的砖块移动到与左边的砖块对齐多少?嗯,这个实际上很简单,因为它与地砖一样:瓷砖高度的一半!
所以我们都准备好了.如果我们将所有内容放在一起,我们最终会得到一些像这样的代码:
int xoffset = wallWidth() - tileWidth / 2;
int yoffset = xoffset * tileHeight / tileWidth;
int wallHeight = wallHeight() - tileHeight / 2 - yoffset;
for (int y = 3; y >= 0; y--) {
for (int x = 5; x >= 0; x--) {
int xCo = x * tileWidth / 2;
int yCo = y * wallHeight - x * tileHeight / 2;
walls.draw(g, xCo - xoffset, yCo - yoffset);
}
}
(我假设wallWidth()和wallHeight()返回砖块PNG的宽度和高度.)
请注意,for循环之前的三个常量可以移出实际绘图代码 – 它们仅依赖于图像属性和其他常量,并且不必在每次绘制墙时重新计算.