我试图找到一个矩形是否与凹多边形相交。我找到了这个算法:
double determinant(Vector2D vec1, Vector2D vec2){
return vec1.x*vec2.y-vec1.y*vec2.x;
}
//one edge is a-b, the other is c-d
Vector2D edgeIntersection(Vector2D a, Vector2D b, Vector2D c, Vector2D d){
double det=determinant(b-a,c-d);
double t=determinant(c-a,c-d)/det;
double u=determinant(b-a,c-a)/det;
if ((t<0)||(u<0)||(t>1)||(u>1))return NO_INTERSECTION;
return a*(1-t)+t*b;
}
如果我执行4次(从上到下,从上到下,从上到下,从下到右)*(我的多边形的所有边缘)这将有效且准确地告诉我矩形是否具有部分或里面的所有凹多边形?如果不是会遗漏什么?
由于
答案 0 :(得分:13)
代码试图找到两个段的交叉点 - AB和CD。
根据您解释这些操作的方式,有许多不同的方法可以解释它是如何做到的。
假设A点有坐标(xa,ya),B - (xb,yb)等等。我们说
dxAB = xb - xa
dyAB = yb - ya
dxCD = xd - xc
dyCD = yd - yc
以下两个线性方程组
| dxAB dxCD | | t | | xc-xa |
| | * | | = | |
| dyAB dyCD | | u | | yc-ya |
如果为t
和u
求解,将为您提供AB线(值t
)和线CD(值u
)上交叉点的比例位置)。如果该点属于相应的段,则这些值将位于[0, 1]
的范围内;如果该点位于该段之外(在包含该段的行上),则这些值将位于该范围之外。
为了解决这个线性方程组,我们可以使用众所周知的Cramer's rule。为此我们需要
的决定因素| dxAB dxCD |
| |
| dyAB dyCD |
与您的代码完全相同determinant(b - a, c - d)
。 (实际上,我在这里有determinant(b - a, d - c)
,但对于这个解释的目的并不重要。你发布的代码由于某种原因交换C和D,见下面的P.S.注释。
我们还需要
的决定因素| xc-xa dxCD |
| |
| yc-ya dyCD |
与您的代码完全相同determinant(c-a,c-d)
,
| dxAB xc-xa |
| |
| dyAB yc-ya |
正是determinant(b-a,c-a)
。
根据Cramer的规则划分这些决定因素将为我们提供t
和u
的值,这正是您发布的代码中所做的。
然后代码会继续测试t
和u
的值,以检查这些段是否实际相交,即t
和u
是否属于{{1} }} 范围。如果他们这样做,它会通过评估[0, 1]
来计算实际交叉点(相当于它可以评估a*t+b*(1-t)
)。 (再次参见下面的P.S.注释)。
P.S。在原始代码中,点D和C在代码执行c*u+d*(1-u)
的意义上是“交换”的,我在解释中c - d
。但这对算法的一般概念没有任何影响,只要一个人注意标志。
此C和D点的交换也是在评估交叉点时使用d - c
表达式的原因。通常,正如在我的解释中,人们希望在那里看到像a*(1-t)+t*b
这样的东西。 (我对此有疑问。我希望即使在您的版本中也会看到a*t+b*(1-t)
。可能是个错误。)
P.P.S。作者如果代码忘记检查a*t+b*(1-t)
(或非常接近0),则会在段并行时发生。
答案 1 :(得分:2)
我认为以下内容应该有效:
(1) for each e1 in rectangle_edges, e2 in polygon_edges
(1.1) if edgeIntersection(e1,e2) != NO_INTERSECTION
(1.1.1) return true
(2) if (max_polygon_x < max_rectangle_x) and (min_polygon_x > min_rectangle_x) and (max_polygon_y < max_rectangle_y) and (min_polygon_y > min_rectangle_y)
(2.1) return true
(2) return false
编辑:添加检查多边形是否在矩形内。
答案 2 :(得分:0)
据我所知,在快速浏览之后,它会尝试确定两个线段是否相交,如果它们相交,那么交点的坐标是什么。
不,确定你的矩形和多边形是否相交是不够的,因为你仍然会错过多边形完全位于矩形内部或相反的情况。