So the idea would be to make a new class derived on the Visitor class for each "optimization" (for ex: finding coplanar faces, finding cylinders, etc)
Yes, we can have for each geometry type an own visitor class.
And then you would simply invoke VisitNeighbourFacets
Yes, but some prerequisites must be met. The mesh facets (class MeshFacet) have a flag "VISIT" which must be reset first,
Code: Select all
// reset VISIT flag
MeshKernel kernel = ...
MeshAlgorithm cAlg(kernel);
cAlg.ResetFacetFlag(MeshFacet::VISIT);
And the algorithm inside which we call VisitNeighbourFacets should look like this:
Code: Select all
// reset VISIT flag
MeshKernel kernel = ...
const MeshFacetArray& rFAry = kernel.GetFacets();
MeshFacetArray::_TConstIterator iTri = rFAry.begin();
MeshFacetArray::_TConstIterator iBeg = rFAry.begin();
MeshFacetArray::_TConstIterator iEnd = rFAry.end();
MeshAlgorithm cAlg(kernel);
cAlg.ResetFacetFlag(MeshFacet::VISIT);
unsigned long ulStartFacet=0, ulVisited=0;
while (ulStartFacet != ULONG_MAX) {
ulVisited = kernel.VisitNeighbourFacets(ourVisitor, ulStartFacet) + 1;
// get the next unvisited facet
iTri = std::find_if(iTri, iEnd, std::bind2nd(MeshIsNotFlag<MeshFacet>(), MeshFacet::VISIT));
if (iTri < iEnd)
ulStartFacet = iTri - iBeg; // this is the new index
else
ulStartFacet = ULONG_MAX; // OK, we reached the end
}
What is the eigenvectors method you mentioned?
This is a method to compute a best-fit-plane in a list of 3d points. The approach is to find a plane which minimizes the sum of squared distances to the points. This problem leads to a symmetric 3x3 matrix (the so called co-variance matrix) where the eigenvector to the smallest eigenvalue is the normal of the plane. The plane always lies in the gravity center of the points.
We have an implementation in Mesh/App/Core/Approximation -- the class PlaneFit.
The same idea could be also applied to cylinders, spheres, ... as done by the WildMagic library. But these algorithms are quite unreliable.
Just one more question: the Visitor will return the number of facets visited, but the cool thing would be to get several mesh segments, so you can create a separate mesh from each one and feed the ShapeFromMesh stuff... I don't see well how to do that... Can you give me some starting point?
Yes, the visitor must decide if the current facet belongs to this type of geometry or not. If none of the neighbours of the inspected "good"facets pass the test the visitor must return false to stop the algorithm. Now we have one segment that describes the geometry.
The best would be to store the indexes of the facets in an array (std::vector).
I think the best would be to store the segments in the MeshObject class. This is a higher-level object and owns a MeshKernel. There we can hold the segment information as I did it with the improved OBJ reader.
Ah, about the "mesh approximation software" I talked about, I was referring to FEM software, but looking better at it I see it's actually completely different...
I don't have much experience with FEM. So, I cannot say what kind of approximation algorithms are used in this field.