Skip to content

aneeshnaik/datahues

Repository files navigation

datahues

Generate perceptually uniform colour ramps for data visualisation.

Test Coverage Status License: MIT

Overview

datahues creates smooth, perceptually uniform colour gradients from a start colour to an end colour. Unlike simple RGB or HSL interpolation, which can produce visually uneven ramps, this library leverages the Oklab colour space: a perceptually uniform space where equal mathematical changes correspond to equal perceptual colour differences.

Comparison of RGB vs Oklab interpolation

A comparison of a linear RGB colour ramp (generated with matplotlib's LinearSegmentedColormap.from_list) versus an Oklab-interpolated ramp generated by datahues. The start and end colours here are #F61212 ("Pure Red") and #12F612 ("Lime").

The figure above demonstrates why it's important to think about perceptual uniformity of colour ramps. If you naïvely interpolate in RGB space between two colours, you end up with a ramp that gives you artificial banding (cf. left panel). You might then see patterns in your data that aren't truly there!

Installation

datahues is available on PyPI and conda-forge.

Install from PyPI with pip:

pip install datahues

Install from conda-forge with conda, setting the conda-forge channel:

conda install -c conda-forge datahues

Core Functions

datahues just has two public functions: generate_hex_list and generate_cmap. Both generate a sequential colour ramp given start and end colour hexes. The former returns a list of hexes, and the latter returns a matplotlib LinearSegmentedColormap object.

generate_hex_list(start_hex, end_hex, n_stops=512)

Between start and end colours, generates a list of hex colour codes representing points along a smooth colour ramp. It is assumed the user wants a discrete number (n_stops) of points, so no warning is given when n_stops is small (unlike in generate_cmap below). However, if these hexes are being used to create a continuous colour ramp, it is recommended to use n_stops>=128.

  • Parameters:
    • start_hex: Starting colour as hex code (e.g., "#FF0000")
    • end_hex: Ending colour as hex code (e.g., "#0000FF")
    • n_stops: Number of colour stops in the ramp (default: 512)
  • Returns: List of hex colour codes representing the gradient

generate_cmap(start_hex, end_hex, n_stops=512, name="interp_ramp")

Betweem start and end colours, creates a matplotlib LinearSegmentedColormap object, forming a smooth colour ramp.

  • Parameters:
    • start_hex, end_hex, n_stops: As above
    • name: The "name" of the colour ramp for matplotlib internal purposes (default: "interp_ramp")
  • Returns: LinearSegmentedColormap object ready to use in matplotlib visualisation
  • Warning: n_stops < 128 may produce visible banding; use larger values for smoother results

How It Works

The library converts colours through multiple colour spaces to achieve perceptual uniformity:

  1. Hex → RGB — Parse hex codes into normalised [0.0, 1.0] RGB values
  2. RGB → XYZ — Apply gamma correction and convert to CIE XYZ (D65 illuminant)
  3. XYZ → Oklab — Convert through LMS intermediate space to Oklab (perceptually uniform)
  4. Interpolate in Oklab — Create evenly-spaced values in perceptual space
  5. Oklab → RGB → Hex — Reverse conversion back to hex color codes

This approach ensures that visual transitions between colours feel smooth and natural across the entire gradient.

Future Features

The list below has some ideas for future features to be implemented in datahues. No promises!

  • Colour sequences with more than 2 colours.
  • Alternative colour spaces (beyond Oklab)
  • Alternative input types (besides hex codes), e.g. matplotlib colour names or RGB tuples.

Feel free to get in touch / make an issue with other requests.

About

Generate perceptually uniform colour ramps for data visualisation.

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors

Languages