我想测试矢量(实际上是多边形顶点法线)是朝外还是内部。多边形缠绕CW,边缘从A(实心圆)到B(描边圆)。我有这些法线是初步计算的结果,现在我想测试他们的面孔。
喜欢这个。灰色法线应无效,而绿色法线应验证。可能我可以通过计算角度来做到,然后简单地比较它们,但我真的想在这里备用三角函数。
是否有任何便宜的方法只比较"斜率"不知何故? 像这样的http://bryceboe.com/2006/10/23/line-segment-intersection-algorithm/
中的Bryce Boe CCW算法答案 0 :(得分:1)
边矢量与法线矢量的叉积符号将告诉您法线矢量指向边的哪一侧。
计算(Xb - Xa).Ny - (Yb - Ya).Nx
。
这适用于凸多边形。
对于一般多边形,您必须将法线的支撑线与多边形轮廓相交;你会发现偶数个交叉点(有些可能是两倍);通过将它们连接成偶数,您将知道线的哪些部分在内部或外部。
答案 1 :(得分:1)
如果你将法线向量与由段的两个点形成的向量(从头到尾是顺时针方向)一起取得,那么要从段向量到正常,你必须逆时针移动。调用正常N和段向量S,逆时针检查变为:
if(cross(S, N) > 0)
// Bad
else
// Good
交叉产品以这种方式计算:
int cross(Vector p, Vector q)
{ return (p.x*q.y - p.y*q.x);
}
因此,如果法线是N =(0,1)并且S =(1,0),则叉积给出1 * 1-0 * 0 = 1> 0。 0,这告诉你正常指出。
答案 2 :(得分:0)
其他人建议的交叉产品标志测试是解决方案。
public static bool PointIsLeftOfSegment(Vector2 point, Vector2 a, Vector2 b)
{
float crossProduct = (b.x - a.x) * (point.y - a.y) - (b.y - a.y) * (point.x - a.x);
return (crossProduct > 0.0f);
}
对于原始问题,我为两个片段组成了测试(同时考虑锐角)。
bool acute = segmentA.IsPointLeft(segmentB.b);
bool leftA = segmentA.IsPointLeft(point);
bool leftB = segmentB.IsPointLeft(point);
bool outward = (acute) ? leftA && leftB : leftA || leftB;
bool inward = !outward;
Testbed就好了:https://vine.co/u/1137617915458592768