问题的本质是求某个物体可见区域内的点数。可见区域是一个梯形。
鉴于:
一个对象数组(图中只有一个对象),每个对象包含以下数据:单位坐标,图中取为(0, 0)。半径向量r
。两侧之间的视角(角度АОВ
)。从对象到最近剪切边界(段AB
)和到远剪切边界(段CD
)的距离。具有点坐标的数组。
数据本身代表以下两类:
struct Point
{
float x;
float y;
};
struct Unit
{
Point position; // позиция игрока
Point direction; // радиус-вектор направления взгляда
float fov_deg; // угол зрения в градусах (между боковыми сторонами)
float z_near, z_far; // ближняя и дальняя границы отсечения
};
我们需要实现一个函数来计算所有单元可见区域中的点数。
int Task::calc_visible_points(const std::vector<Unit> &input_units, const std::vector<Point>& &points)
{
}
我的解决方案
我首先想到的是找到所得梯形的顶点坐标并找到这些顶点内的点。但我有限的数学知识只能帮助我计算 Ox 和 Oy 之间的向量角度r
,线段中间的坐标AB
,CD
它们也是点M
和N
。接下来我推理:知道向量,r
我可以将其移动等于角度 的角度MOB
,我将得到某种向量BD
,我需要找到的线段 位于其上。我还可以将矢量移动线段所在AOM
的角度AC
。接下来,找到梯形的顶点作为移位向量与线段AB
和CD
或AC
和 的交点BD
。也许有人能够补充我的方法或将其推向另一种选择。
您需要:
将点的垂直投影降低到线段 MN 上,并检查它是否位于线段内(系数
t
(此处)在 0..1 内),或降低到中心射线上如果您正在计算向量 OA、OB,那么只需检查向量乘积
OA x OP
和OP x OB
是否具有相同的符号即可 - 在这种情况下,该点位于扇区内部。如果这些向量是推测性的,并且在您的工作中仅使用角度,那么您可以计算出
cos(OP,OM)>cos(половинного угла(например,AOM))