Re-sew non-manifold operands; interior loop re-orientations affect edge identity #8140

This commit is contained in:
Thomas Krijnen
2026-06-04 21:37:41 +02:00
parent 0eedc7bdc2
commit 093fd0e273
@@ -136,20 +136,36 @@ bool IfcGeom::OpenCascadeKernel::convert_openings(const express::Base& entity, c
for (auto& entity_part : parts) {
bool is_manifold = util::is_manifold(entity_part);
if (!is_manifold) {
// force sewing, edge identity might have been mudied by FixAdvFace.FixOrientation.MSG5 to fix interior loop winding order
TopTools_ListOfShape list;
IfcGeom::util::shape_to_face_list(entity_part, list);
IfcGeom::util::create_solid_from_faces(list, entity_part, settings_.get<settings::Precision>().get(), true);
is_manifold = util::is_manifold(entity_part);
if (is_manifold) {
logger::warning("Successfully sewed non-manifold first operand", entity);
}
}
if (!is_manifold) {
if (settings_.get<settings::MakeVolume>().get()) {
BOPAlgo_MakerVolume mv;
mv.AddArgument(entity_part);
mv.Perform();
if (mv.HasErrors()) {
logger::warning("Non-manifold first operand, --make-volume failed");
} else {
entity_part = mv.Shape();
is_manifold = util::is_manifold(entity_part);
mv.SetAvoidInternalShapes(true);
try {
mv.Perform();
if (mv.HasErrors()) {
logger::warning("Non-manifold first operand, --make-volume failed", entity);
} else {
entity_part = mv.Shape();
is_manifold = util::is_manifold(entity_part);
logger::warning("Successfully detected exterior volume to non-manifold first operand", entity);
}
} catch (const Standard_Failure& e) {
logger::warning("MakeVolume failed: " + std::string(e.GetMessageString()), entity);
}
}
if (!is_manifold) {
logger::warning("Non-manifold first operand, use --make-volume to try and make manifold");
} else {
logger::warning("Non-manifold first operand, use --make-volume to try and make manifold", entity);
}
}