From d30b7a4ef80aeb1af1d30ec26541d24926ee3e7b Mon Sep 17 00:00:00 2001 From: Simon Giraudot Date: Tue, 24 Jan 2017 12:59:17 +0100 Subject: [PATCH] Update PLY IO for Point_set_3 --- .../include/CGAL/IO/read_ply_point_set_3.h | 37 ++----- Point_set_3/include/CGAL/Point_set_3/IO.h | 104 +++++++++++++----- 2 files changed, 84 insertions(+), 57 deletions(-) diff --git a/Point_set_3/include/CGAL/IO/read_ply_point_set_3.h b/Point_set_3/include/CGAL/IO/read_ply_point_set_3.h index 348210bae34..6a40421a208 100644 --- a/Point_set_3/include/CGAL/IO/read_ply_point_set_3.h +++ b/Point_set_3/include/CGAL/IO/read_ply_point_set_3.h @@ -29,28 +29,12 @@ namespace CGAL { -/*! - - \ingroup PkgPointSet3 - - \brief PLY interpreter designed to fill a `CGAL::Point_set_3` object. - - This interpreter will instanciate any number of property needed to - store all PLY properties read in the header: - - - points and normals are stored as usual `CGAL::Point_set_3` - properties (property "point" of type `CGAL::Point_3` and property - "normal" of type `CGAL::Vector_3`) - - - other PLY properties are stored on point set properties with the - name and type given by the PLY header - - \tparam Point Point type. - \tparam Vector Normal vector type. - - \cgalModels `PlyInterpreter` - */ +namespace Ply +{ +namespace internal +{ + template ::Kernel::Vector_3> class Ply_interpreter_point_set_3 @@ -100,7 +84,7 @@ public: : m_point_set (point_set), m_use_floats (false) { } - bool is_applicable (Ply_reader& reader) + void instantiate_properties (Ply_reader& reader) { const std::vector& readers = reader.readers(); @@ -187,11 +171,6 @@ public: if (has_normal[0] && has_normal[1] && has_normal[2]) m_point_set.add_normal_map(); - - - return (reader.does_tag_exist ("x") || reader.does_tag_exist ("x")) - && (reader.does_tag_exist ("y") || reader.does_tag_exist ("y")) - && (reader.does_tag_exist ("z") || reader.does_tag_exist ("z")); } void process_line (Ply_reader& reader) @@ -229,6 +208,10 @@ public: } }; +} + +} + } /// \endcond diff --git a/Point_set_3/include/CGAL/Point_set_3/IO.h b/Point_set_3/include/CGAL/Point_set_3/IO.h index ceb3ad302b2..1a1c371a112 100644 --- a/Point_set_3/include/CGAL/Point_set_3/IO.h +++ b/Point_set_3/include/CGAL/Point_set_3/IO.h @@ -110,11 +110,33 @@ read_ply_point_set( std::istream& stream, ///< input stream. CGAL::Point_set_3& point_set) ///< point set { - CGAL::Ply_interpreter_point_set_3 interpreter (point_set); + if(!stream) + { + std::cerr << "Error: cannot open file" << std::endl; + return false; + } - return CGAL::read_ply_custom_points - (stream, interpreter, - typename Kernel_traits::Kernel()); + Ply::internal::Ply_reader reader; + + if (!(reader.init (stream))) + return false; + + Ply::internal::Ply_interpreter_point_set_3 interpreter (point_set); + interpreter.instantiate_properties (reader); + + std::size_t points_read = 0; + + while (!(stream.eof()) && points_read < reader.m_nb_points) + { + for (std::size_t i = 0; i < reader.readers().size (); ++ i) + reader.readers()[i]->get (stream); + + interpreter.process_line (reader); + + ++ points_read; + } + + return (points_read == reader.m_nb_points); } /*! @@ -167,14 +189,6 @@ write_ply_point_set( stream << point_set; return true; - // if (point_set.has_normal_map()) - // return CGAL::write_ply_points_and_normals - // (stream, point_set.begin(), point_set.end(), - // point_set.point_map(), point_set.normal_map()); - - // return CGAL::write_ply_points - // (stream, point_set.begin(), point_set.end(), - // point_set.point_map()); } @@ -221,7 +235,7 @@ namespace internal { public: virtual ~Abstract_property_printer() { } - virtual std::string get_string(const typename CGAL::Point_set_3::Index& index) = 0; + virtual void print (std::ostream& stream, const typename CGAL::Point_set_3::Index& index) = 0; }; template @@ -236,12 +250,33 @@ namespace internal } - virtual std::string get_string(const typename CGAL::Point_set_3::Index& index) + virtual void print(std::ostream& stream, const typename CGAL::Point_set_3::Index& index) { - std::ostringstream oss; - oss.precision (std::numeric_limits::digits10 + 2); - oss << get(m_pmap, index); - return oss.str(); + stream << get(m_pmap, index); + } + }; + + template + class Simple_property_printer : public Abstract_property_printer + { + typedef typename CGAL::Point_set_3 Point_set; + typedef typename Point_set::template Property_map Pmap; + Pmap m_pmap; + public: + Simple_property_printer (const Pmap& pmap) : m_pmap (pmap) + { + + } + + virtual void print(std::ostream& stream, const typename CGAL::Point_set_3::Index& index) + { + if (get_mode(stream) == IO::ASCII) + stream << get(m_pmap, index); + else + { + Type t = get (m_pmap, index); + stream.write (reinterpret_cast(&t), sizeof(t)); + } } }; @@ -257,11 +292,15 @@ namespace internal } - virtual std::string get_string(const typename CGAL::Point_set_3::Index& index) + virtual void print(std::ostream& stream, const typename CGAL::Point_set_3::Index& index) { - std::ostringstream oss; - oss << (int)(get(m_pmap, index)); - return oss.str(); + if (get_mode(stream) == IO::ASCII) + stream << int(get(m_pmap, index)); + else + { + Type t = get (m_pmap, index); + stream.write (reinterpret_cast(&t), sizeof(t)); + } } }; @@ -284,7 +323,7 @@ std::ostream& operator<<(std::ostream& os, typedef CGAL::Point_set_3 Point_set; os << "ply" << std::endl - << "format ascii 1.0" << std::endl + << ((get_mode(os) == IO::BINARY) ? "format binary_little_endian 1.0" : "format ascii 1.0") << std::endl << "comment Generated by the CGAL library" << std::endl << "element vertex " << ps.number_of_points() << std::endl; @@ -340,7 +379,7 @@ std::ostream& operator<<(std::ostream& os, if (okay) { os << "property short " << prop[i] << std::endl; - printers.push_back (new internal::Property_printer(pmap)); + printers.push_back (new internal::Simple_property_printer(pmap)); continue; } } @@ -350,7 +389,7 @@ std::ostream& operator<<(std::ostream& os, if (okay) { os << "property ushort " << prop[i] << std::endl; - printers.push_back (new internal::Property_printer(pmap)); + printers.push_back (new internal::Simple_property_printer(pmap)); continue; } } @@ -360,7 +399,7 @@ std::ostream& operator<<(std::ostream& os, if (okay) { os << "property int " << prop[i] << std::endl; - printers.push_back (new internal::Property_printer(pmap)); + printers.push_back (new internal::Simple_property_printer(pmap)); continue; } } @@ -370,7 +409,7 @@ std::ostream& operator<<(std::ostream& os, if (okay) { os << "property float " << prop[i] << std::endl; - printers.push_back (new internal::Property_printer(pmap)); + printers.push_back (new internal::Simple_property_printer(pmap)); continue; } } @@ -380,7 +419,7 @@ std::ostream& operator<<(std::ostream& os, if (okay) { os << "property double " << prop[i] << std::endl; - printers.push_back (new internal::Property_printer(pmap)); + printers.push_back (new internal::Simple_property_printer(pmap)); continue; } } @@ -391,8 +430,13 @@ std::ostream& operator<<(std::ostream& os, for (typename Point_set::const_iterator it = ps.begin(); it != ps.end(); ++ it) { for (std::size_t i = 0; i < printers.size(); ++ i) - os << printers[i]->get_string(*it) << " "; - os << std::endl; + { + printers[i]->print(os, *it); + if (get_mode (os) == IO::ASCII) + os << " "; + } + if (get_mode (os) == IO::ASCII) + os << std::endl; } return os; }