libultrahdr

repository·main·Indexed 43 days ago

https://github.com/google/libultrahdr

An image compression library using gain map technology to enable high dynamic range (HDR) imaging while maintaining backward compatibility with SDR readers. It supports JPEG, HEIF/HEIC, and AVIF outputs, providing format-agnostic decoding and encoding APIs. The library is compatible with Android, Linux, macOS, and Windows, and supports ISO 21496-1 gain map encoding/decoding.

Tokens
8.5K
Snippets
21
Records
32
Agent score
56%

What's inside libultrahdr

  1. Overview of libultrahdr and Gain Map technology

    main

    libultrahdr is an image compression library that uses gain map technology to store and distribute HDR images.

    How it works:

    1. Encoding: The library takes an SDR rendition and an HDR rendition of an image. It computes a Gain Map (the quotient between the two renditions).
    2. Storage: The resulting file contains the base image (SDR), the gain map image, and associated metadata. This format is backward compatible: legacy readers that do not understand gain maps will simply display the base SDR image, while compatible readers combine the SDR and gain map to render a high dynamic range image.

    For deeper technical details on the format, refer to the android hdr-image-format guide.

  2. Supported Encode Intent Modes for HEIF and AVIF

    main

    When using HEIF or AVIF containers, the encoder supports specific intent modes for handling HDR data:

    • Encode API-0 (HDR Raw Intent): Input is a raw HDR image (uhdr_enc_set_raw_image(..., UHDR_HDR_IMG)). The library automatically tone-maps to an SDR base, computes the gain map, and encapsulates everything via libheif.
    • Encode API-1 (HDR + SDR Raw Intents): Input consists of both a raw HDR image and a raw SDR image. The gain map is generated from the difference between the two.
    • Pre-compressed Intents (API-2/3/4): These are specific to JPEG workflows. For HEIF/AVIF, pre-compressed intent transcoding is not supported and will return UHDR_CODEC_UNSUPPORTED_FEATURE.
  3. Understand the UltraHDR C++ Class Hierarchy

    main

    In v2.0.0, the C++ architecture is reorganized into a base class with format-specific subclasses to avoid duplicating gain map math.

    • UltraHdr (<ultrahdr/ultrahdrcommon.h>): The base class containing shared, format-independent algorithms like generateGainMap(), applyGainMap(), color space transformations, and metadata encoding/decoding (uhdr_gainmap_metadata_ext_t).
    • JpegR (<ultrahdr/jpegr.h>): Handles JPEG MPF, EXIF, and XMP markers. Uses encodeJpegR() and decodeJpegR().
    • HeifUltraHdr (<ultrahdr/heifultrahdr.h>): Handles HEVC bitstream via libheif. Uses encodeHeicUltraHdr() and decodeHeicUltraHdr().
    • AvifUltraHdr (<ultrahdr/avifultrahdr.h>): Handles AV1 bitstream via libheif. Uses encodeAvifUltraHdr() and decodeAvifUltraHdr().
  4. Build libultrahdr on Linux

    main

    To build on Linux, install prerequisites via apt and use the following commands. It is recommended to use -DUHDR_BUILD_DEPS=1 to ensure all necessary patches (like the libheif ISO 21496-1 patch) are applied correctly.

    Prerequisites: sudo apt install cmake pkg-config libjpeg-dev ninja-build

    Build and Test:

    cmake -G Ninja -DCMAKE_C_COMPILER=clang -DCMAKE_CXX_COMPILER=clang++ -DUHDR_BUILD_TESTS=1 ../
    ninja
    ctest

    Installation: sudo ninja install

    Runtime Note: If binaries cannot find the library at runtime, add /usr/local/lib to your LD_LIBRARY_PATH: export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/lib

    # Prerequisites
    sudo apt install cmake pkg-config libjpeg-dev ninja-build
    
    # Build
    cmake -G Ninja -DCMAKE_C_COMPILER=clang -DCMAKE_CXX_COMPILER=clang++ -DUHDR_BUILD_TESTS=1 ../
    ninja
    ctest
    
    # Install
    sudo ninja install
  5. Build libultrahdr from source using CMake

    main

    To build libultrahdr, you need CMake (v3.15+) and a C++ compiler supporting C++17. The library can be built using the following general steps:

    1. Clone the repository and enter the directory.
    2. Create and enter a build directory.
    3. Run CMake configuration with desired options.
    4. Run the build command (e.g., ninja or cmake --build).

    Note on Dependencies: You can avoid manual dependency installation by passing -DUHDR_BUILD_DEPS=1 during configuration. This will automatically clone and statically build libjpeg-turbo and libheif (with the ISO 21496-1 gain map patch).

    git clone https://github.com/google/libultrahdr.git
    cd libultrahdr
    mkdir build_directory
    cd build_directory
    
    # Example configuration with bundled dependencies
    cmake -G Ninja -DUHDR_BUILD_DEPS=1 ../
    
    # Build
    ninja
  6. Cross-compile libultrahdr for Android

    main

    To cross-compile for Android, you must have the Android NDK installed. You can specify the target architecture using -DANDROID_ABI.

    Supported ABIs: armeabi-v7a, arm64-v8a, x86, x86_64.

    Build Command:

    cmake -G Ninja \
      -DCMAKE_TOOLCHAIN_FILE=../cmake/toolchains/android.cmake \
      -DUHDR_ANDROID_NDK_PATH=/path/to/android-ndk \
      -DUHDR_BUILD_DEPS=1 \
      -DANDROID_ABI="arm64-v8a" \
      -DANDROID_PLATFORM=android-23 ../
    ninja
    # Example for arm64-v8a
    cmake -G Ninja \
      -DCMAKE_TOOLCHAIN_FILE=../cmake/toolchains/android.cmake \
      -DUHDR_ANDROID_NDK_PATH=/opt/android-ndk-r26d/ \
      -DUHDR_BUILD_DEPS=1 \
      -DANDROID_ABI="arm64-v8a" \
      -DANDROID_PLATFORM=android-23 ../
    ninja
  7. Enable HEIF/AVIF support via UHDR_ENABLE_HEIF

    main

    To use HEIF or AVIF support, you must enable the UHDR_ENABLE_HEIF compile-time flag during the build process. This links libheif into the library.

    If UHDR_ENABLE_HEIF is disabled, libultrahdr builds as a standalone, zero-dependency JPEG-only library.

    CMake Usage: To enable support when building from source using CMake, use the following flag:

    -DUHDR_ENABLE_HEIF=ON
  8. Build fuzzers for libultrahdr

    main

    To build the libultrahdr fuzzers, you must use a compiler that supports -fsanitize=fuzzer and -fsanitize=fuzzer-no-link (e.g., clang 12 or later).

    Use CMake with the UHDR_BUILD_FUZZERS=1 flag to enable the build process. This generates two fuzzers in your build directory:

    • ultrahdr_enc_fuzzer: The encoder fuzzer.
    • ultrahdr_dec_fuzzer: The decoder fuzzer.
    cmake -G Ninja ../ -DCMAKE_C_COMPILER=clang -DCMAKE_CXX_COMPILER=clang++ -DUHDR_BUILD_FUZZERS=1
    ninja
  9. Enable HEIF and AVIF Gain Map support

    main

    libultrahdr supports ISO 21496-1 gain map encoding/decoding in HEIF and AVIF containers via libheif.

    Use -DUHDR_BUILD_DEPS=1 to automatically download and build a patched version of libheif that includes the required ISO 21496-1 gain map support.

    cmake -G Ninja -DUHDR_BUILD_DEPS=1 -DUHDR_BUILD_TESTS=1 ../
    ninja

    Option 2: System libheif

    If you use a system-installed libheif, ensure it provides the ISO 21496-1 gain map APIs. If it does not, UHDR_ENABLE_HEIF will be disabled with a warning.

    Runtime Codec Plugins

    For full-pixel encoding/decoding, ensure the following plugins are installed on your system (e.g., on Debian/Ubuntu):

    • HEVC Decode: libheif-plugin-libde265
    • HEVC Encode: libheif-plugin-x265
    • AV1 Decode: libheif-plugin-dav1d
    • AV1 Encode: libheif-plugin-aomenc

    If plugins are in a custom directory, set LIBHEIF_PLUGIN_DIRECTORY: export LIBHEIF_PLUGIN_DIRECTORY=/path/to/plugins

    # Recommended way to ensure full support
    cmake -G Ninja -DUHDR_BUILD_DEPS=1 -DUHDR_BUILD_TESTS=1 ../
    ninja
  10. Run libultrahdr fuzzers

    main

    To run the fuzzers, you must first create a corpus directory containing initial "seed" sample inputs.

    • For the decoder fuzzer (ultrahdr_dec_fuzzer), use UltraHDR JPEG images as seeds.
    • For the encoder fuzzer (ultrahdr_enc_fuzzer), use sample YUV files as seeds.

    After preparing the corpus, execute the fuzzer binaries pointing to that directory.

    mkdir CORPUS_DIR
    cp seeds/* CORPUS_DIR
    ./ultrahdr_dec_fuzzer CORPUS_DIR
    ./ultrahdr_enc_fuzzer CORPUS_DIR