如果判断点是否在凸多边形内,则有多种方法,方法简单,计算速度也快,直接使用物理引擎做判断也行
但实际问题中遇到的多边形不一定是凸多边形,它可能是凹边行或者复合多边形判断一个点在多边形内或多边形外,射线法是个不错的选择
射线法:,判断一点是否在多边形内或多边形外,只要从这点起,作一条射线,例如,沿x(或y)向直到负无穷,若与其相交的边是奇,该点位于多边形内;若为偶数,则点位于多边形外。
如下图:
1)若射线恰好穿过P1或者P2,那么这个交点会被算作2次,解决方案是,若P的纵坐标与P1,P2中的纵坐标相同,则将忽略此情况
2)若射线水平,则射线可能与其无交点,可能有无数个,则忽略此情况。
3)若射线竖直,且P的横坐标小于P1,P2的横坐标,则必然相交。
4)在判断相交之前,可先判断P是否在边(P1,P2)的上面,若在,可直接得到结论:P在多边形内部
计算x轴坐标
计算交点逻辑
tanα = b / c;
tanα = d / a;
d = b*a / c;
源代码:
-
bool HelloWorld::IsPointInsideShape(Vec2 pos,
std::
vector<Vec2>& m_vAllShape)
-
{
-
int nCross =
0;
-
int nCount = (
int)m_vAllShape.size();
-
Vec2 p = pos;
-
for (
int i =
0; i < nCount; i++)
-
{
-
Vec2 p1 = m_vAllShape[i];
-
Vec2 p2 = m_vAllShape[(i +
1) % nCount];
-
// 求解 y=p.y 与 p1p2 的交点
-
if (p1.y == p2.y)
-
{
// p1p2 与 y=p0.y平行
-
continue;
-
}
-
if (p.y < MIN(p1.y, p2.y))
-
{
// 交点在p1p2延长线上
-
continue;
-
}
-
if (p.y >= MAX(p1.y, p2.y))
-
{
// 交点在p1p2延长线上
-
continue;
-
}
-
// 求交点的 X 坐标 --------------------------------------------------------------
-
double x = (
double)(p.y - p1.y) * (
double)(p2.x - p1.x) / (
double)(p2.y - p1.y) + p1.x;
-
if (x > p.x){
-
nCross++;
// 只统计单边交点
-
}
-
}
-
// 单边交点为偶数,点在多边形之外
-
// if (nCross % 2 == 1) {
-
// log("在多边形内");
-
// }
-
// if (nCross % 2 == 0) {
-
// log("在多边形外");
-
// }
-
return (nCross %
2 ==
1);
-
}
转载自: https://blog.csdn.net/yanjunmu/article/details/46723407