改变 3D 坐标系做 2D 三角测量

Change 3D coordinate system do 2D for triangulation

我需要在 3D 中对 n 个点的多边形进行三角剖分 space。问题是我使用的库仅在 2D 中进行三角剖分。由于我的多边形可以在 3D 中的任何平面中定向 space,我需要将这些点转换为 2D 和三角剖分后我必须将它们转换回原始 3D 坐标系。

我想我在创建从 3D 到 2D 的变换矩阵时迷路了。

这是我正在做的事情:

1 - 定义新二维坐标系的X轴为P2 - P1 2 - 将辅助轴定义为 P3 - P1 3 - 因为 X 和助手是共面的,所以我使用叉积来找到 Z 轴 4 - 现在我有了 X 和 Z,叉积得到 Y 轴 5 - 归一化所有轴 6 - 使用这些新轴创建一个变换矩阵 7 - 将原始点乘以变换矩阵

由于现在所有点都共面,因此它们的 Z 坐标应该为零,但实际情况并非如此。 Z 坐标至少应该相等,因为我知道我应该以某种方式将平移放入矩阵中...

我做错了什么?

这是一个小例子:

        Point4D p1 = new Point4D(1, -0.75, -0.3, 1);
        Point4D p2 = new Point4D(1,  0.75, -0.3, 1);
        Point4D p3 = new Point4D(1,  0.75,  0.3, 1);
        Point4D p4 = new Point4D(1, -0.75,  0.3, 1);

        Vector3D xAxis = new Vector3D(p2.X - p1.X, p2.Y - p1.Y, p2.Z - p1.Z);
        Vector3D hAxis = new Vector3D(p3.X - p1.X, p3.Y - p1.Y, p3.Z - p1.Z);
        Vector3D zAxis = Vector3D.CrossProduct(xAxis, hAxis);
        Vector3D yAxis = Vector3D.CrossProduct(zAxis, xAxis);

        xAxis.Normalize();
        yAxis.Normalize();
        zAxis.Normalize();

        Matrix3D trans = new Matrix3D(xAxis.X, xAxis.Y, xAxis.Z, 0,
                                      yAxis.X, yAxis.Y, yAxis.Z, 0,
                                      zAxis.X, zAxis.Y, zAxis.Z, 0,
                                      0,       0,       0,       1);

        Point4D n1 = p1 * trans;
        Point4D n2 = p2 * trans;
        Point4D n3 = p3 * trans;
        Point4D n4 = p4 * trans;

你所拥有的是一个转换 trans 服从例如(1,0,0,1)*trans=xAxis 用于齐次坐标中的全局坐标 x 轴 (1,0,0,1)。同样 (0,1,0,1)*trans=yAxis(0,0,1,1)*trans=zAxis

但是你想要一个带有 xAxis*A--->(1,0,0,1) 的变换 A 等等,对吧?所以我认为你应该反转 trans 并做 n1=p1*invert(trans).

我认为您错过了到假定原点的转换,并且您没有反转转换矩阵。所以像这样:

        Point4D p1 = new Point4D(1, -0.75, -0.3, 1);
        Point4D p2 = new Point4D(1, 0.75, -0.3, 1);
        Point4D p3 = new Point4D(1, 0.75, 0.3, 1);
        Point4D p4 = new Point4D(1, -0.75, 0.3, 1);

        Vector3D xAxis = new Vector3D(p2.X - p1.X, p2.Y - p1.Y, p2.Z - p1.Z);
        Vector3D hAxis = new Vector3D(p3.X - p1.X, p3.Y - p1.Y, p3.Z - p1.Z);
        Vector3D zAxis = Vector3D.CrossProduct(xAxis, hAxis);
        Vector3D yAxis = Vector3D.CrossProduct(zAxis, xAxis);

        xAxis.Normalize();
        yAxis.Normalize();
        zAxis.Normalize();

        Matrix3D trans = new Matrix3D(xAxis.X, xAxis.Y, xAxis.Z, 0,
                                      yAxis.X, yAxis.Y, yAxis.Z, 0,
                                      zAxis.X, zAxis.Y, zAxis.Z, 0,
                                      p1.X, p1.Y, p1.Z, 1);    // **** changed this
        trans.Invert();    // **** added this

        Point4D n1 = p1 * trans;
        Point4D n2 = p2 * trans;
        Point4D n3 = p3 * trans;
        Point4D n4 = p4 * trans;

对于您的测试点,结果如下:

n1 { 0,    0, 0, 1}
n2 {1.5,   0, 0, 1}
n3 {1.5, 0.6, 0, 1}
n4 {  0, 0.6, 0, 1}