Skip to main content

Python bindings for libheif - HEIC/AVIF/JPEG2000 image codec

Project description

pylibheif

Python bindings for libheif using pybind11.

Features

  • HEIC/HEIF Support: Read and write HEIC images (HEVC/H.265 encoded)
  • AVIF Support: Read and write AVIF images (AV1 encoded)
  • JPEG2000 Support: Read and write JPEG2000 images in HEIF container
  • NumPy Integration: Zero-copy access to image data via Python Buffer Protocol
  • Metadata Support: Read EXIF and XMP metadata from images
  • RAII Resource Management: Automatic resource cleanup with context managers

Supported Formats

Format Decoding Encoding Codec
HEIC (HEVC/H.265) libde265 / x265
AVIF (AV1) DAV1D + AOM
JPEG2000 OpenJPEG

Requirements

  • Python >= 3.12
  • NumPy >= 1.26.0
  • CMake >= 3.15
  • C++17 compatible compiler

System Dependencies

# macOS
brew install openjpeg

# Ubuntu/Debian
sudo apt install libopenjp2-7-dev

Installation

pip install pylibheif

Or with uv:

uv pip install pylibheif

Building from Source

# Clone with submodules
git clone --recursive https://github.com/twn39/pylibheif.git
cd pylibheif

# Install
uv pip install -e .

Usage

Reading HEIC/AVIF Images

Using context manager (recommended):

import pylibheif
import numpy as np

# Open HEIC file with context manager
with pylibheif.HeifContext() as ctx:
    ctx.read_from_file('image.heic')
    
    # Get primary image handle
    handle = ctx.get_primary_image_handle()
    print(f'Image size: {handle.width}x{handle.height}')
    print(f'Has alpha: {handle.has_alpha}')
    
    # Decode to RGB
    img = handle.decode(pylibheif.HeifColorspace.RGB, 
                        pylibheif.HeifChroma.InterleavedRGB)
    
    # Get as NumPy array (zero-copy)
    plane = img.get_plane(pylibheif.HeifChannel.Interleaved, False)
    arr = np.asarray(plane)  # shape: (height, width, 3)

Explicit creation (for more control):

import pylibheif
import numpy as np

# Create context explicitly
ctx = pylibheif.HeifContext()
ctx.read_from_file('image.heic')

handle = ctx.get_primary_image_handle()
img = handle.decode(pylibheif.HeifColorspace.RGB, 
                    pylibheif.HeifChroma.InterleavedRGB)
plane = img.get_plane(pylibheif.HeifChannel.Interleaved, False)
arr = np.asarray(plane)

# Resources are automatically freed when objects go out of scope

Writing HEIC/AVIF Images

import pylibheif
import numpy as np

# Create image from NumPy array
width, height = 1920, 1080
img = pylibheif.HeifImage(width, height, 
                          pylibheif.HeifColorspace.RGB,
                          pylibheif.HeifChroma.InterleavedRGB)
img.add_plane(pylibheif.HeifChannel.Interleaved, width, height, 8)

# Fill with data
plane = img.get_plane(pylibheif.HeifChannel.Interleaved, True)
arr = np.asarray(plane)
arr[:] = your_image_data  # your RGB data

# Encode and save
ctx = pylibheif.HeifContext()

# For HEIC (HEVC)
encoder = pylibheif.HeifEncoder(pylibheif.HeifCompressionFormat.HEVC)
# For AVIF (AV1)
# encoder = pylibheif.HeifEncoder(pylibheif.HeifCompressionFormat.AV1)
# For JPEG2000
# encoder = pylibheif.HeifEncoder(pylibheif.HeifCompressionFormat.JPEG2000)

encoder.set_lossy_quality(85)
encoder.encode_image(ctx, img)
ctx.write_to_file('output.heic')

Converting HEIC to JPEG

import pylibheif
import numpy as np
from PIL import Image

# Decode HEIC
ctx = pylibheif.HeifContext()
ctx.read_from_file('input.heic')
handle = ctx.get_primary_image_handle()
img = handle.decode(pylibheif.HeifColorspace.RGB, 
                    pylibheif.HeifChroma.InterleavedRGB)

# Get NumPy array
plane = img.get_plane(pylibheif.HeifChannel.Interleaved, False)
arr = np.asarray(plane)

# Save as JPEG using PIL
pil_img = Image.fromarray(arr)
pil_img.save('output.jpg', 'JPEG', quality=85)

Reading Metadata

import pylibheif

ctx = pylibheif.HeifContext()
ctx.read_from_file('image.heic')
handle = ctx.get_primary_image_handle()

# Get metadata block IDs
exif_ids = handle.get_metadata_block_ids('Exif')
for id in exif_ids:
    metadata_type = handle.get_metadata_block_type(id)
    metadata_bytes = handle.get_metadata_block(id)
    print(f'Metadata type: {metadata_type}, size: {len(metadata_bytes)}')

API Reference

class pylibheif.HeifContext

Manages the valid lifetime of libheif context. It is the main entry point (root object) for high-level API.

Methods

__init__() Creates a new empty context.

read_from_file(filename: str) -> None Reads a HEIF file from the given filename.

  • filename: Path to the HEIF file.

read_from_memory(data: bytes) -> None Reads a HEIF file from a bytes object.

  • data: Bytes containing the file content.

write_to_file(filename: str) -> None Writes the current context to a file.

  • filename: Destination path.

write_to_bytes() -> bytes Writes the current context to a bytes object.

  • Returns: bytes object containing the encoded file data.

get_primary_image_handle() -> HeifImageHandle Gets the handle for the primary image in the file.

  • Returns: HeifImageHandle for the primary image.

get_image_handle(id: int) -> HeifImageHandle Gets the handle for a specific image ID.

  • id: The ID of the image (see get_list_of_top_level_image_IDs).
  • Returns: HeifImageHandle.

get_list_of_top_level_image_IDs() -> List[int] Gets a list of IDs of all top-level images in the file.

  • Returns: List of integer IDs.

class pylibheif.HeifImageHandle

Represents a compressed image within the HEIF file.

Properties

  • width (int): The width of the image.
  • height (int): The height of the image.
  • has_alpha (bool): True if the image has an alpha channel.

Methods

decode(colorspace: HeifColorspace = HeifColorspace.RGB, chroma: HeifChroma = HeifChroma.InterleavedRGB) -> HeifImage Decodes the image handle into an uncompressed HeifImage.

  • colorspace: Target colorspace (default: RGB).
  • chroma: Target chroma format (default: InterleavedRGB).
  • Returns: Decoded HeifImage.

get_metadata_block_ids(type_filter: str = "") -> List[str] Gets a list of metadata block IDs attached to this image.

  • type_filter: Optional filter string (e.g. "Exif", "XMP").
  • Returns: List of metadata ID strings.

get_metadata_block_type(id: str) -> str Gets the type string of a specific metadata block.

  • id: Metadata ID.
  • Returns: Type string (e.g. "Exif").

get_metadata_block(id: str) -> bytes Gets the raw data of a metadata block.

  • id: Metadata ID.
  • Returns: bytes object containing the metadata.

class pylibheif.HeifImage

Represents an uncompressed image containing pixel data. Supports the Python Buffer Protocol for zero-copy access with NumPy.

Properties

  • width (int): The width of the image.
  • height (int): The height of the image.

Methods

__init__(width: int, height: int, colorspace: HeifColorspace, chroma: HeifChroma) Creates a new empty image.

  • width: Image width.
  • height: Image height.
  • colorspace: Image colorspace.
  • chroma: Image chroma format.

add_plane(channel: HeifChannel, width: int, height: int, bit_depth: int) -> None Adds a new plane to the image.

  • channel: The channel type (e.g. HeifChannel.Interleaved).
  • width: Width of the plane.
  • height: Height of the plane.
  • bit_depth: Bit depth (e.g. 8).

get_plane(channel: HeifChannel, writeable: bool = False) -> HeifPlane Gets a plane object that supports the buffer protocol.

  • channel: The channel to retrieve.
  • writeable: Whether the buffer should be writable.
  • Returns: HeifPlane object (wrappable with np.asarray()).

class pylibheif.HeifEncoder

Controls the encoding process.

Methods

__init__(format: HeifCompressionFormat) Creates a new encoder for the specified format.

  • format: Compression format (e.g. HeifCompressionFormat.HEVC).

set_lossy_quality(quality: int) -> None Sets the quality for lossy compression.

  • quality: Integer between 0 (lowest) and 100 (highest).

set_parameter(name: str, value: str) -> None Sets a low-level encoder parameter.

  • name: Parameter name (e.g. "speed" for AV1).
  • value: Parameter value.

encode_image(context: HeifContext, image: HeifImage) -> None Encodes the given image and appends it to the context.

  • context: The destination HeifContext.
  • image: The source HeifImage to encode.

Enums

pylibheif.HeifColorspace

  • RGB, YCbCr, Monochrome, Undefined

pylibheif.HeifChroma

  • InterleavedRGB: Interleaved R, G, B bytes.
  • InterleavedRGBA: Interleaved R, G, B, A bytes.
  • C420: YUV 4:2:0 planar.
  • C422: YUV 4:2:2 planar.
  • C444: YUV 4:4:4 planar.
  • Monochrome.

pylibheif.HeifChannel

  • Interleaved: For interleaved RGB/RGBA.
  • Y, Cb, Cr: For YUV planar.
  • R, G, B: For RGB planar.
  • Alpha: For Alpha channel.

pylibheif.HeifCompressionFormat

  • HEVC: H.265 (libx265).
  • AV1: AV1 (AOM/RAV1E/SVT).
  • JPEG: JPEG.
  • JPEG2000: JPEG 2000 (OpenJPEG).

Building from Source

# Clone with submodules
git clone --recursive https://github.com/your-username/pylibheif.git
cd pylibheif

# Build
uv pip install -e .

Performance

Benchmarks on 1920x1080 RGB image (Apple Silicon):

Operation pylibheif pillow-heif Note
HEVC Decode 25 ms 25 ms ~39 FPS
HEVC Encode 279 ms 272 ms Quality 80
AV1 Encode 91 ms - Speed 50

pylibheif offers performance comparable to pillow-heif (both wrapper libheif), but exposes a lower-level C++ API for fine-grained control.

Run benchmarks yourself:

uv pip install pillow-heif pytest-benchmark
uv run pytest tests/test_benchmark.py --benchmark-only

License

This project is licensed under the LGPL-3.0 License - see the LICENSE file for details.

Acknowledgments

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

pylibheif-1.21.2.post1.tar.gz (2.1 MB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

pylibheif-1.21.2.post1-cp313-cp313-manylinux_2_28_x86_64.whl (5.9 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.28+ x86-64

pylibheif-1.21.2.post1-cp313-cp313-macosx_14_0_arm64.whl (5.8 MB view details)

Uploaded CPython 3.13macOS 14.0+ ARM64

pylibheif-1.21.2.post1-cp312-cp312-manylinux_2_28_x86_64.whl (5.9 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.28+ x86-64

pylibheif-1.21.2.post1-cp312-cp312-macosx_14_0_arm64.whl (5.8 MB view details)

Uploaded CPython 3.12macOS 14.0+ ARM64

pylibheif-1.21.2.post1-cp311-cp311-manylinux_2_28_x86_64.whl (5.9 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.28+ x86-64

pylibheif-1.21.2.post1-cp311-cp311-macosx_14_0_arm64.whl (5.8 MB view details)

Uploaded CPython 3.11macOS 14.0+ ARM64

File details

Details for the file pylibheif-1.21.2.post1.tar.gz.

File metadata

  • Download URL: pylibheif-1.21.2.post1.tar.gz
  • Upload date:
  • Size: 2.1 MB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for pylibheif-1.21.2.post1.tar.gz
Algorithm Hash digest
SHA256 f78d75f311b5061f1bffc7304df23cdfec55ddb2a87fe83d113018920c92e0d3
MD5 71f28ac88023837088ae4a187a6fc2ba
BLAKE2b-256 5201ad7477c285d072dfc6638d95e67b8b99e55e65f161b3ad169053b63d0ec2

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1.tar.gz:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pylibheif-1.21.2.post1-cp313-cp313-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for pylibheif-1.21.2.post1-cp313-cp313-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 ebd21b6499be85d29c2e2e8f4b43481604693313ab15ba420981984f08a56003
MD5 acc44ba83f9261101928c697cff5e704
BLAKE2b-256 ec976babd2b6369196d4664cc5cec6cb0542ba6a2d1eba99844d36615fb340fb

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1-cp313-cp313-manylinux_2_28_x86_64.whl:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pylibheif-1.21.2.post1-cp313-cp313-macosx_14_0_arm64.whl.

File metadata

File hashes

Hashes for pylibheif-1.21.2.post1-cp313-cp313-macosx_14_0_arm64.whl
Algorithm Hash digest
SHA256 67eec504edb54aa15b25c093d44b29975bfd2bb9b5602ecdedfdf667e167b889
MD5 85a5fce5e13c6448b996bd786f0ecbea
BLAKE2b-256 badbfdce41e370d134fb06c837e2d5d0a50a2f28b5e4072878c5e0251ac51231

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1-cp313-cp313-macosx_14_0_arm64.whl:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pylibheif-1.21.2.post1-cp312-cp312-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for pylibheif-1.21.2.post1-cp312-cp312-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 f735a31a8291bf5cbbabe978fd996a312506ee558ac973ffb85699ffa234c1d4
MD5 03832bf867ac9f43d727be20624f2205
BLAKE2b-256 3023b803a54e335be6cc76005340419c71016c6217b38bdc3675395a8d4f2415

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1-cp312-cp312-manylinux_2_28_x86_64.whl:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pylibheif-1.21.2.post1-cp312-cp312-macosx_14_0_arm64.whl.

File metadata

File hashes

Hashes for pylibheif-1.21.2.post1-cp312-cp312-macosx_14_0_arm64.whl
Algorithm Hash digest
SHA256 4eda5a2e7e33447a1f6bfc7d2f3fa5f9f95d7495a92537807a837f85d940cf26
MD5 4a27d1a854d17e232561784f82d90971
BLAKE2b-256 e1e44a223097686ae3690783cfd9558f5a2138d349e744e07f9cd2d234b80ceb

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1-cp312-cp312-macosx_14_0_arm64.whl:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pylibheif-1.21.2.post1-cp311-cp311-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for pylibheif-1.21.2.post1-cp311-cp311-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 9cf1fbd2608160d2b68015fdb1f06fac1c8c19a18c8e4125d694329e4590cdf1
MD5 c5a6175ebdbddf7de06784a70cff83c4
BLAKE2b-256 f96fefb864cfecf3aab40efc6433927375a0f14bb2d513ec67b49f9bf5c89db5

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1-cp311-cp311-manylinux_2_28_x86_64.whl:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file pylibheif-1.21.2.post1-cp311-cp311-macosx_14_0_arm64.whl.

File metadata

File hashes

Hashes for pylibheif-1.21.2.post1-cp311-cp311-macosx_14_0_arm64.whl
Algorithm Hash digest
SHA256 8ee5ccfa7ad7f0d05a78eba94dca034f5b46cc70697f016ebaba27a400c0473b
MD5 f1ede3559b48c7afa0401f37fc7960c7
BLAKE2b-256 5a36f08cb30ef7dcb3da4b3cbdfb56df27a2a827816999df9e7f93cfc2a57be4

See more details on using hashes here.

Provenance

The following attestation bundles were made for pylibheif-1.21.2.post1-cp311-cp311-macosx_14_0_arm64.whl:

Publisher: build.yml on twn39/pylibheif

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page