removed the flag to fix irregulars on laplacian and created a version of LaplacianReproject that does not need a triangular mesh

This commit is contained in:
nico 2018-11-21 22:57:31 +11:00
parent 8afa67c9be
commit 06f8a69ee1
1 changed files with 94 additions and 85 deletions

View File

@ -542,33 +542,33 @@ public:
AvVert[i]*(1-Damp); AvVert[i]*(1-Damp);
} }
// //then reproject on border // //then reproject on border
// for (size_t i=0;i<poly_m.vert.size();i++) // for (size_t i=0;i<poly_m.vert.size();i++)
// { // {
// if (!poly_m.vert[i].IsB())continue; // if (!poly_m.vert[i].IsB())continue;
// if (poly_m.vert[i].IsS())continue; // if (poly_m.vert[i].IsS())continue;
// CoordType testPos=poly_m.vert[i].P(); // CoordType testPos=poly_m.vert[i].P();
// ScalarType minD=std::numeric_limits<ScalarType>::max(); // ScalarType minD=std::numeric_limits<ScalarType>::max();
// CoordType closPos; // CoordType closPos;
// for (size_t j=0;j<tri_mesh.face.size();j++) // for (size_t j=0;j<tri_mesh.face.size();j++)
// for (size_t k=0;k<3;k++) // for (size_t k=0;k<3;k++)
// { // {
// if (tri_mesh.face[j].FFp(k)!=(&tri_mesh.face[j]))continue; // if (tri_mesh.face[j].FFp(k)!=(&tri_mesh.face[j]))continue;
// CoordType P0,P1; // CoordType P0,P1;
// P0.Import(tri_mesh.face[j].cP0(k)); // P0.Import(tri_mesh.face[j].cP0(k));
// P1.Import(tri_mesh.face[j].cP1(k)); // P1.Import(tri_mesh.face[j].cP1(k));
// vcg::Segment3<ScalarType> Seg(P0,P1); // vcg::Segment3<ScalarType> Seg(P0,P1);
// ScalarType testD; // ScalarType testD;
// CoordType closTest; // CoordType closTest;
// vcg::SegmentPointDistance(Seg,testPos,closTest,testD); // vcg::SegmentPointDistance(Seg,testPos,closTest,testD);
// if (testD>minD)continue; // if (testD>minD)continue;
// minD=testD; // minD=testD;
// closPos=closTest; // closPos=closTest;
// } // }
// poly_m.vert[i].P()=closPos; // poly_m.vert[i].P()=closPos;
// } // }
ReprojectBorder(poly_m,tri_mesh); ReprojectBorder(poly_m,tri_mesh);
} }
} }
@ -595,7 +595,6 @@ public:
template <class TriMeshType> template <class TriMeshType>
static void LaplacianReproject(PolyMeshType &poly_m, static void LaplacianReproject(PolyMeshType &poly_m,
TriMeshType &tri_mesh, TriMeshType &tri_mesh,
bool fixIrr=false,
int nstep=100, int nstep=100,
ScalarType Damp=0.5) ScalarType Damp=0.5)
{ {
@ -608,8 +607,6 @@ public:
ScalarType MaxD=tri_mesh.bbox.Diag(); ScalarType MaxD=tri_mesh.bbox.Diag();
if (fixIrr)
poly_m.NumIrregular(true);
for (int s=0;s<nstep;s++) for (int s=0;s<nstep;s++)
{ {
std::vector<CoordType> AvVert; std::vector<CoordType> AvVert;
@ -618,7 +615,6 @@ public:
for (size_t i=0;i<poly_m.vert.size();i++) for (size_t i=0;i<poly_m.vert.size();i++)
{ {
if (poly_m.vert[i].IsB())continue; if (poly_m.vert[i].IsB())continue;
if (fixIrr && (poly_m.vert[i].IsS()))continue;
poly_m.vert[i].P()=poly_m.vert[i].P()*Damp+ poly_m.vert[i].P()=poly_m.vert[i].P()*Damp+
AvVert[i]*(1-Damp); AvVert[i]*(1-Damp);
} }
@ -640,8 +636,21 @@ public:
} }
/*! \brief This function laplacian smooth of a polygonal mesh static void LaplacianReproject(PolyMeshType &poly_m,
*/ int nstep=100,
ScalarType Damp=0.5)
{
//transform into triangular
TempMesh GuideSurf;
//vcg::tri::PolygonSupport<TempMesh,PolyMeshType>:(GuideSurf,poly_m);
TriangulateToTriMesh<TempMesh>(poly_m,GuideSurf);
vcg::tri::UpdateBounding<TempMesh>::Box(GuideSurf);
vcg::tri::UpdateNormal<TempMesh>::PerVertexNormalizedPerFace(GuideSurf);
vcg::tri::UpdateTopology<TempMesh>::FaceFace(GuideSurf);
vcg::tri::UpdateFlags<TempMesh>::FaceBorderFromFF(GuideSurf);
LaplacianReproject(poly_m,GuideSurf,nstep,Damp=0.5);
}
static void Laplacian(PolyMeshType &poly_m, static void Laplacian(PolyMeshType &poly_m,
bool FixS=false, bool FixS=false,
int nstep=10, int nstep=10,
@ -685,8 +694,8 @@ public:
//first select sharp features //first select sharp features
if (SharpDeg>0) if (SharpDeg>0)
{ {
for (size_t i=0;i<poly_m.face.size();i++) for (int i=0;i<(int)poly_m.face.size();i++)
for (size_t j=0;j<poly_m.face[i].VN();j++) for (int j=0;j<(int)poly_m.face[i].VN();j++)
{ {
//check only one side //check only one side
if ((&poly_m.face[i])>=poly_m.face[i].FFp(j))continue; if ((&poly_m.face[i])>=poly_m.face[i].FFp(j))continue;
@ -862,14 +871,14 @@ public:
{ {
//reproject on border later //reproject on border later
if (poly_m.vert[i].IsB())continue; if (poly_m.vert[i].IsB())continue;
typename TempMesh::CoordType testPos; typename TempMesh::CoordType testPos;
testPos.Import(poly_m.vert[i].P()); testPos.Import(poly_m.vert[i].P());
typename TempMesh::CoordType closestPt; typename TempMesh::CoordType closestPt;
typename TempMesh::ScalarType minDist; typename TempMesh::ScalarType minDist;
typename TempMesh::FaceType *f=NULL; typename TempMesh::FaceType *f=NULL;
typename TempMesh::CoordType norm,ip; typename TempMesh::CoordType norm,ip;
f=vcg::tri::GetClosestFaceBase(GuideSurf,grid,testPos,MaxD,minDist,closestPt,norm,ip); f=vcg::tri::GetClosestFaceBase(GuideSurf,grid,testPos,MaxD,minDist,closestPt,norm,ip);
poly_m.vert[i].P()=closestPt; poly_m.vert[i].P()=closestPt;
} }
//then reprojec the border //then reprojec the border
ReprojectBorder(poly_m,GuideSurf); ReprojectBorder(poly_m,GuideSurf);
@ -895,14 +904,14 @@ public:
{ {
//reproject on border later //reproject on border later
if (poly_m.vert[i].IsB())continue; if (poly_m.vert[i].IsB())continue;
typename TriMesh::CoordType testPos; typename TriMesh::CoordType testPos;
testPos.Import(poly_m.vert[i].P()); testPos.Import(poly_m.vert[i].P());
typename TriMesh::CoordType closestPt; typename TriMesh::CoordType closestPt;
typename TriMesh::ScalarType minDist; typename TriMesh::ScalarType minDist;
typename TriMesh::FaceType *f=NULL; typename TriMesh::FaceType *f=NULL;
typename TriMesh::CoordType norm,ip; typename TriMesh::CoordType norm,ip;
f=vcg::tri::GetClosestFaceBase(target,grid,testPos,MaxD,minDist,closestPt,norm,ip); f=vcg::tri::GetClosestFaceBase(target,grid,testPos,MaxD,minDist,closestPt,norm,ip);
poly_m.vert[i].P()=closestPt; poly_m.vert[i].P()=closestPt;
} }
//then reprojec the border //then reprojec the border
ReprojectBorder(poly_m,target); ReprojectBorder(poly_m,target);
@ -1291,8 +1300,8 @@ public:
} }
static void MergeAlongEdge(PolyMeshType &poly_m, static void MergeAlongEdge(PolyMeshType &poly_m,
FaceType &f, FaceType &f,
const size_t &EdgeI) const size_t &EdgeI)
{ {
//cannot be a border //cannot be a border
assert(f.FFp(EdgeI)!=&f); assert(f.FFp(EdgeI)!=&f);
@ -1336,46 +1345,46 @@ public:
//then cycle and collapse //then cycle and collapse
do{ do{
for (size_t i=0;i<poly_m.face.size();i++) for (size_t i=0;i<poly_m.face.size();i++)
{
if (poly_m.face[i].IsD())continue;
for (size_t j=0;j<poly_m.face[i].VN();j++)
{ {
CoordType P0=poly_m.face[i].P0(j); if (poly_m.face[i].IsD())continue;
CoordType P1=poly_m.face[i].P1(j); for (size_t j=0;j<poly_m.face[i].VN();j++)
std::pair<CoordType,CoordType> key(std::min(P0,P1),std::max(P0,P1)); {
if (NeedMerge.count(key)==0)continue; CoordType P0=poly_m.face[i].P0(j);
CoordType P1=poly_m.face[i].P1(j);
std::pair<CoordType,CoordType> key(std::min(P0,P1),std::max(P0,P1));
if (NeedMerge.count(key)==0)continue;
//do the merge //do the merge
MergeAlongEdge(poly_m,poly_m.face[i],j); MergeAlongEdge(poly_m,poly_m.face[i],j);
//remove it //remove it
NeedMerge.erase(key); NeedMerge.erase(key);
break; break;
}
} }
} vcg::tri::Allocator<PolyMeshType>::CompactEveryVector(poly_m);
vcg::tri::Allocator<PolyMeshType>::CompactEveryVector(poly_m);
}while (!NeedMerge.empty()); }while (!NeedMerge.empty());
} }
static void Triangulate(PolyMeshType &poly_m, bool alsoTriangles = true) static void Triangulate(PolyMeshType &poly_m, bool alsoTriangles = true)
{ {
size_t size0 = poly_m.face.size(); size_t size0 = poly_m.face.size();
if (alsoTriangles) if (alsoTriangles)
{ {
for (size_t i=0; i<size0; i++) for (size_t i=0; i<size0; i++)
Triangulate(poly_m, i); Triangulate(poly_m, i);
} }
else else
{ {
for (size_t i=0; i<size0; i++) for (size_t i=0; i<size0; i++)
{ {
if (poly_m.face[i].VN() > 3) if (poly_m.face[i].VN() > 3)
{ {
Triangulate(poly_m, i); Triangulate(poly_m, i);
} }
} }
} }
} }
}; };