Document#
该类表示一个文档。它可以从文件或内存中构造。
该类的别名为 open,即 pymupdf.Document(...)
和 pymupdf.open(...)
的功能完全相同。
有关 嵌入文件 的详细信息,请参阅附录 3。
备注
从 v1.17.0 开始,仅针对 EPUB 文件 引入了一种新的页面寻址机制。此类文档在内部按章节组织,因此最有效的页面查找方式是使用所谓的 “location”(位置)。该位置是一个元组 (chapter, pno),其中:
chapter 表示章节编号
pno 表示该章节中的页面编号
这两个编号均从 0 开始。
尽管仍然可以使用页面的(绝对)编号进行定位,但这样可能会导致完整的 EPUB 文档在定位前必须完全布局。如果文档非常大,这可能会对性能产生显著影响。而使用 (chapter, pno) 进行定位可以避免这一问题。
为了保持一致的 API,PyMuPDF 支持对 所有文件类型 使用页面 location 语法——对于不具备此功能的文档,其内容仅包含一个章节。Document.load_page()
以及等效的索引访问现在也支持 location 参数。
此外,还提供了一些方法用于在页面编号和位置之间进行转换,获取章节数、每个章节的页面数,以及计算文档的下一页、上一页和最后一页的位置。
方法 / 属性 |
简要说明 |
---|---|
仅限 PDF:创建新的可选内容配置 |
|
仅限 PDF:添加新的可选内容组 |
|
访问加密文档 |
|
仅限 PDF:使注释 / 表单字段成为永久内容 |
|
检查是否可以增量保存 |
|
章节中的页数 |
|
关闭文档 |
|
将文档转换为 PDF 并存储到内存 |
|
仅限 PDF:复制页面引用 |
|
仅限 PDF:删除单个目录项 |
|
仅限 PDF:删除页面 |
|
仅限 PDF:删除多个页面 |
|
仅限 PDF:从缓冲区添加新的嵌入文件 |
|
仅限 PDF:获取嵌入文件的数量 |
|
仅限 PDF:删除嵌入文件条目 |
|
仅限 PDF:提取嵌入文件的缓冲区 |
|
仅限 PDF:获取嵌入文件的元数据 |
|
仅限 PDF:列出嵌入文件 |
|
仅限 PDF:更新嵌入文件 |
|
仅限 PDF:通过 |
|
仅限 PDF:通过 |
|
仅限 PDF:使用不同默认值调用 |
|
获取文档布局后的书签页位置 |
|
仅限 PDF:复制整个页面 |
|
仅限 PDF:获取开启、关闭、RBGroups 中的 OCGs |
|
仅限 PDF:获取所有可选内容配置 |
|
仅限 PDF:获取图像 / 表单 xobject 的 OCG / OCMD |
|
仅限 PDF:获取所有可选内容组信息 |
|
仅限 PDF:检索 |
|
仅限 PDF:获取页面中引用的字体列表 |
|
仅限 PDF:获取页面中引用的图像列表 |
|
仅限 PDF:获取页面标签定义列表 |
|
仅限 PDF:获取具有特定标签的页码 |
|
通过页码创建页面的 pixmap |
|
通过页码提取页面文本 |
|
仅限 PDF:获取页面引用的 XObjects 列表 |
|
仅限 PDF:确定签名状态 |
|
提取目录(TOC) |
|
仅限 PDF:读取 XML 元数据 |
|
仅限 PDF:检查 PDF 是否包含注释 |
|
仅限 PDF:检查 PDF 是否包含链接 |
|
仅限 PDF:插入新页面 |
|
仅限 PDF:从另一个 PDF 插入页面 |
|
仅限 PDF:从任意文档插入页面 |
|
仅限 PDF:检查支持的日志操作 |
|
仅限 PDF:启用日志记录 |
|
仅限 PDF:从文件加载日志 |
|
仅限 PDF:获取日志步骤名称 |
|
仅限 PDF:获取日志状态 |
|
仅限 PDF:重做当前操作 |
|
仅限 PDF:保存日志到文件 |
|
仅限 PDF:开始新的日志操作并命名 |
|
仅限 PDF:结束当前日志操作 |
|
仅限 PDF:撤销当前操作 |
|
仅限 PDF:获取可选内容的 UI 配置 |
|
重新分页文档(如果支持) |
|
读取页面 |
|
在可重排文档中创建页面指针 |
|
仅限 PDF:移动页面到文档中不同位置 |
|
仅限 PDF:获取 / 设置 |
|
仅限 PDF:插入新的空白页面 |
|
返回下一页的 (chapter, pno) |
|
仅限 PDF:获取目录项的 |
|
仅限 PDF:获取未旋转的页面矩形 |
|
仅限 PDF:获取页面的 |
|
迭代页面范围 |
|
仅限 PDF:获取 PDF 目录的 |
|
仅限 PDF:获取 PDF 预告信息 |
|
返回前一页的 (chapter, pno) |
|
仅限 PDF:重新加载页面 |
|
仅限 PDF:将目标名称转换为 Python 字典 |
|
仅限 PDF:保存文档 |
|
仅限 PDF:增量保存文档 |
|
仅限 PDF:删除敏感数据 |
|
在页面中搜索字符串 |
|
仅限 PDF:选择页面子集 |
|
仅限 PDF:临时设置 OCG 可见性 |
|
仅限 PDF:批量更改 OCG 状态 |
|
仅限 PDF:设置 MarkInfo 值 |
|
仅限 PDF:设置元数据 |
|
仅限 PDF:将 OCG/OCMD 附加到图像 / 表单 xobject |
|
仅限 PDF:创建或更新 |
|
仅限 PDF:添加 / 更新页面标签定义 |
|
仅限 PDF:设置 PageMode |
|
仅限 PDF:设置 PageLayout |
|
仅限 PDF:修改单个目录项 |
|
仅限 PDF:设置目录(TOC) |
|
仅限 PDF:创建或更新 XML 元数据 |
|
仅限 PDF:创建字体子集 |
|
仅限 PDF:激活 OC 配置 |
|
仅限 PDF:将文档写入内存 |
Class API
- class Document#
- __init__(self, filename=None, stream=None, *, filetype=None, rect=None, width=0, height=0, fontsize=11)#
v1.14.13 版本更改:支持
io.BytesIO
作为内存文档。v1.19.6 版本更改:提供更清晰、更简短且更一致的异常消息。如果未指定文件类型,则默认假定为 “pdf”。空文件或空内存区域将始终导致异常。
创建一个 Document 对象。
使用默认参数时,将创建一个 新的空 PDF 文档。
如果提供了 stream,则从内存创建文档。如果该文档不是 PDF,则必须通过 filename 或 filetype 指定其类型。
如果 stream 为
None
,则从 filename 指定的文件创建文档。其类型将根据文件扩展名推断。该推断可以通过 filetype 覆盖。
- 参数:
filename (str,pathlib) – 一个 UTF-8 字符串或 pathlib 对象,表示文件路径。文档类型由文件名扩展名推断。如果未提供,或者扩展名不匹配 支持的类型,则默认假定为 PDF。对于内存文档,可以使用此参数代替
filetype
,详见下文。stream (bytes,bytearray,BytesIO) – 一个包含支持的文档数据的内存区域。如果不是 PDF,则必须通过
filename
或filetype
指定其类型。filetype (str) – 指定文档类型的字符串。它可以是类似于文件名的格式(例如
"x.pdf"
),此时 MuPDF 会使用扩展名来确定类型,或者 MIME 类型(如 application/pdf)。直接使用"pdf"
或".pdf"
也是可以的。对于 PDF 文档,此参数可以省略,否则必须匹配 支持的文档类型。rect (rect_like) – 指定所需页面尺寸的矩形。此参数仅对具有可变页面布局(”可重排” 文档,例如电子书或 HTML)的文档有意义,其他情况下会被忽略。如果指定,该矩形必须是非空的有限矩形,且左上角坐标为 (0, 0)。与 fontsize 参数结合,每个页面将根据此布局计算,并由此决定总页数。
width (float) – 可以与 height 一起用作 rect 的替代方案,以指定页面布局信息。
height (float) – 可以与 width 一起用作 rect 的替代方案,以指定页面布局信息。
fontsize (float) – 可重排文档类型的默认
fontsize
。如果未指定 rect,或者 width 和 height,则该参数被忽略。否则,将用于计算页面布局。
- 抛出:
TypeError – 如果任一参数的类型不符合要求。
FileNotFoundError – 如果无法找到文件/路径。该异常被重新实现为
RuntimeError
的子类。EmptyFileError – 如果文件/路径为空,或内存中的
bytes
对象长度为零。该异常是FileDataError
和RuntimeError
的子类。ValueError – 如果显式指定了未知的文件类型。
FileDataError – 如果文档的结构对于给定的类型无效,或者不是文件(例如是一个文件夹)。该异常是
RuntimeError
的子类。
- 返回:
返回一个文档对象。如果文档无法创建,则按照上述顺序引发异常。请注意,PyMuPDF 特定的异常
FileNotFoundError
、EmptyFileError
和FileDataError
在检查RuntimeError
时也会被拦截。如果遇到问题,可以使用以下方式查看内部消息存储的详细信息:
print(pymupdf.TOOLS.mupdf_warnings())
该调用会清空消息存储,但也可以防止清空,详见Tools.mupdf_warnings()
。
备注
并非所有文档类型都会在打开时立即检查格式的有效性。例如,栅格图像可能会在访问内容时才引发异常。其他类型(尤其是非二进制内容)有时即使内容格式无效也可以打开(甚至可以 访问 部分内容):
HTM, HTML, XHTML:始终 可以打开,
metadata["format"]
分别为"HTML5"
和"XHTML"
。XML, FB2:始终 可以打开,
metadata["format"]
为"FictionBook2"
。
以下是可能的使用方式,注意:
open
是 Document 的同义词:>>> # 从文件打开 >>> doc = pymupdf.open("some.xps") >>> # 处理错误的扩展名 >>> doc = pymupdf.open("some.file", filetype="xps") >>> >>> # 从内存打开,如果不是 PDF,必须提供 filetype >>> doc = pymupdf.open("xps", mem_area) >>> doc = pymupdf.open(None, mem_area, "xps") >>> doc = pymupdf.open(stream=mem_area, filetype="xps") >>> >>> # 创建一个新的空 PDF >>> doc = pymupdf.open() >>> doc = pymupdf.open(None) >>> doc = pymupdf.open("")
备注
如果栅格图像的文件扩展名错误(但仍然是受支持的格式),不会有问题。MuPDF 在实际访问文件 内容 时会确定正确的图像类型,并能正常处理。因此,即使
file.jpg
实际上是 PNG 图像,pymupdf.open("file.jpg")
仍然可以工作。Document 类也可以用作 上下文管理器。退出时,文档会自动关闭。
>>> import pymupdf >>> with pymupdf.open(...) as doc: for page in doc: print("page %i" % page.number) page 0 page 1 page 2 page 3 >>> doc.is_closed True >>>
- get_oc(xref)#
新增于 v1.18.4
返回附加到图像或表单 xobject 的
OCG
或OCMD
的交叉引用号。- 参数:
xref (int) – 图像或表单 xobject 的
xref
。有效的交叉引用号可通过Document.get_page_images()
或Document.get_page_xobjects()
获取。对于无效的编号,将引发异常。- 返回类型:
int
- 返回:
可选内容对象的交叉引用号,如果没有则返回 0。
- set_oc(xref, ocxref)#
新增于 v1.18.4
如果 xref 代表一个图像或表单 xobject,则设置或移除可选内容对象的交叉引用号 ocxref。
- 参数:
xref (int) – 图像或表单 xobject 的
xref
[12]。有效的交叉引用号可通过Document.get_page_images()
或Document.get_page_xobjects()
获取。对于无效的编号,将引发异常。ocxref (int) –
OCG
/OCMD
的xref
号。如果不为 0,则无效的引用会引发异常。如果为 0,则移除任何 OC 引用。
- get_layers()#
新增于 v1.18.3
显示可选的图层配置。始终存在一个标准配置,但不会包含在返回结果中。
>>> for item in doc.get_layers(): print(item) {'number': 0, 'name': 'my-config', 'creator': ''} >>> # 在 add_ocg 中使用 'number' 作为配置标识符
- add_layer(name, creator=None, on=None)#
新增于 v1.18.3
添加一个可选内容配置。图层用于管理可选内容组的开 / 关状态,并允许在同一文档的不同视图之间快速切换可见性。
- 参数:
name (str) – 任意名称。
creator (str) – (可选) 创建此图层的软件。
on (sequ) – 需要在此图层激活时设置为 ON 的 OCG
xref
编号序列。所有未列出的 OCG 将被设置为 OFF。
- switch_layer(number, as_default=False)#
新增于 v1.18.3
切换到由可选图层的配置编号定义的文档视图。该操作是临时的,除非设定为默认配置。
- 参数:
number (int) – 由
Document.layer_configs()
返回的配置编号。as_default (bool) – 是否将此配置设为默认。
激活 OCG 的开 / 关状态,该状态由指定图层定义。如果 as_default=True,则所有图层(包括标准图层)将被合并,并将结果写回标准图层,同时 所有可选图层都会被删除。
- add_ocg(name, config=-1, on=True, intent='View', usage='Artwork')#
新增于 v1.18.3
添加一个可选内容组。OCG 是确定对象可见性的最重要单位。对于 PDF,如果希望支持可选内容,至少需要存在一个 OCG。
- 参数:
name (str) – 任意名称,将显示在支持的 PDF 查看器中。
config (int) – 图层配置编号。默认值 -1 表示标准配置。
on (bool) – 指向该 OCG 的对象的标准可见性状态。
intent (str,list) – 一个字符串或字符串列表,声明可见性意图。PDF 标准提供了两个选项:”View” 和 “Design”。默认值为 “View”。拼写必须正确。
usage (str) – 影响 OCG 可见性的另一个因素。此值将成为 OCG 的
/Usage
键的一部分。PDF 标准提供了两个选项:”Artwork” 和 “Technical”,默认值为 “Artwork”。仅在必要时更改。
- 返回:
创建的 OCG 的
xref
。可用于支持对象的oc
参数。
备注
可以创建多个具有相同参数的 OCG,这不会导致问题。使用
Document.save()
的垃圾回收选项 3 可删除任何重复项。
- set_ocmd(xref=0, ocgs=None, policy='AnyOn', ve=None)#
新增于 v1.18.4
创建或更新一个
OCMD
,即 可选内容成员字典 (Optional Content Membership Dictionary)。- 参数:
- 返回类型:
int
- 返回:
OCMD 的
xref
,可作为支持对象的oc=xref
参数,也可用于Document.set_oc()
或Annot.set_oc()
。
备注
与 OCG 类似,OCMD 具有 ON 或 OFF 的可见性状态,并可与 OCG 相同方式使用。但 OCMD 通过 布尔表达式 计算一个或多个 OCG 的状态,以决定自身的可见性。如果表达式计算结果为 true,则 OCMD 处于 ON 状态;若为 false,则处于 OFF 状态。
OCMD 可通过以下两种方式设定可见性:
使用 ocgs 和 policy 组合:
policy 的值含义如下:
AnyOn ——(默认)至少有一个 OCG 处于 ON 状态,则 OCMD 也为 ON。
AnyOff —— 只要有一个 OCG 处于 OFF 状态,则 OCMD 为 ON。
AllOn —— 仅当所有 OCG 均为 ON 时,OCMD 才为 ON。
AllOff —— 仅当所有 OCG 均为 OFF 时,OCMD 才为 ON。
假设希望两个 PDF 对象交替显示(一个 ON,另一个必须 OFF):
解决方案:对象 1 使用 OCG,对象 2 使用 OCMD。通过
set_ocmd(ocgs=[xref], policy="AllOff")
创建 OCMD,其中 xref 为 OCG 的交叉引用号。使用 可见性表达式 ve:
该参数是一个至少包含两个元素的列表,第一个元素 必须是逻辑关键字之一:”and”、”or” 或 “not”。第二个及后续元素 必须是整数或嵌套列表:
每个列表必须以逻辑关键字开头。
若关键字为 “not”,列表必须包含恰好两个元素。
若关键字为 “and” 或 “or”,则后续可以有任意数量的元素。
逻辑关键字后面的元素可以是整数(OCG 的 xref 号)或嵌套列表(必须符合上述规则)。
示例:
set_ocmd(ve=["or", 4, ["not", 5], ["and", 6, 7]])
逻辑含义:“4 为 ON,或 5 为 OFF,或 6 和 7 均为 ON”。set_ocmd(ve=["not", xref])
其效果与示例 1 中的 OCMD 相同。
更多详细信息和示例可参考 Adobe PDF 参考 第 224 页,以及 此处 的示例脚本。
可见性表达式 (
/VE
) 属于 PDF 规范 1.6 版的一部分,因此并非所有 PDF 查看器都支持此功能。对于不支持的查看器,将采用某种标准处理方式。
- get_ocmd(xref)#
新增于 v1.18.4
获取
OCMD
的定义。- 参数:
xref (int) – OCMD 的
xref
。- 返回类型:
dict
- 返回:
包含以下键的字典:xref、ocgs、policy 和 ve。
- get_layer(config=-1)#
新增于 v1.18.3
按状态列出指定配置中的可选内容组。返回包含 OCG 交叉引用号列表的字典,这些 OCG 出现在
/ON
、/OFF
或单选按钮组 (/RBGroups
) 数组中。- 参数:
config (int) – 配置层编号(默认值为标准配置层)。
>>> pprint(doc.get_layer()) {'off': [8, 9, 10], 'on': [5, 6, 7], 'rbgroups': [[7, 10]]} >>>
- set_layer(config, *, on=None, off=None, basestate=None, rbgroups=None, locked=None)#
新增于 v1.18.3
v1.22.5 变更:支持 locked OCGs 列表。
批量更改可选内容组(OCG)的状态。此方法 永久 设置 OCG 的状态。
- 参数:
config (int) – 目标配置层,选择 -1 代表默认配置层。
on (list) – 需要设置为 ON 的 OCG 的
xref
号列表。会替换先前的值。空列表表示不再将任何 OCG 设为 ON。若使用basestate="ON"
,则应指定此参数。off (list) – 需要设置为 OFF 的 OCG 的
xref
号列表。会替换先前的值。空列表表示不再将任何 OCG 设为 OFF。若使用basestate="OFF"
,则应指定此参数。basestate (str) – 未在 on 或 off 中提及的 OCG 的状态。可能的取值为 “ON”、”OFF” 或 “Unchanged”(不变)。大小写均可。
rbgroups (list) – 一个列表,包含多个子列表。会替换先前的值。每个子列表包含两个或多个 OCG 的 xref 号。处于同一子列表中的 OCG 会像单选按钮一样处理:设定其中一个为 ON,会自动将同组中的其他 OCG 设为 OFF。
locked (list) – OCG xref 号列表,其中的 OCG 不能通过用户界面更改状态。
若参数值为
None
,则不会更改对应的 PDF 数组。>>> doc.set_layer(-1, basestate="OFF") # 仅更改基础状态 >>> pprint(doc.get_layer()) {'basestate': 'OFF', 'off': [8, 9, 10], 'on': [5, 6, 7], 'rbgroups': [[7, 10]]}
- get_ocgs()#
新增于 v1.18.3
获取所有可选内容组 (OCG) 的详细信息。返回一个字典,其中键为 OCG 的
xref
号,值为 OCG 的属性字典:>>> pprint(doc.get_ocgs()) {13: {'on': True, 'intent': ['View', 'Design'], 'name': 'Circle', 'usage': 'Artwork'}, 14: {'on': True, 'intent': ['View', 'Design'], 'name': 'Square', 'usage': 'Artwork'}, 15: {'on': False, 'intent': ['View'], 'name': 'Square', 'usage': 'Artwork'}} >>>
- layer_ui_configs()#
新增于 v1.18.3
显示支持 PDF 查看器的用户界面可修改的可选内容可见性状态。
仅报告当前所选层配置中包含的项目。
字典键的含义如下:
depth: 项目在
/Order
数组中的嵌套级别locked: 若为 true,则无法通过用户界面更改
number: 运行序列号
on: 项目状态
text: 该 OCG 的文本字符串或名称字段
type: 可能的值包括 “label”(由文本字符串设定)、”checkbox”(由单个 OCG 设定)或 “radiobox”(由一组相关 OCG 设定)
- set_layer_ui_config(number, action=0)#
新增于 v1.18.3
修改内容组的可见性状态。其作用类似于支持 PDF 查看器提供的用户界面功能。
请注意,可见性 不是 OCG 本身存储的属性,甚至不一定包含在 PDF 文档中。当前可见性是通过支持的 PDF 软件用户界面 临时 设定的。本方法提供了相同类型的功能。
若需 永久 更改可见性,请使用
Document.set_layer()
。- 参数:
number (int,str) – 可选项的序列号(在
Document.layer_configs()
列表中的索引)或该项的 text 字段值。action (int) –
PDF_OC_ON
= 设为 ON(默认值)PDF_OC_TOGGLE
= 切换 ON/OFFPDF_OC_OFF
= 设为 OFF
- authenticate(password)#
使用字符串 password 解密文档。若解密成功,即可访问文档数据。对于 PDF 文档,“所有者”与“用户”具有不同的权限,因此可能存在不同的密码。该方法会根据提供的密码自动建立适当的访问权限(所有者或用户)。
- 参数:
password (str) – 所有者或用户密码。
- 返回类型:
int
- 返回:
若成功,则返回正值;若失败(密码不匹配),则返回 0。若返回正值,则
Document.is_encrypted
设为 False。 正值 的含义如下:1 => 认证成功,但 PDF 既无所有者密码,也无用户密码。
2 => 认证成功,使用的是 用户 密码。
4 => 认证成功,使用的是 所有者 密码。
6 => 认证成功,且所有者密码与用户密码相同(可能较为罕见)。
备注
文档可能受所有者密码保护,但 未 受用户密码保护。可通过
doc.authenticate("") == 2
进行检测。这种情况下,文档可在 无需认证 的情况下打开和阅读,但具体操作可能受Document.permissions
限制。然而,PyMuPDF(与 MuPDF 一样) 忽略 这些限制。因此,与普通 PDF 查看器不同,即使PDF_PERM_COPY
、PDF_PERM_MODIFY
、PDF_PERM_ANNOTATE
等权限被禁用,仍可提取文本、添加或修改内容。请确保您的应用符合相关法律要求。
- get_page_numbers(label, only_one=False)#
新增于 v1.18.6
仅适用于 PDF:返回具有指定标签的页面编号列表——请注意,在 PDF 中,页面标签可能并不唯一。因此,该方法会 顺序搜索所有页面,以比较其标签。
备注
实现细节 —— 该方法 不会加载页面 进行搜索。
- 参数:
label (str) – 要查找的标签,例如 “vii”(罗马数字 7)。
only_one (bool) – 若为 True,则在找到第一个匹配项后停止。适用于已知标签唯一或文档页面较多的情况。默认行为是检查所有页面。
- 返回类型:
list
- 返回:
包含所有匹配页面编号的列表。若未找到匹配项,或文档未定义页面标签,则返回空列表。
- get_page_labels()#
新增于 v1.18.7
仅适用于 PDF:提取页面标签定义列表。通常用于修改后传递给
Document.set_page_labels()
进行更新。- 返回:
以字典形式表示的页面标签定义列表,格式与
Document.set_page_labels()
相同。
- set_page_labels(labels)#
新增于 v1.18.6
仅适用于 PDF:新增或更新 PDF 的页面标签定义。
- 参数:
labels (list) –
由字典组成的列表,每个字典定义一个标签规则,并指定起始页面编号(从 0 开始)。每个字典最多包含 4 个键,格式如下:
{'startpage': int, 'prefix': str, 'style': str, 'firstpagenum': int}
,其中:startpage
: (int) 规则适用的第一个页面(从 0 开始)。必须提供。该规则适用于所有后续页面,直到文档结束,或被下一个规则覆盖。prefix
: (str) 标签前缀,例如 “A-”。默认为 “”。style
: (str) 编号样式,可选值:"D"
:十进制数字"r"/"R"
:罗马数字(小写 / 大写)"a"/"A"
:字母编号(小写 / 大写)。示例:”a” 至 “z”,然后 “aa” 至 “zz”,以此类推。默认为 “”,即无编号,仅使用
prefix
作为标签。若prefix
也为空,则该范围内的页面标签将为空字符串 “”。
firstpagenum
: (int) 编号的起始值。默认为 1,若小于 1,则忽略。
例如:
[{'startpage': 6, 'prefix': 'A-', 'style': 'D', 'firstpagenum': 10}, {'startpage': 10, 'prefix': '', 'style': 'D', 'firstpagenum': 1}]
以上规则会生成如下页面标签:”A-10”, “A-11”, “A-12”, “A-13”, “1”, “2”, “3”, … 对应的页面为 6, 7, 8, 9, 10, 11, 12,直到文档结束。页面 0 至 5 的标签为空字符串 “”。
- make_bookmark(loc)#
新增于 v1.17.3
在可重排(reflowable)文档中返回一个页面指针。重新布局文档后,可以使用该方法的返回值来查找该页面的新位置。
备注
不要与目录 (TOC) 条目混淆。
- 参数:
loc (list,tuple) – 页面位置。必须是有效的 (chapter, pno)。
- 返回类型:
pointer
- 返回:
一个长整数,表示指针格式。可用于在文档重新布局后查找新位置。请勿修改或重新分配此值。
- find_bookmark(bookmark)#
新增于 v1.17.3
重新布局文档后,返回书签对应的新页面位置。
- 参数:
bookmark (pointer) – 由
Document.make_bookmark()
创建的书签。- 返回类型:
tuple
- 返回:
该页面的新位置 (chapter, pno)。
- chapter_page_count(chapter)#
新增于 v1.17.0
返回指定章节的页面数量。
- 参数:
chapter (int) – 以 0 为基准的章节编号。
- 返回类型:
int
- 返回:
该章节的页面数。仅适用于支持章节结构的文档类型(目前适用于 EPUB)。
- next_location(page_id)#
新增于 v1.17.0
返回下一页的位置。
- 参数:
page_id (tuple) – 当前页面的标识,必须是 (chapter, pno) 形式的元组,指向现有页面。
- 返回:
下一页的位置,即 (chapter, pno + 1) 或 (chapter + 1, 0), 如果当前页面为最后一页,则返回空元组 () 。仅适用于支持章节结构的文档类型(目前适用于 EPUB)。
- prev_location(page_id)#
新增于 v1.17.0
返回前一页的位置。
- 参数:
page_id (tuple) – 当前页面的标识,必须是 (chapter, pno) 形式的元组,指向现有页面。
- 返回:
前一页的位置,即 (chapter, pno - 1) 或前一章节的最后一页, 如果当前页面为第一页,则返回空元组 ()。仅适用于支持章节结构的文档类型(目前适用于 EPUB)。
- load_page(page_id=0)#
变更于 v1.17.0: 对于支持“章节结构”的文档类型(如 EPUB),页面现在也可以通过章节号和相对页码来加载,而不仅仅是绝对页码。这在处理大型文档时 显著提高了访问速度。
创建一个 Page 对象,以便进行后续处理(如渲染、文本搜索等)。
- 参数:
page_id (int,tuple) –
(变更于 v1.17.0)
可以是 0 基准的页面编号,也可以是 (chapter, pno) 形式的元组。
整数类型: 允许
-∞ < page_id < page_count
。如果page_id
为负数,则会自动加上page_count
。例如,要加载最后一页,可以使用 doc.load_page(-1),此时page.number = doc.page_count - 1
。元组类型:
chapter
必须在Document.chapter_count
范围内,pno
必须在该章节的Document.chapter_page_count()
范围内。两者均从 0 开始计数。使用此格式时,Page.number
将等于提供的元组值。
- 返回类型:
备注
文档也遵循 Python 序列协议,页面编号作为索引:doc.load_page(n) == doc[n]。
仅对 绝对页面编号,像 “for page in doc: …” 和 “for page in reversed(doc): …” 这样的表达式将依次返回文档的页面。参见
Document.pages()
,它允许像切片一样处理页面。你也可以使用基于章节的页面标识符的索引表示法:使用 page = doc[(5, 2)] 加载第六章的第三页。
为了保持一致的 API,对于不支持章节结构的文档类型(如 PDF),
Document.chapter_count
为 1,页面也可以通过元组 (0, pno) 来加载。请参阅此 [10] 脚注,了解性能改进的说明。- reload_page(page)#
在 v1.16.10 中新增
仅适用于 PDF:在完成并更新所有待处理更改后,提供页面的新副本。
- resolve_names()#
仅适用于 PDF:将目标名称转换为 Python 字典。
- 返回:
一个字典,包含以下布局:
key: (str) 名称。
- value: (dict),具有以下布局:
”page”: 目标页面编号(从 0 开始)。如果未找到页面编号,则为 -1。
”to”: (x, y) 页面上的目标点。当前为 PDF 坐标, 即点 (0,0) 是页面的左下角。
”zoom”: (float) 缩放因子。
”dest”: (str) 仅在目标位置未提供为 “/XYZ” 或未找到页面编号时出现。
示例:
{ '__bookmark_1': {'page': 0, 'to': (0.0, 541.0), 'zoom': 0.0}, '__bookmark_2': {'page': 0, 'to': (0.0, 481.45), 'zoom': 0.0}, }
或:
{ '21154a7c20684ceb91f9c9adc3b677c40': {'page': -1, 'dest': '/XYZ 15.75 1486 0'}, ... }
所有在目录中通过键 “/Dests” 和 “/Names/Dests” 找到的名称都会被包括。
在 v1.23.6 中新增
- page_cropbox(pno)#
在 v1.17.7 中新增
仅适用于 PDF:返回未旋转的页面矩形—— 无需加载页面 (通过
Document.load_page()
)。此方法用于需要最佳性能的内部用途。- 参数:
pno (int) – 从 0 开始的页面编号。
- 返回:
Rect 页面,如
Page.rect()
,但忽略任何旋转。
- page_xref(pno)#
在 v1.17.7 中新增
仅适用于 PDF:返回页面的
xref
—— 无需加载页面 (通过Document.load_page()
)。此方法用于需要最佳性能的内部用途。
- pages(start=None[, stop=None[, step=None]])#
在 v1.16.4 中新增
一个用于页面范围的生成器。参数的含义与内置函数 range() 相同。用于类似 “for page in doc.pages(start, stop, step): …” 的表达式。
- 参数:
start (int) – 从此页面编号开始迭代。默认值为零,允许的值为
-∞ < start < page_count
。当为负数时,page_count
会 在 开始迭代之前加上。stop (int) – 在此页面编号停止迭代。默认值为
page_count
,允许的值为-∞ < stop <= page_count
。较大的值会 默默地替换 为默认值。负值会循环按相反顺序返回页面。与内置的 range() 一样,这是 不 返回的第一个页面。step (int) – 步进值。如果 start < stop,则默认为 1;如果 start > stop,则默认为 -1。不允许为零。
- 返回:
文档页面的生成器迭代器。以下是一些示例:
”doc.pages()” 返回所有页面。
”doc.pages(4, 9, 2)” 返回页面 4、6、8。
”doc.pages(0, None, 2)” 返回所有偶数页。
”doc.pages(-2)” 返回最后两页。
”doc.pages(-1, -1)” 返回所有页面,按相反顺序。
”doc.pages(-1, -10)” 总是以相反顺序返回 10 页,从最后一页开始——如果文档少于 10 页,则 重复 返回。例如,对于一个 4 页的文档,返回的页面编号依次为:3, 2, 1, 0, 3, 2, 1, 0, 3, 2, 1, 0, 3。
- convert_to_pdf(from_page=-1, to_page=-1, rotate=0)#
创建当前文档的 PDF 版本并将其写入内存。 所有文档类型 都受支持。参数与
insert_pdf()
中的含义相同。实际上,您可以限制转换为页面子集、指定页面旋转角度,并逆转页面顺序。- 参数:
from_page (int) – 要复制的第一页(从 0 开始)。默认是第一页。
to_page (int) – 要复制的最后一页(从 0 开始)。默认是最后一页。
rotate (int) – 旋转角度。默认是 0(不旋转)。应为 n * 90,其中 n 是整数(未检查)。
- 返回类型:
bytes
- 返回:
一个包含 PDF 文件图像的 Python bytes 对象。它是通过内部使用
tobytes(garbage=4, deflate=True)
创建的。参见tobytes()
。您可以直接将其输出到磁盘或将其作为 PDF 打开。以下是一些示例:>>> # 将 XPS 文件转换为 PDF >>> xps = pymupdf.open("some.xps") >>> pdfbytes = xps.convert_to_pdf() >>> >>> # 任选其一 --> >>> pdf = pymupdf.open("pdf", pdfbytes) >>> pdf.save("some.pdf") >>> >>> # 或者这样 --> >>> pdfout = open("some.pdf", "wb") >>> pdfout.tobytes(pdfbytes) >>> pdfout.close()
>>> # 将图像文件复制到 PDF 页面 >>> # 每个页面将具有图像尺寸 >>> doc = pymupdf.open() # 新建 PDF >>> imglist = [ ... 图像文件名 ...] # 例如一个目录列表 >>> for img in imglist: imgdoc=pymupdf.open(img) # 打开图像作为文档 pdfbytes=imgdoc.convert_to_pdf() # 创建一个 1 页的 PDF imgpdf=pymupdf.open("pdf", pdfbytes) doc.insert_pdf(imgpdf) # 插入图像 PDF >>> doc.save("allmyimages.pdf")
备注
该方法使用与 mutool convert CLI 相同的逻辑。在大多数情况下,这非常有效——但是,需要注意以下限制。
图像文件:完美,无检测到问题。然而,图像透明度会被忽略。如果您需要透明度(如水印),请使用
Page.insert_image()
。否则,推荐使用此方法,因为它性能更好。XPS:外观非常好。链接正常,书签(大纲)丢失,但可以轻松恢复 [9]。
EPUB, CBZ, FB2:与 XPS 相似。
SVG:中等。大致可与 svglib 相比。
- get_toc(simple=True)#
从文档的目录链创建目录(TOC)。
- 参数:
simple (bool) – 指示是否需要简单或详细的目录。如果 False,列表中的每个条目还将包含一个字典,包含每个大纲条目的 linkDest 详细信息。
- 返回类型:
list
- 返回:
一个列表的列表。每个条目的形式为 [lvl, title, page, dest]。其条目有以下含义:
lvl – 层级(正整数)。第一个条目总是 1。行中的条目要么 相等 ,要么 增加 1,或者 减少 任意数目。
title – 标题(字符串)。
page – 基于 1 的源页面编号(整数)。如果没有目标或在文档之外,则为
-1
。dest – (字典)仅在 simple=False 时包含。包含以下 TOC 项目的详细信息:
kind: 目标类型,见 链接目标类型。
file: 如果类型为
LINK_GOTOR
或LINK_LAUNCH
,则为文件名。page: 目标页面,基于 0,只有
LINK_GOTOR
或LINK_GOTO
。to: 目标页面上的位置(Point)。
zoom: 目标页面的缩放因子(浮动)。
xref: 项目的
xref
(如果没有 PDF,则为 0)。color: 项目在 PDF 中的 RGB 颜色格式
(红色,绿色,蓝色)
,或者省略(如果没有 PDF,则始终省略)。bold: 如果项目文本是粗体,则为 true,或者省略。仅限 PDF。
italic: 如果项目文本是斜体,则为 true,或者省略。仅限 PDF。
collapse: 如果子项被折叠,则为 true,或者省略。仅限 PDF。
nameddest: 如果 kind=4,目标名称。仅限 PDF。(在 1.23.7 中新增)
- xref_get_keys(xref)#
在 v1.18.7 中新增
仅限 PDF:返回由其 xref 编号提供的 PDF 字典对象的字典键。
- 参数:
xref (int) – 该
xref
。 (在 v1.18.10 中更改) 使用-1
来访问特殊字典“PDF trailer”。- 返回:
一个包含对象
xref
中字典键的元组。示例:>>> from pprint import pprint >>> import pymupdf >>> doc=pymupdf.open("pymupdf.pdf") >>> xref = doc.page_xref(0) # 页面 0 的 xref >>> pprint(doc.xref_get_keys(xref)) # 页面主键 ('Type', 'Contents', 'Resources', 'MediaBox', 'Parent') >>> pprint(doc.xref_get_keys(-1)) # trailer 的主键 ('Type', 'Index', 'Size', 'W', 'Root', 'Info', 'ID', 'Length', 'Filter') >>>
- xref_get_key(xref, key)#
在 v1.18.7 中新增
仅限 PDF:返回给定 xref 的 PDF 字典键的类型和值。
- 参数:
xref (int) – 该
xref
。在 v1.18.10 中更改: 使用-1
来访问特殊字典“PDF trailer”。key (str) – 所需的 PDF 键。必须 完全 匹配(区分大小写)
Document.xref_get_keys()
中包含的键。
- 返回类型:
tuple
- 返回:
一个元组 (type, value) 的字符串,其中 type 是以下之一:“xref”,“array”,“dict”,“int”,“float”,“null”,“bool”,“name”,“string” 或 “unknown”(应避免发生)。独立于 “type” ,键的值 始终 格式化为字符串——见下例——并且(几乎总是)忠实地反映 PDF 中存储的内容。在大多数情况下,值字符串的格式还可以提供有关键类型的线索:
“name” 总是以 “/” 斜杠开头。
“xref” 总是以 “ 0 R” 结尾。
“array” 总是用 “[…]” 括起来。
“dict” 总是用 “<<…>>” 括起来。
“bool” 或 “null” 总是等于 “true”、”false” 或 “null”。
“float” 和 “int” 以其字符串格式表示——因此不能总是区分。
“string” 被转换为 UTF-8,因此可能与 PDF 中存储的内容有所不同。例如,PDF 键 “Author” 在文件中的值可能是 “<FEFF004A006F0072006A00200058002E0020004D0063004B00690065>”,但该方法将返回
('string', 'Jorj X. McKie')
。>>> for key in doc.xref_get_keys(xref): print(key, "=" , doc.xref_get_key(xref, key)) Type = ('name', '/Page') Contents = ('xref', '1297 0 R') Resources = ('xref', '1296 0 R') MediaBox = ('array', '[0 0 612 792]') Parent = ('xref', '1301 0 R') >>> # >>> # 现在对于 PDF trailer 做同样的事情。 >>> # 它没有 xref,因此必须使用 -1。 >>> # >>> for key in doc.xref_get_keys(-1): print(key, "=", doc.xref_get_key(-1, key)) Type = ('name', '/XRef') Index = ('array', '[0 8802]') Size = ('int', '8802') W = ('array', '[1 3 1]') Root = ('xref', '8799 0 R') Info = ('xref', '8800 0 R') ID = ('array', '[<DC9D56A6277EFFD82084E64F9441E18C><DC9D56A6277EFFD82084E64F9441E18C>]') Length = ('int', '21111') Filter = ('name', '/FlateDecode') >>>
- xref_set_key(xref, key, value)#
在 v1.18.7 中新增,v1.18.13 中更改
在 v1.19.4 中更改:如果设置为 “null”,则“物理”地移除一个键。
仅限 PDF:为通过其 xref 提供的
字典
对象设置(添加、更新、删除)PDF 键的值。小心
这是一个专家功能:如果您不知道自己在做什么,存在将(部分)PDF 渲染为不可用的高风险。请参考 Adobe PDF 参考 中关于对象规范格式(第18页)以及诸如页面对象等特殊字典类型的结构。
- 参数:
xref (int) – 该
xref
。在 v1.18.13 中更改: 若要更新 PDF trailer,需指定 -1。key (str) – 所需的 PDF 键(不带前导的 “/”)。不能为空。任何有效的 PDF 键——无论是已经存在于对象中(将被覆盖)还是新的。可以使用 PDF 路径表示法,如
"Resources/ExtGState"
——这会将键"/ExtGState"
的值设置为"/Resources"
的子对象。value (str) – 键的值。它必须是一个非空字符串,并且根据所需的 PDF 对象类型,必须遵守以下规则。存在某些语法检查,但 没有类型检查 ,也没有检查其在 PDF 上是否合理,即 没有语义检查 。大小写非常重要!
xref – 必须作为
"nnn 0 R"
提供,其中 nnn 为有效的xref
编号。后缀 “0 R
” 必须存在,以便 PDF 应用程序识别为 xref。array – 类似
"[a b c d e f]"
的字符串。方括号是必需的。数组项必须至少用一个空格分隔(而不是像 Python 中的逗号)。空数组"[]"
是可能的,并且*等同于*删除该键。数组项可以是任何 PDF 对象,如字典、xref、其他数组等。与 Python 中一样,数组项可以是不同类型的。dict – 类似
"<< ... >>"
的字符串。方括号是必需的,且必须包含有效的 PDF 字典定义。空字典"<<>>"
是可能的,并且*等同于*删除该键。int – 以字符串格式表示的整数。
float – 以字符串格式表示的浮点数。PDF 不允许使用科学记数法(带有指数)。
null – 字符串
"null"
。这是 PDF 等效于 Python 的None
,并导致该键被忽略——但不一定被移除,或者在保存时通过垃圾回收移除。在 v1.19.4 中更改: 如果键不是路径层次(即不包含斜杠 “/”),则将完全移除它。bool – 字符串
"true"
或"false"
。name – 有效的 PDF 名称,前导斜杠,例如:
"/PageLayout"
。请参见 Adobe PDF 参考 第16页。string – 有效的 PDF 字符串。所有 PDF 字符串必须被括在括号中。空字符串表示为
"()"
。根据内容,可能使用以下括号:“(…)” 用于仅包含 ASCII 的文本。保留的 PDF 字符必须使用反斜杠转义,非 ASCII 字符必须使用 3 位的反斜杠转义八进制表示——包括前导零。例如:12 = 0x0C 必须编码为
014
。“<…>” 用于十六进制编码文本。每个字符必须由两个十六进制数字表示(大小写均可)。
如果不确定, 强烈推荐 使用
get_pdf_str()
!此函数会自动生成正确的括号、转义和整体格式。例如:>>> # 由于 € 符号,以下结果为 UTF-16BE BOM >>> pymupdf.get_pdf_str("Pay in $ or €.") '<feff00500061007900200069006e002000240020006f0072002020ac002e>' >>> # 对括号和非 ASCII 字符进行转义 >>> pymupdf.get_pdf_str("Prices in EUR (USD also accepted). Areas are in m².") '(Prices in EUR \\(USD also accepted\\). Areas are in m\\262.)'
- get_page_pixmap(pno: int, *, matrix: matrix_like = Identity, dpi=None, colorspace: Colorspace = csRGB, clip: rect_like = None, alpha: bool = False, annots: bool = True)#
从页面 pno (基于零)创建一个位图。调用
Page.get_pixmap()
。所有参数除了
pno
都是 仅限关键字 。- 参数:
pno (int) – 页面编号,基于零,
-∞ < pno < page_count
。- 返回类型:
- get_page_xobjects(pno)#
在 v1.16.13 中新增
在 v1.18.11 中更改
仅限 PDF:返回页面引用的所有 XObjects 的列表。
- 参数:
pno (int) – 页面编号,基于零,
-∞ < pno < page_count
。- 返回类型:
list
- 返回:
一个包含(非图像)XObjects 的列表。这些对象通常表示嵌入的(而非复制的)其他 PDF 页面。例如,
Page.show_pdf_page()
将创建这种类型的对象。该列表中的一项具有以下布局:(xref, name, invoker, bbox)
,其中:xref (int) 是 XObject 的
xref
。name (str) 是引用 XObject 的符号名称。
invoker (int) 是调用 XObject 的
xref
,如果页面直接调用它,则为零。bbox (Rect) 是 XObject 在页面上的边界框位置 未经过变换的坐标 。要获取实际的、非旋转的页面坐标,可以与页面的变换矩阵
Page.transformation_matrix
相乘。在 v1.18.11 中更改: bbox 现在以 Rect 格式返回。
- get_page_images(pno, full=False)#
仅限 PDF:返回页面直接或间接引用的所有图像的列表。
- 参数:
pno (int) – 页面编号,基于零,
-∞ < pno < page_count
。full (bool) – 是否还包括引用者的
xref
(如果是页面,则为零)。
- 返回类型:
list
- 返回:
一个包含 该页面引用的 图像的列表。每项的格式如下:
(xref, smask, width, height, bpc, colorspace, alt_colorspace, name, filter, referencer)
其中:
xref (int) 是图像对象编号
smask (int) 是其软掩码图像的对象编号
width (int) 是图像宽度
height (int) 是图像高度
bpc (int) 表示每个组件的位数(通常为 8)
colorspace (str) 是表示颜色空间的字符串(如 DeviceRGB)
alt_colorspace (str) 是根据 colorspace 的值可能的任何替代颜色空间
name (str) 是图像的符号名称
filter (str) 是图像的解码过滤器(参考 Adobe PDF 参考,第22页)。
referencer (int) 是引用者的
xref
。如果由页面直接引用,则为零。只有在 full=True 时才会存在。
备注
一般来说,这不是 实际显示的 图像列表。此方法仅解析多个 PDF 对象,以收集对嵌入图像的引用。它并不分析页面的
contents
,其中定义了所有实际的图像显示命令。要获取此信息,请使用Page.get_image_info()
。还请参阅 字典输出的结构 部分中的讨论。
- get_page_fonts(pno, full=False)#
仅限 PDF:返回页面直接或间接引用的所有字体的列表。
- 参数:
- 返回类型:
list
- 返回:
一个包含页面引用的字体的列表。每个条目格式如下:
(xref, ext, type, basefont, name, encoding, referencer),
其中:
xref (int) 是字体对象编号(如果 PDF 直接使用内置字体,则可能为零)
ext (str) 字体文件扩展名(例如 “ttf”,参见 字体文件扩展名)
type (str) 字体类型(如 “Type1” 或 “TrueType” 等)
basefont (str) 基本字体名称,
name (str) 是引用字体的符号名称
encoding (str) 如果字体的字符编码不同于其内置编码,则为字体的字符编码(参考 Adobe PDF 参考,第254页)
referencer (int 可选) 引用者的
xref
。如果由页面直接引用,则为零,否则是 XObject 的 xref。仅在 full=True 时存在。
示例:
>>> pprint(doc.get_page_fonts(0, full=False)) [(12, 'ttf', 'TrueType', 'FNUUTH+Calibri-Bold', 'R8', ''), (13, 'ttf', 'TrueType', 'DOKBTG+Calibri', 'R10', ''), (14, 'ttf', 'TrueType', 'NOHSJV+Calibri-Light', 'R12', ''), (15, 'ttf', 'TrueType', 'NZNDCL+CourierNewPSMT', 'R14', ''), (16, 'ttf', 'Type0', 'MNCSJY+SymbolMT', 'R17', 'Identity-H'), (17, 'cff', 'Type1', 'UAEUYH+Helvetica', 'R20', 'WinAnsiEncoding'), (18, 'ttf', 'Type0', 'ECPLRU+Calibri', 'R23', 'Identity-H'), (19, 'ttf', 'Type0', 'TONAYT+CourierNewPSMT', 'R27', 'Identity-H')]
备注
该列表没有重复项:
xref
、 name 和 referencer 的组合是唯一的。一般来说,这是页面实际使用字体的超集。PDF 创建者可能指定了一些全局字体列表,而每个页面只使用其中的一部分。
- get_page_text(pno, output='text', flags=3, textpage=None, sort=False)#
提取给定页面编号 pno (基于零)的页面文本。调用
Page.get_text()
。- 参数:
pno (int) – 页面编号,基于零,任何值
-∞ < pno < page_count
。
对于其他参数,请参阅页面方法。
- 返回类型:
str
- layout(rect=None, width=0, height=0, fontsize=11)#
根据给定的页面尺寸和字体大小重新分页(“重新流动”)文档。这只影响一些文档类型,如电子书和 HTML。如果不支持则会被忽略。受支持的文档在属性
is_reflowable
中为 True。- 参数:
rect (rect_like) – 所需的页面尺寸。必须是有限的,非空且起始点为 (0, 0)。
width (float) – 与 height 一起使用,作为 rect 的替代。
height (float) – 与 width 一起使用,作为 rect 的替代。
fontsize (float) – 所需的默认字体大小。
- select(s)#
仅限 PDF:仅保留文档中页码出现在列表中的页面。空的序列或超出
range(doc.page_count)
的元素将引发 ValueError。有关更多详细信息,请参见本章节底部的备注。- 参数:
s (sequence) – 要包含的页面编号序列(基于零)。不在序列中的页面将被删除(从内存中)并且直到重新打开文档才会变得可用。页面编号可以多次出现且无特定顺序: 结果文档将完全按照指定的序列反映。
备注
序列中的页面编号无需唯一或按特定顺序排列。这使得该方法成为一个多功能的工具,例如,只选择偶数页或奇数页,或满足其他标准等。
从技术层面讲,该方法始终会创建一个新的
pagetree
。处理少量页面时,使用方法
copy_page()
、move_page()
、delete_page()
会更容易。事实上,当文档包含很多页面时,它们的效率 更高 ——至少提高一个数量级。
- set_metadata(m)#
仅限 PDF:根据 m (一个 Python 字典)设置或更新文档的元数据。
- 参数:
m (dict) – 一个与 metadata 相同键的字典(见下文)。所有键都是可选的。PDF 的格式和加密方法不能设置或更改,并将被忽略。如果任何值不应包含数据,请不要指定其键或将值设置为
None
。如果使用 {},所有元数据将被清除并设置为字符串 “none”。如果您只想选择性地更改某些值,可以修改 doc.metadata 的副本并将其作为参数使用。可以指定任意的 UTF-8 编码的 Unicode 值。
(在 v1.18.4 中更改) 现在空值或 “none” 不再写入,而是完全省略。
- get_xml_metadata()#
仅限 PDF:获取文档的 XML 元数据。
- 返回类型:
str
- 返回:
文档的 XML 元数据。如果没有或不是 PDF,则返回空字符串。
- set_xml_metadata(xml)#
仅限 PDF:设置或更新文档的 XML 元数据。
- 参数:
xml (str) – 新的 XML 元数据。应为 XML 语法,但此方法不进行检查,接受任何字符串。
- set_pagelayout(value)#
新增于 v1.22.2
仅限 PDF:设置
/PageLayout
。- 参数:
value (str) – 以下字符串之一 “SinglePage”, “OneColumn”, “TwoColumnLeft”, “TwoColumnRight”, “TwoPageLeft”, “TwoPageRight”。支持小写。
- set_pagemode(value)#
新增于 v1.22.2
仅限 PDF:设置
/PageMode
。- 参数:
value (str) – 以下字符串之一 “UseNone”, “UseOutlines”, “UseThumbs”, “FullScreen”, “UseOC”, “UseAttachments”。支持小写。
- set_markinfo(value)#
新增于 v1.22.2
仅限 PDF:设置
/MarkInfo
值。- 参数:
value (dict) – 一个类似于
{"Marked": False, "UserProperties": False, "Suspects": False}
的字典。此字典包含有关 Tagged PDF 约定使用情况的信息。有关详细信息,请参见 PDF 规范。
- set_toc(toc, collapse=1)#
仅限 PDF:用提供的参数替换 完整的当前大纲 树(目录)。成功执行后,可以像平常一样通过
Document.get_toc()
或Document.outline
访问新的大纲树。与其他输出导向的方法一样,只有通过save()
(支持增量保存)时,修改才会成为永久性。此方法内部包含以下两个步骤。示例如下所示。第 1 步:删除所有现有的书签。
第 2 步:从 toc 中包含的条目创建新的目录。
- 参数:
toc (sequence) –
一个包含 所有书签条目 的列表/元组,构成新的目录。可以接受
get_toc()
的输出变体。如果要完全删除目录,指定一个空的序列或None
。每个条目必须是具有以下格式的列表。[lvl, title, page [, dest]] 其中
lvl 是项的层级(int > 0), 必须为 1 对于第一个项,且最大为前一个项的层级加 1。
title (str)是要显示的标题。假定它是 UTF-8 编码的(仅对多字节字符集相关)。
page (int)是目标页面编号 (注意:基于 1)。如果是正数,则必须在有效范围内。如果没有目标或目标是外部的,则设置为 -1。
dest (可选)是字典或数字。如果是数字,它将被解释为此条目应指向页面的高度(以点为单位)。使用字典(例如
get_toc(False)
的输出)来详细控制书签的属性,详细信息见Document.get_toc()
。
collapse (int) – (新增于 v1.16.9) 控制大纲条目初始显示折叠的层级。默认值为 1,这意味着仅显示第 1 层级,更高层级需要使用 PDF 查看器展开。要展开所有条目,指定一个较大的整数、0 或
None
。
- 返回类型:
int
- 返回:
插入或删除的条目数量。
在 v1.23.8 中更改:目标 ‘to’ 坐标现在应与
get_toc()
返回的坐标系统相同(内部会使用page.cropbox
和page.rotation_matrix
进行转换)。因此,例如set_toc(get_toc())
现在会返回未更改的目标 ‘to’ 坐标。
- outline_xref(idx)#
新增于 v1.17.7
仅限 PDF:返回大纲项的
xref
。主要用于内部用途。- 参数:
idx (int) – 在
Document.get_toc()
返回的列表中的项的索引。- 返回:
xref
。
- del_toc_item(idx)#
新增于 v1.17.7
在 v1.18.14 中更改:不再移除该项的文本,而是将其显示为灰色。
仅限 PDF:删除此目录项。这是一个高速方法,它 禁用 该项,但保持整体目录结构不变。物理上,该项仍存在于目录树中,但显示为灰色,并且不再指向任何目标。
这也意味着,您可以在需要时通过
Document.set_toc_item()
将该项重新分配到新的目标。- 参数:
idx (int) – 在
Document.get_toc()
返回的列表中的项的索引。
- set_toc_item(idx, dest_dict=None, kind=None, pno=None, uri=None, title=None, to=None, filename=None, zoom=0)#
新增于 v1.17.7
在 v1.18.6 中更改
仅限 PDF:更改由索引标识的 TOC 项目。可以更改项目的 标题、 目标、 外观 (颜色、加粗、斜体)或折叠子项,或者完全删除该项目。
如果只需要对选定的条目进行特定修改,并且想避免替换整个目录,则使用此方法。特别是在处理大型目录时,这非常有用。
- 参数:
idx (int) – 在
Document.get_toc()
创建的列表中的条目的索引。dest_dict (dict) – 新的目标。一个字典,类似于
doc.get_toc(False)
中条目的最后一个条目。建议使用此作为模板。当给定时,所有其他参数将被忽略,仅保留标题。kind (int) – 链接类型,参见 链接目标类型。如果是
LINK_NONE
,则所有其他参数将被忽略,目录项将被移除——与Document.del_toc_item()
相同。如果为 None,则仅修改标题,忽略其余参数。其他所有值将使用随后的参数创建一个新的目标字典。pno (int) – 基于 1 的页面编号,即 1 <= pno <= doc.page_count。对于 LINK_GOTO 是必需的。
uri (str) – URL 文本。对于 LINK_URI 是必需的。
title (str) – 所需的新标题。如果不更改,则为 None。
to (point_like) – (可选)指向目标页面上的坐标。对于 LINK_GOTO 有效。如果省略,则选择页面顶部附近的一个点。
filename (str) – 对于 LINK_GOTOR 和 LINK_LAUNCH 是必需的。
zoom (float) – 显示目标页面时使用的缩放因子。
示例用法: 更改 SWIG 手册的 TOC,如下所示:
折叠所有低于顶级的内容,并将关于 Python 支持的章节显示为红色、加粗和斜体:
>>> import pymupdf >>> doc=pymupdf.open("SWIGDocumentation.pdf") >>> toc = doc.get_toc(False) # 我们需要详细的 TOC >>> # 获取第 1 层级的索引和标题列表 >>> lvl1 = [(i, item[1]) for i, item in enumerate(toc) if item[0] == 1] >>> for i, title in lvl1: d = toc[i][3] # 获取目标字典 d["collapse"] = True # 折叠其下的条目 if "Python" in title: # 显示 'Python' 章节 d["color"] = (1, 0, 0) # 红色, d["bold"] = True # 加粗并且 d["italic"] = True # 斜体 doc.set_toc_item(i, dest_dict=d) # 更新此 TOC 项 >>> doc.save("NEWSWIG.pdf",garbage=3,deflate=True)
在上面的示例中,我们仅更改了文件中 1240 个 TOC 条目中的 42 个。
- bake(*, annots=True, widgets=True)#
仅限 PDF:将注释和/或小部件转换为页面的永久部分。此方法将 更改 PDF 文件。如果
widgets
为True
,则文档将不再是 “表单 PDF”。所有页面看起来相同,但不再包含注释或字段。可见部分将根据需要转换为标准文本、矢量图形或图像。
因此,该方法可能是使用
Document.convert_to_pdf()
进行 PDF 到 PDF 转换的一个有效 替代方案。请考虑到注释是复杂的对象,可能包含其可视外观下方的更多数据。例如,”Text” 和 “FileAttachment” 注释。当将注释/小部件 “烘焙” 进 PDF 时,所有底层信息(附加文件、评论、相关的 PopUp 注释等)将丢失,并在下次垃圾回收时被移除。
例如,当源页面应该在目标中完全相同但不支持注释或小部件时,可以使用此功能,例如在
Page.show_pdf_page()
中。- 参数:
annots (bool) – 是否转换注释。
widgets (bool) – 是否转换字段/小部件。执行后,文档将不再是 “表单 PDF”。
- can_save_incrementally()#
新增于 v1.16.0
检查文档是否可以增量保存。使用此方法可以在不遇到异常的情况下选择正确的选项。
- scrub(attached_files=True, clean_pages=True, embedded_files=True, hidden_text=True, javascript=True, metadata=True, redactions=True, redact_images=0, remove_links=True, reset_fields=True, reset_responses=True, thumbnails=True, xml_metadata=True)#
新增于 v1.16.14
仅限 PDF:从 PDF 中移除潜在的敏感数据。此功能灵感来自于 Adobe Acrobat 产品中的类似 “Sanitize” 功能。该过程可以通过多个选项进行配置。
- 参数:
attached_files (bool) – 搜索 ‘FileAttachment’ 注释并移除文件内容。
clean_pages (bool) – 移除页面绘制源中的所有评论。如果此选项设置为 False,则也会对 hidden_text 和 redactions 进行清理。
embedded_files (bool) – 移除嵌入的文件。
hidden_text (bool) – 移除 OCR 识别的文本和不可见文本 [14]。
javascript (bool) – 移除 JavaScript 源代码。
metadata (bool) – 移除 PDF 标准元数据。
redactions (bool) – 应用删除标记注释。
redact_images (int) – 处理图像时如何应用删除标记。可以选择 0(忽略)、1(遮盖重叠部分)或 2(移除)。
remove_links (bool) – 移除所有链接。
reset_fields (bool) – 重置所有表单字段为默认值。
reset_responses (bool) – 移除所有注释中的响应。
thumbnails (bool) – 移除页面的缩略图。
xml_metadata (bool) – 移除 XML 元数据。
- save(outfile, garbage=0, clean=False, deflate=False, deflate_images=False, deflate_fonts=False, incremental=False, ascii=False, expand=0, linear=False, pretty=False, no_new_id=False, encryption=PDF_ENCRYPT_NONE, permissions=-1, owner_pw=None, user_pw=None, use_objstms=0)#
更改于 v1.18.7
更改于 v1.19.0
更改于 v1.24.1
仅限 PDF:保存文档的 当前状态。
- 参数:
outfile (str, Path, fp) – 要保存的文件路径,
pathlib.Path
或文件对象。文件对象必须通过open(...)
或io.BytesIO()
事先创建。选择io.BytesIO()
类似于下面的Document.tobytes()
,其等同于内部创建的io.BytesIO()
的getvalue()
输出。garbage (int) –
执行垃圾回收。正值将排除 “增量” 保存。
clean (bool) – 清理并消毒内容流 [8]。对应于 “mutool clean -sc”。
deflate (bool) – 压缩(deflate)未压缩的流。
deflate_images (bool) – (v1.18.3 新增) 压缩(deflate)未压缩的图像流 [11]。
deflate_fonts (bool) – (v1.18.3 新增) 压缩(deflate)未压缩的字体文件流 [11]。
incremental (bool) – 仅保存对 PDF 的更改。排除 “garbage” 和 “linear”。此选项仅在 outfile 为字符串或
pathlib.Path
且等于Document.name
时可用。对于解密或修复后的文件以及其他某些情况,不能使用此选项。为了确保,请检查Document.can_save_incrementally()
。如果返回 false,则需要保存到新文件。ascii (bool) – 将二进制数据转换为 ASCII。
expand (int) –
解压对象。生成可以被其他程序更好读取的版本,但文件可能会更大。
0 = 无
1 = 图像
2 = 字体
255 = 所有
linear (bool) – 保存线性化版本的文档。此选项为改进互联网访问性能创建文件格式。排除 “incremental” 和 “use_objstms”。
pretty (bool) – 美化文档源,增加可读性。PDF 对象将重新格式化,以便更像
Document.xref_object()
的默认输出。no_new_id (bool) – 抑制更新文件的
/ID
字段。如果文件根本没有该字段,也抑制创建新字段。默认为False
,即每次保存都会导致文件标识的更新。permissions (int) – (v1.16.0 新增) 设置所需的权限级别。请参阅 文档权限 了解可能的值。默认是授予所有权限。
encryption (int) – (v1.16.0 新增) 设置所需的加密方法。请参阅 PDF 加密方法代码 了解可能的值。
owner_pw (str) – (v1.16.0 新增) 设置文档的所有者密码。(v1.18.3 更改) 如果未提供,则使用用户密码(如果提供)。字符串长度不得超过 40 个字符。
user_pw (str) – (v1.16.0 新增) 设置文档的用户密码。字符串长度不得超过 40 个字符。
use_objstms (int) – (v1.24.0 新增) 压缩选项,将合适的 PDF 对象定义转换为存储在其他对象的
stream
数据中。根据deflate
参数的值,转换后的对象定义将被压缩——这可以显著减少文件大小。
警告
该方法不会检查文件是否已经存在,因此不会提示确认,并会覆盖文件。作为程序员,你需要负责处理这个问题。
备注
文件大小减少
1. 使用保存选项如
garbage=3|4, deflate=True, use_objstms=1
。不要更改默认值expand=False|0, clean=False|0, incremental=False|0, linear=False|0
。 这是一种 “无损” 的文件大小减小。该方法有一个便利版本,默认设置了这些值:Document.ez_save()
,请参阅下面。“有损” 文件大小减小本质上必须放弃某些图像方面的内容,例如 (a) 移除所有图像 (b) 将图像替换为其灰度版本 (c) 降低图像分辨率。可以在 PyMuPDF Utilities “replace-image” 文件夹 找到示例。
- ez_save(*args, **kwargs)#
新增于 v1.18.11
仅限 PDF:与
Document.save()
相同,但默认选项为deflate=True, garbage=3, use_objstms=1
。
- saveIncr()#
PDF only: saves the document incrementally. This is a convenience abbreviation for doc.save(doc.name, incremental=True, encryption=PDF_ENCRYPT_KEEP).
备注
如果文档包含经过验证的签名,保存为新文件可能会导致签名无效,此时可能需要增量保存。
- tobytes(garbage=0, clean=False, deflate=False, deflate_images=False, deflate_fonts=False, ascii=False, expand=0, linear=False, pretty=False, no_new_id=False, encryption=PDF_ENCRYPT_NONE, permissions=-1, owner_pw=None, user_pw=None, use_objstms=0)#
更改于 v1.18.7
更改于 v1.19.0
更改于 v1.24.1
仅限 PDF:将 文档的当前内容 写入字节对象,而不是文件。显然,您应该注意内存要求。参数的含义与
save()
中的完全相同。章节 FAQ 包含一个示例,演示如何将此方法用作 pdfrw 的预处理器。(v1.16.0 更改) 增强的加密支持。
- 返回类型:
bytes
- 返回:
包含完整文档的字节对象。
- search_page_for(pno, text, quads=False)#
在页面编号 “pno” 上搜索 “text”。与对应的
Page.search_for()
完全相同。任何整数-∞ < pno < page_count
都是可接受的。
- insert_pdf(docsrc, from_page=-1, to_page=-1, start_at=-1, rotate=-1, links=True, annots=True, widgets=True, join_duplicates=False, show_progress=0, final=1)#
仅限 PDF:将 PDF 文档 docsrc 的页面范围 [from_page, to_page] (包括两者)复制到当前文档中。插入将从页面编号 start_at 开始。值为 -1 表示使用默认值。所有复制的页面将按照指定的旋转角度进行旋转。链接、注释和小部件可以在目标中排除,具体如下。所有页面编号为 0 基础。
- 参数:
docsrc (Document) – 已打开的 PDF Document,必须与当前文档不同,但可以引用相同的底层文件。
from_page (int) – docsrc 中的第一页编号。默认值为零。
to_page (int) – docsrc 中的最后一页编号。默认为最后一页。
start_at (int) – 第一个复制的页面,将在目标中成为页面编号 start_at。默认 -1 表示将页面范围追加到最后。如果为零,则页面范围将插入到当前第一页之前。
rotate (int) – 所有复制的页面将按提供的值旋转(度数,90 的整数倍)。
links (bool) – 选择是否应包括复制中的(内部和外部)链接。默认值为
True
。 命名 链接 (LINK_NAMED
) 和指向复制页面范围之外的内部链接 始终会被排除。annots (bool) – 选择是否应包括复制中的注释。
widgets (bool) – 选择是否应包括复制中的注释。如果为
True
且源页面中至少有一个表单字段,则目标 PDF 将变成一个表单 PDF(如果尚未是)。join_duplicates (bool) –
(新功能,版本 1.25.5) 选择如何处理源页面中的重复根字段名称。如果
widgets=False
,则此参数被忽略。默认值为
False
,这将为目标中已存在的重复源根字段添加统一的字符串。例如,如果 “name” 已经存在于目标中,源小部件的名称将更改为 “name [text]”,并附加适当选择的字符串 “text”。如果
True
,源和目标中重复名称的根字段将被转换为 “父” 对象的 “Kids”(即列表中的所有子小部件)。这会有效地将这些小部件变成 “相同” 小部件的实例:例如,如果其中一个小部件被更改,则所有实例都会自动继承该更改,无论它们显示在哪一页。show_progress (int) – (新功能,版本 1.17.7) 指定大于零的间隔大小,以便在
sys.stdout
上查看进度消息。每个间隔后,将打印类似 “Inserted 30 of 47 pages.” 的消息。final (int) – (新功能,版本 1.18.0) 控制是否在此方法后 丢弃 已复制对象的列表,默认为 True。除了从同一源 PDF 进行的多次插入的最后一次外,将其设置为 0 以节省目标文件的大小并显著加快执行速度。
备注
这是一个基于页面的方法。因此,源文档的文档级信息大多数将被忽略。例如,包括可选内容、嵌入文件、
StructureElem
、目录、页面标签、元数据、命名目标(和其他命名条目)等。如果
from_page > to_page
,页面将 按相反顺序复制。如果0 <= from_page == to_page
,则只复制一页。docsrc
的 TOC 条目 不会被复制。但是,恢复结果文档的目录是很容易的。请查看下面的示例以及程序 join.py,它可以同时合并 PDF 文档并拼接相应部分的目录。
- insert_file(infile, from_page=-1, to_page=-1, start_at=-1, rotate=-1, links=True, annots=True, show_progress=0, final=1)#
新功能,版本 v1.22.0
仅限 PDF:将任意受支持的文档添加到当前 PDF 中。打开 “infile” 作为文档,将其转换为 PDF 然后调用
Document.insert_pdf()
方法。参数与该方法相同。此功能提供了一种简单的方法,可以将图像作为完整页面附加到输出 PDF 中。
- new_page(pno=-1, width=595, height=842)#
仅限 PDF:插入一个空白页面。
- 参数:
pno (int) – 新页面应插入的页面编号。必须在 1 < pno <= page_count 范围内。特殊值 -1 和 doc.page_count 表示插入到最后一页之后。
width (float) – 页面宽度。
height (float) – 页面高度。
- 返回类型:
- 返回:
创建的页面对象。
- insert_page(pno, text=None, fontsize=11, width=595, height=842, fontname='helv', fontfile=None, color=None)#
仅限 PDF:插入一个新页面并插入一些文本。此便捷函数结合了
Document.new_page()
和(部分)Page.insert_text()
方法。- 参数:
pno (int) –
页面编号(0 基数),表示新页面插入的位置。必须在
range(-1, doc.page_count + 1)
范围内。特殊值 -1 和doc.page_count
表示插入到最后一页之后。- 变更于 v1.14.12
现在是一个位置参数
对于其他参数,请参阅上述方法。
- 返回类型:
int
- 返回:
Page.insert_text()
的结果(成功插入的行数)。
- delete_page(pno=-1)#
仅限 PDF:删除指定的页面,页面编号为
-∞ < pno < page_count - 1
。变更于 v1.18.14:支持 Python 的
del
语句。
- 参数:
pno (int) – 要删除的页面。负数从文档末尾开始计数(与索引类似)。默认值为最后一页。
- delete_pages(*args, **kwds)#
变更于 v1.18.13:更灵活地指定要删除的页面。
变更于 v1.18.14:支持 Python 的
del
语句。
仅限 PDF:删除多个页面,给定 0 基数的页面编号。
- 格式 1:使用关键字参数。表示旧格式。删除一个连续的页面范围。
“from_page”:要删除的第一页。如果省略,则为零。
“to_page”:要删除的最后一页。如果省略,则为文档的最后一页。不能小于 “from_page”。
格式 2:两个页面编号作为位置参数。与格式 1 相同处理。
格式 3:一个位置整数参数。等同于
Page.delete_page()
。格式 4:一个位置参数,类型为 list、tuple 或 range(),包含要删除的页面编号。该序列中的项目可以按任何顺序排列,并且可以包含重复项。
格式 5:(新功能,v1.18.14) 现在可以使用 Python 的
del
语句和索引/切片表示法。备注
(变更于 v1.14.17,优化于 v1.17.7) 为了保持有效的 PDF 结构,此方法和
delete_page()
还会停用指向已删除页面的目录项。此处的“停用”意味着书签将不指向任何位置,并且支持的 PDF 查看器将显示为灰色标题。总体目录结构保持不变。它还会移除所有指向已删除页面的 链接 ,此操作可能对页面较多的文档有较长的响应时间。
以下示例将删除第 500 页至第 519 页:
doc.delete_pages(500, 519)
doc.delete_pages(from_page=500, to_page=519)
doc.delete_pages((500, 501, 502, ... , 519))
doc.delete_pages(range(500, 520))
del doc[500:520]
del doc[(500, 501, 502, ... , 519)]
del doc[range(500, 520)]
对于 Adobe PDF 参考,上述操作大约需要 0.6 秒,因为剩余的 1290 页必须清除无效链接。
一般来说,此方法的性能依赖于剩余页面的数量,而不是删除页面的数量:例如,删除所有页面,只保留那 20 页,将需要更少的时间。
- copy_page(pno, to=-1)#
仅限 PDF:在文档中复制页面引用。
- 参数:
pno (int) – 要复制的页面。必须在
0 <= pno < page_count
范围内。to (int) – 要复制到的页面编号。默认将插入到最后一页之后。
备注
仅会创建页面对象的 新引用 ,而不是新的页面对象,所有复制的页面将具有相同的属性值,包括
Page.xref
。这意味着对其中一个副本的任何更改将出现在所有副本中。
- fullcopy_page(pno, to=-1)#
新功能,v1.14.17
仅限 PDF:完全复制(重复)一个页面。
- 参数:
pno (int) – 要复制的页面。必须在
0 <= pno < page_count
范围内。to (int) – 要复制到的页面编号。默认将插入到最后一页之后。
备注
与
copy_page()
不同,此方法创建一个新的页面对象(带有新的xref
),可以独立于原始页面进行更改。任何弹出窗口和 “IRT”(“响应于”)注释将 不被复制 ,以避免出现潜在的不正确情况。
- move_page(pno, to=-1)#
仅限 PDF:在文档中移动(复制并删除原始页面)一个页面。
- 参数:
pno (int) – 要移动的页面。必须在
0 <= pno < page_count
范围内。to (int) – 要插入的页面编号。默认将移动到最后一页之后。
- need_appearances(value=None)#
新功能,v1.17.4
仅限 PDF:获取或设置表单 PDF 的 /NeedAppearances 属性。引用:“(可选)一个标志,指定是否为文档中的所有小部件注释构建外观流和外观字典… 默认值:false。” 这可能有助于控制某些读取器/查看器的行为。
- 参数:
value (bool) – 设置此属性的值。如果省略或为
None
,则查询当前值。- 返回类型:
bool
- 返回:
None: 不是表单 PDF,或未定义该属性。
True / False: 属性的值(无论是刚设置的还是查询时已有的)。如果不是表单 PDF,则无效。
- get_sigflags()#
仅限 PDF:返回文档是否包含签名字段。这是一个可选的 PDF 属性:如果不存在(返回值为 -1),则无法得出结论——PDF 创建者可能只是没有使用它。
- 返回类型:
int
- 返回:
-1: 不是表单 PDF / 没有记录的签名字段 / 未找到 SigFlags。
1: 至少存在一个签名字段。
3: 包含可能会被使无效的签名,如果文件以一种修改其先前内容的方式保存(写入),而不是增量更新。
- embfile_add(name, buffer, filename=None, ufilename=None, desc=None)#
变更于 v1.14.16:位置参数“name”和“buffer”的顺序已更改,以符合其他函数的调用模式。
仅限 PDF:嵌入一个新文件。所有字符串参数(除了名称)都可以是 Unicode(在以前的版本中,只有 ASCII 正常工作)。文件内容将在有益的情况下进行压缩。
- 参数:
name (str) – 条目标识符,不能已经存在。
buffer (bytes,bytearray,BytesIO) –
文件内容。
(变更于 v1.14.13) 现在也支持 io.BytesIO。
filename (str) – 可选文件名。仅文档说明,如果为
None
,则设置为 name。ufilename (str) – 可选的 Unicode 文件名。仅文档说明,如果为
None
,则设置为 filename。desc (str) – 可选的描述。仅文档说明,如果为
None
,则设置为 name。
- 返回类型:
int
- 返回:
(变更于 v1.18.13) 该方法现在返回插入文件的
xref
。此外,文件对象将自动赋予 PDF 键/CreationDate
和/ModDate
,基于当前日期和时间。
- embfile_count()#
变更于 v1.14.16:现在这是一个方法。在以前的版本中,这是一个属性。
仅限 PDF:返回嵌入文件的数量。
- embfile_get(item)#
仅限 PDF:通过条目编号或名称检索嵌入文件的内容。如果文档不是 PDF,或无法找到条目,则会引发异常。
- 参数:
item (int,str) – 条目的索引或名称。整数必须在
range(embfile_count())
范围内。- 返回类型:
bytes
- embfile_del(item)#
变更于 v1.14.16:现在也可以通过索引删除条目。
仅限 PDF:从
/EmbeddedFiles
中删除一个条目。与往常一样,只有在将文档保存为新文件并使用适当的垃圾回收选项时,才会实际删除嵌入的文件内容(并恢复文件空间)。- 参数:
item (int/str) – 条目的索引或名称。
警告
当指定条目名称时,此函数将仅 删除第一个 具有该名称的条目。请注意,未使用 PyMuPDF 创建的 PDF 可能包含重复的名称。因此,您可能需要采取适当的预防措施。
- embfile_info(item)#
变更于 v1.18.13
仅限 PDF:通过条目的编号或名称检索嵌入文件的信息。
- 参数:
item (int/str) – 条目的索引或名称。整数必须在
range(embfile_count())
范围内。- 返回类型:
dict
- 返回:
包含以下键的字典:
name
– (str) 存储此条目的名称filename
– (str) 文件名ufilename
– (unicode) 文件名description
– (str) 描述size
– (int) 原始文件大小length
– (int) 压缩后的文件长度creationDate
– (str) 项目创建日期时间,PDF 格式modDate
– (str) 最后修改日期时间,PDF 格式collection
– (int) 关联的 PDF 组合项的xref
,如果有的话,否则为零。checksum
– (str) 存储文件内容的哈希码,作为十六进制字符串。根据 PDF 规范,它应该是 MD5,但可以看到其他哈希算法。
- embfile_names()#
仅限 PDF:返回嵌入文件名称的列表。名称的顺序等于文档中物理顺序。
- 返回类型:
list
- embfile_upd(item, buffer=None, filename=None, ufilename=None, desc=None)#
仅限 PDF:根据条目的编号或名称更改嵌入的文件。所有参数都是可选的,默认值会导致无操作。
- 参数:
item (int/str) – 条目的索引或名称。整数必须在
range(embfile_count())
范围内。buffer (bytes,bytearray,BytesIO) –
新的文件内容。
(变更于 v1.14.13) 现在也支持 io.BytesIO。
filename (str) – 新的文件名。
ufilename (str) – 新的 Unicode 文件名。
desc (str) – 新的描述。
(变更于 v1.18.13) 该方法现在返回文件对象的
xref
。- 返回类型:
int
- 返回:
文件对象的 xref。自动地,PDF 键
/ModDate
将会更新为当前日期时间。
- close()#
释放与文档相关的对象和空间分配。如果是从文件创建的,也会关闭 filename (将控制权交还给操作系统)。显式关闭文档等同于删除它,
del doc
,或将其赋值为其他对象,如doc = None
。
- xref_object(xref, compressed=False, ascii=False)#
新功能,v1.16.8
变更于 v1.18.10
仅限 PDF:返回 PDF 对象的定义源。
- 参数:
xref (int) – 对象的
xref
。变更于 v1.18.10: 值为-1
时返回 PDF trailer 源。compressed (bool) – 是否生成没有换行符或空格的紧凑输出。
ascii (bool) – 是否将二进制数据进行 ASCII 编码。
- 返回类型:
str
- 返回:
对象的定义源。
- pdf_catalog()#
新功能,v1.16.8
仅限 PDF:返回 PDF 目录(或根)对象的
xref
编号。使用该编号与Document.xref_object()
来查看其源。
- pdf_trailer(compressed=False)#
新功能,v1.16.8
仅限 PDF:返回 PDF 的 trailer 源,通常位于 PDF 文件的末尾。这相当于
Document.xref_object()
,并且 xref 参数为 -1。
- xref_stream(xref)#
新功能,v1.16.8
仅限 PDF:返回
xref
流对象的 解压缩 内容。- 参数:
xref (int) –
xref
编号。- 返回类型:
bytes
- 返回:
对象的(解压缩的)流内容。
- xref_stream_raw(xref)#
新功能,v1.16.8
仅限 PDF:返回
xref
流对象的 未修改 (尤其是 未解压缩)内容。与Document.xref_stream()
基本相同。- 返回类型:
bytes
- 返回:
对象的(原始,未修改的)流内容。
- update_object(xref, obj_str, page=None)#
新功能,v1.16.8
仅限 PDF:用提供的字符串替换
xref
对象的定义。该 xref 也可以是新的,在这种情况下,此指令将完成对象定义。如果提供了页面对象,页面的链接和注释将在之后重新加载。
- update_stream(xref, data, new=False, compress=True)#
新功能,v1.16.8
变更于 v1.19.2:添加了参数 “compress”
变更于 v1.19.6:弃用参数 “new”。现在确认对象是一个 PDF 字典对象。
替换由 xref 标识的对象的流,该对象必须是 PDF 字典。如果该对象不是
stream
,它将被转换为流。该函数会自动执行压缩操作(”deflate”),如果有益的话。- 参数:
xref (int) –
xref
编号。stream (bytes|bytearray|BytesIO) –
流的新内容。
(变更于 v1.14.13:) 现在也支持 io.BytesIO 对象。
new (bool) – 弃用,将被忽略。将在 v1.20.0 之后移除。
compress (bool) – 是否压缩插入的流。如果
True
(默认),则流将使用/FlateDecode
压缩(如果有益),否则流将按原样插入。
- 抛出:
ValueError – 如果 xref 不代表 PDF
dict
。空字典<<>>
是被接受的。所以,如果您刚创建了 xref 并想给它一个流,请先执行doc.update_object(xref, "<<>>")
,然后使用此方法插入流数据。
此方法主要(但不完全)用于操作包含 PDF 操作符语法的流(请参阅 Adobe PDF 参考 第 643 页),例如页面内容流。
如果更新内容流,请考虑使用保存参数 clean=True 来确保 PDF 操作符源和对象结构之间的一致性。
示例:假设您不再希望页面上出现某个图像。这可以通过删除相应内容源中的引用来实现——事实上:图像在重新加载页面后将消失。但页面的
resources
对象仍会显示该图像被页面引用。此保存选项将清理任何此类不匹配。
- xref_copy(source, target, *, keep=None)#
新功能,v1.19.5
仅限 PDF:使 target xref 成为 source 的精确副本。如果 source 是
stream
,那么这些数据也会被复制。- 参数:
source (int) – 源
xref
。必须是现有的 字典 对象。target (int) – 目标 xref。必须是现有的 字典 对象。如果该 xref 刚刚被创建,请确保将其初始化为具有最小规格的 PDF 字典
<<>>
。keep (list) – 可选的 target 顶级键的列表,这些键在准备复制过程中不应被删除。
- extract_image(xref)#
仅限 PDF:提取存储在文档中的图像数据和元信息。输出可以直接用于存储为图像文件、作为 PIL 输入、创建 Pixmap 等。此方法尽可能避免使用 pixmap 来呈现图像,以其原始格式(例如 JPEG)展示图像。
- 参数:
xref (int) – 图像对象的
xref
。如果不在range(1, doc.xref_length())
范围内,或该对象不是图像或发生其他错误,则返回None
,且不会引发异常。- 返回类型:
dict
- 返回:
包含以下键的字典:
ext (str) 图像类型(例如 ‘jpeg’),可用作图像文件扩展名。
smask (int) 蒙版 (/SMask) 图像的
xref
编号,或为零。width (int) 图像宽度。
height (int) 图像高度。
colorspace (int) 图像的 colorspace.n 编号。
cs-name (str) 图像的 colorspace.name。
xres (int) x 方向的分辨率。请参见
resolution
。yres (int) y 方向的分辨率。请参见
resolution
。image (bytes) 图像数据,可作为图像文件内容使用。
>>> d = doc.extract_image(1373) >>> d {'ext': 'png', 'smask': 2934, 'width': 5, 'height': 629, 'colorspace': 3, 'xres': 96, 'yres': 96, 'cs-name': 'DeviceRGB', 'image': b'\x89PNG\r\n\x1a\n\x00\x00\x00\rIHDR\x00\x00\x00\x05\ ...'} >>> imgout = open(f"image.{d['ext']}", "wb") >>> imgout.write(d["image"]) 102 >>> imgout.close()
备注
此方法与 pix = pymupdf.Pixmap(doc, xref),然后调用 pix.tobytes() 有功能重叠。主要区别在于,
extract_image
(1) 不总是提供 PNG 图像格式, (2) 对非 PNG 图像 非常 快速,(3) 通常会导致提取的图像占用更少的磁盘存储,(4) 在错误情况下返回None
(不会生成异常)。以下是同一 PDF 中的示例图像。xref 1268 是 PNG – 可比的执行时间和相同的输出:
In [23]: %timeit pix = pymupdf.Pixmap(doc, 1268);pix.tobytes() 10.8 ms ± 52.4 µs per loop (mean ± std. dev. of 7 runs, 100 loops each) In [24]: len(pix.tobytes()) Out[24]: 21462 In [25]: %timeit img = doc.extract_image(1268) 10.8 ms ± 86 µs per loop (mean ± std. dev. of 7 runs, 100 loops each) In [26]: len(img["image"]) Out[26]: 21462
xref 1186 是 JPEG –
Document.extract_image()
速度更快,并生成 更小的 输出(2.48 MB vs. 0.35 MB):In [27]: %timeit pix = pymupdf.Pixmap(doc, 1186);pix.tobytes() 341 ms ± 2.86 ms per loop (mean ± std. dev. of 7 runs, 1 loop each) In [28]: len(pix.tobytes()) Out[28]: 2599433 In [29]: %timeit img = doc.extract_image(1186) 15.7 µs ± 116 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each) In [30]: len(img["image"]) Out[30]: 371177
- extract_font(xref, info_only=False, named=None)#
v1.19.4 变更:如果
named == True
,返回一个字典。
仅限 PDF:返回嵌入字体文件的数据和相应的文件扩展名。可用于将字体存储为外部文件。该方法不会引发异常(除了检查 PDF 和有效的
xref
)。- 参数:
xref (int) – 要提取的字体的 PDF 对象编号。
info_only (bool) – 仅返回字体信息,不返回缓冲区。用于仅获取信息的目的,避免分配大型缓冲区区域。
named (bool) – 如果为 True,返回包含以下键的字典:’name’(字体基本名称),’ext’(字体文件扩展名),’type’(字体类型),’content’(字体文件内容)。
- 返回类型:
tuple,dict
- 返回:
一个元组
(basename, ext, type, content)
,其中 ext 是 3 字节的建议文件扩展名 (str),basename 是字体的名称 (str),type 是字体的类型(例如 “Type1”),content 是包含字体文件内容的字节对象(或 b””)。对于可能的扩展值及其含义,请参阅 字体文件扩展名。错误时返回详细信息:("", "", "", b"")
– 无效的 xref 或 xref 不是(有效的)字体对象。(basename, "n/a", "Type1", b"")
– basename 未嵌入,因此无法提取。这适用于例如 PDF Base 14 字体 和 Type 3 字体。
示例:
>>> # 将字体存储为外部文件 >>> name, ext, _, content = doc.extract_font(4711) >>> # 假设 content 不是 None: >>> ofile = open(name + "." + ext, "wb") >>> ofile.write(content) >>> ofile.close()
警告
basename
会保持从 PDF 返回,可能包含一些字符(如空格),这些字符可能不适合您的操作系统的文件名。请采取适当的措施。备注
返回的 basename 通常 不是 原始文件名,但可能与之有某些相似之处。
如果参数
named == True
,则返回一个包含以下键的字典:{'name': 'T1', 'ext': 'n/a', 'type': 'Type3', 'content': b''}
。
- has_links()#
- has_annots()#
v1.18.7 新增
仅限 PDF:检查文档中是否存在链接或注释。
- 返回:
True / False。与字段不同,字段存储在 PDF 文档的中央位置,而链接或注释的存在只能通过解析每个页面来检测。这些方法经过优化,可高效执行,并且如果在某个页面找到 True,则会立即返回。但如果 PDF 包含数千页,并且未找到链接或注释,则可能需要较长时间 [13] 。
- subset_fonts(verbose=False, fallback=False)#
仅限 PDF:分析文档中的字体是否可用于文本,并检查是否可以缩小字体大小。如果字体支持且可以减少大小,则会用仅包含部分字符的字体版本替换原字体。
请在保存文档之前立即使用此方法。
- 参数:
verbose (bool) – 是否向标准输出打印进度信息。目前仅在
fallback
为True
时有效。fallback (bool) – 是否使用已弃用的算法,该算法依赖于 fontTools (必须安装此包)。如果使用推荐值
False
(默认),则会使用 MuPDF 的原生函数 —— 速度快得多 ,并且支持更多种类的字体。在此情况下,无需安装fontTools
。
在创建包含大字体(如亚洲字符集)的新 PDF 时,此方法的优化效果最明显。例如,使用 Story 类或方法
Page.insert_htmlbox()
时,可能会自动包含多个字体,而程序员对此可能并不知情。在这些情况下,实际使用的 Unicode 字符通常远少于字体可用的字形数量。使用此方法可以轻松减少嵌入字体的大小,从几 MB 级别减少到几十 KB。
创建字体子集后,PDF 可能会遗留大量未使用的 PDF 对象(“幽灵对象”)。因此,在保存文件时,请务必进行压缩和垃圾回收。建议使用
Document.ez_save()
。Show/hide history
v1.18.7 新增
v1.18.9 变更
v1.24.2 变更,改为使用 MuPDF 的原生函数。
- journal_enable()#
v1.19.0 新增
仅限 PDF:启用日志记录。在开始记录操作之前,请先调用此方法。
- journal_start_op(name)#
v1.19.0 新增
仅限 PDF:启动一个日志操作,并使用字符串
"name"
作为标识。对于启用了日志记录的 PDF,如果未启动操作,则更新将失败。
- journal_stop_op()#
v1.19.0 新增
仅限 PDF:停止当前操作。从开始到停止之间的所有更新都属于同一个工作单元,并将在撤销/重做时一同应用。
- journal_position()#
v1.19.0 新增
仅限 PDF:返回当前操作编号及总操作数。
- 返回:
一个元组
(step, steps)
,其中 step 是当前操作编号,steps 是日志中的总操作数。如果 step 为 0,表示当前位于日志顶部;如果 step 等于 steps,表示当前位于日志底部。
在执行撤销或重做以外的任何更新时,当前操作之后的所有日志条目都会被删除,新更新将成为日志中的最新条目。被删除的日志条目对应的更新将被永久丢失。
- journal_op_name(step)#
v1.19.0 新增
仅限 PDF:返回编号为 step 的操作名称。
- journal_can_do()#
v1.19.0 新增
仅限 PDF:检查是否可以从当前日志位置执行前进(”redo”)或后退(”undo”)操作。
- 返回:
一个字典
{"undo": bool, "redo": bool}
。如果值为True
,则相应的方法可用。
- journal_undo()#
v1.19.0 新增
仅限 PDF:撤销(undo)日志中的当前步骤。此操作会向日志的顶部移动。
- journal_redo()#
v1.19.0 新增
仅限 PDF:重做(redo)日志中的当前步骤。此操作会向日志的底部移动。
- journal_save(filename)#
v1.19.0 新增
仅限 PDF:将日志保存到文件。
- 参数:
filename (str,fp) – 可以是字符串格式的文件名,也可以是以
"wb"
打开的文件对象(或io.BytesIO()
对象)。
- journal_load(filename)#
v1.19.0 新增
仅限 PDF:从文件加载日志,并为文档启用日志记录。如果日志记录已启用,则会引发异常。
- 参数:
filename (str,fp) – 日志文件的名称(字符串),或以
"rb"
打开的文件对象(或io.BytesIO()
对象)。
- save_snapshot()#
v1.19.0 新增
仅限 PDF:保存文档的“快照”。这是一种特殊的增量保存格式的 PDF 文档,兼容日志记录,因此不提供任何保存选项。新建文档无法保存快照。
这是一个正常的 PDF 文档,没有任何使用限制。如果未进行任何更改,它可以与日志一起使用,以执行撤销 / 重做操作或继续更新。
- is_closed#
如果文档仍然打开,则值为 False。如果文档已关闭,则大多数其他属性和方法都将被删除 / 禁用。此外,所有引用此文档的 Page 对象(即通过
Document.load_page()
创建的页面)及其相关对象也将无法使用。 出于参考目的,Document.name
仍然存在,并包含原始文档的文件名(如果适用)。- Type:
bool
- is_dirty#
如果这是一个 PDF 文档且包含未保存的更改,则值为 True,否则为 False。
- Type:
bool
- is_pdf#
如果这是一个 PDF 文档,则值为 True,否则为 False。
- Type:
bool
- is_form_pdf#
如果文档不是 PDF 或者没有表单字段,则值为 False。否则,返回根表单字段(无父级字段)的数量。
(v1.16.4 变更) 现在返回总的(根)表单字段数量。
- Type:
bool,int
- is_reflowable#
如果文档具有可变页面布局(如电子书或 HTML),则值为 True。在这种情况下,可以在文档创建(打开)时或通过
layout()
方法设置所需的页面尺寸。- Type:
bool
- is_repaired#
v1.18.2 新增
如果 PDF 在打开时因结构问题被修复,则值为 True。对于非 PDF 文档,始终为 False。 如果该值为 True,则详细信息存储在
TOOLS.mupdf_warnings()
中,并且Document.can_save_incrementally()
将返回 False。- Type:
bool
- is_fast_webaccess#
v1.22.2 新增
如果 PDF 采用线性化格式,则值为 True。对于非 PDF 文档,值为 False。
- Type:
bool
- markinfo#
v1.22.2 新增
一个字典,指示
/MarkInfo
值。如果未指定,则返回空字典。对于非 PDF 文档,返回None
。- Type:
dict
- pagemode#
v1.22.2 新增
一个字符串,包含
/PageMode
值。如果未指定,则返回默认值"UseNone"
。对于非 PDF 文档,返回None
。- Type:
str
- pagelayout#
v1.22.2 新增
一个字符串,包含
/PageLayout
值。如果未指定,则返回默认值"SinglePage"
。对于非 PDF 文档,返回None
。- Type:
str
- version_count#
v1.22.2 新增
一个整数,表示文档中存在的版本数量。如果不是 PDF,则返回 0,否则返回增量保存次数加 1。
- Type:
int
- needs_pass#
指示文档是否受密码保护以限制访问。该指示器在 即使文档已通过身份验证 后仍保持不变。如果值为 True,则无法进行增量保存。
- Type:
bool
- is_encrypted#
该指示器初始值等于
Document.needs_pass
。成功身份验证后,该值会被设置为 False 以反映当前状态。- Type:
bool
- permissions#
v1.16.0 变更:该属性现在是一个包含位指示器的整数,之前是一个字典。
包含访问文档的权限。该值是一个整数,其中各个位表示不同的权限。例如,如果 doc.permissions & pymupdf.PDF_PERM_MODIFY > 0,则可以修改文档。 详见 文档权限。
- Type:
int
- metadata#
包含文档的元数据,格式为 Python 字典。如果 is_encrypted=True 且 needs_pass=True,则返回
None
。 键包括 format、encryption、title、author、subject、keywords、creator、producer、creationDate、modDate、trapped,其值均为字符串或None
。对于 PDF 文档,除 format 和 encryption 之外,键名对应于 PDF 的标准元数据键,例如 /Creator、/Producer、/CreationDate、/ModDate、/Title、/Author、/Subject、/Trapped 和 /Keywords。
format 表示文档格式(如
'PDF-1.6'
、'XPS'
、'EPUB'
)。encryption 指示加密方式,可能为
None
(未加密)或加密算法名称(如'Standard V4 R4 128-bit RC4'
)。即使 needs_pass=False,文档仍可能受到部分权限限制,可通过Document.permissions
检查具体权限。如果日期字段包含有效数据(这并不总是保证的),则采用 PDF 专用时间戳格式
"D:<TS><TZ>"
,其中:<TS>
是 12 位 ISO 格式时间戳 YYYYMMDDhhmmss ( YYYY - 年, MM - 月, DD - 日, hh - 小时, mm - 分钟, ss - 秒)。<TZ>
是时区值(相对 GMT 的时间偏移量),格式为+hh'mm'
或-hh'mm'
。
例如,巴拉圭的时间戳可能为
"D:20150415131602-04'00'"
,表示 2015 年 4 月 15 日 13:16:02(当地时间:亚松森)。
- Type:
dict
- name#
包含 Document 创建时的 文件名 或 文件类型。
- Type:
str
- page_count#
文档的总页数。如果文档没有页面,则返回 0。可以使用
len(doc)
获取相同的结果。- Type:
int
- chapter_count#
v1.17.0 新增
文档中的章节数。对于支持章节的文档格式(目前仅 EPUB)有效,始终至少为 1。其他格式返回 1。
- Type:
int
- last_location#
v1.17.0 新增
记录文档的最后位置,格式为
(chapter, pno)
。仅适用于支持章节的格式(目前仅 EPUB)。 其他格式返回(0, page_count - 1)
,如果文档无页面,则返回(0, -1)
。- Type:
tuple(int, int)
- FormFonts#
包含在 /AcroForm 对象中定义的表单字段字体名称的列表。如果不是 PDF,则返回
None
。- Type:
list
备注
对于修改 PDF 结构的方法(如
insert_pdf()
、select()
、copy_page()
、delete_page()
等),请注意,程序中的对象或属性可能会失效或变成孤立对象。例如:Page 对象及其子对象(链接、注释、小部件)可能会变得无效。
存储旧页面计数的变量可能需要更新。
目录结构等数据可能需要重新生成。
请务必保持相关变量的更新,或删除无效对象。详见 确保 PyMuPDF 中重要对象的一致性。
This class represents a document. It can be constructed from a file or from memory.
There exists the alias open for this class, i.e. pymupdf.Document(...)
and pymupdf.open(...)
do exactly the same thing.
For details on embedded files refer to Appendix 3.
备注
Starting with v1.17.0, a new page addressing mechanism for EPUB files only is supported. This document type is internally organized in chapters such that pages can most efficiently be found by their so-called “location”. The location is a tuple (chapter, pno) consisting of the chapter number and the page number in that chapter. Both numbers are zero-based.
While it is still possible to locate a page via its (absolute) number, doing so may mean that the complete EPUB document must be laid out before the page can be addressed. This may have a significant performance impact if the document is very large. Using the page’s (chapter, pno) prevents this from happening.
To maintain a consistent API, PyMuPDF supports the page location syntax for all file types – documents without this feature simply have just one chapter. Document.load_page()
and the equivalent index access now also support a location argument.
There are a number of methods for converting between page numbers and locations, for determining the chapter count, the page count per chapter, for computing the next and the previous locations, and the last page location of a document.
Method / Attribute |
Short Description |
---|---|
PDF only: make new optional content configuration |
|
PDF only: add new optional content group |
|
gain access to an encrypted document |
|
PDF only: make annotations / fields permanent content |
|
check if incremental save is possible |
|
number of pages in chapter |
|
close the document |
|
write a PDF version to memory |
|
PDF only: copy a page reference |
|
PDF only: remove a single TOC item |
|
PDF only: delete a page |
|
PDF only: delete multiple pages |
|
PDF only: add a new embedded file from buffer |
|
PDF only: number of embedded files |
|
PDF only: delete an embedded file entry |
|
PDF only: extract an embedded file buffer |
|
PDF only: metadata of an embedded file |
|
PDF only: list of embedded files |
|
PDF only: change an embedded file |
|
PDF only: extract a font by |
|
PDF only: extract an embedded image by |
|
PDF only: |
|
retrieve page location after laid out document |
|
PDF only: duplicate a page |
|
PDF only: lists of OCGs in ON, OFF, RBGroups |
|
PDF only: list of optional content configurations |
|
PDF only: get OCG /OCMD xref of image / form xobject |
|
PDF only: info on all optional content groups |
|
PDF only: retrieve definition of an |
|
PDF only: list of fonts referenced by a page |
|
PDF only: list of images referenced by a page |
|
PDF only: list of page label definitions |
|
PDF only: get page numbers having a given label |
|
create a pixmap of a page by page number |
|
extract the text of a page by page number |
|
PDF only: list of XObjects referenced by a page |
|
PDF only: determine signature state |
|
extract the table of contents |
|
PDF only: read the XML metadata |
|
PDF only: check if PDF contains any annots |
|
PDF only: check if PDF contains any links |
|
PDF only: insert a new page |
|
PDF only: insert pages from another PDF |
|
PDF only: insert pages from arbitrary document |
|
PDF only: which journal actions are possible |
|
PDF only: enables journalling for the document |
|
PDF only: load journal from a file |
|
PDF only: return name of a journalling step |
|
PDF only: return journalling status |
|
PDF only: redo current operation |
|
PDF only: save journal to a file |
|
PDF only: start an “operation” giving it a name |
|
PDF only: end current operation |
|
PDF only: undo current operation |
|
PDF only: list of optional content intents |
|
re-paginate the document (if supported) |
|
read a page |
|
create a page pointer in reflowable documents |
|
PDF only: move a page to different location in doc |
|
PDF only: get/set |
|
PDF only: insert a new empty page |
|
return (chapter, pno) of following page |
|
PDF only: |
|
PDF only: the unrotated page rectangle |
|
PDF only: |
|
iterator over a page range |
|
PDF only: |
|
PDF only: trailer source |
|
return (chapter, pno) of preceding page |
|
PDF only: provide a new copy of a page |
|
PDF only: Convert destination names into a Python dict |
|
PDF only: save the document |
|
PDF only: save the document incrementally |
|
PDF only: remove sensitive data |
|
search for a string on a page |
|
PDF only: select a subset of pages |
|
PDF only: set OCG visibility temporarily |
|
PDF only: mass changing OCG states |
|
PDF only: set the MarkInfo values |
|
PDF only: set the metadata |
|
PDF only: attach OCG/OCMD to image / form xobject |
|
PDF only: create or update an |
|
PDF only: add/update page label definitions |
|
PDF only: set the PageMode |
|
PDF only: set the PageLayout |
|
PDF only: change a single TOC item |
|
PDF only: set the table of contents (TOC) |
|
PDF only: create or update document XML metadata |
|
PDF only: create font subsets |
|
PDF only: activate OC configuration |
|
PDF only: writes document to memory |
|
PDF only: copy a PDF dictionary to another |
|
PDF only: get the value of a dictionary key |
|
PDF only: list the keys of object at |
|
PDF only: get the definition source of |
|
PDF only: set the value of a dictionary key |
|
PDF only: raw stream source at |
|
PDF only: |
|
number of chapters |
|
PDF only: list of global widget fonts |
|
has document been closed? |
|
PDF only: has document been changed yet? |
|
document (still) encrypted? |
|
is PDF linearized? |
|
is this a Form PDF? |
|
is this a PDF? |
|
is this a reflowable document? |
|
PDF only: has this PDF been repaired during open? |
|
(chapter, pno) of last page |
|
metadata |
|
PDF MarkInfo value |
|
filename of document |
|
require password to access data? |
|
first Outline item |
|
number of pages |
|
permissions to access the document |
|
PDF PageMode value |
|
PDF PageLayout value |
|
PDF count of versions |
Class API
备注
For methods that change the structure of a PDF (insert_pdf()
, select()
, copy_page()
, delete_page()
and others), be aware that objects or properties in your program may have been invalidated or orphaned. Examples are Page objects and their children (links, annotations, widgets), variables holding old page counts, tables of content and the like. Remember to keep such variables up to date or delete orphaned objects. Also refer to 确保 PyMuPDF 中重要对象的一致性.
set_metadata()
例子#
set_metadata()
Example
清除元数据。如果出于隐私或数据保护考虑执行此操作,请确保将文档保存为新文件,并设置 garbage > 0。这样,旧的 /Info 对象也会被物理删除。在这种情况下,您可能还希望清除由多个 PDF 编辑器插入的任何 XML 元数据:
>>> import pymupdf
>>> doc = pymupdf.open("pymupdf.pdf")
>>> doc.metadata # 查看当前的元数据
{'producer': 'rst2pdf, reportlab', 'format': 'PDF 1.4', 'encryption': None, 'author':
'Jorj X. McKie', 'modDate': "D:20160611145816-04'00'", 'keywords': 'PDF, XPS, EPUB, CBZ',
'title': 'The PyMuPDF Documentation', 'creationDate': "D:20160611145816-04'00'",
'creator': 'sphinx', 'subject': 'PyMuPDF 1.9.1'}
>>> doc.set_metadata({}) # 清除所有字段
>>> doc.metadata # 再次查看,验证修改结果
{'producer': 'none', 'format': 'PDF 1.4', 'encryption': None, 'author': 'none',
'modDate': 'none', 'keywords': 'none', 'title': 'none', 'creationDate': 'none',
'creator': 'none', 'subject': 'none'}
>>> doc.del_xml_metadata() # 清除任何 XML 元数据
>>> doc.save("anonymous.pdf", garbage = 4) # 保存匿名化后的文档
Clear metadata information. If you do this out of privacy / data protection concerns, make sure you save the document as a new file with garbage > 0. Only then the old /Info object will also be physically removed from the file. In this case, you may also want to clear any XML metadata inserted by several PDF editors:
>>> import pymupdf
>>> doc=pymupdf.open("pymupdf.pdf")
>>> doc.metadata # look at what we currently have
{'producer': 'rst2pdf, reportlab', 'format': 'PDF 1.4', 'encryption': None, 'author':
'Jorj X. McKie', 'modDate': "D:20160611145816-04'00'", 'keywords': 'PDF, XPS, EPUB, CBZ',
'title': 'The PyMuPDF Documentation', 'creationDate': "D:20160611145816-04'00'",
'creator': 'sphinx', 'subject': 'PyMuPDF 1.9.1'}
>>> doc.set_metadata({}) # clear all fields
>>> doc.metadata # look again to show what happened
{'producer': 'none', 'format': 'PDF 1.4', 'encryption': None, 'author': 'none',
'modDate': 'none', 'keywords': 'none', 'title': 'none', 'creationDate': 'none',
'creator': 'none', 'subject': 'none'}
>>> doc.del_xml_metadata() # clear any XML metadata
>>> doc.save("anonymous.pdf", garbage = 4) # save anonymized doc
set_toc()
演示#
set_toc()
Demonstration
这展示了如何修改或添加目录。也可以查看 import.py 和 export.py 示例目录中的示例。
>>> import pymupdf
>>> doc = pymupdf.open("test.pdf")
>>> toc = doc.get_toc()
>>> for t in toc: print(t) # 显示当前目录
[1, 'The PyMuPDF Documentation', 1]
[2, 'Introduction', 1]
[3, 'Note on the Name fitz', 1]
[3, 'License', 1]
>>> toc[1][1] += " modified by set_toc" # 修改内容
>>> doc.set_toc(toc) # 替换目录树
3 # 插入了 3 个书签
>>> for t in doc.get_toc(): print(t) # 验证修改是否成功
[1, 'The PyMuPDF Documentation', 1]
[2, 'Introduction modified by set_toc', 1] # <<< 这里已更改
[3, 'Note on the Name fitz', 1]
[3, 'License', 1]
This shows how to modify or add a table of contents. Also have a look at import.py and export.py in the examples directory.
>>> import pymupdf
>>> doc = pymupdf.open("test.pdf")
>>> toc = doc.get_toc()
>>> for t in toc: print(t) # show what we have
[1, 'The PyMuPDF Documentation', 1]
[2, 'Introduction', 1]
[3, 'Note on the Name fitz', 1]
[3, 'License', 1]
>>> toc[1][1] += " modified by set_toc" # modify something
>>> doc.set_toc(toc) # replace outline tree
3 # number of bookmarks inserted
>>> for t in doc.get_toc(): print(t) # demonstrate it worked
[1, 'The PyMuPDF Documentation', 1]
[2, 'Introduction modified by set_toc', 1] # <<< this has changed
[3, 'Note on the Name fitz', 1]
[3, 'License', 1]
insert_pdf()
例子#
insert_pdf()
Examples
(1) 合并两个文档并包括它们的目录(TOC):
>>> doc1 = pymupdf.open("file1.pdf") # 必须是 PDF 文件
>>> doc2 = pymupdf.open("file2.pdf") # 必须是 PDF 文件
>>> pages1 = len(doc1) # 保存 doc1 的页面数
>>> toc1 = doc1.get_toc(False) # 保存 TOC 1
>>> toc2 = doc2.get_toc(False) # 保存 TOC 2
>>> doc1.insert_pdf(doc2) # 将 doc2 插入到 doc1 的末尾
>>> for t in toc2: # 增加 toc2 页码
t[2] += pages1 # 增加原 doc1 的页面数
>>> doc1.set_toc(toc1 + toc2) # 现在结果包含总的 TOC
显然,在更一般的情况下可以找到类似的方式。只需确保目录中的层级顺序不会增加超过一级。在 toc2 部分前后插入虚拟书签可以修复此类情况。一个现成的 GUI(wxPython)解决方案可以在 join.py 示例目录中找到。
(2) 更多示例:
>>> # 插入 doc2 的 5 页,其中 doc2 的第 21 页变为 doc1 的第 15 页
>>> doc1.insert_pdf(doc2, from_page=21, to_page=25, start_at=15)
>>>
>>> # 相同示例,但页面被旋转并逆序复制
>>> doc1.insert_pdf(doc2, from_page=25, to_page=21, start_at=15, rotate=90)
>>>
>>> # 将复制的页面插入到 doc1 前面
>>> doc1.insert_pdf(doc2, from_page=21, to_page=25, start_at=0)
(1) Concatenate two documents including their TOCs:
>>> doc1 = pymupdf.open("file1.pdf") # must be a PDF
>>> doc2 = pymupdf.open("file2.pdf") # must be a PDF
>>> pages1 = len(doc1) # save doc1's page count
>>> toc1 = doc1.get_toc(False) # save TOC 1
>>> toc2 = doc2.get_toc(False) # save TOC 2
>>> doc1.insert_pdf(doc2) # doc2 at end of doc1
>>> for t in toc2: # increase toc2 page numbers
t[2] += pages1 # by old len(doc1)
>>> doc1.set_toc(toc1 + toc2) # now result has total TOC
Obviously, similar ways can be found in more general situations. Just make sure that hierarchy levels in a row do not increase by more than one. Inserting dummy bookmarks before and after toc2 segments would heal such cases. A ready-to-use GUI (wxPython) solution can be found in script join.py of the examples directory.
(2) More examples:
>>> # insert 5 pages of doc2, where its page 21 becomes page 15 in doc1
>>> doc1.insert_pdf(doc2, from_page=21, to_page=25, start_at=15)
>>> # same example, but pages are rotated and copied in reverse order
>>> doc1.insert_pdf(doc2, from_page=25, to_page=21, start_at=15, rotate=90)
>>> # put copied pages in front of doc1
>>> doc1.insert_pdf(doc2, from_page=21, to_page=25, start_at=0)
其他例子#
Other Examples
从 PDF 中提取所有页面引用的图像并保存为单独的 PNG 文件:
for i in range(doc.page_count):
imglist = doc.get_page_images(i)
for img in imglist:
xref = img[0] # xref 编号
pix = pymupdf.Pixmap(doc, xref) # 从图像创建 pixmap
if pix.n - pix.alpha < 4: # 可以保存为 PNG 格式
pix.save("p%s-%s.png" % (i, xref))
else: # CMYK: 必须先转换
pix0 = pymupdf.Pixmap(pymupdf.csRGB, pix)
pix0.save("p%s-%s.png" % (i, xref))
pix0 = None # 释放 Pixmap 资源
pix = None # 释放 Pixmap 资源
旋转 PDF 的所有页面:
>>> for page in doc: page.set_rotation(90)
Extract all page-referenced images of a PDF into separate PNG files:
- for i in range(doc.page_count):
imglist = doc.get_page_images(i) for img in imglist:
xref = img[0] # xref number pix = pymupdf.Pixmap(doc, xref) # make pixmap from image if pix.n - pix.alpha < 4: # can be saved as PNG
pix.save(“p%s-%s.png” % (i, xref))
- else: # CMYK: must convert first
pix0 = pymupdf.Pixmap(pymupdf.csRGB, pix) pix0.save(“p%s-%s.png” % (i, xref)) pix0 = None # free Pixmap resources
pix = None # free Pixmap resources
Rotate all pages of a PDF:
>>> for page in doc: page.set_rotation(90)
Footnotes