misc/libfreetype/src/tools/test_trig.c
changeset 9372 915436ff64ab
parent 9371 f3840de881bd
child 9373 b769a8e38cbd
equal deleted inserted replaced
9371:f3840de881bd 9372:915436ff64ab
     1 #include <ft2build.h>
       
     2 #include FT_FREETYPE_H
       
     3 #include FT_TRIGONOMETRY_H
       
     4 
       
     5 #include <math.h>
       
     6 #include <stdio.h>
       
     7 
       
     8 #define  PI   3.14159265358979323846
       
     9 #define  SPI  (PI/FT_ANGLE_PI)
       
    10 
       
    11 /* the precision in 16.16 fixed float points of the checks. Expect */
       
    12 /* between 2 and 5 noise LSB bits during operations, due to        */
       
    13 /* rounding errors..                                               */
       
    14 #define  THRESHOLD  64
       
    15 
       
    16   static  error = 0;
       
    17 
       
    18   static void
       
    19   test_cos( void )
       
    20   {
       
    21     FT_Fixed  f1, f2;
       
    22     double    d1, d2;
       
    23     int       i;
       
    24 
       
    25     for ( i = 0; i < FT_ANGLE_2PI; i += 0x10000 )
       
    26     {
       
    27       f1 = FT_Cos(i);
       
    28       d1 = f1/65536.0;
       
    29       d2 = cos( i*SPI );
       
    30       f2 = (FT_Fixed)(d2*65536.0);
       
    31 
       
    32       if ( abs( f2-f1 ) > THRESHOLD )
       
    33       {
       
    34         error = 1;
       
    35         printf( "FT_Cos[%3d] = %.7f  cos[%3d] = %.7f\n",
       
    36                 (i >> 16), f1/65536.0, (i >> 16), d2 );
       
    37       }
       
    38     }
       
    39   }
       
    40 
       
    41 
       
    42 
       
    43   static void
       
    44   test_sin( void )
       
    45   {
       
    46     FT_Fixed  f1, f2;
       
    47     double    d1, d2;
       
    48     int       i;
       
    49 
       
    50     for ( i = 0; i < FT_ANGLE_2PI; i += 0x10000 )
       
    51     {
       
    52       f1 = FT_Sin(i);
       
    53       d1 = f1/65536.0;
       
    54       d2 = sin( i*SPI );
       
    55       f2 = (FT_Fixed)(d2*65536.0);
       
    56 
       
    57       if ( abs( f2-f1 ) > THRESHOLD )
       
    58       {
       
    59         error = 1;
       
    60         printf( "FT_Sin[%3d] = %.7f  sin[%3d] = %.7f\n",
       
    61                 (i >> 16), f1/65536.0, (i >> 16), d2 );
       
    62       }
       
    63     }
       
    64   }
       
    65 
       
    66 
       
    67   static void
       
    68   test_tan( void )
       
    69   {
       
    70     FT_Fixed  f1, f2;
       
    71     double    d1, d2;
       
    72     int       i;
       
    73 
       
    74     for ( i = 0; i < FT_ANGLE_PI2-0x2000000; i += 0x10000 )
       
    75     {
       
    76       f1 = FT_Tan(i);
       
    77       d1 = f1/65536.0;
       
    78       d2 = tan( i*SPI );
       
    79       f2 = (FT_Fixed)(d2*65536.0);
       
    80 
       
    81       if ( abs( f2-f1 ) > THRESHOLD )
       
    82       {
       
    83         error = 1;
       
    84         printf( "FT_Tan[%3d] = %.7f  tan[%3d] = %.7f\n",
       
    85                 (i >> 16), f1/65536.0, (i >> 16), d2 );
       
    86       }
       
    87     }
       
    88   }
       
    89 
       
    90 
       
    91   static void
       
    92   test_atan2( void )
       
    93   {
       
    94     FT_Fixed  c2, s2;
       
    95     double    l, a, c1, s1;
       
    96     int       i, j;
       
    97 
       
    98     for ( i = 0; i < FT_ANGLE_2PI; i += 0x10000 )
       
    99     {
       
   100       l  = 5.0;
       
   101       a  = i*SPI;
       
   102 
       
   103       c1 = l * cos(a);
       
   104       s1 = l * sin(a);
       
   105 
       
   106       c2 = (FT_Fixed)(c1*65536.0);
       
   107       s2 = (FT_Fixed)(s1*65536.0);
       
   108 
       
   109       j  = FT_Atan2( c2, s2 );
       
   110       if ( j < 0 )
       
   111         j += FT_ANGLE_2PI;
       
   112 
       
   113       if ( abs( i - j ) > 1 )
       
   114       {
       
   115         printf( "FT_Atan2( %.7f, %.7f ) = %.5f, atan = %.5f\n",
       
   116                 c2/65536.0, s2/65536.0, j/65536.0, i/65536.0 );
       
   117       }
       
   118     }
       
   119   }
       
   120 
       
   121   static void
       
   122   test_unit( void )
       
   123   {
       
   124     FT_Vector  v;
       
   125     double     a, c1, s1;
       
   126     FT_Fixed   c2, s2;
       
   127     int        i;
       
   128 
       
   129     for ( i = 0; i < FT_ANGLE_2PI; i += 0x10000 )
       
   130     {
       
   131       FT_Vector_Unit( &v, i );
       
   132       a  = ( i*SPI );
       
   133       c1 = cos(a);
       
   134       s1 = sin(a);
       
   135       c2 = (FT_Fixed)(c1*65536.0);
       
   136       s2 = (FT_Fixed)(s1*65536.0);
       
   137 
       
   138       if ( abs( v.x-c2 ) > THRESHOLD ||
       
   139            abs( v.y-s2 ) > THRESHOLD )
       
   140       {
       
   141         error = 1;
       
   142         printf( "FT_Vector_Unit[%3d] = ( %.7f, %.7f )  vec = ( %.7f, %.7f )\n",
       
   143                 (i >> 16),
       
   144                 v.x/65536.0, v.y/65536.0,
       
   145                 c1, s1 );
       
   146       }
       
   147     }
       
   148   }
       
   149 
       
   150 
       
   151   static void
       
   152   test_length( void )
       
   153   {
       
   154     FT_Vector  v;
       
   155     FT_Fixed   l, l2;
       
   156     int        i;
       
   157 
       
   158     for ( i = 0; i < FT_ANGLE_2PI; i += 0x10000 )
       
   159     {
       
   160       l   = (FT_Fixed)(500.0*65536.0);
       
   161       v.x = (FT_Fixed)( l * cos( i*SPI ) );
       
   162       v.y = (FT_Fixed)( l * sin( i*SPI ) );
       
   163       l2  = FT_Vector_Length( &v );
       
   164 
       
   165       if ( abs( l2-l ) > THRESHOLD )
       
   166       {
       
   167         error = 1;
       
   168         printf( "FT_Length( %.7f, %.7f ) = %.5f, length = %.5f\n",
       
   169                 v.x/65536.0, v.y/65536.0, l2/65536.0, l/65536.0 );
       
   170       }
       
   171     }
       
   172   }
       
   173 
       
   174 
       
   175   static void
       
   176   test_rotate( void )
       
   177   {
       
   178     FT_Fixed  c2, s2, c4, s4;
       
   179     FT_Vector v;
       
   180     double    l, ra, a, c1, s1, cra, sra, c3, s3;
       
   181     int       i, j, rotate;
       
   182 
       
   183     for ( rotate = 0; rotate < FT_ANGLE_2PI; rotate += 0x10000 )
       
   184     {
       
   185       ra  = rotate*SPI;
       
   186       cra = cos( ra );
       
   187       sra = sin( ra );
       
   188 
       
   189       for ( i = 0; i < FT_ANGLE_2PI; i += 0x10000 )
       
   190       {
       
   191         l  = 500.0;
       
   192         a  = i*SPI;
       
   193 
       
   194         c1 = l * cos(a);
       
   195         s1 = l * sin(a);
       
   196 
       
   197         v.x = c2 = (FT_Fixed)(c1*65536.0);
       
   198         v.y = s2 = (FT_Fixed)(s1*65536.0);
       
   199 
       
   200         FT_Vector_Rotate( &v, rotate );
       
   201 
       
   202         c3 = c1 * cra - s1 * sra;
       
   203         s3 = c1 * sra + s1 * cra;
       
   204 
       
   205         c4 = (FT_Fixed)(c3*65536.0);
       
   206         s4 = (FT_Fixed)(s3*65536.0);
       
   207 
       
   208         if ( abs( c4 - v.x ) > THRESHOLD ||
       
   209              abs( s4 - v.y ) > THRESHOLD )
       
   210         {
       
   211           error = 1;
       
   212           printf( "FT_Rotate( (%.7f,%.7f), %.5f ) = ( %.7f, %.7f ), rot = ( %.7f, %.7f )\n",
       
   213                   c1, s1, ra,
       
   214                   c2/65536.0, s2/65536.0,
       
   215                   c4/65536.0, s4/65536.0 );
       
   216         }
       
   217       }
       
   218     }
       
   219   }
       
   220 
       
   221 
       
   222   int main( void )
       
   223   {
       
   224     test_cos();
       
   225     test_sin();
       
   226     test_tan();
       
   227     test_atan2();
       
   228     test_unit();
       
   229     test_length();
       
   230     test_rotate();
       
   231 
       
   232     if (!error)
       
   233       printf( "trigonometry test ok !\n" );
       
   234 
       
   235     return !error;
       
   236   }