使用pdf2cairo将PDF格式化为Python格式的PNG

时间:2013-06-21 08:56:20

标签: python subprocess pyside poppler

我正在寻找一个很好的PDF 2图像转换器很长一段时间。我需要将PDF转换为图像,以便使用Qt打印它。我正在使用Python / Pyside进行编程,所以如果我可以使用子进程将PDF转换为一系列(PNG)图像,我可以毫无问题地打印它们。

我通过从Imagemagick调用convert.exe来实现这一目标。它工作得很好,但它依赖于GhostScript,这是一个我想避免的大包,因为它更难以集成。

我也尝试过GhostScript中的muPDF,但这似乎没有stdin和stdout选项。这很可惜因为它首先保存了我的文件。使用muPDF打开它,转换并保存它,然后在我的Python应用程序中重新加载它。没有所有这些步骤应该是可能的!

今天我开始尝试使用Poppler的pdf2cairo。我认为它可以通过这种方式将我的(多页面)PDF转换为一系列图像并将其传送到标准输出。不幸的是它没有,我遇到两个问题:

  • 它抱怨它只能在你使用-singlepage参数时导出到stdout。如何将所有页面导出到stdout?
  • 当我导出到stdout时,我收到错误:'Error opening output file fd://0.png\r\n

将pdf从stdin转换为图像文件并不是问题。

这是我的代码,它也会触发打开输出文件的错误:

import subprocess

pdf = open('test.pdf')
p = subprocess.Popen(['pop/pdftocairo.exe', '-singlefile', '-png', '-', '-'],stdin = pdf, stdout = subprocess.PIPE, stderr = subprocess.PIPE)
print(p.stderr.read())
print(p.stdout.read())

我已经从http://blog.alivate.com.au/poppler-windows/下载了预编译的PDF2Cairo 可以在此处找到pdf2cairo命令行选项的文档:http://manpages.ubuntu.com/manpages/precise/man1/pdftocairo.1.html

希望你能帮助我完成这项工作!

更新 正如您在下面的答案中所见,pdftocairo是错误的,并且当您想要使用stdout时无法正常工作。 pdftoppm确实有效,它返回的是PDF文件的字节对象:

pdf = open('test.pdf')
p = subprocess.Popen(['pop/pdftoppm.exe',  '-png'],stdin = pdf, stdout = subprocess.PIPE,   stderr = subprocess.PIPE)
data, error = p.communicate()

我唯一需要做的就是将字节对象拆分成多个文件。

2 个答案:

答案 0 :(得分:1)

这是pdftocairo中的一个错误。

输出文件名首先传递给getOutputFilenamereturns the special string fd://0作为stdout的占位符。

但后来该字符串被传递给getImageFilename,无条件地adds an extension到文件名,以便后来comparision失败,程序厌倦了打开文字文件{{1}而不是使用fd://0.png

不幸的是,你唯一能做的就是file a bug report

至于将多页文档导出到stdout,这根本不受支持,并且无论如何都不适用于像png或jpeg这样的文件类型,因为这些格式不支持多页文档。它适用于stdoutsvgpdfeps输出文件,因为这些格式支持多页文档(以及为这些文件正确处理文件名。)

答案 1 :(得分:0)

我认为使用os.system并传递整个命令字符串会更容易。 假设有“pdfs”和“imgs”文件夹;相应地改变。

import os
import glob

for pdf_file in glob.glob("pdfs\*.pdf"):
    cmd_str = "pdftocairo.exe -jpeg \"%s\" \"%s\"" % (pdf_file, os.path.join("imgs", os.path.splitext(os.path.split(pdf_file)[1])[0]))
    print cmd_str
    os.system(cmd_str)