Skip to content
AI360Xpert
Beta

HDR Imaging

HDR imaging fuses bracketed exposures into one photo that holds both sunlit clouds and shadowed streets, beyond any single sensor capture.

HDR fuses bracketed exposures by weighting each pixel's cleanest capture, then tone maps the result for display
HDR fuses bracketed exposures by weighting each pixel's cleanest capture, then tone maps the result for display

Why Does This Exist?

Sensors capture about 1212 stops of light; noon streets span 2020. Single shots choose: white skies or black shadows, never both. The information exists across time, a fast shot holds highlights, a slow one holds shadows, but no single capture holds the scene.

HDR fuses the bracket. Each exposure contributes its clean pixels, weighted by how well-exposed each pixel is, into a wide-range radiance map. Tone mapping then compresses that map onto displays without flattening its local contrast. The capture physics behind exposures is covered in image formation and camera model.

Think of It Like This

A committee writing one report from three drafts

Three reporters cover one event: one catches the opening quotes, one the closing scene, one the middle chaos. An editor fuses the best paragraph from each draft into one report reading as if a single omniscient witness wrote it.

Exposures are the drafts and weight maps are the editor's taste. The report fails when drafts disagree about facts, a moved car appearing in two drafts at once, and the editor must pick one truth, which is ghosting below.

How It Actually Works

Capture a bracket, typically −2-2, 00, +2+2 EV. Recover each frame's response curve to linearise intensities into a common radiance domain, align frames against handshake, then merge with weights favouring mid-tones:

H=∑iw(zi) Ei/ti∑iw(zi),w(z)=min⁡(z,1−z)H = \frac{\sum_i w(z_i) \, E_i / t_i}{\sum_i w(z_i)}, \qquad w(z) = \min(z, 1-z)

Ei/tiE_i/t_i is frame ii's radiance estimate, ziz_i its normalised pixel, and the hat-shaped ww peaks at mid-grey where sensors are cleanest. Deghosting masks or rejects moving pixels before merging. Global-plus-local tone mapping compresses HH to display range while preserving local contrast.

Worked example

Sky pixel: dark frame reads 0.150.15 (clean), normal frame 0.950.95 (clipping), bright frame 1.01.0 (blown). Weights 0.150.15, 0.050.05, 0.00.0 route the merge to the dark frame's estimate almost entirely. Shadow pixel inverts the routing toward the bright frame. The fused radiance spans 1:10,0001:10{,}000 where each single frame spanned 1:2561:256, and tone mapping renders both ends viewable at once.

Code

Hat-weight fusion of one pixel across a three-frame bracket.

import numpy as np

def hat_merge(readings: np.ndarray) -> float:    """Fuse normalised bracket readings with mid-tone weights."""    w = np.minimum(readings, 1 - readings)  # clean mid-tones weigh most    return round(float((w * readings).sum() / w.sum()), 3)

print(hat_merge(np.array([0.15, 0.95, 1.0])))  # -> 0.35 dark frame dominates

Watch Out For

Ghosts from motion between frames

Anything moving, pedestrians, leaves, water, lands at different pixels per frame. Naive merging prints translucent doubles that read as processing errors, not art.

Align carefully and deghost explicitly: detect inconsistent pixels and take them from one reference frame. For heavy motion, single-image HDR avoids ghosts at truth cost.

Overcooked tone mapping halos

Aggressive local mapping rings every high-contrast edge with glowing halos and turns skies to grey mud. The HDR look dates photos instantly and destroys the naturalism fusion worked to save.

Favour gentle global curves with restrained local strength. Judge at full size; thumbnails hide halos.

The Quick Version

  • Bracketed exposures span scenes no single capture holds, 1:10,0001:10{,}000 versus 1:2561:256.
  • Hat weights route each pixel to its cleanest capture automatically.
  • Our sky pixel fuses to 0.350.35, dominated by the dark frame's clean reading.
  • Deghosting handles motion; tone mapping compresses radiance for display.
  • Ghosts and halo overcooking are the two signature failures.