web/Zend/Pdf/Font.php
changeset 0 4eba9c11703f
equal deleted inserted replaced
-1:000000000000 0:4eba9c11703f
       
     1 <?php
       
     2 /**
       
     3  * Zend Framework
       
     4  *
       
     5  * LICENSE
       
     6  *
       
     7  * This source file is subject to the new BSD license that is bundled
       
     8  * with this package in the file LICENSE.txt.
       
     9  * It is also available through the world-wide-web at this URL:
       
    10  * http://framework.zend.com/license/new-bsd
       
    11  * If you did not receive a copy of the license and are unable to
       
    12  * obtain it through the world-wide-web, please send an email
       
    13  * to license@zend.com so we can send you a copy immediately.
       
    14  *
       
    15  * @category   Zend
       
    16  * @package    Zend_Pdf
       
    17  * @subpackage Fonts
       
    18  * @copyright  Copyright (c) 2005-2010 Zend Technologies USA Inc. (http://www.zend.com)
       
    19  * @license    http://framework.zend.com/license/new-bsd     New BSD License
       
    20  * @version    $Id: Font.php 20211 2010-01-12 02:14:29Z yoshida@zend.co.jp $
       
    21  */
       
    22 
       
    23 
       
    24 /**
       
    25  * Abstract factory class which vends {@link Zend_Pdf_Resource_Font} objects.
       
    26  *
       
    27  * Font objects themselves are normally instantiated through the factory methods
       
    28  * {@link fontWithName()} or {@link fontWithPath()}.
       
    29  *
       
    30  * This class is also the home for font-related constants because the name of
       
    31  * the true base class ({@link Zend_Pdf_Resource_Font}) is not intuitive for the
       
    32  * end user.
       
    33  *
       
    34  * @package    Zend_Pdf
       
    35  * @subpackage Fonts
       
    36  * @copyright  Copyright (c) 2005-2010 Zend Technologies USA Inc. (http://www.zend.com)
       
    37  * @license    http://framework.zend.com/license/new-bsd     New BSD License
       
    38  */
       
    39 abstract class Zend_Pdf_Font
       
    40 {
       
    41   /**** Class Constants ****/
       
    42 
       
    43 
       
    44   /* Font Types */
       
    45 
       
    46     /**
       
    47      * Unknown font type.
       
    48      */
       
    49     const TYPE_UNKNOWN = 0;
       
    50 
       
    51     /**
       
    52      * One of the standard 14 PDF fonts.
       
    53      */
       
    54     const TYPE_STANDARD = 1;
       
    55 
       
    56     /**
       
    57      * A PostScript Type 1 font.
       
    58      */
       
    59     const TYPE_TYPE_1 = 2;
       
    60 
       
    61     /**
       
    62      * A TrueType font or an OpenType font containing TrueType outlines.
       
    63      */
       
    64     const TYPE_TRUETYPE = 3;
       
    65 
       
    66     /**
       
    67      * Type 0 composite font.
       
    68      */
       
    69     const TYPE_TYPE_0 = 4;
       
    70 
       
    71     /**
       
    72      * CID font containing a PostScript Type 1 font.
       
    73      * These fonts are used only to construct Type 0 composite fonts and can't be used directly
       
    74      */
       
    75     const TYPE_CIDFONT_TYPE_0 = 5;
       
    76 
       
    77     /**
       
    78      * CID font containing a TrueType font or an OpenType font containing TrueType outlines.
       
    79      * These fonts are used only to construct Type 0 composite fonts and can't be used directly
       
    80      */
       
    81     const TYPE_CIDFONT_TYPE_2 = 6;
       
    82 
       
    83 
       
    84   /* Names of the Standard 14 PDF Fonts */
       
    85 
       
    86     /**
       
    87      * Name of the standard PDF font Courier.
       
    88      */
       
    89     const FONT_COURIER = 'Courier';
       
    90 
       
    91     /**
       
    92      * Name of the bold style of the standard PDF font Courier.
       
    93      */
       
    94     const FONT_COURIER_BOLD = 'Courier-Bold';
       
    95 
       
    96     /**
       
    97      * Name of the italic style of the standard PDF font Courier.
       
    98      */
       
    99     const FONT_COURIER_OBLIQUE = 'Courier-Oblique';
       
   100 
       
   101     /**
       
   102      * Convenience constant for a common misspelling of
       
   103      * {@link FONT_COURIER_OBLIQUE}.
       
   104      */
       
   105     const FONT_COURIER_ITALIC = 'Courier-Oblique';
       
   106 
       
   107     /**
       
   108      * Name of the bold and italic style of the standard PDF font Courier.
       
   109      */
       
   110     const FONT_COURIER_BOLD_OBLIQUE = 'Courier-BoldOblique';
       
   111 
       
   112     /**
       
   113      * Convenience constant for a common misspelling of
       
   114      * {@link FONT_COURIER_BOLD_OBLIQUE}.
       
   115      */
       
   116     const FONT_COURIER_BOLD_ITALIC = 'Courier-BoldOblique';
       
   117 
       
   118     /**
       
   119      * Name of the standard PDF font Helvetica.
       
   120      */
       
   121     const FONT_HELVETICA = 'Helvetica';
       
   122 
       
   123     /**
       
   124      * Name of the bold style of the standard PDF font Helvetica.
       
   125      */
       
   126     const FONT_HELVETICA_BOLD = 'Helvetica-Bold';
       
   127 
       
   128     /**
       
   129      * Name of the italic style of the standard PDF font Helvetica.
       
   130      */
       
   131     const FONT_HELVETICA_OBLIQUE = 'Helvetica-Oblique';
       
   132 
       
   133     /**
       
   134      * Convenience constant for a common misspelling of
       
   135      * {@link FONT_HELVETICA_OBLIQUE}.
       
   136      */
       
   137     const FONT_HELVETICA_ITALIC = 'Helvetica-Oblique';
       
   138 
       
   139     /**
       
   140      * Name of the bold and italic style of the standard PDF font Helvetica.
       
   141      */
       
   142     const FONT_HELVETICA_BOLD_OBLIQUE = 'Helvetica-BoldOblique';
       
   143 
       
   144     /**
       
   145      * Convenience constant for a common misspelling of
       
   146      * {@link FONT_HELVETICA_BOLD_OBLIQUE}.
       
   147      */
       
   148     const FONT_HELVETICA_BOLD_ITALIC = 'Helvetica-BoldOblique';
       
   149 
       
   150     /**
       
   151      * Name of the standard PDF font Symbol.
       
   152      */
       
   153     const FONT_SYMBOL = 'Symbol';
       
   154 
       
   155     /**
       
   156      * Name of the standard PDF font Times.
       
   157      */
       
   158     const FONT_TIMES_ROMAN = 'Times-Roman';
       
   159 
       
   160     /**
       
   161      * Convenience constant for a common misspelling of
       
   162      * {@link FONT_TIMES_ROMAN}.
       
   163      */
       
   164     const FONT_TIMES = 'Times-Roman';
       
   165 
       
   166     /**
       
   167      * Name of the bold style of the standard PDF font Times.
       
   168      */
       
   169     const FONT_TIMES_BOLD = 'Times-Bold';
       
   170 
       
   171     /**
       
   172      * Name of the italic style of the standard PDF font Times.
       
   173      */
       
   174     const FONT_TIMES_ITALIC = 'Times-Italic';
       
   175 
       
   176     /**
       
   177      * Name of the bold and italic style of the standard PDF font Times.
       
   178      */
       
   179     const FONT_TIMES_BOLD_ITALIC = 'Times-BoldItalic';
       
   180 
       
   181     /**
       
   182      * Name of the standard PDF font Zapf Dingbats.
       
   183      */
       
   184     const FONT_ZAPFDINGBATS = 'ZapfDingbats';
       
   185 
       
   186 
       
   187   /* Font Name String Types */
       
   188 
       
   189     /**
       
   190      * Full copyright notice for the font.
       
   191      */
       
   192     const NAME_COPYRIGHT =  0;
       
   193 
       
   194     /**
       
   195      * Font family name. Used to group similar styles of fonts together.
       
   196      */
       
   197     const NAME_FAMILY =  1;
       
   198 
       
   199     /**
       
   200      * Font style within the font family. Examples: Regular, Italic, Bold, etc.
       
   201      */
       
   202     const NAME_STYLE =  2;
       
   203 
       
   204     /**
       
   205      * Unique font identifier.
       
   206      */
       
   207     const NAME_ID =  3;
       
   208 
       
   209     /**
       
   210      * Full font name. Usually a combination of the {@link NAME_FAMILY} and
       
   211      * {@link NAME_STYLE} strings.
       
   212      */
       
   213     const NAME_FULL =  4;
       
   214 
       
   215     /**
       
   216      * Version number of the font.
       
   217      */
       
   218     const NAME_VERSION =  5;
       
   219 
       
   220     /**
       
   221      * PostScript name for the font. This is the name used to identify fonts
       
   222      * internally and within the PDF file.
       
   223      */
       
   224     const NAME_POSTSCRIPT =  6;
       
   225 
       
   226     /**
       
   227      * Font trademark notice. This is distinct from the {@link NAME_COPYRIGHT}.
       
   228      */
       
   229     const NAME_TRADEMARK =  7;
       
   230 
       
   231     /**
       
   232      * Name of the font manufacturer.
       
   233      */
       
   234     const NAME_MANUFACTURER =  8;
       
   235 
       
   236     /**
       
   237      * Name of the designer of the font.
       
   238      */
       
   239     const NAME_DESIGNER =  9;
       
   240 
       
   241     /**
       
   242      * Description of the font. May contain revision information, usage
       
   243      * recommendations, features, etc.
       
   244      */
       
   245     const NAME_DESCRIPTION = 10;
       
   246 
       
   247     /**
       
   248      * URL of the font vendor. Some fonts may contain a unique serial number
       
   249      * embedded in this URL, which is used for licensing.
       
   250      */
       
   251     const NAME_VENDOR_URL = 11;
       
   252 
       
   253     /**
       
   254      * URL of the font designer ({@link NAME_DESIGNER}).
       
   255      */
       
   256     const NAME_DESIGNER_URL = 12;
       
   257 
       
   258     /**
       
   259      * Plain language licensing terms for the font.
       
   260      */
       
   261     const NAME_LICENSE = 13;
       
   262 
       
   263     /**
       
   264      * URL of more detailed licensing information for the font.
       
   265      */
       
   266     const NAME_LICENSE_URL = 14;
       
   267 
       
   268     /**
       
   269      * Preferred font family. Used by some fonts to work around a Microsoft
       
   270      * Windows limitation where only four fonts styles can share the same
       
   271      * {@link NAME_FAMILY} value.
       
   272      */
       
   273     const NAME_PREFERRED_FAMILY = 16;
       
   274 
       
   275     /**
       
   276      * Preferred font style. A more descriptive string than {@link NAME_STYLE}.
       
   277      */
       
   278     const NAME_PREFERRED_STYLE = 17;
       
   279 
       
   280     /**
       
   281      * Suggested text to use as a representative sample of the font.
       
   282      */
       
   283     const NAME_SAMPLE_TEXT = 19;
       
   284 
       
   285     /**
       
   286      * PostScript CID findfont name.
       
   287      */
       
   288     const NAME_CID_NAME = 20;
       
   289 
       
   290 
       
   291   /* Font Weights */
       
   292 
       
   293     /**
       
   294      * Thin font weight.
       
   295      */
       
   296     const WEIGHT_THIN = 100;
       
   297 
       
   298     /**
       
   299      * Extra-light (Ultra-light) font weight.
       
   300      */
       
   301     const WEIGHT_EXTRA_LIGHT = 200;
       
   302 
       
   303     /**
       
   304      * Light font weight.
       
   305      */
       
   306     const WEIGHT_LIGHT = 300;
       
   307 
       
   308     /**
       
   309      * Normal (Regular) font weight.
       
   310      */
       
   311     const WEIGHT_NORMAL = 400;
       
   312 
       
   313     /**
       
   314      * Medium font weight.
       
   315      */
       
   316     const WEIGHT_MEDIUM = 500;
       
   317 
       
   318     /**
       
   319      * Semi-bold (Demi-bold) font weight.
       
   320      */
       
   321     const WEIGHT_SEMI_BOLD = 600;
       
   322 
       
   323     /**
       
   324      * Bold font weight.
       
   325      */
       
   326     const WEIGHT_BOLD = 700;
       
   327 
       
   328     /**
       
   329      * Extra-bold (Ultra-bold) font weight.
       
   330      */
       
   331     const WEIGHT_EXTRA_BOLD = 800;
       
   332 
       
   333     /**
       
   334      * Black (Heavy) font weight.
       
   335      */
       
   336     const WEIGHT_BLACK = 900;
       
   337 
       
   338 
       
   339   /* Font Widths */
       
   340 
       
   341     /**
       
   342      * Ultra-condensed font width. Typically 50% of normal.
       
   343      */
       
   344     const WIDTH_ULTRA_CONDENSED = 1;
       
   345 
       
   346     /**
       
   347      * Extra-condensed font width. Typically 62.5% of normal.
       
   348      */
       
   349     const WIDTH_EXTRA_CONDENSED = 2;
       
   350 
       
   351     /**
       
   352      * Condensed font width. Typically 75% of normal.
       
   353      */
       
   354     const WIDTH_CONDENSED = 3;
       
   355 
       
   356     /**
       
   357      * Semi-condensed font width. Typically 87.5% of normal.
       
   358      */
       
   359     const WIDTH_SEMI_CONDENSED = 4;
       
   360 
       
   361     /**
       
   362      * Normal (Medium) font width.
       
   363      */
       
   364     const WIDTH_NORMAL = 5;
       
   365 
       
   366     /**
       
   367      * Semi-expanded font width. Typically 112.5% of normal.
       
   368      */
       
   369     const WIDTH_SEMI_EXPANDED = 6;
       
   370 
       
   371     /**
       
   372      * Expanded font width. Typically 125% of normal.
       
   373      */
       
   374     const WIDTH_EXPANDED = 7;
       
   375 
       
   376     /**
       
   377      * Extra-expanded font width. Typically 150% of normal.
       
   378      */
       
   379     const WIDTH_EXTRA_EXPANDED = 8;
       
   380 
       
   381     /**
       
   382      * Ultra-expanded font width. Typically 200% of normal.
       
   383      */
       
   384     const WIDTH_ULTRA_EXPANDED = 9;
       
   385 
       
   386 
       
   387   /* Font Embedding Options */
       
   388 
       
   389     /**
       
   390      * Do not embed the font in the PDF document.
       
   391      */
       
   392     const EMBED_DONT_EMBED = 0x01;
       
   393 
       
   394     /**
       
   395      * Embed, but do not subset the font in the PDF document.
       
   396      */
       
   397     const EMBED_DONT_SUBSET = 0x02;
       
   398 
       
   399     /**
       
   400      * Embed, but do not compress the font in the PDF document.
       
   401      */
       
   402     const EMBED_DONT_COMPRESS = 0x04;
       
   403 
       
   404     /**
       
   405      * Suppress the exception normally thrown if the font cannot be embedded
       
   406      * due to its copyright bits being set.
       
   407      */
       
   408     const EMBED_SUPPRESS_EMBED_EXCEPTION = 0x08;
       
   409 
       
   410 
       
   411 
       
   412   /**** Class Variables ****/
       
   413 
       
   414 
       
   415     /**
       
   416      * Array whose keys are the unique PostScript names of instantiated fonts.
       
   417      * The values are the font objects themselves.
       
   418      * @var array
       
   419      */
       
   420     private static $_fontNames = array();
       
   421 
       
   422     /**
       
   423      * Array whose keys are the md5 hash of the full paths on disk for parsed
       
   424      * fonts. The values are the font objects themselves.
       
   425      * @var array
       
   426      */
       
   427     private static $_fontFilePaths = array();
       
   428 
       
   429 
       
   430 
       
   431   /**** Public Interface ****/
       
   432 
       
   433 
       
   434   /* Factory Methods */
       
   435 
       
   436     /**
       
   437      * Returns a {@link Zend_Pdf_Resource_Font} object by full name.
       
   438      *
       
   439      * This is the preferred method to obtain one of the standard 14 PDF fonts.
       
   440      *
       
   441      * The result of this method is cached, preventing unnecessary duplication
       
   442      * of font objects. Repetitive calls for a font with the same name will
       
   443      * return the same object.
       
   444      *
       
   445      * The $embeddingOptions parameter allows you to set certain flags related
       
   446      * to font embedding. You may combine options by OR-ing them together. See
       
   447      * the EMBED_ constants defined in {@link Zend_Pdf_Font} for the list of
       
   448      * available options and their descriptions. Note that this value is only
       
   449      * used when creating a font for the first time. If a font with the same
       
   450      * name already exists, you will get that object and the options you specify
       
   451      * here will be ignored. This is because fonts are only embedded within the
       
   452      * PDF file once.
       
   453      *
       
   454      * If the font name supplied does not match the name of a previously
       
   455      * instantiated object and it is not one of the 14 standard PDF fonts, an
       
   456      * exception will be thrown.
       
   457      *
       
   458      * @param string $name Full PostScript name of font.
       
   459      * @param integer $embeddingOptions (optional) Options for font embedding.
       
   460      * @return Zend_Pdf_Resource_Font
       
   461      * @throws Zend_Pdf_Exception
       
   462      */
       
   463     public static function fontWithName($name, $embeddingOptions = 0)
       
   464         {
       
   465         /* First check the cache. Don't duplicate font objects.
       
   466          */
       
   467         if (isset(Zend_Pdf_Font::$_fontNames[$name])) {
       
   468             return Zend_Pdf_Font::$_fontNames[$name];
       
   469         }
       
   470 
       
   471         /**
       
   472          * @todo It would be cool to be able to have a mapping of font names to
       
   473          *   file paths in a configuration file for frequently used custom
       
   474          *   fonts. This would allow a user to use custom fonts without having
       
   475          *   to hard-code file paths all over the place. Table this idea until
       
   476          *   {@link Zend_Config} is ready.
       
   477          */
       
   478 
       
   479         /* Not an existing font and no mapping in the config file. Check to see
       
   480          * if this is one of the standard 14 PDF fonts.
       
   481          */
       
   482         switch ($name) {
       
   483             case Zend_Pdf_Font::FONT_COURIER:
       
   484                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/Courier.php';
       
   485                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_Courier();
       
   486                 break;
       
   487 
       
   488             case Zend_Pdf_Font::FONT_COURIER_BOLD:
       
   489                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/CourierBold.php';
       
   490                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_CourierBold();
       
   491                 break;
       
   492 
       
   493             case Zend_Pdf_Font::FONT_COURIER_OBLIQUE:
       
   494                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/CourierOblique.php';
       
   495                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_CourierOblique();
       
   496                 break;
       
   497 
       
   498             case Zend_Pdf_Font::FONT_COURIER_BOLD_OBLIQUE:
       
   499                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/CourierBoldOblique.php';
       
   500                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_CourierBoldOblique();
       
   501                 break;
       
   502 
       
   503             case Zend_Pdf_Font::FONT_HELVETICA:
       
   504                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/Helvetica.php';
       
   505                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_Helvetica();
       
   506                 break;
       
   507 
       
   508             case Zend_Pdf_Font::FONT_HELVETICA_BOLD:
       
   509                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/HelveticaBold.php';
       
   510                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_HelveticaBold();
       
   511                 break;
       
   512 
       
   513             case Zend_Pdf_Font::FONT_HELVETICA_OBLIQUE:
       
   514                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/HelveticaOblique.php';
       
   515                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_HelveticaOblique();
       
   516                 break;
       
   517 
       
   518             case Zend_Pdf_Font::FONT_HELVETICA_BOLD_OBLIQUE:
       
   519                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/HelveticaBoldOblique.php';
       
   520                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_HelveticaBoldOblique();
       
   521                 break;
       
   522 
       
   523             case Zend_Pdf_Font::FONT_SYMBOL:
       
   524                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/Symbol.php';
       
   525                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_Symbol();
       
   526                 break;
       
   527 
       
   528             case Zend_Pdf_Font::FONT_TIMES_ROMAN:
       
   529                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/TimesRoman.php';
       
   530                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_TimesRoman();
       
   531                 break;
       
   532 
       
   533             case Zend_Pdf_Font::FONT_TIMES_BOLD:
       
   534                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/TimesBold.php';
       
   535                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_TimesBold();
       
   536                 break;
       
   537 
       
   538             case Zend_Pdf_Font::FONT_TIMES_ITALIC:
       
   539                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/TimesItalic.php';
       
   540                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_TimesItalic();
       
   541                 break;
       
   542 
       
   543             case Zend_Pdf_Font::FONT_TIMES_BOLD_ITALIC:
       
   544                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/TimesBoldItalic.php';
       
   545                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_TimesBoldItalic();
       
   546                 break;
       
   547 
       
   548             case Zend_Pdf_Font::FONT_ZAPFDINGBATS:
       
   549                 require_once 'Zend/Pdf/Resource/Font/Simple/Standard/ZapfDingbats.php';
       
   550                 $font = new Zend_Pdf_Resource_Font_Simple_Standard_ZapfDingbats();
       
   551                 break;
       
   552 
       
   553             default:
       
   554                 require_once 'Zend/Pdf/Exception.php';
       
   555                 throw new Zend_Pdf_Exception("Unknown font name: $name",
       
   556                                              Zend_Pdf_Exception::BAD_FONT_NAME);
       
   557         }
       
   558 
       
   559         /* Add this new font to the cache array and return it for use.
       
   560          */
       
   561         Zend_Pdf_Font::$_fontNames[$name] = $font;
       
   562         return $font;
       
   563     }
       
   564 
       
   565     /**
       
   566      * Returns a {@link Zend_Pdf_Resource_Font} object by file path.
       
   567      *
       
   568      * The result of this method is cached, preventing unnecessary duplication
       
   569      * of font objects. Repetitive calls for the font with the same path will
       
   570      * return the same object.
       
   571      *
       
   572      * The $embeddingOptions parameter allows you to set certain flags related
       
   573      * to font embedding. You may combine options by OR-ing them together. See
       
   574      * the EMBED_ constants defined in {@link Zend_Pdf_Font} for the list of
       
   575      * available options and their descriptions. Note that this value is only
       
   576      * used when creating a font for the first time. If a font with the same
       
   577      * name already exists, you will get that object and the options you specify
       
   578      * here will be ignored. This is because fonts are only embedded within the
       
   579      * PDF file once.
       
   580      *
       
   581      * If the file path supplied does not match the path of a previously
       
   582      * instantiated object or the font type cannot be determined, an exception
       
   583      * will be thrown.
       
   584      *
       
   585      * @param string $filePath Full path to the font file.
       
   586      * @param integer $embeddingOptions (optional) Options for font embedding.
       
   587      * @return Zend_Pdf_Resource_Font
       
   588      * @throws Zend_Pdf_Exception
       
   589      */
       
   590     public static function fontWithPath($filePath, $embeddingOptions = 0)
       
   591     {
       
   592         /* First check the cache. Don't duplicate font objects.
       
   593          */
       
   594         $filePathKey = md5($filePath);
       
   595         if (isset(Zend_Pdf_Font::$_fontFilePaths[$filePathKey])) {
       
   596             return Zend_Pdf_Font::$_fontFilePaths[$filePathKey];
       
   597         }
       
   598 
       
   599         /* Create a file parser data source object for this file. File path and
       
   600          * access permission checks are handled here.
       
   601          */
       
   602         require_once 'Zend/Pdf/FileParserDataSource/File.php';
       
   603         $dataSource = new Zend_Pdf_FileParserDataSource_File($filePath);
       
   604 
       
   605         /* Attempt to determine the type of font. We can't always trust file
       
   606          * extensions, but try that first since it's fastest.
       
   607          */
       
   608         $fileExtension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
       
   609 
       
   610         /* If it turns out that the file is named improperly and we guess the
       
   611          * wrong type, we'll get null instead of a font object.
       
   612          */
       
   613         switch ($fileExtension) {
       
   614             case 'ttf':
       
   615                 $font = Zend_Pdf_Font::_extractTrueTypeFont($dataSource, $embeddingOptions);
       
   616                 break;
       
   617 
       
   618             default:
       
   619                 /* Unrecognized extension. Try to determine the type by actually
       
   620                  * parsing it below.
       
   621                  */
       
   622                 $font = null;
       
   623                 break;
       
   624         }
       
   625 
       
   626 
       
   627         if ($font === null) {
       
   628             /* There was no match for the file extension or the extension was
       
   629              * wrong. Attempt to detect the type of font by actually parsing it.
       
   630              * We'll do the checks in order of most likely format to try to
       
   631              * reduce the detection time.
       
   632              */
       
   633 
       
   634             // OpenType
       
   635 
       
   636             // TrueType
       
   637             if (($font === null) && ($fileExtension != 'ttf')) {
       
   638                 $font = Zend_Pdf_Font::_extractTrueTypeFont($dataSource, $embeddingOptions);
       
   639             }
       
   640 
       
   641             // Type 1 PostScript
       
   642 
       
   643             // Mac OS X dfont
       
   644 
       
   645             // others?
       
   646         }
       
   647 
       
   648 
       
   649         /* Done with the data source object.
       
   650          */
       
   651         $dataSource = null;
       
   652 
       
   653         if ($font !== null) {
       
   654             /* Parsing was successful. Add this font instance to the cache arrays
       
   655              * and return it for use.
       
   656              */
       
   657             $fontName = $font->getFontName(Zend_Pdf_Font::NAME_POSTSCRIPT, '', '');
       
   658             Zend_Pdf_Font::$_fontNames[$fontName] = $font;
       
   659             $filePathKey = md5($filePath);
       
   660             Zend_Pdf_Font::$_fontFilePaths[$filePathKey] = $font;
       
   661             return $font;
       
   662 
       
   663         } else {
       
   664             /* The type of font could not be determined. Give up.
       
   665              */
       
   666             require_once 'Zend/Pdf/Exception.php';
       
   667             throw new Zend_Pdf_Exception("Cannot determine font type: $filePath",
       
   668                                          Zend_Pdf_Exception::CANT_DETERMINE_FONT_TYPE);
       
   669          }
       
   670 
       
   671     }
       
   672 
       
   673 
       
   674 
       
   675   /**** Internal Methods ****/
       
   676 
       
   677 
       
   678   /* Font Extraction Methods */
       
   679 
       
   680     /**
       
   681      * Attempts to extract a TrueType font from the data source.
       
   682      *
       
   683      * If the font parser throws an exception that suggests the data source
       
   684      * simply doesn't contain a TrueType font, catches it and returns null. If
       
   685      * an exception is thrown that suggests the TrueType font is corrupt or
       
   686      * otherwise unusable, throws that exception. If successful, returns the
       
   687      * font object.
       
   688      *
       
   689      * @param Zend_Pdf_FileParserDataSource $dataSource
       
   690      * @param integer $embeddingOptions Options for font embedding.
       
   691      * @return Zend_Pdf_Resource_Font_OpenType_TrueType May also return null if
       
   692      *   the data source does not appear to contain a TrueType font.
       
   693      * @throws Zend_Pdf_Exception
       
   694      */
       
   695     protected static function _extractTrueTypeFont($dataSource, $embeddingOptions)
       
   696     {
       
   697         try {
       
   698             require_once 'Zend/Pdf/FileParser/Font/OpenType/TrueType.php';
       
   699             $fontParser = new Zend_Pdf_FileParser_Font_OpenType_TrueType($dataSource);
       
   700 
       
   701             $fontParser->parse();
       
   702             if ($fontParser->isAdobeLatinSubset) {
       
   703                 require_once 'Zend/Pdf/Resource/Font/Simple/Parsed/TrueType.php';
       
   704                 $font = new Zend_Pdf_Resource_Font_Simple_Parsed_TrueType($fontParser, $embeddingOptions);
       
   705             } else {
       
   706                 require_once 'Zend/Pdf/Resource/Font/CidFont/TrueType.php';
       
   707                 require_once 'Zend/Pdf/Resource/Font/Type0.php';
       
   708                 /* Use Composite Type 0 font which supports Unicode character mapping */
       
   709                 $cidFont = new Zend_Pdf_Resource_Font_CidFont_TrueType($fontParser, $embeddingOptions);
       
   710                 $font    = new Zend_Pdf_Resource_Font_Type0($cidFont);
       
   711             }
       
   712         } catch (Zend_Pdf_Exception $e) {
       
   713             /* The following exception codes suggest that this isn't really a
       
   714              * TrueType font. If we caught such an exception, simply return
       
   715              * null. For all other cases, it probably is a TrueType font but has
       
   716              * a problem; throw the exception again.
       
   717              */
       
   718             $fontParser = null;
       
   719             require_once 'Zend/Pdf/Exception.php';
       
   720             switch ($e->getCode()) {
       
   721                 case Zend_Pdf_Exception::WRONG_FONT_TYPE:    // break intentionally omitted
       
   722                 case Zend_Pdf_Exception::BAD_TABLE_COUNT:    // break intentionally omitted
       
   723                 case Zend_Pdf_Exception::BAD_MAGIC_NUMBER:
       
   724                     return null;
       
   725 
       
   726                 default:
       
   727                     throw new Zend_Pdf_Exception($e->getMessage(), $e->getCode(), $e);
       
   728             }
       
   729         }
       
   730         return $font;
       
   731     }
       
   732 }