From d53f5efb161d6b9820a9ac8938def3d4f4df3054 Mon Sep 17 00:00:00 2001 From: Andreas Fabri Date: Mon, 25 Jun 2012 08:40:03 +0000 Subject: [PATCH 02/10] Bug fix for the interpolation of the z-value in the projection traits class --- .../CGAL/internal/Projection_traits_3.h | 23 ++++++++++++------- 1 file changed, 15 insertions(+), 8 deletions(-) diff --git a/Kernel_23/include/CGAL/internal/Projection_traits_3.h b/Kernel_23/include/CGAL/internal/Projection_traits_3.h index 4d152acda3e..8aa46bca30b 100644 --- a/Kernel_23/include/CGAL/internal/Projection_traits_3.h +++ b/Kernel_23/include/CGAL/internal/Projection_traits_3.h @@ -225,6 +225,13 @@ public: return Point_2(x(p),y(p)); } + FT alpha(const Point_2& p, const Point_2& source, const Point_2& target) const + { + FT dx = target.x() - source.x(); + FT dy = target.y() - source.y(); + return (CGAL::abs(dx)>CGAL::abs(dy)) ? ( p.x()-source.x() ) / dx : (p.y()-source.y() ) / dy; + } + Object operator()(const Segment_3& s1, const Segment_3& s2) const { Point_2 s1_source = project(s1.source()); @@ -244,15 +251,15 @@ public: const Segment_2* si=CGAL::object_cast(&o); if (si==NULL) return Object(); FT src[3],tgt[3]; - tgt[dim] = src[dim] = FT(0); //the third coordinate is the midpoint between the points on s1 and s2 - - FT z1 = s1.source()[dim] + ( si->source().x()-s1_source.x() ) / (s1_target.x() - s1_source.x()) * ( s1.target()[dim] - s1.source()[dim] ); - FT z2 = s2.source()[dim] + ( si->source().x()-s2_source.x() ) / (s2_target.x() - s2_source.x()) * ( s2.target()[dim] - s2.source()[dim] ); + //the third coordinate is the midpoint between the points on s1 and s2 + FT z1 = s1.source()[dim] + ( alpha(si->source(), s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); + FT z2 = s2.source()[dim] + ( alpha(si->source(), s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); src[dim] = (z1+z2) / FT(2); - z1 = s1.source()[dim] + ( si->target().x()-s1_source.x() ) / (s1_target.x() - s1_source.x()) * ( s1.target()[dim] - s1.source()[dim] ); - z2 = s2.source()[dim] + ( si->target().x()-s2_source.x() ) / (s2_target.x() - s2_source.x()) * ( s2.target()[dim] - s2.source()[dim] ); + z1 = s1.source()[dim] + ( alpha(si->target(), s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); + z2 = s2.source()[dim] + ( alpha(si->target(), s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); + tgt[dim] = (z1+z2) / FT(2); @@ -264,8 +271,8 @@ public: } FT coords[3]; //compute the third coordinate of the projected intersection point onto 3D segments - FT z1 = s1.source()[dim] + ( pi->x()-s1_source.x() ) / (s1_target.x() - s1_source.x()) * ( s1.target()[dim] - s1.source()[dim] ); - FT z2 = s2.source()[dim] + ( pi->x()-s2_source.x() ) / (s2_target.x() - s2_source.x()) * ( s2.target()[dim] - s2.source()[dim] ); + FT z1 = s1.source()[dim] + ( alpha(*pi, s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); + FT z2 = s2.source()[dim] + ( alpha(*pi, s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); coords[dim] = (z1+z2) / FT(2); coords[Projector::x_index] = pi->x(); From 7cb640d05d2f52a9cdfa1771ab1a5b239a6fa9c2 Mon Sep 17 00:00:00 2001 From: Andreas Fabri Date: Mon, 25 Jun 2012 10:11:56 +0000 Subject: [PATCH 03/10] The Constraint_hierarchy_2 gets an additional LessXY_2 functor as template argument so that it no longer applies operator<(Point,Point) --- .../CGAL/Constrained_triangulation_plus_2.h | 2 +- .../include/CGAL/Constraint_hierarchy_2.h | 172 +++++++++--------- .../include/CGAL/_test_cls_hierarchy_2.h | 10 +- 3 files changed, 97 insertions(+), 87 deletions(-) diff --git a/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h b/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h index 21583c56d99..cfc2bb49c08 100644 --- a/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h +++ b/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h @@ -58,7 +58,7 @@ public: typedef typename Triangulation::List_vertices List_vertices; typedef typename Triangulation::List_constraints List_constraints; - typedef Constraint_hierarchy_2 Constraint_hierarchy; + typedef Constraint_hierarchy_2 Constraint_hierarchy; typedef Tag_true Constraint_hierarchy_tag; // for user interface with the constraint hierarchy diff --git a/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h b/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h index b57f5b105a7..5d6b676f08a 100644 --- a/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h +++ b/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h @@ -32,13 +32,13 @@ namespace CGAL { // T is expected to be Vertex_handle // Data is intended to store info on a Vertex -template + template class Constraint_hierarchy_2 { public: typedef std::pair H_edge; typedef T H_vertex; - typedef Constraint_hierarchy_2 Hierarchy; + typedef Constraint_hierarchy_2 Hierarchy; typedef std::pair H_constraint; typedef std::list H_vertex_list; typedef std::list H_constraint_list; @@ -47,9 +47,10 @@ public: struct Pair_compare { bool operator()(const H_edge& e1, const H_edge& e2) const { - if(e1.first->point() < e2.first->point()) { + LessXY less; + if(less(e1.first->point(), e2.first->point())) { return true; - } else if(e1.first->point() == e2.first->point() && + } else if((! less(e2.first->point(), e1.first->point())) && // !less(e1,e2) && !less(e2,e1) == equal e1.second->point() < e2.second->point()) { return true; } else { @@ -59,7 +60,7 @@ public: }; class H_context { - friend class Constraint_hierarchy_2; + friend class Constraint_hierarchy_2; private: H_vertex_list* enclosing; H_vertex_it pos; @@ -162,24 +163,24 @@ public: void print() const; }; -template -Constraint_hierarchy_2:: +template +Constraint_hierarchy_2:: Constraint_hierarchy_2(const Constraint_hierarchy_2& ch) { copy(ch); } -template -Constraint_hierarchy_2& -Constraint_hierarchy_2:: +template +Constraint_hierarchy_2& +Constraint_hierarchy_2:: operator=(const Constraint_hierarchy_2& ch){ copy(ch); return *this; } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: copy(const Constraint_hierarchy_2& ch1) { // create a identity transfer vertex map @@ -194,9 +195,9 @@ copy(const Constraint_hierarchy_2& ch1) copy(ch1, vmap); } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: copy(const Constraint_hierarchy_2& ch1, std::map& vmap) // copy with a tranfer vertex map { @@ -245,9 +246,9 @@ copy(const Constraint_hierarchy_2& ch1, std::map& vmap) return; } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: swap(Constraint_hierarchy_2& ch) { c_to_sc_map.swap(ch.c_to_sc_map); @@ -255,31 +256,31 @@ swap(Constraint_hierarchy_2& ch) vertex_map.swap(ch.vertex_map); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: is_constrained_vertex(T v) const { return( vertex_map.find(v) != vertex_map.end() ); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: is_constrained_edge(T va, T vb) const { return( c_to_sc_map.find(make_edge(va, vb)) != c_to_sc_map.end() ); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: is_subconstrained_edge(T va, T vb) const { return( sc_to_c_map.find(make_edge(va, vb)) != sc_to_c_map.end() ); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: vertices_in_constraint(H_constraint hc, H_vertex_it& v_first, H_vertex_it& v_past ) const @@ -291,8 +292,8 @@ vertices_in_constraint(H_constraint hc, return true; } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: enclosing_constraint(H_edge he, H_constraint& hc) const { H_context_iterator hcit, past; @@ -303,8 +304,8 @@ enclosing_constraint(H_edge he, H_constraint& hc) const -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: enclosing_constraint(T vaa, T vbb, T& va, T& vb) const { H_context_iterator hcit, past; @@ -315,8 +316,8 @@ enclosing_constraint(T vaa, T vbb, T& va, T& vb) const } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: enclosing_constraints(T vaa, T vbb , H_constraint_list& hcl) const { H_context_iterator hcit, past; @@ -328,9 +329,9 @@ enclosing_constraints(T vaa, T vbb , H_constraint_list& hcl) const return true; } -template -typename Constraint_hierarchy_2::H_context -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_context +Constraint_hierarchy_2:: context(T va, T vb) { H_context_iterator hcit, past; @@ -338,9 +339,9 @@ context(T va, T vb) return *hcit; } -template +template std::size_t -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: number_of_enclosing_constraints(T va, T vb) { H_context_list* hcl = get_contexts(va, vb); @@ -348,9 +349,9 @@ number_of_enclosing_constraints(T va, T vb) return hcl->size(); } -template -typename Constraint_hierarchy_2::H_context_iterator -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_context_iterator +Constraint_hierarchy_2:: contexts_begin(T va, T vb) { H_context_iterator first, last; @@ -358,9 +359,9 @@ contexts_begin(T va, T vb) return first; } -template -typename Constraint_hierarchy_2::H_context_iterator -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_context_iterator +Constraint_hierarchy_2:: contexts_end(T va, T vb) { H_context_iterator first, last; @@ -368,9 +369,9 @@ contexts_end(T va, T vb) return last; } -template -typename Constraint_hierarchy_2::H_vertex_it -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_vertex_it +Constraint_hierarchy_2:: vertices_in_constraint_begin(T va, T vb) { H_c_iterator cit = c_to_sc_map.find(make_edge(va,vb)); @@ -378,9 +379,9 @@ vertices_in_constraint_begin(T va, T vb) return cit->second->begin(); } -template -typename Constraint_hierarchy_2::H_vertex_it -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_vertex_it +Constraint_hierarchy_2:: vertices_in_constraint_end(T va, T vb) { H_c_iterator cit = c_to_sc_map.find(make_edge(va,vb)); @@ -393,8 +394,8 @@ vertices_in_constraint_end(T va, T vb) when a constraint is inserted, it is, at first, both a constraint and a subconstraint */ -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: insert_constraint(T va, T vb){ H_edge he = make_edge(va, vb); H_vertex_list* children = new H_vertex_list; @@ -427,9 +428,9 @@ insert_constraint(T va, T vb){ return false; //duplicate constraint - no insertion } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: remove_constraint(T va, T vb){ H_edge he = make_edge(va, vb); typename H_c_to_sc_map::iterator c_to_sc_it = c_to_sc_map.find(he); @@ -464,38 +465,38 @@ remove_constraint(T va, T vb){ } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: constrain_vertex(T v, Data data){ vertex_map.insert(std::make_pair(v,data)); } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: unconstrain_vertex(T v){ vertex_map.erase(v); } -template -Data Constraint_hierarchy_2:: +template +Data Constraint_hierarchy_2:: get_data(T v){ CGAL_precondition( is_constrained_vertex(v) ); return (*vertex_map.find(v)).second; } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: set_data(T v, Data data){ vertex_map.erase(v); vertex_map.insert(std::make_pair(v,data)); } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: clear() { H_c_iterator cit; @@ -516,8 +517,8 @@ clear() } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: next_along_sc(T va, T vb, T& w) const { // find the next vertex after vb along any enclosing constrained @@ -545,8 +546,8 @@ next_along_sc(T va, T vb, T& w) const Attention, le point v DOIT etre un point de Steiner, et les segments va,v et v,vb sont des sous contraintes. */ -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: remove_Steiner(T v, T va, T vb) { // remove a Steiner point @@ -577,16 +578,16 @@ remove_Steiner(T v, T va, T vb) same as add_Steiner precondition : va,vb est une souscontrainte. */ -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: split_constraint(T va, T vb, T vc){ add_Steiner(va, vb, vc); } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: add_Steiner(T va, T vb, T vc){ H_context_list* hcl = get_contexts(va, vb); CGAL_triangulation_assertion(hcl != NULL); @@ -635,19 +636,20 @@ add_Steiner(T va, T vb, T vc){ } -template +template inline -typename Constraint_hierarchy_2::H_edge -Constraint_hierarchy_2:: +typename Constraint_hierarchy_2::H_edge +Constraint_hierarchy_2:: make_edge(T va, T vb) const { - return (va->point()point()) ? H_edge(va,vb) : H_edge(vb,va); + LessXY less; + return less(va->point(), vb->point()) ? H_edge(va,vb) : H_edge(vb,va); } -template +template inline -typename Constraint_hierarchy_2::H_context_list* -Constraint_hierarchy_2:: +typename Constraint_hierarchy_2::H_context_list* +Constraint_hierarchy_2:: get_contexts(T va, T vb) const { H_sc_iterator sc_iter = sc_to_c_map.find(make_edge(va,vb)); @@ -656,10 +658,10 @@ get_contexts(T va, T vb) const return (*sc_iter).second; } -template +template inline bool -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: get_contexts(T va, T vb, H_context_iterator& ctxt, H_context_iterator& past) const @@ -674,19 +676,19 @@ get_contexts(T va, T vb, -template +template inline -typename Constraint_hierarchy_2::H_vertex_it -Constraint_hierarchy_2:: +typename Constraint_hierarchy_2::H_vertex_it +Constraint_hierarchy_2:: get_pos(T va, T vb) const //return pos in the first context { return (*sc_to_c_map.find(make_edge(va,vb))).second->begin().pos; } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: oriented_end(T va, T vb, T& vc) const { H_context_iterator ctxt, past; @@ -698,9 +700,9 @@ oriented_end(T va, T vb, T& vc) const } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: print() const { H_c_iterator hcit; diff --git a/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h b/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h index 7fc3279c2cb..62d4901d838 100644 --- a/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h +++ b/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h @@ -11,9 +11,17 @@ public: } }; +struct LessXY +{ + bool operator()(int i, int j) const + { + return i < j; + } +}; + typedef Vertex* Vh; typedef bool Data; -typedef CGAL::Constraint_hierarchy_2 Hierarchy; +typedef CGAL::Constraint_hierarchy_2 Hierarchy; typedef Hierarchy::H_constraint H_constraint; typedef Hierarchy::H_vertex H_vertex; typedef Hierarchy::H_vertex_it H_vertex_it; From 78a2d45173505aaafa0908575d3cf2f496f615c7 Mon Sep 17 00:00:00 2001 From: Andreas Fabri Date: Mon, 25 Jun 2012 11:45:50 +0000 Subject: [PATCH 04/10] Document bug fix in Projection_traits in changes.html --- Installation/changes.html | 1 + 1 file changed, 1 insertion(+) diff --git a/Installation/changes.html b/Installation/changes.html index a1661fb168f..20a08a6694e 100644 --- a/Installation/changes.html +++ b/Installation/changes.html @@ -158,6 +158,7 @@ the following has been changed since CGAL-4.0:

2D and 3D Geometry Kernel

  • Fix a bug in the Segment_3-Triangle_3 intersection function in the case the segment is collinear with a triangle edge..
  • +
  • Fix a bug in the Projection_traits_.._3class in the case a segment was parallel to the x-axis.

Algebraic Kernel

From b8c73f0ce55ca2bd39e5d42de60ab2098e980715 Mon Sep 17 00:00:00 2001 From: Laurent Rineau Date: Tue, 26 Jun 2012 16:01:48 +0000 Subject: [PATCH 05/10] Add a simple test for CGAL::Projection_traits_xz_3::Intersect_2 --- ...est_Projection_traits_xy_3_Intersect_2.cpp | 41 +++++++++++++++++++ 1 file changed, 41 insertions(+) create mode 100644 Kernel_23/test/Kernel_23/test_Projection_traits_xy_3_Intersect_2.cpp diff --git a/Kernel_23/test/Kernel_23/test_Projection_traits_xy_3_Intersect_2.cpp b/Kernel_23/test/Kernel_23/test_Projection_traits_xy_3_Intersect_2.cpp new file mode 100644 index 00000000000..cebb0fe760a --- /dev/null +++ b/Kernel_23/test/Kernel_23/test_Projection_traits_xy_3_Intersect_2.cpp @@ -0,0 +1,41 @@ +#include +#include + +typedef CGAL::Exact_predicates_inexact_constructions_kernel Epik; +typedef CGAL::Projection_traits_xy_3 K; + +typedef K::Orientation_2 Orientation_2; +typedef K::Intersect_2 Intersect_2; + +typedef K::Point_2 Point_2; +typedef K::Segment_2 Segment_2; +typedef CGAL::Object Object; + +int main() +{ + Point_2 p(0,0,0), q(1,1,1), r(1,0,0), s(0,1,1), t(0,1,0), u(0,1,-1); + Point_2 v(0.5, 0, 0), w(0.5,1,0); + + Segment_2 pq(p,q), rs(r,s), rt(r,t), ru(r,u), vw(v,w); + + Point_2 pqrs, pqrt, pqru, pqvw; + + Object o = Intersect_2()(pq,rs); + assert(assign(pqrs,o)); + assert(pqrs == Point_2(0.5, 0.5, 0.5)); + + o = Intersect_2()(pq,rt); + assert(assign(pqrt,o)); + assert(pqrt == Point_2(0.5, 0.5, 0.25)); + + o = Intersect_2()(pq,ru); + assert(assign(pqru,o)); + assert(pqru == Point_2(0.5, 0.5, 0)); + + o = Intersect_2()(pq,vw); + assert(assign(pqvw,o)); + assert(pqvw == Point_2(0.5, 0.5, 0.25)); + + std::cerr << "done" << std::endl; + return 0; +} From 49404f75f54a94ce3499bd8161a505b827335664 Mon Sep 17 00:00:00 2001 From: Laurent Rineau Date: Thu, 28 Jun 2012 09:16:23 +0000 Subject: [PATCH 06/10] Improved patch The Constraint_hierarchy is now templated by T, an anonymous type (that is a Vertex_handle when the constraint hierarchy is used in Ct_plus_2), and a Compare operator, that have a comparison member function: bool operator()(T, T); In Ct_plus_2, the Compare operator passed to the Constraint_hierarchy compares the vertices with a Less_xy_2, implemented by Less_x_2, and Less_y_2. The test test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h has been tweaked, to check that the type T passed in the hierarchy no longer needs to have a point() member function, as it was before May 2010 (when GF has determinized the Cdt_plus_2 using too simple patch). --- .../CGAL/Constrained_triangulation_plus_2.h | 36 +++- .../include/CGAL/Constraint_hierarchy_2.h | 194 ++++++++++-------- .../include/CGAL/_test_cls_hierarchy_2.h | 23 +-- 3 files changed, 142 insertions(+), 111 deletions(-) diff --git a/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h b/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h index cfc2bb49c08..8cd7dd7e82a 100644 --- a/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h +++ b/Triangulation_2/include/CGAL/Constrained_triangulation_plus_2.h @@ -27,6 +27,25 @@ namespace CGAL { +// Comparison functor that compares two Vertex_handle. +// Used as 'Compare' functor for the constraint hierarchy. +template < class Tr > +class Ctp2_vertex_handle_less_xy { + const Tr* tr_p; + +public: + Ctp2_vertex_handle_less_xy(const Tr* tr_p) : tr_p(tr_p) {} + + typedef typename Tr::Vertex_handle Vertex_handle; + + bool operator()(const Vertex_handle& va, + const Vertex_handle& vb) const + { + return tr_p->compare_xy(va->point(), vb->point()) == SMALLER; + } +}; // end class template Ctp2_vertex_handle_less_xy + + // Tr the base triangulation class // Tr has to be Constrained or Constrained_Delaunay @@ -58,8 +77,11 @@ public: typedef typename Triangulation::List_vertices List_vertices; typedef typename Triangulation::List_constraints List_constraints; - typedef Constraint_hierarchy_2 Constraint_hierarchy; - typedef Tag_true Constraint_hierarchy_tag; + typedef Ctp2_vertex_handle_less_xy Vh_less_xy; + typedef Constraint_hierarchy_2 Constraint_hierarchy; + typedef Tag_true Constraint_hierarchy_tag; // for user interface with the constraint hierarchy typedef typename Constraint_hierarchy::H_vertex_it @@ -88,10 +110,14 @@ protected: public: Constrained_triangulation_plus_2(const Geom_traits& gt=Geom_traits()) - : Triangulation(gt) { } + : Triangulation(gt) + , hierarchy(Vh_less_xy(this)) + { } Constrained_triangulation_plus_2(const Self& ctp) - : Triangulation() { copy_triangulation(ctp);} + : Triangulation() + , hierarchy(Vh_less_xy(this)) + { copy_triangulation(ctp);} virtual ~Constrained_triangulation_plus_2() {} @@ -100,6 +126,7 @@ public: Constrained_triangulation_plus_2(List_constraints& lc, const Geom_traits& gt=Geom_traits()) : Triangulation(gt) + , hierarchy(Vh_less_xy(this)) { typename List_constraints::iterator lcit=lc.begin(); for( ;lcit != lc.end(); lcit++) { @@ -113,6 +140,7 @@ public: InputIterator last, const Geom_traits& gt=Geom_traits() ) : Triangulation(gt) + , hierarchy(Vh_less_xy(this)) { while( first != last){ insert_constraint((*first).first, (*first).second); diff --git a/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h b/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h index 5d6b676f08a..a879093b4c3 100644 --- a/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h +++ b/Triangulation_2/include/CGAL/Constraint_hierarchy_2.h @@ -31,27 +31,34 @@ namespace CGAL { // T is expected to be Vertex_handle +// Compare is a comparison operator for type T // Data is intended to store info on a Vertex - template +template class Constraint_hierarchy_2 { public: typedef std::pair H_edge; typedef T H_vertex; - typedef Constraint_hierarchy_2 Hierarchy; + typedef Constraint_hierarchy_2 Hierarchy; typedef std::pair H_constraint; typedef std::list H_vertex_list; typedef std::list H_constraint_list; typedef typename std::list::iterator H_vertex_it; typedef typename std::list::iterator H_constraint_it; - struct Pair_compare { + class Pair_compare { + Compare comp; + + public: + Pair_compare(const Compare& comp) : comp(comp) {} + bool operator()(const H_edge& e1, const H_edge& e2) const { - LessXY less; - if(less(e1.first->point(), e2.first->point())) { + if(comp(e1.first, e2.first)) { return true; - } else if((! less(e2.first->point(), e1.first->point())) && // !less(e1,e2) && !less(e2,e1) == equal - e1.second->point() < e2.second->point()) { + } else if((! comp(e2.first, e1.first)) && // !less(e1,e2) && !less(e2,e1) == equal + comp(e1.second, e2.second)) { return true; } else { return false; @@ -60,7 +67,7 @@ public: }; class H_context { - friend class Constraint_hierarchy_2; + friend class Constraint_hierarchy_2; private: H_vertex_list* enclosing; H_vertex_it pos; @@ -86,6 +93,7 @@ public: typedef std::pair H_sc_value; private: + Compare comp; // data for the 1d hierarchy H_c_to_sc_map c_to_sc_map; H_sc_to_c_map sc_to_c_map; @@ -93,7 +101,11 @@ private: H_vertex_map vertex_map; public: - Constraint_hierarchy_2() { } + Constraint_hierarchy_2(const Compare& comp_ = Compare()) + : comp(comp_) + , c_to_sc_map(Pair_compare(comp)) + , sc_to_c_map(Pair_compare(comp)) + { } Constraint_hierarchy_2(const Constraint_hierarchy_2& ch); ~Constraint_hierarchy_2(){ clear();} void clear(); @@ -163,24 +175,27 @@ public: void print() const; }; -template -Constraint_hierarchy_2:: +template +Constraint_hierarchy_2:: Constraint_hierarchy_2(const Constraint_hierarchy_2& ch) + : comp(ch.comp) + , c_to_sc_map(Pair_compare(comp)) + , sc_to_c_map(Pair_compare(comp)) { copy(ch); } -template -Constraint_hierarchy_2& -Constraint_hierarchy_2:: +template +Constraint_hierarchy_2& +Constraint_hierarchy_2:: operator=(const Constraint_hierarchy_2& ch){ copy(ch); return *this; } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: copy(const Constraint_hierarchy_2& ch1) { // create a identity transfer vertex map @@ -195,9 +210,9 @@ copy(const Constraint_hierarchy_2& ch1) copy(ch1, vmap); } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: copy(const Constraint_hierarchy_2& ch1, std::map& vmap) // copy with a tranfer vertex map { @@ -246,9 +261,9 @@ copy(const Constraint_hierarchy_2& ch1, std::map& vmap) return; } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: swap(Constraint_hierarchy_2& ch) { c_to_sc_map.swap(ch.c_to_sc_map); @@ -256,31 +271,31 @@ swap(Constraint_hierarchy_2& ch) vertex_map.swap(ch.vertex_map); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: is_constrained_vertex(T v) const { return( vertex_map.find(v) != vertex_map.end() ); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: is_constrained_edge(T va, T vb) const { return( c_to_sc_map.find(make_edge(va, vb)) != c_to_sc_map.end() ); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: is_subconstrained_edge(T va, T vb) const { return( sc_to_c_map.find(make_edge(va, vb)) != sc_to_c_map.end() ); } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: vertices_in_constraint(H_constraint hc, H_vertex_it& v_first, H_vertex_it& v_past ) const @@ -292,8 +307,8 @@ vertices_in_constraint(H_constraint hc, return true; } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: enclosing_constraint(H_edge he, H_constraint& hc) const { H_context_iterator hcit, past; @@ -304,8 +319,8 @@ enclosing_constraint(H_edge he, H_constraint& hc) const -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: enclosing_constraint(T vaa, T vbb, T& va, T& vb) const { H_context_iterator hcit, past; @@ -316,8 +331,8 @@ enclosing_constraint(T vaa, T vbb, T& va, T& vb) const } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: enclosing_constraints(T vaa, T vbb , H_constraint_list& hcl) const { H_context_iterator hcit, past; @@ -329,9 +344,9 @@ enclosing_constraints(T vaa, T vbb , H_constraint_list& hcl) const return true; } -template -typename Constraint_hierarchy_2::H_context -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_context +Constraint_hierarchy_2:: context(T va, T vb) { H_context_iterator hcit, past; @@ -339,9 +354,9 @@ context(T va, T vb) return *hcit; } -template +template std::size_t -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: number_of_enclosing_constraints(T va, T vb) { H_context_list* hcl = get_contexts(va, vb); @@ -349,9 +364,9 @@ number_of_enclosing_constraints(T va, T vb) return hcl->size(); } -template -typename Constraint_hierarchy_2::H_context_iterator -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_context_iterator +Constraint_hierarchy_2:: contexts_begin(T va, T vb) { H_context_iterator first, last; @@ -359,9 +374,9 @@ contexts_begin(T va, T vb) return first; } -template -typename Constraint_hierarchy_2::H_context_iterator -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_context_iterator +Constraint_hierarchy_2:: contexts_end(T va, T vb) { H_context_iterator first, last; @@ -369,9 +384,9 @@ contexts_end(T va, T vb) return last; } -template -typename Constraint_hierarchy_2::H_vertex_it -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_vertex_it +Constraint_hierarchy_2:: vertices_in_constraint_begin(T va, T vb) { H_c_iterator cit = c_to_sc_map.find(make_edge(va,vb)); @@ -379,9 +394,9 @@ vertices_in_constraint_begin(T va, T vb) return cit->second->begin(); } -template -typename Constraint_hierarchy_2::H_vertex_it -Constraint_hierarchy_2:: +template +typename Constraint_hierarchy_2::H_vertex_it +Constraint_hierarchy_2:: vertices_in_constraint_end(T va, T vb) { H_c_iterator cit = c_to_sc_map.find(make_edge(va,vb)); @@ -394,8 +409,8 @@ vertices_in_constraint_end(T va, T vb) when a constraint is inserted, it is, at first, both a constraint and a subconstraint */ -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: insert_constraint(T va, T vb){ H_edge he = make_edge(va, vb); H_vertex_list* children = new H_vertex_list; @@ -428,9 +443,9 @@ insert_constraint(T va, T vb){ return false; //duplicate constraint - no insertion } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: remove_constraint(T va, T vb){ H_edge he = make_edge(va, vb); typename H_c_to_sc_map::iterator c_to_sc_it = c_to_sc_map.find(he); @@ -465,38 +480,38 @@ remove_constraint(T va, T vb){ } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: constrain_vertex(T v, Data data){ vertex_map.insert(std::make_pair(v,data)); } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: unconstrain_vertex(T v){ vertex_map.erase(v); } -template -Data Constraint_hierarchy_2:: +template +Data Constraint_hierarchy_2:: get_data(T v){ CGAL_precondition( is_constrained_vertex(v) ); return (*vertex_map.find(v)).second; } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: set_data(T v, Data data){ vertex_map.erase(v); vertex_map.insert(std::make_pair(v,data)); } -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: clear() { H_c_iterator cit; @@ -517,8 +532,8 @@ clear() } -template -bool Constraint_hierarchy_2:: +template +bool Constraint_hierarchy_2:: next_along_sc(T va, T vb, T& w) const { // find the next vertex after vb along any enclosing constrained @@ -546,8 +561,8 @@ next_along_sc(T va, T vb, T& w) const Attention, le point v DOIT etre un point de Steiner, et les segments va,v et v,vb sont des sous contraintes. */ -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: remove_Steiner(T v, T va, T vb) { // remove a Steiner point @@ -578,16 +593,16 @@ remove_Steiner(T v, T va, T vb) same as add_Steiner precondition : va,vb est une souscontrainte. */ -template -void Constraint_hierarchy_2:: +template +void Constraint_hierarchy_2:: split_constraint(T va, T vb, T vc){ add_Steiner(va, vb, vc); } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: add_Steiner(T va, T vb, T vc){ H_context_list* hcl = get_contexts(va, vb); CGAL_triangulation_assertion(hcl != NULL); @@ -636,20 +651,19 @@ add_Steiner(T va, T vb, T vc){ } -template +template inline -typename Constraint_hierarchy_2::H_edge -Constraint_hierarchy_2:: +typename Constraint_hierarchy_2::H_edge +Constraint_hierarchy_2:: make_edge(T va, T vb) const { - LessXY less; - return less(va->point(), vb->point()) ? H_edge(va,vb) : H_edge(vb,va); + return comp(va, vb) ? H_edge(va,vb) : H_edge(vb,va); } -template +template inline -typename Constraint_hierarchy_2::H_context_list* -Constraint_hierarchy_2:: +typename Constraint_hierarchy_2::H_context_list* +Constraint_hierarchy_2:: get_contexts(T va, T vb) const { H_sc_iterator sc_iter = sc_to_c_map.find(make_edge(va,vb)); @@ -658,10 +672,10 @@ get_contexts(T va, T vb) const return (*sc_iter).second; } -template +template inline bool -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: get_contexts(T va, T vb, H_context_iterator& ctxt, H_context_iterator& past) const @@ -676,19 +690,19 @@ get_contexts(T va, T vb, -template +template inline -typename Constraint_hierarchy_2::H_vertex_it -Constraint_hierarchy_2:: +typename Constraint_hierarchy_2::H_vertex_it +Constraint_hierarchy_2:: get_pos(T va, T vb) const //return pos in the first context { return (*sc_to_c_map.find(make_edge(va,vb))).second->begin().pos; } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: oriented_end(T va, T vb, T& vc) const { H_context_iterator ctxt, past; @@ -700,9 +714,9 @@ oriented_end(T va, T vb, T& vc) const } -template +template void -Constraint_hierarchy_2:: +Constraint_hierarchy_2:: print() const { H_c_iterator hcit; diff --git a/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h b/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h index 62d4901d838..cc4a946b13c 100644 --- a/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h +++ b/Triangulation_2/test/Triangulation_2/include/CGAL/_test_cls_hierarchy_2.h @@ -1,17 +1,6 @@ #include -class Vertex { - int i; -public: - int point() const { - return i; - } - Vertex(const int i) { - this->i = i; - } -}; - -struct LessXY +struct Less { bool operator()(int i, int j) const { @@ -19,9 +8,11 @@ struct LessXY } }; -typedef Vertex* Vh; +typedef int Vh; typedef bool Data; -typedef CGAL::Constraint_hierarchy_2 Hierarchy; +typedef CGAL::Constraint_hierarchy_2 Hierarchy; typedef Hierarchy::H_constraint H_constraint; typedef Hierarchy::H_vertex H_vertex; typedef Hierarchy::H_vertex_it H_vertex_it; @@ -37,7 +28,7 @@ void _test_cls_hierarchy_2() { Vh v[10]; - for(int i=0; i <10; i++) { v[i] = new Vertex(i);} + for(int i=0; i <10; i++) { v[i] = i;} Hierarchy h; h.insert_constraint(v[1],v[2]); @@ -143,8 +134,6 @@ _test_cls_hierarchy_2() h.remove_constraint(v[3],v[4]); // h.print(); - for(int i=0; i <10; i++) { delete v[i];} - return; } From 61ff95f149787bd6ce2e25508acb67a3f6703287 Mon Sep 17 00:00:00 2001 From: Laurent Rineau Date: Thu, 28 Jun 2012 09:56:06 +0000 Subject: [PATCH 07/10] Add a test of CDT_plus_2 with the Projection_traits_xy_3 --- ...CDT_plus_2_with_Projection_traits_xy_3.cpp | 49 +++++++++++++++++++ 1 file changed, 49 insertions(+) create mode 100644 Triangulation_2/test/Triangulation_2/test_CDT_plus_2_with_Projection_traits_xy_3.cpp diff --git a/Triangulation_2/test/Triangulation_2/test_CDT_plus_2_with_Projection_traits_xy_3.cpp b/Triangulation_2/test/Triangulation_2/test_CDT_plus_2_with_Projection_traits_xy_3.cpp new file mode 100644 index 00000000000..e9eaf6bc25b --- /dev/null +++ b/Triangulation_2/test/Triangulation_2/test_CDT_plus_2_with_Projection_traits_xy_3.cpp @@ -0,0 +1,49 @@ +#include +#include +#include +#include +#include + +typedef CGAL::Exact_predicates_inexact_constructions_kernel EIK; +typedef CGAL::Projection_traits_xy_3 K; +typedef CGAL::Triangulation_vertex_base_2 Vb; +typedef CGAL::Constrained_triangulation_face_base_2 Fb; +typedef CGAL::Triangulation_data_structure_2 TDS; +typedef CGAL::Exact_predicates_tag Itag; +typedef CGAL::Constrained_Delaunay_triangulation_2 CDTi; +typedef CGAL::Constrained_triangulation_plus_2 CDT; + +typedef CDT::Point Point; +typedef CDT::Vertex_handle Vertex_handle; + +int main() +{ + CDT cdt; + + std::vector > constraints; + std::vector > segments; + + segments.push_back(std::make_pair(Point(212.69651243, 168.58113131, 0), + Point(212.69487813, 169.35340097, 0))); + segments.push_back(std::make_pair(Point( 211.49303932, 161.00812931, 0), + Point(211.49303932, 172.95244391, 0))); + segments.push_back(std::make_pair(Point( 210.13500000, 169.20200000, 0), + Point(232.65300000, 167.91200000, 0))); + segments.push_back(std::make_pair(Point( 210.13500000, 169.20200000, 0), + Point(232.69100000, 189.32500000, 0))); + + Point p, q; + for(unsigned int i=0;i< segments.size(); i++){ + p = segments[i].first; + q = segments[i].second; + Vertex_handle v = cdt.insert(p); + Vertex_handle w = cdt.insert(q); + constraints.push_back(std::make_pair(v,w)); + } + for(unsigned int i=0; i < constraints.size(); ++i){ + std::cerr << i << std::endl; + cdt.insert_constraint(constraints[i].first, constraints[i].second); + } + std::cerr << "done" << std::endl; + return 0; +} From 982a4ec9d8f5a5034506ac262f29e42acfd5e86b Mon Sep 17 00:00:00 2001 From: Laurent Rineau Date: Mon, 2 Jul 2012 16:15:02 +0000 Subject: [PATCH 08/10] Announcement for CGAL-4.0.1 Add remove the fake announcement file for CGAL-3.8.1 (it has never been released). --- .gitattributes | 2 +- .../public_release/announcement/CGAL-3.8.1 | 10 --- .../public_release/announcement/CGAL-4.0.1 | 65 +++++++++++++++++++ 3 files changed, 66 insertions(+), 11 deletions(-) delete mode 100644 Maintenance/public_release/announcement/CGAL-3.8.1 create mode 100644 Maintenance/public_release/announcement/CGAL-4.0.1 diff --git a/.gitattributes b/.gitattributes index 9537bc2f7f0..71b54784a20 100644 --- a/.gitattributes +++ b/.gitattributes @@ -2195,11 +2195,11 @@ Maintenance/public_release/announcement/CGAL-3.7 -text Maintenance/public_release/announcement/CGAL-3.7-beta1 -text Maintenance/public_release/announcement/CGAL-3.8 -text Maintenance/public_release/announcement/CGAL-3.8-beta -text -Maintenance/public_release/announcement/CGAL-3.8.1 -text Maintenance/public_release/announcement/CGAL-3.9 -text Maintenance/public_release/announcement/CGAL-3.9-beta1 -text Maintenance/public_release/announcement/CGAL-4.0 -text Maintenance/public_release/announcement/CGAL-4.0-beta1 -text +Maintenance/public_release/announcement/CGAL-4.0.1 -text Maintenance/public_release/scripts/precompiled_demos_zips -text Maintenance/public_release/scripts/prepare_release -text Maintenance/release_building/BUGFIX_NUMBER -text diff --git a/Maintenance/public_release/announcement/CGAL-3.8.1 b/Maintenance/public_release/announcement/CGAL-3.8.1 deleted file mode 100644 index 98be3611722..00000000000 --- a/Maintenance/public_release/announcement/CGAL-3.8.1 +++ /dev/null @@ -1,10 +0,0 @@ -Subject: CGAL 3.8.1 Released, Computational Geometry Algorithms Library -Body: - -The CGAL Open Source Project is pleased to announce the release 3.8.1 of -CGAL, the Computational Geometry Algorithms Library. - -Version 3.8.1 is a bug-fix release for version 3.8. No new feature has -been added in 3.8.1. The following corrections have been made: - -[...] diff --git a/Maintenance/public_release/announcement/CGAL-4.0.1 b/Maintenance/public_release/announcement/CGAL-4.0.1 new file mode 100644 index 00000000000..aec806cf665 --- /dev/null +++ b/Maintenance/public_release/announcement/CGAL-4.0.1 @@ -0,0 +1,65 @@ +Subject: CGAL 4.0.1 Released, Computational Geometry Algorithms Library +Body: + +The CGAL Open Source Project is pleased to announce the release 4.0.1 +of CGAL, the Computational Geometry Algorithms Library. + + +Version 4.0.1 is a bug-fix release for version 4.0. Apart various minor +fixes in the documentation, the following has been changed since CGAL-4.0: + + +* 2D Voronoi Diagram Adaptor (re-added) + + - The package 2D Voronoi Diagram Adaptor was temporarily removed from the + CGAL distribution because of license issues. That package is now back into + CGAL. + + +* 2D and 3D Geometry Kernel + + - Fix a bug in the Segment_3-Triangle_3 intersection function in the case the + segment is collinear with a triangle edge.. + + +* Algebraic Kernel + + - Avoids linking error "duplicate symbols" when two compilation units using + the algebraic kernel are linked. + + +* 2D Mesh Generation + + - Fix a compilation error in the header + when g++ version 4.7 is used. + + +* Surface Mesh Generation and 3D Mesh Generation + + - Fix an important bug in the CGAL_ImageIO library, that could lead to wrong + result when meshing from a 3D image. + + - Fix the compilation of the demo in demo/Surface_mesher, when Boost version + 1.48 or 1.49 is used. + + +* 3D Boolean Operations on Nef Polygons Embedded on the Sphere + + - Fix a memory leak due to the usage of an internal mechanism that has been + replaced by boost::any. This also influences the packages 2D Boolean + Operations on Nef Polygons, 3D Boolean Operations on Nef Polyhedra, Convex + Decomposition of Polyhedra, and 3D Minkowski Sum of Polyhedra. + + +* Surface Mesh Parameterization + + - Fixed a memory leak. + + +* 2D Arrangement + + - Fixed several memory leaks. + + +For further information and for downloading the library and its +documentation, please visit the CGAL web site: http://www.cgal.org/ From 14106d673fb9bb585e889ba5cdc1159fc3506f89 Mon Sep 17 00:00:00 2001 From: Laurent Rineau Date: Mon, 2 Jul 2012 16:31:33 +0000 Subject: [PATCH 09/10] Revert last commit. Wrong branch. --- .gitattributes | 2 +- .../public_release/announcement/CGAL-3.8.1 | 10 +++ .../public_release/announcement/CGAL-4.0.1 | 65 ------------------- 3 files changed, 11 insertions(+), 66 deletions(-) create mode 100644 Maintenance/public_release/announcement/CGAL-3.8.1 delete mode 100644 Maintenance/public_release/announcement/CGAL-4.0.1 diff --git a/.gitattributes b/.gitattributes index 71b54784a20..9537bc2f7f0 100644 --- a/.gitattributes +++ b/.gitattributes @@ -2195,11 +2195,11 @@ Maintenance/public_release/announcement/CGAL-3.7 -text Maintenance/public_release/announcement/CGAL-3.7-beta1 -text Maintenance/public_release/announcement/CGAL-3.8 -text Maintenance/public_release/announcement/CGAL-3.8-beta -text +Maintenance/public_release/announcement/CGAL-3.8.1 -text Maintenance/public_release/announcement/CGAL-3.9 -text Maintenance/public_release/announcement/CGAL-3.9-beta1 -text Maintenance/public_release/announcement/CGAL-4.0 -text Maintenance/public_release/announcement/CGAL-4.0-beta1 -text -Maintenance/public_release/announcement/CGAL-4.0.1 -text Maintenance/public_release/scripts/precompiled_demos_zips -text Maintenance/public_release/scripts/prepare_release -text Maintenance/release_building/BUGFIX_NUMBER -text diff --git a/Maintenance/public_release/announcement/CGAL-3.8.1 b/Maintenance/public_release/announcement/CGAL-3.8.1 new file mode 100644 index 00000000000..98be3611722 --- /dev/null +++ b/Maintenance/public_release/announcement/CGAL-3.8.1 @@ -0,0 +1,10 @@ +Subject: CGAL 3.8.1 Released, Computational Geometry Algorithms Library +Body: + +The CGAL Open Source Project is pleased to announce the release 3.8.1 of +CGAL, the Computational Geometry Algorithms Library. + +Version 3.8.1 is a bug-fix release for version 3.8. No new feature has +been added in 3.8.1. The following corrections have been made: + +[...] diff --git a/Maintenance/public_release/announcement/CGAL-4.0.1 b/Maintenance/public_release/announcement/CGAL-4.0.1 deleted file mode 100644 index aec806cf665..00000000000 --- a/Maintenance/public_release/announcement/CGAL-4.0.1 +++ /dev/null @@ -1,65 +0,0 @@ -Subject: CGAL 4.0.1 Released, Computational Geometry Algorithms Library -Body: - -The CGAL Open Source Project is pleased to announce the release 4.0.1 -of CGAL, the Computational Geometry Algorithms Library. - - -Version 4.0.1 is a bug-fix release for version 4.0. Apart various minor -fixes in the documentation, the following has been changed since CGAL-4.0: - - -* 2D Voronoi Diagram Adaptor (re-added) - - - The package 2D Voronoi Diagram Adaptor was temporarily removed from the - CGAL distribution because of license issues. That package is now back into - CGAL. - - -* 2D and 3D Geometry Kernel - - - Fix a bug in the Segment_3-Triangle_3 intersection function in the case the - segment is collinear with a triangle edge.. - - -* Algebraic Kernel - - - Avoids linking error "duplicate symbols" when two compilation units using - the algebraic kernel are linked. - - -* 2D Mesh Generation - - - Fix a compilation error in the header - when g++ version 4.7 is used. - - -* Surface Mesh Generation and 3D Mesh Generation - - - Fix an important bug in the CGAL_ImageIO library, that could lead to wrong - result when meshing from a 3D image. - - - Fix the compilation of the demo in demo/Surface_mesher, when Boost version - 1.48 or 1.49 is used. - - -* 3D Boolean Operations on Nef Polygons Embedded on the Sphere - - - Fix a memory leak due to the usage of an internal mechanism that has been - replaced by boost::any. This also influences the packages 2D Boolean - Operations on Nef Polygons, 3D Boolean Operations on Nef Polyhedra, Convex - Decomposition of Polyhedra, and 3D Minkowski Sum of Polyhedra. - - -* Surface Mesh Parameterization - - - Fixed a memory leak. - - -* 2D Arrangement - - - Fixed several memory leaks. - - -For further information and for downloading the library and its -documentation, please visit the CGAL web site: http://www.cgal.org/ From e654f364455c1a22f7ca8fde2a7fed774162a943 Mon Sep 17 00:00:00 2001 From: Laurent Rineau Date: Fri, 2 Nov 2012 08:59:25 +0000 Subject: [PATCH 10/10] Do not recode the file . It is a dos-eol-style file. --- .../CGAL/internal/Projection_traits_3.h | 1169 ++++++++--------- 1 file changed, 584 insertions(+), 585 deletions(-) diff --git a/Kernel_23/include/CGAL/internal/Projection_traits_3.h b/Kernel_23/include/CGAL/internal/Projection_traits_3.h index 6d87c51daef..bc5c563733b 100644 --- a/Kernel_23/include/CGAL/internal/Projection_traits_3.h +++ b/Kernel_23/include/CGAL/internal/Projection_traits_3.h @@ -1,586 +1,585 @@ -<<<<<<< variant A -// Copyright (c) 1997-2010 INRIA Sophia-Antipolis (France). -// All rights reserved. -// -// This file is part of CGAL (www.cgal.org); you can redistribute it and/or -// modify it under the terms of the GNU Lesser General Public License as -// published by the Free Software Foundation; either version 3 of the License, -// or (at your option) any later version. -// -// Licensees holding a valid commercial license may use this file in -// accordance with the commercial license agreement provided with the software. -// -// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE -// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. -// -// $URL$ -// $Id$ -// -// -// Author(s) : Mariette Yvinec, Sebastien Loriot - -#ifndef CGAL_INTERNAL_PROJECTION_TRAITS_3_H -#define CGAL_INTERNAL_PROJECTION_TRAITS_3_H - -#include - -#include -#include -#include - -#include - -namespace CGAL { - -namespace internal { - -//project Point_3 along coordinate dim -template -struct Projector; - -//project onto yz -template -struct Projector -{ - typedef typename R::Less_y_3 Less_x_2; - typedef typename R::Less_z_3 Less_y_2; - typedef typename R::Compare_y_3 Compare_x_2; - typedef typename R::Compare_z_3 Compare_y_2; - typedef typename R::Equal_y_3 Equal_x_2; - typedef typename R::Equal_z_3 Equal_y_2; - - static typename R::FT x(const typename R::Point_3& p) {return p.y();} - static typename R::FT y(const typename R::Point_3& p) {return p.z();} - static const int x_index=1; - static const int y_index=2; -}; -//project onto xz -template -struct Projector -{ - typedef typename R::Less_x_3 Less_x_2; - typedef typename R::Less_z_3 Less_y_2; - typedef typename R::Compare_x_3 Compare_x_2; - typedef typename R::Compare_z_3 Compare_y_2; - typedef typename R::Equal_x_3 Equal_x_2; - typedef typename R::Equal_z_3 Equal_y_2; - static typename R::FT x(const typename R::Point_3& p) {return p.x();} - static typename R::FT y(const typename R::Point_3& p) {return p.z();} - static const int x_index=0; - static const int y_index=2; -}; - -//project onto xy -template -struct Projector -{ - typedef typename R::Less_x_3 Less_x_2; - typedef typename R::Less_y_3 Less_y_2; - typedef typename R::Compare_x_3 Compare_x_2; - typedef typename R::Compare_y_3 Compare_y_2; - typedef typename R::Equal_x_3 Equal_x_2; - typedef typename R::Equal_y_3 Equal_y_2; - static typename R::FT x(const typename R::Point_3& p) {return p.x();} - static typename R::FT y(const typename R::Point_3& p) {return p.y();} - static const int x_index=0; - static const int y_index=1; -}; - - - -template -class Orientation_projected_3 -{ -public: - typedef typename R::Point_3 Point; - typename R::FT x(const Point &p) const { return Projector::x(p); } - typename R::FT y(const Point &p) const { return Projector::y(p); } - - typename R::Point_2 project(const Point& p) const - { - return typename R::Point_2(x(p),y(p)); - } - - CGAL::Orientation operator()(const Point& p, - const Point& q, - const Point& r) const - { - return CGAL::orientation(project(p), project(q), project(r)); - } -}; - -template -class Side_of_oriented_circle_projected_3 -{ -public: - typedef typename R::Point_3 Point; - typename R::FT x(const Point &p) const { return Projector::x(p); } - typename R::FT y(const Point &p) const { return Projector::y(p); } - - - typename R::Point_2 project(const Point& p) const - { - return typename R::Point_2(x(p),y(p)); - } - CGAL::Oriented_side operator() (const Point &p, - const Point &q, - const Point &r, - const Point &s) const - { - return CGAL::side_of_oriented_circle(project(p),project(q),project(r),project(s) ); - } -}; - -template -class Side_of_bounded_circle_projected_3 -{ -public: - typedef typename R::Point_3 Point; - typename R::FT x(const Point &p) const { return Projector::x(p); } - typename R::FT y(const Point &p) const { return Projector::y(p); } - - - typename R::Point_2 project(const Point& p) const - { - return typename R::Point_2(x(p),y(p)); - } - CGAL::Bounded_side operator() (const Point &p, - const Point &q, - const Point &r, - const Point &s) const - { - return CGAL::side_of_bounded_circle(project(p),project(q),project(r),project(s) ); - } - - CGAL::Bounded_side operator() (const Point &p, - const Point &q, - const Point &r) const - { - return CGAL::side_of_bounded_circle(project(p),project(q),project(r)); - } -}; - -template -class Compare_distance_projected_3 -{ -public: - typedef typename R::Point_3 Point_3; - typedef typename R::Point_2 Point_2; - typedef typename R::FT RT; - typename R::FT x(const Point_3 &p) const { return Projector::x(p); } - typename R::FT y(const Point_3 &p) const { return Projector::y(p); } - - Point_2 project(const Point_3& p) const - { - return Point_2(x(p),y(p)); - } - - Comparison_result operator()(const Point_3& p,const Point_3& q,const Point_3& r) const - { - Point_2 p2 = project(p); - Point_2 q2 = project(q); - Point_2 r2 = project(r); - return compare_distance_to_point(p2,q2,r2); - } -}; - -template -class Squared_distance_projected_3 -{ -public: - typedef typename R::Point_3 Point_3; - typedef typename R::Point_2 Point_2; - typedef typename R::Line_3 Line_3; - typedef typename R::Line_2 Line_2; - typedef typename R::FT RT; - typename R::FT x(const Point_3 &p) const { return Projector::x(p); } - typename R::FT y(const Point_3 &p) const { return Projector::y(p); } - - Point_2 project(const Point_3& p) const - { - return Point_2(x(p),y(p)); - } - - RT operator()(const Point_3& p, const Point_3& q) const - { - Point_2 p2(project(p)); - Point_2 q2(project(q)); - return squared_distance(p2, q2); - } - - RT operator()(const Line_3& l, const Point_3& p) const - { - Point_2 p2(project(p)); - Line_2 l2(project(l.point(0)), project(l.point(1))); - return squared_distance(p2, l2); - } -}; - -template -class Intersect_projected_3 -{ -public: - typedef typename R::Point_3 Point_3; - typedef typename R::Segment_3 Segment_3; - typedef typename R::Point_2 Point_2; - typedef typename R::Vector_2 Vector_2; - typedef typename R::Segment_2 Segment_2; - typedef typename R::FT FT; - - typename R::FT x(const Point_3 &p) const { return Projector::x(p); } - typename R::FT y(const Point_3 &p) const { return Projector::y(p); } - - Point_2 project(const Point_3& p) const - { - return Point_2(x(p),y(p)); - } - - FT alpha(const Point_2& p, const Point_2& source, const Point_2& target) const - { - FT dx = target.x() - source.x(); - FT dy = target.y() - source.y(); - return (CGAL::abs(dx)>CGAL::abs(dy)) ? ( p.x()-source.x() ) / dx : (p.y()-source.y() ) / dy; - } - - Object operator()(const Segment_3& s1, const Segment_3& s2) const - { - Point_2 s1_source = project(s1.source()); - Point_2 s1_target = project(s1.target()); - Point_2 s2_source = project(s2.source()); - Point_2 s2_target = project(s2.target()); - Segment_2 s1_2(s1_source, s1_target); - Segment_2 s2_2(s2_source, s2_target); - CGAL_precondition(!s1_2.is_degenerate()); - CGAL_precondition(!s2_2.is_degenerate()); - - //compute intersection points in projected plane - //We know that none of the segment is degenerate - Object o = intersection(s1_2,s2_2); - const Point_2* pi=CGAL::object_cast(&o); - if (pi==NULL) { //case of segment or empty - const Segment_2* si=CGAL::object_cast(&o); - if (si==NULL) return Object(); - FT src[3],tgt[3]; - //the third coordinate is the midpoint between the points on s1 and s2 - FT z1 = s1.source()[dim] + ( alpha(si->source(), s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); - FT z2 = s2.source()[dim] + ( alpha(si->source(), s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); - src[dim] = (z1+z2) / FT(2); - - - z1 = s1.source()[dim] + ( alpha(si->target(), s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); - z2 = s2.source()[dim] + ( alpha(si->target(), s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); - - tgt[dim] = (z1+z2) / FT(2); - - - src[Projector::x_index] = si->source().x(); - src[Projector::y_index] = si->source().y(); - tgt[Projector::x_index] = si->target().x(); - tgt[Projector::y_index] = si->target().y(); - return make_object( Segment_3( Point_3(src[0],src[1],src[2]),Point_3(tgt[0],tgt[1],tgt[2]) ) ); - } - FT coords[3]; - //compute the third coordinate of the projected intersection point onto 3D segments - FT z1 = s1.source()[dim] + ( alpha(*pi, s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); - FT z2 = s2.source()[dim] + ( alpha(*pi, s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); - - coords[dim] = (z1+z2) / FT(2); - coords[Projector::x_index] = pi->x(); - coords[Projector::y_index] = pi->y(); - - Point_3 res(coords[0],coords[1],coords[2]); - CGAL_assertion(x(res)==pi->x() && y(res)==pi->y()); - return make_object(res); - } -}; - -template -class Circumcenter_center_projected -{ - typedef typename R::Point_3 Point_3; - typedef typename R::Point_2 Point_2; - - typename R::FT x(const Point_3 &p) const { return Projector::x(p); } - typename R::FT y(const Point_3 &p) const { return Projector::y(p); } - - Point_2 project(const Point_3& p) const - { - return Point_2(x(p),y(p)); - } - - Point_3 embed (const Point_2& p) const - { - typename R::FT coords[3]; - coords[Projector::x_index]=p.x(); - coords[Projector::y_index]=p.y(); - coords[dim]=typename R::FT(0); - return Point_3(coords[0],coords[1],coords[2]); - } - -public: - Point_3 operator() (const Point_3& p1,const Point_3& p2) const - { - return embed( circumcenter(project(p1),project(p2)) ); - } - - Point_3 operator() (const Point_3& p1,const Point_3& p2,const Point_3& p3) const - { - return embed( circumcenter(project(p1),project(p2),project(p3)) ); - } -}; - -template -class Compute_area_projected -{ - typedef typename R::Point_3 Point_3; - typedef typename R::Point_2 Point_2; - - typename R::FT x(const Point_3 &p) const { return Projector::x(p); } - typename R::FT y(const Point_3 &p) const { return Projector::y(p); } - - Point_2 project(const Point_3& p) const - { - return Point_2(x(p),y(p)); - } - - -public: - typename R::FT operator() (const Point_3& p1,const Point_3& p2,const Point_3& p3) const - { - return R().compute_area_2_object() ( project(p1),project(p2),project(p3) ); - } -}; - -template -class Compute_squared_radius_projected -{ - typedef typename R::Point_3 Point_3; - typedef typename R::Point_2 Point_2; - - typename R::FT x(const Point_3 &p) const { return Projector::x(p); } - typename R::FT y(const Point_3 &p) const { return Projector::y(p); } - - Point_2 project(const Point_3& p) const - { - return Point_2(x(p),y(p)); - } - - -public: - typename R::FT operator() (const Point_3& p1,const Point_3& p2,const Point_3& p3) const - { - return R().compute_squared_radius_2_object() ( project(p1),project(p2),project(p3) ); - } - typename R::FT operator() (const Point_3& p1,const Point_3& p2) const - { - return R().compute_squared_radius_2_object() ( project(p1),project(p2) ); - } - - typename R::FT operator() (const Point_3& p1) const - { - return R().compute_squared_radius_2_object() ( project(p1) ); - } -}; - -template < class R, int dim > -class Projection_traits_3 { -public: - typedef Projection_traits_3 Traits; - typedef R Rp; - typedef typename R::FT FT; - typedef typename Rp::Point_3 Point_2; - typedef typename Rp::Segment_3 Segment_2; - typedef typename Rp::Vector_3 Vector_2; - typedef typename Rp::Triangle_3 Triangle_2; - typedef typename Rp::Line_3 Line_2; - - typedef typename Projector::Less_x_2 Less_x_2; - typedef typename Projector::Less_y_2 Less_y_2; - typedef typename Projector::Compare_x_2 Compare_x_2; - typedef typename Projector::Compare_y_2 Compare_y_2; - typedef Orientation_projected_3 Orientation_2; - typedef typename Rp::Angle_3 Angle_2; - typedef Side_of_oriented_circle_projected_3 Side_of_oriented_circle_2; - typedef Side_of_bounded_circle_projected_3 Side_of_bounded_circle_2; - typedef Compare_distance_projected_3 Compare_distance_2; - typedef Squared_distance_projected_3 Compute_squared_distance_2; - typedef Intersect_projected_3 Intersect_2; - typedef Compute_squared_radius_projected Compute_squared_radius_2; - typedef typename Rp::Construct_segment_3 Construct_segment_2; - typedef typename Rp::Construct_translated_point_3 Construct_translated_point_2; - typedef typename Rp::Construct_midpoint_3 Construct_midpoint_2; - typedef typename Rp::Construct_vector_3 Construct_vector_2; - typedef typename Rp::Construct_scaled_vector_3 Construct_scaled_vector_2; - typedef typename Rp::Construct_triangle_3 Construct_triangle_2; - typedef typename Rp::Construct_line_3 Construct_line_2; - - struct Less_xy_2 { - typedef bool result_type; - bool operator()(const Point_2& p, const Point_2& q) const - { - Compare_x_2 cx; - Comparison_result crx = cx(p,q); - if(crx == SMALLER){ return true;} - if(crx == LARGER){return false;} - Less_y_2 ly; - return ly(p,q); - } - }; - - - struct Less_yx_2 { - typedef bool result_type; - bool operator()(const Point_2& p, const Point_2& q) const - { - Compare_y_2 cy; - Comparison_result cry = cy(p,q); - if(cry == SMALLER){ return true;} - if(cry == LARGER){return false;} - Less_x_2 lx; - return lx(p,q); - } - }; - - struct Equal_2 { - typedef bool result_type; - bool operator()(const Point_2& p, const Point_2& q) const - { - - Equal_x_2 eqx; - Equal_y_2 eqy; - return eqx(p,q) & eqy(p,q); - } - }; - - struct Left_turn_2 { - typedef bool result_type; - bool operator()(const Point_2& p, const Point_2& q, const Point_2& r) const - { - - Orientation_2 ori; - return ori(p,q,r) == LEFT_TURN; - } - }; - - //for natural_neighbor_coordinates_2 - typedef typename Projector::Equal_x_2 Equal_x_2; - typedef typename Projector::Equal_y_2 Equal_y_2; - typedef Circumcenter_center_projected Construct_circumcenter_2; - typedef Compute_area_projected Compute_area_2; - Construct_circumcenter_2 construct_circumcenter_2_object () const {return Construct_circumcenter_2();} - Compute_area_2 compute_area_2_object () const {return Compute_area_2();} - - - // for compatibility with previous versions - typedef Point_2 Point; - typedef Segment_2 Segment; - typedef Triangle_2 Triangle; - - Projection_traits_3(){} - Projection_traits_3( - const Projection_traits_3&){} - Projection_traits_3 &operator=( - const Projection_traits_3&){return *this;} - - typename Rp::FT x(const Point_2 &p) const { return Projector::x(p); } - typename Rp::FT y(const Point_2 &p) const { return Projector::y(p); } - - - Equal_2 - equal_2_object() const - { return Equal_2();} - - Left_turn_2 - left_turn_2_object() const - { return Left_turn_2();} - - Less_x_2 - less_x_2_object() const - { return Less_x_2();} - - Less_xy_2 - less_xy_2_object() const - { return Less_xy_2();} - - Less_yx_2 - less_yx_2_object() const - { return Less_yx_2();} - - Less_y_2 - less_y_2_object() const - { return Less_y_2();} - Compare_x_2 - compare_x_2_object() const - { return Compare_x_2();} - Angle_2 - angle_2_object() const { - return Angle_2(); - } - - Compare_y_2 - compare_y_2_object() const - { return Compare_y_2();} - - Orientation_2 - orientation_2_object() const - { return Orientation_2();} - - Side_of_oriented_circle_2 - side_of_oriented_circle_2_object() const - {return Side_of_oriented_circle_2();} - - Side_of_bounded_circle_2 - side_of_bounded_circle_2_object() const - {return Side_of_bounded_circle_2();} - - Compare_distance_2 - compare_distance_2_object() const - { - return Compare_distance_2(); - } - - Compute_squared_distance_2 - compute_squared_distance_2_object () const - { - return Compute_squared_distance_2(); - } - - Compute_squared_radius_2 - compute_squared_radius_2_object () const - { - return Compute_squared_radius_2(); - } - - Intersect_2 - intersect_2_object () const - { - return Intersect_2(); - } - - Construct_segment_2 construct_segment_2_object() const - {return Construct_segment_2();} - - Construct_translated_point_2 construct_translated_point_2_object() const - {return Construct_translated_point_2();} - - Construct_midpoint_2 construct_midpoint_2_object() const - {return Construct_midpoint_2();} - - Construct_vector_2 construct_vector_2_object() const - {return Construct_vector_2();} - - Construct_scaled_vector_2 construct_scaled_vector_2_object() const - {return Construct_scaled_vector_2();} - - Construct_triangle_2 construct_triangle_2_object() const - {return Construct_triangle_2();} - - Construct_line_2 construct_line_2_object() const - {return Construct_line_2();} - -}; - - -} } //namespace CGAL::internal - +// Copyright (c) 1997-2010 INRIA Sophia-Antipolis (France). +// All rights reserved. +// +// This file is part of CGAL (www.cgal.org); you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public License as +// published by the Free Software Foundation; either version 3 of the License, +// or (at your option) any later version. +// +// Licensees holding a valid commercial license may use this file in +// accordance with the commercial license agreement provided with the software. +// +// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE +// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. +// +// $URL$ +// $Id$ +// +// +// Author(s) : Mariette Yvinec, Sebastien Loriot + +#ifndef CGAL_INTERNAL_PROJECTION_TRAITS_3_H +#define CGAL_INTERNAL_PROJECTION_TRAITS_3_H + +#include + +#include +#include +#include + +#include + +namespace CGAL { + +namespace internal { + +//project Point_3 along coordinate dim +template +struct Projector; + +//project onto yz +template +struct Projector +{ + typedef typename R::Less_y_3 Less_x_2; + typedef typename R::Less_z_3 Less_y_2; + typedef typename R::Compare_y_3 Compare_x_2; + typedef typename R::Compare_z_3 Compare_y_2; + typedef typename R::Equal_y_3 Equal_x_2; + typedef typename R::Equal_z_3 Equal_y_2; + + static typename R::FT x(const typename R::Point_3& p) {return p.y();} + static typename R::FT y(const typename R::Point_3& p) {return p.z();} + static const int x_index=1; + static const int y_index=2; +}; +//project onto xz +template +struct Projector +{ + typedef typename R::Less_x_3 Less_x_2; + typedef typename R::Less_z_3 Less_y_2; + typedef typename R::Compare_x_3 Compare_x_2; + typedef typename R::Compare_z_3 Compare_y_2; + typedef typename R::Equal_x_3 Equal_x_2; + typedef typename R::Equal_z_3 Equal_y_2; + static typename R::FT x(const typename R::Point_3& p) {return p.x();} + static typename R::FT y(const typename R::Point_3& p) {return p.z();} + static const int x_index=0; + static const int y_index=2; +}; + +//project onto xy +template +struct Projector +{ + typedef typename R::Less_x_3 Less_x_2; + typedef typename R::Less_y_3 Less_y_2; + typedef typename R::Compare_x_3 Compare_x_2; + typedef typename R::Compare_y_3 Compare_y_2; + typedef typename R::Equal_x_3 Equal_x_2; + typedef typename R::Equal_y_3 Equal_y_2; + static typename R::FT x(const typename R::Point_3& p) {return p.x();} + static typename R::FT y(const typename R::Point_3& p) {return p.y();} + static const int x_index=0; + static const int y_index=1; +}; + + + +template +class Orientation_projected_3 +{ +public: + typedef typename R::Point_3 Point; + typename R::FT x(const Point &p) const { return Projector::x(p); } + typename R::FT y(const Point &p) const { return Projector::y(p); } + + typename R::Point_2 project(const Point& p) const + { + return typename R::Point_2(x(p),y(p)); + } + + CGAL::Orientation operator()(const Point& p, + const Point& q, + const Point& r) const + { + return CGAL::orientation(project(p), project(q), project(r)); + } +}; + +template +class Side_of_oriented_circle_projected_3 +{ +public: + typedef typename R::Point_3 Point; + typename R::FT x(const Point &p) const { return Projector::x(p); } + typename R::FT y(const Point &p) const { return Projector::y(p); } + + + typename R::Point_2 project(const Point& p) const + { + return typename R::Point_2(x(p),y(p)); + } + CGAL::Oriented_side operator() (const Point &p, + const Point &q, + const Point &r, + const Point &s) const + { + return CGAL::side_of_oriented_circle(project(p),project(q),project(r),project(s) ); + } +}; + +template +class Side_of_bounded_circle_projected_3 +{ +public: + typedef typename R::Point_3 Point; + typename R::FT x(const Point &p) const { return Projector::x(p); } + typename R::FT y(const Point &p) const { return Projector::y(p); } + + + typename R::Point_2 project(const Point& p) const + { + return typename R::Point_2(x(p),y(p)); + } + CGAL::Bounded_side operator() (const Point &p, + const Point &q, + const Point &r, + const Point &s) const + { + return CGAL::side_of_bounded_circle(project(p),project(q),project(r),project(s) ); + } + + CGAL::Bounded_side operator() (const Point &p, + const Point &q, + const Point &r) const + { + return CGAL::side_of_bounded_circle(project(p),project(q),project(r)); + } +}; + +template +class Compare_distance_projected_3 +{ +public: + typedef typename R::Point_3 Point_3; + typedef typename R::Point_2 Point_2; + typedef typename R::FT RT; + typename R::FT x(const Point_3 &p) const { return Projector::x(p); } + typename R::FT y(const Point_3 &p) const { return Projector::y(p); } + + Point_2 project(const Point_3& p) const + { + return Point_2(x(p),y(p)); + } + + Comparison_result operator()(const Point_3& p,const Point_3& q,const Point_3& r) const + { + Point_2 p2 = project(p); + Point_2 q2 = project(q); + Point_2 r2 = project(r); + return compare_distance_to_point(p2,q2,r2); + } +}; + +template +class Squared_distance_projected_3 +{ +public: + typedef typename R::Point_3 Point_3; + typedef typename R::Point_2 Point_2; + typedef typename R::Line_3 Line_3; + typedef typename R::Line_2 Line_2; + typedef typename R::FT RT; + typename R::FT x(const Point_3 &p) const { return Projector::x(p); } + typename R::FT y(const Point_3 &p) const { return Projector::y(p); } + + Point_2 project(const Point_3& p) const + { + return Point_2(x(p),y(p)); + } + + RT operator()(const Point_3& p, const Point_3& q) const + { + Point_2 p2(project(p)); + Point_2 q2(project(q)); + return squared_distance(p2, q2); + } + + RT operator()(const Line_3& l, const Point_3& p) const + { + Point_2 p2(project(p)); + Line_2 l2(project(l.point(0)), project(l.point(1))); + return squared_distance(p2, l2); + } +}; + +template +class Intersect_projected_3 +{ +public: + typedef typename R::Point_3 Point_3; + typedef typename R::Segment_3 Segment_3; + typedef typename R::Point_2 Point_2; + typedef typename R::Vector_2 Vector_2; + typedef typename R::Segment_2 Segment_2; + typedef typename R::FT FT; + + typename R::FT x(const Point_3 &p) const { return Projector::x(p); } + typename R::FT y(const Point_3 &p) const { return Projector::y(p); } + + Point_2 project(const Point_3& p) const + { + return Point_2(x(p),y(p)); + } + + FT alpha(const Point_2& p, const Point_2& source, const Point_2& target) const + { + FT dx = target.x() - source.x(); + FT dy = target.y() - source.y(); + return (CGAL::abs(dx)>CGAL::abs(dy)) ? ( p.x()-source.x() ) / dx : (p.y()-source.y() ) / dy; + } + + Object operator()(const Segment_3& s1, const Segment_3& s2) const + { + Point_2 s1_source = project(s1.source()); + Point_2 s1_target = project(s1.target()); + Point_2 s2_source = project(s2.source()); + Point_2 s2_target = project(s2.target()); + Segment_2 s1_2(s1_source, s1_target); + Segment_2 s2_2(s2_source, s2_target); + CGAL_precondition(!s1_2.is_degenerate()); + CGAL_precondition(!s2_2.is_degenerate()); + + //compute intersection points in projected plane + //We know that none of the segment is degenerate + Object o = intersection(s1_2,s2_2); + const Point_2* pi=CGAL::object_cast(&o); + if (pi==NULL) { //case of segment or empty + const Segment_2* si=CGAL::object_cast(&o); + if (si==NULL) return Object(); + FT src[3],tgt[3]; + //the third coordinate is the midpoint between the points on s1 and s2 + FT z1 = s1.source()[dim] + ( alpha(si->source(), s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); + FT z2 = s2.source()[dim] + ( alpha(si->source(), s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); + src[dim] = (z1+z2) / FT(2); + + + z1 = s1.source()[dim] + ( alpha(si->target(), s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); + z2 = s2.source()[dim] + ( alpha(si->target(), s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); + + tgt[dim] = (z1+z2) / FT(2); + + + src[Projector::x_index] = si->source().x(); + src[Projector::y_index] = si->source().y(); + tgt[Projector::x_index] = si->target().x(); + tgt[Projector::y_index] = si->target().y(); + return make_object( Segment_3( Point_3(src[0],src[1],src[2]),Point_3(tgt[0],tgt[1],tgt[2]) ) ); + } + FT coords[3]; + //compute the third coordinate of the projected intersection point onto 3D segments + FT z1 = s1.source()[dim] + ( alpha(*pi, s1_source, s1_target) * ( s1.target()[dim] - s1.source()[dim] )); + FT z2 = s2.source()[dim] + ( alpha(*pi, s2_source, s2_target) * ( s2.target()[dim] - s2.source()[dim] )); + + coords[dim] = (z1+z2) / FT(2); + coords[Projector::x_index] = pi->x(); + coords[Projector::y_index] = pi->y(); + + Point_3 res(coords[0],coords[1],coords[2]); + CGAL_assertion(x(res)==pi->x() && y(res)==pi->y()); + return make_object(res); + } +}; + +template +class Circumcenter_center_projected +{ + typedef typename R::Point_3 Point_3; + typedef typename R::Point_2 Point_2; + + typename R::FT x(const Point_3 &p) const { return Projector::x(p); } + typename R::FT y(const Point_3 &p) const { return Projector::y(p); } + + Point_2 project(const Point_3& p) const + { + return Point_2(x(p),y(p)); + } + + Point_3 embed (const Point_2& p) const + { + typename R::FT coords[3]; + coords[Projector::x_index]=p.x(); + coords[Projector::y_index]=p.y(); + coords[dim]=typename R::FT(0); + return Point_3(coords[0],coords[1],coords[2]); + } + +public: + Point_3 operator() (const Point_3& p1,const Point_3& p2) const + { + return embed( circumcenter(project(p1),project(p2)) ); + } + + Point_3 operator() (const Point_3& p1,const Point_3& p2,const Point_3& p3) const + { + return embed( circumcenter(project(p1),project(p2),project(p3)) ); + } +}; + +template +class Compute_area_projected +{ + typedef typename R::Point_3 Point_3; + typedef typename R::Point_2 Point_2; + + typename R::FT x(const Point_3 &p) const { return Projector::x(p); } + typename R::FT y(const Point_3 &p) const { return Projector::y(p); } + + Point_2 project(const Point_3& p) const + { + return Point_2(x(p),y(p)); + } + + +public: + typename R::FT operator() (const Point_3& p1,const Point_3& p2,const Point_3& p3) const + { + return R().compute_area_2_object() ( project(p1),project(p2),project(p3) ); + } +}; + +template +class Compute_squared_radius_projected +{ + typedef typename R::Point_3 Point_3; + typedef typename R::Point_2 Point_2; + + typename R::FT x(const Point_3 &p) const { return Projector::x(p); } + typename R::FT y(const Point_3 &p) const { return Projector::y(p); } + + Point_2 project(const Point_3& p) const + { + return Point_2(x(p),y(p)); + } + + +public: + typename R::FT operator() (const Point_3& p1,const Point_3& p2,const Point_3& p3) const + { + return R().compute_squared_radius_2_object() ( project(p1),project(p2),project(p3) ); + } + typename R::FT operator() (const Point_3& p1,const Point_3& p2) const + { + return R().compute_squared_radius_2_object() ( project(p1),project(p2) ); + } + + typename R::FT operator() (const Point_3& p1) const + { + return R().compute_squared_radius_2_object() ( project(p1) ); + } +}; + +template < class R, int dim > +class Projection_traits_3 { +public: + typedef Projection_traits_3 Traits; + typedef R Rp; + typedef typename R::FT FT; + typedef typename Rp::Point_3 Point_2; + typedef typename Rp::Segment_3 Segment_2; + typedef typename Rp::Vector_3 Vector_2; + typedef typename Rp::Triangle_3 Triangle_2; + typedef typename Rp::Line_3 Line_2; + + typedef typename Projector::Less_x_2 Less_x_2; + typedef typename Projector::Less_y_2 Less_y_2; + typedef typename Projector::Compare_x_2 Compare_x_2; + typedef typename Projector::Compare_y_2 Compare_y_2; + typedef Orientation_projected_3 Orientation_2; + typedef typename Rp::Angle_3 Angle_2; + typedef Side_of_oriented_circle_projected_3 Side_of_oriented_circle_2; + typedef Side_of_bounded_circle_projected_3 Side_of_bounded_circle_2; + typedef Compare_distance_projected_3 Compare_distance_2; + typedef Squared_distance_projected_3 Compute_squared_distance_2; + typedef Intersect_projected_3 Intersect_2; + typedef Compute_squared_radius_projected Compute_squared_radius_2; + typedef typename Rp::Construct_segment_3 Construct_segment_2; + typedef typename Rp::Construct_translated_point_3 Construct_translated_point_2; + typedef typename Rp::Construct_midpoint_3 Construct_midpoint_2; + typedef typename Rp::Construct_vector_3 Construct_vector_2; + typedef typename Rp::Construct_scaled_vector_3 Construct_scaled_vector_2; + typedef typename Rp::Construct_triangle_3 Construct_triangle_2; + typedef typename Rp::Construct_line_3 Construct_line_2; + + struct Less_xy_2 { + typedef bool result_type; + bool operator()(const Point_2& p, const Point_2& q) const + { + Compare_x_2 cx; + Comparison_result crx = cx(p,q); + if(crx == SMALLER){ return true;} + if(crx == LARGER){return false;} + Less_y_2 ly; + return ly(p,q); + } + }; + + + struct Less_yx_2 { + typedef bool result_type; + bool operator()(const Point_2& p, const Point_2& q) const + { + Compare_y_2 cy; + Comparison_result cry = cy(p,q); + if(cry == SMALLER){ return true;} + if(cry == LARGER){return false;} + Less_x_2 lx; + return lx(p,q); + } + }; + + struct Equal_2 { + typedef bool result_type; + bool operator()(const Point_2& p, const Point_2& q) const + { + + Equal_x_2 eqx; + Equal_y_2 eqy; + return eqx(p,q) & eqy(p,q); + } + }; + + struct Left_turn_2 { + typedef bool result_type; + bool operator()(const Point_2& p, const Point_2& q, const Point_2& r) const + { + + Orientation_2 ori; + return ori(p,q,r) == LEFT_TURN; + } + }; + + //for natural_neighbor_coordinates_2 + typedef typename Projector::Equal_x_2 Equal_x_2; + typedef typename Projector::Equal_y_2 Equal_y_2; + typedef Circumcenter_center_projected Construct_circumcenter_2; + typedef Compute_area_projected Compute_area_2; + Construct_circumcenter_2 construct_circumcenter_2_object () const {return Construct_circumcenter_2();} + Compute_area_2 compute_area_2_object () const {return Compute_area_2();} + + + // for compatibility with previous versions + typedef Point_2 Point; + typedef Segment_2 Segment; + typedef Triangle_2 Triangle; + + Projection_traits_3(){} + Projection_traits_3( + const Projection_traits_3&){} + Projection_traits_3 &operator=( + const Projection_traits_3&){return *this;} + + typename Rp::FT x(const Point_2 &p) const { return Projector::x(p); } + typename Rp::FT y(const Point_2 &p) const { return Projector::y(p); } + + + Equal_2 + equal_2_object() const + { return Equal_2();} + + Left_turn_2 + left_turn_2_object() const + { return Left_turn_2();} + + Less_x_2 + less_x_2_object() const + { return Less_x_2();} + + Less_xy_2 + less_xy_2_object() const + { return Less_xy_2();} + + Less_yx_2 + less_yx_2_object() const + { return Less_yx_2();} + + Less_y_2 + less_y_2_object() const + { return Less_y_2();} + Compare_x_2 + compare_x_2_object() const + { return Compare_x_2();} + Angle_2 + angle_2_object() const { + return Angle_2(); + } + + Compare_y_2 + compare_y_2_object() const + { return Compare_y_2();} + + Orientation_2 + orientation_2_object() const + { return Orientation_2();} + + Side_of_oriented_circle_2 + side_of_oriented_circle_2_object() const + {return Side_of_oriented_circle_2();} + + Side_of_bounded_circle_2 + side_of_bounded_circle_2_object() const + {return Side_of_bounded_circle_2();} + + Compare_distance_2 + compare_distance_2_object() const + { + return Compare_distance_2(); + } + + Compute_squared_distance_2 + compute_squared_distance_2_object () const + { + return Compute_squared_distance_2(); + } + + Compute_squared_radius_2 + compute_squared_radius_2_object () const + { + return Compute_squared_radius_2(); + } + + Intersect_2 + intersect_2_object () const + { + return Intersect_2(); + } + + Construct_segment_2 construct_segment_2_object() const + {return Construct_segment_2();} + + Construct_translated_point_2 construct_translated_point_2_object() const + {return Construct_translated_point_2();} + + Construct_midpoint_2 construct_midpoint_2_object() const + {return Construct_midpoint_2();} + + Construct_vector_2 construct_vector_2_object() const + {return Construct_vector_2();} + + Construct_scaled_vector_2 construct_scaled_vector_2_object() const + {return Construct_scaled_vector_2();} + + Construct_triangle_2 construct_triangle_2_object() const + {return Construct_triangle_2();} + + Construct_line_2 construct_line_2_object() const + {return Construct_line_2();} + +}; + + +} } //namespace CGAL::internal + #endif // CGAL_INTERNAL_PROJECTION_TRAITS_3_H