23#ifndef VCL_ALGORITHMS_MESH_CLEAN_H
24#define VCL_ALGORITHMS_MESH_CLEAN_H
26#include <vclib/algorithms/mesh/sort.h>
27#include <vclib/algorithms/mesh/stat/topology.h>
29#include <vclib/algorithms/core.h>
30#include <vclib/mesh.h>
31#include <vclib/space/complex.h>
55template<
typename VertexPo
inter>
56class VertPositionComparator
59 inline bool operator()(
const VertexPointer& a,
const VertexPointer& b)
61 return (a->position() == b->position()) ?
63 (a->position() < b->position());
79template<
typename IndexType,
typename SentinelType,
int N>
80class SortedIndexContainer
83 SortedIndexContainer() {}
85 template<Range RangeType>
86 SortedIndexContainer(SentinelType s, RangeType rng) : s(s), v(rng)
88 std::sort(v.begin(), v.end());
91 bool operator<(
const SortedIndexContainer& s)
const
93 if constexpr (N >= 0) {
94 for (uint i = 0; i < N; ++i) {
101 for (uint i = 0; i < v.size() && i < s.v.size(); ++i) {
103 return v[i] < s.v[i];
105 return v.size() < s.v.size();
109 bool operator==(
const SortedIndexContainer& s)
const
111 if constexpr (N >= 0) {
112 for (uint i = 0; i < N; ++i) {
119 if (v.size() != s.v.size())
121 for (uint i = 0; i < v.size(); ++i) {
129 SentinelType sentinel()
const {
return s; }
132 Vector<IndexType, N> v;
156template<MeshConcept MeshType>
159 using VertexType = MeshType::VertexType;
169 if (
n <
m.vertexNumber()) {
174 for (
const VertexType& v :
m.vertices()) {
176 m.deleteVertex(
m.index(v));
210template<MeshConcept MeshType>
213 using VertexType = MeshType::VertexType;
216 if (
m.vertexNumber() == 0)
227 std::vector<VertexPointer>
perm(
m.vertexNumber());
231 for (VertexType& v :
m.vertices())
236 std::execution::par_unseq,
239 detail::VertPositionComparator<VertexPointer>());
251 m.deleteVertex(
m.index(
perm[
j]));
295template<FaceMeshConcept MeshType>
298 using VertexType = MeshType::VertexType;
299 using FaceType = MeshType::FaceType;
303 std::vector<detail::SortedIndexContainer<
306 FaceType::VERTEX_NUMBER>>
309 for (FaceType& f :
m.faces()) {
310 fvec.emplace_back(&f, f.vertices());
314 std::sort(std::execution::par_unseq,
fvec.begin(),
fvec.end());
321 m.deleteFace(
fvec[
i].sentinel());
350template<MeshConcept MeshType>
353 using VertexType = MeshType::VertexType;
359 for (VertexType& v :
m.vertices()) {
360 if (v.position().isDegenerate()) {
369 using FaceType = MeshType::FaceType;
371 for (FaceType& f :
m.faces()) {
373 for (VertexType* v : f.vertices()) {
410template<FaceMeshConcept MeshType>
414 using FaceType = MeshType::FaceType;
418 for (FaceType& f :
m.faces()) {
420 for (uint
i = 0;
i < f.vertexNumber() && !
deg; ++
i) {
421 if (f.vertex(
i) == f.vertexMod(
i + 1)) {
423 m.deleteFace(
m.index(f));
A class representing a box in N-dimensional space.
Definition box.h:46
PointT size() const
Computes the size of the box.
Definition box.h:267
HasFaces concepts is satisfied when at least one of its template types is (or inherits from) a vcl::m...
Definition face_container.h:1389
constexpr uint UINT_NULL
The UINT_NULL value represent a null value of uint that is the maximum value that can be represented ...
Definition base.h:48
uint removeUnreferencedVertices(MeshType &m)
Marks as deleted all the non-deleted unreferenced vertices of the mesh.
Definition clean.h:157
uint removeDegeneratedVertices(MeshType &m, bool deleteAlsoFaces)
Removes all vertices that have position with invalid floating point values (NaN or inf).
Definition clean.h:351
uint removeDegenerateFaces(MeshType &m)
Removes all degenerate faces from the input mesh.
Definition clean.h:411
uint removeDuplicatedFaces(MeshType &m)
Removes all duplicate faces of the mesh by looking only at their vertex references.
Definition clean.h:296
uint removeDuplicatedVertices(MeshType &m)
Marks as deleted the duplicate vertices of the mesh, by looking only at their spatial positions.
Definition clean.h:211