Netpbm


Netpbm is an open-source package of graphics programs and a programming library. It is used primarily in Unix, where it is found in all major open-source operating system distributions, but also works on Microsoft Windows, macOS, and other operating systems.

File formats

Several graphics formats are used and defined by the Netpbm project:
  • portable bitmap format
  • portable graymap format
  • portable pixmap format
PBM, PGM and PPM, sometimes collectively referred to as the portable anymap format are image file formats designed to be easily exchanged between platforms. The magic number at the beginning of a file determines the type. PNM files use a magic number of an ASCII "P" followed by a number defining the file type.
The PBM format was invented by Jef Poskanzer in the 1980s. The format allowed monochrome bitmaps to be transmitted within an email message as plain ASCII text, so that it would survive any changes in text formatting. The first library to handle the PBM format was released in 1988 under the name Pbmplus, containing tools to convert between PBM and other graphics formats. By the end of 1988, Poskanzer had developed the PGM and PPM formats along with their associated tools and added them to Pbmplus. The final release of Pbmplus was December 10, 1991.
The Netpbm library was released in 1993 to replace the then-unmaintained Pbmplus. It repackaged the original library and incorporated fixes created by other developers.

Description

Each file starts with a two-byte magic number in ASCII that identifies the file type and its encoding. The magic number is a capital P followed by a single-digit number.
The Netpbm library supports an additional [|PAM] file format with a magic number of P7.
PNM files can be created as both plain text and raw binary. The ASCII formats allow for human readability and easy transfer to other platforms, whereas the binary formats are easier to parse by programs and more efficient in file size. In the binary formats, PBM uses 1 bit per pixel, PGM uses 8 or 16 bits per pixel, and PPM uses 24 or 48 bits per pixel: 8/16 for red, 8/16 for green, 8/16 for blue. Application support for the 16 bit variants is rare. In either form, the header remains in ASCII format and the arguments are separated by a whitespace.
PGM and PPM documentation defines that gray and color values use the BT.709 color space and gamma transfer function. However, depending on the application, the used color space may be sRGB, linear or some other color space. There is no metadata in the file to indicate which color space is being used.

PBM example

A simple example of the PBM format is as follows:
P1
# This is an example bitmap of the letter "J"
6 10
0 0 0 0 1 0
0 0 0 0 1 0
0 0 0 0 1 0
0 0 0 0 1 0
0 0 0 0 1 0
0 0 0 0 1 0
1 0 0 0 1 0
0 1 1 1 0 0
0 0 0 0 0 0
0 0 0 0 0 0
The string P1 identifies the file format. The number sign introduces a comment. The next two numbers give the width and the height. The following matrix gives the pixel values. As the PBM format is monochromatic and only supports two shades, namely, black and white, the image is described in only ones and zeros. This is known as a bitmap.
The matrix cells do not need to be aligned; the format ignores whitespace and line feeds in the data section. The following displays the same image:
P1
# This is an example bitmap of the letter "J"
6 10
000010000010000010000010000010000010100010011100000000000000
A value of 0 signifies a white pixel, and a 1 signifies a black pixel. This differs from the other formats, where higher values signify brighter pixels.
The P4 binary format of the same image represents each pixel with a single bit. The width of the row in pixels is given in the header, packed to the length of 8 pixels or a byte. The first pixel in a row is the most significant bit. The extra bits used to make the length equal to a byte are ignored. The following formula can be used to calculate the number of required bytes. Using the example above a grid would take 10 instead of 7.5 bytes.
P4
# This is an example binary format of the letter "J" with each byte in decimal notation
6 10
8 8 8 8 8 8 136 112 0 0

PGM example

The PGM and PPM formats have an additional parameter for the maximum value after the X and Y dimensions and before the actual pixel data. Black is 0 and max value is white.
P2
# Shows the word "FEEP"
24 7
15
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 3 3 3 3 0 0 7 7 7 7 0 0 11 11 11 11 0 0 15 15 15 15 0
0 3 0 0 0 0 0 7 0 0 0 0 0 11 0 0 0 0 0 15 0 0 15 0
0 3 3 3 0 0 0 7 7 7 0 0 0 11 11 11 0 0 0 15 15 15 15 0
0 3 0 0 0 0 0 7 0 0 0 0 0 11 0 0 0 0 0 15 0 0 0 0
0 3 0 0 0 0 0 7 7 7 7 0 0 11 11 11 11 0 0 15 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0

PPM example

This is an example of a color RGB image stored in PPM format.
P3
# "P3" means this is a RGB color image in ASCII
# "3 2" is the width and height of the image in pixels
# "255" is the maximum value for each color
# This, up through the "255" line below are the header.
# Everything after that is the image data: RGB triplets.
# In order: red, green, blue, yellow, white, and black.
3 2
255
255 0 0
0 255 0
0 0 255
255 255 0
255 255 255
0 0 0
The P6 binary format of the same image represents each color component of each pixel with one byte in the order red, green, then blue. The file is smaller, but the color information is more difficult to read by humans. The binary image information comes after the header.
In the binary format, last headerline must be like "255\n", with data immediately following it; any comment added after 255 will be taken as the start of image data, and the image will be skewed to the right.
The PPM format is not compressed, and thus requires more space and bandwidth than a compressed format would. For example, the above 192×128 PNG image has a file size of 166 bytes. When converted to a 192×128 PPM image, the file size is 73,848 bytes. Filesize reduction factor 100 or so when converting to png is typical if the image is a line drawing; if the image is a photo, it is best converted to jpeg, which yields a greater filesize reduction.
PPM is generally used as an intermediate format for image work before converting to a more efficient format like PNG without any loss of information in the intermediate step.
The image shown above using only 0 or the maximal value for the red, green and blue channels can be encoded as follows:

P3
  1. The same image with width 3 and height 2,
  2. using 0 or 1 per color
3 2 1
1 0 0 0 1 0 0 0 1
1 1 0 1 1 1 0 0 0

White space and comment lines are syntactically equivalent to a single space within the PNM headers. For the plain formats this is also true of the pixmap lines:

P3 3 2 1 1 0 0 0 1 0 0 0 1 1 1 0 1 1 1 0 0 0

Extensions

16-bit

The original definition of the PGM and the PPM binary formats did not allow bit depths greater than 8 bits. While the ASCII format can accommodate greater bit depths, it increases file sizes and slows read and write operations. Many programmers have extended the format to allow higher bit depths. When using higher bit depths, the endianness of the file matters. Various implementations have not agreed on which byte order to use, and some connected the 16-bit endianness to the pixel packing order. The PGM and PPM documentation says the most significant byte is first and the Netpbm implementation uses big-endian byte order.

32-bit

The PFM is the unofficial four byte IEEE 754 single precision floating point extension.
  1. The first line is either the ASCII text "PF", for a color file, or "Pf", for a grey-scale file.
  2. The next ASCII text line contains the width and height, separated by the space character hex 20 or sometimes with hex 0A. After each line a white space character hex 0A is written and not the Windows/DOS CR/LF combination.
  3. The third ASCII text line holds a nonzero decimal number that indicates little-endian floats for the pixel data when negative and big-endian floats when positive. The absolute value of the number indicates the range. So the third line containing -1.0 indicates little-endian format in range zero to one.
After the header the file, each pixel is specified with a floating point number from left-to-right, bottom-to-top. Some programs suggest PF4 as an additional extension for the RGBA format.
PFM is supported by the programs Photoshop, GIMP, and ImageMagick. It is also supported by the de facto reference implementation netpbm.

Programs

The Netpbm package contains over 350 programs, most of which have "pbm", "pgm", "ppm", "pam", or "pnm" in their names. For example, one might use pamscale to shrink an image by 10%, pamcomp to overlay one image on top of another, pbmtext to create an image of text, or reduce the number of colors in an image with pnmquant.
The programs are designed to be minimal building blocks that can be used in various combinations to do other things. The Netpbm package can, for example, use two successive conversion programs to turn a color picture in the GIF format into a.bmp file:
giftopnm somepic.gif > somepic.ppm
ppmtobmp somepic.ppm > somepic.bmp
This kind of operation is commonly done as a pipeline to save execution time and to avoid creating a temporary file:
giftopnm somepic.gif | ppmtobmp > somepic.bmp
The Netpbm programs are frequently used as intermediates to convert between obscure formats. For instance, there may be no tool to convert an X11 window dump directly to a Macintosh PICT file, but one can do this by running xwdtopnm, then ppmtopict. As a more complex example, Netpbm tools can convert 48×48 XBM to Ikon and eventually X-Face.