diff --git a/src/Mod/Part/App/Tools.cpp b/src/Mod/Part/App/Tools.cpp index 67d4f3a46703..1cf05efca5a8 100644 --- a/src/Mod/Part/App/Tools.cpp +++ b/src/Mod/Part/App/Tools.cpp @@ -748,7 +748,7 @@ TopLoc_Location Part::Tools::fromPlacement(const Base::Placement& plm) } bool Part::Tools::isConcave(const TopoDS_Face &face, - const gp_Pnt &pointOfVue, + const std::vector &pointOfVue, const gp_Dir &direction) { bool result = false; @@ -761,26 +761,35 @@ bool Part::Tools::isConcave(const TopoDS_Face &face, // create a line through the point of vue gp_Lin line; - line.SetLocation(pointOfVue); line.SetDirection(direction); // Find intersection of line with the face BRepIntCurveSurface_Inter mkSection; - mkSection.Init(face, line, Precision::Confusion()); - - if (mkSection.More()) { - result = mkSection.Transition() == IntCurveSurface_In; - - // compute normals at the intersection - gp_Pnt iPnt; - gp_Vec dU, dV; - surf->D1(mkSection.U(), mkSection.V(), iPnt, dU, dV); + mkSection.Load(face, Precision::Confusion()); + for (const auto pnt : pointOfVue) { + line.SetLocation(pnt); + Handle(Geom_Line) geomline = new Geom_Line(line); + GeomAdaptor_Curve aCurve(geomline); + mkSection.Init(aCurve); + + if (mkSection.More()) { + result = mkSection.Transition() == IntCurveSurface_In; + + // compute normals at the intersection + gp_Pnt iPnt; + gp_Vec dU, dV; + surf->D1(mkSection.U(), mkSection.V(), iPnt, dU, dV); + + // check normals orientation + gp_Dir dirdU(dU); + result = (dirdU.Angle(line.Direction()) - M_PI_2) <= Precision::Confusion(); + gp_Dir dirdV(dV); + result = result || ((dirdV.Angle(line.Direction()) - M_PI_2) <= Precision::Confusion()); + } - // check normals orientation - gp_Dir dirdU(dU); - result = (dirdU.Angle(line.Direction()) - M_PI_2) <= Precision::Confusion(); - gp_Dir dirdV(dV); - result = result || ((dirdV.Angle(line.Direction()) - M_PI_2) <= Precision::Confusion()); + if (result) { + break; + } } return result; diff --git a/src/Mod/Part/App/Tools.h b/src/Mod/Part/App/Tools.h index eec971dba85c..1bc33f48a654 100644 --- a/src/Mod/Part/App/Tools.h +++ b/src/Mod/Part/App/Tools.h @@ -234,7 +234,7 @@ class PartExport Tools * \return true if the face is concave when shown from pointOfVue and looking into direction * and false otherwise, plane case included. */ - static bool isConcave(const TopoDS_Face &face, const gp_Pnt &pointOfVue, const gp_Dir &direction); + static bool isConcave(const TopoDS_Face &face, const std::vector &pointOfVue, const gp_Dir &direction); }; } //namespace Part diff --git a/src/Mod/Part/App/TopoShapeExpansion.cpp b/src/Mod/Part/App/TopoShapeExpansion.cpp index 31f4f7010580..fac41db7264b 100644 --- a/src/Mod/Part/App/TopoShapeExpansion.cpp +++ b/src/Mod/Part/App/TopoShapeExpansion.cpp @@ -4244,11 +4244,18 @@ TopoShape& TopoShape::makeElementPrismUntil(const TopoShape& _base, BRepFeat_MakePrism PrismMaker; // don't remove limits of concave face - if (checkLimits && __uptoface.shapeType(true) == TopAbs_FACE){ + if (checkLimits && __uptoface.shapeType(true) == TopAbs_FACE) { + // get all vertexes of the sketch as the COG alone may fail to intersect the face + std::vector pnts; + for (TopExp_Explorer xp(profile.getShape(), TopAbs_VERTEX); xp.More(); xp.Next()) { + pnts.push_back(BRep_Tool::Pnt(TopoDS::Vertex(xp.Current()))); + } + Base::Vector3d vCog; profile.getCenterOfGravity(vCog); - gp_Pnt pCog(vCog.x, vCog.y, vCog.z); - checkLimits = ! Part::Tools::isConcave(TopoDS::Face(__uptoface.getShape()), pCog , direction); + gp_Pnt cog(vCog.x, vCog.y, vCog.z); + pnts.push_back(cog); + checkLimits = !Part::Tools::isConcave(TopoDS::Face(__uptoface.getShape()), pnts , direction); } TopoShape _uptoface(__uptoface);