196 bool subdivide( MeshType& _m,
size_t _n ,
const bool _update_points =
true)
override
201 typename MeshType::VertexIter vit;
202 typename MeshType::VertexVertexIter vvit;
203 typename MeshType::EdgeIter eit;
204 typename MeshType::FaceIter fit;
205 typename MeshType::FaceVertexIter fvit;
206 typename MeshType::FaceHalfedgeIter fheit;
207 typename MeshType::VertexHandle vh;
208 typename MeshType::HalfedgeHandle heh;
209 typename MeshType::Point pos(0,0,0), zero(0,0,0);
210 size_t &gen = _m.property( mp_gen_ );
212 for (
size_t l=0; l<_n; ++l)
215 for (eit=_m.edges_begin(); eit != _m.edges_end();++eit)
217 _m.status( *eit ).set_tagged(
true );
218 if ( (gen%2) && _m.is_boundary(*eit) )
219 compute_new_boundary_points( _m, *eit );
223 typename MeshType::FaceIter fend = _m.faces_end();
224 for (fit = _m.faces_begin();fit != fend; ++fit)
226 if (_m.is_boundary(*fit))
229 _m.property(fp_pos_, *fit).invalidate();
233 for( heh = _m.halfedge_handle(*fit); !_m.is_boundary( _m.opposite_halfedge_handle(heh) ); heh = _m.next_halfedge_handle(heh) )
235 assert(_m.is_boundary( _m.opposite_halfedge_handle(heh) ));
238 if( _m.is_boundary(_m.next_halfedge_handle(heh)) || _m.is_boundary(_m.prev_halfedge_handle(heh)) )
240 if(_m.is_boundary(_m.prev_halfedge_handle(heh)))
241 heh = _m.prev_halfedge_handle(heh);
243 if(_m.is_boundary(_m.next_halfedge_handle(_m.next_halfedge_handle(heh))))
246 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(heh));
247 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(heh)));
248 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(_m.prev_halfedge_handle(heh)));
252#ifdef MIRROR_TRIANGLES
254 pos += real_t(2.0/9) * _m.point(_m.to_vertex_handle(heh));
255 pos += real_t(4.0/9) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(heh)));
256 pos += real_t(4.0/9) * _m.point(_m.to_vertex_handle(_m.prev_halfedge_handle(heh)));
257 pos += real_t(-1.0/9) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)))));
259 pos += real_t(7.0/24) * _m.point(_m.to_vertex_handle(heh));
260 pos += real_t(3.0/8) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(heh)));
261 pos += real_t(3.0/8) * _m.point(_m.to_vertex_handle(_m.prev_halfedge_handle(heh)));
262 pos += real_t(-1.0/24) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)))));
268 vh = _m.to_vertex_handle(_m.next_halfedge_handle(heh));
270 if((_m.valence(vh) == 6) || _m.is_boundary(vh))
272#ifdef MIRROR_TRIANGLES
274 pos += real_t(5.0/9) * _m.point(vh);
275 pos += real_t(3.0/9) * _m.point(_m.to_vertex_handle(heh));
276 pos += real_t(3.0/9) * _m.point(_m.to_vertex_handle(_m.opposite_halfedge_handle(heh)));
277 pos += real_t(-1.0/9) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.next_halfedge_handle(heh)))));
278 pos += real_t(-1.0/9) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)))));
281 pos += real_t(1.0/9) * _m.point(vh);
282 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(heh));
283 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(_m.opposite_halfedge_handle(heh)));
284 pos += real_t(1.0/9) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.next_halfedge_handle(heh)))));
285 pos += real_t(1.0/9) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)))));
287 pos += real_t(1.0/2) * _m.point(vh);
288 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(heh));
289 pos += real_t(1.0/3) * _m.point(_m.to_vertex_handle(_m.opposite_halfedge_handle(heh)));
290 pos += real_t(-1.0/12) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.next_halfedge_handle(heh)))));
291 pos += real_t(-1.0/12) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(_m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)))));
298 unsigned int K = _m.valence(vh);
299 pos += weights_[K][K]*_m.point(vh);
300 heh = _m.opposite_halfedge_handle( _m.next_halfedge_handle(heh) );
301 for(
unsigned int i = 0; i<K; ++i, heh = _m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)) )
303 pos += weights_[K][i]*_m.point(_m.to_vertex_handle(heh));
307 vh = _m.add_vertex( pos );
308 _m.property(fp_pos_, *fit) = vh;
317 for(fvit = _m.fv_iter( *fit ); fvit.is_valid(); ++fvit)
318 if( (_m.valence(*fvit)) == 6 || _m.is_boundary(*fvit) )
323 for(fheit = _m.fh_iter( *fit ); fheit.is_valid(); ++fheit)
327 assert(_m.to_vertex_handle(heh).is_valid());
328 pos += real_t(32.0/81) * _m.point(_m.to_vertex_handle(heh));
330 heh = _m.opposite_halfedge_handle(heh);
331 assert(heh.is_valid());
332 assert(_m.next_halfedge_handle(heh).is_valid());
333 assert(_m.to_vertex_handle(_m.next_halfedge_handle(heh)).is_valid());
334 pos -= real_t(1.0/81) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(heh)));
336 heh = _m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh));
337 assert(heh.is_valid());
338 assert(_m.next_halfedge_handle(heh).is_valid());
339 assert(_m.to_vertex_handle(_m.next_halfedge_handle(heh)).is_valid());
340 pos -= real_t(2.0/81) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(heh)));
341 heh = _m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh));
342 assert(heh.is_valid());
343 assert(_m.next_halfedge_handle(heh).is_valid());
344 assert(_m.to_vertex_handle(_m.next_halfedge_handle(heh)).is_valid());
345 pos -= real_t(2.0/81) * _m.point(_m.to_vertex_handle(_m.next_halfedge_handle(heh)));
351 for(fheit = _m.fh_iter( *fit ); fheit.is_valid(); ++fheit)
353 vh = _m.to_vertex_handle(*fheit);
354 if( (_m.valence(vh) != 6) && (!_m.is_boundary(vh)) )
356 unsigned int K = _m.valence(vh);
357 pos += weights_[K][K]*_m.point(vh);
358 heh = _m.opposite_halfedge_handle( *fheit );
359 for(
unsigned int i = 0; i<K; ++i, heh = _m.opposite_halfedge_handle(_m.prev_halfedge_handle(heh)) )
361 pos += weights_[K][i]*_m.point(_m.to_vertex_handle(heh));
365 pos *= real_t(1.0/(3-nOrdinary));
368 vh = _m.add_vertex( pos );
369 _m.property(fp_pos_, *fit) = vh;
374 for (fit = _m.faces_begin();fit != fend; ++fit)
376 if ( _m.is_boundary(*fit) && (gen%2))
378 boundary_split( _m, *fit );
382 assert(_m.property(fp_pos_, *fit).is_valid());
383 _m.split( *fit, _m.property(fp_pos_, *fit) );
388 for (eit=_m.edges_begin(); eit != _m.edges_end(); ++eit)
389 if ( _m.status( *eit ).tagged() && !_m.is_boundary( *eit ) )
393 ASSERT_CONSISTENCY( MeshType, _m );