Commit 690d48832c1e9eb4704760640130bd0a26f6fe79

henry 2002-12-08T04:40:19

Refactored FTContour - moved it into it's own file

diff --git a/include/FTVectoriser.h b/include/FTVectoriser.h
index 304bb33..23905d4 100644
--- a/include/FTVectoriser.h
+++ b/include/FTVectoriser.h
@@ -5,6 +5,7 @@
 #include FT_FREETYPE_H
 #include FT_GLYPH_H
 
+#include "FTContour.h"
 #include "FTPoint.h"
 #include "FTVector.h"
 #include "FTGL.h"
@@ -15,78 +16,6 @@
 #endif
 
 
-/**
- * FTContour class is a container of points that describe a vector font
- * outline. It is mainly used as a container for the output of the bezier
- * curve evaluator in FTVectoriser.
- *
- * @see FTOutlineGlyph
- * @see FTPolyGlyph
- * @see FTPoint
- *
- */
-class FTGL_EXPORT FTContour
-{
-    public:
-        /**
-         * Default constructor
-         */
-        FTContour()
-        :   kMAXPOINTS( 1000)
-        {   
-            pointList.reserve( kMAXPOINTS);
-        }
-
-        /**
-         *  Destructor
-         */
-        ~FTContour()
-        {
-            pointList.clear();
-        }
-
-        /**
-         * Add a point to the end of this contour.
-         *
-         * Doesn't add the point if it's already on the end or the start
-         * of the contour. The Z component is always 0
-         *
-         * @param x The X component of the point
-         * @param y The Y component of the point
-         */
-        void AddPoint( const FTGL_DOUBLE x, const FTGL_DOUBLE y)
-        {
-            FTPoint point( x, y, 0.0f); 
-            
-            // Eliminate duplicate points.
-            if( pointList.empty() || ( pointList[pointList.size() - 1] != point && pointList[0] != point))
-            {
-                pointList.push_back( point);
-            }
-        }
-
-        /**
-         * How many points define this contour
-         *
-         * @return the number of points in this contour
-         */
-        size_t size() const { return pointList.size();}
-
-        /**
-         *  The list of points in this contour
-         */
-        typedef FTVector<FTPoint> PointVector;
-        PointVector pointList;
-        
-    private:
-        /**
-        * A 'max' number of points that this contour holds. Note however it
-        * can hold more than this number. It is just used to reserve space
-        * in the <vector>
-        */
-        const unsigned int kMAXPOINTS;
-};
-
 
 /**
  * FTTesselation captures points that are output by OpenGL's gluTesselator.
@@ -220,7 +149,7 @@ class FTGL_EXPORT FTVectoriser
         /**
          * Process the freetype outline data into contours of points
          */
-        void Process();
+        void ProcessContours();
 
         /**
          * Copy the outline data into a block of <code>FTGL_DOUBLEs</code>
@@ -265,7 +194,7 @@ class FTGL_EXPORT FTVectoriser
         size_t contours() const { return contourList.size();}
 
         /**
-         * Get the nuber of points in a contour in this outline
+         * Get the number of points in a specific contour in this outline
          *
          * @param c     The contour index
          * @return      the number of points in contour[c]
@@ -281,41 +210,6 @@ class FTGL_EXPORT FTVectoriser
         
     private:
         /**
-         * Process a conic ( second order) bezier curve.
-         *
-         * @param index The index of the current point in the point list.
-         * @param first The index into the pointlist of the first point in
-         *              the contour that the current point is part of.
-         * @param last  The index into the pointlist of the last point in
-         *              the contour that the current point is part of.
-         * @return      the number of control points processed
-         */
-        int Conic( const int index, const int first, const int last);
-
-        /**
-         * Process a cubic ( third order) bezier curve
-         *
-         * @param index The index of the current point in the point list.
-         * @param first The index into the pointlist of the first point in
-         *              the contour that the current point is part of.
-         * @param last  The index into the pointlist of the last point in
-         *              the contour that the current point is part of.
-         * @return      the number of control points processed
-         */
-        int Cubic( const int index, const int first, const int last);
-
-        /**
-         * @param t
-         * @param n
-         */
-        inline void deCasteljau( const float t, const int n);
-
-        /**
-         * @param n
-         */
-        inline void evaluateCurve( const int n);
-
-        /**
          * The list of contours in this outline
          */
         typedef FTVector<FTContour*> ContourVector;
diff --git a/src/FTVectoriser.cpp b/src/FTVectoriser.cpp
index e975ef5..b0cc217 100644
--- a/src/FTVectoriser.cpp
+++ b/src/FTVectoriser.cpp
@@ -114,6 +114,7 @@ FTVectoriser::FTVectoriser( const FT_Glyph glyph)
         ftOutline = outline->outline;
     
         contourList.reserve( ftOutline.n_contours);
+        contourFlag = ftOutline.flags;
     }
 }
 
@@ -132,171 +133,39 @@ FTVectoriser::~FTVectoriser()
 }
 
 
-int FTVectoriser::points()
-{
-    int s = 0;
-    for( size_t c = 0; c < contours(); ++c)
-    {
-        s += contourList[c]->size();
-    }
-    
-    return s;
-}
-
-
-void FTVectoriser::Process()
+void FTVectoriser::ProcessContours()
 {
-    short first = 0;
-    short last;
     const short contourCount = ftOutline.n_contours;
+    short contourLength = 0;
+    short startIndex = 0;
+    short endIndex = 0;
     
-    for( short c = 0; c < contourCount; ++c)
+    for( short contourIndex = 0; contourIndex < contourCount; ++contourIndex)
     {
-        contour = new FTContour;
-        contourFlag = ftOutline.flags;
-        last = ftOutline.contours[c];
-
-        for( int p = first; p <= last; ++p)
-        {
-            switch( ftOutline.tags[p])
-            {
-                case FT_Curve_Tag_Conic:
-                    p += Conic( p, first, last);
-                    break;
-                case FT_Curve_Tag_Cubic:
-                    p += Cubic( p, first, last);
-                    break;
-                case FT_Curve_Tag_On:
-                default:
-                    contour->AddPoint( ftOutline.points[p].x, ftOutline.points[p].y);
-            }
-        }
+        FT_Vector* pointList = &ftOutline.points[startIndex];
+        char* tagList = &ftOutline.tags[startIndex];
         
-        contourList.push_back( contour);
-        first = last + 1;
-    }
-}
-
+        endIndex = ftOutline.contours[contourIndex];
+        contourLength =  ( endIndex - startIndex) + 1;
 
-int FTVectoriser::Conic( const int index, const int first, const int last)
-{
-    int next = index + 1;
-    int prev = index - 1;
-    
-    if( index == last)
-    {
-        next = first; 
-    }
-    
-    if( index == first)
-    {
-        prev = last; 
-    }
-    
-    if( ftOutline.tags[next] != FT_Curve_Tag_Conic)
-    {
-        ctrlPtArray[0][0] = ftOutline.points[prev].x;   ctrlPtArray[0][1] = ftOutline.points[prev].y;
-        ctrlPtArray[1][0] = ftOutline.points[index].x;  ctrlPtArray[1][1] = ftOutline.points[index].y;
-        ctrlPtArray[2][0] = ftOutline.points[next].x;   ctrlPtArray[2][1] = ftOutline.points[next].y;
-        
-        evaluateCurve( 2);
-        return 1;
-    }
-    else
-    {
-        int next2 = next + 1;
-        if( next == last)
-            next2 = first;
-        
-        // create a phantom point
-        float x = ( ftOutline.points[index].x + ftOutline.points[next].x) * 0.5f;
-        float y = ( ftOutline.points[index].y + ftOutline.points[next].y) * 0.5f;
-        
-        // process first curve
-        ctrlPtArray[0][0] = ftOutline.points[prev].x;   ctrlPtArray[0][1] = ftOutline.points[prev].y;
-        ctrlPtArray[1][0] = ftOutline.points[index].x;  ctrlPtArray[1][1] = ftOutline.points[index].y;
-        ctrlPtArray[2][0] = x;                          ctrlPtArray[2][1] = y;
+        FTContour* countour = new FTContour( pointList, tagList, contourLength);
         
-        evaluateCurve( 2);
+        contourList.push_back( countour);
         
-        // process second curve
-        ctrlPtArray[0][0] = x;                          ctrlPtArray[0][1] = y;
-        ctrlPtArray[1][0] = ftOutline.points[next].x;   ctrlPtArray[1][1] = ftOutline.points[next].y;
-        ctrlPtArray[2][0] = ftOutline.points[next2].x;  ctrlPtArray[2][1] = ftOutline.points[next2].y;
-        evaluateCurve( 2);
-        
-        return 2;
+        startIndex = endIndex + 1;
     }
 }
 
 
-int FTVectoriser::Cubic( const int index, const int first, const int last)
+int FTVectoriser::points()
 {
-    int next = index + 1;
-    int prev = index - 1;
-    
-    if( index == last)
-    {
-        next = first; 
-    }
-    
-    int next2 = next + 1;
-    
-    if( next == last)
-    {
-        next2 = first;
-    }
-    
-    if( index == first)
+    int s = 0;
+    for( size_t c = 0; c < contours(); ++c)
     {
-        prev = last; 
+        s += contourList[c]->size();
     }
     
-    ctrlPtArray[0][0] = ftOutline.points[prev].x;       ctrlPtArray[0][1] = ftOutline.points[prev].y;
-    ctrlPtArray[1][0] = ftOutline.points[index].x;      ctrlPtArray[1][1] = ftOutline.points[index].y;
-    ctrlPtArray[2][0] = ftOutline.points[next].x;       ctrlPtArray[2][1] = ftOutline.points[next].y;
-    ctrlPtArray[3][0] = ftOutline.points[next2].x;      ctrlPtArray[3][1] = ftOutline.points[next2].y;
-
-    evaluateCurve( 3);
-    return 2;
-}
-
-
-// De Casteljau algorithm contributed by Jed Soane
-void FTVectoriser::deCasteljau( const float t, const int n)
-{
-    //Calculating successive b(i)'s using de Casteljau algorithm.
-    for( int i = 1; i <= n; i++)
-    {
-        for( int k = 0; k <= (n - i); k++)
-        {
-            bValues[i][k][0] = (1 - t) * bValues[i - 1][k][0] + t * bValues[i - 1][k + 1][0];
-            bValues[i][k][1] = (1 - t) * bValues[i - 1][k][1] + t * bValues[i - 1][k + 1][1];
-        }
-    }
-       
-    //Specify next vertex to be included on curve
-    contour->AddPoint( bValues[n][0][0], bValues[n][0][1]);
-}
-
-
-// De Casteljau algorithm contributed by Jed Soane
-void FTVectoriser::evaluateCurve( const int n)
-{
-    // setting the b(0) equal to the control points
-    for( int i = 0; i <= n; i++)
-    {
-        bValues[0][i][0] = ctrlPtArray[i][0];
-        bValues[0][i][1] = ctrlPtArray[i][1];
-    }
-
-    float t; //parameter for curve point calc. [0.0, 1.0]
-
-    for( int m = 0; m <= ( 1 / kBSTEPSIZE); m++)
-    {
-        t = m * kBSTEPSIZE;
-        deCasteljau( t, n);  //calls to evaluate point on curve at t.
-    }
+    return s;
 }
 
 
@@ -387,6 +256,7 @@ void FTVectoriser::GetMesh( FTGL_DOUBLE* data)
         
         data[i+1] = tesselationType;
         data[i+2] = tesselationSize;
+
         i += 3;
         for( size_t q = 0; q < ( tesselation->pointList.size()); ++q)
         {
@@ -397,3 +267,4 @@ void FTVectoriser::GetMesh( FTGL_DOUBLE* data)
         }
     }
 }
+