PDF生成插件--TcPDF

前言

上星期給畢設(shè)網(wǎng)站添加了markdown編輯器春缕,然后周末突然想到如果給編輯器添加一個(gè)導(dǎo)出pdf的功能應(yīng)該挺不錯(cuò)的(話說(shuō)簡(jiǎn)書為啥不能導(dǎo)出pdf呢),所以就從網(wǎng)上找了一個(gè)生成pdf的PHP插件艘蹋,叫做 tcpdf锄贼,東西很大,連帶著實(shí)例文件接近16m女阀,花了一天時(shí)間去弄這個(gè)宅荤。

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

code顯示不正確

code無(wú)法顯示

雖然對(duì)我來(lái)說(shuō)沒(méi)什么價(jià)值夫晌,但畢竟研究了一番雕薪,寫個(gè)小日志記錄一下吧。

文件引入

TCPDF下載最新的版本晓淀,雖然下載包中附帶了65個(gè)demo所袁,但它沒(méi)告訴我哪些文檔是必須引入的。那我們直接來(lái)看程序文件凶掰。打開主程序文件tcpdf.php燥爷,從開始的代碼可以看出,以下文件必須被包含:

tcpdf_autoconfig.php
include文件夾

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

tcpdf_barcodes_1d.php
tcpdf_barcodes_2d.php

ok前翎,將tcpdf.php和上述文件復(fù)制到項(xiàng)目文件夾,

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

執(zhí)行畅涂,然后就出錯(cuò)了:

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文件夾復(fù)制到項(xiàng)目中港华。

執(zhí)行

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

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

具體說(shuō)明如下:

$orientation

用來(lái)設(shè)置pdf頁(yè)面的方向臊岸,有兩個(gè)參數(shù):

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

$unit

用來(lái)設(shè)置pdf單元的測(cè)量單位橙数,有四個(gè)參數(shù)

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

$format

表示頁(yè)面的版式,如 A4等帅戒。而他默認(rèn)的也是 A4商模。 tcpdf支持很多版式,可以到tcpdf_static.php中的$page_formats屬性中查看。

$unicode

布爾類型施流,true代表是輸入文本是$unicode响疚。這個(gè)沒(méi)什么說(shuō)的,一般都是unicode瞪醋,默認(rèn)為true就行忿晕。

$encoding

字符編碼,默認(rèn)是utf-8银受。

$diskcache

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

$pdfa

PDF/A是PDF 的 ISO 標(biāo)準(zhǔn)肄程,它是為長(zhǎng)期保存文件而設(shè)計(jì)的,屏蔽了一些編輯功能选浑。即設(shè)置`$pdfa = true**的話蓝厌,生成的pdf是不能夠編輯的。

好了古徒,弄清楚了這7個(gè)參數(shù)拓提,可以實(shí)例化了,當(dāng)然如果你只是簡(jiǎn)單的使用一下可以直接進(jìn)行實(shí)例化隧膘,因?yàn)檫@7個(gè)參數(shù)都有默認(rèn)值代态,而一般這些默認(rèn)值不用修改。

配置

tcpdf的配置選項(xiàng)很多疹吃,大致分成4個(gè)部分膨处,包括文檔的信息設(shè)置王带,頁(yè)眉頁(yè)腳設(shè)置绊含,文本間距設(shè)置缤谎,正文設(shè)置蒋搜。其中分成若干小部分篡撵。在完成功能之前,簡(jiǎn)單介紹一下豆挽,這幾部分必要的方法育谬。

如下:

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

包括 SetCreator(文檔創(chuàng)建者名稱)SetAuthor(設(shè)置作者)帮哈,SetTitle(設(shè)置文檔標(biāo)題)膛檀,SetKeywords(文檔關(guān)鍵詞)。這幾個(gè)方法的參數(shù)沒(méi)什么可說(shuō)的,string類型咖刃,主要就是用來(lái)設(shè)置文檔的屬性的泳炉,如下面的東西一樣:

文檔屬性

2 頁(yè)眉頁(yè)腳設(shè)置

包括SetHeaderDatasetFooterData嚎杨,setHeaderFont花鹅,setFooterFont

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

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

setFooterData只有兩個(gè)參數(shù)枫浙,頁(yè)腳文本顏色和下劃線的顏色刨肃。

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

array(family, style, size)

對(duì)應(yīng)的是font-family紧帕,font-style盔然,font-size

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

3 文本間距設(shè)置

間距包含正文間距和頁(yè)眉頁(yè)腳的間距刻帚,有三個(gè)方法SetMarginsSetHeaderMargin涩嚣,SetFooterMargin崇众。

SetMargins是用于正文的,有三個(gè)參數(shù)航厚,分別表示左側(cè)顷歌、上側(cè)、右側(cè)的間距幔睬。SetHeaderMarginSetFooterMargin分別是頁(yè)眉與頁(yè)腳的間距眯漩。

4.設(shè)置正文

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

首先利用 SetAutoPageBreak開啟分頁(yè)。該方法傳遞兩個(gè)參數(shù)辅肾,參數(shù)1用戶啟動(dòng)或禁用自動(dòng)分頁(yè)队萤,而參數(shù)2只有參數(shù)1等于true時(shí)才起作用,它定義了頁(yè)面距底部的距離矫钓。

再利用AddPage方法新添分頁(yè)要尔。同時(shí)舍杜,該方法如果前面已有頁(yè)面,該方法會(huì)在將頁(yè)腳添加到頁(yè)面中 并自動(dòng)添加下一頁(yè)赵辕,否則直接添加新一頁(yè)既绩。

字體的設(shè)置包括,setFontSubsetting匆帚、SetFont熬词、SetDefaultMonospacedFont

setFontSubsetting這個(gè)方法我沒(méi)弄懂吸重,因?yàn)椴涣私馐裁唇凶煮w構(gòu)造子集互拾,跳過(guò)。SetFont就是用來(lái)設(shè)置正文字體嚎幸,參數(shù)傳遞和setHeaderFont類似颜矿,但該方法將三個(gè)選項(xiàng)分成了三個(gè)參數(shù)傳遞,而不是傳遞數(shù)組嫉晶。另外骑疆,如果是生成中文pdf需要尤其注意,必須設(shè)置字體為stsongstdlight替废,否則會(huì)出現(xiàn)中文亂碼箍铭。

當(dāng)然還有正文寫入了,如果只是普通文檔椎镣,一般使用Write方法诈火,共有12個(gè)參數(shù),所以我就不一一介紹了状答,說(shuō)一下必填的兩個(gè)參數(shù)冷守,也就是前兩個(gè)參數(shù),$h表示行高惊科,$txt表示要打印的內(nèi)容拍摇。其他可以默認(rèn)。

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

好了,配置翎蹈、參數(shù)介紹完畢,按照我介紹的步驟一步步的來(lái)男公,就能生成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對(duì)象存儲(chǔ)
    protected $pdf = null;
    
    /**
     * 構(gòu)造函數(shù) 引入插件并實(shí)例化
     */
    public function __construct() {     
        # 實(shí)例化該插件
        $this->pdf = new TCPDF(); 
    }

    /**
     * 設(shè)置文檔信息    
     * @param  $user        string  文檔作者
     * @param  $title       string  文檔標(biāo)題
     * @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);
        # 文檔標(biāo)題
        $this->pdf->SetTitle($title);
        # 文檔主題
        if(!empty($subject)) $this->pdf->SetSubject($subject);
        # 文檔關(guān)鍵字
        if(!empty($keywords)) $this->pdf->SetKeywords($keywords);       

    }

    /**
     * 設(shè)置文檔的頁(yè)眉頁(yè)腳信息
     * @param  null
     * @return null
     */
    protected function setHeaderFooter() {
        # 設(shè)置頁(yè)眉信息 
        # 格式 logo地址 logo寬度 頁(yè)眉標(biāo)題 頁(yè)眉說(shuō)明文字 頁(yè)眉字體顏色 頁(yè)眉下劃線顏色
        $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è)置頁(yè)腳信息
        # 格式 頁(yè)腳字體顏色 頁(yè)腳下劃線顏色
        $this->pdf->setFooterData(array(35 , 35 , 35) , array(221,221,221));
        
        # 設(shè)置頁(yè)眉頁(yè)腳字體
        $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)閉頁(yè)眉頁(yè)腳
     * @param  null
     * @return null
     */
    protected function closeHeaderFooter() {
        # 關(guān)閉頁(yè)頭
        $this->pdf->setPrintHeader(false);
        # 關(guān)閉頁(yè)腳
        $this->pdf->setPrintFooter(false);
    }

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

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

    /**
     * 生成pdf
     * @param  $info    array   
     *   array(
     *          'user'=>'文檔作者' , 
     *          'title'=>'文檔標(biāo)題' , 
     *          'subject'=>'文檔主題' , 
     *          'keywords'=>'文檔關(guān)鍵字' , 
     *          'content'=>'文檔正文內(nèi)容' , 
     *          'HT'=>'是否開啟頁(yè)眉頁(yè)腳' , 
     *          '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é)語(yǔ)

雖然合陵,沒(méi)達(dá)到我預(yù)想的效果,但還是有收獲的澄阳,而且我是第一次看到兩萬(wàn)多行代碼在一個(gè)文件中的PHP文件拥知,有點(diǎn)66的,本來(lái)準(zhǔn)備看看源碼碎赢,學(xué)習(xí)學(xué)習(xí)的低剔,看到代碼后有點(diǎn)發(fā)虛,哈哈肮塞。

END

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末襟齿,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子枕赵,更是在濱河造成了極大的恐慌猜欺,老刑警劉巖,帶你破解...
    沈念sama閱讀 210,978評(píng)論 6 490
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件拷窜,死亡現(xiàn)場(chǎng)離奇詭異开皿,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)篮昧,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 89,954評(píng)論 2 384
  • 文/潘曉璐 我一進(jìn)店門赋荆,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人懊昨,你說(shuō)我怎么就攤上這事窄潭。” “怎么了疚颊?”我有些...
    開封第一講書人閱讀 156,623評(píng)論 0 345
  • 文/不壞的土叔 我叫張陵狈孔,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我材义,道長(zhǎng)均抽,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 56,324評(píng)論 1 282
  • 正文 為了忘掉前任其掂,我火速辦了婚禮油挥,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘款熬。我一直安慰自己深寥,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,390評(píng)論 5 384
  • 文/花漫 我一把揭開白布贤牛。 她就那樣靜靜地躺著惋鹅,像睡著了一般。 火紅的嫁衣襯著肌膚如雪殉簸。 梳的紋絲不亂的頭發(fā)上闰集,一...
    開封第一講書人閱讀 49,741評(píng)論 1 289
  • 那天沽讹,我揣著相機(jī)與錄音,去河邊找鬼武鲁。 笑死爽雄,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的沐鼠。 我是一名探鬼主播挚瘟,決...
    沈念sama閱讀 38,892評(píng)論 3 405
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼饲梭!你這毒婦竟也來(lái)了乘盖?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,655評(píng)論 0 266
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤排拷,失蹤者是張志新(化名)和其女友劉穎侧漓,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體监氢,經(jīng)...
    沈念sama閱讀 44,104評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡布蔗,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,451評(píng)論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了浪腐。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片纵揍。...
    茶點(diǎn)故事閱讀 38,569評(píng)論 1 340
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖议街,靈堂內(nèi)的尸體忽然破棺而出泽谨,到底是詐尸還是另有隱情,我是刑警寧澤特漩,帶...
    沈念sama閱讀 34,254評(píng)論 4 328
  • 正文 年R本政府宣布吧雹,位于F島的核電站,受9級(jí)特大地震影響涂身,放射性物質(zhì)發(fā)生泄漏雄卷。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,834評(píng)論 3 312
  • 文/蒙蒙 一蛤售、第九天 我趴在偏房一處隱蔽的房頂上張望丁鹉。 院中可真熱鬧,春花似錦悴能、人聲如沸揣钦。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,725評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)冯凹。三九已至,卻和暖如春炒嘲,著一層夾襖步出監(jiān)牢的瞬間宇姚,已是汗流浹背团驱。 一陣腳步聲響...
    開封第一講書人閱讀 31,950評(píng)論 1 264
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留空凸,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 46,260評(píng)論 2 360
  • 正文 我出身青樓寸痢,卻偏偏與公主長(zhǎng)得像呀洲,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子啼止,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,446評(píng)論 2 348

推薦閱讀更多精彩內(nèi)容

  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見(jiàn)模式的工具(例如配置管理道逗,服務(wù)發(fā)現(xiàn),斷路器献烦,智...
    卡卡羅2017閱讀 134,628評(píng)論 18 139
  • Word 2003長(zhǎng)篇文檔排版技巧(一) 重點(diǎn)總結(jié)為兩點(diǎn): 1. 制作長(zhǎng)文檔前滓窍,先要規(guī)劃好各種設(shè)置,尤其是樣式設(shè)置...
    MrSunbeam閱讀 1,980評(píng)論 0 12
  • 1. 問(wèn):WORD 里邊怎樣設(shè)置每頁(yè)不同的頁(yè)眉东囚?如何使不同的章節(jié)顯示的頁(yè)眉不同跺嗽? 答:分節(jié),每節(jié)可以設(shè)置不同的頁(yè)眉...
    Jiang鋒時(shí)刻閱讀 5,226評(píng)論 4 110
  • 1. 問(wèn):WORD 里邊怎樣設(shè)置每頁(yè)不同的頁(yè)眉?如何使不同的章節(jié)顯示的頁(yè)眉不同份帐? 答:分節(jié)璃吧,每節(jié)可以設(shè)置不同的頁(yè)眉...
    Irinaa閱讀 2,833評(píng)論 0 43
  • 八月份的時(shí)候我和我的好朋友一起去了越南芽莊,是一個(gè)海島弥鹦,我們?cè)谀抢锔惺艿搅寺畹墓?jié)奏 越南人都有一個(gè)習(xí)慣肚逸,早晨四...
    小小小十七閱讀 358評(píng)論 0 1