pam - Netpbm 通用二维位图格式
概述
PAM 图像格式是一种最简单的二维映射格式。
它被设计用于各种各样的图形,但从理论上讲,它可以用于任何以二维矩形数组排列的数据。实际上,从另一个角度来看,它可以被视为一种用于数据排列为三维数组的格式。
“PAM”这个名称是一个首字母缩写词,代表“可移植任意映射”。如果将其与 Netpbm 格式的名称(PBM、PGM 和 PPM)联系起来,那么这个名称更有意义。
这种格式不定义数组中任何特定点的含义。它可以是红色、绿色和蓝色光强度,这样数组就表示一个视觉图像,或者它可以是相同的红色、绿色和蓝色组件加上一个透明度组件,或者它可以包含地球表面地点每年的降雨量。任何使用 PAM 格式的进程都必须进一步定义该格式,以指定数据的含义。
PAM 图像描述了一个二维的元组网格。元组排列成行和列。图像的宽度是列数。图像的高度是行数。所有行的宽度都相同,所有列的高度都相同。元组可以具有任意度数,但所有元组的度数都相同。元组的度数称为图像的深度。元组的每个成员称为一个样本。样本是一个无符号整数,它表示沿着从零开始到某个最大值的比例尺上的位置,该最大值称为 maxval。maxval 对于图像中的每个样本都是相同的。所有 N 个样本的二维数组称为图像的第 N 个平面或第 N 个通道。
虽然基本格式不为元组值指定任何含义,但它包含一个可选字符串,用于描述该含义。从基本 PAM 格式的角度来看,此字符串的内容是任意的,但该格式的用户可以通过约定为其赋值,以便他们可以识别其 PAM 格式的特定实现。一些元组类型被定义为 PAM 的官方子格式。请参见定义的元组类型。
令人困惑的 Netpbm 格式世界
很容易对 PAM 格式与 PBM、PGM、PPM 和 PNM 之间的关系感到困惑。以下是一些说明:
“PNM”实际上不是一种格式。它是 PBM、PGM 和 PPM 格式的统称。它也是一组库函数的名称,每个库函数都可以处理这三个格式。
“PAM”实际上是一种第四种格式。但它非常通用,因此您可以用 PAM 图像来表示与 PBM、PGM 或 PPM 图像相同的信息。实际上,如果一个程序被设计用来读取 PBM、PGM 或 PPM,并且它使用 Netpbm 库的最新版本,那么它可以很好地读取等效的 PAM 图像,并且该程序甚至不会注意到任何区别。
为了让事情更加复杂,有一组名为“pam”函数的库例程,用于读取和写入 PAM 格式,同时也读取和写入 PBM、PGM 和 PPM 格式。它们这样做是因为后三种格式更古老且更流行,因此即使是新的程序也必须能够处理它们。让库处理所有格式,可以方便地编写程序,这些程序也可以使用较新的 PAM 格式。
布局
一种准确地读取和写入 PAM 格式的便捷方法是使用 libnetpbm(1) C 子例程库。
PAM 文件由一个或多个 PAM 图像序列组成。在图像之间没有数据、分隔符或填充。
每个 PAM 图像由一个标头紧接着一个栅格组成。
这是一个示例标头:
P7
WIDTH 227
HEIGHT 149
DEPTH 3
MAXVAL 255
TUPLTYPE RGB
ENDHDR
标头以 ASCII 字符“P7”开头,后跟一个换行符。这是魔数。
注意:xv 缩略图图像也以“P7”魔数开头。(这和 PAM 是对 Netpbm 格式的独立扩展)。其余格式使很容易区分 PAM 和该格式。
标头继续包含任意数量的 ASCII 文本行。每行都以换行符结尾,并由换行符分隔。
每个标头行由零个或多个以空格分隔的标记组成,或者以“#”开头。如果它以“#”开头,则是一条注释,并且本规范的其余部分不适用于它。
具有零个标记的标头行是有效的,但没有意义。
标头行的类型由其第一个标记标识,该标记的长度不超过 8 个字符:
ENDHDR 这是标头中的最后一个行。标头必须包含恰好一个这样的标头行。
HEIGHT 第二个标记是一个十进制数,表示图像的高度(行数)。标头必须包含恰好一个这样的标头行。
WIDTH 第二个标记是一个十进制数,表示图像的宽度(列数)。标头必须包含恰好一个这样的标头行。
DEPTH 第二个标记是一个十进制数,表示图像的深度(平面或通道数)。标头必须包含恰好一个这样的标头行。
MAXVAL 第二个标记是一个十进制数,表示图像的最大值。标头必须包含恰好一个这样的标头行。
TUPLTYPE
标头可以包含任意数量的这些标头行,包括零个。该行的其余部分是元组类型的一部分。该行的其余部分不被标记化,但元组类型不包括在 TUPLTYPE 标记之后或该行的末尾的任何空格。它不包括换行符。在 TUPLTYPE 标记之后必须有除了空格之外的其他内容。
如果有多个 TUPLTYPE 头部行,则元组类型是每个行中的值的串联,用单个空格分隔,顺序是它们在头部中出现的顺序。如果没有 TUPLTYPE 头部行,则元组类型为空字符串。
栅格由图像的每一行组成,从上到下,连续排列,在行之间、之前或之后没有任何分隔符。
每一行由该行中的每个元组组成,从左到右,连续排列,在元组之间、之前或之后没有任何分隔符。
每个元组由元组中的每个样本组成,按顺序排列,样本之间、之前或之后没有任何分隔符。
每个样本由纯二进制格式的无符号整数组成,最高有效字节在前。字节数是表示图像的 maxval 所需的最小字节数。
此处所说的“换行符”是指 ASCII 中称为换行符或 LF 的字符。
限制
高度、宽度、深度和 maxval 至少为 1。
高度、宽度和深度没有定义的上限,但图像处理器和生成器通常有自己的限制。
图像的 maxval 永远不会大于 65535。(限制它的原因是,为了更容易构建图像处理器,其中中间算术值通常必须适合 31 位或 32 位)。在 2005 年 10 月之前没有指定限制,但实际上所有实现都始终遵守它。
定义的元组类型
此规范中定义了一些元组类型,以指定 PAM 的官方子格式,用于特别流行的应用程序。该格式的用户也可以定义自己的元组类型,并因此定义自己的子格式。
元组类型仅影响图像中元组的样本(无符号整数)的含义。它不会影响样本或元组的编码方式。元组类型可能会影响元组在数组中的位置的含义(例如,它可能指示在视觉图像中,第一行的元组位于图像的顶部,而不是底部)。
元组类型绝不会确定元组中包含多少个样本(而是由 DEPTH 头部行确定)。可以这样说,元组类型会暗示一个深度(每个元组的样本数),因为某些元组类型仅与某些 DEPTH 值一起有效,但良好的编程实践是在解码栅格时使用 DEPTH 作为深度,并单独验证该深度是否与元组类型一致。此外,良好的做法是接受过大的深度,并忽略编号较高的平面。
用于视觉图像的 PAM
PAM 图像的一个常见用途是表示视觉图像,例如通常由较旧且更具体的 PBM、PGM 和 PPM 格式的图像表示的图像。
黑白
黑白图像(例如,也可以用 PBM 图像表示)具有“BLACKANDWHITE”类型的元组。 这样的 PAM 图像的深度为 1,maxval 为 1,其中每个元组中的一个样本为 0,表示黑色像素;为 1,表示白色像素。 maxval、高度、宽度以及栅格中元组的顺序与等效 PBM 图像具有明显的关系。
请注意,在 PBM 格式中,样本值为零表示白色,但在 PAM 中,零表示黑色。
灰度
灰度图像(例如,也可以用 PGM 图像表示)具有“GRAYSCALE”类型的元组。 这样的 PAM 图像的深度为 1。 maxval、高度、宽度以及栅格与等效 PGM 图像具有明显的关系。
彩色
彩色图像(例如,也可以用 PPM 图像表示)具有“RGB”类型的元组。 这样的 PAM 图像的深度为 3。 maxval、高度、宽度以及栅格与等效 PPM 图像具有明显的关系。 第一个平面表示红色,第二个平面表示绿色,第三个平面表示蓝色。
透明
上述所有视觉图像格式都有包含透明度信息的变体。 在这种变体中,元组类型会添加“_ALPHA”(例如,“RGB_ALPHA”),并且还有一个额外的平面。 编号最高的平面是不透明度平面(有时称为 alpha 平面或透明度平面)。
在这种类型的图像中,像素的颜色实际上是显式指定的颜色和稍后要标识的背景色的组合。
除了不透明度平面之外的其他平面描述了前景颜色。 平面中的一个样本通过指示像素的光有多少来自前景颜色来指示像素的不透明度,其余的光来自(未指定的)背景颜色。
例如,在 GRAYSCALE_ALPHA 图像中,假设平面 0 表示 60% 的白色灰度,平面 1 表示 25% 的不透明度。 前景色是 60% 的灰度,其中 25% 的灰度对像素的最终颜色有贡献。 其余的 75% 来自某种背景颜色。 因此,假设像素的背景颜色是纯白色。 那么像素的颜色是 90% 的白色:25% 的前景 60%,加上 75% 的背景 100%。
样本值是如上所述的不透明度分数,作为 maxval 的一部分。 请注意,它不像前景颜色样本那样经过伽玛校正。
互联网媒体类型
尽管 PAM 没有在 IANA 注册互联网媒体类型(也称为 MIME 类型、内容类型),但本规范指定非官方值为 image/x-portable-arbitrarymap,以与较旧的 Netpbm 格式的常规值保持一致。
文件名
PAM 文件的名称的常用后缀是“.pam”。但这并非强制要求。
参见
Netpbm(1), pbm(1), pgm(1), ppm(1), pnm(1), libnetpbm(1)
文档来源
此手册页由 Netpbm 工具“makeman”从 HTML 源代码生成。主文档位于:
http://netpbm.sourceforge.net/doc/pam.html