UNPKG

colorjs.io

Version:

Let’s get serious about color

75 lines (65 loc) 2.01 kB
import ColorSpace from "../space.js"; import {multiplyMatrices} from "../util.js"; import XYZ_D65 from "./xyz-d65.js"; // Recalculated for consistent reference white // see https://github.com/w3c/csswg-drafts/issues/6642#issuecomment-943521484 const XYZtoLMS_M = [ [ 0.8190224432164319, 0.3619062562801221, -0.12887378261216414 ], [ 0.0329836671980271, 0.9292868468965546, 0.03614466816999844 ], [ 0.048177199566046255, 0.26423952494422764, 0.6335478258136937 ] ]; // inverse of XYZtoLMS_M const LMStoXYZ_M = [ [ 1.2268798733741557, -0.5578149965554813, 0.28139105017721583], [ -0.04057576262431372, 1.1122868293970594, -0.07171106666151701], [ -0.07637294974672142, -0.4214933239627914, 1.5869240244272418 ] ] const LMStoLab_M = [ [ 0.2104542553, 0.7936177850, -0.0040720468 ], [ 1.9779984951, -2.4285922050, 0.4505937099 ], [ 0.0259040371, 0.7827717662, -0.8086757660 ] ]; // LMStoIab_M inverted const LabtoLMS_M = [ [ 0.99999999845051981432, 0.39633779217376785678, 0.21580375806075880339 ], [ 1.0000000088817607767, -0.1055613423236563494, -0.063854174771705903402 ], [ 1.0000000546724109177, -0.089484182094965759684, -1.2914855378640917399 ] ]; export default new ColorSpace({ id: "oklab", name: "OKLab", coords: { l: { refRange: [0, 1], name: "L" }, a: { refRange: [-0.4, 0.4] }, b: { refRange: [-0.4, 0.4] } }, // Note that XYZ is relative to D65 white: "D65", base: XYZ_D65, fromBase (XYZ) { // move to LMS cone domain let LMS = multiplyMatrices(XYZtoLMS_M, XYZ); // non-linearity let LMSg = LMS.map(val => Math.cbrt(val)); return multiplyMatrices(LMStoLab_M, LMSg); }, toBase (OKLab) { // move to LMS cone domain let LMSg = multiplyMatrices(LabtoLMS_M, OKLab); // restore linearity let LMS = LMSg.map(val => val ** 3); return multiplyMatrices(LMStoXYZ_M, LMS); }, formats: { "oklab": { coords: ["<number> | <percentage>", "<number>", "<number>"], } } });