BSD-3-Clause licensed by Alexey Kuleshevich
Maintained by [email protected]
This version can be pinned in stack with:Color-0.4.0@sha256:cbe782a33790ab40cfba495b444f107511a51072777546a8f008b32c61faaebb,8820

Module documentation for 0.4.0

Used by 2 packages in nightly-2025-03-01(full list with versions):

Color

A library for dealing with Colors and pixels. It implements arbitrary color space conversion, chromatic adaptation and other color manipulations.

Status

Language Github Actions Coveralls Gitter.im
GitHub top language Build Status Coverage Status Join the chat at https://gitter.im/haskell-massiv/Lobby
Package Hackage Nightly LTS
Color Hackage Nightly Nightly

Description

There is a clear separation between color models, color spaces and alternative representations of color spaces. All are distinct at the type level. The goal is to prevent mixups of incompatible color types as well as utilize type information for conversion between them.

Currently supported:

  • Color models:

    • Y
    • RGB
    • HSI
    • HSL
    • HSV
    • YCbCr
    • CMYK
  • Color spaces and arbitrary conversions between them:

    • Y - luminance

    • Y' - luma

    • CIE XYZ

    • CIE L*a*b*

    • DIN99

    • RGB:

      • sRGB - both standardized and derived

      • AdobeRGB - both standardized and derived

      • ITU: Rec470, Rec601 and Rec709

      • Alternative representations:

        • HSI
        • HSL
        • HSV
        • YCbCr
        • CMYK
  • Illuminants:

    • CIE1931 - 2 degree observer
    • CIE1964 - 10 degree observer
    • Some common alternatives
  • Chromatic adaptation:

    • VonKries adaptation with transformations:

      • VonKries
      • Bradford (default)
      • Fairchild
      • CIECAM02
      • CMCCAT2000
  • Color Standards:

    • RAL
    • SVG

Example

Here is a short example how this library can be used. Here we assume a GHCi session that can be started like so:

$ stack ghci --package Color

Perceived lightness

Let’s say we need find the perceived lightness as described in this StackOverflow answer for an RGB triple (128, 255, 65) :: (Word8, Word8, Word8).

Before we can attempt getting the lightness we need to do these two things:

  1. Figure out what is the color space of the RGB triplet? In particular the Illuminant and the Linearity of the RGB color space.
  2. Convert your RGB color to CIE L*a*b* and then we can get the L* out, which is the perceived lightness.

More often than not an RGB image will be encoded in non-linear sRGB color space with 8 bits per channel, so we’ll use that for this example:

ghci> :set -XDataKinds
ghci> import Graphics.Color.Space
ghci> let rgb8 = ColorSRGB 128 255 65 :: Color (SRGB 'NonLinear) Word8
ghci> print rgb8
<SRGB 'NonLinear:(128,255, 65)>

Before we convert sRGB to CIE L*a*b* color space we need to increase the precision to Double, because for now Word8 is not supported by the LAB color space implementation:

ghci> let rgb = toDouble <$> rgb8
ghci> print rgb
<SRGB 'NonLinear:( 0.5019607843137255, 1.0000000000000000, 0.2549019607843137)>

In order to convert to another color space without changing the Illuminant we can use convertColor function. So here is how we convert to CIELAB and extract the perceived lightness L*:

ghci> let lab@(ColorLAB l _ _) = convertColor rgb :: Color (LAB D65) Double
ghci> lab
<LAB * D65:(90.0867507593648500,-65.7999116680496000,74.4643898323530600)>
ghci> l
90.08675075936485

Color adaptation

When a change of Illuminant is also needed during color space conversion we can use convert function

ghci> import Graphics.Color.Adaptation (convert)
ghci> import qualified Graphics.Color.Illuminant.CIE1964 as CIE1964
ghci> let lab@(ColorLAB l _ _) = convert rgb :: Color (LAB 'CIE1964.D50) Double
ghci> lab
<LAB CIE1964 'D50:(90.2287735564601500,-59.3846969983265500,72.9304679742930800)>

External resources

Changes

Changelog for Color

0.4.0

  • Addition of DIN99 color space.
  • Scale L*a*b* color space to [0, 1] range from the more common [0, 100] for consistency.
  • Addition of: toGrayscale, applyGrayscale and replaceGrayscale.
  • Addition of: ChannelCount, channelCount, channelNames and channelColors
  • Remove RealFloat constraint from ColorSpace for Y'

0.3.3

Addition of SVG colors

0.3.2

  • Addition of CIEL*u*v* colorspace and LCh views of both CIEL*a*b* and L*u*v*.

0.3.1

  • Remove RealFloat constraint from ColorSpace for Y'

0.3.0

  • Rename Y color model into X to avoid the annoying name conflict.

  • Add ColorSpace instance for Y' and enrich it with base space info

  • Rename YCbCr -> Y'CbCr and remove explicit linearity from its base space

  • Fix BT470 transfer function. ecctf and dcctf were mixed up.

  • Move transfer and itransfer functions into the RedGreenBlue class

  • Move out ecctf and dcctf functions outside of RedGreenBlue class

  • Remove all customized functions from RGB modules in favor of their respective class implementations:

    • primaries (standalone) -> gamut (in class)
    • transfer (standalone) -> transfer (in class)
    • itransfer (standalone) -> itransfer (in class)
    • npmStandard (standalone) -> npm (in class)
    • inpmStandard (standalone) -> inpm (in class)
  • Addition of coerceGamut

  • Fix re-export of vector’s MVector, Vector type families.

  • Re-arrange how modules are exported a little bit.

0.2.0

  • Addition of CIE1931 RGB color space
  • Add Linearity kind to RedGreenBlue color spaces.
  • Add Default instance for Pixel
  • Addition of universal division (//) to Elevator
  • Addition of CIE1931 RGB color space.
  • Fix show instance for floating point colors: adjust formatting in Elevator for Float and Double
  • Add record accessor functions: chromaticityCIExyY, whitePointChromaticity
  • Fix show instance for Gamut
  • Remove deprecated: CIECAM02 and ciecam02Adaptation

0.1.4

  • Export pixelColor
  • Add luma related patterns: PixelY', PixelY'A, Y' and Y'A. Also rgbPixelLuma

0.1.3.1

  • Fix introduced in 0.1.2 for Alpha cs was incomplete and is fixed in this version without breakage.

0.1.3 (deprecated)

  • Addition of CMCCAT2000.
  • Rename CIECAM02 to CIECAT02 with a fallback synonym for backwards compatibility
  • Fix ColorSpace instance for Alpha cs
  • Add ColorSpace instances for YCbCr cs color spaces that have Luma instance: BT709, BT601_525 and BT601_625

0.1.2

  • Fix YCbCr conversion to derived RGB color spaces
  • Fix conversion of toWord64 (1 :: Double) and toWord632 (1 :: Float).
  • Addition of xyzColorMatchingFunctions and spectralPowerDistributions

0.1.1

  • Addition of Graphics.Color.Illuminant.Wikipedia module
  • Addition of convertColor and convertColorFloat functions

0.1.0

Initial alpha release