PDF生成插件--TcPDF

前言

上星期給畢設(shè)網(wǎng)站添加了markdown編輯器,然后周末突然想到如果給編輯器添加一個導出pdf的功能應該挺不錯的(話說簡書為啥不能導出pdf呢),所以就從網(wǎng)上找了一個生成pdf的PHP插件,叫做 tcpdf,東西很大,連帶著實例文件接近16m,花了一天時間去弄這個。

其實這個根據(jù)這個插件的實例很快就能弄出pdf來,不過剩下的時間我都在研究怎么能讓生成的pdf更好看,很明顯我失敗了。普通文本還好,如果有這樣的代碼,要么是顯示不出來了,而顯示出來的部分也是亂七八糟的。如下:

code顯示不正確

code無法顯示

雖然對我來說沒什么價值,但畢竟研究了一番,寫個小日志記錄一下吧。

文件引入

TCPDF下載最新的版本,雖然下載包中附帶了65個demo,但它沒告訴我哪些文檔是必須引入的。那我們直接來看程序文件。打開主程序文件tcpdf.php,從開始的代碼可以看出,以下文件必須被包含:

tcpdf_autoconfig.php
include文件夾

在搜索所有文件中的require_once,有如下文件:

tcpdf_barcodes_1d.php
tcpdf_barcodes_2d.php

ok,將tcpdf.php和上述文件復制到項目文件夾,

require_once('./tcpdf.php');
$pdf = new TCPDF();

執(zhí)行,然后就出錯了:

Warning: opendir(C:\Practice\Apache24\htdocs\demo\PDF/fonts/,C:\Practice\Apache24\htdocs\demo\PDF/fonts/): in C:\Practice\Apache24\htdocs\demo\PDF\tcpdf.php on line 4148
Warning: opendir(C:\Practice\Apache24\htdocs\demo\PDF/fonts/): failed to open dir: No such file or directory in C:\Practice\Apache24\htdocs\demo\PDF\tcpdf.php on line 4148
TCPDF ERROR: Could not include font definition file: helvetica

顯然還要將下載包中的fonts文件夾復制到項目中。

執(zhí)行

經(jīng)過上面的引入和調(diào)試,現(xiàn)在能正常實例化了,在上面代碼中我實例化tcpdf方法未傳遞任何參數(shù),但實際上該方法有7個參數(shù)可傳遞,如下:

屬性 說明 默認值
$orientation 設(shè)置pdf頁面的方向 Portrait
$unit 設(shè)置pdf單元的測量單位 mm
$format 頁面的版式 A4
$unicode 是否使用unicode true
$encoding 字符編碼 utf-8
$diskcache 該功能被廢棄 false
$pdfa 啟用/關(guān)閉pdf/a true

具體說明如下:

$orientation

用來設(shè)置pdf頁面的方向,有兩個參數(shù):

參數(shù)名 含義 默認
P/Portrait 縱向 true
L/Landscape 橫向 false

$unit

用來設(shè)置pdf單元的測量單位,有四個參數(shù)

參數(shù)名 含義 默認
pt: point 點數(shù) false
mm: millimeter 毫米 true
cm: centimeter 厘米 false
in: inch 英寸 false

$format

表示頁面的版式,如 A4等。而他默認的也是 A4。 tcpdf支持很多版式,可以到tcpdf_static.php中的$page_formats屬性中查看。

$unicode

布爾類型,true代表是輸入文本是$unicode。這個沒什么說的,一般都是unicode,默認為true就行。

$encoding

字符編碼,默認是utf-8。

$diskcache

這個參數(shù)官網(wǎng)沒多做解釋,程序文件也是,不過在其中寫了DEPRECATED FEATURE,顯然該功能被廢棄了,不建議使用,直接設(shè)置為false即可。

$pdfa

PDF/A是PDF 的 ISO 標準,它是為長期保存文件而設(shè)計的,屏蔽了一些編輯功能。即設(shè)置`$pdfa = true**的話,生成的pdf是不能夠編輯的。

好了,弄清楚了這7個參數(shù),可以實例化了,當然如果你只是簡單的使用一下可以直接進行實例化,因為這7個參數(shù)都有默認值,而一般這些默認值不用修改。

配置

tcpdf的配置選項很多,大致分成4個部分,包括文檔的信息設(shè)置,頁眉頁腳設(shè)置文本間距設(shè)置,正文設(shè)置。其中分成若干小部分。在完成功能之前,簡單介紹一下,這幾部分必要的方法。

如下:

1 文檔的信息設(shè)置

包括 SetCreator(文檔創(chuàng)建者名稱)SetAuthor(設(shè)置作者),SetTitle(設(shè)置文檔標題),SetKeywords(文檔關(guān)鍵詞)。這幾個方法的參數(shù)沒什么可說的,string類型,主要就是用來設(shè)置文檔的屬性的,如下面的東西一樣:

文檔屬性

2 頁眉頁腳設(shè)置

包括SetHeaderData,setFooterData,setHeaderFont,setFooterFont

SetHeaderData方法有6個參數(shù),包括:

屬性 說明 默認值
$ln logo文件路徑 ''
$lw logo寬度 0
$ht 頁眉標題 ''
$hs 頁眉的說明文字 ''
$tc 文本的rgb顏色 array(0,0,0) (黑色)
$lc 頁眉下劃線的顏色 array(0,0,0) (黑色)

setFooterData只有兩個參數(shù),頁腳文本顏色和下劃線的顏色。

setHeaderFontsetFooterFont分別是設(shè)置頁眉和頁腳的字體,參數(shù)只有一個,且注意是數(shù)組類型,且傳遞的數(shù)組格式如下:

array(family, style, size)

對應的是font-family,font-stylefont-size。

另外,如果不希望使用頁眉頁腳,可以使用setPrintHeadersetPrintFooter方法關(guān)閉頁眉頁腳,只要傳遞參數(shù)false即可。

3 文本間距設(shè)置

間距包含正文間距和頁眉頁腳的間距,有三個方法SetMargins,SetHeaderMarginSetFooterMargin。

SetMargins是用于正文的,有三個參數(shù),分別表示左側(cè)、上側(cè)、右側(cè)的間距。SetHeaderMarginSetFooterMargin分別是頁眉與頁腳的間距。

4.設(shè)置正文

正文設(shè)置包括 分頁,圖片比例正文字體等。

首先利用 SetAutoPageBreak開啟分頁。該方法傳遞兩個參數(shù),參數(shù)1用戶啟動或禁用自動分頁,而參數(shù)2只有參數(shù)1等于true時才起作用,它定義了頁面距底部的距離。

再利用AddPage方法新添分頁。同時,該方法如果前面已有頁面,該方法會在將頁腳添加到頁面中 并自動添加下一頁,否則直接添加新一頁。

字體的設(shè)置包括,setFontSubsettingSetFont、SetDefaultMonospacedFont。

setFontSubsetting這個方法我沒弄懂,因為不了解什么叫字體構(gòu)造子集,跳過。SetFont就是用來設(shè)置正文字體,參數(shù)傳遞和setHeaderFont類似,但該方法將三個選項分成了三個參數(shù)傳遞,而不是傳遞數(shù)組。另外,如果是生成中文pdf需要尤其注意,必須設(shè)置字體為stsongstdlight,否則會出現(xiàn)中文亂碼。

當然還有正文寫入了,如果只是普通文檔,一般使用Write方法,共有12個參數(shù),所以我就不一一介紹了,說一下必填的兩個參數(shù),也就是前兩個參數(shù),$h表示行高,$txt表示要打印的內(nèi)容。其他可以默認。

如果打印html文檔且包含了css文件,就需要使用writeHTML方法,該方法有6個參數(shù),但必填的只有一個就是需要打印的內(nèi)容,其他的參數(shù)可以是默認值。

好了,配置、參數(shù)介紹完畢,按照我介紹的步驟一步步的來,就能生成pdf了,下面是我自己寫的生成代碼:

class pdf {

    # 常量設(shè)置
    const PDF_LOGO       = '\Logo\logo_big.png';                    // LOGO路徑 該路徑是tcpdf下
    const PDF_LOGO_WIDTH = '20';                                    // LOGO寬度
    const PDF_TITLE      = 'www.liuweime.me';                       // 
    const PDF_HEAD       = '上電腦課';
    const PDF_FONT       = 'stsongstdlight';
    const PDF_FONT_STYLE = '';
    const PDF_FONT_SIZE  = 10;
    const PDF_FONT_MONOSPACED = 'courier';
    const PDF_IMAGE_SCALE='1.25';


    # tcpdf對象存儲
    protected $pdf = null;
    
    /**
     * 構(gòu)造函數(shù) 引入插件并實例化
     */
    public function __construct() {     
        # 實例化該插件
        $this->pdf = new TCPDF(); 
    }

    /**
     * 設(shè)置文檔信息    
     * @param  $user        string  文檔作者
     * @param  $title       string  文檔標題
     * @param  $subject     string  文檔主題
     * @param  $keywords    string  文檔關(guān)鍵字
     * @return null
     */
    protected function setDocumentInfo($user = '', $title = '', $subject ='', $keywords = '') {
        if(empty($user) || empty($title)) return false;
        # 文檔創(chuàng)建者名稱
        $this->pdf->SetCreator(APP_NAME);
        # 作者
        $this->pdf->SetAuthor($user);
        # 文檔標題
        $this->pdf->SetTitle($title);
        # 文檔主題
        if(!empty($subject)) $this->pdf->SetSubject($subject);
        # 文檔關(guān)鍵字
        if(!empty($keywords)) $this->pdf->SetKeywords($keywords);       

    }

    /**
     * 設(shè)置文檔的頁眉頁腳信息
     * @param  null
     * @return null
     */
    protected function setHeaderFooter() {
        # 設(shè)置頁眉信息 
        # 格式 logo地址 logo寬度 頁眉標題 頁眉說明文字 頁眉字體顏色 頁眉下劃線顏色
        $this->pdf->SetHeaderData(self::PDF_LOGO , self::PDF_LOGO_WIDTH , self::PDF_TITLE , self::PDF_HEAD , array(35 , 35 , 35) , array(221,221,221));
        # 設(shè)置頁腳信息
        # 格式 頁腳字體顏色 頁腳下劃線顏色
        $this->pdf->setFooterData(array(35 , 35 , 35) , array(221,221,221));
        
        # 設(shè)置頁眉頁腳字體
        $this->pdf->setHeaderFont(array('stsongstdlight' , self::PDF_FONT_STYLE , self::PDF_FONT_SIZE));
        $this->pdf->setFooterFont(array('helvetica' , self::PDF_FONT_STYLE , self::PDF_FONT_SIZE));
    }

    /**
     * 關(guān)閉頁眉頁腳
     * @param  null
     * @return null
     */
    protected function closeHeaderFooter() {
        # 關(guān)閉頁頭
        $this->pdf->setPrintHeader(false);
        # 關(guān)閉頁腳
        $this->pdf->setPrintFooter(false);
    }

    /**
     * 設(shè)置間距 包括正文間距 頁眉頁腳間距
     * @param  null
     * @return null
     */
    protected function setMargin() {
        # 設(shè)置默認的等寬字體
        $this->pdf->SetDefaultMonospacedFont('courier');
        # 正文左側(cè) 上側(cè) 右側(cè)間距
        $this->pdf->SetMargins(15, 7, 15);
        # 頁眉間距
        $this->pdf->SetHeaderMargin(5);
        # 頁腳間距
        $this->pdf->SetFooterMargin(10);
    }

    /**
     * 正文設(shè)置 包括 分頁 圖片比例 正文字體
     * @param  null
     * @return null  
     */
    protected function setMainBody() {
        
        # 開啟分頁 true開啟 false關(guān)閉 開啟分頁時參數(shù)2起作用 表示正文距底部的間距
        $this->pdf->SetAutoPageBreak(true , 25);
        # 設(shè)置圖片比例
        $this->pdf->setImageScale(self::PDF_IMAGE_SCALE);
        #
        $this->pdf->setFontSubsetting(true);
        # 設(shè)置正文字體 stsongstdlight是Adobe Reader默認字體
>       $this->pdf->SetFont('stsongstdlight', '', 14); 
        # 添加頁面 該方法如果前面已有頁面 會在將頁腳添加到頁面中 并自動添加下一頁 否則添加新一頁
        $this->pdf->AddPage();      
    }

    /**
     * 生成pdf
     * @param  $info    array   
     *   array(
     *          'user'=>'文檔作者' , 
     *          'title'=>'文檔標題' , 
     *          'subject'=>'文檔主題' , 
     *          'keywords'=>'文檔關(guān)鍵字' , 
     *          'content'=>'文檔正文內(nèi)容' , 
     *          'HT'=>'是否開啟頁眉頁腳' , 
     *          'path'=>'文檔保存路徑');
     * @return null  
     */
    public function createPDF($info = array()) {
        if(empty($info) || !is_array($info)) return false;

        $this->setDocumentInfo($info['user'] , $info['title'] , $info['subject'] , $info['keywords']);
        if(!$info['HT']) {

            $this->closeHeaderFooter();
        } else {
            $this->setHeaderFooter();
        }
        
        $this->setMargin();
        $this->setMainBody();

        # 寫入內(nèi)容
        $this->pdf->writeHTML($info['content'], true, false, true, false, '');

        # 輸出  I輸出到瀏覽器 F輸出到指定路徑
        $this->pdf->Output($info['path'] , 'F');
    }
}

結(jié)語

雖然,沒達到我預想的效果,但還是有收獲的,而且我是第一次看到兩萬多行代碼在一個文件中的PHP文件,有點66的,本來準備看看源碼,學習學習的,看到代碼后有點發(fā)虛,哈哈。

END

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關(guān)閱讀更多精彩內(nèi)容

  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,564評論 19 139
  • Word 2003長篇文檔排版技巧(一) 重點總結(jié)為兩點: 1. 制作長文檔前,先要規(guī)劃好各種設(shè)置,尤其是樣式設(shè)置...
    MrSunbeam閱讀 2,153評論 0 12
  • 1. 問:WORD 里邊怎樣設(shè)置每頁不同的頁眉?如何使不同的章節(jié)顯示的頁眉不同? 答:分節(jié),每節(jié)可以設(shè)置不同的頁眉...
    Jiang鋒時刻閱讀 5,364評論 4 110
  • 1. 問:WORD 里邊怎樣設(shè)置每頁不同的頁眉?如何使不同的章節(jié)顯示的頁眉不同? 答:分節(jié),每節(jié)可以設(shè)置不同的頁眉...
    Irinaa閱讀 2,944評論 0 43
  • 八月份的時候我和我的好朋友一起去了越南芽莊,是一個海島,我們在那里感受到了慢生活的節(jié)奏 越南人都有一個習慣,早晨四...
    小小小十七閱讀 428評論 0 1

友情鏈接更多精彩內(nèi)容