【问题标题】:barycentric coordinate clamping on 3d triangle3d三角形上的重心坐标钳制
【发布时间】:2013-01-22 20:20:15
【问题描述】:

我要计算一个点到一个三角形的最短距离(3d)。我已将该点投影到三角形平面上,然后采用该点投影的重心坐标。但是我找不到将坐标固定在三角形内的方法。

搜索时我只找到了 0

【问题讨论】:

  • 如果平面上的投影不在三角形中,你可以忽略它,看看到线段的距离。
  • 哦,没想到。仍然如果可以夹紧,它可能会更快。

标签: c++ math geometry


【解决方案1】:

我意识到这是一个老问题,但还没有真正得到解答,而且它目前是 Google 上“钳制重心坐标”的第一个热门话题。

在下面,p0p1p2 是三角形的顶点,uvw 是点 p = p0*u + p1*v + p2*w 的重心坐标。我假设u+v+w = 1

正如 MSN 指出的那样,三角形上最近的点取决于三角形,因此任何仅对 uvw 的操作都无法工作。

如果uvw都是正数,则点在三角形内,无事可做。

如果其中任何一个为负数,则该点位于相应边的错误一侧。我们需要将点移动到该边上。对于相应的重心坐标,三角形边缘上的点为零。另外两个只是点从一端到另一端的距离。

if ( u < 0)
{
    float t = Dot(p-p1,p2-p1)/Dot(p2-p1,p2-p1);
    t = Clamp01( t );
    return Vector3( 0.0f, 1.0f-t, t );
}
else if ( v < 0 )
{
    float t = Dot(p-p2,p0-p2)/Dot(p0-p2,p0-p2);
    t = Clamp01( t );
    return Vector3( t, 0.0f, 1.0f-t );
}
else if ( w < 0 )
{
    float t = Dot(p-p0,p1-p0)/Dot(p1-p0,p1-p0);
    t = Clamp01( t );
    return Vector3( 1.0f-t, t, 0.0f );
}
else
{
    return Vector3( u, v, w );
}

Clamp01() 如果介于01 之间,则返回t,如果为负数,则返回0,如果大于1,则返回1Dot( a, b ) 是两个向量 ab 的点积。

【讨论】:

    【解决方案2】:

    如果你想找到一个点到一个三角形的最短距离,你不能用这种方式把一个点夹在一个三角形上。距离在笛卡尔空间中,而重心坐标不在。

    为了确定点到三角形外的三角形的距离,您需要确定该点最接近三角形的哪个特征(线段或角),然后确定到该特征的距离。以任何不考虑转换回笛卡尔空间的方式来钳制重心坐标都是行不通的。

    【讨论】:

    • 你确定吗?我描述的方法为我的目的(体素网格)提供了一个非常好的结果。当然,我不计算重心空间中的距离,而是将夹紧点再次转换回世界空间。稍后可能会进行一些测试以检查准确性。
    • @lasvig,在重心空间中夹紧可以让您获得到三角形上某个点的距离。三角形上的那个点不一定是三角形上离查询点最近的点。
    【解决方案3】:

    尝试将uv 钳制为0..1,然后设置w = 1 - u - v 以保持规范化约束。

    【讨论】:

    • 试过了,它似乎没有工作,但我的代码可能是错误的,尝试修复以再次测试。
    【解决方案4】:

    uvw 需要夹在0..1 之间。就是这样。

    例如

    [u,v,w] = [-0.17, 0.64, 1.85]
    

    三角形上会是

    [u,v,w] = [0, 0.64, 1]
    

    【讨论】:

    • 你如何处理那些“夹住”的 u、v 和 w?它们是什么意思?
    • 实际上是否会将其夹在距离原始坐标最近的点?我以前试过这个,但它可能是我的测试代码中的一些错误。会尝试更多。
    • 重心坐标在 u + v + w != 1 处是合法的吗?
    • 是的。重心坐标是齐次的。这意味着[u,v,w][2u,2v,2w] 指向同一个位置。所以你总是可以除以一个标量来得到u+v+w=1,但你不必这样做。要最终提取(x,y) 坐标,您需要进行除法,但从数学上讲,任何值都是有效的。
    【解决方案5】:

    如果有人想知道,我先解决了 夹紧uvw = 1 - u - v 比 夹紧uwv = 1 - u - w 比 夹紧vwu = 1 - v - w

    其他 2 个建议的解决方案给了我奇怪的输出,并且似乎正确钳位。

    可能有更好/更快的方法,但目前这项工作。

    【讨论】:

      猜你喜欢
      • 2013-02-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-09-09
      • 2010-12-03
      • 2020-12-29
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多