Math 钻石上的像素坐标

Math 钻石上的像素坐标,math,coordinates,Math,Coordinates,我得到了一张图片,上面有两颗钻石并排放置,如下图所示 我知道的图像上唯一的坐标是顶角(绿色文本)。 当我点击图像时,我得到了该点的坐标,但我无法得到我在哪个钻石上。 例如,我点击红点,我如何知道x:260,y:179=顶部的钻石? 蓝色是属于左边的吗?等等 非常感谢你的帮助 编辑: 我最终使用了Canvas,但我认为SVG在我需要做的事情上也能很好地工作。你所需要的一切——只是保留什么是roration。这里是链接:) 应该旋转点,以便使正方形的边与坐标的栅格平行。旋转点应该是你将威胁为0,0

我得到了一张图片,上面有两颗钻石并排放置,如下图所示

我知道的图像上唯一的坐标是顶角(绿色文本)。
当我点击图像时,我得到了该点的坐标,但我无法得到我在哪个钻石上。
例如,我点击红点,我如何知道x:260,y:179=顶部的钻石?
蓝色是属于左边的吗?等等

非常感谢你的帮助

编辑:

我最终使用了Canvas,但我认为SVG在我需要做的事情上也能很好地工作。

你所需要的一切——只是保留什么是roration。这里是链接:)


应该旋转点,以便使正方形的边与坐标的栅格平行。旋转点应该是你将威胁为0,0钻石的钻石的1角。旋转后,您可以轻松定义从0,0指向的daimond数。基本上,您所拥有的可能是4个瓷砖的等距视图(基于您对菱形显示为梯形的评论)

一个快速的方法是创建两条平行于“钻石”的“轴”(但仍然相互交叉…这也很重要)。在给出的示例图像中,这意味着两条线彼此垂直,但旋转45度。在等轴测情况下,线不会彼此垂直,而是以其他角度(取决于您的视图)

一旦有了这两条直线,就可以创建一个“hitTest()”函数,该函数将获取单击点的坐标,并将计算两条直线方程。您对直线方程返回的实际数字并不感兴趣,只对符号感兴趣。该标志显示您的点位于直线的哪一侧

这意味着您的“菱形”将对应于这些符号对(每条直线方程一个符号)[-,-],[-,+],[+,-],[+,-],[+,-],[+,+]

(请注意,符号取决于直线的定义方式,换句话说,对于给定的点p,如果直线定义为“从左到右”或“从右到左”,则某些直线方程(L)中的符号将不同,或者更一般地说,符号将是反向的。)


有关所需直线方程形式的更多信息,可以使用矩阵获得,您可以导出选择菱形的快速公式

您需要将
(x,y)
转换为“菱形空间”。也就是说,一个坐标系,
(0,0)
是顶部菱形,
(1,0)
是右下方的坐标系,而
(0,1)
是左下方的坐标系

A * x = y
其中,
A
是变换,
x
是图像坐标,
y
是菱形坐标。要处理转换(
(0,0)
在两个空格中不是同一点),可以向向量添加另一行,该行始终为
1

可以同时变换多个向量,方法是将它们放在一起,使它们形成一个矩阵

[ a b dx ]   [ 225 337 113 ]   [ 0 1 0 ]
[ c d dy ] * [   2 114 114 ] = [ 0 0 1 ]
[ 0 0  1 ]   [   1   1   1 ]   [ 1 1 1 ]
                 ^   ^   ^-left  ^-^-^--- new coordinates for each point
                 |   '-right
                 '-top diamond
要求解第一个矩阵中的系数,需要除以第二个矩阵(或乘以逆矩阵)

结果是:

[ a b dx ]   [  (1/224) (1/224) (-227/224) ]
[ c d dy ] = [ (-1/224) (1/224)  (223/224) ]
[ 0 0  1 ]   [   0       0          1      ]
要将其放入程序代码中,请执行以下操作:

函数getDiamond(x,y){ 返回[(x+y-227)/224,(-x+y+223)/224]; } 例如:

>getDiamond(260179);//红色
[0.9464285714285714, 0.6339285714285714]
>getDiamond(250230);//绿色
[1.1294642857142858, 0.90625]
>getDiamond(189250);//蓝色
[0.9464285714285714, 1.2678571428571428]
>getDiamond(420230);//黄色的
[1.8883928571428572, 0.14732142857142858]
如果查看整数部分,可以看到坐标对应于哪个菱形。红色的位于
(0.94,0.63)
区域,该区域
(0,0)
非常接近
(1,0)
的边缘


NB.OP中的蓝色和绿色点绘制在错误的位置(或给定错误的坐标),因此我的函数结果将它们放置在不同的相对位置


如果您以象征性方式进行计算,您将得到以下结果:

[ a b dx ]   [ (y2 - y0)/M  -(x2 - x0)/M  -(x0*y2 - y0*x2)/M ]
[ c d dy ] = [-(y1 - y0)/M   (x1 - x0)/M   (x0*y1 - y0*x1)/M ]
[ 0 0  1 ]   [        0             0                   1    ]
其中
M=x1*y2-x2*y1-y0*x1+y0*x2+x0*y1-x0*y2

点0表示顶部菱形的位置,点1表示右侧菱形的位置,点2表示左侧菱形的位置

下面是一个计算此值的函数:

函数DiamondMaker(topx,topy,leftx,lefty,rightx,righty)
{
var M=topx*lefty-topx*righty+
leftx*righty-leftx*topy+
rightx*topy-rightx*lefty;
变量a=-(topy-righty)/M;
var b=(topx-右X)/M;
变量dx=-(topx*righty-topy*rightx)/M;
变量c=(topy-lefty)/M;
变量d=-(topx-leftx)/M;
变量dy=(topx*lefty-topy*leftx)/M;
返回函数(x,y){
返回[a*x+b*y+dx,c*x+d*y+dy];
};
}
var getDiamond=DiamondMaker(225,2,337114,113114);
//(与前面的示例相同)

我看到了两种可能的方法:直接检查点是否在菱形内和使用仿射变换。我将描述两者

直接点位置检查 要确定一个点是否在钻石内,必须检查它与钻石中点的偏差。你必须把X和Y偏差与钻石的X和Y范围成比例,你会得到两个因子。对于菱形内的所有点,这些因子的模值之和小于或等于1。在代码中,如下所示:

var dx=Math.abs(coords[0]-middle[0]);
var dy=Math.abs(coords[1]-middle[1]);

如果(dx/size[0]+dy/size[1],它与Javascript和jQuery有什么关系?这只是数学问题。抱歉,因为我是在jQuery中做的,但true与这些无关。我编辑了您的图像,将绿点放在底部菱形中,但
[ a b dx ]   [ (y2 - y0)/M  -(x2 - x0)/M  -(x0*y2 - y0*x2)/M ]
[ c d dy ] = [-(y1 - y0)/M   (x1 - x0)/M   (x0*y1 - y0*x1)/M ]
[ 0 0  1 ]   [        0             0                   1    ]