PDF文件结构Word文件下载.docx
《PDF文件结构Word文件下载.docx》由会员分享,可在线阅读,更多相关《PDF文件结构Word文件下载.docx(19页珍藏版)》请在冰豆网上搜索。
![PDF文件结构Word文件下载.docx](https://file1.bdocx.com/fileroot1/2023-1/24/0c3d2ca3-7fa9-49ef-a10b-51fcfa0986be/0c3d2ca3-7fa9-49ef-a10b-51fcfa0986be1.gif)
上面这个交叉引用表一共有3个子段,分别有1个,1个,3个对象,第一个子段的对象不可用,其余子段对象可用。
4.trailer:
通过trailer可以快速的找到交叉引用表的位置,进而可以精确定位每一个对象;
还可以通过它本身的字典还可以获取文件的一些全局信息(作者,关键字,标题等),加密信息,等等。
具体形式如下:
trailer
<
<
key1
value1
key2
value2
key3
value3
…
>
>
startxref
553
%%EOF
trailer后面紧跟一个字典,包含若干键-值对。
具体含义如下:
键
值类型
值说明
Size
整形数字
所有间接对象的个数。
一个PDF文件,如果被更新过,则会有多个对象集合、交叉引用表、trailer,最后一个trailer的这个字段记录了之前所有对象的个数。
这个值必须是直接对象。
Prev
当文件有多个对象集合、交叉引用表和trailer时,才会有这个键,它表示前一个相对于文件头的偏移位置。
Root
字典
Catalog字典(文件的逻辑入口点)的对象号。
必须是间接对象。
Encrypt
文档被保护时,会有这个字段,加密字典的对象号。
Info
存放文档信息的字典,必须是间接对象。
ID
数组
文件的ID
startxref:
后面的数字表示最后一个交叉引用表相对于文件起始位置的偏移量。
%%EOF
:
文件结束符.
一个PDF文件,都会有上面这样的结构(线性化优化的PDF例外,这个后面单独说)。
实际一个pdf文件是很复杂的,但是上面几个部分是确定的,只能多不能少.了解了PDF文件的物理结构,就可以提取出一个一个的对象了.PDF中的对象有8种:
1.booleam
用关键字true或false表示,可以是array对象的一个元素,或dictionary对象的一个条目.也可以用在PostScript计算函数里面,做为if或ifesle的一个条件。
2.numeric
包括整形和实型,不支持非十进制数字,不支持指数形式的数字.
例:
1)整数
123
4567
+111
-2
范围:
正2的31次方-1到负的2的31次方
2)实数
12.3
0.8
+6.3
-4.01
-3.
+.03
±
3.403
×
10的38次方
1.175
10的-38次方
注意:
如果整数超过表示范围将转化成实数,如果实数超过范围就出错了
3.string
由一系列0-255之间的字节组成,一个string总长度不能超过65535.string有以下两种方式:
1)
直接字串
由()包含起来的一个字串,中间可以使用转义符"
/"
.
(abc)
表示abc
(a//)
表示a/
转义符的定义如下:
转义字符
含义
/n
换行
/r
回车
/t
水平制表符
/b
退格
/f
换页(Formfeed(FF))
/(
左括号
/)
右括号
//
反斜杠
/ddd
八进制形式的字符
2)
十六进制字串
由<
包含起来的一个16进制串,两位表示一个字符,不足两位用0补齐
Aabb>
表示AA和BB两个字符
AAB>
表示AA和B0两个字符
4.name
由一个前导/和后面一系列字符组成,最大长度为127.和string不同的是,name是不可分割的和唯一的,不可分割就是说一个name对象就是一个原子,比如/name,不能说n就是这个name的一个元素;
唯一就是指两个相同的name一定代表同一个对象.从pdf1.2开始,除了ascii的0,别的都可以用一个#加两个十六进制的数字表示.
/name
表示name
/name#20is
表示nameis
/name#200
表示name0
5.array
用[]包含的一组对象,可以是任何pdf对象(包括array).虽然pdf只支持一维array,但可以通过array的嵌套实现任意维数的array(但是一个array的元素不能超过8191)
[549
3.14
false
(Ralph)
/SomeName]
6.Dictionary
用"
"
和"
包含的若干组条目,每组条目都由key和value组成,其中key必须是name对象,并且一个dictionary内的key是唯一的;
value可以是任何pdf的合法对象(包括dictionary对象).
/IntegerItem
12
/StringItem
(a
string)
/Subdictionary
/Item1
0.4
/Item2
true
/LastItem
(not!
)
/VeryLastItem
(OK)
7.stream
由一个字典,和紧跟其后面的一组关键字stream和endstream以及这组关键字中间包含一系列字节组成.内容和string很相似,但有区别:
stream可以分几次读取,分开使用不同的部分,string必须作为一个整体一次全部读取使用;
string有长度限制,但stream却没有这个限制.一般较大的数据都用stream表示.
需要注意的是,Stream必须是间接对象,并且stream的字典必须是直接对象。
从1.2规范以后,stream可以以外部文件形式存在,这种情况下,解析PDF的时候stream和endstream之间的内容就被忽略掉。
dictionary
stream
data
…
endstream
stream字典中常用的字段如下:
字段名
类型
值
Length
整形
(必须)关键字stream和endstream之间的数据长度,endstream之前可能会有一个多余的EOL标记,这个不计算在数据的长度中。
Filter
名字
或
(可选)Stream的编码算法名称(列表)。
如果有多个,则数组中的编码算法列表顺序就是数据被编码的顺序。
DecodeParms
字典
(可选)一个参数字典或由参数字典组成的一个数组,供Filter使用。
如果仅有一个Filter并且这个Filter需要参数,除非这个Filter的所有参数都已经给了默认值,否则的话DecodeParms必须设置给Filter。
如果有多个Filter,并且任意一个Filter使用了非默认的参数,
DecodeParms
必须是个数组,每个元素对应一个Filter的参数列表(如果某个Filter无需参数或所有参数都有了默认值,就用空对象代替)。
如果没有Filter需要参数,或者所有Filter的参数都有默认值,DecodeParms
就被忽略了。
F
文件标识
(可选)保存stream数据的文件。
如果有这个字段,stream和endstream就被忽略,FFilter将会代替Filter,FDecodeParms将代替DecodeParms。
Length字段还是表示stream和endstream之间数据的长度,但是通常此刻已经没有数据了,长度是0.
FFilter
(可选)和filter类似,针对外部文件。
FDecodeParms
(可选)和DecodeParams类似,针对外部文件。
8.NULL
用null表示,代表空.如果一个key的值为null,则这个key可以被忽略;
如果引用一个不存在的object则等价于引用一个空对象.
(略)
以上八种对象是按照对象内涵来分的,如果按照对象的使用规则来说,对象又分为间接对象和直接对象。
间接对象是PDF中最常用的对象,如前面对象集合里面的,所有对象都是间接对象,在其他位置通过R关键字来引用,在交叉引用表里面都是通过间接对象来引用的。
直接对象就更好理解了,上面的8种对象单独出现的时候就叫直接对象。
PDF文件结构
(二)
————逻辑结构
作者:
bobob
邮件:
zxbbobob@
要解析一个PDF文件,首先要掌握PDF的物理结构,这是第一步。
但是这个仅仅只是基础,更重要的是对PDF逻辑结构的解析。
PDF的逻辑大体上是一个树状结构,根节点是catalog字典,通过这里去解析页、目录、链接信息等等,在这里按照PDF的树形结构,详细讨论一下整个文件的逻辑框架。
一、catalog根节点
catalog是整个PDF逻辑结构的根节点,这个可以通过trailer的Root字段定位,虽然简单,但是相当重要,因为这里是PDF文件物理结构和逻辑结构的连接点。
Catalog字典包含的信息非常多,这里仅就最主要的几个字段做个说明。
(1)Pages字段
这是个必须字段,是PDF里面所有页面的描述集合。
Pages字段本身是个字典,它里面又包含了一下几个主要字段:
字段
Type
name
(必须)只能为Pages
。
Parent
(如果不是catalog里面指定的跟节点,则必须有,并且必须是间接对象)
当前节点的直接父节点。
Kids
array
(必须)一个间接对象组成的数组,节点可能是page或pagetree。
Count
integer
(必须)pagetree里面所包含叶子节点(page
对象)的个数。
从以上字段可以看出,Pages最主要的功能就是组织所有的page对象。
Page对象描述了一个PDF页面的属性、资源等信息。
Page对象是一个字典,它主要包含一下几个重要的属性:
(必须)必须是Page。
(必须;
并且只能是间接对象)当前page节点的直接父节点pagetree
LastModified
date
(如果存在PieceInfo字段,就必须有,否则可选)记录当前页面被最后一次修改的日期和时间。
Resources
(必须;
可继承)记录了当前page用到的所有资源。
如果当前页不用任何资源,则这是个空字典。
忽略所有字段则表示继承父节点的资源。
MediaBox
rectangle
可继承)定义了要显示或打印页面的物理媒介的区域(defaultuserspaceunits)
CropBox
(可选;
可继承)定义了一个可视区域,当前页被显示或打印的时候,它的内容会被这个区域裁剪。
默认值就是MediaBox。
BleedBox
(可选)
定义了一个区域,当输出设备是个生产环境(productionenvironment)的时候,页面显示的内容会被裁剪。
默认值是
CropBox.
Contents
stream
or
描述页面内容的流。
如果这个字段缺省,则页面上什么也不会显示。
这个值可以是一个流,也可以是由几个流组成的一个数组。
如果是数组,实际效果相当于所有的流是按顺序连在一起的一个流,这就允许PDF生成的时候可以随时插入图片或其他资源。
流之间的分割只是词汇上的一个分割,并不是逻辑上或者组织形式的切割。
Rotate
可继承)
顺时钟旋转的角度数,这个必须是90的整数倍,默认是0。
Thumb
(可选)定义当前页的缩略图。
Annots
和当前页面关联的注释。
Metadata
当前页包含的元数据。
一个简单例子:
30obj
/Type/Page
/Parent40R
/MediaBox[00612792]
/Resources<
/Font<
/F370R/F590R/F7110R
/ProcSet[/PDF]
/Contents120R
/Thumb140R
/Annots[230R240R]
endobj
(2)Outlines字段
Outline是PDF里面为了方便用户从PDF的一部分跳转到另外一部分而设计的,有时候也叫书签(Bookmark),它是一个树状结构,可以直观的把PDF文件结构展现给用户。
用户可以通过鼠标点击来打开或者关闭某个outline项来实现交互,当打开一个outline时,用户可以看到它的所有子节点,关闭一个outline的时候,这个outline的所有子节点会自动隐藏。
并且,在点击的时候,阅读器会自动跳转到outline对应的页面位置。
Outlines包含一下几个字段:
KEY
TYPE
VALUE
(可选)如果这个字段有值,则必须是Outlines。
First
必须是间接对象)
第一个顶层Outlineitem。
Last
必须是间接对象)最后一个顶层outlineitem。
(必须)outline的所有层次的item的总数。
Outline是一个管理outlineitem的顶层对象,我们看到的,其实是outlineitem,这个里面才包含了文字、行为、目标区域等等。
一个outlineitem主要有一下几个字段:
Title
text
string
(必须)当前item要显示的标题。
必须是间接对象)outline层级中,当前item的父对象。
如果item本身是顶级item,则父对象就是它本身。
(除了每层的第一个item外,其他item必须有这个字段;
必须是间接对象)当前层级中,此item的前一个item。
Next
(除了每层的最后一个item外,其他item必须有这个字段;
必须是间接对象)当前层级中,此item的后一个item。
(如果当前item有任何子节点,则这个字段是必须的;
当前item的第一个直接子节点。
当前item的最后一个直接子节点。
Dest
name,
bytestring,orarray
如果A字段存在,则这个不能被会略)当前的outlineitem被激活的时候,要显示的区域。
A
如果Dest
字段存在,则这个不能被忽略)当前的outlineitem被激活的时候,要执行的动作。
(3)URI字段
URI(uniformresourceidentifier),定义了文档级别的统一资源标识符和相关链接信息。
目录和文档中的链接就是通过这个字段来处理的。
(4)Metadata字段
文档的一些附带信息,用xml表示,符合adobe的xmp规范。
这个可以方便程序不用解析整个文件就能获得文件的大致信息。
(5)其他
Catalog字典中,常用的字段一般有以下一些:
(必须)必须为Catalog。
Version
(可选)PDF文件所遵循的版本号(如果比文件头指定的版本号高的话)。
如果这个字段缺省或者文件头指定的版本比这里的高,那就以文件头为准。
一个PDF生成程序可以通过更新这个字段的值来修改PDF文件版本号。
Pages
(必须并且必须为间接对象)当前文档的页面集合入口。
PageLabels
number
tree
(可选)numbertree,定义了页面和页面label对应关系。
Names
(可选)文档的name字典。
Dests
必须是间接对象)name和相应目标对应关系字典。
ViewerPreferences
(可选)阅读参数配置字典,定义了文档被打开时候的行为。
如果缺省,则使用阅读器自己的配置。
PageLayout
指定文档被打开的时候页面的布局方式。
SinglePageDisplay
单页
OneColumnDisplay
单列
TwoColumnLeftDisplay
双列,奇数页在左
TwoColumnRightDisplay
双列,奇数页在右
TwoPageLeft
双页,奇数页在左
TwoPageRight
双页,奇数页在右
缺省值:
SinglePage.
PageMode
当文档被打开时,指定文档怎么显示
UseNone
目录和缩略图都不显示
UseOutlines
显示目录
UseThumbs
显示缩略图
FullScreen
全屏模式,没有菜单,任何其他窗口
UseOC
显示Optionalcontentgroup
面板
UseAttachments显示附件面板
UseNone.
Outlines
(可选;
必须为间接对象)文档的目录字典
Threads
必须为间接对象)文章线索字典组成的数组。
OpenAction
arrayordictionary
指定一个区域或一个action,在文档打开的时候显示(区域)或者执行(action)。
如果缺省,则会用默认缩放率显示第一页的顶部。
AA
(可选)一个附加的动作字典,在全局范围内定义了响应各种事件的action。
URI
(可选)一个URI字典包含了文档级别的URIaction信息。
Ac