Changelog

Copy Markdown

All notable changes to this project are documented here. The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

[0.11.0] — April 20th, 2026

Added

  • Add :chroma_ceiling option and expose :gamut in tonal visualizer.

  • Drop seed label on gamut plot and add white-point legend entry.

  • Propagate palette gamut and ceiling between tonal and gamut tabs

[0.10.0] — April 19th, 2026

Added

[0.9.0] — April 16th, 2026

Bug Fixes

  • Add the seed as a URL param so the seed travels to each tab in the visualizer.

[0.8.0] — April 16th, 2026

Bug Fixes

  • Smooth the tonal lightness gradient for the palette.

Changed

  • Generate Tailwind 4 classes, not Tailwind 3.

[0.7.0] — April 16th, 2026

Changed

  • Generate Tailwind 4 classes, not Tailwind 3.

[0.6.0] — April 15th, 2026

Added

  • Color.Palette.semantic/3 and semantic_categories/0 — synthesise a colour in a chosen category (semantic :success, :danger, :warning, :info, :neutral, or raw hue :red, :orange, :yellow, :green, :teal, :blue, :purple, :pink) from a seed while preserving the seed's Oklch lightness and chroma. Lets a brand colour drive a matched set of semantic accents — a success green that feels like the same palette as the brand blue — without hand-picking every one. Options: :chroma_factor to mute, :lightness to override, :gamut to target a non-sRGB display. Canonical workflow is semantic/3 → any palette generator (tonal/2, theme/2, contrast/2, contrast_scale/2) to produce a full scale for the role.

  • Palette gamut checks. Color.Palette.in_gamut?/2 and Color.Palette.gamut_report/2 answer "is every stop in this palette inside the chosen RGB working space?", with gamut_report/2 returning a per-stop breakdown listing exactly which stops failed.

  • Public APIs for designer-tool integrations.

  • Color.Gamut.Diagram — pure-data module for chromaticity diagrams.

  • Color.Palette.Visualizer gains a /gamut tab rendering an inline SVG chromaticity diagram.

  • Color.Palette.ContrastScale — a fourth palette algorithm, inspired by Matt Ström-Awn's Generating colour palettes with math.

  • Color.DesignTokens — encode and decode W3C Design Tokens Community Group color tokens (2025.10 draft).

  • Color.Palette.Tonal.to_tokens/2, Color.Palette.Theme.to_tokens/2, and Color.Palette.Contrast.to_tokens/2 emit each palette type as a DTCG-compliant token map ready for :json.encode/1.

  • Color.Palette.Visualizer Tonal and Theme views now include a "Design Tokens (W3C DTCG)" export block alongside the existing CSS custom properties and Tailwind config blocks, showing the palette as pretty-printed JSON ready to copy into a tokens.json file.

  • Color.Palette.Visualizer seed input is now a native <input type="color"> paired with a text input. Clicking the picker opens the OS colour picker; typing a named colour, oklch(...), or any other CSS syntax still works via the text field. On submit the server prefers the text field if it was changed, otherwise uses the picker's value. The picker is pre-initialised to the resolved hex of whatever the current seed is, so seed=rebeccapurple opens the picker on #663399.

[0.5.0] — April 14th, 2026

Added

[0.4.0]

Added

  • Color.LED module with support for multi-channel addressable LED pixels that include extra white channels. Color.LED.RGBW covers four-channel pixels (R, G, B, W) used by WS2814 and SK6812-RGBW. Color.LED.RGBWW covers five-channel RGB+CCT pixels (R, G, B, WW, CW) used by WS2805 and several SK6812 variants. Both provide from_srgb/2, to_srgb/1, and to_xyz/1. Color.LED.chip_options/1 returns recommended extraction options for common chip variants (:ws2814_ww, :ws2814_nw, :ws2814_cw, :sk6812_ww, :sk6812_nw, :sk6812_cw, :ws2805).

  • Color.ANSI module for parsing and emitting ANSI SGR colour escape sequences. Supports 16-colour, 256-colour indexed, and 24-bit truecolor forms, with perceptual nearest-palette matching (CIEDE2000) when encoding to the 16- or 256-colour palette. Includes parse/1, to_string/2, wrap/3, nearest_256/1, nearest_16/1, palette_256/0, palette_16/0, and a typed Color.ANSI.ParseError exception.

  • Top-level Color.to_hex/1, Color.to_css/1,2, and Color.to_ansi/1,2 convenience functions that accept any input Color.new/1 accepts and raise a typed exception on failure.

Changed

  • Changed the module Color.CSSNames to Color.CSS.Names

  • Changed all colorspace module names to be the closest possible match to their standard names.

[0.3.0]

Added

  • Twenty-one color-space struct modules covering CIE, modern perceptual, HDR, video, device, and web spaces: Color.SRGB, Color.AdobeRGB, Color.RGB (linear, in any of 24 named working spaces), Color.Lab, Color.LCHab, Color.Luv, Color.LCHuv, Color.XYZ, Color.XyY, Color.Oklab, Color.Oklch, Color.HSLuv, Color.HPLuv, Color.HSL, Color.HSV, Color.CMYK, Color.YCbCr, Color.JzAzBz, Color.ICtCp, Color.IPT, Color.CAM16UCS.

  • Top-level Color.new/1,2, Color.convert/2,3,4, Color.convert_many/2,3,4, Color.luminance/1, Color.sort/2, Color.premultiply/1, Color.unpremultiply/1.

  • Chromatic adaptation (Color.XYZ.adapt/3) with six methods: :bradford, :xyz_scaling, :von_kries, :sharp, :cmccat2000, :cat02. Color.XYZ.apply_bpc/3 for black point compensation.

  • ICC rendering intents wired into Color.convert/3,4: :relative_colorimetric (default), :absolute_colorimetric, :perceptual, :saturation. Optional bpc: true and adaptation: method override.

  • Color.ICC.Profile matrix-profile reader covering ICC v2/v4 RGB→XYZ profiles with curv LUT and para parametric (types 0–4) tone response curves; load/1, parse/1, to_xyz/2, from_xyz/2.

  • Color difference metrics (Color.Distance): CIE76, CIE94, CIEDE2000 (verified against Sharma 2005), and CMC l:c.

  • Contrast (Color.Contrast): WCAG 2.x relative luminance and contrast ratio, APCA W3 0.1.9, contrast-aware pick_contrasting/2.

  • Color mixing and gradients (Color.Mix) with the default Oklab interpolation space and CSS Color 4 hue-interpolation modes.

  • Gamut checking and mapping (Color.Gamut) with both :clip and the CSS Color 4 Oklch binary-search perceptual algorithm.

  • Color harmonies (Color.Harmony) — complementary, analogous, triadic, tetradic, split-complementary — in any cylindrical space.

  • Color temperature (Color.Temperature): McCamy CCT, Planckian and CIE daylight loci, xyz/2.

  • CSS Color Module Level 4 / 5 parser and serialiser (Color.CSS): hex, named colors, all standard color functions, color() with display-p3 / a98-rgb / prophoto-rgb / rec2020 / xyz, device-cmyk(), color-mix(), relative color syntax, none, and calc() expressions.

  • CSS named colors (Color.CSSNames): all 148 CSS Color Module Level 4 names plus chromagreen and chromablue. Atom and snake-case input. Reverse nearest/1 lookup via CIEDE2000.

  • ~COLOR sigil (Color.Sigil) for compile-time color literals, compile-fenced behind Elixir 1.15.

  • Spectral pipeline (Color.Spectral + Color.Spectral.Tables): CIE 1931 2° and CIE 1964 10° standard observer CMFs, D65 / D50 / A / E illuminant SPDs, emissive and reflective integration, metamerism index.

  • All sixteen CSS Compositing Level 1 blend modes (Color.Blend).

  • Transfer functions (Color.Conversion.Lindbloom): sRGB, gamma 2.2 / 1.8, L*, BT.709, BT.2020, PQ (SMPTE ST 2084), HLG, Adobe RGB γ.

  • Typed exception modules under Color.*Error for every fallible function. Every error returns {:ok, _} or {:error, %SomeError{...}} with semantic fields.

  • Public Color.Behaviour declaring the to_xyz/1 and from_xyz/1 contract that every color-space struct module satisfies.

  • Color.is_color/1 and Color.is_css_name/1 compile-time guards plus Color.color?/1, Color.css_name?/1, and Color.validate_transparency/1 migration helpers.

  • @type t on every public color-space struct module and @spec annotations across the public API.

  • Benchee benchmark suite under bench/ covering single-color conversions, batch vs Enum.map, and the :persistent_term working-space cache.

  • Property-based test suite (test/property_test.exs) covering round-trip identity, alpha preservation, hue wrap-around, gamut-mapping invariance, ΔE symmetry, mix endpoint identity, and WCAG contrast bounds across every supported space.

Performance