CSS and design tools write colors as hex because three bytes (red, green, blue) fit neatly into six digits: #RRGGBB. Developers meet this format in themes, design tokens, email templates, and visual regression diffs.
Convert both directions with Hex to RGB and RGB to Hex. Broader hex context: What is hexadecimal encoding?.
How #RRGGBB maps to bytes
#0F5C8C
| | |
R G B each channel 00–FF → 0–255
#RGBshort form expands by duplication:#0F8→#00FF88.- Eight-digit forms add alpha. Ordering is usually
#RRGGBBAAon the web, but some native APIs historically usedAARRGGBB—verify before converting.
Parse hex colors in code
function parseHexColor(hex) {
const h = hex.trim().replace(/^#/, "");
const full = h.length === 3
? [...h].map((c) => c + c).join("")
: h;
if (!/^[0-9a-fA-F]{6}$/.test(full)) {
throw new Error("expected #RGB or #RRGGBB");
}
return {
r: parseInt(full.slice(0, 2), 16),
g: parseInt(full.slice(2, 4), 16),
b: parseInt(full.slice(4, 6), 16),
};
}
console.log(parseHexColor("#0F5C8C")); // { r:15, g:92, b:140 }
const toHex = (n) =>
Math.max(0, Math.min(255, n | 0)).toString(16).padStart(2, "0").toUpperCase();
const rgbToHex = (r, g, b) => `#${toHex(r)}${toHex(g)}${toHex(b)}`;
console.log(rgbToHex(15, 92, 140)); // #0F5C8C
Where teams get confused
- Color hex ≠ arbitrary data hex. Same digits, different meaning. A SHA-1 prefix that looks like a color is coincidence.
- Case: browsers treat
#abcand#ABCthe same. Pick a house style for design systems. - Named colors:
rebeccapurpleis not hex. Convert only when you have numeric channels. - Accessibility: contrast math wants luminance from RGB (or better color spaces). Hex is storage, not the calculation format.
Design-system tips
- Store tokens as hex or RGB consistently; avoid mixing without a converter in CI.
- Document whether alpha is supported.
- When diffing themes, normalize to uppercase 6-digit hex so reviews stay quiet.
Related formats
- Pantone matching is approximate—use Hex to Pantone as a helper, not a lab substitute.
- For binary dumps of image files, start with magic numbers, not color parsers.
Relative luminance (why hex alone is not enough)
Contrast checkers convert hex → sRGB 0–1 → approximate relative luminance. You do not need the full WCAG formula memorized, but you should know hex is only the storage form:
function channel(c) {
const s = c / 255;
return s <= 0.03928 ? s / 12.92 : Math.pow((s + 0.055) / 1.055, 2.4);
}
function relativeLuminance({ r, g, b }) {
return 0.2126 * channel(r) + 0.7152 * channel(g) + 0.0722 * channel(b);
}
Use this (or a library) before declaring a text/background pair “accessible.”
FAQ
Is #fff different from #ffffff?
No. Short form expands by repeating each digit.
Why does my design tool export 8 digits?
It included alpha. Strip or interpret the last two digits according to that tool’s docs.
Can I average two hex colors by averaging the hex strings?
No. Average the numeric channels (or use a proper color space), then convert back to hex.
Also see: Hex vs Base64 · Hex Calculator.