经过一路的测试和刷选,后来选择mpdf,支持中文字体和自定义字体,但这东西不支持tfoot,虽然也是有点痛苦,总算了解了他的使用方法,算是皮毛吧,也够用了就是。
tcpdf 支持中文字体
dompdf 支持css和样式,H5
anam-hossain/phantommagick 好用,HTML转PDF,但是需要安装phantomjs
https://github.com/anam-hossain/phantommagick
spatie/browsershot 依赖Puppeteer 好用,HTML转PDF
html2pdf 这个不会自动换行,支持中文,支持tfoot,少部分css样式
https://github.com/spipu/html2pdf
着重讲mpdf,下面是开源地址
使用文档
安装简单
composer require mpdf/mpdf
接着引入,一个简单的示例
<?php
require_once __DIR__ . '/vendor/autoload.php';
$mpdf = new \Mpdf\Mpdf();
$mpdf->WriteHTML('<h1>Hello world!</h1>');
$mpdf->Output();
复杂点的选择
require ROOT_PATH.'/vendor/autoload.php';
$tempDir = __DIR__.'/Cache/tmp';
if(!is_dir($tempDir)){
mkdir($tempDir,0777,true);
};
$mpdf = new \Mpdf\Mpdf([
'mode' => 'utf-8',
//'format' => 'A4-L', //横向A4
'debug' => true,
//'tabSpaces' => 4,
//'ignore_invalid_utf8' => true,
'orientation' => 'L', //横向
"autoScriptToLang"=>true, //自动适配语言(支持中文)
"autoLangToFont"=>true, //自动选字体
"default_font_size"=>10, //默认字号px
"default_font"=>'simsun', //自定义字体,这个后面讲解
//"tempDir"=>$tempDir, //缓存目录
'margin_top' => 0, //上边距
'margin_left' => 7, //左边距
'margin_right' => 7, //右边距
//'mirrorMargins' => true,
"setAutoTopMargin"=>"stretch", //自动适应顶边距
//"setAutoBottomMargin"=>"stretch",
"autoMarginPadding"=>0 //边距和pad
]);
//$mpdf->default_font='STFangsong'; //courier SimHei
$mpdf->defaultheaderline = 0; //删除header底线
$mpdf->defaultfooterline = 0; //删除footer顶线
上面提到的字体,首先 把ttf字体放在
/vendor/mpdf/mpdf/ttfonts
目录里面,然后编辑文件 /vendor/mpdf/mpdf/src/Config/FontVariables.php
找到 'fontdata' => [] 区域,把自己的字体放在里面,以宋体等几个字体为例,添加配置如下:
"simsun" => [
'R' => "simsun.ttf", //宋体
],
"simhei" => [
'R' => "simhei.ttf", //黑体
],
"stsongstdlight" => [
'R' => "STSongStdLight.ttf", //据说中文
],
"droidsansfallback" => [
'R' => "DroidSansFallback.ttf", //安卓专用中文字体
],
"华文黑体" => [
'R' => "华文黑体.ttf",
],
"华文宋体" => [
'R' => "华文宋体.ttf",
],
你看见里面有一个sun-exta字体配置吧,那个是mpdf默认的中文字体。
这样你在pdf文档的html代码里面就可以css定义font-family:simsun即可
或者像上面那样"default_font"=>'simsun'指定自定义的字体,或者mpdf自带字体,比如sun-exta
接着说下内容组织方面,这功能太多了,不好全面描述。
样式表css代码
$csscode=<<<EOD
<style type="text/css">
*{
}
.pdftable table{
display:table;
table-layout: fixed;
border:0px;
margin:0px;
border-collapse:collapse;
border-spacing:0;
width: 100%;
}
.pdftable table, td, th
{
border:1px solid black;
}
.pdftable tr{
width: 100%;
}
</style>
EOD;
$mpdf->WriteHTML($csscode,\Mpdf\HTMLParserMode::HEADER_CSS); //写样式
每页重复出现的头部
$headhtml=<<<EOD
<div style="width:100%;" class="pdfhead">
<table style="width: 100%;">
<tr>
<td style="border:1px; text-align: center;width:100%;font-size: 23px;font-family:simhei">
我是一个大标题
</td>
</tr>
</table>
<br /><br /><br />
<table style="width: 100%; border:0;border-spacing:0;border-collapse:collapse;">
<tr>
<td style="border:0px; text-align: right; width: 10%">我是文档:</td>
<td style="border:0px; text-align: left; width: 70.5%"> 001</td>
<td style="border:0px; text-align: left; width: 19.5%">第 {PAGENO} 页,共 {nbpg} 页</td>
</tr>
</table>
</div>
EOD;
$mpdf->SetHTMLHeader($headhtml); //写入头
接着内容不用我多说了吧,爱怎么组织都行,这里看个表格吧。
其中thead,每个分页,表格头都会重复出现的
$htmlcode=<<<EOD
<div style="width:100%;" class="pdftable">
<table style="width:100%;">
<thead>
<tr style="width:100%;">
<th rowspan="2" style="width: 16mm">序号</th>
<th rowspan="2" style="width: 48.3mm">工号</th>
<th rowspan="2" style="width: 22.1mm">姓名</th>
<th rowspan="2" style="width: 20.4mm">绩效</th>
<th rowspan="2" style="width: 21.1mm">底薪</th>
<th colspan="2" style="width: 43.1mm">分类</th>
<th rowspan="2" style="width: 17.7mm">总计</th>
</tr>
<tr>
<th style="border-left:0;width: 21.5mm">夜班</th>
<th style="border-left:0;width: 21.5mm">双休</th>
</tr>
</thead>
<tbody>
<tr>
<td>1</td>
<td>007</td>
<td>张同学</td>
<td>5000</td>
<td>5000</td>
<td>2000</td>
<td>1500</td>
<td>13500</td>
</tr>
<tr><td colspan="8" style="text-align:left;border:0;width:100%;">我是底座</td></tr>
</tbody>
</table>
</div>
EOD;
$mpdf->WriteHTML($htmlcode,\Mpdf\HTMLParserMode::HTML_BODY); //写内容
最后应该就是尾巴,说累了,就简单点吧。
$mpdf->SetHTMLFooter('<div>我是小尾巴</div>');
其它一些特异功能也是有的。
文字水印
$mpdf->watermark_font='simsun';
$mpdf->SetWatermarkText('每页水印',0.1);
$mpdf->showWatermarkText = true;
图片水印(用于盖章或者你公司的LOGO之类,总之酷毕了)
$mpdf->SetWatermarkImage('/test.png', 1, array(60,60), array(75,3));
//分别为图片路径、未知、宽高、坐标XY
$mpdf->showWatermarkImage = true;
其它特异功能不一一介绍,用到再描述
最后,输出到浏览器或者生成下载。
$mpdf->output(); //只输出到浏览器
$mpdf->output('document.pdf','D'); //下载
简单吧
附自定义字体方法二
//自定义字体目录和字体定义
$defaultConfig = (new Mpdf\Config\ConfigVariables())->getDefaults();
$fontDirs = $defaultConfig['fontDir'];
$defaultFontConfig = (new Mpdf\Config\FontVariables())->getDefaults();
$fontData = $defaultFontConfig['fontdata'];
$mpdf = new \Mpdf\Mpdf([
'fontDir' => array_merge($fontDirs, [
__DIR__ . '/custom/font/directory',
]),
'fontdata' => $fontData + [
'frutiger' => [
'R' => 'Frutiger-Normal.ttf',
'I' => 'FrutigerObl-Normal.ttf',
]
],
'default_font' => 'frutiger'
]);
附二,自定义输出
function myMpdfOutput($mpdf, $name)
{
if ($mpdf->state < 3)
$mpdf->Close();
$numpages = $mpdf->docPageNumTotal();
//We send to a browser
header('Content-Type: application/pdf');
if (!isset($_SERVER['HTTP_ACCEPT_ENCODING']) OR empty($_SERVER['HTTP_ACCEPT_ENCODING'])) {
// don't use length if server using compression
header('Content-Length: ' . strlen($this->buffer));
}
header('Content-disposition: inline; filename="' . $name . '"');
header('Cache-Control: public, must-revalidate, max-age=0');
header('Pragma: public');
header('Expires: Sat, 26 Jul 1997 05:00:00 GMT');
header('Last-Modified: ' . gmdate('D, d M Y H:i:s') . ' GMT');
echo str_replace('{nbpg}', $numpages, $mpdf->buffer);
}