removed object Side_of_hyperbolic_triangle from traits; added object Side_of_oriented_hyperbolic_segment in traits; added function side_of_hyperbolic_triangle in triangulation class

This commit is contained in:
Iordan Iordanov 2018-08-08 22:41:01 +02:00
parent 8d441cebc1
commit e133fcea32
3 changed files with 130 additions and 135 deletions

View File

@ -85,7 +85,7 @@ public:
}; };
typedef typename Geom_traits::Side_of_hyperbolic_triangle_2 Side_of_hyperbolic_triangle; typedef typename Geom_traits::Side_of_oriented_hyperbolic_segment_2 Side_of_oriented_hyperbolic_segment;
typedef typename Geom_traits::Is_Delaunay_hyperbolic Is_Delaunay_hyperbolic; typedef typename Geom_traits::Is_Delaunay_hyperbolic Is_Delaunay_hyperbolic;
Hyperbolic_Delaunay_triangulation_2(const Geom_traits& gt = Geom_traits()) Hyperbolic_Delaunay_triangulation_2(const Geom_traits& gt = Geom_traits())
@ -205,6 +205,68 @@ public:
private: private:
Oriented_side side_of_hyperbolic_triangle(const Point p, const Point q, const Point r,
const Point query, Locate_type &lt, int& li) const {
// The triangle (p,q,r) must be Delaunay hyperbolic
CGAL_triangulation_precondition(Is_Delaunay_hyperbolic()(p, q, r));
// Point p is assumed to be at index 0, q at index 1 and r at index 2 in the face.
li = -1;
if (query == p) {
lt = VERTEX;
li = 0;
return ON_ORIENTED_BOUNDARY;
}
if (query == q) {
lt == VERTEX;
li = 1;
return ON_ORIENTED_BOUNDARY;
}
if (query == r) {
lt == VERTEX;
li = 2;
return ON_ORIENTED_BOUNDARY;
}
Oriented_side cp1 = Side_of_oriented_hyperbolic_segment()(p, q, query);
if (cp1 == ON_ORIENTED_BOUNDARY) {
lt = EDGE;
li = 2;
return ON_ORIENTED_BOUNDARY;
}
Oriented_side cp2 = Side_of_oriented_hyperbolic_segment()(q, r, query);
if (cp2 == ON_ORIENTED_BOUNDARY) {
lt = EDGE;
li = 0;
return ON_ORIENTED_BOUNDARY;
}
Oriented_side cp3 = Side_of_oriented_hyperbolic_segment()(r, p, query);
if (cp3 == ON_ORIENTED_BOUNDARY) {
lt = EDGE;
li = 1;
return ON_ORIENTED_BOUNDARY;
}
Oriented_side cs1 = Side_of_oriented_hyperbolic_segment()(p, q, r);
Oriented_side cs2 = Side_of_oriented_hyperbolic_segment()(q, r, p);
Oriented_side cs3 = Side_of_oriented_hyperbolic_segment()(r, p, q);
// Cannot be on the boundary here.
lt = FACE;
if (cs1 != cp1 || cs2 != cp2 || cs3 != cp3) {
return ON_NEGATIVE_SIDE;
} else {
return ON_POSITIVE_SIDE;
}
}
bool has_infinite_vertex(Face_handle f) const bool has_infinite_vertex(Face_handle f) const
{ {
return Base::is_infinite(f); return Base::is_infinite(f);
@ -675,12 +737,12 @@ public:
Point q = fh->vertex(1)->point(); Point q = fh->vertex(1)->point();
Point r = fh->vertex(2)->point(); Point r = fh->vertex(2)->point();
if (Is_Delaunay_hyperbolic()(p, q, r)) { if (Is_Delaunay_hyperbolic()(p, q, r)) {
Bounded_side side = Side_of_hyperbolic_triangle()(p, q, r, query, li); Oriented_side side = side_of_hyperbolic_triangle(p, q, r, query, lt, li);
if (side == ON_BOUNDARY) { if (side == ON_ORIENTED_BOUNDARY) {
lt = EDGE; lt = EDGE;
return fh; return fh;
} else { } else {
if (side == ON_BOUNDED_SIDE) { if (side == ON_POSITIVE_SIDE) {
lt = FACE; lt = FACE;
return fh; return fh;
} else { } else {
@ -693,12 +755,12 @@ public:
q = fh->mirror_vertex(li)->point(); q = fh->mirror_vertex(li)->point();
r = fh->vertex(cw(li))->point(); r = fh->vertex(cw(li))->point();
if (Is_Delaunay_hyperbolic()(p, q, r)) { if (Is_Delaunay_hyperbolic()(p, q, r)) {
Bounded_side side = Side_of_hyperbolic_triangle()(p, q, r, query, li); Oriented_side side = side_of_hyperbolic_triangle(p, q, r, query, lt, li);
if (side == ON_BOUNDARY) { if (side == ON_ORIENTED_BOUNDARY) {
lt = EDGE; lt = EDGE;
return fh; return fh;
} else { } else {
if (side == ON_BOUNDED_SIDE) { if (side == ON_POSITIVE_SIDE) {
lt = FACE; lt = FACE;
return fh; return fh;
} else { } else {
@ -719,12 +781,12 @@ public:
return Face_handle(); return Face_handle();
} }
Bounded_side side = Side_of_hyperbolic_triangle()(p, q, r, query, li); Oriented_side side = side_of_hyperbolic_triangle(p, q, r, query, lt, li);
if (side == ON_BOUNDED_SIDE) { if (side == ON_POSITIVE_SIDE) {
lt = FACE; lt = FACE;
return fh; return fh;
} else { } else {
if (side == ON_BOUNDARY) { if (side == ON_ORIENTED_BOUNDARY) {
lt = EDGE; lt = EDGE;
return fh; return fh;
} else { } else {
@ -732,11 +794,11 @@ public:
for (int i = 0; i < 3; i++) { for (int i = 0; i < 3; i++) {
Face_handle nfh = fh->neighbor(i); Face_handle nfh = fh->neighbor(i);
if (Is_Delaunay_hyperbolic()(nfh->vertex(0)->point(),nfh->vertex(1)->point(),nfh->vertex(2)->point())) { if (Is_Delaunay_hyperbolic()(nfh->vertex(0)->point(),nfh->vertex(1)->point(),nfh->vertex(2)->point())) {
Bounded_side nside = Side_of_hyperbolic_triangle()(nfh->vertex(0)->point(),nfh->vertex(1)->point(),nfh->vertex(2)->point(), query, li); Oriented_side nside = side_of_hyperbolic_triangle(nfh->vertex(0)->point(),nfh->vertex(1)->point(),nfh->vertex(2)->point(), query, lt, li);
if (nside == ON_BOUNDED_SIDE) { if (nside == ON_POSITIVE_SIDE) {
lt = FACE; lt = FACE;
return nfh; return nfh;
} else if (nside == ON_BOUNDARY) { } else if (nside == ON_ORIENTED_BOUNDARY) {
lt = EDGE; lt = EDGE;
return nfh; return nfh;
} }

View File

@ -368,95 +368,62 @@ public:
class Side_of_hyperbolic_triangle_2 { class Side_of_oriented_hyperbolic_segment_2 {
public:
Side_of_hyperbolic_triangle_2() {}
typedef Bounded_side result_type;
// Returns the relative position of point t to the hyperbolic triangle (p,q,r)
Bounded_side operator()(Point_2 p, Point_2 q, Point_2 r, Point_2 t, int& li) const {
// The triangle (p,q,r) cannot be hyperbolic! This case should be handled at triangulation level
CGAL_triangulation_precondition(Is_Delaunay_hyperbolic()(p, q, r));
// Point p is assumed to be at index 0, q at index 1 and r at index 2 in the face.
li = -1;
Bounded_side cp1 = side_of_segment_2(t, p, q);
if (cp1 == ON_BOUNDARY) {
li = 2;
return ON_BOUNDARY;
}
Bounded_side cp2 = side_of_segment_2(t, q, r);
if (cp2 == ON_BOUNDARY) {
li = 0;
return ON_BOUNDARY;
}
Bounded_side cp3 = side_of_segment_2(t, r, p);
if (cp3 == ON_BOUNDARY) {
li = 1;
return ON_BOUNDARY;
}
Bounded_side cs1 = side_of_segment_2(r, p, q);
Bounded_side cs2 = side_of_segment_2(p, q, r);
Bounded_side cs3 = side_of_segment_2(q, r, p);
// Cannot be on the boundary here.
if (cs1 != cp1 || cs2 != cp2 || cs3 != cp3) {
return ON_UNBOUNDED_SIDE;
} else {
return ON_BOUNDED_SIDE;
}
}
private:
typedef typename R::Construct_weighted_circumcenter_2 Construct_weighted_circumcenter_2; typedef typename R::Construct_weighted_circumcenter_2 Construct_weighted_circumcenter_2;
typedef typename R::Weighted_point_2 Weighted_point_2; typedef typename R::Weighted_point_2 Weighted_point_2;
typedef typename R::Point_2 Bare_point; typedef typename R::Point_2 Bare_point;
Bounded_side side_of_segment_2(const Point_2 query, const Point_2 p, const Point_2 q) const { public:
Side_of_oriented_hyperbolic_segment_2() {}
typedef Oriented_side result_type;
result_type operator()(Point_2 p, Point_2 q, Point_2 query) const {
// Check first if the points are collinear with the origin // Check first if the points are collinear with the origin
Circle_2 poincare(Point_2(FT(0),FT(0)), FT(1)); Circle_2 poincare(Point_2(FT(0),FT(0)), FT(1));
Orientation ori = orientation(poincare.center(), p, q); Point_2 O(FT(0), FT(0));
Orientation ori = orientation(p, q, O);
if (ori == COLLINEAR) { if (ori == COLLINEAR) {
Euclidean_line_2 seg(p, q); Euclidean_line_2 seg(p, q);
Orientation qori = orientation(query, p, q); Orientation qori = orientation(p, q, query);
if (qori == COLLINEAR) { if (qori == COLLINEAR) {
return ON_BOUNDARY; return ON_ORIENTED_BOUNDARY;
} else { } else {
// It is sufficient that these are consistent. // It is sufficient that these are consistent.
if (qori == LEFT_TURN) { if (qori == LEFT_TURN) {
return ON_BOUNDED_SIDE; return ON_POSITIVE_SIDE;
} else { } else {
return ON_UNBOUNDED_SIDE; return ON_NEGATIVE_SIDE;
} }
} }
} }
Origin o;
Weighted_point_2 wp(p); Weighted_point_2 wp(p);
Weighted_point_2 wq(q); Weighted_point_2 wq(q);
Weighted_point_2 wo(Point_2(o), FT(1)); // Poincaré circle Weighted_point_2 wo(O, FT(1)); // Poincaré circle
Bare_point center = Construct_weighted_circumcenter_2()(wp, wo, wq); Bare_point center = Construct_weighted_circumcenter_2()(wp, wo, wq);
FT sq_radius = Compute_squared_Euclidean_distance_2()(p, center); FT sq_radius = Compute_squared_Euclidean_distance_2()(p, center);
Circle_2 circle(center, sq_radius); Circle_2 circle(center, sq_radius);
return circle.bounded_side(query); Bounded_side bs = circle.bounded_side(query);
if (bs == ON_BOUNDARY) {
return ON_ORIENTED_BOUNDARY;
} else {
if (bs == ON_BOUNDED_SIDE) {
return ON_POSITIVE_SIDE;
} else {
return ON_NEGATIVE_SIDE;
}
}
} }
}; };
Side_of_hyperbolic_triangle_2 Side_of_oriented_hyperbolic_segment_2
side_of_hyperbolic_triangle_2_object() { side_of_oriented_hyperbolic_segment_2() {
return Side_of_hyperbolic_triangle_2(); return Side_of_oriented_hyperbolic_segment_2();
} }

View File

@ -658,96 +658,62 @@ public:
} }
class Side_of_oriented_hyperbolic_segment_2 {
class Side_of_hyperbolic_triangle_2 {
public:
Side_of_hyperbolic_triangle_2() {}
typedef Bounded_side result_type;
// Returns the relative position of point t to the hyperbolic triangle (p,q,r)
Bounded_side operator()(Point_2 p, Point_2 q, Point_2 r, Point_2 t, int& li) const {
// The triangle (p,q,r) cannot be hyperbolic! This case should be handled at triangulation level
CGAL_triangulation_precondition(Is_Delaunay_hyperbolic()(p, q, r));
// Point p is assumed to be at index 0, q at index 1 and r at index 2 in the face.
li = -1;
Bounded_side cp1 = side_of_segment_2(t, p, q);
if (cp1 == ON_BOUNDARY) {
li = 2;
return ON_BOUNDARY;
}
Bounded_side cp2 = side_of_segment_2(t, q, r);
if (cp2 == ON_BOUNDARY) {
li = 0;
return ON_BOUNDARY;
}
Bounded_side cp3 = side_of_segment_2(t, r, p);
if (cp3 == ON_BOUNDARY) {
li = 1;
return ON_BOUNDARY;
}
Bounded_side cs1 = side_of_segment_2(r, p, q);
Bounded_side cs2 = side_of_segment_2(p, q, r);
Bounded_side cs3 = side_of_segment_2(q, r, p);
// Cannot be on the boundary here.
if (cs1 != cp1 || cs2 != cp2 || cs3 != cp3) {
return ON_UNBOUNDED_SIDE;
} else {
return ON_BOUNDED_SIDE;
}
}
private:
typedef typename Kernel::Construct_weighted_circumcenter_2 Construct_weighted_circumcenter_2; typedef typename Kernel::Construct_weighted_circumcenter_2 Construct_weighted_circumcenter_2;
typedef typename Kernel::Weighted_point_2 Weighted_point_2; typedef typename Kernel::Weighted_point_2 Weighted_point_2;
typedef typename Kernel::Point_2 Bare_point; typedef typename Kernel::Point_2 Bare_point;
Bounded_side side_of_segment_2(const Point_2 query, const Point_2 p, const Point_2 q) const { public:
Side_of_oriented_hyperbolic_segment_2() {}
typedef Oriented_side result_type;
result_type operator()(Point_2 p, Point_2 q, Point_2 query) const {
// Check first if the points are collinear with the origin // Check first if the points are collinear with the origin
Circle_2 poincare(Point_2(FT(0),FT(0)), FT(1)); Circle_2 poincare(Point_2(FT(0),FT(0)), FT(1));
Orientation ori = orientation(poincare.center(), p, q); Point_2 O(FT(0), FT(0));
Orientation ori = orientation(p, q, O);
if (ori == COLLINEAR) { if (ori == COLLINEAR) {
Euclidean_line_2 seg(p, q); Euclidean_line_2 seg(p, q);
Orientation qori = orientation(query, p, q); Orientation qori = orientation(p, q, query);
if (qori == COLLINEAR) { if (qori == COLLINEAR) {
return ON_BOUNDARY; return ON_ORIENTED_BOUNDARY;
} else { } else {
// It is sufficient that these are consistent. // It is sufficient that these are consistent.
if (qori == LEFT_TURN) { if (qori == LEFT_TURN) {
return ON_BOUNDED_SIDE; return ON_POSITIVE_SIDE;
} else { } else {
return ON_UNBOUNDED_SIDE; return ON_NEGATIVE_SIDE;
} }
} }
} }
Origin o;
Weighted_point_2 wp(p); Weighted_point_2 wp(p);
Weighted_point_2 wq(q); Weighted_point_2 wq(q);
Weighted_point_2 wo(Point_2(o), FT(1)); // Poincaré circle Weighted_point_2 wo(O, FT(1)); // Poincaré circle
Bare_point center = Construct_weighted_circumcenter_2()(wp, wo, wq); Bare_point center = Construct_weighted_circumcenter_2()(wp, wo, wq);
FT sq_radius = Compute_squared_Euclidean_distance_2()(p, center); FT sq_radius = Compute_squared_Euclidean_distance_2()(p, center);
Circle_2 circle(center, sq_radius); Circle_2 circle(center, sq_radius);
return circle.bounded_side(query); Bounded_side bs = circle.bounded_side(query);
if (bs == ON_BOUNDARY) {
return ON_ORIENTED_BOUNDARY;
} else {
if (bs == ON_BOUNDED_SIDE) {
return ON_POSITIVE_SIDE;
} else {
return ON_NEGATIVE_SIDE;
}
}
} }
}; };
Side_of_hyperbolic_triangle_2 Side_of_oriented_hyperbolic_segment_2
side_of_hyperbolic_triangle_2_object() { side_of_oriented_hyperbolic_segment_2() {
return Side_of_hyperbolic_triangle_2(); return Side_of_oriented_hyperbolic_segment_2();
} }