A Python wrapper of libjpeg-turbo for decoding and encoding JPEG images.
npx @tessl/cli install tessl/pypi-pyturbo-jpeg@1.8.0A Python wrapper of libjpeg-turbo for decoding and encoding JPEG image. Provides high-performance JPEG operations with comprehensive functionality for image manipulation including direct decoding to BGR/grayscale/YUV arrays, in-place operations for memory efficiency, image scaling with quality control, lossless cropping, and advanced encoding options.
pip install git+https://github.com/lilohuang/PyTurboJPEG.gitfrom turbojpeg import TurboJPEGWith constants for formats and options:
from turbojpeg import (
TurboJPEG,
TJPF_BGR, TJPF_RGB, TJPF_GRAY,
TJSAMP_422, TJSAMP_420, TJSAMP_GRAY,
TJFLAG_PROGRESSIVE, TJFLAG_FASTUPSAMPLE, TJFLAG_FASTDCT
)from turbojpeg import TurboJPEG
import numpy as np
# Initialize the JPEG processor
jpeg = TurboJPEG()
# Decode JPEG from file to numpy array
with open('input.jpg', 'rb') as in_file:
bgr_array = jpeg.decode(in_file.read())
# Encode numpy array to JPEG
with open('output.jpg', 'wb') as out_file:
out_file.write(jpeg.encode(bgr_array))
# Get image dimensions without full decode
with open('input.jpg', 'rb') as in_file:
width, height, subsample, colorspace = jpeg.decode_header(in_file.read())
print(f"Image: {width}x{height}")PyTurboJPEG is organized around a single main class that provides access to libjpeg-turbo functionality:
Core decoding functionality for converting JPEG data to numpy arrays, with support for various pixel formats, scaling factors, and output options including YUV and grayscale formats.
def decode_header(jpeg_buf: bytes) -> tuple[int, int, int, int]:
"""Decode JPEG header returning (width, height, subsample, colorspace)"""
def decode(
jpeg_buf: bytes,
pixel_format: int = TJPF_BGR,
scaling_factor: tuple[int, int] | None = None,
flags: int = 0,
dst: np.ndarray | None = None
) -> np.ndarray:
"""Decode JPEG to numpy array"""
def decode_to_yuv(
jpeg_buf: bytes,
scaling_factor: tuple[int, int] | None = None,
pad: int = 4,
flags: int = 0
) -> tuple[np.ndarray, list[tuple[int, int]]]:
"""Decode JPEG to YUV format"""Encoding functionality for converting numpy arrays to JPEG data with quality control, subsampling options, and various pixel format support including progressive encoding.
def encode(
img_array: np.ndarray,
quality: int = 85,
pixel_format: int = TJPF_BGR,
jpeg_subsample: int = TJSAMP_422,
flags: int = 0,
dst: bytearray | None = None
) -> bytes | tuple[bytearray, int]:
"""Encode numpy array to JPEG"""
def encode_from_yuv(
img_array: np.ndarray,
height: int,
width: int,
quality: int = 85,
jpeg_subsample: int = TJSAMP_420,
flags: int = 0
) -> bytes:
"""Encode YUV array to JPEG"""Lossless transformation operations including cropping, scaling with quality adjustment, multiple crop operations, and background filling for extended crops.
def crop(
jpeg_buf: bytes,
x: int, y: int, w: int, h: int,
preserve: bool = False,
gray: bool = False,
copynone: bool = False
) -> bytes:
"""Lossless crop operation"""
def crop_multiple(
jpeg_buf: bytes,
crop_parameters: list[tuple[int, int, int, int]],
background_luminance: float = 1.0,
gray: bool = False,
copynone: bool = False
) -> list[bytes]:
"""Multiple crop/extend operations"""
def scale_with_quality(
jpeg_buf: bytes,
scaling_factor: tuple[int, int] | None = None,
quality: int = 85,
flags: int = 0
) -> bytes:
"""Scale and re-encode with quality"""Buffer size calculation and scaling factor information for optimizing memory usage and determining available scaling options.
def buffer_size(img_array: np.ndarray, jpeg_subsample: int = TJSAMP_422) -> int:
"""Calculate maximum buffer size needed for encoding"""
@property
def scaling_factors(self) -> frozenset[tuple[int, int]]:
"""Available scaling factors for decode operations"""class TurboJPEG:
"""Main wrapper class for libjpeg-turbo operations"""
def __init__(self, lib_path: str | None = None): ...