laravel-dompdf 中文乱码的处理
背景
最近在处理 pdf
需求时使用了 laravel-dompdf
扩展包, 但是此包在默认使用场景下是不支持中文的, 会出现乱码. 因此针对此包中文乱码的处理整理如下
参考
重点参考: dompdf 处理中文字体问题
步骤
字体处理
这一步是重点
- 首先我们要下载一个中文字体库 和
load_font.php
, 例如字体库simsun.ttf
,参考文档中有.load_font.php
的下载参考文档中也有. - 然后将
simsum.ttf
和load_font.php
这两个文件,拷贝到项目的根目录,为下一步的脚本执行做准备. - 运行脚本,这样脚本会把根目录
simsum.ttf
这个字体库,同步到vendor\dompdf\dompdf\lib\fonts
文件夹下php load_font.php simsun simsun.ttf
生成 PDF
字体处理完成之后, 已经是可以按照参考链接中的使用 Dompdf
示例来生产中文的 pdf 了. 我这里示例使用的是 blade 模板的形式,中间多一个 balde 转 html 过程,但是这样更利于工程.
模板如下:
<html>
<head>
<meta charset="UTF-8">
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<style>
* {
font-family: simsun, DejaVu Sans, sans-serif;
}
</style>
</head>
<body>
<p>测试展示</p>
</body>
</html>
生成 PDF
代码如下:
$dompdf = new Dompdf();
// 这里使用模板 view()->render() 得到 html
$dompdf->loadHtml(view('report')->render());
// 设置文件页面大小
$dompdf->setPaper('A4', 'landscape');
// 将 html 转为 pdf
$dompdf->render();
// 输出到浏览器
return $dompdf->stream();
// 可以存储
// Storage::put('test.pdf', $dompdf->output());
但是我们使用的是laravel-dompdf
扩展包这个扩展包依赖 dompdf
扩展包,所以上面能够生成 PDF
. 使用 laravel-dompdf
扩展包来生成 PDF
的代码如下
$pdf = Pdf::loadHTML(view('report', ['data' => $data])->render());
$pdf->save('test.pdf');
仅仅这么做, 还是乱码, 这是为什么呢? 这是因为 laravel-dompdf
扩展包无法前面我们安装的字体库, 因为这个字体库是安装到了 dompdf
扩展包的目录下, laravel-dompdf
扩展包不支持这种. 我们需做如下操作.
- 加载
laravel-dompdf
扩展包配置文件, 生成dompdf.php
的配置文件.php artisan vendor:publish --provider="Barryvdh\DomPDF\ServiceProvider"
- 可以看到
dompdf.php
文件中"font_dir" => storage_path('fonts')
字体地址指向的是storage
下的fonts
文件夹下. 所以我们复制前面 安装字体 时vendor\dompdf\dompdf\lib\fonts
文件加下的全部字体到storage/fonts
文件夹下. 这种处理, 更有利于代码仓库管理和部署. - 再看在使用前面的
laravel-dompdf
扩展包的生产PDF
的代码来生成 PDF . 可以看到已经支持中文正常显示了. 需要注意的是我们复制字体时,需要全部字体都复制. 不然还是会存在乱码, 因为还需要dompdf
扩展包下的其他字体. - 此时如果你发现生成的
PDF
文件过大, 或者生成速度慢时, 可以修改dompdf.php
文件"enable_font_subsetting" => true,
- 最后我们提交代码只需要提交
composer
,config
,storage/fonts
变化的部分, 前面根目录下的simsum.ttf
和load_font.php
这两个文件可以删除了.
本作品采用《CC 协议》,转载必须注明作者和本文链接