From 2c37b32f92f42072b33fbcf70e512bc343f995c8 Mon Sep 17 00:00:00 2001 From: Baskin Senbaslar Date: Wed, 10 Jul 2019 14:04:00 +0300 Subject: [PATCH] borders are handled based on edges instead of vertices --- ...collapse_surface_mesh_garland_heckbert.cpp | 4 +- ...rlandHeckbert_edge_collapse_visitor_base.h | 11 ++-- .../Edge_collapse/GarlandHeckbert_placement.h | 1 + .../internal/GarlandHeckbert_core.h | 58 +++++++++++++++---- 4 files changed, 55 insertions(+), 19 deletions(-) diff --git a/Surface_mesh_simplification/examples/Surface_mesh_simplification/edge_collapse_surface_mesh_garland_heckbert.cpp b/Surface_mesh_simplification/examples/Surface_mesh_simplification/edge_collapse_surface_mesh_garland_heckbert.cpp index c54b5a68236..1769d30e8f5 100644 --- a/Surface_mesh_simplification/examples/Surface_mesh_simplification/edge_collapse_surface_mesh_garland_heckbert.cpp +++ b/Surface_mesh_simplification/examples/Surface_mesh_simplification/edge_collapse_surface_mesh_garland_heckbert.cpp @@ -83,8 +83,8 @@ int main(int argc, char** argv) // In this example, the simplification stops when the number of undirected edges // drops below 10% of the initial count double threshold = (argc > 2) ? std::atof(argv[2]) : 0.1; -// SMS::Count_ratio_stop_predicate stop(threshold); - SMS::GarlandHeckbert_cost_stop_predicate stop(threshold); + SMS::Count_ratio_stop_predicate stop(threshold); + //SMS::GarlandHeckbert_cost_stop_predicate stop(threshold); SMS::GarlandHeckbert_edge_collapse_visitor_base::garland_heckbert_map_type map; SMS::GarlandHeckbert_edge_collapse_visitor_base vis(map); diff --git a/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/GarlandHeckbert_edge_collapse_visitor_base.h b/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/GarlandHeckbert_edge_collapse_visitor_base.h index 8017a1a8aa5..7d257339556 100644 --- a/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/GarlandHeckbert_edge_collapse_visitor_base.h +++ b/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/GarlandHeckbert_edge_collapse_visitor_base.h @@ -26,15 +26,16 @@ struct GarlandHeckbert_edge_collapse_visitor_base : Edge_collapse_visitor_base::Matrix4x4 Matrix4x4; typedef typename internal::GarlandHeckbertCore::garland_heckbert_map_type garland_heckbert_map_type; - + typedef typename internal::GarlandHeckbertCore::FT FT; garland_heckbert_map_type& mCostMatrices; - + FT mDiscontinuityMultiplier; GarlandHeckbert_edge_collapse_visitor_base( - garland_heckbert_map_type& aCostMatrices) + garland_heckbert_map_type& aCostMatrices, FT aDiscontinuityMultiplier = 100.0) : - mCostMatrices(aCostMatrices) { + mCostMatrices(aCostMatrices), + mDiscontinuityMultiplier(aDiscontinuityMultiplier) { } @@ -45,7 +46,7 @@ struct GarlandHeckbert_edge_collapse_visitor_base : Edge_collapse_visitor_base::fundamental_error_quadric(hd, aTM)) + std::move(internal::GarlandHeckbertCore::fundamental_error_quadric(hd, aTM, mDiscontinuityMultiplier)) ); } } diff --git a/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/GarlandHeckbert_placement.h b/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/GarlandHeckbert_placement.h index e2847ee9949..c17a25b1f7e 100644 --- a/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/GarlandHeckbert_placement.h +++ b/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/GarlandHeckbert_placement.h @@ -45,6 +45,7 @@ public: const Col4 opt = std::move(GHC::optimal_point(combinedMatrix, p0, p1)); + boost::optional pt = typename Profile::Point(opt(0) / opt(3), opt(1) / opt(3), opt(2) / opt(3)); diff --git a/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/internal/GarlandHeckbert_core.h b/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/internal/GarlandHeckbert_core.h index f9f6d496a9e..db4b9a97109 100644 --- a/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/internal/GarlandHeckbert_core.h +++ b/Surface_mesh_simplification/include/CGAL/Surface_mesh_simplification/Policies/Edge_collapse/internal/GarlandHeckbert_core.h @@ -34,6 +34,7 @@ struct GarlandHeckbertCore typedef typename Kernel::Line_3 Line_3; typedef typename Kernel::FT FT; typedef typename Kernel::RT RT; + typedef typename Kernel::Vector_3 Vector_3; typedef typename Eigen::Matrix Matrix4x4; typedef typename Eigen::Matrix Row4; @@ -60,13 +61,15 @@ struct GarlandHeckbertCore * * Currently, only checks if vertex belongs to a border. */ - static bool is_discontinuity_vertex(const halfedge_descriptor& aHD, const TM& aTM) { - for(face_descriptor fd: faces_around_target(aHD, aTM)) { - if(fd == GraphTraits::null_face()) { - return true; - } + /*static bool is_discontinuity_vertex(const halfedge_descriptor& aHD, const TM& aTM) { + if(is_border(target(aHD, aTM), aTM)) { + return true; } return false; + }*/ + + static bool is_discontinuity_edge(const halfedge_descriptor& aHD, const TM& aTM) { + return is_border_edge(aHD, aTM); } /* @@ -78,12 +81,21 @@ struct GarlandHeckbertCore vertex_descriptor target_vd = target(aHD, aTM); const Point target_vertex_point = std::move(get(boost::vertex_point, aTM, target_vd)); + const Vector_3 target_vertex_vector(target_vertex_point.x(), + target_vertex_point.y(), + target_vertex_point.z()); - bool discontinuity_vertex = is_discontinuity_vertex(aHD, aTM); + //std::cout << "point: " << target_vertex_point.x() << " " + // << target_vertex_point.y() << " " + // << target_vertex_point.z() << std::endl; + //bool discontinuity_vertex = is_discontinuity_vertex(aHD, aTM); + + int i = 0; for(const halfedge_descriptor hd: halfedges_around_target(target_vd, aTM)) { face_descriptor fd = face(hd, aTM); if(fd != GraphTraits::null_face()) { + //std::cout << "face" << std::endl; std::vector vds; for(vertex_descriptor vd: vertices_around_face(hd, aTM)) { vds.push_back(vd); @@ -96,8 +108,30 @@ struct GarlandHeckbertCore FT norm = sqrt(plane.a() * plane.a() + plane.b() * plane.b() + plane.c() * plane.c()); plane_mtr << plane.a() / norm, plane.b() / norm, plane.c() / norm, plane.d() / norm; quadric += plane_mtr.transpose() * plane_mtr; + //std::cout << plane_mtr << std::endl; - if(discontinuity_vertex) { + if(is_discontinuity_edge(hd, aTM)) { + const vertex_descriptor source_vd = source(hd, aTM); + const Vector_3 p1p2(target_vertex_point, get(boost::vertex_point, aTM, source_vd)); + const Vector_3 normal = cross_product(p1p2, plane.orthogonal_vector()); + FT d = - normal * target_vertex_vector; + FT norm = sqrt(normal.x() * normal.x() + normal.y() * normal.y() + normal.z() * normal.z()); + plane_mtr << normal.x() / norm, normal.y() / norm, normal.z() / norm, d / norm; + quadric += plane_mtr.transpose() * plane_mtr * aDiscontinuityMultiplier; + } + + halfedge_descriptor shd = next(hd, aTM); + if(is_discontinuity_edge(shd, aTM)) { + const vertex_descriptor target_vd = target(shd, aTM); + const Vector_3 p1p2(target_vertex_point, get(boost::vertex_point, aTM, target_vd)); + const Vector_3 normal = cross_product(p1p2, plane.orthogonal_vector()); + FT d = - normal * target_vertex_vector; + FT norm = sqrt(normal.x() * normal.x() + normal.y() * normal.y() + normal.z() * normal.z()); + plane_mtr << normal.x() / norm, normal.y() / norm, normal.z() / norm, d / norm; + quadric += plane_mtr.transpose() * plane_mtr * aDiscontinuityMultiplier; + } + + /*if(discontinuity_vertex) { const vertex_descriptor source_vd = source(hd, aTM); const Line_3 edge_line = Line_3(get(boost::vertex_point, aTM, source_vd), target_vertex_point); @@ -107,15 +141,15 @@ struct GarlandHeckbertCore Row4 plane_mtr; FT norm = sqrt(plane.a() * plane.a() + plane.b() * plane.b() + plane.c() * plane.c()); plane_mtr << plane.a() / norm, plane.b() / norm, plane.c() / norm, plane.d() / norm; + std::cout << plane_mtr << std::endl; quadric += plane_mtr.transpose() * plane_mtr; - } + }*/ + } else { + //std::cout << "null face." << std::endl; } } - if(discontinuity_vertex) { - quadric *= aDiscontinuityMultiplier; - } - + //std::cout << std::endl; return quadric; }