A little help goes a long way. Find a tool/

Design FIELD NOTES · 4 MIN READ

How Color Contrast Works

The WCAG contrast ratio explained: relative luminance, why normal text needs 4.5:1, AA vs AAA, and how to pick accessible color pairs.

Color contrast is the measured brightness difference between text and its background, expressed as a ratio from 1:1 (identical colors) to 21:1 (black on white). WCAG, the web accessibility standard, sets the pass thresholds — 4.5:1 for normal text at AA — and the whole thing comes from one small formula anyone can run.

The ratio comes from relative luminance

Raw RGB numbers are a poor brightness scale: a pure green channel looks far brighter to the human eye than the same amount of blue, because our vision is tuned to green. WCAG therefore converts each color to relative luminance — a perceived-brightness value from 0 (black) to 1 (white). Each channel is first "linearized" to undo the display's gamma curve, then combined with weights that mirror the eye:

linear c = ((c/255 + 0.055) / 1.055)^2.4     (for c/255 > 0.03928; otherwise c/255 / 12.92)
L = 0.2126·R + 0.7152·G + 0.0722·B
contrast = (L_lighter + 0.05) / (L_darker + 0.05)

Green's weight, 0.7152, is more than three times blue's 0.0722 — that's why a mid-green text color reads as "light" even when its numbers look modest. The + 0.05 offset keeps the formula finite at pure black and represents the faint light a real display emits. One nice consequence: the ratio is symmetric. Text and background can swap places without changing the result, because only the lighter and darker luminance matter.

A worked example: gray text on white

Take the gray #767676. Each channel is 118/255 = 0.4627; linearized, that is ((0.4627 + 0.055) / 1.055)^2.4 ≈ 0.1813. All three channels are equal, so L = 0.1813. White has L = 1.0, so:

contrast = (1.0 + 0.05) / (0.1813 + 0.05) = 1.05 / 0.2313 ≈ 4.54:1

That passes AA for normal text (4.5:1) with a hair to spare — #767676 is famously about the lightest gray that makes it. One step lighter, #999999: L ≈ 0.3186, ratio = 1.05 / 0.3686 ≈ 2.85:1, which fails AA. The other direction passes easily: #333333 on white comes out at ≈ 12.6:1, and pure black on white is (1.05 / 0.05) = 21:1, the maximum possible.

Why 4.5:1, and AA versus AAA

The thresholds were chosen from studies of vision loss rather than aesthetics. Roughly, 4.5:1 is the level at which normal-size text stays readable for someone with 20/40 vision — about half the acuity of standard 20/20, in the range typical for older readers — and the stricter AAA level of 7:1 covers further loss. Large text earns a lower bar because size itself carries legibility: at AA, "large" means at least 18pt (24px) regular or 14pt (about 18.7px) bold, and it needs only 3:1 (4.5:1 at AAA).

AA is the baseline most laws and style guides reference; AAA is an enhancement most sites meet selectively, on long-form body text, for example. WCAG also checks non-text elements separately: buttons, form borders, and icons need about 3:1 so people can find the controls at all (WCAG 2.1, 1.4.11).

What people get wrong

  • Light-gray placeholders and captions. Placeholder text styled like #999999 fails everywhere it appears.
  • Links inside text. A link must contrast with the background, not just differ from the surrounding text by hue.
  • Brand colors on the wrong background. White text on a mid-tone brand color often lands between 2:1 and 3:1 — a button that looks fine to a young designer on a good screen.
  • Real link blues sit right on the line. Google's link blue #1a73e8 on white is ≈ 4.51:1 — passes AA by a margin of one hundredth, fails AAA. Thresholds this close deserve rechecking, not eyeballing.
  • Color alone carrying meaning. Contrast helps everyone, but 1 in 12 men has a color vision deficiency; pair contrast with icons, underlines, or labels.

Age matters too: the eye's lens yellows and contrast sensitivity drops with decades, so text that "looks fine to me" at 25 may be work at 65. The formula's thresholds are a floor, not a target — body text with headroom above 7:1 reads more comfortably for everyone.

Practical tips for picking pairs

The cheapest fix is usually adjusting lightness, not hue: darken the text or lighten the background while keeping the brand color's identity. That's where HSL beats hex for reasoning — "same blue, lower lightness" is a one-number change you can make in a Color Converter and verify instantly. Check every combination that can occur, including hover states, disabled buttons, and text over images, and remember the ratio is symmetric so one check covers both orderings.

Try it yourself

The Color Contrast Checker computes the exact ratio for any two hex colors and reports pass/fail for AA and AAA, normal and large text, with a live preview. Convert or tune candidates with the Color Converter (hex, RGB, HSL), and use the Color Blindness Simulator to see how your pair survives protan, deutan, and tritan vision before you ship it.

Frequently asked questions

What does a contrast ratio of 4.5:1 mean?
It means the lighter color's relative luminance, plus 0.05, is 4.5 times the darker color's. The scale runs from 1:1 (identical colors) to 21:1 (black on white). WCAG AA requires at least 4.5:1 for normal text and 3:1 for large text.
What counts as large text?
At least 18pt (24px) regular, or 14pt (about 18.7px) bold. Large text needs only 3:1 at AA because size itself adds legibility; at AAA it needs 4.5:1, the same bar normal text faces at AA.
Does it matter which color is the text?
No. The ratio is computed from the lighter and darker luminance, so swapping foreground and background gives the same number. What matters is that one is the text and the other is the surface it sits on.
What is relative luminance?
A 0-to-1 brightness value that mimics human vision. Each sRGB channel is linearized to undo the display's gamma curve, then combined as 0.2126·R + 0.7152·G + 0.0722·B — the large green weight reflects how much more sensitive the eye is to green.
What contrast do buttons and icons need?
WCAG 2.1 (criterion 1.4.11) asks for about 3:1 between interactive controls or meaningful graphics and their adjacent background, so users can identify boundaries and states. Text inside the button still follows the normal text thresholds.