00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00027
#ifndef SHUTIL_SHMESHIMPL_HPP
00028
#define SHUTIL_SHMESHIMPL_HPP
00029
00030
#include <iostream>
00031
#include <string>
00032
#include <map>
00033
#include "ShError.hpp"
00034
#include "ShException.hpp"
00035
#include "ShDebug.hpp"
00036
#include "ShMesh.hpp"
00037
00038
namespace ShUtil {
00039
00041
template<
typename M>
00042 ShMeshVertex<M>::ShMeshVertex()
00043 : edge(0) {}
00044
00045
template<
typename M>
00046 ShMeshVertex<M>::ShMeshVertex(
const ShMeshVertex<M> &other)
00047 : edge(0) {}
00048
00049
template<
typename M>
00050 ShMeshFace<M>::ShMeshFace()
00051 : edge(0) {}
00052
00053
template<
typename M>
00054 ShMeshFace<M>::ShMeshFace(
const ShMeshFace<M> &other)
00055 : edge(0) {}
00056
00058
template<
typename M>
00059 ShMeshEdge<M>::ShMeshEdge()
00060 : start(0), end(0), face(0), sym(0), next(0), prev(0) {}
00061
00062
template<
typename M>
00063 ShMeshEdge<M>::ShMeshEdge(
const ShMeshEdge<M> &other)
00064 : start(0), end(0), face(0), sym(0), next(0), prev(0) {}
00065
00066
template<
typename M>
00067
void ShMeshEdge<M>::setLinks(Vertex *s, Vertex *e, Face *f,
00068 Edge *next, Edge *prev, Edge *sym) {
00069
00070
00071
if(start || end) {
00072 SH_DEBUG_WARN(
"Changing start/end vertex of an edge. "
00073 <<
"This is probably not a good idea.");
00074 }
00075
00076 start = s;
00077 end = e;
00078 face = f;
00079 setNext(next);
00080 setPrev(prev);
00081 setSym(sym);
00082 }
00083
00084
template<
typename M>
00085
void ShMeshEdge<M>::setNext(Edge *n) {
00086
if( next ) next->prev = 0;
00087 next = n;
00088
if( next ) next->prev = reinterpret_cast<Edge*>(
this);
00089 }
00090
00091
template<
typename M>
00092
void ShMeshEdge<M>::setPrev(Edge *p) {
00093
if( prev ) prev->next = 0;
00094 prev = p;
00095
if( prev ) prev->next = reinterpret_cast<Edge*>(
this);
00096 }
00097
00098
template<
typename M>
00099
void ShMeshEdge<M>::setSym(Edge *e) {
00100
if( sym ) sym->sym = 0;
00101 sym = e;
00102
if( sym ) sym->sym = reinterpret_cast<Edge*>(
this);
00103 }
00104
00105
00106
template<
typename M>
00107 ShMesh<M>::ShMesh() {}
00108
00109
template<
typename M>
00110 ShMesh<M>::ShMesh(
const ShMesh<M> &other) {
00111 *
this = other;
00112 }
00113
00114
template<
typename M>
00115 ShMesh<M>::~ShMesh() {
00116
clear();
00117 }
00118
00119
template<
typename M>
00120 ShMesh<M>&
ShMesh<M>::operator=(
const ShMesh<M> &other) {
00121
00122
00123 VertexMap vmap;
00124 EdgeMap emap;
00125 FaceMap fmap;
00126
00127 SH_DEBUG_WARN(
"Assignment");
00128
clear();
00129
00130
00131 vmap[0] = 0;
00132 emap[0] = 0;
00133 fmap[0] = 0;
00134
00135
00136
for(
typename EdgeSet::const_iterator J = other.
edges.begin(); J != other.
edges.end(); ++J) {
00137 Edge* newedge =
new Edge(**J);
00138 edges.insert(newedge);
00139 emap[*J] = newedge;
00140 }
00141
00142
for(
typename VertexSet::const_iterator I = other.
verts.begin(); I != other.
verts.end(); ++I) {
00143 Vertex* newvert =
new Vertex(**I);
00144 verts.insert(newvert);
00145 vmap[*I] = newvert;
00146 newvert->edge = emap[(*I)->edge];
00147 }
00148
00149
for(
typename FaceSet::const_iterator K = other.
faces.begin(); K != other.
faces.end(); ++K) {
00150 Face* newface =
new Face(**K);
00151 faces.insert(newface);
00152 fmap[*K] = newface;
00153 newface->edge = emap[(*K)->edge];
00154 }
00155
00156
for(
typename EdgeSet::const_iterator J = other.
edges.begin(); J != other.
edges.end(); ++J) {
00157 Edge *e = emap[*J];
00158 e->start = vmap[(*J)->start];
00159 e->end = vmap[(*J)->end];
00160 e->face = fmap[(*J)->face];
00161 e->sym = emap[(*J)->sym];
00162 e->prev = emap[(*J)->prev];
00163 e->next = emap[(*J)->next];
00164 m_incidences.insert(Incidence(e->start, e));
00165 }
00166
00167
return *
this;
00168 }
00169
00170
template<
typename M>
00171 void ShMesh<M>::clear() {
00172
for(
typename VertexSet::iterator I = verts.begin(); I != verts.end(); ++I) {
00173
delete (*I);
00174 }
00175 verts.clear();
00176
00177
for(
typename FaceSet::iterator K = faces.begin(); K != faces.end(); ++K) {
00178
delete (*K);
00179 }
00180 faces.clear();
00181
00182
for(
typename EdgeSet::iterator J = edges.begin(); J != edges.end(); ++J) {
00183
delete (*J);
00184 }
00185 edges.clear();
00186
00187 m_incidences.clear();
00188 }
00189
00190
template<
typename M>
00191
typename ShMesh<M>::Face*
00192
ShMesh<M>::addFace(
const typename ShMesh<M>::VertexList &vl) {
00193 verts.insert(vl.begin(), vl.end());
00194
00195
if( vl.size() < 1 ) {
00196
SH::shError(
SH::ShException(
"ShMesh::addFace can only handle faces with >= 1 vertices"));
00197 }
00198 Face *newf =
new Face();
00199 faces.insert(newf);
00200
00201 Edge *newe = 0, *olde = 0;
00202 Vertex *first = vl.front();
00203
for(
typename VertexList::const_iterator I = vl.begin(); I != vl.end();) {
00204 Vertex *start = *(I++);
00205 Vertex *end = (I == vl.end() ? first : *I);
00206
00207 SH_DEBUG_ASSERT(start);
00208
00209 newe =
new Edge();
00210 newe->setLinks(start, end, newf, 0, olde, 0);
00211 olde = newe;
00212
00213
if( !newf->edge ) newf->edge = newe;
00214 insertHalfEdge(newe);
00215 }
00216 newf->edge->setPrev(newe);
00217
return newf;
00218 }
00219
00220
00221
template<
typename M>
00222 void ShMesh<M>::removeFace(Face *f) {
00223 Edge *olde, *e;
00224 e = f->edge;
00225
00226
00227
00228
00229
do {
00230 olde = e;
00231 e = e->next;
00232
removeHalfEdge(e);
00233 }
while( e != f->edge );
00234 faces.erase(f);
00235
delete f;
00236 }
00237
00238
template<
typename M>
00239
template<
typename VertLess>
00240 void ShMesh<M>::mergeVertices() {
00241
typedef std::map<Vertex*, Vertex*, VertLess> MergedVertMap;
00242 MergedVertMap mvmap;
00243
00244
00245
for(
typename VertexSet::iterator I = verts.begin(); I != verts.end(); ++I) {
00246
if( mvmap.count(*I) == 0 ) mvmap[*I] = *I;
00247 }
00248
00249
for(
typename EdgeSet::iterator J = edges.begin(); J != edges.end(); ++J) {
00250 (*J)->start = mvmap[(*J)->start];
00251 (*J)->end = mvmap[(*J)->end];
00252 }
00253
00254
00255
00256
00257
00258
for(
typename VertexSet::iterator I = verts.begin(); I != verts.end();) {
00259
if( mvmap[*I] != *I ) {
00260
typename VertexSet::iterator deadI = I;
00261 ++I;
00262 Vertex *deadVert = *deadI;
00263 verts.erase(deadI);
00264
00265
00266 IncidenceRange ir = m_incidences.equal_range(deadVert);
00267
for(IncidenceIterator K = ir.first; K != ir.second; ++K) {
00268 m_incidences.insert(Incidence(mvmap[K->first], K->second));
00269 }
00270 m_incidences.erase(ir.first, ir.second);
00271
00272
delete deadVert;
00273 }
else {
00274 ++I;;
00275 }
00276 }
00277 }
00278
00279
template<
typename M>
00280 void ShMesh<M>::mergeEdges() {
00281
typedef std::map<Vertex*, std::map<Vertex*, Edge*> > EdgeMatchMap;
00282
00283 EdgeMatchMap edgeMatch;
00284
00285
for(
typename EdgeSet::iterator J = edges.begin(); J != edges.end(); ++J) {
00286 Edge *e = (*J);
00287 Edge *match = edgeMatch[e->end][e->start];
00288
00289
if(match) match->setSym(e);
00290
00291
if( edgeMatch[e->start][e->end] != 0 ) {
00292 SH_DEBUG_WARN(
"Duplicate edge found in mesh");
00293 }
00294 edgeMatch[e->start][e->end] = e;
00295 }
00296 }
00297
00298
template<
typename M>
00299 bool ShMesh<M>::earTriangulate() {
00300
bool changed =
false;
00301
for(
typename FaceSet::iterator I = faces.begin(); I != faces.end(); ++I) {
00302 Edge *e = (*I)->edge;
00303
00304
if( e->next->next->next == e )
continue;
00305
00306 changed =
true;
00307
if( e->next == e || e->next->next == e ) {
00308
removeFace(*(I++));
00309
continue;
00310 }
00311
00312
00313 Face *lastface = *I;
00314 Edge *e0 = e;
00315 Edge *en = e0->prev;
00316
for(e = e->next->next; e != en; e = e->next) {
00317 Face *newf =
new Face();
00318 newf->edge = e;
00319
00320
00321 Edge *ee0 =
new Edge(*e);
00322 ee0->setLinks(e->start, e0->start, lastface, e->prev->prev, e->prev, 0);
00323
00324 Edge *e0e =
new Edge(*e0);
00325 e0e->setLinks(e0->start, e->start, newf, e, en, 0);
00326
00327 ee0->setSym(e0e);
00328
00329
insertHalfEdge(ee0);
00330
insertHalfEdge(e0e);
00331 faces.insert(newf);
00332
00333 lastface = newf;
00334 }
00335 e->face = lastface;
00336 }
00337
return changed;
00338 }
00339
00340
template<
typename M>
00341 void ShMesh<M>::removeHalfEdge(Edge *e) {
00342 edges.erase(e);
00343 e->setNext(0);
00344 e->setPrev(0);
00345 e->setSym(0);
00346
00347
00348 IncidenceRange ir = m_incidences.equal_range(e->start);
00349
for(IncidenceIterator I = ir.first; I != ir.second; ++I) {
00350
if(I->second == e) {
00351 m_incidences.erase(I);
00352
break;
00353 }
00354 }
00355
if(e->start->edge == e) {
00356
if(m_incidences.count(e->start) > 0) {
00357 e->start->edge = m_incidences.find(e->start)->second;
00358 }
else {
00359 e->start->edge = 0;
00360 }
00361 }
00362
delete e;
00363 }
00364
00365
template<
typename M>
00366 void ShMesh<M>::insertHalfEdge(Edge *e) {
00367 edges.insert(e);
00368 SH_DEBUG_ASSERT(e->start);
00369 m_incidences.insert(Incidence(e->start, e));
00370 }
00371
00372 }
00373
00374
#endif