UNPKG

@ctrl/tinycolor

Version:

Fast, small color manipulation and conversion for JavaScript

293 lines (292 loc) 8.61 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.numberInputToObject = exports.parseIntFromHex = exports.convertHexToDecimal = exports.convertDecimalToHex = exports.rgbToCmyk = exports.cmykToRgb = exports.rgbaToArgbHex = exports.rgbaToHex = exports.rgbToHex = exports.hsvToRgb = exports.rgbToHsv = exports.hslToRgb = exports.rgbToHsl = exports.rgbToRgb = void 0; const util_js_1 = require("./util.js"); // `rgbToHsl`, `rgbToHsv`, `hslToRgb`, `hsvToRgb` modified from: // <http://mjijackson.com/2008/02/rgb-to-hsl-and-rgb-to-hsv-color-model-conversion-algorithms-in-javascript> /** * Handle bounds / percentage checking to conform to CSS color spec * <http://www.w3.org/TR/css3-color/> * *Assumes:* r, g, b in [0, 255] or [0, 1] * *Returns:* { r, g, b } in [0, 255] */ function rgbToRgb(r, g, b) { return { r: (0, util_js_1.bound01)(r, 255) * 255, g: (0, util_js_1.bound01)(g, 255) * 255, b: (0, util_js_1.bound01)(b, 255) * 255, }; } exports.rgbToRgb = rgbToRgb; /** * Converts an RGB color value to HSL. * *Assumes:* r, g, and b are contained in [0, 255] or [0, 1] * *Returns:* { h, s, l } in [0,1] */ function rgbToHsl(r, g, b) { r = (0, util_js_1.bound01)(r, 255); g = (0, util_js_1.bound01)(g, 255); b = (0, util_js_1.bound01)(b, 255); const max = Math.max(r, g, b); const min = Math.min(r, g, b); let h = 0; let s = 0; const l = (max + min) / 2; if (max === min) { s = 0; h = 0; // achromatic } else { const d = max - min; s = l > 0.5 ? d / (2 - max - min) : d / (max + min); switch (max) { case r: h = (g - b) / d + (g < b ? 6 : 0); break; case g: h = (b - r) / d + 2; break; case b: h = (r - g) / d + 4; break; default: break; } h /= 6; } return { h, s, l }; } exports.rgbToHsl = rgbToHsl; function hue2rgb(p, q, t) { if (t < 0) { t += 1; } if (t > 1) { t -= 1; } if (t < 1 / 6) { return p + (q - p) * (6 * t); } if (t < 1 / 2) { return q; } if (t < 2 / 3) { return p + (q - p) * (2 / 3 - t) * 6; } return p; } /** * Converts an HSL color value to RGB. * * *Assumes:* h is contained in [0, 1] or [0, 360] and s and l are contained [0, 1] or [0, 100] * *Returns:* { r, g, b } in the set [0, 255] */ function hslToRgb(h, s, l) { let r; let g; let b; h = (0, util_js_1.bound01)(h, 360); s = (0, util_js_1.bound01)(s, 100); l = (0, util_js_1.bound01)(l, 100); if (s === 0) { // achromatic g = l; b = l; r = l; } else { const q = l < 0.5 ? l * (1 + s) : l + s - l * s; const p = 2 * l - q; r = hue2rgb(p, q, h + 1 / 3); g = hue2rgb(p, q, h); b = hue2rgb(p, q, h - 1 / 3); } return { r: r * 255, g: g * 255, b: b * 255 }; } exports.hslToRgb = hslToRgb; /** * Converts an RGB color value to HSV * * *Assumes:* r, g, and b are contained in the set [0, 255] or [0, 1] * *Returns:* { h, s, v } in [0,1] */ function rgbToHsv(r, g, b) { r = (0, util_js_1.bound01)(r, 255); g = (0, util_js_1.bound01)(g, 255); b = (0, util_js_1.bound01)(b, 255); const max = Math.max(r, g, b); const min = Math.min(r, g, b); let h = 0; const v = max; const d = max - min; const s = max === 0 ? 0 : d / max; if (max === min) { h = 0; // achromatic } else { switch (max) { case r: h = (g - b) / d + (g < b ? 6 : 0); break; case g: h = (b - r) / d + 2; break; case b: h = (r - g) / d + 4; break; default: break; } h /= 6; } return { h, s, v }; } exports.rgbToHsv = rgbToHsv; /** * Converts an HSV color value to RGB. * * *Assumes:* h is contained in [0, 1] or [0, 360] and s and v are contained in [0, 1] or [0, 100] * *Returns:* { r, g, b } in the set [0, 255] */ function hsvToRgb(h, s, v) { h = (0, util_js_1.bound01)(h, 360) * 6; s = (0, util_js_1.bound01)(s, 100); v = (0, util_js_1.bound01)(v, 100); const i = Math.floor(h); const f = h - i; const p = v * (1 - s); const q = v * (1 - f * s); const t = v * (1 - (1 - f) * s); const mod = i % 6; const r = [v, q, p, p, t, v][mod]; const g = [t, v, v, q, p, p][mod]; const b = [p, p, t, v, v, q][mod]; return { r: r * 255, g: g * 255, b: b * 255 }; } exports.hsvToRgb = hsvToRgb; /** * Converts an RGB color to hex * * *Assumes:* r, g, and b are contained in the set [0, 255] * *Returns:* a 3 or 6 character hex */ function rgbToHex(r, g, b, allow3Char) { const hex = [ (0, util_js_1.pad2)(Math.round(r).toString(16)), (0, util_js_1.pad2)(Math.round(g).toString(16)), (0, util_js_1.pad2)(Math.round(b).toString(16)), ]; // Return a 3 character hex if possible if (allow3Char && hex[0].startsWith(hex[0].charAt(1)) && hex[1].startsWith(hex[1].charAt(1)) && hex[2].startsWith(hex[2].charAt(1))) { return hex[0].charAt(0) + hex[1].charAt(0) + hex[2].charAt(0); } return hex.join(''); } exports.rgbToHex = rgbToHex; /** * Converts an RGBA color plus alpha transparency to hex * * *Assumes:* r, g, b are contained in the set [0, 255] and a in [0, 1] * *Returns:* a 4 or 8 character rgba hex */ // eslint-disable-next-line max-params function rgbaToHex(r, g, b, a, allow4Char) { const hex = [ (0, util_js_1.pad2)(Math.round(r).toString(16)), (0, util_js_1.pad2)(Math.round(g).toString(16)), (0, util_js_1.pad2)(Math.round(b).toString(16)), (0, util_js_1.pad2)(convertDecimalToHex(a)), ]; // Return a 4 character hex if possible if (allow4Char && hex[0].startsWith(hex[0].charAt(1)) && hex[1].startsWith(hex[1].charAt(1)) && hex[2].startsWith(hex[2].charAt(1)) && hex[3].startsWith(hex[3].charAt(1))) { return hex[0].charAt(0) + hex[1].charAt(0) + hex[2].charAt(0) + hex[3].charAt(0); } return hex.join(''); } exports.rgbaToHex = rgbaToHex; /** * Converts an RGBA color to an ARGB Hex8 string * Rarely used, but required for "toFilter()" * * *Assumes:* r, g, b are contained in the set [0, 255] and a in [0, 1] * *Returns:* a 8 character argb hex */ function rgbaToArgbHex(r, g, b, a) { const hex = [ (0, util_js_1.pad2)(convertDecimalToHex(a)), (0, util_js_1.pad2)(Math.round(r).toString(16)), (0, util_js_1.pad2)(Math.round(g).toString(16)), (0, util_js_1.pad2)(Math.round(b).toString(16)), ]; return hex.join(''); } exports.rgbaToArgbHex = rgbaToArgbHex; /** * Converts CMYK to RBG * Assumes c, m, y, k are in the set [0, 100] */ function cmykToRgb(c, m, y, k) { const cConv = c / 100; const mConv = m / 100; const yConv = y / 100; const kConv = k / 100; const r = 255 * (1 - cConv) * (1 - kConv); const g = 255 * (1 - mConv) * (1 - kConv); const b = 255 * (1 - yConv) * (1 - kConv); return { r, g, b }; } exports.cmykToRgb = cmykToRgb; function rgbToCmyk(r, g, b) { let c = 1 - r / 255; let m = 1 - g / 255; let y = 1 - b / 255; let k = Math.min(c, m, y); if (k === 1) { c = 0; m = 0; y = 0; } else { c = ((c - k) / (1 - k)) * 100; m = ((m - k) / (1 - k)) * 100; y = ((y - k) / (1 - k)) * 100; } k *= 100; return { c: Math.round(c), m: Math.round(m), y: Math.round(y), k: Math.round(k), }; } exports.rgbToCmyk = rgbToCmyk; /** Converts a decimal to a hex value */ function convertDecimalToHex(d) { return Math.round(parseFloat(d) * 255).toString(16); } exports.convertDecimalToHex = convertDecimalToHex; /** Converts a hex value to a decimal */ function convertHexToDecimal(h) { return parseIntFromHex(h) / 255; } exports.convertHexToDecimal = convertHexToDecimal; /** Parse a base-16 hex value into a base-10 integer */ function parseIntFromHex(val) { return parseInt(val, 16); } exports.parseIntFromHex = parseIntFromHex; function numberInputToObject(color) { return { r: color >> 16, g: (color & 0xff00) >> 8, b: color & 0xff, }; } exports.numberInputToObject = numberInputToObject;