线形对象与平面相交
来源:互联网 发布:国牌lolita淘宝店铺 编辑:程序博客网 时间:2024/06/04 18:27
三维空间中的线形对象包括直线、射线和线段,为了统一三者的表达,在三维图形学中一般使用一个点和方向向量的方式来描述这些线形对象。
假设有一个点P位于线形对象上,方向向量是
基于这个表达式,直线方程可以描述为:
射线方程可以描述为(P是射线的端点):
在描述线段时,使用一对点{
平面的描述方式很多,最简单的是使用一般式
1. 直线与平面相交
如上图所示,直线方程L是
写成向量的形式是:
针对这个表达式展开讨论:
- 如果
n⃗ ⋅d⃗ =0 那么说明直线平行于平面或者直线位于平面之内。怎么判断直线是否位于平面之内呢?很简单,判断直线的另一个点P是否位于平面内即可,也就是把P点带入平面方程中,如果满足平面方程,那么直线位于平面内,不满足则二者平行。 - 如果
n⃗ ⋅d⃗ ≠0 ,那么直线和平面有唯一的交点,将t值带入到Q=P+td⃗ 可以求出二者的交点坐标。
总结如下:
n⃗ ⋅d⃗ =0 且aPx+bPy+cPz+D=0 直线位于平面内n⃗ ⋅d⃗ =0 且aPx+bPy+cPz+D≠0 直线与平面平行n⃗ ⋅d⃗ ≠0 直线与平面有唯一交点
在编码过程中由于浮点数的舍入误差,一般将结果与一个阈值
2. 射线与平面相交
射线的方程表达式与直线类似,但是射线稍有不同的是它表达式中的 P一定是射线的端点,如果P是射线的端点,那么计算的过程与直线中的结论完全一样,只不过需要在判断相交的时候t的取值,如果取值范围
总结如下:
n⃗ ⋅d⃗ =0 且aPx+bPy+cPz+D=0 直线位于平面内n⃗ ⋅d⃗ =0 且aPx+bPy+cPz+D≠0 直线与平面平行n⃗ ⋅d⃗ ≠0 且t≥0 射线与平面有唯一交点n⃗ ⋅d⃗ ≠0 且t<0 射线与平面没有交点
3. 线段与平面相交
线段的计算过程同样与射线类似,可以通过直线方程
来计算,需要注意的是线段的方向向量
总结如下:
- 直线方程的方向向量必须是
P1−P0 (直线和射线只要方向相同即可,甚至可以单位化方向向量,但是线段必须是P1−P0 )n⃗ ⋅d⃗ =0 且aPx+bPy+cPz+D=0 直线位于平面n⃗ ⋅d⃗ =0 且aPx+bPy+cPz+D≠0 直线与平面平行n⃗ ⋅d⃗ ≠0 且t∈[0,1] 射线与平面有唯一交点n⃗ ⋅d⃗ ≠0 且t∉[0,1] 射线与平面没有交点
4. 算法实现
使用OpenSceneGraph实现线段和平面的相交判断的代码如下:
/* * 线段和平面的相交关系判断:返回值是0表示没有交点,返回值是1表示二者有唯一交点,返回值是2表示线段位于平面内**/int intersectSegmentPlane(const osg::Plane& plane, const osg::LineSegment& lineSegment, osg::Vec3d& intersection){ double epsilon = 1e-6; osg::Vec3d planeNorm = plane.getNormal(); osg::Vec3d segmentDirection = lineSegment.end() - lineSegment.start(); double dotPlaneNormSegDir = planeNorm * segmentDirection; osg::Vec4d planeParam = plane.asVec4(); double lineInPlane = planeParam.x() * lineSegment.start().x() + planeParam.y() * lineSegment.start().y() + planeParam.z() * planeParam.z() + planeParam.w(); if (fabs(dotPlaneNormSegDir) < epsilon) { //如果直线端点满足平面方程,那么直线在平面内 if (fabs(lineInPlane) < epsilon) { return 2; } else { return 0; } } double planeNormDotP = -(planeParam.w() + planeNorm * lineSegment.start()); double t = planeNormDotP / dotPlaneNormSegDir; if (t < 0 || t > 1) return 0; intersection = lineSegment.start() + segmentDirection*t; return 1;}
5. 参考文献
- Line and Segment Intersections
- [书籍:Geometric Tools for Computer Graphics]
- 线形对象与平面相交
- 线形对象与平面的相交
- 射线与平面相交判断
- 平面与三维网格相交
- 射线与平面相交检测程序
- 射线与平面的相交检测
- 射线与平面的相交检测(Ray-Plane intersection test)
- 射线与平面的相交检测(Ray-Plane intersection test)
- 平面矩形与圆相交(重叠)的判断
- 射线与平面的相交检测(Ray-Plane intersection test)
- 射线与平面的相交检测(Ray-Plane intersection test)
- 射线与平面的相交检测(Ray-Plane intersection test)
- 线形回归与损失函数
- 平面内两条线段的位置关系(相交)判定与交点求解
- 平面内两条线段的位置关系(相交)判定与交点求解
- 平面内两条线段的位置关系(相交)判定与交点求解
- 平面内两条线段的位置关系(相交)判定与交点求解
- 平面内两条线段的位置关系(相交)判定与交点求解
- 文件系统读写--文件写过程代码分析
- 数据结构第七周项目1--建立顺序环形队列算法库
- 懒人读算法(四)-寻找最大连续值
- Ubuntu 16.04 安装 PyCharm-Python IDE
- 正则表达式(习题)
- 线形对象与平面相交
- 第四周 循环双链表应用
- 插入排序
- Linux ALSA声卡驱动之三:PCM设备的创建
- sql问题总结
- android常用框架集合
- 并行计算学习计划
- Fields in a "Serializable" class should either be transient or serializable序列化
- 职场,最需要的是主动