1 // Copyright (c) 1997 INRIA Sophia-Antipolis (France).
2 // All rights reserved.
3 //
4 // This file is part of CGAL (www.cgal.org).
5 //
6 // $URL: https://github.com/CGAL/cgal/blob/v5.3/TDS_2/include/CGAL/Triangulation_ds_circulators_2.h $
7 // $Id: Triangulation_ds_circulators_2.h 74d8922 2020-04-20T15:25:40+02:00 Guillaume Damiand
8 // SPDX-License-Identifier: GPL-3.0-or-later OR LicenseRef-Commercial
9 //
10 //
11 // Author(s) : Mariette Yvinec
12 // Menelaos Karavelas <mkaravel@cse.nd.edu>
13
14 #ifndef CGAL_TRIANGULATION_DS_CIRCULATORS_2_H
15 #define CGAL_TRIANGULATION_DS_CIRCULATORS_2_H
16
17 #include <CGAL/license/TDS_2.h>
18
19
20 #include <utility>
21 #include <iterator>
22 #include <CGAL/circulator.h>
23 #include <CGAL/triangulation_assertions.h>
24 #include <CGAL/Triangulation_utils_2.h>
25
26 namespace CGAL {
27
28 template < class Tds>
29 class Triangulation_ds_face_circulator_2
30 : public Bidirectional_circulator_base< typename Tds::Face,
31 std::ptrdiff_t,
32 std::size_t>,
33 public Triangulation_cw_ccw_2
34
35 {
36 private:
37 typedef
38 Bidirectional_circulator_base< typename Tds::Face,
39 std::ptrdiff_t,
40 std::size_t> Base_circulator;
41
42 public:
43 typedef Triangulation_ds_face_circulator_2<Tds> Face_circulator;
44 typedef typename Tds::Face Face;
45 typedef typename Tds::Vertex Vertex;
46 typedef typename Tds::Face_handle Face_handle;
47 typedef typename Tds::Vertex_handle Vertex_handle;
48
49
50 private:
51 Vertex_handle _v;
52 Face_handle pos;
53
54 public:
Triangulation_ds_face_circulator_2()55 Triangulation_ds_face_circulator_2()
56 : _v(), pos()
57 {}
58
59 Triangulation_ds_face_circulator_2(Vertex_handle v,
60 Face_handle f = Face_handle());
61
62 Face_circulator& operator++();
63 Face_circulator operator++(int);
64 Face_circulator& operator--();
65 Face_circulator operator--(int);
66
67 bool operator==(const Face_circulator &fc) const;
68 bool operator!=(const Face_circulator &fc) const;
69
70 bool operator==(const Face_handle &fh) const { return pos == fh; }
71 bool operator!=(const Face_handle &fh) const { return pos != fh; }
72
73 bool is_empty() const;
74 bool operator==(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const;
75 bool operator!=(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const;
76
77 Face&
78 operator*() const
79 {
80 CGAL_triangulation_precondition(pos != Face_handle() &&
81 _v != Vertex_handle());
82 return *pos;
83 }
84
85 Face*
86 operator->() const
87 {
88 CGAL_triangulation_precondition(pos != Face_handle() &&
89 _v != Vertex_handle());
90 return &*pos;
91 }
92
base()93 Face_handle base() const {return pos;}
Face_handle()94 operator Face_handle() const {return pos;}
95 };
96
97 template < class Tds_ >
98 bool
99 operator==(typename Tds_::Face_handle fh,
100 Triangulation_ds_face_circulator_2<Tds_> fc)
101 {
102 return (fc==fh);
103 }
104
105 template < class Tds_ >
106 bool
107 operator!=(typename Tds_::Face_handle fh,
108 Triangulation_ds_face_circulator_2<Tds_> fc)
109 {
110 return (fc!=fh);
111 }
112
113
114 template < class Tds >
115 class Triangulation_ds_vertex_circulator_2 :
116 public Bidirectional_circulator_base< typename Tds::Vertex,
117 std::ptrdiff_t,
118 std::size_t>,
119 public Triangulation_cw_ccw_2
120 {
121 public:
122 typedef Triangulation_ds_vertex_circulator_2<Tds> Vertex_circulator;
123 typedef typename Tds::Face Face;
124 typedef typename Tds::Vertex Vertex;
125 typedef typename Tds::Face_handle Face_handle;
126 typedef typename Tds::Vertex_handle Vertex_handle;
127
128 private:
129 Vertex_handle _v;
130 Face_handle pos;
131 int _ri;
132
133 public:
Triangulation_ds_vertex_circulator_2()134 Triangulation_ds_vertex_circulator_2()
135 : _v(), pos()
136 {}
137
138 Triangulation_ds_vertex_circulator_2(Vertex_handle v,
139 Face_handle f = Face_handle());
140
141 Vertex_circulator& operator++();
142 Vertex_circulator operator++(int);
143 Vertex_circulator& operator--();
144 Vertex_circulator operator--(int);
145
146 bool operator==(const Vertex_circulator &vc) const;
147 bool operator!=(const Vertex_circulator &vc) const;
148
149 bool operator==(const Vertex_handle &vh) const
150 { return pos->vertex(_ri) == vh; }
151 bool operator!=(const Vertex_handle &vh) const
152 { return pos->vertex(_ri) != vh; }
153
154 bool is_empty() const;
155 bool operator==(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const;
156 bool operator!=(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const;
157
158 Vertex&
159 operator*() const
160 {
161 CGAL_triangulation_precondition(pos != Face_handle() &&
162 _v != Vertex_handle());
163 return *(pos->vertex(_ri));
164 }
165
166 Vertex*
167 operator->() const
168 {
169 CGAL_triangulation_precondition(pos != Face_handle() &&
170 _v != Vertex_handle());
171 return &*(pos->vertex(_ri));
172 }
173
base()174 Vertex_handle base() const {return pos->vertex(_ri);}
Vertex_handle()175 operator Vertex_handle() const {return pos->vertex(_ri);}
176 };
177
178 template < class Tds_ >
179 inline
180 bool
181 operator==(typename Tds_::Vertex_handle vh,
182 Triangulation_ds_vertex_circulator_2<Tds_> vc)
183 {
184 return (vc==vh);
185 }
186
187 template < class Tds_ >
188 inline
189 bool
190 operator!=(typename Tds_::Vertex_handle vh,
191 Triangulation_ds_vertex_circulator_2<Tds_> vc)
192 {
193 return !(vc==vh);
194 }
195
196
197 template < class Tds >
198 class Triangulation_ds_edge_circulator_2 :
199 public Bidirectional_circulator_base < typename Tds::Edge,
200 std::ptrdiff_t,
201 std::size_t>,
202 public Triangulation_cw_ccw_2
203 {
204 public:
205 typedef Triangulation_ds_edge_circulator_2<Tds> Edge_circulator;
206 typedef typename Tds::Face Face;
207 typedef typename Tds::Vertex Vertex;
208 typedef typename Tds::Edge Edge;
209 typedef typename Tds::Face_handle Face_handle;
210 typedef typename Tds::Vertex_handle Vertex_handle;
211
212 private:
213 int _ri;
214 Vertex_handle _v;
215 Face_handle pos;
216 mutable Edge edge;
217
218 public:
Triangulation_ds_edge_circulator_2()219 Triangulation_ds_edge_circulator_2()
220 : _ri(0), _v(), pos()
221 {}
222
223 Triangulation_ds_edge_circulator_2( Vertex_handle v,
224 Face_handle f = Face_handle());
225
226 Edge_circulator& operator++();
227 Edge_circulator operator++(int);
228 Edge_circulator& operator--();
229 Edge_circulator operator--(int);
230
231 bool operator==(const Edge_circulator &vc) const;
232 bool operator!=(const Edge_circulator &vc) const;
233 bool is_empty() const;
234 bool operator==(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const;
235 bool operator!=(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const;
236
237 Edge* operator->() const {
238 edge.first=pos;
239 edge.second= _ri;
240 return &edge;
241 }
242
243 Edge& operator*() const {
244 edge.first=pos;
245 edge.second= _ri;
246 return edge;
247 }
248
249 };
250
251
252 template < class Tds >
253 Triangulation_ds_face_circulator_2<Tds> ::
Triangulation_ds_face_circulator_2(Vertex_handle v,Face_handle f)254 Triangulation_ds_face_circulator_2(Vertex_handle v, Face_handle f)
255 : _v(v), pos(f)
256 {
257 if (_v == Vertex_handle()) pos = Face_handle();
258 else if ( pos == Face_handle()) pos = v->face();
259
260 if (pos == Face_handle()|| pos->dimension() < 2) {
261 _v = Vertex_handle() ; pos = Face_handle(); return;}
262 else CGAL_triangulation_precondition( pos->has_vertex(v));
263 }
264
265
266 template < class Tds >
267 Triangulation_ds_face_circulator_2<Tds>&
268 Triangulation_ds_face_circulator_2<Tds> ::
269 operator++()
270 {
271 CGAL_triangulation_precondition( pos != Face_handle() &&
272 _v != Vertex_handle());
273 int i = pos->index(_v);
274 pos = pos->neighbor(ccw(i));
275 return *this;
276 }
277
278 template < class Tds >
279 Triangulation_ds_face_circulator_2<Tds>
280 Triangulation_ds_face_circulator_2<Tds> ::
281 operator++(int)
282 {
283 CGAL_triangulation_precondition(pos != Face_handle() &&
284 _v != Vertex_handle());
285 Face_circulator tmp(*this);
286 ++(*this);
287 return tmp;
288 }
289
290 template < class Tds >
291 Triangulation_ds_face_circulator_2<Tds>&
292 Triangulation_ds_face_circulator_2<Tds> ::
293 operator--()
294 {
295 CGAL_triangulation_precondition(pos != Face_handle() &&
296 _v != Vertex_handle());
297 int i = pos->index(_v);
298 pos = pos->neighbor(cw(i));
299 return *this;
300 }
301
302 template < class Tds >
303 Triangulation_ds_face_circulator_2<Tds>
304 Triangulation_ds_face_circulator_2<Tds> ::
305 operator--(int)
306 {
307 CGAL_triangulation_precondition(pos != Face_handle() &&
308 _v != Vertex_handle());
309 Face_circulator tmp(*this);
310 --(*this);
311 return tmp;
312 }
313
314 template < class Tds >
315 inline bool
316 Triangulation_ds_face_circulator_2<Tds> ::
317 operator==(const Face_circulator &fc) const
318 {
319 return (_v == fc._v) && (pos == fc.pos);
320 }
321
322 template < class Tds >
323 inline bool
324 Triangulation_ds_face_circulator_2<Tds> ::
325 operator!=(const Face_circulator &fc) const
326 {
327 return ! (*this == fc);
328 }
329
330 template < class Tds >
331 inline bool
332 Triangulation_ds_face_circulator_2<Tds> ::
is_empty()333 is_empty() const
334 {
335 return (_v == Vertex_handle() || pos == Face_handle() );
336 }
337
338 template < class Tds >
339 inline bool
340 Triangulation_ds_face_circulator_2<Tds> ::
341 operator==(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const
342 {
343 //CGAL_triangulation_assertion( n == nullptr);
344 return (_v == Vertex_handle() || pos == Face_handle() );
345 }
346
347 template < class Tds >
348 inline bool
349 Triangulation_ds_face_circulator_2<Tds> ::
350 operator!=(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const
351 {
352 //CGAL_triangulation_assertion( n == nullptr);
353 return ! (*this == nullptr);
354 }
355
356 template < class Tds >
357 Triangulation_ds_vertex_circulator_2<Tds> ::
Triangulation_ds_vertex_circulator_2(Vertex_handle v,Face_handle f)358 Triangulation_ds_vertex_circulator_2 (Vertex_handle v,
359 Face_handle f)
360 : _v( v ), pos(f)
361 {
362 if (_v == Vertex_handle()) { pos = Face_handle();}
363 else if (pos == Face_handle()) {pos = v->face();}
364
365 if (pos == Face_handle() || pos->dimension() < 1){
366 _v = Vertex_handle(); pos = Face_handle(); return;}
367 int i = pos->index(_v);
368 if (pos->dimension() == 2) {_ri = ccw(i);}
369 else {CGAL_assertion(i>=0 && i<=1);_ri = (i == 0) ? 1 : 0;}
370 return;
371 }
372
373
374 template < class Tds >
375 Triangulation_ds_vertex_circulator_2<Tds>&
376 Triangulation_ds_vertex_circulator_2<Tds> ::
377 operator++()
378 {
379 CGAL_triangulation_precondition(pos != Face_handle() &&
380 _v != Vertex_handle());
381 int i = pos->index(_v);
382
383 if (pos->dimension() == 1) {
384 CGAL_assertion(i>=0 && i<=1);
385 pos = pos->neighbor((i == 0) ? 1 : 0);
386 _ri = 1 - pos->index(_v);
387 }
388 else{
389 pos = pos->neighbor(ccw(i));
390 i = pos->index(_v);
391 _ri = ccw(i);
392 }
393 return *this;
394 }
395
396 template < class Tds >
397 Triangulation_ds_vertex_circulator_2<Tds>
398 Triangulation_ds_vertex_circulator_2<Tds> ::
399 operator++(int)
400 {
401 Vertex_circulator tmp(*this);
402 ++(*this);
403 return tmp;
404 }
405
406 template < class Tds >
407 Triangulation_ds_vertex_circulator_2<Tds>&
408 Triangulation_ds_vertex_circulator_2<Tds> ::
409 operator--()
410 {
411 CGAL_triangulation_precondition(pos != Face_handle() &&
412 _v != Vertex_handle());
413 int i = pos->index(_v);
414
415 if (pos->dimension() == 1) {
416 CGAL_assertion(i>=0 && i<=1);
417 pos = pos->neighbor((i == 0) ? 1 : 0);
418 _ri = 1 - pos->index(_v);
419 }
420 else{
421 pos = pos->neighbor(cw(i));
422 i = pos->index(_v);
423 _ri = ccw(i);
424 }
425 return *this;
426 }
427
428 template < class Tds >
429 Triangulation_ds_vertex_circulator_2<Tds>
430 Triangulation_ds_vertex_circulator_2<Tds> ::
431 operator--(int)
432 {
433 Vertex_circulator tmp(*this);
434 --(*this);
435 return tmp;
436 }
437
438 template < class Tds >
439 inline bool
440 Triangulation_ds_vertex_circulator_2<Tds> ::
441 operator==(const Vertex_circulator &vc) const
442 {
443 return (_v == vc._v) && (_ri == vc._ri) && (pos == vc.pos);
444 }
445
446 template < class Tds >
447 inline bool
448 Triangulation_ds_vertex_circulator_2<Tds> ::
449 operator!=(const Vertex_circulator &vc) const
450 {
451 return ! (*this == vc);
452 }
453
454 template < class Tds >
455 inline bool
456 Triangulation_ds_vertex_circulator_2<Tds> ::
is_empty()457 is_empty() const
458 {
459 return (_v == Vertex_handle() || pos == Face_handle());
460 }
461
462 template < class Tds >
463 inline bool
464 Triangulation_ds_vertex_circulator_2<Tds> ::
465 operator==(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const
466 {
467 //CGAL_triangulation_assertion( n == nullptr);
468 return (_v == Vertex_handle() || pos == Face_handle());
469 }
470
471 template < class Tds >
472 inline bool
473 Triangulation_ds_vertex_circulator_2<Tds> ::
474 operator!=(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const
475 {
476 //CGAL_triangulation_assertion( n == nullptr);
477 return !(*this == nullptr);
478 }
479
480
481 template < class Tds >
482 Triangulation_ds_edge_circulator_2<Tds> ::
Triangulation_ds_edge_circulator_2(Vertex_handle v,Face_handle f)483 Triangulation_ds_edge_circulator_2(Vertex_handle v, Face_handle f)
484 : _v(v), pos(f)
485 {
486 if (_v == Vertex_handle()) { pos = Face_handle();}
487 else if (pos==Face_handle()) {pos = v->face();}
488
489 if (pos == Face_handle() || pos->dimension() < 1){
490 _ri = 0; _v = Vertex_handle(); pos = Face_handle();return;}
491 int i = pos->index(_v);
492 if (pos->dimension() == 2) {_ri = ccw(i);}
493 else {_ri = 2;}
494 return;
495 }
496
497 template < class Tds >
498 Triangulation_ds_edge_circulator_2<Tds>&
499 Triangulation_ds_edge_circulator_2<Tds> ::
500 operator++()
501 {
502 CGAL_triangulation_precondition(pos != Face_handle() &&
503 _v != Vertex_handle());
504 int i = pos->index(_v);
505 if (pos->dimension() == 1) {
506 CGAL_assertion(i>=0 && i<=1);
507 pos = pos->neighbor(i == 0 ? 1 : 0);
508 return *this;
509 }
510 else{
511 pos = pos->neighbor(ccw(i));
512 i = pos->index(_v);
513 _ri = ccw(i);
514 }
515 return *this;
516 }
517
518 template < class Tds >
519 Triangulation_ds_edge_circulator_2<Tds>
520 Triangulation_ds_edge_circulator_2<Tds> ::
521 operator++(int)
522 {
523 Edge_circulator tmp(*this);
524 ++(*this);
525 return tmp;
526 }
527
528 template < class Tds >
529 Triangulation_ds_edge_circulator_2<Tds>&
530 Triangulation_ds_edge_circulator_2<Tds> ::
531 operator--()
532 {
533 CGAL_triangulation_precondition(pos != Face_handle() &&
534 _v != Vertex_handle());
535 int i = pos->index(_v);
536
537 if (pos->dimension() == 1) {
538 CGAL_assertion(i>=0 && i<=1);
539 pos = pos->neighbor((i == 0) ? 1 : 0);
540 return *this;
541 }
542 else{
543 pos = pos->neighbor(cw(i));
544 i = pos->index(_v);
545 _ri = ccw(i);
546 }
547 return *this;
548 }
549
550 template < class Tds >
551 Triangulation_ds_edge_circulator_2<Tds>
552 Triangulation_ds_edge_circulator_2<Tds> ::
553 operator--(int)
554 {
555 Edge_circulator tmp(*this);
556 --(*this);
557 return tmp;
558 }
559
560 template < class Tds >
561 inline bool
562 Triangulation_ds_edge_circulator_2<Tds> ::
563 operator==(const Edge_circulator &vc) const
564 {
565 return (_v == vc._v) && (_ri == vc._ri) && (pos == vc.pos);
566 }
567
568 template < class Tds >
569 inline bool
570 Triangulation_ds_edge_circulator_2<Tds> ::
571 operator!=(const Edge_circulator &vc) const
572 {
573 return ! (*this == vc);
574 }
575
576 template < class Tds >
577 inline bool
578 Triangulation_ds_edge_circulator_2<Tds> ::
is_empty()579 is_empty() const
580 {
581 return (_v == Vertex_handle() || pos == Face_handle());
582 }
583
584 template < class Tds >
585 inline bool
586 Triangulation_ds_edge_circulator_2<Tds> ::
587 operator==(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const
588 {
589 //CGAL_triangulation_assertion( n == nullptr);
590 return (_v == Vertex_handle() || pos == Face_handle());
591 }
592
593 template < class Tds >
594 inline bool
595 Triangulation_ds_edge_circulator_2<Tds> ::
596 operator!=(std::nullptr_t /*CGAL_triangulation_assertion_code(n)*/) const
597 {
598 //CGAL_triangulation_assertion( n == nullptr);
599 return !(*this == nullptr);
600 }
601
602
603 } //namespace CGAL
604
605 #endif //CGAL_TRIANGULATION_DS_CIRCULATORS_2_H
606