Mesh segmentation
This commit is contained in:
parent
a87f558125
commit
d6b6f6b379
|
@ -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<float>(fabs(ci.fMaxCurvature), fabs(ci.fMinCurvature));
|
||||
float fMin = std::min<float>(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;
|
||||
}
|
||||
|
||||
|
|
|
@ -84,53 +84,63 @@ protected:
|
|||
class MeshExport MeshCurvatureSurfaceSegment : public MeshSurfaceSegment
|
||||
{
|
||||
public:
|
||||
MeshCurvatureSurfaceSegment(const std::vector<CurvatureInfo>& ci, unsigned long minFacets, float tol)
|
||||
: MeshSurfaceSegment(minFacets), info(ci), tolerance(tol) {}
|
||||
MeshCurvatureSurfaceSegment(const std::vector<CurvatureInfo>& ci, unsigned long minFacets)
|
||||
: MeshSurfaceSegment(minFacets), info(ci) {}
|
||||
|
||||
protected:
|
||||
const std::vector<CurvatureInfo>& info;
|
||||
float tolerance;
|
||||
};
|
||||
|
||||
class MeshExport MeshCurvaturePlanarSegment : public MeshCurvatureSurfaceSegment
|
||||
{
|
||||
public:
|
||||
MeshCurvaturePlanarSegment(const std::vector<CurvatureInfo>& 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<CurvatureInfo>& ci, unsigned long minFacets, float tol, float radius)
|
||||
: MeshCurvatureSurfaceSegment(ci, minFacets, tol) { curvature = 1/radius;}
|
||||
MeshCurvatureCylindricalSegment(const std::vector<CurvatureInfo>& 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<CurvatureInfo>& 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<CurvatureInfo>& ci, unsigned long minFacets, float tol, float c1, float c2)
|
||||
: MeshCurvatureSurfaceSegment(ci, minFacets, tol), c1(c1), c2(c2) {}
|
||||
MeshCurvatureFreeformSegment(const std::vector<CurvatureInfo>& 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
|
||||
|
|
|
@ -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<Segment> MeshObject::getSegmentsFromType(MeshObject::Type type, cons
|
|||
float dev, unsigned long minFacets) const
|
||||
{
|
||||
std::vector<Segment> 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<MeshCore::MeshSurfaceSegment*> surfaces;
|
||||
surfaces.push_back(surf);
|
||||
finder.FindSegments(surfaces);
|
||||
|
||||
const std::vector<MeshCore::MeshSegment>& data = surf->GetSegments();
|
||||
for (std::vector<MeshCore::MeshSegment>::const_iterator it = data.begin(); it != data.end(); ++it) {
|
||||
segm.push_back(Segment(const_cast<MeshObject*>(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>(),
|
||||
MeshCore::MeshFacet::VISIT));
|
||||
startFacet = iTri - iBeg;
|
||||
|
||||
while (startFacet != ULONG_MAX) {
|
||||
// collect all facets of the same geometry
|
||||
std::vector<unsigned long> 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>(),
|
||||
MeshCore::MeshFacet::VISIT));
|
||||
if (iTri < iEnd)
|
||||
startFacet = iTri - iBeg;
|
||||
else
|
||||
startFacet = ULONG_MAX;
|
||||
if (indices.size() > minFacets)
|
||||
segm.push_back(Segment(const_cast<MeshObject*>(this), indices, false));
|
||||
}
|
||||
|
||||
delete surf;
|
||||
return segm;
|
||||
}
|
||||
|
||||
|
|
|
@ -382,10 +382,10 @@ plane if none of its neighours is coplanar.</UserDocu>
|
|||
<Documentation>
|
||||
<UserDocu>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])
|
||||
</UserDocu>
|
||||
</Documentation>
|
||||
|
|
|
@ -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);
|
||||
|
|
|
@ -76,7 +76,7 @@ void Segmentation::accept()
|
|||
std::vector<MeshCore::MeshSurfaceSegment*> 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
|
||||
|
|
|
@ -106,12 +106,12 @@
|
|||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="label_4">
|
||||
<property name="text">
|
||||
<string>Tolerance</string>
|
||||
<string>Tolerance (Flat)</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="1">
|
||||
<widget class="QDoubleSpinBox" name="tolCyl">
|
||||
<widget class="QDoubleSpinBox" name="tol1Cyl">
|
||||
<property name="singleStep">
|
||||
<double>0.100000000000000</double>
|
||||
</property>
|
||||
|
@ -121,13 +121,30 @@
|
|||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="label_9">
|
||||
<property name="text">
|
||||
<string>Tolerance (Curved)</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<widget class="QDoubleSpinBox" name="tol2Cyl">
|
||||
<property name="singleStep">
|
||||
<double>0.100000000000000</double>
|
||||
</property>
|
||||
<property name="value">
|
||||
<double>0.100000000000000</double>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QLabel" name="label_5">
|
||||
<property name="text">
|
||||
<string>Minimum number of faces</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<item row="3" column="1">
|
||||
<widget class="QSpinBox" name="numCyl">
|
||||
<property name="maximum">
|
||||
<number>100000</number>
|
||||
|
|
Loading…
Reference in New Issue
Block a user