我已经从事web开发多年了,现在我正在慢慢地让自己参与游戏开发,对于我目前的项目,我有这个等距地图,在那里我需要使用算法来检测哪个字段被点击。顺便说一下,这些都是在浏览器中使用Javascript完成的。
地图
它看起来是这样的,我添加了一些数字来显示字段(tile)的结构和它们的id。所有的字段都有一个中心点(数组x,y),四个角在绘制时都基于这个中心点。
正如你所看到的,它不是一个菱形,而是一个锯齿形的地图,没有角度(自上而下的视图),这就是为什么我自己找不到答案,因为所有的文章和计算通常都是基于一个有角度的菱形。
这是一个动态的地图,所有的大小和数字都可以改变来生成一个新的地图。我知道这不是很多数据,但地图是根据地图和字段大小生成的。
-地图尺寸:x:800 y:400
-区域大小:80x80(边角之间)
-所有字段(x,y)的中心位置
提出一种算法,告诉客户端(游戏)鼠标在任何给定事件(点击,移动等)中位于哪个字段。
免责声明
我确实想提一下,我自己已经想出了一个可行的解决方案,但是我100%肯定它可以用更好的方式编写(我的解决方案涉及许多嵌套的if语句和循环),这就是我在这里问的原因。
这是我的解决方案的一个例子,我基本上是在最近的4个已知位置找到一个正方形,然后我根据两个最近的字段之间的最小正方形得到我的结果。这说得通吗?
问我是否漏掉了什么
我是这么想的
function posInGrid(x, y, length) {
xFromColCenter = x % length - length / 2;
yFromRowCenter = y % length - length / 2;
col = (x - xFromColCenter) / length;
row = (y - yFromRowCenter) / length;
if (yFromRowCenter < xFromColCenter) {
if (yFromRowCenter < (-xFromColCenter))--row;
else++col;
} else if (yFromRowCenter > xFromColCenter) {
if (yFromRowCenter < (-xFromColCenter))--col;
else++row;
}
return "Col:"+col+", Row:"+row+", xFC:"+xFromColCenter+", yFC:"+yFromRowCenter;
}
X和Y为图像中的坐标,length为网格的间距。
现在它返回一个字符串,只是为了测试。结果应该是row和col,这些是我选择的坐标:你的贴图1有坐标(1,0),贴图2是(3,0),贴图10是(0,1),贴图11是(2,1)。你可以用一两行把我的坐标转换成你的数字贴图。
和用于测试http://jsfiddle.net/NHV3y/
的JSFiddle欢呼。
EDIT:改变了返回语句,保留了一些用于调试的变量。
我过去使用过的一种像素完美的命中检测方法(在OpenGL中,但这个概念在这里也适用)是场景的屏幕外渲染,其中不同的对象被识别为不同的颜色。
这种方法需要双倍的内存和双倍的渲染,但是任意复杂场景的命中检测是通过简单的颜色查找完成的。
既然你想在网格中检测一个单元格,可能有更有效的解决方案,但我想提到这个,因为它的简单性和灵活性。
这个问题以前已经解决了,让我看看我的笔记…
这里有一些很好的资源:
From Laserbrain Studios, The basics of isometric programming
有用的文章张贴在这里的线程,在Java
让我知道这是否有帮助,祝你的游戏好运!
此代码计算给定不均匀间距的网格中的位置。应该很快;几乎所有的操作都是用数学方法完成的,只使用一个循环。我以后再考虑问题的另一部分。
def cspot(x,y,length):
l=length
lp=length+1
vlist = [ (l*(k%2))+(lp*((k+1)%2)) for k in range(1,y+1) ]
vlist.append(1)
return x + sum(vlist)