File: glu_tessellator_cap.h

package info (click to toggle)
meshlab 2020.09%2Bdfsg1-2
  • links: PTS, VCS
  • area: main
  • in suites: bookworm
  • size: 45,132 kB
  • sloc: cpp: 400,238; ansic: 31,952; javascript: 1,578; sh: 387; yacc: 238; lex: 139; python: 86; makefile: 30
file content (72 lines) | stat: -rw-r--r-- 2,332 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
#ifndef GLU_TESSELLATOR_CAP_H
#define GLU_TESSELLATOR_CAP_H
#include "glu_tesselator.h"
#include <vcg/simplex/edge/pos.h>
#include <vcg/complex/algorithms/clean.h>
#include <vcg/complex/algorithms/update/bounding.h>

namespace vcg {
namespace tri {


// This function take a mesh with one or more boundary stored as edges, and fill another mesh with a triangulation of that boundaries.
// it assumes that boundary are planar and exploits glutessellator for the triangulaiton
template <class MeshType>
void CapEdgeMesh(MeshType &em, MeshType &cm, bool revertFlag=false)
{
  typedef typename MeshType::EdgeType EdgeType;
  typedef typename MeshType::CoordType CoordType;
  std::vector< std::vector<CoordType> > outlines;
  std::vector<CoordType> outline;
  UpdateFlags<MeshType>::EdgeClearV(em);
  UpdateTopology<MeshType>::EdgeEdge(em);
  int nv=0;
  for(size_t i=0;i<em.edge.size();i++) if(!em.edge[i].IsD())
  {
    if (!em.edge[i].IsV())
    {
      edge::Pos<EdgeType> startE(&em.edge[i],0);
       edge::Pos<EdgeType> curE=startE;
      do
      {
        curE.E()->SetV();
        outline.push_back(curE.V()->P());
        curE.NextE();
        nv++;
      }
      while(curE != startE);
      if(revertFlag) std::reverse(outline.begin(),outline.end());
      outlines.push_back(outline);
      outline.clear();
    }
  }
  if (nv<2) return;
//  printf("Found %i outlines for a total of %i vertices",outlines.size(),nv);

  typename MeshType::VertexIterator vi=vcg::tri::Allocator<MeshType>::AddVertices(cm,nv);
  for (size_t i=0;i<outlines.size();i++)
  {
    for(size_t j=0;j<outlines[i].size();++j,++vi)
      (&*vi)->P()=outlines[i][j];
  }

  std::vector<int> indices;
  glu_tesselator::tesselate(outlines, indices);
  std::vector<CoordType> points;
  glu_tesselator::unroll(outlines, points);
  //typename MeshType::FaceIterator fi=tri::Allocator<MeshType>::AddFaces(cm,nv-2);
  typename MeshType::FaceIterator fi=tri::Allocator<MeshType>::AddFaces(cm,indices.size()/3);
  for (size_t i=0; i<indices.size(); i+=3,++fi)
  {
    (*&fi)->V(0)=&cm.vert[ indices[i+0] ];
    (*&fi)->V(1)=&cm.vert[ indices[i+1] ];
    (*&fi)->V(2)=&cm.vert[ indices[i+2] ];
  }
  Clean<MeshType>::RemoveDuplicateVertex(cm);
  UpdateBounding<MeshType>::Box(cm);
}

} // end namespace tri
} // end namespace vcg

#endif // GLU_TESSELLATOR_CAP_H