Documentation TYPO3 par Ameos

fpdf.php

00001 <?php
00002 /* $Id: fpdf.php,v 2.1 2003/11/20 16:31:51 garvinhicking Exp $ */
00003 // vim: expandtab sw=4 ts=4 sts=4:
00004 
00005 /****************************************************************************
00006 * Software : FPDF                                                           *
00007 * Version :  1.51                                                           *
00008 * Date :     2002/08/03                                                     *
00009 * Author :   Olivier PLATHEY                                                *
00010 * Website :  http://www.fpdf.org                                            *
00011 * Licence :  Freeware                                                       *
00012 *                                                                           *
00013 * You are entitled to modify this soft as you want to.                      *
00014 ****************************************************************************/
00015 
00016 
00017 $FPDF_version = (string) '1.51';
00018 
00019 
00023 class FPDF
00024 {
00028     var $page;               // current page number
00029     var $n;                  // current object number
00030     var $offsets;            // array of object offsets
00031     var $buffer;             // buffer holding in-memory PDF
00032     var $pages;              // array containing pages
00033     var $state;              // current document state
00034     var $compress;           // compression flag
00035     var $DefOrientation;     // default orientation
00036     var $CurOrientation;     // current orientation
00037     var $OrientationChanges; // array indicating orientation changes
00038     var $fwPt, $fhPt;        // dimensions of page format in points
00039     var $fw, $fh;            // dimensions of page format in user unit
00040     var $wPt, $hPt;          // current dimensions of page in points
00041     var $k;                  // scale factor (number of points in user unit)
00042     var $w, $h;              // current dimensions of page in user unit
00043     var $lMargin;            // left margin
00044     var $tMargin;            // top margin
00045     var $rMargin;            // right margin
00046     var $bMargin;            // page break margin
00047     var $cMargin;            // cell margin
00048     var $x, $y;              // current position in user unit for cell positionning
00049     var $lasth;              // height of last cell printed
00050     var $LineWidth;          // line width in user unit
00051     var $CoreFonts;          // array of standard font names
00052     var $fonts;              // array of used fonts
00053     var $FontFiles;          // array of font files
00054     var $diffs;              // array of encoding differences
00055     var $images;             // array of used images
00056     var $PageLinks;          // array of links in pages
00057     var $links;              // array of internal links
00058     var $FontFamily;         // current font family
00059     var $FontStyle;          // current font style
00060     var $CurrentFont;        // current font info
00061     var $FontSizePt;         // current font size in points
00062     var $FontSize;           // current font size in user unit
00063     var $DrawColor;          // commands for drawing color
00064     var $FillColor;          // commands for filling color
00065     var $TextColor;          // commands for text color
00066     var $ColorFlag;          // indicates whether fill and text colors are different
00067     var $ws;                 // word spacing
00068     var $underline;          // whether underline is current state or not
00069     var $AutoPageBreak;      // automatic page breaking
00070     var $PageBreakTrigger;   // threshold used to trigger page breaks
00071     var $InFooter;           // flag set when processing footer
00072     var $ZoomMode;           // zoom display mode
00073     var $LayoutMode;         // layout display mode
00074     var $title;              // title
00075     var $subject;            // subject
00076     var $author;             // author
00077     var $keywords;           // keywords
00078     var $creator;            // creator
00079     var $AliasNbPages;       // alias for total number of pages
00080 
00081 
00082 
00083     /**************************************************************************
00084     *                                                                         *
00085     *      Public methods below are used by some private ones. Then they      *
00086     *      are placed at the top of the class.                                *
00087     *                                                                         *
00088     **************************************************************************/
00089 
00099     function GetStringWidth($s)
00100     {
00101         $s     = (string) $s;
00102         // loic1: PHP3 compatibility
00103         // $cw    = &$this->CurrentFont['cw'];
00104         $w     = 0;
00105         $l     = strlen($s);
00106         for ($i = 0; $i < $l; $i++) {
00107             // $w += $cw[$s[$i]];
00108             $w += $this->CurrentFont['cw'][$s[$i]];
00109         } // end for
00110 
00111         return $w * $this->FontSize / 1000;
00112     } // end of the "GetStringWidth()" method
00113 
00114 
00122     function Error($msg)
00123     {
00124         die('<b>FPDF error: </b>' . $msg);
00125     } // end of the "Error()" method
00126 
00127 
00128 
00129     /**************************************************************************
00130     *                                                                         *
00131     *                             Private methods                             *
00132     *                                                                         *
00133     **************************************************************************/
00134 
00142     function _out($s)
00143     {
00144         if ($this->state == 2) {
00145             $this->pages[$this->page] .= $s . "\n";
00146         } else {
00147             $this->buffer             .= $s . "\n";
00148         }
00149     } // end of the "_out()" method
00150 
00151 
00157     function _newobj()
00158     {
00159         $this->n++;
00160         $this->offsets[$this->n] = strlen($this->buffer);
00161         $this->_out($this->n . ' 0 obj');
00162     } // end of the "_newobj()" method
00163 
00164 
00174     function _escape($s)
00175     {
00176         return str_replace(')', '\\)', str_replace('(', '\\(', str_replace('\\', '\\\\', $s)));
00177     } // end of the "_escape()" method
00178 
00179 
00191     function _textstring($s)
00192     {
00193         return '(' . $this->_escape($s) . ')';
00194     } // end of the "_textstring()" method
00195 
00196 
00206     function _putstream($s)
00207     {
00208         $this->_out('stream');
00209         $this->_out($s);
00210         $this->_out('endstream');
00211     } // end of the "_putstream()" method
00212 
00213 
00219     function _begindoc()
00220     {
00221         $this->state = 1;
00222         $this->_out('%PDF-1.3');
00223     } // end of the "_begindoc()" method
00224 
00225 
00231     function _putpages()
00232     {
00233         $nb = $this->page;
00234 
00235         if (!empty($this->AliasNbPages)) {
00236             // Replaces number of pages
00237             for ($n = 1; $n <= $nb; $n++) {
00238                 $this->pages[$n] = str_replace($this->AliasNbPages, $nb, $this->pages[$n]);
00239             }
00240         }
00241         if ($this->DefOrientation == 'P') {
00242             $wPt = $this->fwPt;
00243             $hPt = $this->fhPt;
00244         } else {
00245             $wPt = $this->fhPt;
00246             $hPt = $this->fwPt;
00247         }
00248         $filter = ($this->compress) ? '/Filter /FlateDecode ' : '';
00249 
00250         for ($n=1; $n <= $nb; $n++) {
00251             // Page
00252             $this->_newobj();
00253             $this->_out('<</Type /Page');
00254             $this->_out('/Parent 1 0 R');
00255             if (isset($this->OrientationChanges[$n])) {
00256                 $this->_out(sprintf('/MediaBox [0 0 %.2f %.2f]', $hPt, $wPt));
00257             }
00258             $this->_out('/Resources 2 0 R');
00259             if (isset($this->PageLinks[$n])) {
00260                 // Links
00261                 $annots         = '/Annots [';
00262                 reset($this->PageLinks[$n]);
00263                 while (list(, $pl) = each($this->PageLinks[$n])) {
00264                     $rect       = sprintf('%.2f %.2f %.2f %.2f', $pl[0], $pl[1], $pl[0] + $pl[2], $pl[1] - $pl[3]);
00265                     $annots     .= '<</Type /Annot /Subtype /Link /Rect [' . $rect . '] /Border [0 0 0] ';
00266                     if (is_string($pl[4])) {
00267                         $annots .= '/A <</S /URI /URI ' . $this->_textstring($pl[4]) . '>>>>';
00268                     }
00269                     else {
00270                         $l      = $this->links[$pl[4]];
00271                         $h      = isset($this->OrientationChanges[$l[0]]) ? $wPt : $hPt;
00272                         $annots .= sprintf('/Dest [%d 0 R /XYZ 0 %.2f null]>>', 1 + 2 * $l[0], $h - $l[1] * $this->k);
00273                     }
00274                 } // end while
00275                 $this->_out($annots . ']');
00276             } // end if
00277             $this->_out('/Contents ' . ($this->n+1).' 0 R>>');
00278             $this->_out('endobj');
00279 
00280             // Page content
00281             $p = ($this->compress) ? gzcompress($this->pages[$n]) : $this->pages[$n];
00282             $this->_newobj();
00283             $this->_out('<<' . $filter . '/Length ' . strlen($p) . '>>');
00284             $this->_putstream($p);
00285             $this->_out('endobj');
00286         } // end for
00287 
00288         // Pages root
00289         $this->offsets[1]=strlen($this->buffer);
00290         $this->_out('1 0 obj');
00291         $this->_out('<</Type /Pages');
00292         $kids     = '/Kids [';
00293         for ($i = 0; $i < $nb; $i++) {
00294             $kids .= (3 + 2 * $i) . ' 0 R ';
00295         }
00296         $this->_out($kids . ']');
00297         $this->_out('/Count ' . $nb);
00298         $this->_out(sprintf('/MediaBox [0 0 %.2f %.2f]', $wPt, $hPt));
00299         $this->_out('>>');
00300         $this->_out('endobj');
00301     } // end of the "_putpages()" method
00302 
00303 
00309     function _putfonts()
00310     {
00311         $nf = $this->n;
00312 
00313         foreach($this->diffs AS $diff) {
00314             // Encodings
00315             $this->_newobj();
00316             $this->_out('<</Type /Encoding /BaseEncoding /WinAnsiEncoding /Differences [' . $diff . ']>>');
00317             $this->_out('endobj');
00318         } // end while
00319 
00320         $mqr = get_magic_quotes_runtime();
00321         set_magic_quotes_runtime(0);
00322 
00323         foreach($this->FontFiles AS $file => $info) {
00324             // Font file embedding
00325             $this->_newobj();
00326             $this->FontFiles[$file]['n'] = $this->n;
00327             if (isset($GLOBALS['FPDF_font_path'])) {
00328                 $file = $GLOBALS['FPDF_font_path'] . $file;
00329             }
00330             $size     = filesize($file);
00331             if (!$size) {
00332                 $this->Error('Font file not found');
00333             }
00334             $this->_out('<</Length ' . $size);
00335             if (substr($file, -2) == '.z') {
00336                 $this->_out('/Filter /FlateDecode');
00337             }
00338             $this->_out('/Length1 ' . $info['length1']);
00339             if (isset($info['length2'])) {
00340                 $this->_out('/Length2 ' . $info['length2'] . ' /Length3 0');
00341             }
00342             $this->_out('>>');
00343             $f = fopen($file, 'rb');
00344             $this->_putstream(fread($f, $size));
00345             fclose($f);
00346             $this->_out('endobj');
00347         } // end while
00348         set_magic_quotes_runtime($mqr);
00349 
00350         foreach($this->fonts AS $k => $font) {
00351             // Font objects
00352             $this->_newobj();
00353             $this->fonts[$k]['n'] = $this->n;
00354             $name                 = $font['name'];
00355             $this->_out('<</Type /Font');
00356             $this->_out('/BaseFont /' . $name);
00357             if ($font['type'] == 'core')  {
00358                 // Standard font
00359                 $this->_out('/Subtype /Type1');
00360                 if ($name != 'Symbol' && $name != 'ZapfDingbats') {
00361                     $this->_out('/Encoding /WinAnsiEncoding');
00362                 }
00363             }
00364             else {
00365                 // Additional font
00366                 $this->_out('/Subtype /' . $font['type']);
00367                 $this->_out('/FirstChar 32');
00368                 $this->_out('/LastChar 255');
00369                 $this->_out('/Widths ' . ($this->n + 1) . ' 0 R');
00370                 $this->_out('/FontDescriptor ' . ($this->n + 2) . ' 0 R');
00371                 if ($font['enc']) {
00372                     if (isset($font['diff'])) {
00373                         $this->_out('/Encoding ' . ($nf + $font['diff']) . ' 0 R');
00374                     } else {
00375                         $this->_out('/Encoding /WinAnsiEncoding');
00376                     }
00377                 }
00378             } // end if... else...
00379             $this->_out('>>');
00380             $this->_out('endobj');
00381             if ($font['type'] != 'core')  {
00382                 // Widths
00383                 $this->_newobj();
00384                 $s     = '[';
00385                 for ($i = 32; $i <= 255; $i++) {
00386                     $s .= $font['cw'][chr($i)] . ' ';
00387                 }
00388                 $this->_out($s . ']');
00389                 $this->_out('endobj');
00390                 // Descriptor
00391                 $this->_newobj();
00392                 $s     = '<</Type /FontDescriptor /FontName /' . $name;
00393                 foreach($font['desc'] AS $k => $v) {
00394                     $s .= ' /' . $k . ' ' . $v;
00395                 }
00396                 $file = $font['file'];
00397                 if ($file) {
00398                     $s .= ' /FontFile' . ($font['type'] == 'Type1' ? '' : '2') . ' ' . $this->FontFiles[$file]['n'] . ' 0 R';
00399                 }
00400                 $this->_out($s . '>>');
00401                 $this->_out('endobj');
00402             } // end if
00403         } // end while
00404     } // end of the "_putfonts()" method
00405 
00406 
00412     function _putimages()
00413     {
00414         $filter = ($this->compress) ? '/Filter /FlateDecode ' : '';
00415 
00416         foreach($this->images AS $file => $info) {
00417             $this->_newobj();
00418             $this->images[$file]['n'] = $this->n;
00419             $this->_out('<</Type /XObject');
00420             $this->_out('/Subtype /Image');
00421             $this->_out('/Width ' . $info['w']);
00422             $this->_out('/Height ' . $info['h']);
00423             if ($info['cs'] == 'Indexed') {
00424                 $this->_out('/ColorSpace [/Indexed /DeviceRGB ' . (strlen($info['pal'])/ 3 - 1) . ' ' . ($this->n + 1) . ' 0 R]');
00425             }
00426             else {
00427                 $this->_out('/ColorSpace /' . $info['cs']);
00428                 if ($info['cs'] == 'DeviceCMYK') {
00429                     $this->_out('/Decode [1 0 1 0 1 0 1 0]');
00430                 }
00431             } // end if... else...
00432             $this->_out('/BitsPerComponent ' . $info['bpc']);
00433             $this->_out('/Filter /' . $info['f']);
00434             if (isset($info['parms'])) {
00435                 $this->_out($info['parms']);
00436             }
00437             if (isset($info['trns']) && is_array($info['trns'])) {
00438                 $trns     = '';
00439                 $trns_cnt = count($info['trns']);
00440                 for ($i = 0; $i < $trns_cnt; $i++) {
00441                     $trns .= $info['trns'][$i] . ' ' . $info['trns'][$i] . ' ';
00442                 }
00443                 $this->_out('/Mask [' . $trns . ']');
00444             } // end if
00445             $this->_out('/Length ' . strlen($info['data']) . '>>');
00446             $this->_putstream($info['data']);
00447             $this->_out('endobj');
00448 
00449             // Palette
00450             if ($info['cs'] == 'Indexed') {
00451                 $this->_newobj();
00452                 $pal = ($this->compress) ? gzcompress($info['pal']) : $info['pal'];
00453                 $this->_out('<<' . $filter . '/Length ' . strlen($pal) . '>>');
00454                 $this->_putstream($pal);
00455                 $this->_out('endobj');
00456             } // end if
00457         } // end while
00458     } // end of the "_putimages()" method
00459 
00460 
00466     function _putresources()
00467     {
00468         $this->_putfonts();
00469         $this->_putimages();
00470         // Resource dictionary
00471         $this->offsets[2] = strlen($this->buffer);
00472         $this->_out('2 0 obj');
00473         $this->_out('<</ProcSet [/PDF /Text /ImageB /ImageC /ImageI]');
00474         $this->_out('/Font <<');
00475         foreach($this->fonts AS $font) {
00476             $this->_out('/F' . $font['i'] . ' ' . $font['n'] . ' 0 R');
00477         }
00478         $this->_out('>>');
00479         if (count($this->images)) {
00480             $this->_out('/XObject <<');
00481             foreach($this->images AS $image) {
00482                 $this->_out('/I' . $image['i'] . ' ' . $image['n'] . ' 0 R');
00483             }
00484             $this->_out('>>');
00485         }
00486         $this->_out('>>');
00487         $this->_out('endobj');
00488     } // end of the "_putresources()" method
00489 
00490 
00496     function _putinfo()
00497     {
00498         // loic1: PHP3 compatibility
00499         // $this->_out('/Producer ' . $this->_textstring('FPDF ' . FPDF_VERSION));
00500         $this->_out('/Producer ' . $this->_textstring('FPDF ' . $GLOBALS['FPDF_version']));
00501         if (!empty($this->title)) {
00502             $this->_out('/Title ' . $this->_textstring($this->title));
00503         }
00504         if (!empty($this->subject)) {
00505             $this->_out('/Subject ' . $this->_textstring($this->subject));
00506         }
00507         if (!empty($this->author)) {
00508             $this->_out('/Author ' . $this->_textstring($this->author));
00509         }
00510         if (!empty($this->keywords)) {
00511             $this->_out('/Keywords ' . $this->_textstring($this->keywords));
00512         }
00513         if (!empty($this->creator)) {
00514             $this->_out('/Creator ' . $this->_textstring($this->creator));
00515         }
00516         $this->_out('/CreationDate ' . $this->_textstring('D:' . date('YmdHis')));
00517     } // end of the "_putinfo()" method
00518 
00519 
00525     function _putcatalog()
00526     {
00527         $this->_out('/Type /Catalog');
00528         $this->_out('/Pages 1 0 R');
00529         if ($this->ZoomMode == 'fullpage') {
00530             $this->_out('/OpenAction [3 0 R /Fit]');
00531         } else if ($this->ZoomMode == 'fullwidth') {
00532             $this->_out('/OpenAction [3 0 R /FitH null]');
00533         } else if ($this->ZoomMode == 'real') {
00534             $this->_out('/OpenAction [3 0 R /XYZ null null 1]');
00535         } else if (!is_string($this->ZoomMode)) {
00536             $this->_out('/OpenAction [3 0 R /XYZ null null ' . ($this->ZoomMode / 100) . ']');
00537         }
00538         if ($this->LayoutMode == 'single') {
00539             $this->_out('/PageLayout /SinglePage');
00540         } else if ($this->LayoutMode == 'continuous') {
00541             $this->_out('/PageLayout /OneColumn');
00542         } else if ($this->LayoutMode == 'two') {
00543             $this->_out('/PageLayout /TwoColumnLeft');
00544         }
00545     } // end of the "_putcatalog()" method
00546 
00547 
00553     function _puttrailer()
00554     {
00555         $this->_out('/Size ' . ($this->n + 1));
00556         $this->_out('/Root ' . $this->n . ' 0 R');
00557         $this->_out('/Info ' . ($this->n - 1) . ' 0 R');
00558     } // end of the "_puttrailer()" method
00559 
00560 
00566     function _enddoc()
00567     {
00568         $this->_putpages();
00569         $this->_putresources();
00570 
00571         // Info
00572         $this->_newobj();
00573         $this->_out('<<');
00574         $this->_putinfo();
00575         $this->_out('>>');
00576         $this->_out('endobj');
00577 
00578         // Catalog
00579         $this->_newobj();
00580         $this->_out('<<');
00581         $this->_putcatalog();
00582         $this->_out('>>');
00583         $this->_out('endobj');
00584 
00585         // Cross-ref
00586         $o = strlen($this->buffer);
00587         $this->_out('xref');
00588         $this->_out('0 ' . ($this->n + 1));
00589         $this->_out('0000000000 65535 f ');
00590         for ($i = 1; $i <= $this->n; $i++) {
00591             $this->_out(sprintf('%010d 00000 n ', $this->offsets[$i]));
00592         }
00593 
00594         // Trailer
00595         $this->_out('trailer');
00596         $this->_out('<<');
00597         $this->_puttrailer();
00598         $this->_out('>>');
00599         $this->_out('startxref');
00600         $this->_out($o);
00601         $this->_out('%%EOF');
00602         $this->state=3;
00603     } // end of the "_enddoc()" method
00604 
00605 
00613     function _beginpage($orientation)
00614     {
00615         $this->page++;
00616         $this->pages[$this->page] = '';
00617         $this->state              = 2;
00618         $this->x                  = $this->lMargin;
00619         $this->y                  = $this->tMargin;
00620         $this->lasth              = 0;
00621         $this->FontFamily         = '';
00622 
00623         // Page orientation
00624         if (!$orientation) {
00625             $orientation = $this->DefOrientation;
00626         } else {
00627             $orientation = strtoupper($orientation[0]);
00628         }
00629         if ($orientation != $this->DefOrientation) {
00630             $this->OrientationChanges[$this->page] = TRUE;
00631         }
00632         if ($orientation != $this->CurOrientation) {
00633             // Changes orientation
00634             if ($orientation == 'P') {
00635                 $this->wPt = $this->fwPt;
00636                 $this->hPt = $this->fhPt;
00637                 $this->w   = $this->fw;
00638                 $this->h   = $this->fh;
00639             }
00640             else {
00641                 $this->wPt = $this->fhPt;
00642                 $this->hPt = $this->fwPt;
00643                 $this->w   = $this->fh;
00644                 $this->h   = $this->fw;
00645             }
00646             $this->PageBreakTrigger = $this->h - $this->bMargin;
00647             $this->CurOrientation   = $orientation;
00648         } // end if
00649     } // end of the "_beginpage()" method
00650 
00651 
00657     function _endpage()
00658     {
00659         $this->state=1;
00660     } // end of the "_endpage()" method
00661 
00662 
00674     function _dounderline($x,$y,$txt)
00675     {
00676         $up = $this->CurrentFont['up'];
00677         $ut = $this->CurrentFont['ut'];
00678         $w  = $this->GetStringWidth($txt) + $this->ws * substr_count($txt, ' ');
00679 
00680         return sprintf('%.2f %.2f %.2f %.2f re f', $x * $this->k, ($this->h - ($y - $up / 1000 * $this->FontSize)) * $this->k, $w * $this->k, -$ut / 1000 * $this->FontSizePt);
00681     } // end of the "_dounderline()" method
00682 
00683 
00693     function _parsejpg($file)
00694     {
00695         $a = GetImageSize($file);
00696         if (!$a) {
00697             $this->Error('Missing or incorrect image file: ' . $file);
00698         }
00699         if ($a[2] != 2) {
00700             $this->Error('Not a JPEG file: ' . $file);
00701         }
00702         if (!isset($a['channels']) || $a['channels'] == 3) {
00703             $colspace = 'DeviceRGB';
00704         }
00705         else if($a['channels'] == 4) {
00706             $colspace = 'DeviceCMYK';
00707         }
00708         else {
00709             $colspace = 'DeviceGray';
00710         }
00711         $bpc = isset($a['bits']) ? $a['bits'] : 8;
00712 
00713         // Reads whole file
00714         $f    = fopen($file, 'rb');
00715         $data = fread($f, filesize($file));
00716         fclose($f);
00717 
00718         return array('w'    => $a[0],
00719                      'h'    => $a[1],
00720                      'cs'   => $colspace,
00721                      'bpc'  => $bpc,
00722                      'f'    => 'DCTDecode',
00723                      'data' => $data);
00724     } // end of the "_parsejpg()" method
00725 
00726 
00738     function _freadint($f)
00739     {
00740         $i = ord(fread($f, 1)) << 24;
00741         $i += ord(fread($f, 1)) << 16;
00742         $i += ord(fread($f, 1)) << 8;
00743         $i += ord(fread($f, 1));
00744 
00745         return $i;
00746     } // end of the "_freadint()" method
00747 
00748 
00760     function _parsepng($file)
00761     {
00762         $f = fopen($file, 'rb');
00763         if (!$f) {
00764             $this->Error('Can\'t open image file: ' . $file);
00765         }
00766 
00767         // Checks signature
00768         if (fread($f, 8) != chr(137) . 'PNG' . chr(13) . chr(10) . chr(26) . chr(10)) {
00769             $this->Error('Not a PNG file: ' . $file);
00770         }
00771 
00772         // Reads header chunk
00773         fread($f,4);
00774         if (fread($f, 4) != 'IHDR') {
00775             $this->Error('Incorrect PNG file: ' . $file);
00776         }
00777         $w   = $this->_freadint($f);
00778         $h   = $this->_freadint($f);
00779         $bpc = ord(fread($f,1));
00780         if ($bpc > 8) {
00781             $this->Error('16-bit depth not supported: ' . $file);
00782         }
00783         $ct  = ord(fread($f, 1));
00784         if ($ct == 0) {
00785             $colspace = 'DeviceGray';
00786         }
00787         else if ($ct == 2) {
00788             $colspace = 'DeviceRGB';
00789         }
00790         else if ($ct == 3) {
00791             $colspace = 'Indexed';
00792         }
00793         else {
00794             $this->Error('Alpha channel not supported: ' . $file);
00795         }
00796         if (ord(fread($f, 1)) != 0) {
00797             $this->Error('Unknown compression method: ' . $file);
00798         }
00799         if (ord(fread($f, 1)) != 0) {
00800             $this->Error('Unknown filter method: ' . $file);
00801         }
00802         if (ord(fread($f, 1)) != 0) {
00803             $this->Error('Interlacing not supported: ' . $file);
00804         }
00805         fread($f, 4);
00806         $parms = '/DecodeParms <</Predictor 15 /Colors ' . ($ct == 2 ? 3 : 1)
00807                . ' /BitsPerComponent ' . $bpc
00808                . ' /Columns ' . $w . '>>';
00809 
00810         // Scans chunks looking for palette, transparency and image data
00811         $pal  = '';
00812         $trns = '';
00813         $data = '';
00814         do {
00815             $n    = $this->_freadint($f);
00816             $type = fread($f, 4);
00817             if ($type == 'PLTE') {
00818                 // Reads palette
00819                 $pal = fread($f, $n);
00820                 fread($f, 4);
00821             }
00822             else if ($type == 'tRNS') {
00823                 // Reads transparency info
00824                 $t            = fread($f, $n);
00825                 if ($ct == 0) {
00826                     $trns     = array(ord(substr($t, 1, 1)));
00827                 }
00828                 else if ($ct == 2) {
00829                     $trns     = array(ord(substr($t, 1, 1)), ord(substr($t, 3, 1)), ord(substr($t, 5, 1)));
00830                 }
00831                 else {
00832                     $pos      = strpos(' ' . $t, chr(0));
00833                     if ($pos) {
00834                         $trns = array($pos - 1);
00835                     }
00836                     fread($f,4);
00837                 } // end if... else if... else
00838             }
00839             else if ($type == 'IDAT') {
00840                 // Reads image data block
00841                 $data .= fread($f, $n);
00842                 fread($f, 4);
00843             }
00844             else if ($type == 'IEND') {
00845                 break;
00846             }
00847             else {
00848                 fread($f, $n + 4);
00849             } // end if... else if... else
00850         } while($n); // end do
00851 
00852         if ($colspace == 'Indexed' && empty($pal)) {
00853             $this->Error('Missing palette in ' . $file);
00854         }
00855         fclose($f);
00856 
00857         return array('w'     => $w,
00858                      'h'     => $h,
00859                      'cs'    => $colspace,
00860                      'bpc'   => $bpc,
00861                      'f'     => 'FlateDecode',
00862                      'parms' => $parms,
00863                      'pal'   => $pal,
00864                      'trns'  => $trns,
00865                      'data'  => $data);
00866     } // end of the "_parsepng()" method
00867 
00868 
00869 
00870     /**************************************************************************
00871     *                                                                         *
00872     *                             Public methods                              *
00873     *                                                                         *
00874     **************************************************************************/
00875 
00885     function SetAutoPageBreak($auto, $margin = 0)
00886     {
00887         $this->AutoPageBreak    = $auto;
00888         $this->bMargin          = $margin;
00889         $this->PageBreakTrigger = $this->h - $margin;
00890     } // end of the "SetAutoPageBreak()" method
00891 
00892 
00902     function SetDisplayMode($zoom = 'default', $layout = 'continuous')
00903     {
00904         if (is_string($zoom)) {
00905             $zoom = strtolower($zoom);
00906         }
00907         $layout   = strtolower($layout);
00908 
00909         // Zoom mode
00910         if ($zoom == 'fullpage' || $zoom == 'fullwidth' || $zoom == 'real' || $zoom == 'default'
00911             || !is_string($zoom)) {
00912             $this->ZoomMode = $zoom;
00913         } else if ($zoom == 'zoom') {
00914             $this->ZoomMode = $layout;
00915         } else {
00916             $this->Error('Incorrect zoom display mode: ' . $zoom);
00917         } // end if... else if... else...
00918 
00919         // Layout mode
00920         if ($layout == 'single' || $layout == 'continuous' || $layout=='two' || $layout=='default') {
00921             $this->LayoutMode = $layout;
00922         } else if ($zoom != 'zoom') {
00923             $this->Error('Incorrect layout display mode: ' . $layout);
00924         } // end if... else if...
00925     } // end of the "SetDisplayMode()" method
00926 
00927 
00935     function SetCompression($compress)
00936     {
00937         if (function_exists('gzcompress')) {
00938             $this->compress = $compress;
00939         } else {
00940             $this->compress = FALSE;
00941         } // end if... else...
00942     } // end of the "SetCompression()" method
00943 
00944 
00954     function SetMargins($left, $top, $right = -1)
00955     {
00956         $this->lMargin = $left;
00957         $this->tMargin = $top;
00958         if ($right == -1) {
00959             $right = $left;
00960         }
00961         $this->rMargin = $right;
00962     } // end of the "SetMargins()" method
00963 
00964 
00975     function FPDF($orientation = 'P', $unit = 'mm', $format = 'A4')
00976     {
00977         // Check for PHP locale-related bug
00978         if (1.1 == 1) {
00979             $this->Error('Don\'t call setlocale() before including class file');
00980         }
00981 
00982         // Initialization of properties
00983         $this->page               = 0;
00984         $this->n                  = 2;
00985         $this->buffer             = '';
00986         $this->pages              = array();
00987         $this->OrientationChanges = array();
00988         $this->state              = 0;
00989         $this->fonts              = array();
00990         $this->FontFiles          = array();
00991         $this->diffs              = array();
00992         $this->images             = array();
00993         $this->links              = array();
00994         $this->InFooter           = FALSE;
00995         $this->FontFamily         = '';
00996         $this->FontStyle          = '';
00997         $this->FontSizePt         = 12;
00998         $this->underline          = FALSE;
00999         $this->DrawColor          = '0 G';
01000         $this->FillColor          = '0 g';
01001         $this->TextColor          = '0 g';
01002         $this->ColorFlag          = FALSE;
01003         $this->ws                 = 0;
01004 
01005         // Standard fonts
01006         $this->CoreFonts['courier']      = 'Courier';
01007         $this->CoreFonts['courierB']     = 'Courier-Bold';
01008         $this->CoreFonts['courierI']     = 'Courier-Oblique';
01009         $this->CoreFonts['courierBI']    = 'Courier-BoldOblique';
01010         $this->CoreFonts['helvetica']    = 'Helvetica';
01011         $this->CoreFonts['helveticaB']   = 'Helvetica-Bold';
01012         $this->CoreFonts['helveticaI']   = 'Helvetica-Oblique';
01013         $this->CoreFonts['helveticaBI']  = 'Helvetica-BoldOblique';
01014         $this->CoreFonts['times']        = 'Times-Roman';
01015         $this->CoreFonts['timesB']       = 'Times-Bold';
01016         $this->CoreFonts['timesI']       = 'Times-Italic';
01017         $this->CoreFonts['timesBI']      = 'Times-BoldItalic';
01018         $this->CoreFonts['symbol']       = 'Symbol';
01019         $this->CoreFonts['zapfdingbats'] = 'ZapfDingbats';
01020 
01021         // Scale factor
01022         if ($unit == 'pt') {
01023             $this->k = 1;
01024         } else if ($unit == 'mm') {
01025             $this->k = 72/25.4;
01026         } else if ($unit == 'cm') {
01027             $this->k = 72/2.54;
01028         } else if ($unit == 'in') {
01029             $this->k = 72;
01030         } else {
01031             $this->Error('Incorrect unit: ' . $unit);
01032         } // end if... else if... else...
01033 
01034         // Page format
01035         if (is_string($format)) {
01036             // 2002-07-24 - Nicola Asuni (info@tecnick.com)
01037             // Added new page formats (45 standard ISO paper formats and 4
01038             // american common formats).
01039             // Paper cordinates are calculated in this way:
01040             //    (inches * 72) where (1 inch = 2.54 cm)
01041             switch (strtoupper($format)) {
01042                 case '4A0':
01043                     $format = array(4767.87, 6740.79);
01044                     break;
01045                 case '2A0':
01046                     $format = array(3370.39, 4767.87);
01047                     break;
01048                 case 'A0':
01049                     $format = array(2383.94, 3370.39);
01050                     break;
01051                 case 'A1':
01052                     $format = array(1683.78, 2383.94);
01053                     break;
01054                 case 'A2':
01055                     $format = array(1190.55, 1683.78);
01056                     break;
01057                 case 'A3':
01058                     $format = array(841.89, 1190.55);
01059                     break;
01060                 case 'A4':
01061                     $format = array(595.28, 841.89);
01062                     break;
01063                 case 'A5':
01064                     $format = array(419.53, 595.28);
01065                     break;
01066                 case 'A6':
01067                     $format = array(297.64, 419.53);
01068                     break;
01069                 case 'A7':
01070                     $format = array(209.76, 297.64);
01071                     break;
01072                 case 'A8':
01073                     $format = array(147.40, 209.76);
01074                     break;
01075                 case 'A9':
01076                     $format = array(104.88, 147.40);
01077                     break;
01078                 case 'A10':
01079                     $format = array(73.70, 104.88);
01080                     break;
01081                 case 'B0':
01082                     $format = array(2834.65, 4008.19);
01083                     break;
01084                 case 'B1':
01085                     $format = array(2004.09, 2834.65);
01086                     break;
01087                 case 'B2':
01088                     $format = array(1417.32, 2004.09);
01089                     break;
01090                 case 'B3':
01091                     $format = array(1000.63, 1417.32);
01092                     break;
01093                 case 'B4':
01094                     $format = array(708.66, 1000.63);
01095                     break;
01096                 case 'B5':
01097                     $format = array(498.90, 708.66);
01098                     break;
01099                 case 'B6':
01100                     $format = array(354.33, 498.90);
01101                     break;
01102                 case 'B7':
01103                     $format = array(249.45, 354.33);
01104                     break;
01105                 case 'B8':
01106                     $format = array(175.75, 249.45);
01107                     break;
01108                 case 'B9':
01109                     $format = array(124.72, 175.75);
01110                     break;
01111                 case 'B10':
01112                     $format = array(87.87, 124.72);
01113                     break;
01114                 case 'C0':
01115                     $format = array(2599.37, 3676.54);
01116                     break;
01117                 case 'C1':
01118                     $format = array(1836.85, 2599.37);
01119                     break;
01120                 case 'C2':
01121                     $format = array(1298.27, 1836.85);
01122                     break;
01123                 case 'C3':
01124                     $format = array(918.43, 1298.27);
01125                     break;
01126                 case 'C4':
01127                     $format = array(649.13, 918.43);
01128                     break;
01129                 case 'C5':
01130                     $format = array(459.21, 649.13);
01131                     break;
01132                 case 'C6':
01133                     $format = array(323.15, 459.21);
01134                     break;
01135                 case 'C7':
01136                     $format = array(229.61, 323.15);
01137                     break;
01138                 case 'C8':
01139                     $format = array(161.57, 229.61);
01140                     break;
01141                 case 'C9':
01142                     $format = array(113.39, 161.57);
01143                     break;
01144                 case 'C10':
01145                     $format = array(79.37, 113.39);
01146                     break;
01147                 case 'RA0':
01148                     $format = array(2437.80, 3458.27);
01149                     break;
01150                 case 'RA1':
01151                     $format = array(1729.13, 2437.80);
01152                     break;
01153                 case 'RA2':
01154                     $format = array(1218.90, 1729.13);
01155                     break;
01156                 case 'RA3':
01157                     $format = array(864.57, 1218.90);
01158                     break;
01159                 case 'RA4':
01160                     $format = array(609.45, 864.57);
01161                     break;
01162                 case 'SRA0':
01163                     $format = array(2551.18, 3628.35);
01164                     break;
01165                 case 'SRA1':
01166                     $format = array(1814.17, 2551.18);
01167                     break;
01168                 case 'SRA2':
01169                     $format = array(1275.59, 1814.17);
01170                     break;
01171                 case 'SRA3':
01172                     $format = array(907.09, 1275.59);
01173                     break;
01174                 case 'SRA4':
01175                     $format = array(637.80, 907.09);
01176                     break;
01177                 case 'LETTER':
01178                     $format = array(612.00, 792.00);
01179                     break;
01180                 case 'LEGAL':
01181                     $format = array(612.00, 1008.00);
01182                     break;
01183                 case 'EXECUTIVE':
01184                     $format = array(521.86, 756.00);
01185                     break;
01186                 case 'FOLIO':
01187                     $format = array(612.00, 936.00);
01188                     break;
01189                 default:
01190                     $this->Error('Unknown page format: ' . $format);
01191                     break;
01192             } // end switch
01193             $this->fwPt = $format[0];
01194             $this->fhPt = $format[1];
01195         }
01196         else {
01197             $this->fwPt = $format[0] * $this->k;
01198             $this->fhPt = $format[1] * $this->k;
01199         } // end if... else...
01200         $this->fw       = $this->fwPt / $this->k;
01201         $this->fh       = $this->fhPt / $this->k;
01202 
01203         // Page orientation
01204         $orientation    = strtolower($orientation);
01205         if ($orientation == 'p' || $orientation == 'portrait') {
01206             $this->DefOrientation = 'P';
01207             $this->wPt            = $this->fwPt;
01208             $this->hPt            = $this->fhPt;
01209         }
01210         else if ($orientation == 'l' || $orientation == 'landscape') {
01211             $this->DefOrientation = 'L';
01212             $this->wPt            = $this->fhPt;
01213             $this->hPt            = $this->fwPt;
01214         }
01215         else {
01216             $this->Error('Incorrect orientation: ' . $orientation);
01217         } // end if... else if... else...
01218         $this->CurOrientation     = $this->DefOrientation;
01219         $this->w                  = $this->wPt / $this->k;
01220         $this->h                  = $this->hPt / $this->k;
01221 
01222         // Page margins (1 cm)
01223         $margin          = 28.35 / $this->k;
01224         $this->SetMargins($margin, $margin);
01225 
01226         // Interior cell margin (1 mm)
01227         $this->cMargin   = $margin / 10;
01228 
01229         // Line width (0.2 mm)
01230         $this->LineWidth = .567 / $this->k;
01231 
01232         // Automatic page break
01233         $this->SetAutoPageBreak(TRUE, 2 * $margin);
01234 
01235         // Full width display mode
01236         $this->SetDisplayMode('fullwidth');
01237 
01238         // Compression
01239         $this->SetCompression(TRUE);
01240     } // end of the "FPDF()" constructor
01241 
01242 
01250     function SetLeftMargin($margin)
01251     {
01252         $this->lMargin = $margin;
01253         if ($this->page > 0 && $this->x < $margin) {
01254             $this->x   = $margin;
01255         }
01256     } // end of the "SetLeftMargin()" method
01257 
01258 
01266     function SetTopMargin($margin)
01267     {
01268         $this->tMargin = $margin;
01269     } // end of the "SetTopMargin()" method
01270 
01271 
01279     function SetRightMargin($margin)
01280     {
01281         $this->rMargin = $margin;
01282     } // end of the "SetRightMargin()" method
01283 
01284 
01292     function SetTitle($title)
01293     {
01294         $this->title = $title;
01295     } // end of the "SetTitle()" method
01296 
01297 
01305     function SetSubject($subject)
01306     {
01307         $this->subject = $subject;
01308     } // end of the "SetSubject()" method
01309 
01310 
01318     function SetAuthor($author)
01319     {
01320         $this->author = $author;
01321     } // end of the "SetAuthor()" method
01322 
01323 
01331     function SetKeywords($keywords)
01332     {
01333         $this->keywords = $keywords;
01334     } // end of the "SetKeywords()" method
01335 
01336 
01344     function SetCreator($creator)
01345     {
01346         $this->creator = $creator;
01347     } // end of the "SetCreator()" method
01348 
01349 
01357     function AliasNbPages($alias = '{nb}')
01358     {
01359         $this->AliasNbPages = $alias;
01360     } // end of the "AliasNbPages()" method
01361 
01362 
01374     function SetFont($family, $style = '', $size = 0)
01375     {
01376         global $fpdf_charwidths;
01377 
01378         $family     = strtolower($family);
01379         if ($family == '') {
01380             $family = $this->FontFamily;
01381         }
01382         if ($family == 'arial') {
01383             $family = 'helvetica';
01384         }
01385         else if ($family == 'symbol' || $family == 'zapfdingbats') {
01386             $style  = '';
01387         }
01388         $style      = strtoupper($style);
01389 
01390         if (strpos(' ' . $style, 'U')) {
01391             $this->underline = TRUE;
01392             $style           = str_replace('U', '', $style);
01393         } else {
01394             $this->underline = FALSE;
01395         }
01396         if ($style == 'IB') {
01397             $style  = 'BI';
01398         }
01399         if ($size == 0) {
01400             $size   = $this->FontSizePt;
01401         }
01402 
01403         // Tests if the font is already selected
01404         if ($this->FontFamily == $family && $this->FontStyle == $style && $this->FontSizePt == $size) {
01405             return;
01406         }
01407 
01408         // Tests if used for the first time
01409         $fontkey = $family . $style;
01410         if (!isset($this->fonts[$fontkey])) {
01411             // Checks if one of the standard fonts
01412             if (isset($this->CoreFonts[$fontkey])) {
01413                 if (!isset($fpdf_charwidths[$fontkey])) {
01414                     // Loads metric file
01415                     $file     = $family;
01416                     if ($family == 'times' || $family == 'helvetica') {
01417                         $file .= strtolower($style);
01418                     }
01419                     $file     .= '.php';
01420                     if (isset($GLOBALS['FPDF_font_path'])) {
01421                         $file = $GLOBALS['FPDF_font_path'] . $file;
01422                     }
01423                     include($file);
01424                     if (!isset($fpdf_charwidths[$fontkey])) {
01425                         $this->Error('Could not include font metric file');
01426                     }
01427                 } // end if
01428                 $i = count($this->fonts) + 1;
01429                 $this->fonts[$fontkey] = array('i'    => $i,
01430                                                'type' => 'core',
01431                                                'name' => $this->CoreFonts[$fontkey],
01432                                                'up'   => -100,
01433                                                'ut'   => 50,
01434                                                'cw'   => $fpdf_charwidths[$fontkey]);
01435             }
01436             else {
01437                 $this->Error('Undefined font: ' . $family . ' ' . $style);
01438             } // end if... else...
01439         } // end if
01440 
01441         // Selects it
01442         $this->FontFamily  = $family;
01443         $this->FontStyle   = $style;
01444         $this->FontSizePt  = $size;
01445         $this->FontSize    = $size / $this->k;
01446         $this->CurrentFont = &$this->fonts[$fontkey];
01447         if ($this->page > 0) {
01448             $this->_out(sprintf('BT /F%d %.2f Tf ET', $this->CurrentFont['i'], $this->FontSizePt));
01449         }
01450     } // end of the "SetFont()" method
01451 
01452 
01460     function Header()
01461     {
01462         // void
01463     } // end of the "Header()" method
01464 
01465 
01473     function Footer()
01474     {
01475         // void
01476     } // end of the "Footer()" method
01477 
01478 
01484     function Open()
01485     {
01486         $this->_begindoc();
01487     } // end of the "Open()" method
01488 
01489 
01497     function AddPage($orientation = '')
01498     {
01499         // Backups some core variables
01500         $family             = $this->FontFamily;
01501         $style              = $this->FontStyle . ($this->underline ? 'U' : '');
01502         $size               = $this->FontSizePt;
01503         $lw                 = $this->LineWidth;
01504         $dc                 = $this->DrawColor;
01505         $fc                 = $this->FillColor;
01506         $tc                 = $this->TextColor;
01507         $cf                 = $this->ColorFlag;
01508 
01509         // If a page is already defined close it before starting the new one
01510         if ($this->page > 0) {
01511             // Page footer
01512             $this->InFooter = TRUE;
01513             $this->Footer();
01514             $this->InFooter = FALSE;
01515             // Close page
01516             $this->_endpage();
01517         }
01518 
01519         // Do start the new page
01520         $this->_beginpage($orientation);
01521         // Sets line cap style to square
01522         $this->_out('2 J');
01523         // Sets line width
01524         $this->LineWidth = $lw;
01525         $this->_out(sprintf('%.2f w', $lw * $this->k));
01526         // Sets font
01527         if ($family) {
01528             $this->SetFont($family, $style, $size);
01529         }
01530         // Sets colors
01531         $this->DrawColor = $dc;
01532         if ($dc != '0 G') {
01533             $this->_out($dc);
01534         }
01535         $this->FillColor = $fc;
01536         if ($fc != '0 g') {
01537             $this->_out($fc);
01538         }
01539         $this->TextColor = $tc;
01540         $this->ColorFlag = $cf;
01541         // Sets Page header
01542         $this->Header();
01543         // Restores line width
01544         if ($this->LineWidth != $lw) {
01545             $this->LineWidth = $lw;
01546             $this->_out(sprintf('%.2f w', $lw * $this->k));
01547         }
01548         // Restores font
01549         if ($family) {
01550             $this->SetFont($family, $style, $size);
01551         }
01552         // Restores colors
01553         if ($this->DrawColor!=$dc) {
01554             $this->DrawColor = $dc;
01555             $this->_out($dc);
01556         }
01557         if ($this->FillColor!=$fc) {
01558             $this->FillColor = $fc;
01559             $this->_out($fc);
01560         }
01561         $this->TextColor     = $tc;
01562         $this->ColorFlag     = $cf;
01563     } // end of the "AddPage()" method
01564 
01565 
01571     function Close()
01572     {
01573         // Terminates document
01574         if ($this->page == 0) {
01575             $this->AddPage();
01576         }
01577 
01578         // Displays the page footer
01579         $this->InFooter = TRUE;
01580         $this->Footer();
01581         $this->InFooter = FALSE;
01582 
01583         // Closes page and document
01584         $this->_endpage();
01585         $this->_enddoc();
01586     } // end of the "Close()" method
01587 
01588 
01596     function PageNo()
01597     {
01598         return $this->page;
01599     } // end of the "PageNo()" method
01600 
01601 
01611     function SetDrawColor($r, $g = -1, $b = -1)
01612     {
01613         if (($r == 0 && $g == 0 && $b == 0) || $g == -1) {
01614             $this->DrawColor = sprintf('%.3f G', $r / 255);
01615         } else {
01616             $this->DrawColor = sprintf('%.3f %.3f %.3f RG', $r / 255, $g / 255, $b / 255);
01617         } // end if... else...
01618 
01619         // If a page is defined, applies this property
01620         if ($this->page > 0) {
01621             $this->_out($this->DrawColor);
01622         }
01623     } // end of the "SetDrawColor()" method
01624 
01625 
01635     function SetFillColor($r, $g = -1, $b =-1)
01636     {
01637         if (($r == 0 && $g == 0 && $b == 0) || $g == -1) {
01638             $this->FillColor = sprintf('%.3f g', $r / 255);
01639         } else {
01640             $this->FillColor = sprintf('%.3f %.3f %.3f rg', $r / 255, $g / 255, $b / 255);
01641         } // end if... else...
01642 
01643         $this->ColorFlag     = ($this->FillColor != $this->TextColor);
01644 
01645         // If a page is defined, applies this property
01646         if ($this->page > 0) {
01647             $this->_out($this->FillColor);
01648         }
01649     } // end of the "SetDrawColor()" method
01650 
01651 
01661     function SetTextColor($r, $g = -1, $b =-1)
01662     {
01663         if (($r == 0 && $g == 0 && $b == 0) || $g == -1) {
01664             $this->TextColor = sprintf('%.3f g', $r / 255);
01665         } else {
01666             $this->TextColor = sprintf('%.3f %.3f %.3f rg', $r / 255, $g / 255, $b / 255);
01667         } // end if... else...
01668 
01669         $this->ColorFlag     = ($this->FillColor != $this->TextColor);
01670     } // end of the "SetTextColor()" method
01671 
01672 
01680     function SetLineWidth($width)
01681     {
01682         $this->LineWidth = $width;
01683 
01684         // If a page is defined, applies this property
01685         if ($this->page > 0) {
01686             $this->_out(sprintf('%.2f w', $width * $this->k));
01687         }
01688     } // end of the "SetLineWidth()" method
01689 
01690 
01701     function Line($x1, $y1, $x2, $y2)
01702     {
01703         $this->_out(sprintf('%.2f %.2f m %.2f %.2f l S', $x1 * $this->k, ($this->h - $y1) * $this->k, $x2 * $this->k, ($this->h - $y2) * $this->k));
01704     } // end of the "Line()" method
01705 
01706 
01718     function Rect($x, $y, $w, $h, $style = '')
01719     {
01720         if ($style == 'F') {
01721             $op = 'f';
01722         } else if ($style == 'FD' || $style=='DF') {
01723             $op = 'B';
01724         } else {
01725             $op = 'S';
01726         } // end if... else if... else
01727 
01728         $this->_out(sprintf('%.2f %.2f %.2f %.2f re %s', $x * $this->k, ($this->h - $y) * $this->k, $w * $this->k, -$h * $this->k, $op));
01729     } // end of the "Rect()" method
01730 
01731 
01741     function AddFont($family, $style = '', $file = '')
01742     {
01743         $family     = strtolower($family);
01744         if ($family == 'arial') {
01745             $family = 'helvetica';
01746         }
01747 
01748         $style  = strtoupper($style);
01749         if ($style == 'IB') {
01750             $style = 'BI';
01751         }
01752         if (isset($this->fonts[$family . $style])) {
01753             $this->Error('Font already added: ' . $family . ' ' . $style);
01754         }
01755         if ($file == '') {
01756             $file = str_replace(' ', '', $family) . strtolower($style) . '.php';
01757         }
01758         if (isset($GLOBALS['FPDF_font_path'])) {
01759             $file = $GLOBALS['FPDF_font_path'] . $file;
01760         }
01761         include($file);
01762         if (!isset($name)) {
01763             $this->Error('Could not include font definition file');
01764         }
01765 
01766         $i = count($this->fonts) + 1;
01767         $this->fonts[$family . $style] = array('i'    => $i,
01768                                                'type' => $type,
01769                                                'name' => $name,
01770                                                'desc' => $desc,
01771                                                'up'   => $up,
01772                                                'ut'   => $ut,
01773                                                'cw'   => $cw,
01774                                                'enc'  => $enc,
01775                                                'file' => $file);
01776         // Searches existing encodings
01777         if ($diff) {
01778             $d  = 0;
01779             $nb = count($this->diffs);
01780             for ($i = 1; $i <= $nb; $i++) {
01781                 if ($this->diffs[$i] == $diff) {
01782                     $d = $i;
01783                     break;
01784                 } // end if
01785             } // end for
01786             if ($d == 0) {
01787                 $d               = $nb + 1;
01788                 $this->diffs[$d] = $diff;
01789             } // end if
01790             $this->fonts[$family . $style]['diff'] = $d;
01791         } // end if
01792 
01793         if ($file) {
01794             if ($type == 'TrueType') {
01795                 $this->FontFiles[$file] = array('length1' => $originalsize);
01796             } else {
01797                 $this->FontFiles[$file] = array('length1' => $size1, 'length2' => $size2);
01798             }
01799         } // end if
01800     } // end of the "AddFont()" method
01801 
01802 
01810     function SetFontSize($size)
01811     {
01812         if ($this->FontSizePt == $size) {
01813             return;
01814         }
01815         $this->FontSizePt = $size;
01816         $this->FontSize   = $size / $this->k;
01817         if ($this->page > 0) {
01818             $this->_out(sprintf('BT /F%d %.2f Tf ET', $this->CurrentFont['i'], $this->FontSizePt));
01819         }
01820     } // end of the "SetFontSize()" method
01821 
01822 
01830     function AddLink()
01831     {
01832         $n = count($this->links) + 1;
01833         $this->links[$n] = array(0, 0);
01834         return $n;
01835     } // end of the "AddLink()" method
01836 
01837 
01847     function SetLink($link, $y = 0, $page = -1)
01848     {
01849         if ($y == -1) {
01850             $y    = $this->y;
01851         }
01852         if ($page == -1) {
01853             $page = $this->page;
01854         }
01855         $this->links[$link] = array($page, $y);
01856     } // end of the "SetLink()" method
01857 
01858 
01870     function Link($x, $y, $w, $h, $link)
01871     {
01872         $this->PageLinks[$this->page][] = array($x * $this->k,
01873                                                 $this->hPt - $y * $this->k,
01874                                                 $w * $this->k,
01875                                                 $h * $this->k,
01876                                                 $link);
01877     } // end of the "Link()" method
01878 
01879 
01889     function Text($x, $y, $txt)
01890     {
01891         $txt   = str_replace(')', '\\)', str_replace('(', '\\(', str_replace('\\', '\\\\', $txt)));
01892         $s     = sprintf('BT %.2f %.2f Td (%s) Tj ET', $x * $this->k, ($this->h - $y) * $this->k, $txt);
01893         if ($this->underline && $txt != '') {
01894             $s .= ' ' . $this->_dounderline($x, $y, $txt);
01895         }
01896         if ($this->ColorFlag) {
01897             $s = 'q ' . $this->TextColor . ' ' . $s . ' Q';
01898         }
01899         $this->_out($s);
01900     } // end of the "Text()" method
01901 
01902 
01910     function AcceptPageBreak()
01911     {
01912         return $this->AutoPageBreak;
01913     } // end of the "AcceptPageBreak()" method
01914 
01915 
01930     function Cell($w, $h = 0, $txt = '', $border = 0, $ln = 0, $align = '', $fill = 0, $link = '')
01931     {
01932         $k = $this->k;
01933 
01934         if ($this->y + $h > $this->PageBreakTrigger
01935             && !$this->InFooter
01936             && $this->AcceptPageBreak()) {
01937             $x  = $this->x;
01938             $ws = $this->ws;
01939             if ($ws > 0) {
01940                 $this->ws = 0;
01941                 $this->_out('0 Tw');
01942             }
01943             $this->AddPage($this->CurOrientation);
01944             $this->x = $x;
01945             if ($ws > 0) {
01946                 $this->ws = $ws;
01947                 $this->_out(sprintf('%.3f Tw', $ws * $k));
01948             }
01949         } // end if
01950 
01951         if ($w == 0) {
01952             $w = $this->w - $this->rMargin - $this->x;
01953         }
01954 
01955         $s          = '';
01956         if ($fill == 1 || $border == 1) {
01957             if ($fill == 1) {
01958                 $op = ($border == 1) ? 'B' : 'f';
01959             } else {
01960                 $op = 'S';
01961             }
01962             $s      = sprintf('%.2f %.2f %.2f %.2f re %s ', $this->x * $k, ($this->h - $this->y) * $k, $w * $k, -$h * $k, $op);
01963         } // end if
01964 
01965         if (is_string($border)) {
01966             $x     = $this->x;
01967             $y     = $this->y;
01968             if (strpos(' ' . $border, 'L')) {
01969                 $s .= sprintf('%.2f %.2f m %.2f %.2f l S ', $x * $k, ($this->h - $y) * $k, $x * $k, ($this->h - ($y+$h)) * $k);
01970             }
01971             if (strpos(' ' . $border, 'T')) {
01972                 $s .= sprintf('%.2f %.2f m %.2f %.2f l S ', $x * $k, ($this->h - $y) * $k, ($x + $w) * $k, ($this->h - $y) * $k);
01973             }
01974             if (strpos(' ' . $border, 'R')) {
01975                 $s .= sprintf('%.2f %.2f m %.2f %.2f l S ', ($x + $w) * $k, ($this->h - $y) * $k, ($x + $w) * $k, ($this->h - ($y + $h)) * $k);
01976             }
01977             if (strpos(' ' . $border, 'B')) {
01978                 $s .= sprintf('%.2f %.2f m %.2f %.2f l S ', $x * $k, ($this->h - ($y + $h)) * $k, ($x + $w) * $k, ($this->h - ($y + $h)) * $k);
01979             }
01980         } // end if
01981 
01982         if ($txt != '') {
01983             if ($align == 'R') {
01984                 $dx = $w - $this->cMargin - $this->GetStringWidth($txt);
01985             }
01986             else if ($align == 'C') {
01987                 $dx = ($w - $this->GetStringWidth($txt)) / 2;
01988             }
01989             else {
01990                 $dx = $this->cMargin;
01991             }
01992             $txt    = str_replace(')', '\\)', str_replace('(', '\\(', str_replace('\\', '\\\\', $txt)));
01993             if ($this->ColorFlag) {
01994                 $s  .= 'q ' . $this->TextColor . ' ';
01995             }
01996             $s      .= sprintf('BT %.2f %.2f Td (%s) Tj ET', ($this->x + $dx) * $k, ($this->h - ($this->y + .5 * $h + .3 * $this->FontSize)) * $k, $txt);
01997             if ($this->underline) {
01998                 $s  .= ' ' . $this->_dounderline($this->x+$dx, $this->y + .5 * $h + .3 * $this->FontSize, $txt);
01999             }
02000             if ($this->ColorFlag) {
02001                 $s  .= ' Q';
02002             }
02003             if ($link) {
02004                 $this->Link($this->x + $dx, $this->y + .5 * $h - .5 * $this->FontSize, $this->GetStringWidth($txt), $this->FontSize, $link);
02005             }
02006         } // end if
02007 
02008         if ($s) {
02009             $this->_out($s);
02010         }
02011         $this->lasth = $h;
02012 
02013         if ($ln > 0) {
02014             // Go to next line
02015             $this->y     += $h;
02016             if ($ln == 1) {
02017                 $this->x = $this->lMargin;
02018             }
02019         } else {
02020             $this->x     += $w;
02021         }
02022     } // end of the "Cell()" method
02023 
02024 
02037     function MultiCell($w, $h, $txt, $border = 0, $align = 'J', $fill = 0)
02038     {
02039         // loic1: PHP3 compatibility
02040         // $cw    = &$this->CurrentFont['cw'];
02041         if ($w == 0) {
02042             $w = $this->w - $this->lMargin - $this->x;
02043         }
02044         $wmax  = ($w - 2 * $this->cMargin) * 1000 / $this->FontSize;
02045         $s     = str_replace("\r", '', $txt);
02046         $nb    = strlen($s);
02047         if ($nb>0 && $s[$nb - 1] == "\n") {
02048             $nb--;
02049         }
02050 
02051         $b              = 0;
02052         if ($border) {
02053             if ($border == 1) {
02054                 $border = 'LTRB';
02055                 $b      = 'LRT';
02056                 $b2     = 'LR';
02057             }
02058             else {
02059                 $b2     = '';
02060                 if (strpos(' ' . $border, 'L')) {
02061                     $b2 .= 'L';
02062                 }
02063                 if (strpos(' ' . $border, 'R')) {
02064                     $b2 .= 'R';
02065                 }
02066                 $b      = (strpos(' ' . $border, 'T')) ? $b2 . 'T' : $b2;
02067             } // end if... else...
02068         } // end if
02069 
02070         $sep = -1;
02071         $i   = 0;
02072         $j   = 0;
02073         $l   = 0;
02074         $ns  = 0;
02075         $nl  = 1;
02076         while ($i < $nb) {
02077             // Gets next character
02078             $c = $s[$i];
02079 
02080             // Explicit line break
02081             if ($c == "\n") {
02082                 if ($this->ws > 0) {
02083                     $this->ws = 0;
02084                     $this->_out('0 Tw');
02085                 }
02086                 $this->Cell($w, $h, substr($s, $j, $i - $j), $b, 2, $align, $fill);
02087                 $i++;
02088                 $sep   = -1;
02089                 $j     = $i;
02090                 $l     = 0;
02091                 $ns    = 0;
02092                 $nl++;
02093                 if ($border && $nl == 2) {
02094                     $b = $b2;
02095                 }
02096                 continue;
02097             } // end if
02098 
02099             // Space character
02100             if ($c == ' ') {
02101                 $sep = $i;
02102                 $ls  = $l;
02103                 $ns++;
02104             } // end if
02105 
02106             $l += $this->CurrentFont['cw'][$c];
02107             if ($l > $wmax) {
02108                 // Automatic line break
02109                 if ($sep == -1) {
02110                     if ($i == $j) {
02111                         $i++;
02112                     }
02113                     if ($this->ws > 0) {
02114                         $this->ws = 0;
02115                         $this->_out('0 Tw');
02116                     }
02117                     $this->Cell($w, $h, substr($s, $j, $i - $j), $b, 2, $align, $fill);
02118                 }
02119                 else {
02120                     if ($align == 'J') {
02121                         $this->ws = ($ns > 1)
02122                                   ? ($wmax - $ls) / 1000 * $this->FontSize / ($ns - 1)
02123                                   : 0;
02124                         $this->_out(sprintf('%.3f Tw', $this->ws * $this->k));
02125                     }
02126                     $this->Cell($w, $h, substr($s, $j, $sep - $j), $b, 2, $align, $fill);
02127                     $i = $sep + 1;
02128                 } // end if... else...
02129 
02130                 $sep   = -1;
02131                 $j     = $i;
02132                 $l     = 0;
02133                 $ns    = 0;
02134                 $nl++;
02135                 if ($border && $nl == 2) {
02136                     $b = $b2;
02137                 }
02138             }
02139             else {
02140                 $i++;
02141             } // end if... else
02142         } // end while
02143 
02144         // Last chunk
02145         if ($this->ws > 0) {
02146             $this->ws = 0;
02147             $this->_out('0 Tw');
02148         }
02149 
02150         if ($border && strpos(' ' . $border, 'B')) {
02151             $b .= 'B';
02152         }
02153         $this->Cell($w, $h, substr($s, $j, $i), $b, 2, $align, $fill);
02154         $this->x = $this->lMargin;
02155     } // end of the "MultiCell()" method
02156 
02157 
02167     function Write($h, $txt, $link = '')
02168     {
02169         $w    = $this->w - $this->rMargin - $this->x;
02170         $wmax = ($w - 2 * $this->cMargin) * 1000 / $this->FontSize;
02171         $s    = str_replace("\r", '', $txt);
02172         $nb   = strlen($s);
02173         $sep  = -1;
02174         $i    = 0;
02175         $j    = 0;
02176         $l    = 0;
02177         $nl   = 1;
02178 
02179         while ($i < $nb) {
02180             // Gets next character
02181             $c = $s[$i];
02182 
02183             // Explicit line break
02184             if ($c == "\n") {
02185                 $this->Cell($w, $h, substr($s, $j, $i - $j), 0, 2, '', 0, $link);
02186                 $i++;
02187                 $sep = -1;
02188                 $j   = $i;
02189                 $l   = 0;
02190                 if ($nl == 1) {
02191                     $this->x = $this->lMargin;
02192                     $w       = $this->w - $this->rMargin - $this->x;
02193                     $wmax    = ($w - 2 * $this->cMargin) * 1000 / $this->FontSize;
02194                 }
02195                 $nl++;
02196                 continue;
02197             }
02198 
02199             // Space character
02200             if ($c == ' ') {
02201                 $sep = $i;
02202                 $ls  = $l;
02203             } // end if
02204 
02205             $l += $this->CurrentFont['cw'][$c];
02206             if ($l > $wmax) {
02207                 // Automatic line break
02208                 if ($sep == -1) {
02209                     if($this->x > $this->lMargin)  {
02210                         // Move to next line
02211                         $this->x =$this->lMargin;
02212                         $this->y +=$h;
02213                         $w       = $this->w - $this->rMargin - $this->x;
02214                         $wmax    =($w - 2 * $this->cMargin) * 1000 / $this->FontSize;
02215                         $i++;
02216                         $nl++;
02217                         continue;
02218                     }
02219                     if ($i == $j) {
02220                         $i++;
02221                     }
02222                     $this->Cell($w, $h, substr($s, $j, $i - $j), 0, 2, '', 0, $link);
02223                 }
02224                 else {
02225                     $this->Cell($w, $h, substr($s, $j, $sep - $j), 0, 2, '', 0, $link);
02226                     $i = $sep + 1;
02227                 } // end if... else...
02228 
02229                 $sep         = -1;
02230                 $j           = $i;
02231                 $l           = 0;
02232                 if ($nl == 1) {
02233                     $this->x = $this->lMargin;
02234                     $w       = $this->w - $this->rMargin - $this->x;
02235                     $wmax    = ($w - 2 * $this->cMargin) * 1000 / $this->FontSize;
02236                 }
02237                 $nl++;
02238             }
02239             else {
02240                 $i++;
02241             } // end if... else...
02242         } // end while
02243 
02244         // Last chunk
02245         if ($i != $j) {
02246             $this->Cell($l / 1000 * $this->FontSize, $h, substr($s, $j, $i), 0, 0, '', 0, $link);
02247         }
02248     } // end of the "Write()" method
02249 
02250 
02264     function Image($file, $x, $y, $w, $h = 0, $type = '', $link = '')
02265     {
02266         if (!isset($this->images[$file])) {
02267             // First use of image, get info
02268             if ($type == '') {
02269                 $pos = strrpos($file, '.');
02270                 if (!$pos) {
02271                     $this->Error('Image file has no extension and no type was specified: ' . $file);
02272                 }
02273                 $type = substr($file, $pos + 1);
02274             } // end if
02275 
02276             $type = strtolower($type);
02277             $mqr  = get_magic_quotes_runtime();
02278             set_magic_quotes_runtime(0);
02279             if ($type == 'jpg' || $type == 'jpeg') {
02280                 $info = $this->_parsejpg($file);
02281             }
02282             else if ($type == 'png') {
02283                 $info = $this->_parsepng($file);
02284             }
02285             else {
02286                 $this->Error('Unsupported image file type: ' . $type);
02287             }
02288             set_magic_quotes_runtime($mqr);
02289             $info['i']           = count($this->images) + 1;
02290             $this->images[$file] = $info;
02291         }
02292         else {
02293             $info                = $this->images[$file];
02294         } // end if... else...
02295 
02296         // Automatic width or height calculation
02297         if ($w == 0) {
02298             $w = $h * $info['w'] / $info['h'];
02299         }
02300         if ($h == 0) {
02301             $h = $w * $info['h'] / $info['w'];
02302         }
02303         $this->_out(sprintf('q %.2f 0 0 %.2f %.2f %.2f cm /I%d Do Q', $w * $this->k, $h * $this->k, $x * $this->k, ($this->h - ($y + $h)) * $this->k, $info['i']));
02304 
02305         if ($link) {
02306             $this->Link($x, $y, $w, $h, $link);
02307         }
02308     } // end of the "Image()" method
02309 
02310 
02318     function Ln($h = '')
02319     {
02320         $this->x = $this->lMargin;
02321         // Sets default line height to last cell height
02322         if (is_string($h)) {
02323             $this->y += $this->lasth;
02324         }
02325         else {
02326             $this->y += $h;
02327         }
02328     } // end of the "Ln()" method
02329 
02330 
02338     function GetX()
02339     {
02340         return $this->x;
02341     } // end of the "GetX()" method
02342 
02343 
02351     function SetX($x)
02352     {
02353         if ($x >= 0) {
02354             $this->x = $x;
02355         } else {
02356             $this->x = $this->w + $x;
02357         }
02358     } // end of the "SetX()" method
02359 
02360 
02368     function GetY()
02369     {
02370         return $this->y;
02371     } // end of the "GetY()" method
02372 
02373 
02381     function SetY($y)
02382     {
02383         $this->x = $this->lMargin;
02384         if ($y >= 0) {
02385             $this->y = $y;
02386         } else {
02387             $this->y = $this->h + $y;
02388         }
02389     } // end of the "SetY()" method
02390 
02391 
02400     function SetXY($x,$y)
02401     {
02402         $this->SetY($y);
02403         $this->SetX($x);
02404     } // end of the "SetXY()" method
02405 
02406 
02419     function Output($file = '', $download = FALSE)
02420     {
02421         global $HTTP_USER_AGENT;
02422 
02423         if ($this->state < 3) {
02424             $this->Close();
02425         }
02426 
02427         // Send to browser
02428         if ($file == '') {
02429             header('Content-Type: application/pdf');
02430             if (headers_sent()) {
02431                 $this->Error('Some data has already been output to browser, can\'t send PDF file');
02432             }
02433             header('Content-Length: ' . strlen($this->buffer));
02434             header('Content-Disposition: inline; filename=doc.pdf');
02435             echo $this->buffer;
02436         }
02437         // Download file
02438         else if ($download) {
02439             if (!empty($HTTP_USER_AGENT)
02440                 && (strpos($HTTP_USER_AGENT, 'MSIE 5.5') || strpos($HTTP_USER_AGENT, 'Opera'))) {
02441                 header('Content-Type: application/dummy');
02442             }
02443             // fix for Gecko-based browsers < 1.1
02444             else if (!empty($HTTP_USER_AGENT)
02445                   &&  (strpos($HTTP_USER_AGENT, 'Gecko') &&
02446                   (strpos($HTTP_USER_AGENT, 'rv:0.') || strpos($HTTP_USER_AGENT, 'rv:1.0') || strpos($HTTP_USER_AGENT, 'rv:1.1')))) {
02447                      header('Content-Type: application/');
02448             }
02449             else {
02450                 header('Content-Type: application/pdf');
02451             }
02452             if (headers_sent()) {
02453                 $this->Error('Some data has already been output to browser, can\'t send PDF file');
02454             }
02455             header('Content-Length: ' . strlen($this->buffer));
02456             header('Content-Disposition: attachment; filename=' . $file);
02457             echo $this->buffer;
02458         }
02459         // Save file locally
02460         else {
02461             $f = fopen($file, 'wb');
02462             if (!$f) {
02463                 $this->Error('Unable to create output file: ' . $file);
02464             }
02465             fwrite($f, $this->buffer, strlen($this->buffer));
02466             fclose($f);
02467         } // end if... else if... else
02468     } // end of the "Output()" method
02469 
02470 } // End of the "FPDF" class
02471 
02472 
02473 
02477 if (!empty($_ENV) && isset($_ENV['HTTP_USER_AGENT'])) {
02478     $HTTP_USER_AGENT = $_ENV['HTTP_USER_AGENT'];
02479 }
02480 else if (!empty($_SERVER) && isset($_SERVER['HTTP_USER_AGENT'])) {
02481     $HTTP_USER_AGENT = $_SERVER['HTTP_USER_AGENT'];
02482 }
02483 else if (@getenv('HTTP_USER_AGENT')) {
02484     $HTTP_USER_AGENT = getenv('HTTP_USER_AGENT');
02485 }
02486 
02487 if ($HTTP_USER_AGENT == 'contype') {
02488     header('Content-Type: application/pdf');
02489     exit();
02490 }
02491 ?>


Généré par L'expert TYPO3 avec  doxygen 1.4.6