通过边循环拆分3D模型

时间:2014-02-25 11:21:25

标签: algorithm computational-geometry graph-algorithm 3d-model

我有一个3D模型,代表如下:

class Vertex
{
    double x, y, z;
}

class Edge
{
    Vertex *v1, *v2; // no particular order
    Face *f1, *f2; // no particular order. f2 may be null.
}

class Face
{
    List<Vertex*> vertices; // clockwise order
    List<Edge*> edges; // clockwise order
}

class Model
{
    List<Face*> faces;
    List<Vertex*> vertices;
    List<Edge*> edges;
}

当然,这可以转化为最方便的表达方式。

我想将这个模型拆分成几个断开的部分,沿着连接边的多个循环,然后创建新的面来封顶。一个循环的示例:

新面孔应该处于相同的位置,并且与它们与其他面孔的连接相同,但是对于这个例子,我将它们分开了。我怎么能这样做?

在其他断开的部分之间是否共享顶点并不重要。

由于每个边都恰好连接两个面,我尝试将每个边分别分成两个副本(每个面一个)。这确实根据需要分离了模型,但后来我找不到正确添加新面孔的方法。

这个问题是标记图形算法,因为这个问题似乎与图论有某种联系。

1 个答案:

答案 0 :(得分:2)

  • 修复您的模型。 class Edge应该指向FaceVertex而不是值。
  • 您想在set中使用某种List代替class Model。这有助于查找和删除内容,并确保没有重复项。
  • 想出你的功能原型。我建议
pair<Model*, Model*> split_model( const Model* mx, const List<Edge*>& loop );
  • 创建两个新的空模型,例如mamb。将loop的边缘添加到每个边缘。
  • loop中挑选一条边。让我们调用附加到它的两个面fafb
  • fa添加到模型ma。从fa开始,按照fa附加的所有边以及附加到这些边的所有边进行完整的图搜索,依此类推。必须遵循遇到的所有面和边并将其添加到模型ma。如果遇到已经属于ma的面孔或边缘,则不要遵循它们。特别是当遇到属于loop的边缘时会发生这种情况,因此您永远不会越过边界。这样,您可以在一侧完整搜索所有边和面,最终得到一个完整的模型ma。最后,添加一个代表切割的面。这里可以忽略顶点,但当然最后你可能想要添加属于你添加的面的所有顶点。
  • 从面部fb开始重复此步骤,以创建代表另一部分的模型mb