JPEG XL (.jxl)

Technology & Engineering Advanced file-formats-skills universal
0 Upvotes
3 Views
0 Downloads
1,507 Words

Description

Expert guidance on JPEG XL: explain modes, progressive decoding, HDR, and when to use it in image workflows.

When to Use

tell me about JPEG XL features and usage | should i use jpeg xl for archival images | compare jpeg xl to jpeg for image storage | explain progressive decoding in jpeg xl

Use Cases

Assess space savings when transcoding legacy JPEGs to JPEG XL. | Plan progressive delivery for large images with DC previews. | Evaluate lossless vs lossy modes for archival images. | Support HDR and wide-gamut workflows in digital publishing.

SKILL.md Content

---
name: jxl
description: "Expert guidance on JPEG XL: explain modes, progressive decoding, HDR, and when to use it in image workflows."
metadata:
  tags: "file-formats, image-compression, jpeg-xl, lossless, lossy, progressive-decoding, hdr"
  source: "https://skilldb.dev/skills/file-formats-skills/jxl"
  pack: "file-formats-skills"
  category: "Technology & Engineering"
---

# JPEG XL (.jxl)

## When to use this skill
Use when the user says things like:
- "tell me about JPEG XL features and usage"
- "should i use jpeg xl for archival images"
- "compare jpeg xl to jpeg for image storage"
- "explain progressive decoding in jpeg xl"


You are a file format specialist with deep knowledge of the JPEG XL image format, its compression technology, progressive delivery, and the ongoing debate over its adoption.

## Overview

JPEG XL was developed by the Joint Photographic Experts Group and standardized as ISO/IEC 18181 (published in parts from 2022). It was designed as a comprehensive successor to legacy JPEG, combining the best features of Google's PIK and Cloudinary's FUIF proposals. JPEG XL is unique among next-gen formats in its ability to losslessly transcode existing JPEG files to ~20% smaller sizes while allowing exact reconstruction of the original JPEG bitstream. The format supports progressive decoding, HDR, wide gamut, animation, and both lossy and lossless modes. Despite strong technical merits, its future is uncertain after Google removed JPEG XL support from Chrome in 2022, though Safari and other ecosystems continue support.

## Technical Specifications

- **File extension(s):** `.jxl`
- **MIME type:** `image/jxl`
- **Compression type:** Lossy (VarDCT transform coding with variable block sizes 8x8 to 256x256), lossless (Modular mode with prediction and entropy coding), and JPEG recompression (lossless repackaging of JPEG data)
- **Color depth:** Up to 32-bit float per channel. Standard: 8-bit, 10-bit, 12-bit, 16-bit integer and half-float. Full HDR with PQ and HLG transfer functions.
- **Max dimensions:** 2^30 - 1 (over 1 billion) pixels per dimension
- **Max channels:** 4096+ extra channels (alpha, depth, selection masks, spot colors)
- **Transparency:** Full alpha channel at any bit depth
- **Animation:** Frame-based animation with partial frame updates (only changed regions re-encoded)
- **Progressive decode:** Designed for progressive rendering; DC coefficients provide a ~1/8 resolution preview, then progressively refines. This is a core architectural feature, not an afterthought.
- **Metadata support:** EXIF, XMP, JUMBF, ICC color profiles (natively supports Display P3, Rec. 2020, PQ, HLG without ICC overhead)
- **JPEG recompression:** Existing JPEG files can be losslessly converted to JXL (~20% size reduction) and perfectly reconstructed back to the identical JPEG bitstream
- **Color spaces:** Linear light, sRGB, Display P3, Rec. 2020, PQ, HLG, arbitrary ICC profiles. Native support means no ICC profile embedding needed for common spaces.
- **Responsive rendering:** A single JXL file can serve multiple resolutions via progressive decode (no need for multiple srcset files)

## How to Work With It

### Opening & Viewing

- **Safari:** 17+ (September 2023, full support)
- **Chrome:** Removed in version 110 (February 2023). Was behind a flag in 91-109.
- **Firefox:** Behind a flag (`image.jxl.enabled` in about:config); not enabled by default
- **Edge:** Not supported (follows Chrome)
- **Windows:** Via third-party viewers or jxl-winthumb for Explorer thumbnails
- **macOS:** Supported in Ventura 13.0+ via system image frameworks
- **iOS:** 17+ natively
- **Viewers:** XnView MP, IrfanView (with plugin), ImageGlass

### Creating & Editing

- **Reference encoder:** `cjxl input.png output.jxl -q 75` (lossy) or `cjxl input.png output.jxl -q 100` (lossless)
- **Quality scale:** 0-100 where 100 is mathematically lossless. Quality 75-85 is excellent for photos.
- **Effort/speed:** `-e 7` (1-9 scale, higher = slower + smaller). Default is 7.
- **JPEG recompression:** `cjxl input.jpg output.jxl` (automatic lossless JPEG recompression; no quality parameter needed)
- **ImageMagick:** 7.1.0-20+ with libjxl delegate: `magick input.png output.jxl`
- **GIMP:** Plugin available for import/export
- **Encoding speed:** Competitive with JPEG at lower effort levels; significantly faster than AVIF at comparable quality

### Converting To/From

- **To JXL (lossy):** `cjxl photo.png photo.jxl -q 80 -e 7`
- **To JXL (from JPEG, lossless):** `cjxl photo.jpg photo.jxl` (~20% smaller, perfectly reversible)
- **From JXL:** `djxl photo.jxl photo.png` or `djxl photo.jxl photo.jpg`
- **Reconstruct JPEG:** `djxl photo.jxl photo.jpg` (if originally created from JPEG recompression, produces bit-identical JPEG)
- **Batch convert:** `for f in *.jpg; do cjxl "$f" "${f%.jpg}.jxl"; done`
- **Python:** `import jxlpy; jxlpy.encode("input.png", "output.jxl", quality=80)`

## Common Use Cases

- Web image delivery (where browser support exists, primarily Safari/Apple ecosystem)
- Photo archival with lossless JPEG recompression (immediate 20% storage savings)
- HDR photo delivery
- Progressive image loading (single file serves low-res preview through full resolution)
- Photography workflows (replacement for JPEG as camera output format)
- Image CDN storage optimization
- Print-ready image delivery (CMYK-like support via extra channels)
- Animation (more efficient than GIF or APNG)

## Pros & Cons

**Pros:**
- Superior compression (often best-in-class across both lossy and lossless)
- Lossless JPEG recompression with perfect bit-level reconstruction
- True progressive decode built into the format architecture
- Fastest encoding speed among next-gen formats at comparable quality
- HDR and wide gamut as first-class features
- Royalty-free licensing
- Extremely large dimension and channel count support
- Responsive image delivery from a single file
- JPEG Committee backing (ISO standard)

**Cons:**
- No Chrome or Edge support (removed in 2023; the single biggest adoption barrier)
- Firefox support only behind a flag
- Limited ecosystem tooling compared to WebP and AVIF
- Political/corporate dynamics around adoption (Google's removal was controversial)
- Uncertain future due to browser support gaps
- Not yet widely supported in CMSs, CDNs, or image processing services
- Reference encoder is fast but ecosystem maturity is still developing

## Compatibility

| Platform | Support |
|----------|---------|
| Safari | 17+ (September 2023) |
| Chrome | Removed (was experimental in 91-109) |
| Firefox | Flag only (image.jxl.enabled) |
| Edge | Not supported |
| iOS | 17+ |
| macOS | Ventura 13.0+ |
| Windows | Third-party viewers only |
| GIMP | Via plugin |
| Krita | 5.2+ |
| Cloudinary | Supported |
| Fastly | Supported |

## Practical Usage

### Losslessly recompress a JPEG photo archive to save ~20% storage

```bash
# Convert a single JPEG to JXL (lossless, perfectly reversible)
cjxl photo.jpg photo.jxl

# Batch convert an entire photo library
find /photos -name '*.jpg' -print0 | while IFS= read -r -d '' f; do
    cjxl "$f" "${f%.jpg}.jxl"
    original=$(stat -c%s "$f")
    compressed=$(stat -c%s "${f%.jpg}.jxl")
    savings=$(( (original - compressed) * 100 / original ))
    echo "$f: ${savings}% smaller"
done

# Reconstruct the original JPEG bit-for-bit
djxl photo.jxl photo_restored.jpg
# Verify: diff <(md5sum photo.jpg) <(md5sum photo_restored.jpg)
```

### Encode lossy JPEG XL for web delivery with progressive decode

```bash
# High-quality lossy encoding for photography
cjxl photo.png photo.jxl -q 80 -e 7

# Fast encoding for batch processing (lower effort)
cjxl photo.png photo.jxl -q 75 -e 4

# Lossless encoding (for screenshots, diagrams)
cjxl screenshot.png screenshot.jxl -q 100 -e 7

# Compare quality metrics
ssimulacra2 original.png compressed.jxl
# Score > 70 is visually excellent, > 90 is near-transparent
```

### Serve JPEG XL with content negotiation and Safari support

```python
# Python Flask — serve JXL to Safari, JPEG to others
from flask import Flask, request, send_file
app = Flask(__name__)

@app.route('/images/<name>')
def serve_image(name):
    accept = request.headers.get('Accept', '')
    base = name.rsplit('.', 1)[0]

    if 'image/jxl' in accept:
        jxl_path = f'static/images/{base}.jxl'
        return send_file(jxl_path, mimetype='image/jxl')
    else:
        return send_file(f'static/images/{name}')
```

```nginx
# Nginx — content negotiation for JXL
map $http_accept $jxl_suffix {
    default   "";
    "~*jxl"   ".jxl";
}

location /images/ {
    add_header Vary Accept;
    try_files $uri$jxl_suffix $uri =404;
}
```

## Anti-Patterns

**Deploying JPEG XL as the sole image format for web delivery.** JPEG XL lacks Chrome and Edge support (removed in 2023) and is only behind a flag in Firefox. Serving JXL without fallback formats leaves the majority of web users unable to see images. Always implement content negotiation or use `<picture>` with JPEG/WebP fallbacks.

**Re-encoding a lossy JPEG to lossy JXL instead of using lossless JPEG recompression.** Transcoding a JPEG with a lossy quality setting applies a second generation of lossy compression, degrading quality. When the source is JPEG, always use `cjxl input.jpg output.jxl` without a quality flag to trigger lossless JPEG recompression, which preserves exact quality while saving ~20% space.

**Using low effort settings and blaming JXL for poor compression ratios.** JPEG XL's compression efficiency scales significantly with effort level. Encoding at effort 1-3 produces results barely better than JPEG. Use effort 7 (default) for production encoding, and only drop to effort 4-5 for real-time or batch scenarios where encoding speed is critical.

**Discarding original JPEGs after lossless JXL conversion without verifying round-trip fidelity.** While JXL's JPEG recompression is designed to be bit-identical on reconstruction, always verify the round-trip on a sample before bulk-deleting originals. Run `djxl` to reconstruct and compare checksums to confirm your toolchain produces identical output.

**Assuming JPEG XL will eventually gain Chrome support and building infrastructure around it.** The Chrome removal was a deliberate decision, not a temporary setback. Building web infrastructure solely around JXL availability is speculative. Design systems that treat JXL as one option in a multi-format pipeline alongside AVIF and WebP.

## Related Formats

- **JPEG:** The legacy format JPEG XL is designed to replace and can losslessly recompress
- **AVIF:** Competing next-gen format; better browser support (Chrome, Firefox) but slower encoding and no progressive decode
- **WebP:** Established web format; JPEG XL surpasses it technically but has weaker browser support
- **HEIC:** Apple's photo format; JPEG XL offers similar quality with royalty-free licensing
- **PNG:** JPEG XL lossless mode typically achieves better compression than PNG
- **JPEG 2000:** Previous JPEG successor; limited adoption despite strong technical foundation