jos*_*sch 5 linux pdf batch command-line images
是否存在适用于 Linux 的命令行工具,它允许我从 PDF 中提取所有 /Subtype /Image 光栅图像对象,允许我使用另一个 3rd 方工具处理它们,然后能够将它们重新插入原始 PDF?
Debian 软件包 poppler-utils 带来了 pdfimages 工具,它允许我从 PDF 中提取所有图像,但在更改它们后我无法轻松地将它们重新插入 PDF。
我之前为 PDF 编写了简单的解析器,所以我目前对这个问题的看法是
但也许一个允许所有这些并且不限于我编写的简单解析器的功能的工具已经存在?
如果你说这样的工具不存在,那么告诉我一个允许提取和稍后替换图像的库也是可以的。
您可以尝试在命令行中使用inkscape
inkscape -S # show all the object inside the document
inkscape --select=YouImage --verb=YourTransformation
inkscape --verb-list #to obtain all the possibilities
Run Code Online (Sandbox Code Playgroud)
或者你可以提取图像,用你想要的任何东西修改它们(imagemagick?),然后在你的文档中用inkscape替换它们。
问候
这似乎(还)不可能在命令行中执行,但我找到了一种使用pdfrw python 模块在 python 中编写脚本的简单方法,如下所示:
#!/usr/bin/env python
import sys
import os
import zlib
import Image
import StringIO
from pdfrw import PdfReader, PdfDict, PdfArray, PdfName, PdfWriter
def process_image(image):
if image["/Filter"] == PdfName("FlateDecode"):
pass
elif image["/Filter"] == PdfName("DCTDecode"):
im = Image.open(StringIO.StringIO(image.stream))
outf = StringIO.StringIO()
im.save(outf, "JPEG", quality=45)
image.stream = outf.getvalue()
outf.close()
def find_images(obj, visited=set()):
if not isinstance(obj, (PdfDict, PdfArray)):
return
myid = id(obj)
if myid in visited:
return
visited.add(myid)
if isinstance(obj, PdfDict):
if obj.Type == PdfName.XObject and obj.Subtype == PdfName.Image:
process_image(obj)
obj = obj.itervalues()
for item in obj:
find_images(item, visited)
if __name__ == '__main__':
inpfn,outfn = sys.argv[1:]
reader = PdfReader(inpfn)
find_images(reader)
PdfWriter().addpages(reader.pages).write(outfn)
Run Code Online (Sandbox Code Playgroud)
您可以在process_images
函数中实现您想要的任何内容,甚至可以轻松完成诸如调用外部程序来修改当前图像之类的复杂事情。在本例中,我们仅使用 PIL 对质量为 45 的 jpeg 图像进行重新编码。