sfdriver.c
上传用户:yisoukefu
上传日期:2020-08-09
资源大小:39506k
文件大小:14k
源码类别:

其他游戏

开发平台:

Visual C++

  1. /***************************************************************************/
  2. /*                                                                         */
  3. /*  sfdriver.c                                                             */
  4. /*                                                                         */
  5. /*    High-level SFNT driver interface (body).                             */
  6. /*                                                                         */
  7. /*  Copyright 1996-2001, 2002, 2003, 2004, 2005, 2006, 2007 by             */
  8. /*  David Turner, Robert Wilhelm, and Werner Lemberg.                      */
  9. /*                                                                         */
  10. /*  This file is part of the FreeType project, and may only be used,       */
  11. /*  modified, and distributed under the terms of the FreeType project      */
  12. /*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     */
  13. /*  this file you indicate that you have read the license and              */
  14. /*  understand and accept it fully.                                        */
  15. /*                                                                         */
  16. /***************************************************************************/
  17. #include <ft2build.h>
  18. #include FT_INTERNAL_SFNT_H
  19. #include FT_INTERNAL_OBJECTS_H
  20. #include "sfdriver.h"
  21. #include "ttload.h"
  22. #include "sfobjs.h"
  23. #include "sferrors.h"
  24. #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS
  25. #include "ttsbit.h"
  26. #endif
  27. #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES
  28. #include "ttpost.h"
  29. #endif
  30. #ifdef TT_CONFIG_OPTION_BDF
  31. #include "ttbdf.h"
  32. #include FT_SERVICE_BDF_H
  33. #endif
  34. #include "ttcmap.h"
  35. #include "ttkern.h"
  36. #include "ttmtx.h"
  37. #include FT_SERVICE_GLYPH_DICT_H
  38. #include FT_SERVICE_POSTSCRIPT_NAME_H
  39. #include FT_SERVICE_SFNT_H
  40. #include FT_SERVICE_TT_CMAP_H
  41.  /*
  42.   *  SFNT TABLE SERVICE
  43.   *
  44.   */
  45.   static void*
  46.   get_sfnt_table( TT_Face      face,
  47.                   FT_Sfnt_Tag  tag )
  48.   {
  49.     void*  table;
  50.     switch ( tag )
  51.     {
  52.     case ft_sfnt_head:
  53.       table = &face->header;
  54.       break;
  55.     case ft_sfnt_hhea:
  56.       table = &face->horizontal;
  57.       break;
  58.     case ft_sfnt_vhea:
  59.       table = face->vertical_info ? &face->vertical : 0;
  60.       break;
  61.     case ft_sfnt_os2:
  62.       table = face->os2.version == 0xFFFFU ? 0 : &face->os2;
  63.       break;
  64.     case ft_sfnt_post:
  65.       table = &face->postscript;
  66.       break;
  67.     case ft_sfnt_maxp:
  68.       table = &face->max_profile;
  69.       break;
  70.     case ft_sfnt_pclt:
  71.       table = face->pclt.Version ? &face->pclt : 0;
  72.       break;
  73.     default:
  74.       table = 0;
  75.     }
  76.     return table;
  77.   }
  78.   static FT_Error
  79.   sfnt_table_info( TT_Face    face,
  80.                    FT_UInt    idx,
  81.                    FT_ULong  *tag,
  82.                    FT_ULong  *length )
  83.   {
  84.     if ( !tag || !length )
  85.       return SFNT_Err_Invalid_Argument;
  86.     if ( idx >= face->num_tables )
  87.       return SFNT_Err_Table_Missing;
  88.     *tag    = face->dir_tables[idx].Tag;
  89.     *length = face->dir_tables[idx].Length;
  90.     return SFNT_Err_Ok;
  91.   }
  92.   static const FT_Service_SFNT_TableRec  sfnt_service_sfnt_table =
  93.   {
  94.     (FT_SFNT_TableLoadFunc)tt_face_load_any,
  95.     (FT_SFNT_TableGetFunc) get_sfnt_table,
  96.     (FT_SFNT_TableInfoFunc)sfnt_table_info
  97.   };
  98. #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES
  99.  /*
  100.   *  GLYPH DICT SERVICE
  101.   *
  102.   */
  103.   static FT_Error
  104.   sfnt_get_glyph_name( TT_Face     face,
  105.                        FT_UInt     glyph_index,
  106.                        FT_Pointer  buffer,
  107.                        FT_UInt     buffer_max )
  108.   {
  109.     FT_String*  gname;
  110.     FT_Error    error;
  111.     error = tt_face_get_ps_name( face, glyph_index, &gname );
  112.     if ( !error )
  113.       FT_STRCPYN( buffer, gname, buffer_max );
  114.     return error;
  115.   }
  116.   static const FT_Service_GlyphDictRec  sfnt_service_glyph_dict =
  117.   {
  118.     (FT_GlyphDict_GetNameFunc)  sfnt_get_glyph_name,
  119.     (FT_GlyphDict_NameIndexFunc)NULL
  120.   };
  121. #endif /* TT_CONFIG_OPTION_POSTSCRIPT_NAMES */
  122.  /*
  123.   *  POSTSCRIPT NAME SERVICE
  124.   *
  125.   */
  126.   static const char*
  127.   sfnt_get_ps_name( TT_Face  face )
  128.   {
  129.     FT_Int       n, found_win, found_apple;
  130.     const char*  result = NULL;
  131.     /* shouldn't happen, but just in case to avoid memory leaks */
  132.     if ( face->postscript_name )
  133.       return face->postscript_name;
  134.     /* scan the name table to see whether we have a Postscript name here, */
  135.     /* either in Macintosh or Windows platform encodings                  */
  136.     found_win   = -1;
  137.     found_apple = -1;
  138.     for ( n = 0; n < face->num_names; n++ )
  139.     {
  140.       TT_NameEntryRec*  name = face->name_table.names + n;
  141.       if ( name->nameID == 6 && name->stringLength > 0 )
  142.       {
  143.         if ( name->platformID == 3     &&
  144.              name->encodingID == 1     &&
  145.              name->languageID == 0x409 )
  146.           found_win = n;
  147.         if ( name->platformID == 1 &&
  148.              name->encodingID == 0 &&
  149.              name->languageID == 0 )
  150.           found_apple = n;
  151.       }
  152.     }
  153.     if ( found_win != -1 )
  154.     {
  155.       FT_Memory         memory = face->root.memory;
  156.       TT_NameEntryRec*  name   = face->name_table.names + found_win;
  157.       FT_UInt           len    = name->stringLength / 2;
  158.       FT_Error          error  = SFNT_Err_Ok;
  159.       FT_UNUSED( error );
  160.       if ( !FT_ALLOC( result, name->stringLength + 1 ) )
  161.       {
  162.         FT_Stream   stream = face->name_table.stream;
  163.         FT_String*  r      = (FT_String*)result;
  164.         FT_Byte*    p      = (FT_Byte*)name->string;
  165.         if ( FT_STREAM_SEEK( name->stringOffset ) ||
  166.              FT_FRAME_ENTER( name->stringLength ) )
  167.         {
  168.           FT_FREE( result );
  169.           name->stringLength = 0;
  170.           name->stringOffset = 0;
  171.           FT_FREE( name->string );
  172.           goto Exit;
  173.         }
  174.         p = (FT_Byte*)stream->cursor;
  175.         for ( ; len > 0; len--, p += 2 )
  176.         {
  177.           if ( p[0] == 0 && p[1] >= 32 && p[1] < 128 )
  178.             *r++ = p[1];
  179.         }
  180.         *r = '';
  181.         FT_FRAME_EXIT();
  182.       }
  183.       goto Exit;
  184.     }
  185.     if ( found_apple != -1 )
  186.     {
  187.       FT_Memory         memory = face->root.memory;
  188.       TT_NameEntryRec*  name   = face->name_table.names + found_apple;
  189.       FT_UInt           len    = name->stringLength;
  190.       FT_Error          error  = SFNT_Err_Ok;
  191.       FT_UNUSED( error );
  192.       if ( !FT_ALLOC( result, len + 1 ) )
  193.       {
  194.         FT_Stream  stream = face->name_table.stream;
  195.         if ( FT_STREAM_SEEK( name->stringOffset ) ||
  196.              FT_STREAM_READ( result, len )        )
  197.         {
  198.           name->stringOffset = 0;
  199.           name->stringLength = 0;
  200.           FT_FREE( name->string );
  201.           FT_FREE( result );
  202.           goto Exit;
  203.         }
  204.         ((char*)result)[len] = '';
  205.       }
  206.     }
  207.   Exit:
  208.     face->postscript_name = result;
  209.     return result;
  210.   }
  211.   static const FT_Service_PsFontNameRec  sfnt_service_ps_name =
  212.   {
  213.     (FT_PsName_GetFunc)sfnt_get_ps_name
  214.   };
  215.   /*
  216.    *  TT CMAP INFO
  217.    */
  218.   static const FT_Service_TTCMapsRec  tt_service_get_cmap_info =
  219.   {
  220.     (TT_CMap_Info_GetFunc)tt_get_cmap_info
  221.   };
  222. #ifdef TT_CONFIG_OPTION_BDF
  223.   static FT_Error
  224.   sfnt_get_charset_id( TT_Face       face,
  225.                        const char*  *acharset_encoding,
  226.                        const char*  *acharset_registry )
  227.   {
  228.     BDF_PropertyRec  encoding, registry;
  229.     FT_Error         error;
  230.     /* XXX: I don't know whether this is correct, since
  231.      *      tt_face_find_bdf_prop only returns something correct if we have
  232.      *      previously selected a size that is listed in the BDF table.
  233.      *      Should we change the BDF table format to include single offsets
  234.      *      for `CHARSET_REGISTRY' and `CHARSET_ENCODING'?
  235.      */
  236.     error = tt_face_find_bdf_prop( face, "CHARSET_REGISTRY", &registry );
  237.     if ( !error )
  238.     {
  239.       error = tt_face_find_bdf_prop( face, "CHARSET_ENCODING", &encoding );
  240.       if ( !error )
  241.       {
  242.         if ( registry.type == BDF_PROPERTY_TYPE_ATOM &&
  243.              encoding.type == BDF_PROPERTY_TYPE_ATOM )
  244.         {
  245.           *acharset_encoding = encoding.u.atom;
  246.           *acharset_registry = registry.u.atom;
  247.         }
  248.         else
  249.           error = FT_Err_Invalid_Argument;
  250.       }
  251.     }
  252.     return error;
  253.   }
  254.   static const FT_Service_BDFRec  sfnt_service_bdf =
  255.   {
  256.     (FT_BDF_GetCharsetIdFunc) sfnt_get_charset_id,
  257.     (FT_BDF_GetPropertyFunc)  tt_face_find_bdf_prop,
  258.   };
  259. #endif /* TT_CONFIG_OPTION_BDF */
  260.   /*
  261.    *  SERVICE LIST
  262.    */
  263.   static const FT_ServiceDescRec  sfnt_services[] =
  264.   {
  265.     { FT_SERVICE_ID_SFNT_TABLE,           &sfnt_service_sfnt_table },
  266.     { FT_SERVICE_ID_POSTSCRIPT_FONT_NAME, &sfnt_service_ps_name },
  267. #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES
  268.     { FT_SERVICE_ID_GLYPH_DICT,           &sfnt_service_glyph_dict },
  269. #endif
  270. #ifdef TT_CONFIG_OPTION_BDF
  271.     { FT_SERVICE_ID_BDF,                  &sfnt_service_bdf },
  272. #endif
  273.     { FT_SERVICE_ID_TT_CMAP,              &tt_service_get_cmap_info },
  274.     { NULL, NULL }
  275.   };
  276.   FT_CALLBACK_DEF( FT_Module_Interface )
  277.   sfnt_get_interface( FT_Module    module,
  278.                       const char*  module_interface )
  279.   {
  280.     FT_UNUSED( module );
  281.     return ft_service_list_lookup( sfnt_services, module_interface );
  282.   }
  283. #ifdef FT_CONFIG_OPTION_OLD_INTERNALS
  284.   FT_CALLBACK_DEF( FT_Error )
  285.   tt_face_load_sfnt_header_stub( TT_Face      face,
  286.                                  FT_Stream    stream,
  287.                                  FT_Long      face_index,
  288.                                  SFNT_Header  header )
  289.   {
  290.     FT_UNUSED( face );
  291.     FT_UNUSED( stream );
  292.     FT_UNUSED( face_index );
  293.     FT_UNUSED( header );
  294.     return FT_Err_Unimplemented_Feature;
  295.   }
  296.   FT_CALLBACK_DEF( FT_Error )
  297.   tt_face_load_directory_stub( TT_Face      face,
  298.                                FT_Stream    stream,
  299.                                SFNT_Header  header )
  300.   {
  301.     FT_UNUSED( face );
  302.     FT_UNUSED( stream );
  303.     FT_UNUSED( header );
  304.     return FT_Err_Unimplemented_Feature;
  305.   }
  306.   FT_CALLBACK_DEF( FT_Error )
  307.   tt_face_load_hdmx_stub( TT_Face    face,
  308.                           FT_Stream  stream )
  309.   {
  310.     FT_UNUSED( face );
  311.     FT_UNUSED( stream );
  312.     return FT_Err_Unimplemented_Feature;
  313.   }
  314.   FT_CALLBACK_DEF( void )
  315.   tt_face_free_hdmx_stub( TT_Face  face )
  316.   {
  317.     FT_UNUSED( face );
  318.   }
  319.   FT_CALLBACK_DEF( FT_Error )
  320.   tt_face_set_sbit_strike_stub( TT_Face    face,
  321.                                 FT_UInt    x_ppem,
  322.                                 FT_UInt    y_ppem,
  323.                                 FT_ULong*  astrike_index )
  324.   {
  325.     /*
  326.      * We simply forge a FT_Size_Request and call the real function
  327.      * that does all the work.
  328.      *
  329.      * This stub might be called by libXfont in the X.Org Xserver,
  330.      * compiled against version 2.1.8 or newer.
  331.      */
  332.     FT_Size_RequestRec  req;
  333.     req.type           = FT_SIZE_REQUEST_TYPE_NOMINAL;
  334.     req.width          = (FT_F26Dot6)x_ppem;
  335.     req.height         = (FT_F26Dot6)y_ppem;
  336.     req.horiResolution = 0;
  337.     req.vertResolution = 0;
  338.     *astrike_index = 0x7FFFFFFFUL;
  339.     return tt_face_set_sbit_strike( face, &req, astrike_index );
  340.   }
  341.   FT_CALLBACK_DEF( FT_Error )
  342.   tt_face_load_sbit_stub( TT_Face    face,
  343.                           FT_Stream  stream )
  344.   {
  345.     FT_UNUSED( face );
  346.     FT_UNUSED( stream );
  347.     /*
  348.      *  This function was originally implemented to load the sbit table.
  349.      *  However, it has been replaced by `tt_face_load_eblc', and this stub
  350.      *  is only there for some rogue clients which would want to call it
  351.      *  directly (which doesn't make much sense).
  352.      */
  353.     return FT_Err_Unimplemented_Feature;
  354.   }
  355.   FT_CALLBACK_DEF( void )
  356.   tt_face_free_sbit_stub( TT_Face  face )
  357.   {
  358.     /* nothing to do in this stub */
  359.     FT_UNUSED( face );
  360.   }
  361.   FT_CALLBACK_DEF( FT_Error )
  362.   tt_face_load_charmap_stub( TT_Face    face,
  363.                              void*      cmap,
  364.                              FT_Stream  input )
  365.   {
  366.     FT_UNUSED( face );
  367.     FT_UNUSED( cmap );
  368.     FT_UNUSED( input );
  369.     return FT_Err_Unimplemented_Feature;
  370.   }
  371.   FT_CALLBACK_DEF( FT_Error )
  372.   tt_face_free_charmap_stub( TT_Face  face,
  373.                              void*    cmap )
  374.   {
  375.     FT_UNUSED( face );
  376.     FT_UNUSED( cmap );
  377.     return 0;
  378.   }
  379. #endif /* FT_CONFIG_OPTION_OLD_INTERNALS */
  380.   static
  381.   const SFNT_Interface  sfnt_interface =
  382.   {
  383.     tt_face_goto_table,
  384.     sfnt_init_face,
  385.     sfnt_load_face,
  386.     sfnt_done_face,
  387.     sfnt_get_interface,
  388.     tt_face_load_any,
  389. #ifdef FT_CONFIG_OPTION_OLD_INTERNALS
  390.     tt_face_load_sfnt_header_stub,
  391.     tt_face_load_directory_stub,
  392. #endif
  393.     tt_face_load_head,
  394.     tt_face_load_hhea,
  395.     tt_face_load_cmap,
  396.     tt_face_load_maxp,
  397.     tt_face_load_os2,
  398.     tt_face_load_post,
  399.     tt_face_load_name,
  400.     tt_face_free_name,
  401. #ifdef FT_CONFIG_OPTION_OLD_INTERNALS
  402.     tt_face_load_hdmx_stub,
  403.     tt_face_free_hdmx_stub,
  404. #endif
  405.     tt_face_load_kern,
  406.     tt_face_load_gasp,
  407.     tt_face_load_pclt,
  408. #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS
  409.     /* see `ttload.h' */
  410.     tt_face_load_bhed,
  411. #else
  412.     0,
  413. #endif
  414. #ifdef FT_CONFIG_OPTION_OLD_INTERNALS
  415.     tt_face_set_sbit_strike_stub,
  416.     tt_face_load_sbit_stub,
  417.     tt_find_sbit_image,
  418.     tt_load_sbit_metrics,
  419. #endif
  420. #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS
  421.     tt_face_load_sbit_image,
  422. #else
  423.     0,
  424. #endif
  425. #ifdef FT_CONFIG_OPTION_OLD_INTERNALS
  426.     tt_face_free_sbit_stub,
  427. #endif
  428. #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES
  429.     /* see `ttpost.h' */
  430.     tt_face_get_ps_name,
  431.     tt_face_free_ps_names,
  432. #else
  433.     0,
  434.     0,
  435. #endif
  436. #ifdef FT_CONFIG_OPTION_OLD_INTERNALS
  437.     tt_face_load_charmap_stub,
  438.     tt_face_free_charmap_stub,
  439. #endif
  440.     /* since version 2.1.8 */
  441.     tt_face_get_kerning,
  442.     /* since version 2.2 */
  443.     tt_face_load_font_dir,
  444.     tt_face_load_hmtx,
  445. #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS
  446.     /* see `ttsbit.h' and `sfnt.h' */
  447.     tt_face_load_eblc,
  448.     tt_face_free_eblc,
  449.     tt_face_set_sbit_strike,
  450.     tt_face_load_strike_metrics,
  451. #else
  452.     0,
  453.     0,
  454.     0,
  455.     0,
  456. #endif
  457.     tt_face_get_metrics
  458.   };
  459.   FT_CALLBACK_TABLE_DEF
  460.   const FT_Module_Class  sfnt_module_class =
  461.   {
  462.     0,  /* not a font driver or renderer */
  463.     sizeof( FT_ModuleRec ),
  464.     "sfnt",     /* driver name                            */
  465.     0x10000L,   /* driver version 1.0                     */
  466.     0x20000L,   /* driver requires FreeType 2.0 or higher */
  467.     (const void*)&sfnt_interface,  /* module specific interface */
  468.     (FT_Module_Constructor)0,
  469.     (FT_Module_Destructor) 0,
  470.     (FT_Module_Requester)  sfnt_get_interface
  471.   };
  472. /* END */