Rev 183 | Blame | Last modification | View Log | RSS feed
#include <iostream>
#include "HMesh/Manifold.h"
#include "HMesh/VertexCirculator.h"
#include "HMesh/FaceCirculator.h"
#include "build_manifold.h"
using namespace std;
using namespace CGLA;
using namespace HMesh;
namespace HMesh
{
class EdgeKey
{
int v0;
int v1;
public:
EdgeKey(int va, int vb)
{
if(va<vb)
{
v0 = va;
v1 = vb;
}
else
{
v0 = vb;
v1 = va;
}
}
bool operator<(const EdgeKey& k2) const
{
if(v0<k2.v0)
return true;
else if(v0>k2.v0)
return false;
else
return v1<k2.v1;
return false;
}
};
struct Edge
{
HalfEdgeIter h0;
HalfEdgeIter h1;
int count;
Edge(): h0(NULL_HALFEDGE_ITER), h1(NULL_HALFEDGE_ITER), count(0) {}
};
void build_manifold(Manifold& m,
int no_vertices,
const Vec3f* vertvec,
int no_faces,
const int* facevec,
const int* indices,
const int* touch)
{
std::vector<VertexIter> vertices(no_vertices);
if(touch==0)
{
for(int i=0;i<no_vertices;++i)
vertices[i] = m.create_vertex(vertvec[i]);
}
else
{
for(int i=0;i<no_vertices;++i)
{
vertices[i] = m.create_vertex(vertvec[i]);
vertices[i]->touched = touch[i];
}
}
typedef std::map<EdgeKey, Edge> EdgeMap;
EdgeMap edge_map;
int n=0;
for(int i=0;i<no_faces;++i)
{
FaceIter face = m.create_face();
int N = facevec[i];
vector<HalfEdgeIter> h(N);
for(int j=0;j<N;++j)
{
int v_idx = indices[j+n];
int v_idx1 = indices[(j+1)%N+n];
assert(v_idx < no_vertices);
assert(v_idx1 < no_vertices);
EdgeKey ek = EdgeKey(v_idx, v_idx1);
EdgeMap::iterator em_iter = edge_map.find(ek);
if(em_iter == edge_map.end())
{
Edge e;
e.count = 1;
e.h0 = m.create_halfedge();
e.h1 = m.create_halfedge();
glue(e.h0, e.h1);
vertices[v_idx]->he = e.h0;
vertices[v_idx1]->he = e.h1;
e.h0->vert = vertices[v_idx1];
e.h1->vert = vertices[v_idx];
edge_map[ek] = e;
h[j]=e.h0;
}
else
{
h[j] = em_iter->second.h1;
em_iter->second.count++;
assert(em_iter->second.count !=3);
assert(em_iter->second.count ==2);
}
}
for(int j=0;j<N;++j)
{
h[j]->face = face;
link(h[j], h[(j+1)%N]);
}
face->last = h[0];
n += N;
}
VertexIter vi = m.vertices_begin();
while(vi != m.vertices_end())
{
if(vi->he == NULL_HALFEDGE_ITER)
{
VertexIter v_old = vi;
++vi;
m.erase_vertex(v_old);
}
else
++vi;
}
for(vi = m.vertices_begin(); vi != m.vertices_end(); ++vi)
check_boundary_consistency(vi);
}
}