Updated the mc simplifier to the new framework of local optimization...

This commit is contained in:
Paolo Cignoni cignoni 2011-06-17 13:37:56 +00:00
parent b558d2f4eb
commit 9061a96f12
2 changed files with 54 additions and 45 deletions

View File

@ -527,12 +527,11 @@ void Process(vcg::CallBackPos *cb=0)
}; //end PlyMC class
template < class MeshType>
class PlyMCTriEdgeCollapse: public MCTriEdgeCollapse< MeshType, PlyMCTriEdgeCollapse<MeshType> > {
template < class MeshType, class VertexPair>
class PlyMCTriEdgeCollapse: public MCTriEdgeCollapse< MeshType, VertexPair, PlyMCTriEdgeCollapse<MeshType,VertexPair> > {
public:
typedef MCTriEdgeCollapse< MeshType, PlyMCTriEdgeCollapse > MCTEC;
typedef typename MeshType::VertexType::EdgeType EdgeType;
inline PlyMCTriEdgeCollapse( const EdgeType &p, int i) :MCTEC(p,i){}
typedef MCTriEdgeCollapse< MeshType, VertexPair, PlyMCTriEdgeCollapse > MCTEC;
inline PlyMCTriEdgeCollapse( const VertexPair &p, int i, BaseParameterClass *pp) :MCTEC(p,i,pp){}
};
@ -540,13 +539,15 @@ template < class MeshType>
template< class MeshType>
void MCSimplify( MeshType &m, float absoluteError, bool preserveBB, vcg::CallBackPos *cb)
{
typedef PlyMCTriEdgeCollapse<MeshType> MyColl;
typedef PlyMCTriEdgeCollapse<MeshType,BasicVertexPair<typename MeshType::VertexType> > MyColl;
tri::UpdateBounding<MeshType>::Box(m);
tri::UpdateTopology<MeshType>::VertexFace(m);
vcg::LocalOptimization<MeshType> DeciSession(m);
MyColl::bb()=m.bbox;
MyColl::preserveBBox()=preserveBB;
TriEdgeCollapseMCParameter pp;
pp.bb=m.bbox;
pp.preserveBBox=preserveBB;
vcg::LocalOptimization<MeshType> DeciSession(m,&pp);
if(absoluteError==0)
{
// guess the mc side.
@ -584,7 +585,7 @@ void MCSimplify( MeshType &m, float absoluteError, bool preserveBB, vcg::CallBac
char buf[1024];
DeciSession.template Init< MyColl > ();
MyColl::areaThr()=TargetError*TargetError;
pp.areaThr=TargetError*TargetError;
DeciSession.SetTimeBudget(1.0f);
if(TargetError < std::numeric_limits<float>::max() ) DeciSession.SetTargetMetric(TargetError);
while(DeciSession.DoOptimization() && DeciSession.currMetric < TargetError)

View File

@ -9,66 +9,73 @@
#ifndef __TRI_EDGE_COLLAPSE_MC__
#define __TRI_EDGE_COLLAPSE_MC__
#include<vcg/simplex/face/topology.h>
template<class MCTriMesh, class MYTYPE >
class TriEdgeCollapseMCParameter : public BaseParameterClass
{
public:
Box3f bb;
bool preserveBBox;
float areaThr;
void SetDefaultParams()
{
bb.SetNull();
preserveBBox=true;
areaThr=0;
}
TriEdgeCollapseMCParameter() {SetDefaultParams();}
};
template<class MCTriMesh, class VertexPair, class MYTYPE >
// Specialized Simplification classes for removing all small pieces on meshes.
class MCTriEdgeCollapse: public tri::TriEdgeCollapse< MCTriMesh, MYTYPE> {
class MCTriEdgeCollapse: public tri::TriEdgeCollapse< MCTriMesh, VertexPair, MYTYPE> {
public:
typedef typename MCTriMesh::VertexPointer VertexPointer;
typedef typename MCTriMesh::VertexType::EdgeType EdgeType;
typedef typename MCTriMesh::FaceType FaceType;
typedef typename MCTriMesh::VertexType::CoordType CoordType;
typedef typename MCTriMesh::VertexType::ScalarType ScalarType;
static Box3f &bb() {
static Box3f bb;
return bb;
}
static bool &preserveBBox() {
static bool _preserveBBox=true;
return _preserveBBox;
}
inline MCTriEdgeCollapse( const EdgeType &p, int mark)
inline MCTriEdgeCollapse( const VertexPair &p, int mark, BaseParameterClass *pp)
{
this->localMark = mark;
this->pos=p;
this->_priority = ComputePriority();
this->_priority = ComputePriority(pp);
}
// The priority is simply the edge lenght,
// but we consider collapsing edges that lies on one plane of the MC grid.
virtual inline ScalarType ComputePriority()
virtual inline ScalarType ComputePriority(BaseParameterClass *_pp)
{
const CoordType & p0 = this->pos.V(0)->cP();
const CoordType & p1 = this->pos.V(1)->cP();
TriEdgeCollapseMCParameter *pp=(TriEdgeCollapseMCParameter *)_pp;
const CoordType & p0 = this->pos.V(0)->cP();
const CoordType & p1 = this->pos.V(1)->cP();
int diffCnt=0;
if( (p0[0] != p1[0]) ) diffCnt++;
if( (p0[1] != p1[1]) ) diffCnt++;
if( (p0[2] != p1[2]) ) diffCnt++;
int diffCnt=0;
if( (p0[0] != p1[0]) ) diffCnt++;
if( (p0[1] != p1[1]) ) diffCnt++;
if( (p0[2] != p1[2]) ) diffCnt++;
// non MC plane collapse return highest cost
// if(diffCnt>2) return this->_priority=std::numeric_limits<float>::max() ;
if(preserveBBox())
if(pp->preserveBBox)
{
const Box3f &bb=pp->bb;
// collapse on the bbox border. Avoid it.
if(p0[0]==bb().min[0] || p0[0]==bb().max[0]) return this->_priority=std::numeric_limits<float>::max() ;
if(p0[1]==bb().min[1] || p0[1]==bb().max[1]) return this->_priority=std::numeric_limits<float>::max() ;
if(p0[2]==bb().min[2] || p0[2]==bb().max[2]) return this->_priority=std::numeric_limits<float>::max() ;
if(p1[0]==bb().min[0] || p1[0]==bb().max[0]) return this->_priority=std::numeric_limits<float>::max() ;
if(p1[1]==bb().min[1] || p1[1]==bb().max[1]) return this->_priority=std::numeric_limits<float>::max() ;
if(p1[2]==bb().min[2] || p1[2]==bb().max[2]) return this->_priority=std::numeric_limits<float>::max() ;
if(p0[0]==bb.min[0] || p0[0]==bb.max[0]) return this->_priority=std::numeric_limits<float>::max() ;
if(p0[1]==bb.min[1] || p0[1]==bb.max[1]) return this->_priority=std::numeric_limits<float>::max() ;
if(p0[2]==bb.min[2] || p0[2]==bb.max[2]) return this->_priority=std::numeric_limits<float>::max() ;
if(p1[0]==bb.min[0] || p1[0]==bb.max[0]) return this->_priority=std::numeric_limits<float>::max() ;
if(p1[1]==bb.min[1] || p1[1]==bb.max[1]) return this->_priority=std::numeric_limits<float>::max() ;
if(p1[2]==bb.min[2] || p1[2]==bb.max[2]) return this->_priority=std::numeric_limits<float>::max() ;
}
return this->_priority=Distance(p0,p1);
}
static float & areaThr(){
static float t;
return t;
}
inline void Execute(MCTriMesh &m)
inline void Execute(MCTriMesh &m,BaseParameterClass *)
{
const CoordType & p0 = this->pos.V(0)->cP();
const CoordType & p1 = this->pos.V(1)->cP();
@ -98,7 +105,8 @@ class MCTriEdgeCollapse: public tri::TriEdgeCollapse< MCTriMesh, MYTYPE> {
// assert( (p0[0]==p1[0]) ||
// (p0[1]==p1[1]) ||
// (p0[2]==p1[2]) );
DoCollapse(m, this->pos, MidPoint);
// DoCollapse(m, this->pos, MidPoint);
vcg::tri::EdgeCollapser<MCTriMesh,VertexPair>::Do(m, this->pos, MidPoint);
}