Subversion Repositories gelsvn

Rev

Rev 129 | Go to most recent revision | Blame | Last modification | View Log | RSS feed

#include <vector>
#include "CGLA/Mat3x3f.h"
#include "CGLA/Vec2f.h"
#include "Face.h"
#include "Manifold.h"
#include "FaceCirculator.h"

using namespace CGLA;
using namespace std;

namespace HMesh
{
        FaceIter get_null_face_iter()
        {
                static FaceList l;
                return l.end();
        }
        
        template<class R>
        Face_template<R>::Face_template(): 
        last(NULL_HALFEDGE_ITER),
        touched(0)
        {}
        
        int no_edges(FaceIter f)
        {
                FaceCirculator fc(f);
                while(!fc.end()) ++fc;
                return fc.no_steps();
        }
        
        Vec3f normal(FaceIter f)
        {
                vector<Vec3f> v;
                FaceCirculator fc(f);
                int k;
                for(k=0;!fc.end();++fc,++k)
                {
                        Vec3f p = fc.get_vertex()->pos;
                        v.push_back(p);
                }
                Vec3f norm(0);
                for(int i=0;i<k;++i)
                {
                        norm[0] += (v[i][1]-v[(i+1)%k][1])*(v[i][2]+v[(i+1)%k][2]);
                        norm[1] += (v[i][2]-v[(i+1)%k][2])*(v[i][0]+v[(i+1)%k][0]);
                        norm[2] += (v[i][0]-v[(i+1)%k][0])*(v[i][1]+v[(i+1)%k][1]);
                }
                float l = norm.length();
                if(l>0.0f)
                        norm /= l;
                return norm;
        }
        
        float area(FaceIter f)
        {
                FaceCirculator fc(f);
                int k;
                
                // M is a matrix that projects a vector onto the orthogonal
                // complement of the face normal
                Vec3f n = normal(f);
                Vec3f a,b;
                orthogonal(n, a, b);
                Mat3x3f M(a,b,n);
                
                // Get all projected vertices
                vector<Vec2f> v;                
                for(k=0;!fc.end();++fc,++k)
                {
                        Vec3f p = M * fc.get_vertex()->pos;
                        v.push_back(Vec2f(p[0], p[1]));
                }
                float area = 0;
                for(int i=0;i<k;++i)
                {
                        area += 0.5 * cross(v[i], v[(i+1)%k]);
                }
                return fabs(area);
        }
        
        Vec3f centre(FaceIter f)
        {
                Vec3f c(0);
                FaceCirculator fc(f);
                while(!fc.end())
                {
                        c += fc.get_vertex()->pos;
                        ++fc;
                }
                c /= fc.no_steps();
                return c;
        }
        
        template struct Face_template<Iters>;   
        
}