ImageLensCorrection

ImageLensCorrection provides corrections for the four most common camera-lens defects — radial (barrel/pincushion) distortion, vignetting, lateral chromatic aberration (TCA), and geometric projection — for images created or processed with the :image library. Calibration coefficients come from the lensfun project's community-maintained database, which is bundled with the package as a compact ~5 MB Erlang term file covering 1000+ camera bodies and 1400+ lenses.

Corrections are evaluated as libvips arithmetic expressions on top of Vix, so every correction stays inside the Vix pipeline; no external C library is required at runtime.

Documentation can be found at https://hexdocs.pm/image_lens_correction.

Features

Installation

The package can be installed by adding image_lens_correction to your list of dependencies in mix.exs:

def deps do
  [
    {:image_lens_correction, "~> 0.1.0"}
  ]
end

Usage

One-shot correction from EXIF

For an image whose EXIF metadata identifies the camera and lens, all available corrections (distortion, vignetting and TCA) can be applied with a single call:

{:ok, image}     = Image.open("photo.jpg")
{:ok, corrected} = Image.LensFun.Correct.correct(image)

For an image without complete EXIF metadata, supply the missing parameters as options. Every parameter that correct/2 reads from EXIF is overridable:

{:ok, corrected} =
  Image.LensFun.Correct.correct(image,
    make: "Canon",
    model: "Canon EOS 5D Mark III",
    lens_make: "Canon",
    lens_model: "Canon EF 100mm f/2.8 Macro USM",
    focal_length: 100.0,
    aperture: 5.6
  )

The :corrections option selects which corrections to run; the default is [:distortion, :vignetting, :tca]. Projection conversion is opt-in (since it changes the field of view) via corrections: [:projection] and an optional :target_projection.

Direct correction with explicit coefficients

When you have your own calibration data — or you're experimenting — each model is exposed as a standalone function that takes raw coefficients in the Hugin coordinate convention (r = 1 at the half short-edge for distortion / TCA / projection, r = 1 at the corner for vignetting):

# ptlens distortion (Hugin form)
{:ok, image} = Image.LensCorrection.radial_distortion_correction(image, -0.0077, 0.087, 0.0)

# poly3 distortion
{:ok, image} = Image.LensCorrection.poly3_correction(image, -0.005)

# poly5 distortion
{:ok, image} = Image.LensCorrection.poly5_correction(image, -0.005, 0.001)

# Vignetting (Adobe Camera Model "pa")
{:ok, image} = Image.LensCorrection.vignette_correction(image, -0.2764, -1.26031, 0.7727)

# Linear TCA
{:ok, image} = Image.LensCorrection.Tca.linear_tca_correction(image, 1.0004, 1.0002)

# Fisheye → rectilinear
focal = Image.LensCorrection.Geometry.focal_length_in_pixels(8.0, 1.5, 5000.0)
{:ok, image} = Image.LensCorrection.Geometry.fisheye_to_rectilinear(image, focal)

Database lookup

# Find a lens (case-insensitive maker, fuzzy-substring model)
{:ok, lens} = Image.LensFun.find_lens("Canon", "Canon EF 100mm f/2.8 Macro USM")

# Interpolate the calibration to a specific focal length
{:ok, distortion} = Image.LensFun.interpolate_distortion(lens, 100.0)

# Vignetting needs focal length, aperture and focus distance
{:ok, vignetting} = Image.LensFun.interpolate_vignetting(lens, 100.0, 5.6, 1000.0)

# TCA needs focal length only
{:ok, tca} = Image.LensFun.interpolate_tca(lens, 100.0)

# Apply the result
{:ok, image} = Image.LensCorrection.apply_distortion(image, distortion)
{:ok, image} = Image.LensCorrection.apply_vignetting(image, vignetting)
{:ok, image} = Image.LensCorrection.Tca.apply_tca(image, tca)

Background

The lens defects this library corrects, the mathematical models it uses, and the relationship to the upstream lensfun project are described in detail in the Lens corrections guide.

Rebuilding the bundled database

git clone https://github.com/lensfun/lensfun ../lensfun
mix run -e 'Image.LensFun.Importer.import()'

Attribution

This library re-implements the calibration math and bundles a snapshot of the calibration data from the lensfun project. Lens calibration data is distributed under CC BY-SA 3.0; the lensfun reference C library is LGPL v3 (this library does not link to or distribute it).

License

ImageLensCorrection is licensed under the Apache 2.0 License.