如何通过Ghostscript为PDF每页添加动态递增页码?
解决Ghostscript给PDF添加动态页码的问题
我来帮你搞定这个动态页码的难题!其实你不用费劲传外部参数,Ghostscript的EndPage操作符本身就自带了当前页码和总页数的参数,这才是最直接的解决方案,之前的思路绕远路啦。
问题根源
你之前尝试用命令行传参数的方式行不通,是因为Ghostscript会把命令行里额外的非选项参数(比如你写的"pageNumber")当作PostScript文件来加载,而不是作为脚本可读取的变量。而且更关键的是,EndPage回调本身就提供了我们需要的页码信息,根本不需要额外传参。
正确的PostScript脚本(pages.ps)
直接用EndPage的内置参数来实现动态页码,脚本如下:
<< /EndPage { % EndPage的参数栈结构:总页数 当前页码 拷贝次数 设备字典 % 2 eq 判断是否是最后一页的最后一份拷贝,这里我们处理所有页面 2 eq { pop false } { gsave % 设置字体,Helvetica是Ghostscript内置字体,避免找不到Arial的问题 /Helvetica 8 selectfont % 设置页码位置(x,y坐标,可根据需求调整) 550 820 moveto % 输出"page "前缀,然后是当前页码 (page ) show % 把当前页码从数字转成字符串并显示 0 exch string cvs show grestore true % 返回true表示继续处理页面 } ifelse } bind >> setpagedevice
调用命令
和你之前的命令几乎一样,不需要额外加参数:
gs -dBATCH -dNOPAUSE -dSAFER -sDEVICE=pdfwrite -sOutputFile=out.pdf pages.ps in.pdf
进阶:显示总页数(page X of Y)
如果想要显示类似page 1 of 5的格式,只需要利用EndPage的第二个参数(总页数),修改脚本即可:
<< /EndPage { 2 eq { pop false } { gsave /Helvetica 8 selectfont 550 820 moveto (page ) show % 显示当前页码 0 exch string cvs show ( of ) show % 交换栈元素,拿到总页数并显示 exch string cvs show grestore true } ifelse } bind >> setpagedevice
注意事项
- 如果一定要用Arial字体,需要确保Ghostscript能找到该字体文件,可以通过
-sFONTPATH=/path/to/fonts参数指定字体路径; - 坐标
550 820是页码的位置,你可以根据PDF的页面尺寸调整(比如A4页面的左下角是(0,0),右上角是(595,842)); string cvs是PostScript里把数字转换成字符串的标准方法,确保数字能正确显示成文本。
内容的提问来源于stack exchange,提问作者Luiz Henrique Salazar
相关产品推荐
相关产品推荐

