BWAPI
SPAR/AIModule/BWTA/vendors/CGAL/CGAL/Nef_S2/SM_decorator.h
Go to the documentation of this file.
00001 // Copyright (c) 1997-2002  Max-Planck-Institute Saarbruecken (Germany).
00002 // All rights reserved.
00003 //
00004 // This file is part of CGAL (www.cgal.org); you may redistribute it under
00005 // the terms of the Q Public License version 1.0.
00006 // See the file LICENSE.QPL distributed with CGAL.
00007 //
00008 // Licensees holding a valid commercial license may use this file in
00009 // accordance with the commercial license agreement provided with the software.
00010 //
00011 // This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
00012 // WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
00013 //
00014 // $URL: svn+ssh://scm.gforge.inria.fr/svn/cgal/branches/CGAL-3.5-branch/Nef_S2/include/CGAL/Nef_S2/SM_decorator.h $
00015 // $Id: SM_decorator.h 45448 2008-09-09 16:03:25Z spion $
00016 // 
00017 //
00018 // Author(s)     : Michael Seel       <seel@mpi-sb.mpg.de>
00019 //                 Miguel Granados    <granados@mpi-sb.mpg.de>
00020 //                 Susan Hert         <hert@mpi-sb.mpg.de>
00021 //                 Lutz Kettner       <kettner@mpi-sb.mpg.de>
00022 //                 Peter Hachenberger <hachenberger@mpi-sb.mpg.de>
00023 #ifndef CGAL_SM_DECORATOR_H 
00024 #define CGAL_SM_DECORATOR_H
00025 
00026 #include <CGAL/basic.h>
00027 #include <CGAL/Nef_S2/SM_const_decorator.h>
00028 
00029 #undef CGAL_NEF_DEBUG
00030 #define CGAL_NEF_DEBUG  23
00031 #include <CGAL/Nef_2/debug.h>
00032 #include <CGAL/Nef_S2/SM_decorator_traits.h>
00033 #include <CGAL/Nef_S2/Sphere_map.h>
00034 #include <CGAL/Nef_S2/Normalizing.h>
00035 #include <CGAL/Unique_hash_map.h>
00036 #include <CGAL/IO/Verbose_ostream.h>
00037 
00038 CGAL_BEGIN_NAMESPACE
00039 
00040 /*{\Moptions print_title=yes }*/ 
00041 /*{\Moptions outfile=SM_decorator.man }*/
00042 /*{\Manpage {SM_decorator}{Sphere_map}
00043 {Topological sphere map decorator}{D}}*/
00044 
00045 template <typename Map_>
00046 class SM_decorator
00047 { 
00048 public:
00049 typedef Map_              Map;
00050 typedef Map_              Sphere_map;
00051 typedef SM_decorator<Map> Self;
00052 typedef SM_decorator_traits<Map>  Decorator_traits;
00053 /*{\Mdefinition ...}*/
00054 
00055 /*{\Mtypes 5}*/
00056 
00057 typedef CGAL::SM_const_decorator<Map>   SM_const_decorator;
00058 
00059 typedef typename Map::Sphere_kernel    Sphere_kernel;
00060 /*{\Mtypemember spherical geometry.}*/
00061 
00062 typedef typename Map::Sphere_point     Sphere_point;
00063 /*{\Mtypemember embedding vertices.}*/
00064 
00065 typedef typename Map::Sphere_segment   Sphere_segment;
00066 /*{\Mtypemember embedding edges.}*/
00067 
00068 typedef typename Map::Sphere_circle    Sphere_circle;
00069 /*{\Mtypemember embedding loops.}*/
00070 
00071 typedef typename Map::Sphere_direction Sphere_direction;
00072 /*{\Mtypemember embedding directions.}*/
00073 
00074 typedef typename Map::Mark   Mark;
00075 /*{\Mtypemember attributes of objects (vertices, edges, faces).}*/
00076 
00077 typedef size_t Size_type;
00078 /*{\Mtypemember size type.}*/
00079 
00080 enum { BEFORE = -1, AFTER = 1 };
00081 /*{\Menum insertion order labels.}*/
00082 
00083 typedef typename Sphere_kernel::Aff_transformation_3 Aff_transformation_3;
00084 
00085 typedef void*  GenPtr;
00086 typedef typename Map::SVertex                   SVertex;
00087 typedef typename Map::SVertex_handle            SVertex_handle;
00088 typedef typename Map::SVertex_iterator          SVertex_iterator;
00089 typedef typename Map::SVertex_const_handle      SVertex_const_handle;
00090 typedef typename Map::SVertex_const_iterator    SVertex_const_iterator;
00091 typedef typename Map::SHalfedge                 SHalfedge;
00092 typedef typename Map::SHalfedge_handle          SHalfedge_handle;
00093 typedef typename Map::SHalfedge_iterator        SHalfedge_iterator;
00094 typedef typename Map::SHalfedge_const_handle    SHalfedge_const_handle;
00095 typedef typename Map::SHalfedge_const_iterator  SHalfedge_const_iterator;
00096 typedef typename Map::SFace                     SFace;
00097 typedef typename Map::SFace_handle              SFace_handle;
00098 typedef typename Map::SFace_iterator            SFace_iterator;
00099 typedef typename Map::SFace_const_handle        SFace_const_handle;
00100 typedef typename Map::SFace_const_iterator      SFace_const_iterator;
00101 typedef typename Map::SHalfloop                 SHalfloop;
00102 typedef typename Map::SHalfloop_handle          SHalfloop_handle;
00103 typedef typename Map::SHalfloop_iterator        SHalfloop_iterator;
00104 typedef typename Map::SHalfloop_const_handle    SHalfloop_const_handle;
00105 typedef typename Map::SHalfloop_const_iterator  SHalfloop_const_iterator;
00106 typedef typename Map::Object_handle             Object_handle;
00107 typedef typename Map::SHalfedge_around_svertex_circulator
00108                       SHalfedge_around_svertex_circulator;
00109 typedef typename Map::SHalfedge_around_sface_circulator
00110                       SHalfedge_around_sface_circulator;
00111 typedef typename Map::SFace_cycle_iterator      SFace_cycle_iterator;
00112 
00113 /*{\Mtypemember iterating all face cycles of an face |f|.
00114 The iterator has method |bool is_svertex()|, |bool is_shalfedge()|,
00115 |bool is_shalfloop()|, and can be converted to the corresponding
00116 handles |SVertex_handle|, |SHalfedge_handle|, or 
00117 |SHalfloop_handle|.}*/
00118 
00119 protected: 
00120   Map* psm_;
00121 
00122 public:
00123 /*{\Mcreation 3}*/
00124 SM_decorator() : psm_(0) {}
00125 SM_decorator(const Self& D) : psm_(D.psm_) {}
00126 Self& operator=(const Self& D) { psm_=D.psm_; return *this; }
00127 
00128 SM_decorator(Map* M) : psm_(M) {}
00129  
00130 /*{\Moperations 4 4}*/
00131 
00132 Map* sphere_map() const { return psm_; }
00133 
00134 Map* map() { return psm_; }
00135 const Map* map() const { return psm_; }
00136 
00137 bool is_isolated(SVertex_const_handle v) const
00138 { return (v->out_sedge() == SHalfedge_handle()); }
00139 
00140 bool is_isolated(SVertex_handle v) const
00141 /*{\Mop returns |true| when |v| is linked to the interior of a face.}*/
00142 { return (v->out_sedge() == SHalfedge_handle()); }
00143 
00144 SHalfedge_const_handle first_out_edge(SVertex_const_handle v) const
00145 { return v->out_sedge(); }
00146 SHalfedge_const_handle last_out_edge(SVertex_const_handle v) const
00147 { return cap(v->out_sedge()); }
00148 
00149 SHalfedge_handle first_out_edge(SVertex_handle v) const
00150 /*{\Mop returns one edge with source |v|. It's the starting point for
00151   the circular iteration over the edges with source |v|.
00152   \precond |!is_isolated(v)|.}*/
00153 { return v->out_sedge(); }
00154 
00155 SHalfedge_handle last_out_edge(SVertex_handle v) const
00156 /*{\Mop returns one edge with source |v|. \precond |!is_isolated(v)|.}*/
00157 { return cap(v->out_sedge()); }
00158 
00159 SHalfedge_const_handle cyclic_adj_succ(SHalfedge_const_handle e) const
00160 { return e->sprev()->twin(); }
00161 SHalfedge_const_handle cyclic_adj_pred(SHalfedge_const_handle e) const
00162 { return e->twin()->snext(); }
00163 
00164 SHalfedge_handle cyclic_adj_succ(SHalfedge_handle e) const
00165 /*{\Mop returns the edge after |e| in the cyclic ordered adjacency list of
00166   |e->source()|.}*/
00167 { return e->sprev()->twin(); }
00168 
00169 SHalfedge_handle cyclic_adj_pred(SHalfedge_handle e) const
00170 /*{\Mop returns the edge before |e| in the cyclic ordered adjacency list of
00171   |e->source()|.}*/
00172 { return e->twin()->snext(); }
00173 
00174 bool has_shalfloop() const
00175 /*{\Mop returns true iff there is a loop.}*/
00176 { return psm_->has_shalfloop(); }
00177 
00178 /*{\Mtext \headerline{Iteration} \setopdims{3.3cm}{0cm}}*/
00179   
00180 SVertex_iterator svertices_begin() const
00181 { return psm_->svertices_begin(); }
00182 SVertex_iterator svertices_end() const
00183 { return psm_->svertices_end(); }
00184 SHalfedge_iterator shalfedges_begin() const
00185 { return psm_->shalfedges_begin(); }
00186 SHalfedge_iterator shalfedges_end() const
00187 { return psm_->shalfedges_end(); }
00188 SFace_iterator sfaces_begin() const
00189 { return psm_->sfaces_begin(); }
00190 SFace_iterator sfaces_end() const
00191 { return psm_->sfaces_end(); }
00192 SHalfloop_iterator shalfloops_begin() const
00193 { return psm_->shalfloops_begin(); }
00194 SHalfloop_iterator shalfloops_end() const
00195 { return psm_->shalfloops_end(); }
00196 
00197 SHalfloop_handle& shalfloop()
00198 { return psm_->shalfloop(); }
00199 SHalfloop_const_handle shalfloop() const
00200 { return psm_->shalfloop(); }
00201 
00202 Size_type number_of_svertices() const 
00203 /*{\Mop returns the number of vertices.}*/
00204 { return psm_->number_of_svertices(); }
00205 
00206 Size_type number_of_shalfedges() const 
00207 /*{\Mop returns the number of halfedges.}*/
00208 { return psm_->number_of_shalfedges(); }
00209 
00210 Size_type number_of_sedges() const 
00211 /*{\Mop returns the number of edges.}*/
00212 { return number_of_shalfedges()/2; }
00213 
00214 Size_type number_of_shalfloops() const 
00215 /*{\Mop returns the number of halfloops.}*/
00216 { return psm_->number_of_shalfloops(); }
00217 
00218 Size_type number_of_sloops() const 
00219 /*{\Mop returns the number of loops.}*/
00220 { return psm_->number_of_shalfloops()/2; }
00221 
00222 Size_type number_of_sfaces() const    
00223 /*{\Mop returns the number of faces.}*/
00224 { return psm_->number_of_sfaces(); }
00225 
00226 SFace_cycle_iterator sface_cycles_begin(SFace_handle f) const
00227 /*{\Mop returns an iterator for all bounding face cycles of |f|.
00228 The iterator is is convertable to |SVertex_handle|, 
00229 |SHalfloop_handle|, or |SHalfedge_handle|.}*/
00230 { return f->boundary_entry_objects().begin(); }
00231 
00232 SFace_cycle_iterator sface_cycles_end(SFace_handle f) const
00233 /*{\Mop returns the past the end iterator of |f|.}*/
00234 { return f->boundary_entry_objects_.end(); }
00235 
00236 SHalfedge_around_svertex_circulator 
00237   out_edges(SVertex_handle v) const
00238 /*{\Mop returns a circulator for the cyclic adjacency list of |v|.
00239 \precond the adjacency list is not empty.}*/
00240 { return SHalfedge_around_svertex_circulator(first_out_edge(v)); }
00241 
00242 /*{\Mtext \headerline{Update Operations}}*/
00243 
00244 void clear() const
00245 /*{\Mop reintializes |P| to the empty map.}*/
00246 { psm_->clear(); }
00247 
00248 bool is_closed_at_source(SHalfedge_handle e) const
00249 /*{\Mop returns |true| when |e->sprev() == e->twin()|.}*/
00250 { return e->sprev() == e->twin(); }
00251 
00252 bool is_closed_at_target(SHalfedge_handle e) const
00253 /*{\Mop returns |true| when |e->snext() == e->twin()|.}*/
00254 { return e->snext() == e->twin(); }
00255 
00256 SHalfedge_handle cas(SHalfedge_handle e) const 
00257 { return cyclic_adj_succ(e); } 
00258 SHalfedge_handle cap(SHalfedge_handle e) const
00259 { return cyclic_adj_pred(e); }
00260 
00261 template <typename H>
00262 void make_twins(H h1, H h2) const
00263 { h1->twin() = h2; h2->twin() = h1; }
00264 
00265 SVertex_handle new_svertex(const Sphere_point& p = Sphere_point())
00266 /*{\Mop creates a new vertex.}*/
00267 { return map()->new_svertex(p); }
00268 
00269 SHalfedge_handle new_shalfedge_pair() {
00270 /*{\Xop creates a new edge pair. No connectivity is provided.}*/
00271   return map()->new_shalfedge_pair();
00272 }
00273 
00274 SHalfloop_handle new_shalfloop_pair()
00275 /*{\Mop creates a new loop pair.
00276 \precond No sloop pair exists in the local graph.}*/ 
00277 { CGAL_assertion(!has_shalfloop());
00278   return map()->new_shalfloop_pair(); 
00279 }
00280 
00281 SFace_handle new_sface()
00282 /*{\Mop creates a new face.}*/
00283 { return map()->new_sface(); }
00284 
00285 void delete_vertex_only(SVertex_handle v)
00286 /*{\Mop deletes |v| without any connectivity update.}*/
00287 { map()->delete_svertex(v); }
00288 
00289 void delete_edge_pair_only(SHalfedge_handle e)
00290 /*{\Mop deletes |e| and its twin without any connectivity update.}*/
00291 { map()->delete_shalfedge_pair(e); }
00292 
00293 void delete_halfedge_only(SHalfedge_handle e)
00294 /*{\Mop deletes |e| without its twin and without any connectivity update.}*/
00295 { map()->delete_shalfedge(e); }
00296 
00297 void delete_face_only(SFace_handle f) 
00298 /*{\Mop deletes |f| without any connectivity update.}*/
00299 { map()->delete_sface(f); }
00300 
00301 void delete_loop_only()
00302 /*{\Mop deletes the loop and its twin without any connectivity update.}*/ 
00303 { map()->delete_shalfloop_pair(); }
00304 
00305 template <typename H>
00306 bool is_sm_boundary_object(H h) const
00307 { return map()->is_sm_boundary_object(h); }
00308 
00309 template <typename H>
00310 void store_sm_boundary_object(H h, SFace_handle f) {
00311   CGAL_assertion(!map()->is_sm_boundary_object(h));
00312   f->boundary_entry_objects().push_back(make_object(h));
00313   map()->store_sm_boundary_item(h, --(f->sface_cycles_end()));
00314 }
00315 
00316 template <typename H>
00317 void undo_sm_boundary_object(H h, SFace_handle f)
00318 { CGAL_assertion(map()->is_sm_boundary_object(h));
00319   SFace_cycle_iterator it = map()->sm_boundary_item(h);
00320   map()->undef_sm_boundary_item(h);
00321   f->boundary_entry_objects().erase(it);
00322 }
00323 
00324 void link_as_face_cycle(SHalfedge_handle e, SFace_handle f)
00325 /*{\Mop creates a new face cycle of |f| and 
00326    makes |e| the entry point of it.}*/
00327 {
00328   SHalfedge_around_sface_circulator hfc(e), hend(hfc);
00329   CGAL_For_all(hfc,hend) hfc->incident_sface() = f;
00330   store_sm_boundary_object(e,f);
00331 } 
00332 
00333 void link_as_loop(SHalfloop_handle l, SFace_handle f)
00334 /*{\Mop creates a new trivial face cycle of |f| and 
00335    makes |l| the singular object of it.}*/
00336 { store_sm_boundary_object(l,f); l->incident_sface() = f; } 
00337 
00338 void link_as_isolated_vertex(SVertex_handle v, SFace_handle f)
00339 /*{\Mop creates a new trivial face cycle of |f|.
00340    (makes |v| an isolated vertex within |f|).}*/
00341 { store_sm_boundary_object(v,f); v->incident_sface() = f; } 
00342 
00343 void unlink_as_face_cycle(SHalfedge_handle e)
00344 /*{\Mop removes the face cycle defined by |e| from |e->incident_sface()|.
00345     Does not update the face links of the corresponding face cycle
00346     edges. \precond |e| is the entry object of the face cycle.}*/
00347 { undo_sm_boundary_object(e,e->incident_sface()); }
00348   
00349 void unlink_as_loop(SHalfloop_handle l)
00350 /*{\Mop removes the trivial face cycle defined by |l| from
00351    |l->incident_sface()|. Does not update |l|'s face link.}*/
00352 { undo_sm_boundary_object(l,l->incident_sface()); }
00353 
00354 void unlink_as_isolated_vertex(SVertex_handle v)
00355 /*{\Mop removes the trivial face cycle defined by |v| from
00356    |v->incident_sface()|. Does not update |v|'s face link.
00357    \precond |v| is a trivial face cycle of |v->incident_sface()|.}*/
00358 { undo_sm_boundary_object(v,v->incident_sface()); }
00359 
00360 void clear_face_cycle_entries(SFace_handle f)
00361 { map()->reset_sm_object_list(f->boundary_entry_objects());
00362   // removes entries of list and the hashed membership
00363 }
00364 
00365 SHalfedge_handle new_shalfedge_pair(SVertex_handle v1,
00366                                     SVertex_handle v2)
00367 /*{\Mop creates a new pair of edges |(e1,e2)| representing |(v1,v2)| 
00368   by appending the |ei| to |A(vi)| $(i=1,2)$.}*/
00369 { SHalfedge_handle e1 = new_shalfedge_pair();
00370   SHalfedge_handle e2 = e1->twin();
00371   if (!is_isolated(v1))
00372     set_adjacency_at_source_between(cap(first_out_edge(v1)),e1,
00373                                     first_out_edge(v1));
00374   else
00375     close_tip_at_source(e1,v1);
00376   if (!is_isolated(v2))
00377     set_adjacency_at_source_between(cap(first_out_edge(v2)),e2,
00378                                     first_out_edge(v2));
00379   else 
00380     close_tip_at_source(e2,v2);
00381   return e1;
00382 }
00383 
00384 
00385 SHalfedge_handle new_shalfedge_pair(SHalfedge_handle e1, 
00386                                     SHalfedge_handle e2,
00387                                     int pos1 = AFTER, int pos2 = AFTER)
00388 /*{\Mop creates a new pair of edges |(es1,es2)| representing the uedge
00389   |\{e1->source(),e2->source()\}| by inserting the |esi| before or after |ei| 
00390   into the cyclic adjacency list of |ei->source()| depending on |posi| 
00391   $(i=1,2)$ from |\Mname::BEFORE|, |\Mname::AFTER|.}*/
00392 { 
00393   SHalfedge_handle er = new_shalfedge_pair();
00394   SHalfedge_handle ero = er->twin();
00395   if (pos1 < 0) { // before e1
00396     set_adjacency_at_source_between(cap(e1),er,e1);
00397     if ( e1 == first_out_edge(e1->source()) )
00398       set_first_out_edge(e1->source(),er);
00399   } else { // after e1
00400     set_adjacency_at_source_between(e1,er,cas(e1));
00401   }
00402   if (pos2 < 0) { // before e2
00403     set_adjacency_at_source_between(cap(e2),ero,e2);
00404     if ( e2 == first_out_edge(e2->source()) )
00405       set_first_out_edge(e2->source(),ero);
00406   } else { // after e2
00407     set_adjacency_at_source_between(e2,ero,cas(e2));
00408   }
00409   return er;
00410 }
00411 
00412 SHalfedge_handle new_shalfedge_pair(SHalfedge_handle e, SVertex_handle v,
00413                                int pos = AFTER)
00414 /*{\Mop creates a new pair of edges  |(e1,e2)| representing the uedge
00415   |\{e->source(),v\}| by inserting |e1| before or after |e| into cyclic 
00416   adjacency list of |e->source()| depending on |pos| from |\Mname::BEFORE|,
00417   |\Mname::AFTER| and appending |e2| at |A(v)|.}*/
00418 {
00419   SHalfedge_handle e_new = new_shalfedge_pair();
00420   SHalfedge_handle e_opp = e_new->twin();
00421   if (pos < 0) { // before e
00422     set_adjacency_at_source_between(cap(e),e_new,e);
00423     if ( e == first_out_edge(e->source()) )
00424       set_first_out_edge(e->source(),e_new);
00425   } else  // after e
00426     set_adjacency_at_source_between(e,e_new,cas(e));
00427   
00428   if (!is_isolated(v)) {
00429     SHalfedge_handle e_first = first_out_edge(v);
00430     set_adjacency_at_source_between(cap(e_first),e_opp,e_first);
00431   } else
00432     close_tip_at_source(e_opp,v);
00433   return e_new;
00434 }
00435 
00436 
00437 SHalfedge_handle new_shalfedge_pair(SVertex_handle v, SHalfedge_handle e,
00438                                     int pos = AFTER)
00439 /*{\Mop symmetric to the previous one.}*/
00440 { return new_shalfedge_pair(e,v,pos)->twin(); }
00441 
00442 void delete_edge_pair(SHalfedge_handle e)
00443 /*{\Mop deletes |e| and its twin and maintains the adjacency at its source 
00444         and its target.}*/
00445 { remove_from_adj_list_at_source(e);
00446   remove_from_adj_list_at_source(e->twin());
00447   delete_edge_pair_only(e);
00448 }
00449 
00450 SHalfedge_handle split_at(SHalfedge_handle e, Sphere_point sp)
00451 {
00452   CGAL_assertion(sp != e->source()->point());
00453   CGAL_assertion(sp != e->twin()->source()->point());
00454   CGAL_assertion(Sphere_segment(e->source()->point(),
00455                                 e->twin()->source()->point(),
00456                                 e->circle()).has_on(sp));
00457   SVertex_handle v_new = new_svertex(sp);
00458   v_new->mark() = e->mark();
00459   return split_at(e, v_new);
00460 }  
00461 
00462 SHalfedge_handle split_at(SHalfedge_handle e, SVertex_handle v)
00463 {
00464   CGAL_assertion(v->point() != e->source()->point());
00465   CGAL_assertion(v->point() != e->twin()->source()->point());
00466   CGAL_assertion(Sphere_segment(e->source()->point(),
00467                                 e->twin()->source()->point(),
00468                                 e->circle()).has_on(v->point()));
00469 
00470   SHalfedge_handle e_new = new_shalfedge_pair(v, e->twin());
00471   e_new->mark() = e_new->twin()->mark() = e->mark();
00472   e_new->circle() = e->circle();
00473   e_new->twin()->circle() = e->twin()->circle();
00474   if(e->twin()->source()->out_sedge() == e->twin())
00475     e->twin()->source()->out_sedge() = e_new->twin();
00476   e->twin()->source() = v;
00477   e->snext()->sprev() = e_new;
00478   e_new->snext() = e->snext();
00479   e_new->sprev() = e;
00480   e->snext() = e_new;
00481   e_new->twin()->snext() = e->twin();
00482   e->twin()->sprev() = e_new->twin();
00483   e_new->incident_sface() = e->incident_sface();
00484   e_new->twin()->incident_sface() = e->twin()->incident_sface();
00485   return e_new;
00486 }
00487 
00488 void delete_vertex(SVertex_handle v)
00489 /*{\Mop deletes |v| and all outgoing edges |A(v)| as well as their twins. 
00490    Updates the adjacency at the targets of the edges in |A(v)|.}*/
00491 { 
00492   if (!is_isolated(v)) {
00493     SHalfedge_handle e = first_out_edge(v);
00494     while ( e != cap(e) ) 
00495       delete_edge_pair(cap(e));  
00496     delete_edge_pair(e); 
00497   }
00498   delete_vertex_only(v);
00499 }
00500 
00501 void delete_face(SFace_handle f)
00502 /*{\Mop deletes the face |f| without consideration of topological 
00503    linkage.}*/
00504 { clear_face_cycle_entries(f); delete_face_only(f); }
00505 
00506 bool has_outdeg_two(SVertex_handle v) const
00507 /*{\Mop return true when |v| has outdegree two.}*/
00508 // does this work for looping edges?
00509 { if (is_isolated(v)) return false;
00510   SHalfedge_handle e1 = first_out_edge(v);
00511   SHalfedge_handle e2 = last_out_edge(v);
00512   return (e1!=e2 && e2==cas(e1));
00513 }
00514 
00515 void link_as_prev_next_pair(SHalfedge_handle e1, SHalfedge_handle e2)
00516 /*{\Xop makes |e1| and |e2| adjacent in the face cycle 
00517    $\ldots-|e1-e2|-\ldots$.
00518    Afterwards |e1 = e2->sprev()| and |e2 = e1->snext()|.}*/
00519 { e1->snext() = e2; e2->sprev() = e1; }
00520 
00521 void merge_edge_pairs_at_target(SHalfedge_handle e)
00522 /*{\Mop merges the edge pairs at |v = e->target()|. |e| and |twin(e)| 
00523   are preserved, |e->snext()|, |twin(e->snext())| and |v| are deleted
00524   in the merger. \precond |v| has outdegree two. The adjacency at 
00525   |e->source()| and |target(e->snext())| is kept consistent.
00526   If |e->snext()| was entry point of |e->incident_sface()| then |e| takes this role.
00527   The same holds for |twin(e->snext())| and |face(twin(e))|.}*/
00528 {
00529   CGAL_NEF_TRACEN("merge_edge_pairs_at_target "<<PH(e));
00530   SHalfedge_handle en = e->snext(), eno = en->twin(), enn, enno,
00531                eo = e->twin() ;
00532   if ( is_closed_at_target(en) ) { enn = eo; enno=e; }
00533   else { enn = en->snext(), enno = eno->sprev(); }
00534   SVertex_handle v = e->target(), vn = en->target();
00535   CGAL_assertion(has_outdeg_two(v));
00536   SFace_handle f1 = en->incident_sface(), f2 = eno->incident_sface();
00537   // transfer the opposite face cycles e-en-enn to e-enn
00538   if ( enn != eno ) {
00539     link_as_prev_next_pair(e,enn);
00540     link_as_prev_next_pair(enno,eo);
00541   } else {
00542     link_as_prev_next_pair(e,eo);
00543   }
00544   // set vertex of e and deal with vertex-halfedge incidence
00545   eo->source() = vn;
00546 
00547   if ( first_out_edge(vn) == eno ) set_first_out_edge(vn,eo);
00548   if ( is_sm_boundary_object(en) )
00549   { undo_sm_boundary_object(en,f1); store_sm_boundary_object(e,f1); }
00550   if ( is_sm_boundary_object(eno) )
00551   { undo_sm_boundary_object(eno,f2); store_sm_boundary_object(eo,f2); }
00552   delete_vertex_only(v);
00553   delete_edge_pair_only(en);
00554   CGAL_NEF_TRACEN("END "<<PH(e->sprev())<<PH(e)<<PH(e->snext()));
00555 }
00556 
00557 void convert_edge_to_loop(SHalfedge_handle e)
00558 /*{\Mop converts the edge at |v = e->target()| to the unique
00559   loop |l| of |\Mvar|. |e|, |e->twin()| and |v| are deleted
00560   in the conversion. \precond there was no loop in |\Mvar|.
00561   As |e| was entry point of |e->incident_sface()| then |l| takes this role.}*/
00562 { CGAL_NEF_TRACEN("convert_edge_to_loop "<<PH(e));
00563   CGAL_assertion( e->source()==e->target() );
00564   CGAL_assertion( !has_shalfloop() );
00565   SHalfloop_handle l = new_shalfloop_pair();
00566   SVertex_handle v = e->target();
00567   SFace_handle f1 = e->incident_sface(), f2 = e->twin()->incident_sface();
00568   if( is_sm_boundary_object(e)) {
00569     CGAL_assertion( is_sm_boundary_object(e->twin()));
00570     undo_sm_boundary_object(e,f1); undo_sm_boundary_object(e->twin(),f2);
00571   }
00572   link_as_loop(l,f1), link_as_loop(l->twin(),f2);
00573   l->circle() = e->circle(); l->twin()->circle() = e->twin()->circle();
00574   l->mark() = l->twin()->mark() = e->mark();
00575   delete_vertex_only(v);
00576   delete_edge_pair_only(e);
00577 }
00578 
00579 void flip_diagonal(SHalfedge_handle e)
00580 { SHalfedge_handle r = e->twin();
00581   SHalfedge_handle en = e->snext(), enn= en->snext();
00582   SHalfedge_handle rn = r->snext(), rnn= rn->snext();
00583   CGAL_NEF_TRACEN(PH(e)<<PH(en)<<PH(enn));
00584   CGAL_NEF_TRACEN(PH(r)<<PH(rn)<<PH(rnn));
00585   CGAL_assertion( enn->snext()==e && rnn->snext()==r );
00586   remove_from_adj_list_at_source(e);
00587   remove_from_adj_list_at_source(r);
00588   set_adjacency_at_source_between(enn,e,en->twin());
00589   set_adjacency_at_source_between(rnn,r,rn->twin());
00590 }
00591      
00592 
00593 /*{\Mtext \headerline{Incomplete topological update primitives}}*/
00594 
00595 SHalfedge_handle new_shalfedge_pair_at_source
00596   (SHalfedge_handle e, int pos = AFTER) const
00597 /*{\Xop creates a new pair of edges  |(e1,e2)| representing |(e->source(),())| 
00598   by inserting |e1| before or after |e| into cyclic adjacency list of
00599   |e->source()| depending on |pos| from |\Mname::BEFORE, \Mname::AFTER|.}*/
00600 { SHalfedge_handle e_new = new_shalfedge_pair();
00601   if (pos < 0) set_adjacency_at_source_between(cap(e),e_new,e);
00602   else         set_adjacency_at_source_between(e,e_new,cas(e));
00603   return e_new;
00604 }
00605 
00606 SHalfedge_handle new_shalfedge_pair_at_source
00607   (SVertex_handle v, int pos = AFTER)
00608 /*{\Mop creates a new pair of edges  |(e1,e2)| representing |(v,())| 
00609   by inserting |e1| at the beginning (BEFORE) or end (AFTER)
00610   of adjacency list of |v|.}*/
00611 { SHalfedge_handle e1 = new_shalfedge_pair();
00612   if (!is_isolated(v)) {
00613     SHalfedge_handle ef = first_out_edge(v);
00614     if (pos < 0) { // before e1
00615       set_adjacency_at_source_between(cap(ef),e1,ef);
00616       set_first_out_edge(v,e1);
00617     } else {
00618       set_adjacency_at_source_between(cap(ef),e1,ef);
00619     }
00620   } else
00621     close_tip_at_source(e1,v);
00622   return e1;
00623 }
00624 
00625 void delete_edge_pair_at_source(SHalfedge_handle e) const
00626 /*{\Mop deletes |e| and its twin and maintains the adjacency at its 
00627   source.}*/
00628 { remove_from_adj_list_at_source(e);
00629   delete_edge_pair_only(e);
00630 }
00631 
00632 void link_as_target_and_append(SVertex_handle v, SHalfedge_handle e, int pos = AFTER)
00633 /*{\Mop makes |v| the target of |e| appends |e->twin()| to the adjacency list
00634    of |v|.}*/
00635 { if (!is_isolated(v)) {
00636     SHalfedge_handle ef = first_out_edge(v);
00637     set_adjacency_at_source_between(cap(ef), e->twin(), ef);
00638     if(pos<0)
00639       set_first_out_edge(v,e->twin());
00640   } else
00641     close_tip_at_target(e,v);
00642 }
00643 
00644 void link_as_source_of(SHalfedge_handle e, SVertex_handle v) const
00645 /*{\Mop makes |e->source() = v| and sets |e| as the first
00646         out edge if |v| was isolated before.}*/
00647 { e->source() = v;
00648   if (v->out_sedge() == SHalfedge_handle()) v->out_sedge() = e; }
00649 
00650 void link_as_target_of(SHalfedge_handle e, SVertex_handle v) const
00651 /*{\Mop makes |e->target() = v| and sets |e| as the first
00652   in edge if |v| was isolated before.}*/
00653 { link_as_source_of(e->twin(),v); }
00654 
00655 void set_adjacency_at_source_between(SHalfedge_handle e, SHalfedge_handle en)
00656 /*{\Mop makes |e| and |en| neigbors in the cyclic ordered adjacency list 
00657     around |v=e->source()|. \precond |e->source()==en->source()|.}*/
00658 { CGAL_assertion(e->source()==en->source());
00659   link_as_prev_next_pair(en->twin(),e);
00660 }
00661 
00662 void set_adjacency_at_source_between(SHalfedge_handle e1, 
00663                                      SHalfedge_handle e_between, 
00664                                      SHalfedge_handle e2)
00665 /*{\Mop inserts |e_between| into the adjacency list around |e1->source()| 
00666   between |e1| and |e2| and makes |e1->source()| the source of |e_between|. 
00667   \precond |e1->source()==e2->source()|.}*/
00668 { 
00669   e_between->source() = e1->source();
00670   set_adjacency_at_source_between(e1,e_between);
00671   set_adjacency_at_source_between(e_between,e2);
00672 }
00673 
00674 void close_tip_at_source(SHalfedge_handle e, SVertex_handle v) 
00675 /*{\Mop sets |v| as source of |e| and closes the tip by setting the 
00676   corresponding pointers such that |prev(e) == e->twin()| and
00677   |next(e->twin()) == e|.}*/
00678 { link_as_source_of(e,v); 
00679   link_as_prev_next_pair(e->twin(),e); }
00680 
00681 void close_tip_at_target(SHalfedge_handle e, SVertex_handle v) 
00682 /*{\Mop sets |v| as target of |e| and closes the tip by setting the 
00683   corresponding pointers such that |prev(e->twin()) == e| and 
00684   |e->snext() == e->twin()|.}*/
00685 { link_as_target_of(e,v);
00686   link_as_prev_next_pair(e,e->twin()); }
00687 
00688 
00689 void remove_from_adj_list_at_source(SHalfedge_handle e)
00690 /*{\Mop removes a halfedge pair |(e,e->twin()| from the adjacency list
00691 of |e->source()|. Afterwards |next(prev(e))==next(e->twin())| and
00692 |first_out_edge(e->source())| is valid if |degree(v->source())>1| before
00693 the operation.}*/
00694 {
00695   SVertex_handle v = e->source();
00696   if ( is_closed_at_source(e) ) { // last outgoing
00697     v->out_sedge() = SHalfedge_handle();
00698   } else {
00699     if (e == first_out_edge(v)) v->out_sedge() = cap(e);
00700     set_adjacency_at_source_between(cap(e),cas(e));
00701   }
00702 }
00703 
00704 void set_face(SHalfedge_handle e, SFace_handle f) const
00705 { e->incident_sface() = f; }
00706 void set_face(SHalfloop_handle l, SFace_handle f) const
00707 { l->incident_sface() = f; }
00708 void set_face(SVertex_handle v, SFace_handle f) const
00709 { v->incident_sface() = f; }
00710 void set_first_out_edge(SVertex_handle v, SHalfedge_handle e) const
00711 { v->out_sedge() = e; }
00712 void set_prev(SHalfedge_handle e, SHalfedge_handle ep) const
00713 { e->sprev() = ep; }
00714 void set_next(SHalfedge_handle e, SHalfedge_handle en) const
00715 { e->snext() = en; }
00716 void set_source(SHalfedge_handle e, SVertex_handle v) const
00717 { e->source() = v; }
00718 
00719 /*{\Mtext \headerline{Associated Information}\restoreopdims}*/
00720 
00721 void set_marks_in_face_cycle(SHalfedge_handle e, Mark m) const
00722 { SHalfedge_around_sface_circulator hfc(e), hend(hfc);
00723   CGAL_For_all(hfc,hend) hfc->mark() = hfc->target()->mark() = m;
00724 }
00725 
00726 GenPtr& info(SVertex_handle v) const
00727 { return v->info(); }
00728 GenPtr& info(SHalfedge_handle e) const
00729 { return e->info(); }
00730 GenPtr& info(SFace_handle f) const
00731 { return f->info(); }
00732 
00733 const GenPtr& info(SVertex_const_handle v) const
00734 { return v->info(); }
00735 const GenPtr& info(SHalfedge_const_handle e) const
00736 { return e->info(); }
00737 const GenPtr& info(SFace_const_handle f) const
00738 { return f->info(); }
00739 
00740  
00741 /*{\Mtext \headerline{Iteration}}*/
00742 /*{\Mtext The list of all objects can be accessed via iterator ranges.
00743 For comfortable iteration we also provide iterations macros. 
00744 The iterator range access operations are of the following kind:\\
00745 |SVertex_iterator svertices_begin()/svertices_end()|\\
00746 |SHalfedge_iterator shalfedges_begin()/shalfedges_end()|\\
00747 |SHalfedge_iterator sedges_begin()/sedges_end()|\\
00748 |SFace_iterator sfaces_begin()/sfaces_end()|
00749 
00750 The macros are then |CGAL_forall_svertices_of(v,V)|,
00751 |CGAL_forall_shalfedges_of(e,V)|, |CGAL_forall_sedges_of(e,V)|, 
00752 |CGAL_forall_sfaces_of(f,V)|, |CGAL_forall_sface_cycles_of(fc,F)|.}*/
00753 
00754 void transform( const Aff_transformation_3& linear) {
00755   //  CGAL_NEF_TRACEN("transform sphere map of vertex" << center_vertex()->point());
00756     // The affine transformation is linear, i.e., no translation part.
00757     CGAL_precondition( linear.hm(0,3) == 0 && 
00758                        linear.hm(1,3) == 0 && 
00759                        linear.hm(2,3) == 0);
00760 
00761     //    CGAL_NEF_TRACEN(linear);
00762     for (SVertex_iterator i = svertices_begin(); i != svertices_end(); ++i)
00763       i->point() = normalized(Sphere_point( i->point().transform( linear)));
00764     for (SHalfedge_iterator i = shalfedges_begin(); i !=shalfedges_end(); ++i)
00765       i->circle() = Sphere_circle( i->circle().transform( linear));
00766     if ( has_shalfloop()) {
00767       shalfloop()->circle() = Sphere_circle(shalfloop()->circle()
00768                                           .transform( linear));
00769       shalfloop()->twin()->circle()
00770         = Sphere_circle(shalfloop()->twin()->circle().transform( linear));
00771     }
00772 }
00773 
00774 void extract_complement() {
00775 
00776   SVertex_handle sv;
00777   CGAL_forall_svertices(sv,*this) sv->mark() = !sv->mark();
00778   SHalfedge_handle she;
00779   CGAL_forall_shalfedges(she,*this) she->mark() = !she->mark();
00780   SHalfloop_handle shl;
00781   if(has_shalfloop()) {
00782     shl = shalfloop(); 
00783     shl->mark() = shl->twin()->mark() = !shl->mark();
00784   }
00785   SFace_handle sf;
00786   CGAL_forall_sfaces(sf,*this) 
00787     sf->mark() = !sf->mark();
00788 }
00789 
00790 void extract_interior() {
00791 
00792   SVertex_handle sv;
00793   CGAL_forall_svertices(sv,*this) sv->mark() = false;
00794   SHalfedge_handle she;
00795   CGAL_forall_shalfedges(she,*this) she->mark() = false;
00796   SHalfloop_handle shl;
00797   if(has_shalfloop()) { 
00798     shl = shalfloop(); 
00799     shl->mark() = shl->twin()->mark() = false;
00800   }
00801 }
00802 
00803 void extract_boundary() {
00804 
00805   SVertex_handle sv;
00806   CGAL_forall_svertices(sv,*this) sv->mark() = true;
00807   SHalfedge_handle she;
00808   CGAL_forall_shalfedges(she,*this) she->mark() = true;
00809   SHalfloop_handle shl;
00810   if(has_shalfloop()) { 
00811     shl = shalfloop(); 
00812     shl->mark() = shl->twin()->mark() = true;
00813   }
00814   SFace_handle sf;
00815   CGAL_forall_sfaces(sf,*this) sf->mark() = false;
00816 }
00817 
00818 bool is_valid( Unique_hash_map<SVertex_handle,bool>& sv_hash,
00819                Unique_hash_map<SHalfedge_handle,bool>& se_hash,
00820                Unique_hash_map<SFace_handle,bool>& sf_hash,
00821                bool verb = false, int level = 0) {
00822     
00823   Verbose_ostream verr(verb);
00824   verr << "begin CGAL::SNC_SM_decorator<...>::is_valid( verb=true, "
00825     "level = " << level << "):" << std::endl;
00826     
00827   bool valid = true;
00828 
00829   int count = 0;
00830   int max = 2 * number_of_svertices() 
00831     + 2 * number_of_shalfedges()
00832     + number_of_sfaces()
00833     + 2;
00834   
00835   SVertex_handle sv;
00836   int isolated_vertices_found = 0;
00837   CGAL_forall_svertices(sv,*this) {
00838     valid = valid && (!sv_hash[sv]);
00839     sv_hash[sv] = true;
00840     if(is_isolated(sv)) 
00841       isolated_vertices_found++;
00842     valid = valid && (++count <= max);
00843   }
00844 
00845   SHalfedge_iterator she;
00846   CGAL_forall_shalfedges(she,*this) {
00847     valid = valid && she->is_valid(verb, level);
00848 
00849     valid = valid && (she->twin() != she);
00850     valid = valid && (she->twin()->twin() == she);
00851     valid = valid && (she->snext()->sprev() == she);
00852     valid = valid && ((she->sprev() != she && she->snext() != she) || 
00853                       (she->sprev() == she && she->snext() == she));
00854     valid = valid && (she->incident_sface() == she->snext()->incident_sface());
00855     valid = valid && (she->incident_sface() == she->sprev()->incident_sface());
00856 
00857     valid = valid && (!se_hash[she]);
00858 
00859     //    Plane_3 pl(point(she->source()),point(she->target()),Point_3(0,0,0));
00860     //    Sphere_point vct(pl.orthogonal_vector());
00861     //    valid = valid && (normalized(Sphere_point(she->circle().orthogonal_vector())) == normalized(vct) || 
00862     //        normalized(Sphere_point(she->circle().opposite().orthogonal_vector())) == normalized(vct));
00863 
00864     se_hash[she] = true;
00865     valid = valid && (++count <= max);
00866   }
00867 
00868   if(has_shalfloop()) {
00869     SHalfloop_handle shl = shalfloop();
00870     valid = valid && shl->is_valid();
00871     valid = valid && shl->twin()->is_valid();
00872     valid = valid && (shl->twin() != shl);
00873     valid = valid && (shl->twin()->twin() == shl); 
00874   }
00875 
00876   SFace_iterator sf;
00877   SFace_cycle_iterator sfc;  
00878   int loop_entries_found = 0;
00879   int edge_entries_found = 0;
00880   int vertex_entries_found = 0;
00881   CGAL_forall_sfaces(sf,*this) {
00882     valid = valid && sf->is_valid(verb, level);
00883     valid = valid && (!sf_hash[sf]);
00884     sf_hash[sf] = true;
00885     
00886     CGAL_forall_sface_cycles_of(sfc,sf) {
00887       if (sfc.is_shalfloop()) 
00888         loop_entries_found++;
00889       else if(sfc.is_shalfedge())
00890         edge_entries_found++;
00891       else if(sfc.is_svertex())
00892         vertex_entries_found++;
00893       valid = valid && (++count <= max);
00894     }
00895     
00896     valid = valid && (++count <= max);
00897   }
00898 
00899   if(has_shalfloop())
00900     valid = valid && (loop_entries_found == 2);
00901   else
00902     valid = valid && (loop_entries_found == 0);
00903 
00904   if(number_of_shalfedges() > 0)
00905     valid = valid && (edge_entries_found > 0);
00906   else
00907     valid = valid && (edge_entries_found == 0);
00908 
00909   valid = valid && (vertex_entries_found == isolated_vertices_found);
00910 
00911   verr << "end of CGAL::SNC_SM_decorator<...>::is_valid(): structure is "
00912        << ( valid ? "valid." : "NOT VALID.") << std::endl;
00913 
00914   return valid;
00915 }
00916 
00917   template <typename Selection>
00918   void change_marks(const Mark& m, const Selection& SP) {
00919    
00920     psm_->mark() = SP(m, psm_->mark());
00921 
00922     SVertex_iterator v;
00923     CGAL_forall_svertices(v,*this)
00924       v->mark() = SP(m, v->mark());
00925 
00926     SHalfedge_iterator e;
00927     CGAL_forall_shalfedges(e,*this)
00928       e->mark() = SP(m, e->mark());
00929 
00930     SFace_iterator f;
00931     CGAL_forall_sfaces(f,*this) 
00932       f->mark() = SP(m, f->mark());
00933   }
00934 
00935   template <typename Selection>
00936   void change_marks(const Selection& SP, const Mark& m) {
00937    
00938     psm_->mark() = SP(psm_->mark(), m);
00939 
00940     SVertex_iterator v;
00941     CGAL_forall_svertices(v,*this)
00942       v->mark() = SP(v->mark(),m);
00943 
00944     SHalfedge_iterator e;
00945     CGAL_forall_shalfedges(e,*this)
00946       e->mark() = SP(e->mark(),m);
00947 
00948     SFace_iterator f;
00949     CGAL_forall_sfaces(f,*this) 
00950       f->mark() = SP(f->mark(),m);
00951   }
00952 
00953 void check_integrity_and_topological_planarity(bool faces=true) const {
00954   SM_const_decorator C(psm_);
00955   C.check_integrity_and_topological_planarity(faces);
00956 }
00957 
00958 }; // SM_decorator
00959 
00960 
00961 CGAL_END_NAMESPACE
00962 #endif // CGAL_SM_DECORATOR_H
00963 
00964 
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines