Approximation.h

Go to the documentation of this file.
00001 /***************************************************************************
00002  *   Copyright (c) 2005 Imetric 3D GmbH                                    *
00003  *                                                                         *
00004  *   This file is part of the FreeCAD CAx development system.              *
00005  *                                                                         *
00006  *   This library is free software; you can redistribute it and/or         *
00007  *   modify it under the terms of the GNU Library General Public           *
00008  *   License as published by the Free Software Foundation; either          *
00009  *   version 2 of the License, or (at your option) any later version.      *
00010  *                                                                         *
00011  *   This library  is distributed in the hope that it will be useful,      *
00012  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
00013  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
00014  *   GNU Library General Public License for more details.                  *
00015  *                                                                         *
00016  *   You should have received a copy of the GNU Library General Public     *
00017  *   License along with this library; see the file COPYING.LIB. If not,    *
00018  *   write to the Free Software Foundation, Inc., 59 Temple Place,         *
00019  *   Suite 330, Boston, MA  02111-1307, USA                                *
00020  *                                                                         *
00021  ***************************************************************************/
00022 
00023 
00024 #ifndef MESH_APPROXIMATION_H
00025 #define MESH_APPROXIMATION_H
00026 
00027 #include <Mod/Mesh/App/WildMagic4/Wm4Vector3.h>
00028 #include <Mod/Mesh/App/WildMagic4/Wm4QuadricSurface.h>
00029 #include <Mod/Mesh/App/WildMagic4/Wm4Eigen.h>
00030 #include <list>
00031 #include <set>
00032 #include <vector>
00033 
00034 #include <Base/Vector3D.h>
00035 #include <Base/Matrix.h>
00036 
00037 namespace MeshCore {
00038 
00039 
00043 class MeshExport Approximation
00044 {
00045 public:
00049     Approximation() : _bIsFitted(false) { }
00053     virtual ~Approximation(){ Clear(); }
00057     void AddPoint(const Base::Vector3f &rcVector);
00061     void AddPoints(const std::vector<Base::Vector3f> &rvPointVect);
00065     void AddPoints(const std::set<Base::Vector3f> &rsPointSet);
00069     void AddPoints(const std::list<Base::Vector3f> &rsPointList);
00073     const std::list<Base::Vector3f>& GetPoints() const { return _vPoints; }
00078     Base::Vector3f GetGravity() const;
00083     unsigned long CountPoints() const;
00087     void Clear();
00092     float GetLastResult() const;
00097     virtual float Fit() = 0;
00101     bool Done() const;
00102 
00103 protected:
00107     static void Convert( const Wm4::Vector3<float>&, Base::Vector3f&);
00111     static void Convert( const Base::Vector3f&, Wm4::Vector3<float>&);
00115     void GetMgcVectorArray( std::vector< Wm4::Vector3<float> >& rcPts ) const;
00116 
00117 protected:
00118     std::list< Base::Vector3f > _vPoints; 
00119     bool _bIsFitted; 
00120     float _fLastResult; 
00121 };
00122 
00123 // -------------------------------------------------------------------------------
00124 
00128 class MeshExport PlaneFit : public Approximation
00129 {
00130 public:
00134     PlaneFit(){};
00138     virtual ~PlaneFit(){};
00139     Base::Vector3f GetBase() const;
00140     Base::Vector3f GetDirU() const;
00141     Base::Vector3f GetDirV() const;
00146     Base::Vector3f GetNormal() const;
00151     float Fit();
00156     float GetDistanceToPlane(const Base::Vector3f &rcPoint) const;
00161     float GetStdDeviation() const;
00166     float GetSignedStdDeviation() const;
00170     void ProjectToPlane();
00171 
00172 protected:
00173     Base::Vector3f _vBase; 
00174     Base::Vector3f _vDirU;
00175     Base::Vector3f _vDirV;
00176     Base::Vector3f _vDirW; 
00177 };
00178 
00179 // -------------------------------------------------------------------------------
00180 
00190 class MeshExport QuadraticFit : public Approximation
00191 {
00192 public:
00196     QuadraticFit() : Approximation() {};
00200     virtual ~QuadraticFit(){};
00206     float GetCoeff(unsigned long ulIndex) const;
00212     const float& GetCoeffArray() const;
00217     float Fit();
00218 
00219     void CalcZValues(float x, float y, float &dZ1, float &dZ2) const;
00232     bool GetCurvatureInfo(float x, float y, float z,
00233                           float &rfCurv0, float &rfCurv1,
00234                           Base::Vector3f &rkDir0, Base::Vector3f &rkDir1, float &dDistance);
00235 
00236     bool GetCurvatureInfo(float x, float y, float z,
00237                           float &rfCurv0, float &rfcurv1);
00247     void CalcEigenValues(float &dLambda1, float &dLambda2, float &dLambda3,
00248                          Base::Vector3f &clEV1, Base::Vector3f &clEV2, Base::Vector3f &clEV3) const;
00249 
00250 protected:
00251     float _fCoeff[ 10 ];  
00252 };
00253 
00254 // -------------------------------------------------------------------------------
00255 
00266 class MeshExport SurfaceFit : public PlaneFit
00267 {
00268 public:
00272     SurfaceFit();
00276     virtual ~SurfaceFit(){};
00277 
00278     bool GetCurvatureInfo(float x, float y, float z, float &rfCurv0, float &rfCurv1,
00279                           Base::Vector3f &rkDir0, Base::Vector3f &rkDir1, float &dDistance);
00280     bool GetCurvatureInfo(float x, float y, float z, float &rfCurv0, float &rfcurv1);
00281     float Fit();
00282     float Value(float x, float y) const;
00283 
00284 protected:
00285     float PolynomFit();
00286     float _fCoeff[ 10 ];  
00287 };
00288 
00289 // -------------------------------------------------------------------------------
00290 
00296 class FunctionContainer
00297 {
00298 public:
00303     typedef float (*Function)(float,float,float);
00310     FunctionContainer(const float *pKoef)
00311     {
00312         Assign( pKoef );
00313 /*
00314         Function oF;     
00315         Function aoDF[3];
00316         Function aoD2F[6];
00317 
00318         oF = &F;
00319         aoDF[0] = &Fx;
00320         aoDF[1] = &Fy;
00321         aoDF[2] = &Fz;
00322         aoD2F[0] = &Fxx;
00323         aoD2F[1] = &Fxy;
00324         aoD2F[2] = &Fxz;
00325         aoD2F[3] = &Fyy;
00326         aoD2F[4] = &Fyz;
00327         aoD2F[5] = &Fzz;
00328 
00329         pImplSurf = new Wm4::QuadricSurface<float>( oF, aoDF, aoD2F );*/
00330 
00331         pImplSurf = new Wm4::QuadricSurface<float>( dKoeff );
00332     }
00338     void Assign( const float *pKoef )
00339     {
00340         for (long ct=0; ct < 10; ct++)
00341             dKoeff[ ct ] = pKoef[ ct ];
00342     }
00347     virtual ~FunctionContainer(){ delete pImplSurf; }
00353     float& operator[](int idx){ return dKoeff[ idx ]; }
00367     bool CurvatureInfo(float x, float y, float z, 
00368                        float &rfCurv0, float &rfCurv1,
00369                        Wm4::Vector3<float> &rkDir0,  Wm4::Vector3<float> &rkDir1, float &dDistance)
00370     {
00371         return pImplSurf->ComputePrincipalCurvatureInfo( Wm4::Vector3<float>(x, y, z),rfCurv0, rfCurv1, rkDir0, rkDir1 );
00372     }
00373 
00374     Base::Vector3f GetGradient( float x, float y, float z ) const
00375     {
00376         Wm4::Vector3<float> grad = pImplSurf->GetGradient( Wm4::Vector3<float>(x, y, z) );
00377         return Base::Vector3f( grad.X(), grad.Y(), grad.Z() );
00378     }
00379 
00380     Base::Matrix4D GetHessian( float x, float y, float z ) const
00381     {
00382         Wm4::Matrix3<float> hess = pImplSurf->GetHessian( Wm4::Vector3<float>(x, y, z) );
00383         Base::Matrix4D cMat; cMat.setToUnity();
00384         cMat[0][0] = hess[0][0]; cMat[0][1] = hess[0][1]; cMat[0][2] = hess[0][2];
00385         cMat[1][0] = hess[1][0]; cMat[1][1] = hess[1][1]; cMat[1][2] = hess[1][2];
00386         cMat[2][0] = hess[2][0]; cMat[2][1] = hess[2][1]; cMat[2][2] = hess[2][2];
00387         return cMat;
00388     }
00389 
00390     bool CurvatureInfo(float x, float y, float z,
00391                        float &rfCurv0, float &rfCurv1)
00392     {
00393         float dQuot = Fz(x,y,z);
00394         float zx = - ( Fx(x,y,z) / dQuot );
00395         float zy = - ( Fy(x,y,z) / dQuot );
00396         
00397         float zxx = - ( 2.0f * ( dKoeff[5] + dKoeff[6] * zx * zx + dKoeff[8] * zx ) ) / dQuot;
00398         float zyy = - ( 2.0f * ( dKoeff[5] + dKoeff[6] * zy * zy + dKoeff[9] * zy ) ) / dQuot;
00399         float zxy = - ( dKoeff[6] * zx * zy + dKoeff[7] + dKoeff[8] * zy + dKoeff[9] * zx ) / dQuot;
00400 
00401         float dNen = 1 + zx*zx + zy*zy;
00402         float dNenSqrt = (float)sqrt( dNen );
00403         float K = ( zxx * zyy - zxy * zxy ) / ( dNen * dNen );
00404         float H = 0.5f * ( ( 1.0f+zx*zx - 2*zx*zy*zxy + (1.0f+zy*zy)*zxx ) / ( dNenSqrt * dNenSqrt * dNenSqrt ) ) ;
00405 
00406         float dDiscr = (float)sqrt(fabs(H*H-K));
00407         rfCurv0 = H - dDiscr;
00408         rfCurv1 = H + dDiscr;
00409 
00410         return true;
00411     }
00412 
00413     //+++++++++ Quadric +++++++++++++++++++++++++++++++++++++++
00414     static float F  ( float x, float y, float z ) 
00415     {
00416         return (dKoeff[0] + dKoeff[1]*x + dKoeff[2]*y + dKoeff[3]*z +
00417                 dKoeff[4]*x*x + dKoeff[5]*y*y + dKoeff[6]*z*z +
00418                 dKoeff[7]*x*y + dKoeff[8]*x*z + dKoeff[9]*y*z);
00419     }
00420   
00421     //+++++++++ 1. derivations ++++++++++++++++++++++++++++++++
00422     static float Fx ( float x, float y, float z )
00423     {
00424         return( dKoeff[1] + 2.0f*dKoeff[4]*x + dKoeff[7]*y + dKoeff[8]*z );
00425     }
00426     static float Fy ( float x, float y, float z ) 
00427     {
00428         return( dKoeff[2] + 2.0f*dKoeff[5]*y + dKoeff[7]*x + dKoeff[9]*z );
00429     }
00430     static float Fz ( float x, float y, float z ) 
00431     {
00432         return( dKoeff[3] + 2.0f*dKoeff[6]*z + dKoeff[8]*x + dKoeff[9]*y );
00433     }
00434 
00435     //+++++++++ 2. derivations ++++++++++++++++++++++++++++++++
00436     static float Fxx( float x, float y, float z ) 
00437     {
00438         return( 2.0f*dKoeff[4] );
00439     }
00440     static float Fxy( float x, float y, float z ) 
00441     {
00442         return( dKoeff[7] );
00443     }
00444     static float Fxz( float x, float y, float z ) 
00445     {
00446         return( dKoeff[8] );
00447     }
00448     static float Fyy( float x, float y, float z ) 
00449     {
00450         return( 2.0f*dKoeff[5] );
00451     }
00452     static float Fyz( float x, float y, float z ) 
00453     {
00454         return( dKoeff[9] );
00455     }
00456     static float Fzz( float x, float y, float z ) 
00457     {
00458         return( 2.0f*dKoeff[6] );
00459     }
00460    
00461 protected:
00462     static float dKoeff[ 10 ];     
00463     Wm4::ImplicitSurface<float> *pImplSurf;  
00465 private:
00469     FunctionContainer(){};
00470 };
00471 
00472 class MeshExport PolynomialFit : public Approximation
00473 {
00474 public:
00478     PolynomialFit();
00479 
00483     virtual ~PolynomialFit();
00484     float Fit();
00485     float Value(float x, float y) const;
00486 
00487 protected:
00488     float _fCoeff[9];
00489 };
00490 
00491 } // namespace MeshCore
00492 
00493 #endif // MESH_APPROXIMATION_H

Generated on Wed Nov 23 18:59:57 2011 for FreeCAD by  doxygen 1.6.1