Pillow (TIFF)
| Language | Python |
|---|---|
| License | MIT-CMU (permissive) |
| Repository | github.com/python-pillow/Pillow |
| Documentation | TIFF in the Pillow docs |
| Depends on | libtiff (included in the wheels) |
| Read / write | yes / yes, multi-page, strips and tiles, BigTIFF, LZW, Deflate, PackBits, JPEG, Group 3/4, WebP, ZSTD |
Pillow is the standard imaging library for Python. It uses libtiff for compressed TIFF, so it opens almost any TIFF: 1-bit fax, grayscale, palette, RGB, CMYK, 16-bit grayscale and 32-bit float. Pages are frames you move between with seek(). Tags are in img.tag_v2, a dict keyed by tag number.
Pillow’s image modes limit what it can represent: 16-bit RGB TIFF is reduced to 8 bits, and images with many channels or unusual sample formats may fail to open. Use tifffile for scientific data.
Installation#
Shell
pip install Pillow
Basic usage: open a TIFF and save as PNG#
Python
from PIL import Image
with Image.open("in.tif") as img:
print(img.size, img.mode, img.n_frames, img.info.get("compression"), img.info.get("dpi"))
img.save("out.png")
How to save a TIFF with compression#
Python
from PIL import Image
with Image.open("in.png") as img:
img.save("out_lzw.tif", compression="tiff_lzw")
img.save("out_zip.tif", compression="tiff_adobe_deflate")
img.convert("RGB").save("out_jpeg.tif", compression="jpeg", quality=85)
img.convert("1").save("out_fax.tif", compression="group4", dpi=(300, 300))
Without compression, Pillow writes an uncompressed TIFF.
How to iterate the pages of a multi-page TIFF#
Python
from PIL import Image, ImageSequence
with Image.open("scan.tif") as doc:
for i, page in enumerate(ImageSequence.Iterator(doc)):
page.save(f"page-{i}.png")
Or jump to a page with doc.seek(2); doc.n_frames is the number of pages.
How to create a multi-page TIFF#
Python
from PIL import Image
pages = [Image.open(p) for p in ["page1.png", "page2.png", "page3.png"]]
pages[0].save("pages.tif", save_all=True, append_images=pages[1:], compression="tiff_lzw")
How to read TIFF tags#
Python
from PIL import Image, TiffTags
with Image.open("in.tif") as img:
for tag, value in img.tag_v2.items():
name = TiffTags.lookup(tag).name
print(tag, name, value)
print("Software:", img.tag_v2.get(305))
How to write TIFF tags#
Python
from PIL import Image
from PIL.TiffImagePlugin import ImageFileDirectory_v2
ifd = ImageFileDirectory_v2()
ifd[305] = "my app" # Software
ifd[270] = "scanned invoice" # ImageDescription
with Image.open("in.png") as img:
img.save("out.tif", tiffinfo=ifd, compression="tiff_lzw")
Tips#
- Save with
big_tiff=True(Pillow 11.1+) for files over 4 GB. Image.openreads only the header; pixels are decoded on first access, so gettingimg.sizeof a large TIFF is cheap.img.info["compression"]tells you the compression of the opened file; passcompression=img.info["compression"]to keep it when saving.