UNPKG

chroma-js

Version:

JavaScript library for color conversions

102 lines (85 loc) 2.95 kB
import LAB_CONSTANTS from './lab-constants.js'; import { unpack } from '../../utils/index.js'; /* * L* [0..100] * a [-100..100] * b [-100..100] */ const lab2rgb = (...args) => { args = unpack(args, 'lab'); const [L, a, b] = args; const [x, y, z] = lab2xyz(L, a, b); const [r, g, b_] = xyz2rgb(x, y, z); return [r, g, b_, args.length > 3 ? args[3] : 1]; }; const lab2xyz = (L, a, b) => { const { kE, kK, kKE, Xn, Yn, Zn } = LAB_CONSTANTS; const fy = (L + 16.0) / 116.0; const fx = 0.002 * a + fy; const fz = fy - 0.005 * b; const fx3 = fx * fx * fx; const fz3 = fz * fz * fz; const xr = fx3 > kE ? fx3 : (116.0 * fx - 16.0) / kK; const yr = L > kKE ? Math.pow((L + 16.0) / 116.0, 3.0) : L / kK; const zr = fz3 > kE ? fz3 : (116.0 * fz - 16.0) / kK; const x = xr * Xn; const y = yr * Yn; const z = zr * Zn; return [x, y, z]; }; const compand = (linear) => { /* sRGB */ const sign = Math.sign(linear); linear = Math.abs(linear); return ( (linear <= 0.0031308 ? linear * 12.92 : 1.055 * Math.pow(linear, 1.0 / 2.4) - 0.055) * sign ); }; const xyz2rgb = (x, y, z) => { const { MtxAdaptMa, MtxAdaptMaI, MtxXYZ2RGB, RefWhiteRGB, Xn, Yn, Zn } = LAB_CONSTANTS; const As = Xn * MtxAdaptMa.m00 + Yn * MtxAdaptMa.m10 + Zn * MtxAdaptMa.m20; const Bs = Xn * MtxAdaptMa.m01 + Yn * MtxAdaptMa.m11 + Zn * MtxAdaptMa.m21; const Cs = Xn * MtxAdaptMa.m02 + Yn * MtxAdaptMa.m12 + Zn * MtxAdaptMa.m22; const Ad = RefWhiteRGB.X * MtxAdaptMa.m00 + RefWhiteRGB.Y * MtxAdaptMa.m10 + RefWhiteRGB.Z * MtxAdaptMa.m20; const Bd = RefWhiteRGB.X * MtxAdaptMa.m01 + RefWhiteRGB.Y * MtxAdaptMa.m11 + RefWhiteRGB.Z * MtxAdaptMa.m21; const Cd = RefWhiteRGB.X * MtxAdaptMa.m02 + RefWhiteRGB.Y * MtxAdaptMa.m12 + RefWhiteRGB.Z * MtxAdaptMa.m22; const X1 = (x * MtxAdaptMa.m00 + y * MtxAdaptMa.m10 + z * MtxAdaptMa.m20) * (Ad / As); const Y1 = (x * MtxAdaptMa.m01 + y * MtxAdaptMa.m11 + z * MtxAdaptMa.m21) * (Bd / Bs); const Z1 = (x * MtxAdaptMa.m02 + y * MtxAdaptMa.m12 + z * MtxAdaptMa.m22) * (Cd / Cs); const X2 = X1 * MtxAdaptMaI.m00 + Y1 * MtxAdaptMaI.m10 + Z1 * MtxAdaptMaI.m20; const Y2 = X1 * MtxAdaptMaI.m01 + Y1 * MtxAdaptMaI.m11 + Z1 * MtxAdaptMaI.m21; const Z2 = X1 * MtxAdaptMaI.m02 + Y1 * MtxAdaptMaI.m12 + Z1 * MtxAdaptMaI.m22; const r = compand( X2 * MtxXYZ2RGB.m00 + Y2 * MtxXYZ2RGB.m10 + Z2 * MtxXYZ2RGB.m20 ); const g = compand( X2 * MtxXYZ2RGB.m01 + Y2 * MtxXYZ2RGB.m11 + Z2 * MtxXYZ2RGB.m21 ); const b = compand( X2 * MtxXYZ2RGB.m02 + Y2 * MtxXYZ2RGB.m12 + Z2 * MtxXYZ2RGB.m22 ); return [r * 255, g * 255, b * 255]; }; export default lab2rgb; export { xyz2rgb };