Blame | Letzte Änderung | Log anzeigen | RSS feed
<?php/******************************************************************************** Software: FPDF ** Version: 1.53 ** Date: 2004-12-31 ** Author: Olivier PLATHEY ** License: Freeware ** ** You may use, modify and redistribute this software as you wish. ********************************************************************************//*** Heavily patched to adapt to the HTML2PS/HTML2PDF script requirements by* Konstantin Bournayev (bkon@bkon.ru)*/if (!class_exists('FPDF')) {define('FPDF_VERSION','1.53');/*** See PDF Reference 1.6 p.664 for explanation of flags specific to submit form action*/define('PDF_SUBMIT_FORM_HTML', 1 << 2); // 1 - HTML, 0 - FDFdefine('PDF_SUBMIT_FORM_COORDINATES', 1 << 4);/*** See PDF Reference 1.6 p.656 for explanation of flags specific to choice fields*/define('PDF_FIELD_CHOICE_COMBO', 1 << 17);/*** See PDF Reference 1.6 p.653 for explanation of flags specific to text fields*/define('PDF_FIELD_TEXT_MULTILINE',1 << 12);define('PDF_FIELD_TEXT_PASSWORD', 1 << 13);define('PDF_FIELD_TEXT_FILE', 1 << 20);/*** See PDF Reference 1.6 p.663 for examplanation of flags specific to for submit actions*/define("PDF_FORM_SUBMIT_EXCLUDE", 1 << 0);define("PDF_FORM_SUBMIT_NOVALUE", 1 << 1);define("PDF_FORM_SUBMIT_EFORMAT", 1 << 2);define("PDF_FORM_SUBMIT_GET", 1 << 3);class PDFIndirectObject {var $object_id;var $generation_id;function get_object_id() {return $this->object_id;}function get_generation_id() {return $this->generation_id;}/*** Outputs the PDF indirect object to PDF file.** To pervent infinite loop on circular references, this method checks* if current object have been already written to the file.** Note that, in general, nested objects should be written to PDF file* here too; this task is accomplished by calling _out_nested method,* which should be overridden by children classes.** @param FPDF $handler PDF file wrapper (FPDF object)** @final** @see FPDF::is_object_written* @see PDFIndirectObject::_out_nested*/function out(&$handler) {if (!$handler->is_object_written($this->get_object_id())) {$handler->offsets[$this->get_object_id()] = strlen($handler->buffer);$handler->_out($handler->_indirect_object($this));$this->_out_nested($handler);};}/*** Writes all nested objects to the PDF file. Should be overridden by* PDFIndirectObject descendants.** @param FPDF $handler PDF file wrapper (FPDF object)** @see PDFIndirectObject::out*/function _out_nested(&$handler) {return true;}function PDFIndirectObject(&$handler,$object_id,$generation_id) {$this->object_id = $object_id;$this->generation_id = $generation_id;}function pdf(&$handler) {return $handler->_dictionary($this->_dict($handler));}function _dict() {return array();}}class PDFPage extends PDFIndirectObject {var $annotations;function PDFPage(&$handler,$object_id,$generation_id) {$this->PDFIndirectObject($handler,$object_id,$generation_id);}function add_annotation(&$annotation) {$this->annotations[] =& $annotation;}function _annotations(&$handler) {return $handler->_reference_array($this->annotations);}}class PDFAppearanceStream extends PDFIndirectObject {var $_content;function PDFAppearanceStream(&$handler,$object_id,$generation_id,$content) {$this->PDFIndirectObject($handler,$object_id,$generation_id);$this->_content = $content;}function pdf(&$handler) {$dict_content = array('Type' => "/XObject",'Subtype' => "/Form",'FormType' => "1",'BBox' => "[0 0 100 100]",'Matrix' => "[1 0 0 1 0 0]",'Resources'=> "2 0 R",'Length' => strlen($this->_content));$content = $handler->_dictionary($dict_content);$content .= "\n";$content .= $handler->_stream($this->_content);return $content;}}class PDFAnnotation extends PDFIndirectObject {function PDFAnnotation(&$handler,$object_id,$generation_id) {$this->PDFIndirectObject($handler,$object_id,$generation_id);}function _dict(&$handler) {return array_merge(parent::_dict($handler),array("Type" => $handler->_name("Annot")));}}class PDFRect {var $x;var $y;var $w;var $h;function PDFRect($x,$y,$w,$h) {$this->x = $x;$this->y = $y;$this->w = $w;$this->h = $h;}function left(&$handler) {return $handler->x_coord($this->x);}function right(&$handler) {return $handler->x_coord($this->x+$this->w);}function top(&$handler) {return $handler->y_coord($this->y);}function bottom(&$handler) {return $handler->y_coord($this->y+$this->h);}function pdf(&$handler) {return $handler->_array(sprintf("%.2f %.2f %.2f %.2f",$this->left($handler),$this->top($handler),$this->right($handler),$this->bottom($handler)));}}class PDFAnnotationExternalLink extends PDFAnnotation {var $rect;var $link;function PDFAnnotationExternalLink(&$handler,$object_id,$generation_id,$rect,$link) {$this->PDFAnnotation($handler,$object_id,$generation_id);$this->rect = $rect;$this->link = $link;}function _dict(&$handler) {return array_merge(parent::_dict($handler),array('Subtype' => "/Link",'Rect' => $this->rect->pdf($handler),'Border' => "[0 0 0]",'A' => "<</S /URI /URI ".$handler->_textstring($this->link).">>"));}}class PDFAnnotationInternalLink extends PDFAnnotation {var $rect;var $link;function PDFAnnotationInternalLink(&$handler,$object_id,$generation_id,$rect,$link) {$this->PDFAnnotation($handler,$object_id,$generation_id);$this->rect = $rect;$this->link = $link;}function pdf(&$handler) {if ($handler->DefOrientation=='P') {$wPt=$handler->fwPt;$hPt=$handler->fhPt;} else {$wPt=$handler->fhPt;$hPt=$handler->fwPt;};$l = $handler->links[$this->link];$h = isset($handler->OrientationChanges[$l[0]]) ? $wPt : $hPt;/*** Sometimes hyperlinks may refer to pages NOT present in PDF document* Example: a very long frame content; it it trimmed to one page, as* framesets newer take more than one frame. A link targe which should be rendered* on third page without frames will be never rendered at all.** In this case we should disable link at all to prevent error from appearing*/if (!isset($handler->_pages[$l[0]-1])) {return "";}$content = $handler->_dictionary(array('Type' => "/Annot",'Subtype' => "/Link",'Rect' => $this->rect->pdf($handler),'Border' => "[0 0 0]",'Dest' => sprintf("[%s /XYZ 0 %.2f null]",$handler->_reference($handler->_pages[$l[0]-1]),$h-$l[1]*$handler->k)));return $content;}}class PDFAnnotationWidget extends PDFAnnotation {var $_rect;function PDFAnnotationWidget(&$handler,$object_id,$generation_id,$rect) {$this->PDFAnnotation($handler,$object_id,$generation_id);$this->_rect = $rect;}function _dict(&$handler) {return array_merge(parent::_dict($handler),array("Subtype" => $handler->_name("Widget"),'Rect' => $this->_rect->pdf($handler)));}}/*** Generic PDF Form*/class PDFFieldGroup extends PDFIndirectObject {var $_kids;var $_group_name;function PDFFieldGroup(&$handler,$object_id,$generation_id,$group_name) {$this->PDFIndirectObject($handler,$object_id,$generation_id);/*** Generate default group name, if needed*/if (is_null($group_name) || $group_name == "") {$group_name = sprintf("FieldGroup%d", $this->get_object_id());};$this->_group_name = $group_name;$this->_kids = array();}function _check_field_name($field) {/*** Check if field name is empty*/if (trim($field->get_field_name()) == "") {error_log(sprintf("Found form field with empty name"));return false;};/*** Check if field name is unique inside this form! If we will not do it,* some widgets may become inactive (ignored by PDF Reader)*/foreach ($this->_kids as $kid) {if ($kid->get_field_name() == $field->get_field_name()) {error_log(sprintf("Interactive form '%s' already contains field named '%s'",$this->_group_name,$kid->get_field_name()));return false;}};return true;}function add_field(&$field) {if (!$this->_check_field_name($field)) {/*** Field name is not unique; replace it with automatically-generated one*/$field->set_field_name(sprintf("%s_FieldObject%d",$field->get_field_name(),$field->get_object_id()));};$this->_kids[] =& $field;$field->set_parent($this);}function _dict(&$handler) {return array_merge(parent::_dict($handler),array("Kids" => $handler->_reference_array($this->_kids),"T" => $handler->_textstring($this->_group_name)));return $content;}function _out_nested(&$handler) {parent::_out_nested($handler);foreach ($this->_kids as $field) {$field->out($handler);}}}/*** Generic superclass for all PDF interactive field widgets*/class PDFField extends PDFAnnotationWidget {/*** @var string Partial field name (see PDF Specification 1.6 p.638 for explanation on "partial" and* "fully qualified" field names* @access private*/var $_field_name;/*** @var PDFFieldGroup REference to a containing form object* @access private*/var $_parent;function PDFField(&$handler,$object_id,$generation_id,$rect,$field_name) {$this->PDFAnnotationWidget($handler,$object_id,$generation_id,$rect);/*** Generate default field name, if needed* @TODO: validate field_name contents*/if (is_null($field_name) || $field_name == "") {$field_name = sprintf("FieldObject%d", $this->get_object_id());};$this->_field_name = $field_name;}function get_field_name() {if ($this->_field_name) {return $this->_field_name;} else {return sprintf("FormObject%d", $this->get_object_id());};}function _dict(&$handler) {return array_merge(parent::_dict($handler),array("Parent" => $handler->_reference($this->_parent),"T" => $handler->_textstring($this->get_field_name())));}function pdf(&$handler) {return $handler->_dictionary($this->_dict($handler));}function set_field_name($value) {$this->_field_name = $value;}function set_parent(&$form) {$this->_parent =& $form;}function get_parent() {return $this->_parent;}}/*** Checkbox interactive form widget*/class PDFFieldCheckBox extends PDFField {var $_value;var $_appearance_on;var $_appearance_off;var $_checked;function PDFFieldCheckBox(&$handler,$object_id,$generation_id,$rect,$field_name,$value,$checked) {$this->PDFField($handler,$object_id,$generation_id,$rect,$field_name);$this->_value = $value;$this->_checked = $checked;$this->_appearance_on = new PDFAppearanceStream($handler,$handler->_generate_new_object_number(),$generation_id,"Q 0 0 1 rg BT /F1 10 Tf 0 0 Td (8) Tj ET q");$this->_appearance_off = new PDFAppearanceStream($handler,$handler->_generate_new_object_number(),$generation_id,"Q 0 0 1 rg BT /F1 10 Tf 0 0 Td (8) Tj ET q");}function _dict(&$handler) {return array_merge(parent::_dict($handler),array('FT' => '/Btn','Ff' => sprintf("%d", 0),'TU' => "<FEFF>",'MK' => "<< /CA (3) >>",'DV' => $this->_checked ? $handler->_name($this->_value) : "/Off",'V' => $this->_checked ? $handler->_name($this->_value) : "/Off",'AP' => sprintf("<< /N << /%s %s /Off %s >> >>",$this->_value,$handler->_reference($this->_appearance_on),$handler->_reference($this->_appearance_off))));}function _out_nested(&$handler) {parent::_out_nested($handler);$this->_appearance_on->out($handler);$this->_appearance_off->out($handler);}}class PDFFieldPushButton extends PDFField {var $_appearance;var $fontindex;var $fontsize;function _out_nested(&$handler) {parent::_out_nested($handler);$this->_appearance->out($handler);}function PDFFieldPushButton(&$handler,$object_id,$generation_id,$rect,$fontindex,$fontsize) {$this->PDFField($handler,$object_id,$generation_id,$rect,null);$this->fontindex = $fontindex;$this->fontsize = $fontsize;$this->_appearance = new PDFAppearanceStream($handler,$handler->_generate_new_object_number(),$generation_id,"Q 0 0 1 rg BT /F1 10 Tf 0 0 Td (8) Tj ET q");}function _action(&$handler) {return "<< >>";}function _dict(&$handler) {return array_merge(parent::_dict($handler),array('FT' => '/Btn','Ff' => sprintf("%d", 1 << 16),'TU' => "<FEFF>",'DR' => "2 0 R",'DA' => sprintf("(0 0 0 rg /F%d %.2f Tf)",$this->fontindex,$this->fontsize),'AP' => "<< /N ".$handler->_reference($this->_appearance)." >>",'AA' => $this->_action($handler)));}}class PDFFieldPushButtonImage extends PDFFieldPushButton {var $_link;function PDFFieldPushButtonImage(&$handler,$object_id,$generation_id,$rect,$fontindex,$fontsize,$field_name,$value,$link) {$this->PDFFieldPushButton($handler,$object_id,$generation_id,$rect,$fontindex,$fontsize);$this->_link = $link;$this->set_field_name($field_name);}function _action(&$handler) {$action = $handler->_dictionary(array('S' => "/SubmitForm",'F' => $handler->_textstring($this->_link),'Fields'=> $handler->_reference_array(array($this->get_parent())),'Flags' => PDF_SUBMIT_FORM_HTML | PDF_SUBMIT_FORM_COORDINATES));return $handler->_dictionary(array('U' => $action));}}class PDFFieldPushButtonSubmit extends PDFFieldPushButton {var $_link;var $_caption;function PDFFieldPushButtonSubmit(&$handler,$object_id,$generation_id,$rect,$fontindex,$fontsize,$field_name,$value,$link) {$this->PDFFieldPushButton($handler,$object_id,$generation_id,$rect,$fontindex,$fontsize);$this->_link = $link;$this->_caption = $value;$this->set_field_name($field_name);}function _action(&$handler) {$action = $handler->_dictionary(array('S' => "/SubmitForm",'F' => $handler->_textstring($this->_link),'Fields'=> $handler->_reference_array(array($this->get_parent())),'Flags' =>(1 << 2) // ExportFormat (HTML)));return $handler->_dictionary(array('U' => $action));}}class PDFFieldPushButtonReset extends PDFFieldPushButton {function PDFFieldPushButtonReset(&$handler,$object_id,$generation_id,$rect,$fontindex,$fontsize) {$this->PDFFieldPushButton($handler,$object_id,$generation_id,$rect,$fontindex,$fontsize);}function _action(&$handler) {$action = $handler->_dictionary(array('S' => "/ResetForm"));return $handler->_dictionary(array('U' => $action));}}/*** Radio button inside the group.** Note that radio button is not a field itself; only a group of radio buttons* should have name.*/class PDFFieldRadio extends PDFAnnotationWidget {/*** @var PDFFieldRadioGroup reference to a radio button group* @access private*/var $_parent;/*** @var String value of this radio button* @access private*/var $_value;var $_appearance_on;var $_appearance_off;function PDFFieldRadio(&$handler,$object_id,$generation_id,$rect,$value) {$this->PDFAnnotationWidget($handler,$object_id,$generation_id,$rect);$this->_value = $value;$this->_appearance_on = new PDFAppearanceStream($handler,$handler->_generate_new_object_number(),$generation_id,"Q 0 0 1 rg BT /F1 10 Tf 0 0 Td (8) Tj ET q");$this->_appearance_off = new PDFAppearanceStream($handler,$handler->_generate_new_object_number(),$generation_id,"Q 0 0 1 rg BT /F1 10 Tf 0 0 Td (8) Tj ET q");}function _dict(&$handler) {return array_merge(parent::_dict($handler),array('MK' => "<< /CA (l) >>",'Parent' => $handler->_reference($this->_parent),'AP' => sprintf("<< /N << /%s %s /Off %s >> >>",$this->_value,$handler->_reference($this->_appearance_on),$handler->_reference($this->_appearance_off))));}function _out_nested(&$handler) {parent::_out_nested($handler);$this->_appearance_on->out($handler);$this->_appearance_off->out($handler);}/*** Set a reference to the radio button group containing this group** @param PDFFieldRadioGroup $parent reference to a group object*/function set_parent(&$parent) {$this->_parent =& $parent;}}/*** Create new group of radio buttons*/class PDFFieldRadioGroup extends PDFFieldGroup {var $_parent;var $_checked;function _dict($handler) {return array_merge(parent::_dict($handler),array('DV' => $this->_checked ? $handler->_name($this->_checked) : "/Off",'V' => $this->_checked ? $handler->_name($this->_checked) : "/Off","FT" => $handler->_name('Btn'),"Ff" => sprintf("%d", 1 << 15),"Parent" => $handler->_reference($this->_parent)));}function _check_field_name($field) {/*** As radio buttons always have same field name, no checking should be made here*/return true;}function PDFFieldRadioGroup(&$handler,$object_id,$generation_id,$group_name) {$this->PDFFieldGroup($handler,$object_id,$generation_id,$group_name);$this->_checked = null;}/*** @return String name of the radio group*/function get_field_name() {return $this->_group_name;}function set_checked($value) {$this->_checked = $value;}function set_parent(&$parent) {$this->_parent =& $parent;}}class PDFFieldSelect extends PDFField {var $_options;var $_value;function _dict(&$handler) {$options = array();foreach ($this->_options as $arr) {$options[] = $handler->_array(sprintf("%s %s",$handler->_textstring($arr[0]),$handler->_textstring($arr[1])));};$options_str = $handler->_array(implode(" ",$options));return array_merge(parent::_dict($handler),array('FT' => '/Ch','Ff' => PDF_FIELD_CHOICE_COMBO,'V' => $handler->_textstring($this->_value), // Current value'DV' => $handler->_textstring($this->_value), // Default value'DR' => "2 0 R",'Opt' => $options_str));}function PDFFieldSelect(&$handler,$object_id,$generation_id,$rect,$field_name,$value,$options) {$this->PDFField($handler,$object_id,$generation_id,$rect,$field_name);$this->_options = $options;$this->_value = $value;}}/*** Interactive text input*/class PDFFieldText extends PDFField {var $fontindex;var $fontsize;var $_appearance;/*** @var String contains the default value of this text field* @access private*/var $_value;function _dict(&$handler) {return array_merge(parent::_dict($handler),array('FT' => '/Tx','V' => $handler->_textstring($this->_value), // Current value'DV' => $handler->_textstring($this->_value), // Default value'DR' => "2 0 R",// @TODO fix font references'DA' => sprintf("(0 0 0 rg /FF%d %.2f Tf)",$this->fontindex,$this->fontsize),// 'AP' => $handler->_dictionary(array("N" => $handler->_reference($this->_appearance))),));}function _out_nested(&$handler) {// $this->_appearance->out($handler);}function PDFFieldText(&$handler,$object_id,$generation_id,$rect,$field_name,$value,$fontindex,$fontsize) {$this->PDFField($handler,$object_id,$generation_id,$rect,$field_name);$this->fontindex = $fontindex;$this->fontsize = $fontsize;$this->_value = $value;// $this->_appearance = new PDFAppearanceStream($handler,// $handler->_generate_new_object_number(),// $generation_id,// "/Tx BMC EMC");}}class PDFFieldMultilineText extends PDFFieldText {function _dict(&$handler) {return array_merge(parent::_dict($handler),array('Ff' => PDF_FIELD_TEXT_MULTILINE));}}/*** "Password" text input field*/class PDFFieldPassword extends PDFFieldText {function PDFFieldPassword(&$handler,$object_id,$generation_id,$rect,$field_name,$value,$fontindex,$fontsize) {$this->PDFFieldText($handler,$object_id,$generation_id,$rect,$field_name,$value,$fontindex,$fontsize);}function _dict(&$handler) {return array_merge(parent::_dict($handler),array('Ff' => PDF_FIELD_TEXT_PASSWORD));}}class FPDF {//Private propertiesvar $page; //current page numbervar $n; //current object numbervar $offsets; //array of object offsetsvar $buffer; //buffer holding in-memory PDFvar $pages; //array containing pagesvar $state; //current document statevar $compress; //compression flagvar $DefOrientation; //default orientationvar $CurOrientation; //current orientationvar $OrientationChanges; //array indicating orientation changesvar $k; //scale factor (number of points in user unit)var $fwPt,$fhPt; //dimensions of page format in pointsvar $fw,$fh; //dimensions of page format in user unitvar $wPt,$hPt; //current dimensions of page in pointsvar $w,$h; //current dimensions of page in user unitvar $lMargin; //left marginvar $tMargin; //top marginvar $rMargin; //right marginvar $bMargin; //page break marginvar $cMargin; //cell marginvar $x,$y; //current position in user unit for cell positioningvar $lasth; //height of last cell printedvar $LineWidth; //line width in user unitvar $fonts; //array of used fontsvar $FontFiles; //array of font filesvar $diffs; //array of encoding differencesvar $images; //array of used images// var $PageLinks; //array of links in pagesvar $links; //array of internal linksvar $FontFamily; //current font familyvar $FontStyle; //current font stylevar $underline; //underlining flagvar $overline;var $strikeout;var $CurrentFont; //current font infovar $FontSizePt; //current font size in pointsvar $FontSize; //current font size in user unitvar $DrawColor; //commands for drawing colorvar $FillColor; //commands for filling colorvar $TextColor; //commands for text colorvar $ColorFlag; //indicates whether fill and text colors are differentvar $ws; //word spacingvar $AutoPageBreak; //automatic page breakingvar $PageBreakTrigger; //threshold used to trigger page breaksvar $InFooter; //flag set when processing footervar $ZoomMode; //zoom display modevar $LayoutMode; //layout display modevar $title; //titlevar $subject; //subjectvar $author; //authorvar $keywords; //keywordsvar $creator; //creatorvar $AliasNbPages; //alias for total number of pagesvar $PDFVersion; //PDF version numbervar $_forms;var $_form_radios;var $_pages;function moveto($x, $y) {$this->_out(sprintf("%.2f %.2f m",$this->x_coord($x),$this->y_coord($y)));}function lineto($x, $y) {$this->_out(sprintf("%.2f %.2f l",$this->x_coord($x),$this->y_coord($y)));}function closepath() {$this->_out("h");}function stroke() {$this->_out("S");}function is_object_written($id) {return isset($this->offsets[$id]);}function x_coord($x) {return $x * $this->k;}function y_coord($y) {return ($this->h - $y)*$this->k;}// PDF specs:// 3.2.9 Indirect Objects// Any object in a PDF file may be labeled as an indirect object. This gives the object// a unique object identifier by which other objects can refer to it (for example, as an// element of an array or as the value of a dictionary entry). The object identifier// consists of two parts:// * A positive integer object number. Indirect objects are often numbered sequentially// within a PDF file, but this is not required; object numbers may be// assigned in any arbitrary order.// * A non-negative integer generation number. In a newly created file, all indirect// objects have generation numbers of 0. Nonzero generation numbers may be introduced// when the file is later updated; see Sections 3.4.3, “Cross-Reference// Table,” and 3.4.5, “Incremental Updates.”// Together, the combination of an object number and a generation number uniquely// identifies an indirect object. The object retains the same object number and// generation number throughout its existence, even if its value is modified.//function _indirect_object($object) {$object_number = $object->get_object_id();$generation_number = $object->get_generation_id();$object_string = $object->pdf($this);$this->offsets[$object_number] = strlen($this->buffer);return "$object_number $generation_number obj\n${object_string}\nendobj";}function _stream($content) {return "stream\n".$content."\nendstream";}/*** @TODO check name for validity*/function _name($name) {return sprintf("/%s", $name);}function _dictionary($dict) {$content = "";foreach ($dict as $key => $value) {$content .= "/$key $value\n";};return "<<\n".$content."\n>>";}function _array($array_str) {return "[$array_str]";}function _reference(&$object) {$object_id = $object->get_object_id();$generation_id = $object->get_generation_id();return "$object_id $generation_id R";}function _reference_array($object_array) {$array_str = "";for ($i=0; $i<count($object_array); $i++) {$array_str .= $this->_reference($object_array[$i])." ";};return $this->_array($array_str);}function _generate_new_object_number() {$this->n++;return $this->n;}function add_form($name) {$form = new PDFFieldGroup($this,$this->_generate_new_object_number(), // Object identifier0,$name);$this->_forms[] =& $form;}function add_field_select($x, $y, $w, $h, $name, $value, $options) {$field =& new PDFFieldSelect($this,$this->_generate_new_object_number(), // Object identifier0, // Generationnew PDFRect($x, $y, $w, $h), // Annotation rectangle$name, // Field name$value,$options);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}/*** Create new checkbox field object** @param $x Integer Left coordinate of the widget bounding bog* @param $y Integer Upper coordinate of the widget bounding bog* @param $w Integer Widget width* @param $h Integer Widget height* @param $name String name of the field to be created* @param $value String value to be posted for this checkbox** @TODO check if fully qualified field name will be unique in PDF file*/function add_field_checkbox($x, $y, $w, $h, $name, $value, $checked) {$field =& new PDFFieldCheckBox($this,$this->_generate_new_object_number(), // Object identifier0, // Generationnew PDFRect($x, $y, $w, $h), // Annotation rectangle$name, // Field name$value, $checked); // Checkbox "on" value$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function ¤t_form() {if (count($this->_forms) == 0) {/*** Handle invalid HTML; if we've met an input control outside the form,* generate a new form with random name*/$id = $this->_generate_new_object_number();$name = sprintf("AnonymousFormObject_%u", $id);error_log(sprintf("Anonymous form generated with name %s; check your HTML for validity",$name));$form = new PDFFieldGroup($this,$id, // Object identifier0,$name);$this->_forms[] =& $form;};return $this->_forms[count($this->_forms)-1];}function add_field_radio($x, $y, $w, $h, $group_name, $value, $checked) {if (isset($this->_form_radios[$group_name])) {$field =& $this->_form_radios[$group_name];} else {$field =& new PDFFieldRadioGroup($this,$this->_generate_new_object_number(),0,$group_name);$current_form =& $this->current_form();$current_form->add_field($field);$this->_form_radios[$group_name] =& $field;};$radio =& new PDFFieldRadio($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$value);$field->add_field($radio);if ($checked) { $field->set_checked($value); };$this->_pages[count($this->_pages)-1]->add_annotation($radio);}/*** Create a new interactive text form** @param $x Left coordinate of the widget bounding box* @param $y Top coordinate of the widget bounding box* @param $w Widget width* @param $h Widget height* @param $value Default widget value* @param $field_name Field name** @return Field number*/function add_field_text($x, $y, $w, $h, $value, $field_name) {$field =& new PDFFieldText($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$field_name,$value,$this->CurrentFont['i'],$this->FontSizePt);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function add_field_multiline_text($x, $y, $w, $h, $value, $field_name) {$field =& new PDFFieldMultilineText($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$field_name,$value,$this->CurrentFont['i'],$this->FontSizePt);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}/*** Create a new interactive password input field** @param $x Left coordinate of the widget bounding box* @param $y Top coordinate of the widget bounding box* @param $w Widget width* @param $h Widget height* @param $value Default widget value* @param $field_name Field name** @return Field number*/function add_field_password($x, $y, $w, $h, $value, $field_name) {$field =& new PDFFieldPassword($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$field_name,$value,$this->CurrentFont['i'],$this->FontSizePt);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function add_field_pushbuttonimage($x, $y, $w, $h, $field_name, $value, $actionURL) {$field =& new PDFFieldPushButtonImage($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$this->CurrentFont['i'],$this->FontSizePt,$field_name,$value,$actionURL);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function add_field_pushbuttonsubmit($x, $y, $w, $h, $field_name, $value, $actionURL) {$field =& new PDFFieldPushButtonSubmit($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$this->CurrentFont['i'],$this->FontSizePt,$field_name,$value,$actionURL);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function add_field_pushbuttonreset($x, $y, $w, $h) {$field =& new PDFFieldPushButtonReset($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),null,$this->CurrentFont['i'],$this->FontSizePt);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function add_field_pushbutton($x, $y, $w, $h) {$field =& new PDFFieldPushButton($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),null,$this->CurrentFont['i'],$this->FontSizePt);$current_form =& $this->current_form();$current_form->add_field($field);$this->_pages[count($this->_pages)-1]->add_annotation($field);}function SetDash($x, $y) {$x = (int)$x;$y = (int)$y;$this->_out(sprintf("[%d %d] 0 d", $x*2, $y*2));}function _GetFontBBox() {return preg_split("/[\[\]\s]+/", $this->CurrentFont['desc']['FontBBox']);}function _dounderline($x,$y,$txt) {//Underline text$up=$this->CurrentFont['up'];$ut=$this->CurrentFont['ut'];$w=$this->GetStringWidth($txt)+$this->ws*substr_count($txt,' ');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);}function _dooverline($x,$y,$txt) {$bbox = $this->_GetFontBBox();$up = round($bbox[3] * 0.8);$ut=$this->CurrentFont['ut'];$w=$this->GetStringWidth($txt)+$this->ws*substr_count($txt,' ');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);}function _dostrikeout($x,$y,$txt) {$bbox = $this->_GetFontBBox();$up = round($bbox[3] * 0.25);$ut=$this->CurrentFont['ut'];$w=$this->GetStringWidth($txt)+$this->ws*substr_count($txt,' ');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);}function SetDecoration($underline, $overline, $strikeout) {$this->underline = $underline;$this->overline = $overline;$this->strikeout = $strikeout;}function ClipPath($path) {if (count($path) < 3) {die("Attempt to clip on the path containing less than three points");};$this->MakePath($path);$this->Clip();}function Clip() {$this->_out("W n");}function _LoadFont($fontkey, $family, $encoding, $style) {$style = strtolower($style);if (!isset($this->fonts[$fontkey])) {global $g_font_resolver_pdf;$file = $g_font_resolver_pdf->ttf_mappings[$family];$embed = $g_font_resolver_pdf->embed[$family];// Remove the '.ttf' suffix$file = substr($file, 0, strlen($file) - 4);// Generate (if required) PHP font description filesif (!file_exists($this->_getfontpath().$fontkey.'.php')) {// As MakeFont squeaks a lot, we'll need to capture and discard its outputob_start();MakeFont(PDFLIB_TTF_FONTS_REPOSITORY.$file.'.ttf',PDFLIB_TTF_FONTS_REPOSITORY.$file.'.afm',$this->_getfontpath(),$fontkey.'.php',$encoding);ob_end_clean();};$this->AddFont($fontkey, $family, "", $encoding, $fontkey.'.php', $embed);};}function _MakeFontKey($family, $encoding) {return $family.'-'.$encoding;}function GetFontAscender($name, $encoding) {$fontkey = $this->_MakeFontKey($name, $encoding);$this->_LoadFont($fontkey, $name, $encoding, '');return $this->fonts[$fontkey]['desc']['Ascent'] / 1000;}function GetFontDescender($name, $encoding) {$fontkey = $this->_MakeFontKey($name, $encoding);$this->_LoadFont($fontkey, $name, $encoding, '');return -$this->fonts[$fontkey]['desc']['Descent'] / 1000;}// Note that FPDF do some caching, which can conflict with "save/restore" pairsfunction Save() { $this->_out("q"); }function Restore() { $this->_out("Q"); }function Translate($dx, $dy) {$this->_out(sprintf("1 0 0 1 %.2f %.2f cm", $dx, $dy));}function Rotate($alpha) {$this->_out(sprintf("%.2f %.2f %.2f %.2f 0 0 cm",cos($alpha/180*pi()),sin($alpha/180*pi()),-sin($alpha/180*pi()),cos($alpha/180*pi())));}function SetTextRendering($mode) {$this->_out(sprintf("%d Tr", $mode));}function MakePath($path) {$this->_out(sprintf("%.2f %.2f m", $path[0]['x'], $path[0]['y']));for ($i=1; $i<count($path); $i++) {$this->_out(sprintf("%.2f %.2f l", $path[$i]['x'], $path[$i]['y']));};}function FillPath($path) {if (count($path) < 3) {die("Attempt to fill path containing less than three points");};$this->_out($this->FillColor);$this->MakePath($path);$this->Fill();}function Fill() {$this->_out("f");}// Thanks G. Adam Stanislav for information about approximation circle using bezier curves// http://www.whizkidtech.redprince.net/bezier/circle///function Circle($x, $y, $r) {$kappa = (sqrt(2) - 1) / 3 * 4;$l = $kappa * $r;$this->_out(sprintf("%.2f %.f2 m", $x + $r, $y));$this->_out(sprintf("%.2f %.f2 %.2f %.2f %.2f %.2f c",$x + $r, $y + $l,$x + $l, $y + $r,$x, $y + $r));$this->_out(sprintf("%.2f %.f2 %.2f %.2f %.2f %.2f c",$x - $l, $y + $r,$x - $r, $y + $l,$x - $r, $y));$this->_out(sprintf("%.2f %.f2 %.2f %.2f %.2f %.2f c",$x - $r, $y - $l,$x - $l, $y - $r,$x, $y - $r));$this->_out(sprintf("%.2f %.f2 %.2f %.2f %.2f %.2f c",$x + $l, $y - $r,$x + $r, $y - $l,$x + $r, $y));}/******************************************************************************** ** Public methods ** ********************************************************************************/function FPDF($orientation='P',$unit='mm',$format='A4') {$this->_forms = array();$this->_form_radios = array();$this->_pages = array();//Some checks$this->_dochecks();//Initialization of properties$this->page=0;$this->n=2;$this->buffer='';$this->pages=array();$this->OrientationChanges=array();$this->state=0;$this->fonts=array();$this->FontFiles=array();$this->diffs = array();$this->images = array();$this->links = array();$this->InFooter=false;$this->lasth=0;$this->FontFamily='';$this->FontStyle='';$this->FontSizePt=12;$this->underline = false;$this->overline = false;$this->strikeout = false;$this->DrawColor='0 G';$this->FillColor='0 g';$this->TextColor='0 g';$this->ColorFlag=false;$this->ws=0;//Scale factorswitch ($unit) {case 'pt':$this->k = 1; break;case 'mm':$this->k = 72/25.4; break;case 'cm':$this->k = 72/2.54; break;case 'in':$this->k = 72;default:$this->Error('Incorrect unit: '.$unit);};//Page formatif (is_string($format)) {$format=strtolower($format);switch ($format) {case 'a3':$format=array(841.89,1190.55); break;case 'a4':$format=array(595.28,841.89); break;case 'a5':$format=array(420.94,595.28); break;case 'letter':$format=array(612,792); break;case 'legal':$format=array(612,1008); break;default:$this->Error('Unknown page format: '.$format);};$this->fwPt=$format[0];$this->fhPt=$format[1];} else {$this->fwPt=$format[0]*$this->k;$this->fhPt=$format[1]*$this->k;};$this->fw=$this->fwPt/$this->k;$this->fh=$this->fhPt/$this->k;//Page orientation$orientation=strtolower($orientation);if($orientation=='p' || $orientation=='portrait') {$this->DefOrientation='P';$this->wPt=$this->fwPt;$this->hPt=$this->fhPt;} elseif($orientation=='l' || $orientation=='landscape') {$this->DefOrientation='L';$this->wPt=$this->fhPt;$this->hPt=$this->fwPt;} else {$this->Error('Incorrect orientation: '.$orientation);};$this->CurOrientation=$this->DefOrientation;$this->w=$this->wPt/$this->k;$this->h=$this->hPt/$this->k;//Page margins (1 cm)$margin=28.35/$this->k;$this->SetMargins($margin,$margin);//Interior cell margin (1 mm)$this->cMargin=$margin/10;//Line width (0.2 mm)$this->LineWidth=.567/$this->k;//Automatic page break$this->SetAutoPageBreak(true,2*$margin);//Full width display mode$this->SetDisplayMode('fullwidth');//Enable compression$this->SetCompression(true);//Set default PDF version number$this->PDFVersion='1.3';}function SetMargins($left,$top,$right=-1){//Set left, top and right margins$this->lMargin=$left;$this->tMargin=$top;if($right==-1)$right=$left;$this->rMargin=$right;}function SetLeftMargin($margin){//Set left margin$this->lMargin=$margin;if($this->page>0 && $this->x<$margin)$this->x=$margin;}function SetTopMargin($margin){//Set top margin$this->tMargin=$margin;}function SetRightMargin($margin){//Set right margin$this->rMargin=$margin;}function SetAutoPageBreak($auto,$margin=0){//Set auto page break mode and triggering margin$this->AutoPageBreak=$auto;$this->bMargin=$margin;$this->PageBreakTrigger=$this->h-$margin;}function SetDisplayMode($zoom,$layout='continuous'){//Set display mode in viewerif($zoom=='fullpage' || $zoom=='fullwidth' || $zoom=='real' || $zoom=='default' || !is_string($zoom))$this->ZoomMode=$zoom;else$this->Error('Incorrect zoom display mode: '.$zoom);if($layout=='single' || $layout=='continuous' || $layout=='two' || $layout=='default')$this->LayoutMode=$layout;else$this->Error('Incorrect layout display mode: '.$layout);}function SetCompression($compress){//Set page compressionif(function_exists('gzcompress'))$this->compress=$compress;else$this->compress=false;}function SetTitle($title){//Title of document$this->title=$title;}function SetSubject($subject){//Subject of document$this->subject=$subject;}function SetAuthor($author){//Author of document$this->author=$author;}function SetKeywords($keywords){//Keywords of document$this->keywords=$keywords;}function SetCreator($creator){//Creator of document$this->creator=$creator;}function AliasNbPages($alias='{nb}'){//Define an alias for total number of pages$this->AliasNbPages=$alias;}function Error($msg){//Fatal errordie('<B>FPDF error: </B>'.$msg);}function Open() {//Begin document$this->state=1;}function Close() {//Terminate documentif ($this->state==3) {return;};if ($this->page==0) {$this->AddPage();};//Page footer$this->InFooter=true;$this->Footer();$this->InFooter=false;//Close page$this->_endpage();//Close document$this->_enddoc();}function AddPage($orientation='') {$this->_pages[] =& new PDFPage($this, $this->_generate_new_object_number(), 0);//Start a new pageif ($this->state==0) {$this->Open();};$family=$this->FontFamily;$style=$this->FontStyle.($this->underline ? 'U' : '');$size=$this->FontSizePt;$lw=$this->LineWidth;$dc=$this->DrawColor;$fc=$this->FillColor;$tc=$this->TextColor;$cf=$this->ColorFlag;if ($this->page>0) {//Page footer$this->InFooter=true;$this->Footer();$this->InFooter=false;//Close page$this->_endpage();}//Start new page$this->_beginpage($orientation);//Set line cap style to square$this->_out('2 J');//Set line width$this->LineWidth=$lw;$this->_out(sprintf('%.2f w',$lw*$this->k));//Set colors$this->DrawColor=$dc;if ($dc!='0 G') {$this->_out($dc);};$this->FillColor=$fc;if ($fc!='0 g') {$this->_out($fc);};$this->TextColor=$tc;$this->ColorFlag=$cf;//Page header$this->Header();//Restore line widthif ($this->LineWidth!=$lw) {$this->LineWidth=$lw;$this->_out(sprintf('%.2f w',$lw*$this->k));}//Restore colorsif ($this->DrawColor!=$dc) {$this->DrawColor=$dc;$this->_out($dc);}if ($this->FillColor!=$fc) {$this->FillColor=$fc;$this->_out($fc);}$this->TextColor=$tc;$this->ColorFlag=$cf;if (!is_null($this->CurrentFont)) {$this->_out(sprintf('BT /F%d %.2f Tf ET',$this->CurrentFont['i'],$this->FontSizePt));};}function Header(){//To be implemented in your own inherited class}function Footer(){//To be implemented in your own inherited class}function PageNo(){//Get current page numberreturn $this->page;}function SetDrawColor($r,$g=-1,$b=-1) {// Set color for all stroking operationsif (($r==0 && $g==0 && $b==0) || $g==-1) {$new_color = sprintf('%.3f G',$r/255);} else {$new_color = sprintf('%.3f %.3f %.3f RG',$r/255,$g/255,$b/255);};if ($this->page > 0 /*&& $this->DrawColor != $new_color*/) {$this->DrawColor = $new_color;$this->_out($this->DrawColor);};}function SetFillColor($r,$g=-1,$b=-1) {// Set color for all filling operationsif (($r==0 && $g==0 && $b==0) || $g==-1) {$new_color = sprintf('%.3f g',$r/255);} else {$new_color = sprintf('%.3f %.3f %.3f rg',$r/255,$g/255,$b/255);};if ($this->page>0 /*&& $this->FillColor != $new_color*/) {$this->FillColor = $new_color;$this->ColorFlag=($this->FillColor!=$this->TextColor);$this->_out($this->FillColor);};}function SetTextColor($r,$g=-1,$b=-1) {//Set color for textif (($r==0 && $g==0 && $b==0) || $g==-1) {$this->TextColor=sprintf('%.3f g',$r/255);} else {$this->TextColor=sprintf('%.3f %.3f %.3f rg',$r/255,$g/255,$b/255);};$this->ColorFlag=($this->FillColor!=$this->TextColor);}function GetStringWidth($s) {//Get width of a string in the current font$s=(string)$s;$cw = &$this->CurrentFont['cw'];$w=0;$l=strlen($s);for($i=0; $i<$l; $i++) {$w+=$cw[$s{$i}];};return $w*$this->FontSize/1000;}function SetLineWidth($width) {//Set line width$this->LineWidth=$width;if($this->page>0)$this->_out(sprintf('%.2f w',$width*$this->k));}function Line($x1,$y1,$x2,$y2) {//Draw a line$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));}function Rect($x,$y,$w,$h,$style=''){//Draw a rectangleif($style=='F')$op='f';elseif($style=='FD' || $style=='DF')$op='B';else$op='S';$this->_out(sprintf('%.2f %.2f %.2f %.2f re %s',$x*$this->k,($this->h-$y)*$this->k,$w*$this->k,-$h*$this->k,$op));}function AddFont($fontkey, $family, $style, $encoding, $file, $bEmbed) {//Add a TrueType or Type1 fontif ($file=='') {$file=str_replace(' ','',$family).strtolower($style).'.php';};$style=strtoupper($style);if ($style=='IB') { $style='BI'; };if(isset($this->fonts[$fontkey])) {$this->Error('Font already added: '.$family.' '.$style);};$filepath = $this->_getfontpath().$file;include($filepath);// After we've executed 'include' the $file variable// have been overwritten by $file declared in font definition file; if we do not want// to embed the font in the PDF file, we should set to empty stringif (!$bEmbed) { $file = ''; };if(!isset($name)) {$this->Error("Could not include font definition file: $filepath");};$i=count($this->fonts)+1;$this->fonts[$fontkey]=array('i' =>$i,'type' =>$type,'name' =>$name,'desc' =>$desc,'up' =>$up,'ut' =>$ut,'cw' =>$cw,'enc' =>$enc,'file' =>$file);if ($diff) {//Search existing encodings$d=0;$nb=count($this->diffs);for ($i=1; $i<=$nb; $i++) {if($this->diffs[$i]==$diff){$d=$i;break;}}if ($d==0) {$d=$nb+1;$this->diffs[$d]=$diff;}$this->fonts[$fontkey]['diff']=$d;}if ($file) {if($type=='TrueType') {$this->FontFiles[$file]=array('length1'=>$originalsize);} else {$this->FontFiles[$file]=array('length1'=>$size1,'length2'=>$size2);};}}function SetFont($family,$encoding, $style='',$size=0) {// Select a font; size given in pointsglobal $fpdf_charwidths;$style=strtoupper($style);if (strpos($style,'U')!==false) {$this->underline=true;$style=str_replace('U','',$style);} else {$this->underline=false;};if ($style=='IB') { $style='BI'; };if ($size==0) {$size = $this->FontSizePt;};$fontkey = $this->_MakeFontKey($family, $encoding);$this->_LoadFont($fontkey, $family, $encoding, $style);if ($this->page > 0 /* &&($this->CurrentFont['i'] != $this->fonts[$fontkey]['i'] ||$this->FontSizePt != $size) */) {//Select it$this->FontFamily = $family;$this->FontStyle = $style;$this->FontSizePt = $size;$this->FontSize = $size/$this->k;$this->CurrentFont = &$this->fonts[$fontkey];$this->_out(sprintf('BT /F%d %.2f Tf ET',$this->CurrentFont['i'],$this->FontSizePt));};}// function SetFontSize($size) {// //Set font size in points// if ($this->FontSizePt == $size) {// return;// };// $this->FontSizePt=$size;// $this->FontSize=$size/$this->k;// if ($this->page>0) {// $this->_out(sprintf('BT /F%d %.2f Tf ET',$this->CurrentFont['i'],$this->FontSizePt));// };// }function AddLink() {//Create a new internal link$n=count($this->links)+1;$this->links[$n]=array(0,0);return $n;}function SetLink($link,$y=0,$page=-1) {//Set destination of internal linkif ($y==-1) {$y=$this->y;};if ($page==-1) {$page=$this->page;};$this->links[$link]=array($page,$y);}/*** Add an external hyperlink on the page (an rectangular area). It is not bound to any other PDF element,* like text. It is the task of layout engine to draw the appropriate text inside this area.** @param Float $x X-coordinate of the upper-left corner of the link area* @param Float $y Y-coordinate of the upper-left corner of the link area* @param Float $w link area width* @param Float $h link area height* @param String $link Link URL*/function add_link_external($x, $y, $w, $h, $link) {$link = new PDFAnnotationExternalLink($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$link);$this->_pages[count($this->_pages)-1]->add_annotation($link);}/*** Add an internal hyperlink on the page (an rectangular area). It is not bound to any other PDF element,* like text. It is the task of layout engine to draw the appropriate text inside this area.** @param Float $x X-coordinate of the upper-left corner of the link area* @param Float $y Y-coordinate of the upper-left corner of the link area* @param Float $w link area width* @param Float $h link area height* @param Integer $link Internal Link identifier*/function add_link_internal($x, $y, $w, $h, $link) {$link = new PDFAnnotationInternalLink($this,$this->_generate_new_object_number(),0,new PDFRect($x, $y, $w, $h),$link);$this->_pages[count($this->_pages)-1]->add_annotation($link);}function Text($x,$y,$txt) {//Output a string$s=sprintf('BT %.2f %.2f Td (%s) Tj ET',$x*$this->k,($this->h-$y)*$this->k,$this->_escape($txt));if ($this->underline && $txt!='') {$s.=' '.$this->_dounderline($x,$y,$txt);}if ($this->overline && $txt!='') {$s.=' '.$this->_dooverline($x,$y,$txt);}if ($this->strikeout && $txt!='') {$s.=' '.$this->_dostrikeout($x,$y,$txt);}if($this->ColorFlag)$s='q '.$this->TextColor.' '.$s.' Q';$this->_out($s);}function AcceptPageBreak(){//Accept automatic page break or notreturn $this->AutoPageBreak;}function Cell($w,$h=0,$txt='',$border=0,$ln=0,$align='',$fill=0,$link=''){//Output a cell$k=$this->k;if($this->y+$h>$this->PageBreakTrigger && !$this->InFooter && $this->AcceptPageBreak()){//Automatic page break$x=$this->x;$ws=$this->ws;if($ws>0){$this->ws=0;$this->_out('0 Tw');}$this->AddPage($this->CurOrientation);$this->x=$x;if($ws>0){$this->ws=$ws;$this->_out(sprintf('%.3f Tw',$ws*$k));}}if($w==0)$w=$this->w-$this->rMargin-$this->x;$s='';if($fill==1 || $border==1){if($fill==1)$op=($border==1) ? 'B' : 'f';else$op='S';$s=sprintf('%.2f %.2f %.2f %.2f re %s ',$this->x*$k,($this->h-$this->y)*$k,$w*$k,-$h*$k,$op);}if(is_string($border)){$x=$this->x;$y=$this->y;if(strpos($border,'L')!==false)$s.=sprintf('%.2f %.2f m %.2f %.2f l S ',$x*$k,($this->h-$y)*$k,$x*$k,($this->h-($y+$h))*$k);if(strpos($border,'T')!==false)$s.=sprintf('%.2f %.2f m %.2f %.2f l S ',$x*$k,($this->h-$y)*$k,($x+$w)*$k,($this->h-$y)*$k);if(strpos($border,'R')!==false)$s.=sprintf('%.2f %.2f m %.2f %.2f l S ',($x+$w)*$k,($this->h-$y)*$k,($x+$w)*$k,($this->h-($y+$h))*$k);if(strpos($border,'B')!==false)$s.=sprintf('%.2f %.2f m %.2f %.2f l S ',$x*$k,($this->h-($y+$h))*$k,($x+$w)*$k,($this->h-($y+$h))*$k);}if($txt!==''){if ($align=='R') {$dx=$w-$this->cMargin-$this->GetStringWidth($txt);} elseif ($align=='C') {$dx=($w-$this->GetStringWidth($txt))/2;} else {$dx=$this->cMargin;};if ($this->ColorFlag) {$s.='q '.$this->TextColor.' ';};$txt2=str_replace(')','\\)',str_replace('(','\\(',str_replace('\\','\\\\',$txt)));$s.=sprintf('BT %.2f %.2f Td (%s) Tj ET',($this->x+$dx)*$k,($this->h-($this->y+.5*$h+.3*$this->FontSize))*$k,$txt2);if ($this->underline) {$s.=' '.$this->_dounderline($this->x+$dx,$this->y+.5*$h+.3*$this->FontSize,$txt);};if($this->ColorFlag)$s.=' Q';if($link)$this->Link($this->x+$dx,$this->y+.5*$h-.5*$this->FontSize,$this->GetStringWidth($txt),$this->FontSize,$link);}if($s)$this->_out($s);$this->lasth=$h;if($ln>0){//Go to next line$this->y+=$h;if($ln==1)$this->x=$this->lMargin;}else$this->x+=$w;}function MultiCell($w,$h,$txt,$border=0,$align='J',$fill=0){//Output text with automatic or explicit line breaks$cw=&$this->CurrentFont['cw'];if($w==0)$w=$this->w-$this->rMargin-$this->x;$wmax=($w-2*$this->cMargin)*1000/$this->FontSize;$s=str_replace("\r",'',$txt);$nb=strlen($s);if($nb>0 && $s[$nb-1]=="\n")$nb--;$b=0;if($border){if($border==1){$border='LTRB';$b='LRT';$b2='LR';}else{$b2='';if(strpos($border,'L')!==false)$b2.='L';if(strpos($border,'R')!==false)$b2.='R';$b=(strpos($border,'T')!==false) ? $b2.'T' : $b2;}}$sep=-1;$i=0;$j=0;$l=0;$ns=0;$nl=1;while($i<$nb){//Get next character$c=$s{$i};if($c=="\n"){//Explicit line breakif($this->ws>0){$this->ws=0;$this->_out('0 Tw');}$this->Cell($w,$h,substr($s,$j,$i-$j),$b,2,$align,$fill);$i++;$sep=-1;$j=$i;$l=0;$ns=0;$nl++;if($border && $nl==2)$b=$b2;continue;}if($c==' '){$sep=$i;$ls=$l;$ns++;}$l+=$cw[$c];if($l>$wmax){//Automatic line breakif($sep==-1){if($i==$j)$i++;if($this->ws>0){$this->ws=0;$this->_out('0 Tw');}$this->Cell($w,$h,substr($s,$j,$i-$j),$b,2,$align,$fill);}else{if($align=='J'){$this->ws=($ns>1) ? ($wmax-$ls)/1000*$this->FontSize/($ns-1) : 0;$this->_out(sprintf('%.3f Tw',$this->ws*$this->k));}$this->Cell($w,$h,substr($s,$j,$sep-$j),$b,2,$align,$fill);$i=$sep+1;}$sep=-1;$j=$i;$l=0;$ns=0;$nl++;if($border && $nl==2)$b=$b2;}else$i++;}//Last chunkif($this->ws>0){$this->ws=0;$this->_out('0 Tw');}if($border && strpos($border,'B')!==false)$b.='B';$this->Cell($w,$h,substr($s,$j,$i-$j),$b,2,$align,$fill);$this->x=$this->lMargin;}function Write($h, $txt, $link='') {//Output text in flowing mode$cw=&$this->CurrentFont['cw'];$w=$this->w-$this->rMargin-$this->x;$wmax=($w-2*$this->cMargin)*1000/$this->FontSize;$s=str_replace("\r",'',$txt);$nb=strlen($s);$sep=-1;$i=0;$j=0;$l=0;$nl=1;while ($i<$nb) {//Get next character$c=$s{$i};if ($c=="\n") {//Explicit line break$this->Cell($w,$h,substr($s,$j,$i-$j),0,2,'',0,$link);$i++;$sep=-1;$j=$i;$l=0;if ($nl==1) {$this->x=$this->lMargin;$w=$this->w-$this->rMargin-$this->x;$wmax=($w-2*$this->cMargin)*1000/$this->FontSize;}$nl++;continue;}if ($c==' ') {$sep=$i;};$l+=$cw[$c];if ($l>$wmax) {//Automatic line breakif ($sep==-1) {if($this->x>$this->lMargin) {//Move to next line$this->x=$this->lMargin;$this->y+=$h;$w=$this->w-$this->rMargin-$this->x;$wmax=($w-2*$this->cMargin)*1000/$this->FontSize;$i++;$nl++;continue;}if ($i==$j) {$i++;};$this->Cell($w,$h,substr($s,$j,$i-$j),0,2,'',0,$link);} else {$this->Cell($w,$h,substr($s,$j,$sep-$j),0,2,'',0,$link);$i=$sep+1;}$sep=-1;$j=$i;$l=0;if ($nl==1) {$this->x=$this->lMargin;$w=$this->w-$this->rMargin-$this->x;$wmax=($w-2*$this->cMargin)*1000/$this->FontSize;}$nl++;}else$i++;}//Last chunkif($i!=$j)$this->Cell($l/1000*$this->FontSize,$h,substr($s,$j),0,0,'',0,$link);}function Image($file,$x,$y,$w=0,$h=0,$type='',$link=''){//Put an image on the pageif(!isset($this->images[$file])){//First use of image, get infoif($type==''){$pos=strrpos($file,'.');if(!$pos)$this->Error('Image file has no extension and no type was specified: '.$file);$type=substr($file,$pos+1);}$type=strtolower($type);$mqr=get_magic_quotes_runtime();set_magic_quotes_runtime(0);if($type=='jpg' || $type=='jpeg')$info=$this->_parsejpg($file);elseif($type=='png')$info=$this->_parsepng($file);else{//Allow for additional formats$mtd='_parse'.$type;if(!method_exists($this,$mtd))$this->Error('Unsupported image type: '.$type);$info=$this->$mtd($file);}set_magic_quotes_runtime($mqr);$info['i']=count($this->images)+1;$this->images[$file]=$info;}else {$info=$this->images[$file];};//Automatic width and height calculation if neededif ($w==0 && $h==0) {//Put image at 72 dpi$w=$info['w']/$this->k;$h=$info['h']/$this->k;}if ($w==0) {$w=$h*$info['w']/$info['h'];};if ($h==0) {$h=$w*$info['h']/$info['w'];};$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']));if ($link) {$this->Link($x,$y,$w,$h,$link);};}function Ln($h=''){//Line feed; default value is last cell height$this->x=$this->lMargin;if(is_string($h))$this->y+=$this->lasth;else$this->y+=$h;}function GetX(){//Get x positionreturn $this->x;}function SetX($x){//Set x positionif($x>=0)$this->x=$x;else$this->x=$this->w+$x;}function GetY(){//Get y positionreturn $this->y;}function SetY($y){//Set y position and reset x$this->x=$this->lMargin;if($y>=0)$this->y=$y;else$this->y=$this->h+$y;}function SetXY($x,$y){//Set x and y positions$this->SetY($y);$this->SetX($x);}function Output($name='',$dest=''){//Output PDF to some destination//Finish document if necessaryif($this->state<3)$this->Close();//Normalize parametersif(is_bool($dest))$dest=$dest ? 'D' : 'F';$dest=strtoupper($dest);if($dest==''){if($name==''){$name='doc.pdf';$dest='I';}else$dest='F';}switch($dest){case 'I'://Send to standard outputif(ob_get_contents())$this->Error('Some data has already been output, can\'t send PDF file');if(php_sapi_name()!='cli'){//We send to a browserheader('Content-Type: application/pdf');if(headers_sent())$this->Error('Some data has already been output to browser, can\'t send PDF file');header('Content-Length: '.strlen($this->buffer));header('Content-disposition: inline; filename="'.$name.'"');}echo $this->buffer;break;case 'D'://Download fileif(ob_get_contents())$this->Error('Some data has already been output, can\'t send PDF file');if(isset($_SERVER['HTTP_USER_AGENT']) && strpos($_SERVER['HTTP_USER_AGENT'],'MSIE'))header('Content-Type: application/force-download');elseheader('Content-Type: application/octet-stream');if(headers_sent())$this->Error('Some data has already been output to browser, can\'t send PDF file');header('Content-Length: '.strlen($this->buffer));header('Content-disposition: attachment; filename="'.$name.'"');echo $this->buffer;break;case 'F'://Save to local file$f=fopen($name,'wb');if(!$f)$this->Error('Unable to create output file: '.$name);fwrite($f,$this->buffer,strlen($this->buffer));fclose($f);break;case 'S'://Return as a stringreturn $this->buffer;default:$this->Error('Incorrect output destination: '.$dest);}return '';}/******************************************************************************** ** Protected methods ** ********************************************************************************/function _dochecks(){//Check for locale-related bugif(1.1==1)$this->Error('Don\'t alter the locale before including class file');//Check for decimal separatorif(sprintf('%.1f',1.0)!='1.0')setlocale(LC_NUMERIC,'C');}function _getfontpath(){if(!defined('FPDF_FONTPATH') && is_dir(dirname(__FILE__).'/font'))define('FPDF_FONTPATH',dirname(__FILE__).'/font/');return defined('FPDF_FONTPATH') ? FPDF_FONTPATH : '';}function _putpages() {$nb=$this->page;if (!empty($this->AliasNbPages)) {//Replace number of pagesfor ($n=1; $n<=$nb; $n++) {$this->pages[$n]=str_replace($this->AliasNbPages,$nb,$this->pages[$n]);};}if ($this->DefOrientation=='P') {$wPt=$this->fwPt;$hPt=$this->fhPt;} else {$wPt=$this->fhPt;$hPt=$this->fwPt;};$filter=($this->compress) ? '/Filter /FlateDecode ' : '';$pages_start_obj_number = $this->n+1;for ($n=1; $n<=$nb; $n++) {//Page// $this->_newobj();$page = $this->_pages[$n-1];$this->offsets[$page->get_object_id()] = strlen($this->buffer);$this->_out(sprintf("%u %u obj",$page->object_id, $page->generation_id));$this->_out('<</Type /Page');$this->_out('/Parent 1 0 R');$this->_out("/Annots ".$this->_pages[$n-1]->_annotations($this));if (isset($this->OrientationChanges[$n])) {$this->_out(sprintf('/MediaBox [0 0 %.2f %.2f]',$hPt,$wPt));};$this->_out('/Resources 2 0 R');$this->_out('/Contents '.($this->n+1).' 0 R>>');$this->_out('endobj');//Page content$p=($this->compress) ? gzcompress($this->pages[$n]) : $this->pages[$n];$this->_newobj();$this->_out('<<'.$filter.'/Length '.strlen($p).'>>');$this->_putstream($p);$this->_out('endobj');// Output annotation object for this page$annotations = $this->_pages[$n-1]->annotations;$size = count($annotations);for ($j=0; $j<$size; $j++) {$annotations[$j]->out($this);};}//Pages root$this->offsets[1] = strlen($this->buffer);$this->_out('1 0 obj');$this->_out('<</Type /Pages');$this->_out('/Kids '.$this->_reference_array($this->_pages));$this->_out('/Count '.$nb);$this->_out(sprintf('/MediaBox [0 0 %.2f %.2f]',$wPt,$hPt));$this->_out('>>');$this->_out('endobj');return $pages_start_obj_number;}function _putfonts() {$nf=$this->n;foreach($this->diffs as $diff) {//Encodings$this->_newobj();$this->_out($this->_dictionary(array("Type" => "/Encoding","BaseEncoding" => "/WinAnsiEncoding","Differences" => $this->_array($diff))));$this->_out('endobj');}$mqr=get_magic_quotes_runtime();set_magic_quotes_runtime(0);foreach ($this->FontFiles as $file=>$info) {//Font file embedding$this->_newobj();$this->FontFiles[$file]['n'] = $this->n;$font='';$f=fopen($this->_getfontpath().$file,'rb',1);if (!$f) {$this->Error('Font file not found');};while(!feof($f)) { $font.=fread($f,8192); };fclose($f);$compressed=(substr($file,-2)=='.z');if(!$compressed && isset($info['length2'])) {$header=(ord($font{0})==128);if($header) {//Strip first binary header$font=substr($font,6);}if($header && ord($font{$info['length1']})==128) {//Strip second binary header$font=substr($font,0,$info['length1']).substr($font,$info['length1']+6);}}$this->_out('<</Length '.strlen($font));if ($compressed) {$this->_out('/Filter /FlateDecode');};$this->_out('/Length1 '.$info['length1']);if(isset($info['length2'])) {$this->_out('/Length2 '.$info['length2'].' /Length3 0');};$this->_out('>>');$this->_putstream($font);$this->_out('endobj');}set_magic_quotes_runtime($mqr);foreach ($this->fonts as $k=>$font) {//Font objects$this->fonts[$k]['n'] = $this->n+1;$type=$font['type'];$name=$font['name'];if ($type=='Type1' || $type=='TrueType') {//Additional Type1 or TrueType font$this->_newobj();$this->_out('<</Type /Font');$this->_out('/BaseFont /'.$name);$this->_out('/Subtype /'.$type);$this->_out('/FirstChar 32 /LastChar 255');$this->_out('/Widths '.($this->n+1).' 0 R');$this->_out('/FontDescriptor '.($this->n+2).' 0 R');if ($font['enc']) {if(isset($font['diff'])) {$this->_out('/Encoding '.($nf+$font['diff']).' 0 R');} else {$this->_out('/Encoding /WinAnsiEncoding');};}$this->_out('>>');$this->_out('endobj');//Widths$this->_newobj();$cw=&$font['cw'];$s='[';for ($i=32;$i<=255;$i++) {$s.=$cw[chr($i)].' ';};$this->_out($s.']');$this->_out('endobj');//Descriptor$this->_newobj();$s='<</Type /FontDescriptor /FontName /'.$name;foreach($font['desc'] as $k=>$v) {$s.=' /'.$k.' '.$v;};$file=$font['file'];if($file) {$s.=' /FontFile'.($type=='Type1' ? '' : '2').' '.$this->FontFiles[$file]['n'].' 0 R';};$this->_out($s.'>>');$this->_out('endobj');} else {//Allow for additional types$mtd='_put'.strtolower($type);if(!method_exists($this,$mtd))$this->Error('Unsupported font type: '.$type);$this->$mtd($font);}}}function _putimages() {$filter=($this->compress) ? '/Filter /FlateDecode ' : '';reset($this->images);while (list($file,$info) = each($this->images)) {$this->_newobj();$this->images[$file]['n']=$this->n;$this->_out('<</Type /XObject');$this->_out('/Subtype /Image');$this->_out('/Width '.$info['w']);$this->_out('/Height '.$info['h']);if ($info['cs']=='Indexed') {$this->_out('/ColorSpace [/Indexed /DeviceRGB '.(strlen($info['pal'])/3-1).' '.($this->n+1).' 0 R]');} else {$this->_out('/ColorSpace /'.$info['cs']);if($info['cs']=='DeviceCMYK') {$this->_out('/Decode [1 0 1 0 1 0 1 0]');};}$this->_out('/BitsPerComponent '.$info['bpc']);if (isset($info['f'])) {$this->_out('/Filter /'.$info['f']);};if(isset($info['parms'])) {$this->_out($info['parms']);};if(isset($info['trns']) && is_array($info['trns'])) {$trns='';for ($i=0;$i<count($info['trns']);$i++) {$trns.=$info['trns'][$i].' '.$info['trns'][$i].' ';};$this->_out('/Mask ['.$trns.']');};$this->_out('/Length '.strlen($info['data']).'>>');$this->_putstream($info['data']);unset($this->images[$file]['data']);$this->_out('endobj');// Paletteif ($info['cs']=='Indexed') {$this->_newobj();$pal=($this->compress) ? gzcompress($info['pal']) : $info['pal'];$this->_out('<<'.$filter.'/Length '.strlen($pal).'>>');$this->_putstream($pal);$this->_out('endobj');};}}function _putxobjectdict() {foreach($this->images as $image)$this->_out('/I'.$image['i'].' '.$image['n'].' 0 R');}function _putresourcedict(){$this->_out('/ProcSet [/PDF /Text /ImageB /ImageC /ImageI]');$this->_out('/Font <<');foreach($this->fonts as $font)$this->_out('/F'.$font['i'].' '.$font['n'].' 0 R');$this->_out('>>');$this->_out('/XObject <<');$this->_putxobjectdict();$this->_out('>>');}function _putresources(){$this->_putfonts();$this->_putimages();//Resource dictionary$this->offsets[2]=strlen($this->buffer);$this->_out('2 0 obj');$this->_out('<<');$this->_putresourcedict();$this->_out('>>');$this->_out('endobj');}function _putinfo(){$this->_out('/Producer '.$this->_textstring('FPDF '.FPDF_VERSION));if(!empty($this->title))$this->_out('/Title '.$this->_textstring($this->title));if(!empty($this->subject))$this->_out('/Subject '.$this->_textstring($this->subject));if(!empty($this->author))$this->_out('/Author '.$this->_textstring($this->author));if(!empty($this->keywords))$this->_out('/Keywords '.$this->_textstring($this->keywords));if(!empty($this->creator))$this->_out('/Creator '.$this->_textstring($this->creator));$this->_out('/CreationDate '.$this->_textstring('D:'.date('YmdHis')));}// Generate the document catalog entry of PDF filefunction _putcatalog($pages_start_obj_number) {$this->_out('/Type /Catalog');$this->_out('/Pages 1 0 R');if ($this->ZoomMode=='fullpage') {$this->_out("/OpenAction [$pages_start_obj_number 0 R /Fit]");} elseif ($this->ZoomMode=='fullwidth') {$this->_out("/OpenAction [$pages_start_obj_number 0 R /FitH null]");} elseif ($this->ZoomMode=='real') {$this->_out("/OpenAction [$pages_start_obj_number 0 R /XYZ null null 1]");} elseif (!is_string($this->ZoomMode)) {$this->_out("/OpenAction [$pages_start_obj_number 0 R /XYZ null null ".($this->ZoomMode/100).']');};if ($this->LayoutMode=='single') {$this->_out('/PageLayout /SinglePage');} elseif ($this->LayoutMode=='continuous') {$this->_out('/PageLayout /OneColumn');} elseif ($this->LayoutMode=='two') {$this->_out('/PageLayout /TwoColumnLeft');};if (count($this->_forms) > 0) {$this->_out('/AcroForm <<');$this->_out('/Fields '.$this->_reference_array($this->_forms));$this->_out('/DR 2 0 R');$this->_out('/NeedAppearances true');$this->_out('>>');};}function _putheader() {$this->_out('%PDF-'.$this->PDFVersion);}function _puttrailer(){$this->_out('/Size '.($this->n+1));$this->_out('/Root '.$this->n.' 0 R');$this->_out('/Info '.($this->n-1).' 0 R');}function _enddoc() {$this->_putheader();$pages_start_obj_number = $this->_putpages();$this->_putresources();//Info$this->_newobj();$this->_out('<<');$this->_putinfo();$this->_out('>>');$this->_out('endobj');// Form fieldsfor ($i=0; $i<count($this->_forms); $i++) {$form =& $this->_forms[$i];$form->out($this);// // @todo: remove this dirty hack// if (isset($form->appearance)) {// $this->offsets[$form->appearance->get_object_id()] = strlen($this->buffer);// $this->_out($this->_indirect_object($form->appearance));// };// if (isset($form->_radios)) {// for ($i=0; $i<count($form->_radios); $i++) {// // $radio = $form->_radios[$i];// // $this->offsets[$radio->get_object_id()] = strlen($this->buffer);// // $this->_out($this->_indirect_object($radio));// };// }// Not required, as forms fields are annotations which are output at the end of the page// $this->offsets[$form->get_object_id()] = strlen($this->buffer);// $this->_out($this->_indirect_object($form));};//Catalog$this->_newobj();$this->_out('<<');$this->_putcatalog($pages_start_obj_number);$this->_out('>>');$this->_out('endobj');//Cross-ref$o=strlen($this->buffer);$this->_out('xref');$this->_out('0 '.($this->n+1));$this->_out('0000000000 65535 f ');for ($i=1; $i<=$this->n; $i++) {$this->_out(sprintf('%010d 00000 n ',$this->offsets[$i]));};//Trailer$this->_out('trailer');$this->_out('<<');$this->_puttrailer();$this->_out('>>');$this->_out('startxref');$this->_out($o);$this->_out('%%EOF');$this->state=3;}function _beginpage($orientation) {$this->page++;$this->pages[$this->page]='';$this->state=2;$this->x=$this->lMargin;$this->y=$this->tMargin;$this->FontFamily='';//Page orientationif(!$orientation) {$orientation=$this->DefOrientation;} else {$orientation=strtoupper($orientation{0});if($orientation!=$this->DefOrientation) {$this->OrientationChanges[$this->page]=true;};}if($orientation!=$this->CurOrientation) {//Change orientationif($orientation=='P') {$this->wPt=$this->fwPt;$this->hPt=$this->fhPt;$this->w=$this->fw;$this->h=$this->fh;}else{$this->wPt=$this->fhPt;$this->hPt=$this->fwPt;$this->w=$this->fh;$this->h=$this->fw;}$this->PageBreakTrigger=$this->h-$this->bMargin;$this->CurOrientation=$orientation;}}function _endpage() {//End of page contents$this->state=1;}// Start a new indirect objectfunction _newobj() {$num = $this->_generate_new_object_number();$this->offsets[$num]=strlen($this->buffer);$this->_out($num.' 0 obj');}function _parsejpg($file){//Extract info from a JPEG file$a=GetImageSize($file);if (!$a) {$this->Error('Missing or incorrect image file: '.$file);};if ($a[2]!=2) {$this->Error('Not a JPEG file: '.$file);};if (!isset($a['channels']) || $a['channels']==3) {$colspace='DeviceRGB';} elseif ($a['channels']==4) {$colspace='DeviceCMYK';} else {$colspace='DeviceGray';};$bpc=isset($a['bits']) ? $a['bits'] : 8;//Read whole file$f = fopen($file,'rb');$data = '';while (!feof($f)) {$data .= fread($f,4096);};fclose($f);return array('w'=>$a[0],'h'=>$a[1],'cs'=>$colspace,'bpc'=>$bpc,'f'=>'DCTDecode','data'=>$data);}function _parsepng($file) {//Extract info from a PNG file$f=fopen($file,'rb');if (!$f) {$this->Error('Can\'t open image file: '.$file);};//Check signatureif (fread($f,8)!=chr(137).'PNG'.chr(13).chr(10).chr(26).chr(10)) {$this->Error('Not a PNG file: '.$file);};//Read header chunkfread($f,4);if (fread($f,4)!='IHDR') {$this->Error('Incorrect PNG file: '.$file);};$w=$this->_freadint($f);$h=$this->_freadint($f);$bpc=ord(fread($f,1));if ($bpc>8) {$this->Error('16-bit depth not supported: '.$file);};$ct=ord(fread($f,1));if ($ct==0) {$colspace='DeviceGray';} elseif($ct==2) {$colspace='DeviceRGB';} elseif($ct==3) {$colspace='Indexed';} else {$this->Error('Alpha channel not supported: '.$file);};if (ord(fread($f,1))!=0) {$this->Error('Unknown compression method: '.$file);};if (ord(fread($f,1))!=0) {$this->Error('Unknown filter method: '.$file);};if (ord(fread($f,1))!=0) {$this->Error('Interlacing not supported: '.$file);};fread($f,4);$parms='/DecodeParms <</Predictor 15 /Colors '.($ct==2 ? 3 : 1).' /BitsPerComponent '.$bpc.' /Columns '.$w.'>>';//Scan chunks looking for palette, transparency and image data$pal='';$trns='';$data='';do{$n=$this->_freadint($f);$type=fread($f,4);if($type=='PLTE'){//Read palette$pal=fread($f,$n);fread($f,4);}elseif($type=='tRNS'){//Read transparency info$t=fread($f,$n);if($ct==0)$trns=array(ord(substr($t,1,1)));elseif($ct==2)$trns=array(ord(substr($t,1,1)),ord(substr($t,3,1)),ord(substr($t,5,1)));else{$pos=strpos($t,chr(0));if($pos!==false)$trns=array($pos);}fread($f,4);}elseif($type=='IDAT'){//Read image data block$data.=fread($f,$n);fread($f,4);}elseif($type=='IEND')break;elsefread($f,$n+4);}while($n);if($colspace=='Indexed' && empty($pal))$this->Error('Missing palette in '.$file);fclose($f);return array('w'=>$w,'h'=>$h,'cs'=>$colspace,'bpc'=>$bpc,'f'=>'FlateDecode','parms'=>$parms,'pal'=>$pal,'trns'=>$trns,'data'=>$data);}function _freadint($f){//Read a 4-byte integer from file$a=unpack('Ni',fread($f,4));return $a['i'];}function _textstring($s){//Format a text stringreturn '('.$this->_escape($s).')';}function _escape($s) {//Add \ before \, ( and )return str_replace(')','\\)',str_replace('(','\\(',str_replace('\\','\\\\',$s)));}function _putstream($s) {$this->_out('stream');$this->_out($s);$this->_out('endstream');}function _out($s) {//Add a line to the documentif($this->state==2)$this->pages[$this->page].=$s."\n";else$this->buffer.=$s."\n";}//End of class}//Handle special IE contype requestif(isset($_SERVER['HTTP_USER_AGENT']) && $_SERVER['HTTP_USER_AGENT']=='contype'){header('Content-Type: application/pdf');exit;}}?>