BWAPI
|
00001 // Copyright (c) 1997 Tel-Aviv University (Israel). 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/Arrangement_on_surface_2/include/CGAL/Arr_topology_traits/Arr_unb_planar_construction_helper.h $ 00015 // $Id: Arr_unb_planar_construction_helper.h 49772 2009-06-03 21:25:53Z eric $ 00016 // 00017 // 00018 // Author(s) : Baruch Zukerman <baruchzu@post.tau.ac.il> 00019 // Ron Wein <wein@post.tau.ac.il> 00020 // Efi Fogel <efif@post.tau.ac.il> 00021 00022 #ifndef CGAL_ARR_UNB_PLANAR_CONSTRUCTION_HELPER_H 00023 #define CGAL_ARR_UNB_PLANAR_CONSTRUCTION_HELPER_H 00024 00029 #include <CGAL/Sweep_line_empty_visitor.h> 00030 #include <CGAL/Unique_hash_map.h> 00031 00032 CGAL_BEGIN_NAMESPACE 00033 00039 template <class Traits_, class Arrangement_, class Event_, class Subcurve_> 00040 class Arr_unb_planar_construction_helper 00041 { 00042 public: 00043 00044 typedef Traits_ Traits_2; 00045 typedef Arrangement_ Arrangement_2; 00046 typedef Event_ Event; 00047 typedef Subcurve_ Subcurve; 00048 00049 typedef typename Traits_2::X_monotone_curve_2 X_monotone_curve_2; 00050 typedef typename Traits_2::Point_2 Point_2; 00051 00052 typedef Sweep_line_empty_visitor<Traits_2, Subcurve, Event> 00053 Base_visitor; 00054 00055 typedef typename Arrangement_2::Halfedge_handle Halfedge_handle; 00056 typedef typename Arrangement_2::Face_handle Face_handle; 00057 00058 typedef typename Subcurve::Halfedge_indices_list Indices_list; 00059 typedef Unique_hash_map<Halfedge_handle, 00060 Indices_list> Halfedge_indices_map; 00061 00062 protected: 00063 00064 typedef typename Arrangement_2::Topology_traits Topology_traits; 00065 typedef typename Arrangement_2::Vertex_handle Vertex_handle; 00066 00067 // Data members: 00068 Topology_traits *m_top_traits; // The topology-traits class. 00069 Arr_accessor<Arrangement_2> 00070 m_arr_access; // An arrangement accessor. 00071 00072 Halfedge_handle m_lh; // The current left fictitious 00073 // halfedge (on x = -oo). 00074 Halfedge_handle m_th; // The current top fictitious 00075 // halfedge (on y = +oo). 00076 Halfedge_handle m_bh; // The current bottom fictitious 00077 // halfedge (on y = -oo). 00078 Halfedge_handle m_rh; // The current right fictitious 00079 // halfedge (on x = +oo). 00080 00081 Indices_list m_subcurves_at_ubf; // Indices of the curves that 00082 // "see" m_th from below. 00083 Event* m_prev_minus_inf_x_event; // The previous event at x = -oo. 00084 Event* m_prev_plus_inf_y_event; // The previous event at y = +oo. 00085 00086 Halfedge_indices_map *m_he_ind_map_p; // A pointer to a map of 00087 // halfedges to indices lists 00088 // (stored in the visitor class). 00089 00090 public: 00091 00093 Arr_unb_planar_construction_helper (Arrangement_2 *arr) : 00094 m_top_traits (arr->topology_traits()), 00095 m_arr_access (*arr), 00096 m_prev_minus_inf_x_event (NULL), 00097 m_prev_plus_inf_y_event (NULL), 00098 m_he_ind_map_p (NULL) 00099 {} 00100 00102 virtual ~Arr_unb_planar_construction_helper(){} 00103 00105 00106 00107 /* A notification issued before the sweep process starts. */ 00108 virtual void before_sweep (); 00109 00114 virtual void before_handle_event (Event* event); 00115 00117 virtual void add_subcurve (Halfedge_handle /* he */, 00118 Subcurve* /* sc */) 00119 { 00120 return; 00121 } 00122 00124 void add_subcurve_in_top_face (unsigned int index) 00125 { 00126 m_subcurves_at_ubf.push_back (index); 00127 return; 00128 } 00129 00131 void before_deallocate_event (Event* event) 00132 { 00133 // The last event at y = +oo may be deallocated if it has no incident 00134 // right subcurves, so we should not keep a pointer to it. 00135 if (event == m_prev_plus_inf_y_event) 00136 m_prev_plus_inf_y_event = NULL; 00137 00138 return; 00139 } 00141 00146 void set_halfedge_indices_map (Halfedge_indices_map& table) 00147 { 00148 m_he_ind_map_p = &table; 00149 return; 00150 } 00151 00156 bool swap_predecessors (Event* event) const 00157 { 00158 // If we insert an edge whose right end lies on the top edge of the 00159 // ficititous bounding rectangle, we have to flip the order of predecessor 00160 // halfegdes. 00161 return ((event->parameter_space_in_x() == ARR_INTERIOR) && 00162 (event->parameter_space_in_y() == ARR_TOP_BOUNDARY)); 00163 } 00164 00166 Face_handle top_face () const 00167 { 00168 return (m_th->face()); 00169 } 00170 }; 00171 00172 //----------------------------------------------------------------------------- 00173 // Memeber-function definitions: 00174 //----------------------------------------------------------------------------- 00175 00176 //----------------------------------------------------------------------------- 00177 // A notification issued before the sweep process starts. 00178 // 00179 template <class Tr, class Arr, class Evnt, class Sbcv> 00180 void Arr_unb_planar_construction_helper<Tr,Arr,Evnt,Sbcv>::before_sweep () 00181 { 00182 // Obtain the four fictitious vertices that form the "corners" of the 00183 // fictitious face in the DCEL. 00184 Vertex_handle v_bl = Vertex_handle (m_top_traits->bottom_left_vertex()); 00185 Vertex_handle v_tl = Vertex_handle (m_top_traits->top_left_vertex()); 00186 Vertex_handle v_br = Vertex_handle (m_top_traits->bottom_right_vertex()); 00187 Vertex_handle v_tr = Vertex_handle (m_top_traits->top_right_vertex()); 00188 00189 // Get the fictitous halfedges incident to these vertices, representing 00190 // the left, right, top and bottom edges of the fictitious face. 00191 // 00192 // m_th 00193 // v_tl (.)<----------(.) v_tr 00194 // | ^ 00195 // m_lh | | m_rh 00196 // v | 00197 // v_bl (.)---------->(.) v_br 00198 // m_bh 00199 // 00200 m_lh = v_tl->incident_halfedges(); 00201 00202 if(m_lh->source() != v_bl) 00203 m_lh = m_lh->next(); 00204 else 00205 m_lh = m_lh->twin(); 00206 00207 m_bh = m_lh->next(); 00208 m_rh = m_bh->next(); 00209 m_th = m_rh->next(); 00210 00211 CGAL_assertion_code ( 00212 Face_handle fict_face = Face_handle (m_top_traits->fictitious_face()); 00213 ); 00214 CGAL_assertion (m_lh->direction() == ARR_RIGHT_TO_LEFT); 00215 CGAL_assertion (m_lh->face() != fict_face); 00216 CGAL_assertion (m_lh->source() == v_tl && m_lh->target() == v_bl); 00217 00218 CGAL_assertion (m_bh->direction() == ARR_LEFT_TO_RIGHT); 00219 CGAL_assertion (m_bh->face() != fict_face); 00220 CGAL_assertion (m_bh->source() == v_bl && m_bh->target() == v_br); 00221 00222 CGAL_assertion (m_rh->direction() == ARR_LEFT_TO_RIGHT); 00223 CGAL_assertion (m_rh->face() != fict_face); 00224 CGAL_assertion (m_rh->source() == v_br && m_rh->target() == v_tr); 00225 00226 CGAL_assertion (m_th->direction() == ARR_RIGHT_TO_LEFT); 00227 CGAL_assertion (m_th->face() != fict_face); 00228 CGAL_assertion (m_th->source() == v_tr && m_th->target() == v_tl); 00229 } 00230 00231 //----------------------------------------------------------------------------- 00232 // A notification invoked before the sweep-line starts handling the given 00233 // event. 00234 // 00235 template <class Tr, class Arr, class Evnt, class Sbcv> 00236 void Arr_unb_planar_construction_helper<Tr,Arr,Evnt,Sbcv>:: 00237 before_handle_event (Event* event) 00238 { 00239 if (event->is_closed()) 00240 return; 00241 00242 // As the event lieas at infinity, it must have only one (right or left) 00243 // incident curve. 00244 CGAL_assertion(((event->number_of_left_curves() == 0) && 00245 (event->number_of_right_curves() == 1)) || 00246 ((event->number_of_left_curves() == 1) && 00247 (event->number_of_right_curves() == 0))); 00248 Arr_curve_end ind = (event->number_of_left_curves() == 0 && 00249 event->number_of_right_curves() == 1) ? 00250 ARR_MIN_END : ARR_MAX_END; 00251 const X_monotone_curve_2& xc = (ind == ARR_MIN_END) ? 00252 (*(event->right_curves_begin()))->last_curve() : 00253 (*(event->left_curves_begin()))->last_curve(); 00254 00255 const Arr_parameter_space ps_x = event->parameter_space_in_x(); 00256 const Arr_parameter_space ps_y = event->parameter_space_in_y(); 00257 00258 // Create a vertex at infinity and split the corresponding fictitious edge. 00259 Vertex_handle v_at_inf = 00260 m_arr_access.create_boundary_vertex (xc, ind, ps_x, ps_y, false); 00261 00262 switch (ps_x) { 00263 case ARR_LEFT_BOUNDARY: 00264 // The event lies on the left fictitious halfedge. 00265 m_arr_access.split_fictitious_edge(m_lh, v_at_inf); 00266 event->set_halfedge_handle(m_lh); 00267 00268 // Update the incident halfedge of the previous vertex at x = -oo 00269 // (m_lh used to be incident to it, but now we have split it). 00270 if (m_prev_minus_inf_x_event != NULL) 00271 m_prev_minus_inf_x_event->set_halfedge_handle(m_lh->next()); 00272 m_prev_minus_inf_x_event = event; 00273 return; 00274 00275 case ARR_RIGHT_BOUNDARY: 00276 // The event lies on the right fictitious halfedge. 00277 m_arr_access.split_fictitious_edge(m_rh, v_at_inf); 00278 event->set_halfedge_handle(m_rh); 00279 m_rh = m_rh->next(); 00280 return; 00281 00282 case ARR_INTERIOR: 00283 break; 00284 00285 default: 00286 CGAL_error(); 00287 } 00288 00289 switch (ps_y) { 00290 case ARR_BOTTOM_BOUNDARY: 00291 // The event lies on the bottom fictitious halfedge. 00292 m_arr_access.split_fictitious_edge(m_bh, v_at_inf); 00293 event->set_halfedge_handle(m_bh); 00294 m_bh = m_bh->next(); 00295 return; 00296 00297 case ARR_TOP_BOUNDARY: 00298 { 00299 // The event lies on the top fictitious halfedge. 00300 m_arr_access.split_fictitious_edge(m_th, v_at_inf); 00301 event->set_halfedge_handle(m_th); 00302 00303 // Update the incident halfedge of the previous vertex at y = +oo 00304 // (m_th used to be incident to it, but now we have split it). 00305 if(m_prev_plus_inf_y_event != NULL) 00306 m_prev_plus_inf_y_event->set_halfedge_handle(m_th->next()); 00307 m_prev_plus_inf_y_event = event; 00308 00309 // Associate all curve indices of subcurves that "see" m_th from 00310 // below with the left portion of the split halfedge (m_th->next()). 00311 if (m_he_ind_map_p != NULL) 00312 { 00313 Indices_list& list_ref = (*m_he_ind_map_p)[m_th->next()]; 00314 list_ref.clear(); 00315 list_ref.splice (list_ref.end(), m_subcurves_at_ubf); 00316 } 00317 else 00318 { 00319 m_subcurves_at_ubf.clear(); 00320 } 00321 CGAL_assertion (m_subcurves_at_ubf.empty()); 00322 } 00323 return; 00324 00325 case ARR_INTERIOR: 00326 default: 00327 // We are not supposed to reach here at all. 00328 CGAL_error(); 00329 } 00330 00331 return; 00332 } 00333 00334 CGAL_END_NAMESPACE 00335 00336 #endif