Chroma Panel

Search documentation

Find a page or section

Pick a readable text colour, or check a pair against WCAG.

Available without React:

import { contrastReport, readableTextColor } from "chroma-panel/contrast";

Picking a text colour

readableTextColor("#001f3f"); // '#ffffff'
function readableTextColor(background: string | Hsva, options?: { dark?: string; light?: string; }): string

Picks black or white for text on the given background. Uses APCA rather than plain luminance, so it chooses white over mid-blues where the older method wrongly picks black.

Checking a pair

function contrastReport(a: string | Hsva, b: string | Hsva): ContrastReport

Everything known about a pair of colours at once: the WCAG ratio, the APCA lightness contrast, and which levels the pair passes.

function contrastRatio(a: string | Hsva, b: string | Hsva): number

The WCAG 2.1 contrast ratio, from 1 to 21.

function meetsContrast(a: string | Hsva, b: string | Hsva, options: ContrastOptions): boolean

Whether a pair clears a WCAG level for text. The thresholds are 4.5:1 for AA and 7:1 for AAA, relaxed for large text.

function meetsNonTextContrast(a: string | Hsva, b: string | Hsva): boolean

Whether a pair clears the 3:1 threshold WCAG applies to UI components and graphical objects rather than text.

function wcagLevel(a: string | Hsva, b: string | Hsva): WcagLevel

The highest WCAG level a pair reaches, rather than a yes or no against one threshold.

The underlying measures

function apcaContrast(text: string | Hsva, background: string | Hsva): number

The APCA lightness contrast, which models perceived contrast better than the WCAG ratio, particularly for light text on dark grounds.

function relativeLuminance(color: string | Hsva): number

The WCAG relative luminance of a colour, the quantity the contrast ratio is built from.

Why APCA for text colour

readableTextColor uses APCA rather than plain luminance. It picks white over mid-blues, where the older method wrongly picks black.