diff --git a/src/ifcgeom/IfcGeomRepresentation.cpp b/src/ifcgeom/IfcGeomRepresentation.cpp index e1c1c4e167..3be3e3bdb8 100644 --- a/src/ifcgeom/IfcGeomRepresentation.cpp +++ b/src/ifcgeom/IfcGeomRepresentation.cpp @@ -145,11 +145,6 @@ IfcGeom::Representation::Serialization::Serialization(const BRep& brep) : Representation(brep.settings()) , id_(brep.id()) { -#ifdef IFOPSH_WITH_OPENCASCADE - ConversionResultShape* shape = brep.as_compound(); - TopoDS_Compound compound = TopoDS::Compound(((ifcopenshell::geometry::OpenCascadeShape*)shape)->shape()); - delete shape; - for (auto it = brep.begin(); it != brep.end(); ++it) { int sid = -1; @@ -175,12 +170,24 @@ IfcGeom::Representation::Serialization::Serialization(const BRep& brep) surface_style_ids_.push_back(sid); } - std::stringstream sstream; - BRepTools::Write(compound,sstream); - brep_data_ = sstream.str(); -#else - throw std::runtime_error("Not available without Open Cascade"); -#endif + if (brep.begin() != brep.end()) { + if (dynamic_cast(brep.begin()->Shape())) { + ConversionResultShape* shape = brep.as_compound(); + shape->Serialize(brep_data_); + delete shape; + } else { + for (auto it = brep.begin(); it != brep.end(); ++it) { + std::string part; + it->Shape()->Serialize(part); + if (brep_data_.size()) { + brep_data_ = brep_data_ + "\n---\n" + part; + } else { + brep_data_ = part; + } + } + } + } + } IfcGeom::ConversionResultShape* IfcGeom::Representation::BRep::as_compound(bool force_meters) const { diff --git a/src/ifcgeom/Iterator.h b/src/ifcgeom/Iterator.h index 8190783713..83e10e1065 100644 --- a/src/ifcgeom/Iterator.h +++ b/src/ifcgeom/Iterator.h @@ -753,6 +753,24 @@ namespace IfcGeom { { } + Iterator(const std::string& geometry_library, const IteratorSettings& settings, IfcParse::IfcFile* file) + : settings_(settings) + , ifc_file(file) + , owns_ifc_file(false) + , num_threads_(1) + , geometry_library_(geometry_library) + { + } + + Iterator(const std::string& geometry_library, const IteratorSettings& settings, IfcParse::IfcFile* file, int num_threads) + : settings_(settings) + , ifc_file(file) + , owns_ifc_file(false) + , num_threads_(num_threads) + , geometry_library_(geometry_library) + { + } + ~Iterator() { if (owns_ifc_file) { delete ifc_file; diff --git a/src/ifcgeom/kernels/cgal/CgalConversionResult.cpp b/src/ifcgeom/kernels/cgal/CgalConversionResult.cpp index 05e9861d40..94f3164262 100644 --- a/src/ifcgeom/kernels/cgal/CgalConversionResult.cpp +++ b/src/ifcgeom/kernels/cgal/CgalConversionResult.cpp @@ -102,6 +102,12 @@ void ifcopenshell::geometry::CgalShape::Triangulate(const IfcGeom::IteratorSetti } +void ifcopenshell::geometry::CgalShape::Serialize(std::string& r) const { + std::stringstream sstream; + sstream << shape_; + r = sstream.str(); +} + #include double ifcopenshell::geometry::CgalShape::bounding_box(void *& b) const { diff --git a/src/ifcgeom/kernels/cgal/CgalConversionResult.h b/src/ifcgeom/kernels/cgal/CgalConversionResult.h index 5e9acbf4c4..72d3927a6e 100644 --- a/src/ifcgeom/kernels/cgal/CgalConversionResult.h +++ b/src/ifcgeom/kernels/cgal/CgalConversionResult.h @@ -96,9 +96,7 @@ namespace ifcopenshell { namespace geometry { virtual void Triangulate(const IfcGeom::IteratorSettings& settings, const ifcopenshell::geometry::taxonomy::matrix4& place, IfcGeom::Representation::Triangulation* t, int surface_style_id) const; - virtual void Serialize(std::string&) const { - throw std::runtime_error("Not implemented"); - } + virtual void Serialize(std::string&) const; virtual IfcGeom::ConversionResultShape* clone() const { return new CgalShape(shape_); diff --git a/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.cpp b/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.cpp index 789de9d4ae..f2a66d5838 100644 --- a/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.cpp +++ b/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.cpp @@ -217,6 +217,12 @@ void ifcopenshell::geometry::OpenCascadeShape::Triangulate(const IfcGeom::Iterat BRepTools::Clean(shape_); } +void ifcopenshell::geometry::OpenCascadeShape::Serialize(std::string& r) const { + std::stringstream sstream; + BRepTools::Write(shape_, sstream); + r = sstream.str(); +} + int ifcopenshell::geometry::OpenCascadeShape::surface_genus() const { throw std::runtime_error("Not implemented"); } diff --git a/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.h b/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.h index c7af0ee1c1..bee6e18fa5 100644 --- a/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.h +++ b/src/ifcgeom/kernels/opencascade/OpenCascadeConversionResult.h @@ -49,9 +49,7 @@ namespace ifcopenshell { virtual void Triangulate(const IfcGeom::IteratorSettings& settings, const ifcopenshell::geometry::taxonomy::matrix4& place, IfcGeom::Representation::Triangulation* t, int surface_style_id) const; - virtual void Serialize(std::string&) const { - throw std::runtime_error("Not implemented"); - } + virtual void Serialize(std::string&) const; virtual IfcGeom::ConversionResultShape* clone() const { return new OpenCascadeShape(shape_); diff --git a/src/ifcopenshell-python/ifcopenshell/geom/main.py b/src/ifcopenshell-python/ifcopenshell/geom/main.py index 8cde9af253..4fe6dfe210 100644 --- a/src/ifcopenshell-python/ifcopenshell/geom/main.py +++ b/src/ifcopenshell-python/ifcopenshell/geom/main.py @@ -75,7 +75,7 @@ class settings(ifcopenshell_wrapper.SerializerSettings): # Make sure people are able to use python's platform agnostic paths class iterator(ifcopenshell_wrapper.Iterator): - def __init__(self, settings, file_or_filename, num_threads=1, include=None, exclude=None): + def __init__(self, settings, file_or_filename, num_threads=1, include=None, exclude=None, geometry_library="opencascade"): self.settings = settings if isinstance(file_or_filename, file): file_or_filename = file_or_filename.wrapped_data @@ -105,10 +105,10 @@ class iterator(ifcopenshell_wrapper.Iterator): initializer = ifcopenshell_wrapper.construct_iterator_with_include_exclude self.this = initializer( - self.settings, file_or_filename, include_or_exclude, include is not None, num_threads + geometry_library, self.settings, file_or_filename, include_or_exclude, include is not None, num_threads ) else: - ifcopenshell_wrapper.Iterator.__init__(self, settings, file_or_filename, num_threads) + ifcopenshell_wrapper.Iterator.__init__(self, geometry_library, settings, file_or_filename, num_threads) if has_occ: