# Python : Media : pillow
\[ [src](https://github.com/python-pillow/Pillow/) | [docs](https://pillow.readthedocs.io/en/stable/) | [API](https://pillow.readthedocs.io/en/stable/reference/) ]
Friendly fork of PIL (Python Imaging Library). (Author died.)
## Overview
The core image library is designed for fast access to data stored in a few basic pixel formats.
- extensive file format support
- efficient internal representation
- powerful image processing capabilities
- create thumbnails, convert between file formats, print images
- point operations, filtering with a set of built-in convolution kernels, color space conversions
- image resizing, rotation and arbitrary affine transforms
- histogram method to generate image stats — can be used for automatic contrast enhancement
When you open a file, the file header is read to determine the file format and extract things like mode, size, and other properties required to decode the file, but the raster data isn't loaded and decoded until and unless necessary. This means that opening an image file is a fast operation, which is independent of the file size and compression type.
Coordinates (0,0) refer to the implied pixel corners. The center of a pixel addressed as (0, 0) actually lies at (0.5, 0.5).
#### Metadata
You can attach auxiliary information to an image using the `info` dict.
How such information is handled when loading and saving image files is up to the file format handler. Most handlers add properties to the `info` attribute when loading an image, but ignore it when saving images.
> [!EXIF Orientation]
> A common element of the info attribute for JPG and TIFF images is the EXIF orientation tag. This is an instruction for how the image data should be oriented. For example, it may instruct an image to be rotated by 90 degrees, or to be mirrored. To apply this information to an image, `exif_transpose()` can be used.
## Cheatsheet
```python
# imports
from PIL import Image, ImageDraw, ImageEnhance, ImageFilter, ImageOps, ImagePalette, ImageSequence, ImageTk, PSDraw
# constants
Image.Transpose.
FLIP_LEFT_RIGHT
FLIP_TOP_BOTTOM
ROTATE_90 (counter-clockwise)
ROTATE_180
ROTATE_270 (counter-clockwise)
TRANSPOSE
TRANSVERSE
ImageFilter.
BLUR
CONTOUR
DETAIL
EDGE_ENHANCE, EDGE_ENHANCE_MORE
EMBOSS
FIND_EDGES
SHARPEN
SMOOTH, SMOOTH_MORE
# opening
im = Image.open( "filename" | fileobj ) # PngImagePlugin.PngImageFile
-or-
with Image.open( "filename" ) as im:
...
# attributes
im.filename "a.png"
im.format "PNG" # None if not read from file
im.has_transparency_data False
im.info { str: <record_type> } # ex: PngImagePlugin.iTXt (subclass of str)
im.is_animated False
im.mode "RGB"
im.n_frames 1
im.palette None | ImagePalette.ImagePalette
im.size ( 512, 512 )
# methods
im.filter( ImageFilter.DETAIL ) # BLUR, DETAIL, ...
im.resize( (x,y) ) # returns resized copy
im.rotate( int ) # returns rotated copy; int -> degrees counter-clockwise
im.save( "filename" ) # output format based on file extension
im.show() # save image to tmp file and call external display utility (for debugging)
im.thumbnail( (x,y) ) # like resize(), but modifies existing image
# regions
region = im.crop( box ) # box = ( left, upper, right, lower ) (0,0 -> upper-left corner)
region = region.transpose( Image.Transpose.ROTATE_180 )
im.paste( region, box ) # doesn't require modes to match; can take transparency mask (0..255)
# RECIPE: merging two images
im = Image.new( "RGBA", ( w, h ) )
im.paste( im1 )
im.paste( im2, ( w, h ) )
```
> [!NOTE] File Format
> When an image is opened from a file, only that instance of the image is considered to have the format. Copies of the image will contain data loaded from the file, but not the file itself, meaning that it can no longer be considered to be in the original format. So if copy() is called on an image, or another method internally creates a copy of the image, then any methods or attributes specific to the format will no longer be present. The fp (file pointer) attribute will no longer be present, and the format attribute will be None.
## INBOX
```
expand = True # allow for size changes resulting from actions like rotate
GIF: TODO
ICO: TODO
JPEG: TODO
APNG: TODO
WebP: TODO
plus many more
PDF: TODO (write-only, as binary PDF 1.4)
PNG
EXIF data can be read; not guaranateed to be present until load()
open() sets:
info.chromaticity
info.gamma
info.srgb
info.transparency
info.text = { tEXt, zTXt, iTXt }
save( ...options... )
Other interesting modules:
ImageDraw - 2D + text
ImageOps - common / useful operations
ExifTags
PIL.PngImagePlugin.PngInfo
```