diff --git a/src/Mod/Mesh/App/Core/Segmentation.cpp b/src/Mod/Mesh/App/Core/Segmentation.cpp index 2e86fdb17..01d99fb11 100644 --- a/src/Mod/Mesh/App/Core/Segmentation.cpp +++ b/src/Mod/Mesh/App/Core/Segmentation.cpp @@ -108,22 +108,12 @@ bool MeshCurvatureCylindricalSegment::TestFacet (const MeshFacet &rclFacet) cons { for (int i=0; i<3; i++) { const CurvatureInfo& ci = info[rclFacet._aulPoints[i]]; - if (ci.fMaxCurvature > ci.fMinCurvature) { - // convexe - if (fabs(ci.fMinCurvature) > tolerance) - return false; - float diff = ci.fMaxCurvature - curvature; - if (fabs(diff) > tolerance) - return false; - } - else { - // concave - if (fabs(ci.fMaxCurvature) > tolerance) - return false; - float diff = ci.fMinCurvature + curvature; - if (fabs(diff) > tolerance) - return false; - } + float fMax = std::max(fabs(ci.fMaxCurvature), fabs(ci.fMinCurvature)); + float fMin = std::min(fabs(ci.fMaxCurvature), fabs(ci.fMinCurvature)); + if (fMin > toleranceMin) + return false; + if (fabs(fMax - curvature) > toleranceMax) + return false; } return true; @@ -151,9 +141,9 @@ bool MeshCurvatureFreeformSegment::TestFacet (const MeshFacet &rclFacet) const { for (int i=0; i<3; i++) { const CurvatureInfo& ci = info[rclFacet._aulPoints[i]]; - if (fabs(ci.fMinCurvature-c2) > tolerance) + if (fabs(ci.fMinCurvature-c2) > toleranceMin) return false; - if (fabs(ci.fMaxCurvature-c1) > tolerance) + if (fabs(ci.fMaxCurvature-c1) > toleranceMax) return false; } diff --git a/src/Mod/Mesh/App/Core/Segmentation.h b/src/Mod/Mesh/App/Core/Segmentation.h index 561385c1c..c894147ad 100644 --- a/src/Mod/Mesh/App/Core/Segmentation.h +++ b/src/Mod/Mesh/App/Core/Segmentation.h @@ -84,53 +84,63 @@ protected: class MeshExport MeshCurvatureSurfaceSegment : public MeshSurfaceSegment { public: - MeshCurvatureSurfaceSegment(const std::vector& ci, unsigned long minFacets, float tol) - : MeshSurfaceSegment(minFacets), info(ci), tolerance(tol) {} + MeshCurvatureSurfaceSegment(const std::vector& ci, unsigned long minFacets) + : MeshSurfaceSegment(minFacets), info(ci) {} protected: const std::vector& info; - float tolerance; }; class MeshExport MeshCurvaturePlanarSegment : public MeshCurvatureSurfaceSegment { public: MeshCurvaturePlanarSegment(const std::vector& ci, unsigned long minFacets, float tol) - : MeshCurvatureSurfaceSegment(ci, minFacets, tol) {} + : MeshCurvatureSurfaceSegment(ci, minFacets), tolerance(tol) {} virtual bool TestFacet (const MeshFacet &rclFacet) const; + +private: + float tolerance; }; class MeshExport MeshCurvatureCylindricalSegment : public MeshCurvatureSurfaceSegment { public: - MeshCurvatureCylindricalSegment(const std::vector& ci, unsigned long minFacets, float tol, float radius) - : MeshCurvatureSurfaceSegment(ci, minFacets, tol) { curvature = 1/radius;} + MeshCurvatureCylindricalSegment(const std::vector& ci, unsigned long minFacets, + float tolMin, float tolMax, float radius) + : MeshCurvatureSurfaceSegment(ci, minFacets), toleranceMin(tolMin), toleranceMax(tolMax) { curvature = 1/radius;} virtual bool TestFacet (const MeshFacet &rclFacet) const; private: float curvature; + float toleranceMin; + float toleranceMax; }; class MeshExport MeshCurvatureSphericalSegment : public MeshCurvatureSurfaceSegment { public: MeshCurvatureSphericalSegment(const std::vector& ci, unsigned long minFacets, float tol, float radius) - : MeshCurvatureSurfaceSegment(ci, minFacets, tol) { curvature = 1/radius;} + : MeshCurvatureSurfaceSegment(ci, minFacets), tolerance(tol) { curvature = 1/radius;} virtual bool TestFacet (const MeshFacet &rclFacet) const; private: float curvature; + float tolerance; }; class MeshExport MeshCurvatureFreeformSegment : public MeshCurvatureSurfaceSegment { public: - MeshCurvatureFreeformSegment(const std::vector& ci, unsigned long minFacets, float tol, float c1, float c2) - : MeshCurvatureSurfaceSegment(ci, minFacets, tol), c1(c1), c2(c2) {} + MeshCurvatureFreeformSegment(const std::vector& ci, unsigned long minFacets, + float tolMin, float tolMax, float c1, float c2) + : MeshCurvatureSurfaceSegment(ci, minFacets), c1(c1), c2(c2), + toleranceMin(tolMin), toleranceMax(tolMax) {} virtual bool TestFacet (const MeshFacet &rclFacet) const; private: float c1, c2; + float toleranceMin; + float toleranceMax; }; class MeshExport MeshSurfaceVisitor : public MeshFacetVisitor diff --git a/src/Mod/Mesh/App/Mesh.cpp b/src/Mod/Mesh/App/Mesh.cpp index 89f85856a..dec5da73b 100644 --- a/src/Mod/Mesh/App/Mesh.cpp +++ b/src/Mod/Mesh/App/Mesh.cpp @@ -44,6 +44,7 @@ #include "Core/TopoAlgorithm.h" #include "Core/Evaluation.h" #include "Core/Degeneration.h" +#include "Core/Segmentation.h" #include "Core/SetOperations.h" #include "Core/Visitor.h" @@ -1426,48 +1427,21 @@ std::vector MeshObject::getSegmentsFromType(MeshObject::Type type, cons float dev, unsigned long minFacets) const { std::vector segm; - unsigned long startFacet; if (this->_kernel.CountFacets() == 0) return segm; - // reset VISIT flags - MeshCore::MeshAlgorithm cAlgo(this->_kernel); - if (aSegment.isEmpty()) { - cAlgo.ResetFacetFlag(MeshCore::MeshFacet::VISIT); + MeshCore::MeshSegmentAlgorithm finder(this->_kernel); + MeshCore::MeshDistanceSurfaceSegment* surf; + surf = new MeshCore::MeshDistancePlanarSegment(this->_kernel, minFacets, dev); + std::vector surfaces; + surfaces.push_back(surf); + finder.FindSegments(surfaces); + + const std::vector& data = surf->GetSegments(); + for (std::vector::const_iterator it = data.begin(); it != data.end(); ++it) { + segm.push_back(Segment(const_cast(this), *it, false)); } - else { - cAlgo.SetFacetFlag(MeshCore::MeshFacet::VISIT); - cAlgo.ResetFacetsFlag(aSegment.getIndices(), MeshCore::MeshFacet::VISIT); - } - - const MeshCore::MeshFacetArray& rFAry = this->_kernel.GetFacets(); - MeshCore::MeshFacetArray::_TConstIterator iTri = rFAry.begin(); - MeshCore::MeshFacetArray::_TConstIterator iBeg = rFAry.begin(); - MeshCore::MeshFacetArray::_TConstIterator iEnd = rFAry.end(); - - // start from the first not visited facet - cAlgo.CountFacetFlag(MeshCore::MeshFacet::VISIT); - iTri = std::find_if(iTri, iEnd, std::bind2nd(MeshCore::MeshIsNotFlag(), - MeshCore::MeshFacet::VISIT)); - startFacet = iTri - iBeg; - - while (startFacet != ULONG_MAX) { - // collect all facets of the same geometry - std::vector indices; - indices.push_back(startFacet); - MeshCore::MeshPlaneVisitor pv(this->_kernel, startFacet, dev, indices); - this->_kernel.VisitNeighbourFacets(pv, startFacet); - - iTri = std::find_if(iTri, iEnd, std::bind2nd(MeshCore::MeshIsNotFlag(), - MeshCore::MeshFacet::VISIT)); - if (iTri < iEnd) - startFacet = iTri - iBeg; - else - startFacet = ULONG_MAX; - if (indices.size() > minFacets) - segm.push_back(Segment(const_cast(this), indices, false)); - } - + delete surf; return segm; } diff --git a/src/Mod/Mesh/App/MeshPy.xml b/src/Mod/Mesh/App/MeshPy.xml index f29a59730..116979807 100644 --- a/src/Mod/Mesh/App/MeshPy.xml +++ b/src/Mod/Mesh/App/MeshPy.xml @@ -382,10 +382,10 @@ plane if none of its neighours is coplanar. getSegmentsByCurvature(list) -> list The argument list gives a list if tuples where it defines the preferred maximum curvature, -the preferred minumum curvature, the tolerance and the number of minimum faces for the segment. +the preferred minumum curvature, the tolerances and the number of minimum faces for the segment. Example: -c=(1.0, 0.0, 0.1, 500) # search for a cylinder with radius 1.0 -p=(0.0, 0.0, 0.1, 500) # search for a plane +c=(1.0, 0.0, 0.1, 0.1, 500) # search for a cylinder with radius 1.0 +p=(0.0, 0.0, 0.1, 0.1, 500) # search for a plane mesh.getSegmentsByCurvature([c,p]) diff --git a/src/Mod/Mesh/App/MeshPyImp.cpp b/src/Mod/Mesh/App/MeshPyImp.cpp index dd1f0e3e1..a2a1e6302 100644 --- a/src/Mod/Mesh/App/MeshPyImp.cpp +++ b/src/Mod/Mesh/App/MeshPyImp.cpp @@ -1399,9 +1399,10 @@ PyObject* MeshPy::getSegmentsByCurvature(PyObject *args) Py::Tuple t(*it); float c1 = (float)Py::Float(t[0]); float c2 = (float)Py::Float(t[1]); - float tol = (float)Py::Float(t[2]); - int num = (int)Py::Int(t[3]); - segm.push_back(new MeshCore::MeshCurvatureFreeformSegment(meshCurv.GetCurvature(), num, tol, c1, c2)); + float tol1 = (float)Py::Float(t[2]); + float tol2 = (float)Py::Float(t[3]); + int num = (int)Py::Int(t[4]); + segm.push_back(new MeshCore::MeshCurvatureFreeformSegment(meshCurv.GetCurvature(), num, tol1, tol2, c1, c2)); } finder.FindSegments(segm); diff --git a/src/Mod/Mesh/Gui/Segmentation.cpp b/src/Mod/Mesh/Gui/Segmentation.cpp index 962d65f2e..223479c56 100644 --- a/src/Mod/Mesh/Gui/Segmentation.cpp +++ b/src/Mod/Mesh/Gui/Segmentation.cpp @@ -76,7 +76,7 @@ void Segmentation::accept() std::vector segm; if (ui->groupBoxCyl->isChecked()) { segm.push_back(new MeshCore::MeshCurvatureCylindricalSegment - (meshCurv.GetCurvature(), ui->numCyl->value(), ui->tolCyl->value(), ui->radCyl->value())); + (meshCurv.GetCurvature(), ui->numCyl->value(), ui->tol1Cyl->value(), ui->tol2Cyl->value(), ui->radCyl->value())); } if (ui->groupBoxSph->isChecked()) { segm.push_back(new MeshCore::MeshCurvatureSphericalSegment diff --git a/src/Mod/Mesh/Gui/Segmentation.ui b/src/Mod/Mesh/Gui/Segmentation.ui index 129c89873..b6ce13bd8 100644 --- a/src/Mod/Mesh/Gui/Segmentation.ui +++ b/src/Mod/Mesh/Gui/Segmentation.ui @@ -106,12 +106,12 @@ - Tolerance + Tolerance (Flat) - + 0.100000000000000 @@ -121,13 +121,30 @@ + + + Tolerance (Curved) + + + + + + + 0.100000000000000 + + + 0.100000000000000 + + + + Minimum number of faces - + 100000