确定3D点是否在三角形内

时间:2009-06-15 10:41:00

标签: 3d geometry

给定3D点(x,y& z)和由三个其他3D点组成的三角形,如何确定该点是否为三角形?

我已经阅读了很多关于在2D中执行此操作的内容,最有帮助的是http://imusthaveit.spaces.live.com/blog/cns!B5212D3C9F7D8093!410.entry,但我正在努力将概念转移到3D - 任何人都可以帮助解决一般概念或代码示例吗? / p>

最终我想要做的是获得一个可以代表三角形内部的点列表。

7 个答案:

答案 0 :(得分:7)

给定点P和三角形A,B,C,计算:

1. the unit normal of triange (A, B, P)  - call it N1
2. the unit normal of triangle (B, C, P) - call it N2

(订单正确!)

现在想想点积N1 * N2。如果P在三角形的平面内,并且在三边内,那些法线应该是平行的,所以这个点积将是1.0000(或0.999 ......)。如果P保持在平面中但移动到BC侧以外,则这两个法线将相反:N1 * N2 == - 1。如果P不在平面内,则点积将是某个中间值。哎呀,我们还有一个漏洞 - 如果P超过了CA.我们需要再计算一次:

3.  the unit normal (C,A,P) called N3

进行这两项测试(在理想世界中):

N1*N2 == 1.0 ?
N2*N3 == 1.0 ?  

(测试N3 * N1是多余的)当然,测试将不得不允许一些slop来解决计算机算术的不完善问题。寻找(N1 * N2> 1-epsilon)其中epsilon是一个小值,取决于所需的精度和浮点类型。

您可能需要这些单位法线的公式。给定(A,B,C)计算叉积N =(B-A)x(C-B)。然后除以sqrt(N * N)。 “dot product”和“cross product”的定义很容易在教科书和维基百科等中找到。可以通过一些代数来提高性能,使其达到平方根。

我并不认为这是最快的算法,但应该有效(直到

答案 1 :(得分:6)

你真的在谈论三角形的3个点或金字塔的4个点吗?

单个点极不可能完全位于3d空间中的平面三角形平面上。

编辑:

作为三角形版本的想法(因为它似乎你想要)。您可以执行3x2D检查。从检查点和三个三角形点丢弃Z cooridinates,然后使用现有方法查看该点是否在平面中。然后不管只考虑X坐标,然后再忽略Y坐标。我确信它不是最有效的方法,但编码很简单。

答案 2 :(得分:5)

private bool PointInTriangle(Vector3[] TriangleVectors, Vector3 P)
    {
        Vector3 A = TriangleVectors[0], B = TriangleVectors[1], C = TriangleVectors[2];
        if (SameSide(P, A, B, C) && SameSide(P, B, A, C) && SameSide(P, C, A, B))
        {
            Vector3 vc1 = Vector3.Cross(Vector3.Subtract(A, B), Vector3.Subtract(A, C));
            if (Math.Abs(Vector3.Dot(Vector3.Subtract(A, P), vc1)) <= .01f)
                return true;
        }

        return false;
    }

    private bool SameSide(Vector3 p1, Vector3 p2, Vector3 A, Vector3 B)
    {
        Vector3 cp1 = Vector3.Cross(Vector3.Subtract(B, A), Vector3.Subtract(p1, A));
        Vector3 cp2 = Vector3.Cross(Vector3.Subtract(B, A), Vector3.Subtract(p2, A));
        if (Vector3.Dot(cp1, cp2) >= 0) return true;
        return false;

    }

答案 3 :(得分:3)

描述的方法here非常适合2D情况。我认为可以修改它以在3D中工作。这并不直接回答您的问题,但如果您了解这种方法,您应该能够找出如何修改它的3D(如果可能的话)。

答案 4 :(得分:2)

  1. 使用三角形的三个点来计算它们所在平面的等式
  2. 检查您的观点是否满足该等式。

答案 5 :(得分:2)

给定3D点P和三角形T1,T2,T3的三个顶点

现在,您可以将所有点转换为在三角形中查找点的2D问题。 此外,P与平面的距离将告诉您该点与三角形之间的距离有多近。

如果我理解您的详细说明,您计划检查3D网格中的所有体素,以确定它们是否在给定的三角形中?这将是非常低效的 - 我认为Bresenham's line algorithm的3D版本可能适用于您想要做的事情。找到T1所在的体素,然后通过体素向T2前进,重复T3并返回T1,这将是微不足道的。

答案 6 :(得分:0)

我对此(旧)帖子的改进观察。 如果你(预)计算三角形的U&amp; V向量(U是从A到B的向量,V是在标准三角形ABC中从A到C的向量,U和V都不是不一定< / em>单位长度)然后矢量P(从A到点)可以按以下方式使用:计算P与U的点积和P与V的点积。如果两个点积较小(或等于边缘上的点) )对于一个但是更大(或等于)为零并且它们的总和小于(或等于)为1,那么该点在内部,否则它在外面。这种方法比首先比较法线(交叉产品)以及它们的点积更有效。 这种方法并不要求这些点实际上已经是形成右手三角形的顺序,因此更加稳定。它需要的是该点位于平面内(或靠近它),以便近似准确。