UNPKG

use-material-you

Version:

React hook to create dynamic schemes and variants based on M3/material-color-utilities

1,285 lines 162 kB
import * as Fe from "react"; function X(a) { return a < 0 ? -1 : a === 0 ? 0 : 1; } function he(a, e, t) { return (1 - t) * a + t * e; } function je(a, e, t) { return t < a ? a : t > e ? e : t; } function G(a, e, t) { return t < a ? a : t > e ? e : t; } function Ae(a) { return a = a % 360, a < 0 && (a = a + 360), a; } function W(a) { return a = a % 360, a < 0 && (a = a + 360), a; } function Je(a, e) { return 180 - Math.abs(Math.abs(a - e) - 180); } function Ie(a, e) { const t = a[0] * e[0][0] + a[1] * e[0][1] + a[2] * e[0][2], r = a[0] * e[1][0] + a[1] * e[1][1] + a[2] * e[1][2], n = a[0] * e[2][0] + a[1] * e[2][1] + a[2] * e[2][2]; return [t, r, n]; } const Ue = [ [0.41233895, 0.35762064, 0.18051042], [0.2126, 0.7152, 0.0722], [0.01932141, 0.11916382, 0.95034478] ], Qe = [ [ 3.2413774792388685, -1.5376652402851851, -0.49885366846268053 ], [ -0.9691452513005321, 1.8758853451067872, 0.04156585616912061 ], [ 0.05562093689691305, -0.20395524564742123, 1.0571799111220335 ] ], Be = [95.047, 100, 108.883]; function Se(a, e, t) { return (255 << 24 | (a & 255) << 16 | (e & 255) << 8 | t & 255) >>> 0; } function Ne(a) { const e = ie(a[0]), t = ie(a[1]), r = ie(a[2]); return Se(e, t, r); } function Ze(a) { return a >> 24 & 255; } function ke(a) { return a >> 16 & 255; } function Ce(a) { return a >> 8 & 255; } function be(a) { return a & 255; } function ze(a, e, t) { const r = Qe, n = r[0][0] * a + r[0][1] * e + r[0][2] * t, o = r[1][0] * a + r[1][1] * e + r[1][2] * t, i = r[2][0] * a + r[2][1] * e + r[2][2] * t, c = ie(n), f = ie(o), p = ie(i); return Se(c, f, p); } function et(a) { const e = te(ke(a)), t = te(Ce(a)), r = te(be(a)); return Ie([e, t, r], Ue); } function tt(a, e, t) { const r = Be, n = (a + 16) / 116, o = e / 500 + n, i = n - t / 200, c = Te(o), f = Te(n), p = Te(i), h = c * r[0], y = f * r[1], P = p * r[2]; return ze(h, y, P); } function Ge(a) { const e = te(ke(a)), t = te(Ce(a)), r = te(be(a)), n = Ue, o = n[0][0] * e + n[0][1] * t + n[0][2] * r, i = n[1][0] * e + n[1][1] * t + n[1][2] * r, c = n[2][0] * e + n[2][1] * t + n[2][2] * r, f = Be, p = o / f[0], h = i / f[1], y = c / f[2], P = fe(p), g = fe(h), m = fe(y), d = 116 * g - 16, T = 500 * (P - g), D = 200 * (g - m); return [d, T, D]; } function rt(a) { const e = ae(a), t = ie(e); return Se(t, t, t); } function Ve(a) { const e = et(a)[1]; return 116 * fe(e / 100) - 16; } function ae(a) { return 100 * Te((a + 16) / 116); } function ve(a) { return fe(a / 100) * 116 - 16; } function te(a) { const e = a / 255; return e <= 0.040449936 ? e / 12.92 * 100 : Math.pow((e + 0.055) / 1.055, 2.4) * 100; } function ie(a) { const e = a / 100; let t = 0; return e <= 31308e-7 ? t = e * 12.92 : t = 1.055 * Math.pow(e, 1 / 2.4) - 0.055, je(0, 255, Math.round(t * 255)); } function nt() { return Be; } function fe(a) { const e = 0.008856451679035631, t = 24389 / 27; return a > e ? Math.pow(a, 1 / 3) : (t * a + 16) / 116; } function Te(a) { const e = 0.008856451679035631, t = 24389 / 27, r = a * a * a; return r > e ? r : (116 * a - 16) / t; } class Z { /** * Create ViewingConditions from a simple, physically relevant, set of * parameters. * * @param whitePoint White point, measured in the XYZ color space. * default = D65, or sunny day afternoon * @param adaptingLuminance The luminance of the adapting field. Informally, * how bright it is in the room where the color is viewed. Can be * calculated from lux by multiplying lux by 0.0586. default = 11.72, * or 200 lux. * @param backgroundLstar The lightness of the area surrounding the color. * measured by L* in L*a*b*. default = 50.0 * @param surround A general description of the lighting surrounding the * color. 0 is pitch dark, like watching a movie in a theater. 1.0 is a * dimly light room, like watching TV at home at night. 2.0 means there * is no difference between the lighting on the color and around it. * default = 2.0 * @param discountingIlluminant Whether the eye accounts for the tint of the * ambient lighting, such as knowing an apple is still red in green light. * default = false, the eye does not perform this process on * self-luminous objects like displays. */ static make(e = nt(), t = 200 / Math.PI * ae(50) / 100, r = 50, n = 2, o = !1) { const i = e, c = i[0] * 0.401288 + i[1] * 0.650173 + i[2] * -0.051461, f = i[0] * -0.250268 + i[1] * 1.204414 + i[2] * 0.045854, p = i[0] * -2079e-6 + i[1] * 0.048952 + i[2] * 0.953127, h = 0.8 + n / 10, y = h >= 0.9 ? he(0.59, 0.69, (h - 0.9) * 10) : he(0.525, 0.59, (h - 0.8) * 10); let P = o ? 1 : h * (1 - 1 / 3.6 * Math.exp((-t - 42) / 92)); P = P > 1 ? 1 : P < 0 ? 0 : P; const g = h, m = [ P * (100 / c) + 1 - P, P * (100 / f) + 1 - P, P * (100 / p) + 1 - P ], d = 1 / (5 * t + 1), T = d * d * d * d, D = 1 - T, A = T * t + 0.1 * D * D * Math.cbrt(5 * t), C = ae(r) / e[1], v = 1.48 + Math.sqrt(C), M = 0.725 / Math.pow(C, 0.2), O = M, k = [ Math.pow(A * m[0] * c / 100, 0.42), Math.pow(A * m[1] * f / 100, 0.42), Math.pow(A * m[2] * p / 100, 0.42) ], F = [ 400 * k[0] / (k[0] + 27.13), 400 * k[1] / (k[1] + 27.13), 400 * k[2] / (k[2] + 27.13) ], N = (2 * F[0] + F[1] + 0.05 * F[2]) * M; return new Z(C, N, M, O, y, g, m, A, Math.pow(A, 0.25), v); } /** * Parameters are intermediate values of the CAM16 conversion process. Their * names are shorthand for technical color science terminology, this class * would not benefit from documenting them individually. A brief overview * is available in the CAM16 specification, and a complete overview requires * a color science textbook, such as Fairchild's Color Appearance Models. */ constructor(e, t, r, n, o, i, c, f, p, h) { this.n = e, this.aw = t, this.nbb = r, this.ncb = n, this.c = o, this.nc = i, this.rgbD = c, this.fl = f, this.fLRoot = p, this.z = h; } } Z.DEFAULT = Z.make(); class q { /** * All of the CAM16 dimensions can be calculated from 3 of the dimensions, in * the following combinations: * - {j or q} and {c, m, or s} and hue * - jstar, astar, bstar * Prefer using a static method that constructs from 3 of those dimensions. * This constructor is intended for those methods to use to return all * possible dimensions. * * @param hue * @param chroma informally, colorfulness / color intensity. like saturation * in HSL, except perceptually accurate. * @param j lightness * @param q brightness; ratio of lightness to white point's lightness * @param m colorfulness * @param s saturation; ratio of chroma to white point's chroma * @param jstar CAM16-UCS J coordinate * @param astar CAM16-UCS a coordinate * @param bstar CAM16-UCS b coordinate */ constructor(e, t, r, n, o, i, c, f, p) { this.hue = e, this.chroma = t, this.j = r, this.q = n, this.m = o, this.s = i, this.jstar = c, this.astar = f, this.bstar = p; } /** * CAM16 instances also have coordinates in the CAM16-UCS space, called J*, * a*, b*, or jstar, astar, bstar in code. CAM16-UCS is included in the CAM16 * specification, and is used to measure distances between colors. */ distance(e) { const t = this.jstar - e.jstar, r = this.astar - e.astar, n = this.bstar - e.bstar, o = Math.sqrt(t * t + r * r + n * n); return 1.41 * Math.pow(o, 0.63); } /** * @param argb ARGB representation of a color. * @return CAM16 color, assuming the color was viewed in default viewing * conditions. */ static fromInt(e) { return q.fromIntInViewingConditions(e, Z.DEFAULT); } /** * @param argb ARGB representation of a color. * @param viewingConditions Information about the environment where the color * was observed. * @return CAM16 color. */ static fromIntInViewingConditions(e, t) { const r = (e & 16711680) >> 16, n = (e & 65280) >> 8, o = e & 255, i = te(r), c = te(n), f = te(o), p = 0.41233895 * i + 0.35762064 * c + 0.18051042 * f, h = 0.2126 * i + 0.7152 * c + 0.0722 * f, y = 0.01932141 * i + 0.11916382 * c + 0.95034478 * f, P = 0.401288 * p + 0.650173 * h - 0.051461 * y, g = -0.250268 * p + 1.204414 * h + 0.045854 * y, m = -2079e-6 * p + 0.048952 * h + 0.953127 * y, d = t.rgbD[0] * P, T = t.rgbD[1] * g, D = t.rgbD[2] * m, A = Math.pow(t.fl * Math.abs(d) / 100, 0.42), C = Math.pow(t.fl * Math.abs(T) / 100, 0.42), v = Math.pow(t.fl * Math.abs(D) / 100, 0.42), M = X(d) * 400 * A / (A + 27.13), O = X(T) * 400 * C / (C + 27.13), k = X(D) * 400 * v / (v + 27.13), F = (11 * M + -12 * O + k) / 11, N = (M + O - 2 * k) / 9, L = (20 * M + 20 * O + 21 * k) / 20, U = (40 * M + 20 * O + k) / 20, Q = Math.atan2(N, F) * 180 / Math.PI, z = W(Q), oe = z * Math.PI / 180, me = U * t.nbb, re = 100 * Math.pow(me / t.aw, t.c * t.z), pe = 4 / t.c * Math.sqrt(re / 100) * (t.aw + 4) * t.fLRoot, we = z < 20.14 ? z + 360 : z, xe = 0.25 * (Math.cos(we * Math.PI / 180 + 2) + 3.8), De = 5e4 / 13 * xe * t.nc * t.ncb * Math.sqrt(F * F + N * N) / (L + 0.305), ge = Math.pow(De, 0.9) * Math.pow(1.64 - Math.pow(0.29, t.n), 0.73), Le = ge * Math.sqrt(re / 100), Me = Le * t.fLRoot, Xe = 50 * Math.sqrt(ge * t.c / (t.aw + 4)), qe = (1 + 100 * 7e-3) * re / (1 + 7e-3 * re), Oe = 1 / 0.0228 * Math.log(1 + 0.0228 * Me), We = Oe * Math.cos(oe), $e = Oe * Math.sin(oe); return new q(z, Le, re, pe, Me, Xe, qe, We, $e); } /** * @param j CAM16 lightness * @param c CAM16 chroma * @param h CAM16 hue */ static fromJch(e, t, r) { return q.fromJchInViewingConditions(e, t, r, Z.DEFAULT); } /** * @param j CAM16 lightness * @param c CAM16 chroma * @param h CAM16 hue * @param viewingConditions Information about the environment where the color * was observed. */ static fromJchInViewingConditions(e, t, r, n) { const o = 4 / n.c * Math.sqrt(e / 100) * (n.aw + 4) * n.fLRoot, i = t * n.fLRoot, c = t / Math.sqrt(e / 100), f = 50 * Math.sqrt(c * n.c / (n.aw + 4)), p = r * Math.PI / 180, h = (1 + 100 * 7e-3) * e / (1 + 7e-3 * e), y = 1 / 0.0228 * Math.log(1 + 0.0228 * i), P = y * Math.cos(p), g = y * Math.sin(p); return new q(r, t, e, o, i, f, h, P, g); } /** * @param jstar CAM16-UCS lightness. * @param astar CAM16-UCS a dimension. Like a* in L*a*b*, it is a Cartesian * coordinate on the Y axis. * @param bstar CAM16-UCS b dimension. Like a* in L*a*b*, it is a Cartesian * coordinate on the X axis. */ static fromUcs(e, t, r) { return q.fromUcsInViewingConditions(e, t, r, Z.DEFAULT); } /** * @param jstar CAM16-UCS lightness. * @param astar CAM16-UCS a dimension. Like a* in L*a*b*, it is a Cartesian * coordinate on the Y axis. * @param bstar CAM16-UCS b dimension. Like a* in L*a*b*, it is a Cartesian * coordinate on the X axis. * @param viewingConditions Information about the environment where the color * was observed. */ static fromUcsInViewingConditions(e, t, r, n) { const o = t, i = r, c = Math.sqrt(o * o + i * i), p = (Math.exp(c * 0.0228) - 1) / 0.0228 / n.fLRoot; let h = Math.atan2(i, o) * (180 / Math.PI); h < 0 && (h += 360); const y = e / (1 - (e - 100) * 7e-3); return q.fromJchInViewingConditions(y, p, h, n); } /** * @return ARGB representation of color, assuming the color was viewed in * default viewing conditions, which are near-identical to the default * viewing conditions for sRGB. */ toInt() { return this.viewed(Z.DEFAULT); } /** * @param viewingConditions Information about the environment where the color * will be viewed. * @return ARGB representation of color */ viewed(e) { const t = this.chroma === 0 || this.j === 0 ? 0 : this.chroma / Math.sqrt(this.j / 100), r = Math.pow(t / Math.pow(1.64 - Math.pow(0.29, e.n), 0.73), 1 / 0.9), n = this.hue * Math.PI / 180, o = 0.25 * (Math.cos(n + 2) + 3.8), i = e.aw * Math.pow(this.j / 100, 1 / e.c / e.z), c = o * (5e4 / 13) * e.nc * e.ncb, f = i / e.nbb, p = Math.sin(n), h = Math.cos(n), y = 23 * (f + 0.305) * r / (23 * c + 11 * r * h + 108 * r * p), P = y * h, g = y * p, m = (460 * f + 451 * P + 288 * g) / 1403, d = (460 * f - 891 * P - 261 * g) / 1403, T = (460 * f - 220 * P - 6300 * g) / 1403, D = Math.max(0, 27.13 * Math.abs(m) / (400 - Math.abs(m))), A = X(m) * (100 / e.fl) * Math.pow(D, 1 / 0.42), C = Math.max(0, 27.13 * Math.abs(d) / (400 - Math.abs(d))), v = X(d) * (100 / e.fl) * Math.pow(C, 1 / 0.42), M = Math.max(0, 27.13 * Math.abs(T) / (400 - Math.abs(T))), O = X(T) * (100 / e.fl) * Math.pow(M, 1 / 0.42), k = A / e.rgbD[0], F = v / e.rgbD[1], N = O / e.rgbD[2], L = 1.86206786 * k - 1.01125463 * F + 0.14918677 * N, U = 0.38752654 * k + 0.62144744 * F - 897398e-8 * N, $ = -0.0158415 * k - 0.03412294 * F + 1.04996444 * N; return ze(L, U, $); } /// Given color expressed in XYZ and viewed in [viewingConditions], convert to /// CAM16. static fromXyzInViewingConditions(e, t, r, n) { const o = 0.401288 * e + 0.650173 * t - 0.051461 * r, i = -0.250268 * e + 1.204414 * t + 0.045854 * r, c = -2079e-6 * e + 0.048952 * t + 0.953127 * r, f = n.rgbD[0] * o, p = n.rgbD[1] * i, h = n.rgbD[2] * c, y = Math.pow(n.fl * Math.abs(f) / 100, 0.42), P = Math.pow(n.fl * Math.abs(p) / 100, 0.42), g = Math.pow(n.fl * Math.abs(h) / 100, 0.42), m = X(f) * 400 * y / (y + 27.13), d = X(p) * 400 * P / (P + 27.13), T = X(h) * 400 * g / (g + 27.13), D = (11 * m + -12 * d + T) / 11, A = (m + d - 2 * T) / 9, C = (20 * m + 20 * d + 21 * T) / 20, v = (40 * m + 20 * d + T) / 20, O = Math.atan2(A, D) * 180 / Math.PI, k = O < 0 ? O + 360 : O >= 360 ? O - 360 : O, F = k * Math.PI / 180, N = v * n.nbb, L = 100 * Math.pow(N / n.aw, n.c * n.z), U = 4 / n.c * Math.sqrt(L / 100) * (n.aw + 4) * n.fLRoot, $ = k < 20.14 ? k + 360 : k, Q = 1 / 4 * (Math.cos($ * Math.PI / 180 + 2) + 3.8), oe = 5e4 / 13 * Q * n.nc * n.ncb * Math.sqrt(D * D + A * A) / (C + 0.305), me = Math.pow(oe, 0.9) * Math.pow(1.64 - Math.pow(0.29, n.n), 0.73), re = me * Math.sqrt(L / 100), pe = re * n.fLRoot, we = 50 * Math.sqrt(me * n.c / (n.aw + 4)), xe = (1 + 100 * 7e-3) * L / (1 + 7e-3 * L), Ee = Math.log(1 + 0.0228 * pe) / 0.0228, De = Ee * Math.cos(F), ge = Ee * Math.sin(F); return new q(k, re, L, U, pe, we, xe, De, ge); } /// XYZ representation of CAM16 seen in [viewingConditions]. xyzInViewingConditions(e) { const t = this.chroma === 0 || this.j === 0 ? 0 : this.chroma / Math.sqrt(this.j / 100), r = Math.pow(t / Math.pow(1.64 - Math.pow(0.29, e.n), 0.73), 1 / 0.9), n = this.hue * Math.PI / 180, o = 0.25 * (Math.cos(n + 2) + 3.8), i = e.aw * Math.pow(this.j / 100, 1 / e.c / e.z), c = o * (5e4 / 13) * e.nc * e.ncb, f = i / e.nbb, p = Math.sin(n), h = Math.cos(n), y = 23 * (f + 0.305) * r / (23 * c + 11 * r * h + 108 * r * p), P = y * h, g = y * p, m = (460 * f + 451 * P + 288 * g) / 1403, d = (460 * f - 891 * P - 261 * g) / 1403, T = (460 * f - 220 * P - 6300 * g) / 1403, D = Math.max(0, 27.13 * Math.abs(m) / (400 - Math.abs(m))), A = X(m) * (100 / e.fl) * Math.pow(D, 1 / 0.42), C = Math.max(0, 27.13 * Math.abs(d) / (400 - Math.abs(d))), v = X(d) * (100 / e.fl) * Math.pow(C, 1 / 0.42), M = Math.max(0, 27.13 * Math.abs(T) / (400 - Math.abs(T))), O = X(T) * (100 / e.fl) * Math.pow(M, 1 / 0.42), k = A / e.rgbD[0], F = v / e.rgbD[1], N = O / e.rgbD[2], L = 1.86206786 * k - 1.01125463 * F + 0.14918677 * N, U = 0.38752654 * k + 0.62144744 * F - 897398e-8 * N, $ = -0.0158415 * k - 0.03412294 * F + 1.04996444 * N; return [L, U, $]; } } class x { /** * Sanitizes a small enough angle in radians. * * @param angle An angle in radians; must not deviate too much * from 0. * @return A coterminal angle between 0 and 2pi. */ static sanitizeRadians(e) { return (e + Math.PI * 8) % (Math.PI * 2); } /** * Delinearizes an RGB component, returning a floating-point * number. * * @param rgbComponent 0.0 <= rgb_component <= 100.0, represents * linear R/G/B channel * @return 0.0 <= output <= 255.0, color channel converted to * regular RGB space */ static trueDelinearized(e) { const t = e / 100; let r = 0; return t <= 31308e-7 ? r = t * 12.92 : r = 1.055 * Math.pow(t, 1 / 2.4) - 0.055, r * 255; } static chromaticAdaptation(e) { const t = Math.pow(Math.abs(e), 0.42); return X(e) * 400 * t / (t + 27.13); } /** * Returns the hue of a linear RGB color in CAM16. * * @param linrgb The linear RGB coordinates of a color. * @return The hue of the color in CAM16, in radians. */ static hueOf(e) { const t = Ie(e, x.SCALED_DISCOUNT_FROM_LINRGB), r = x.chromaticAdaptation(t[0]), n = x.chromaticAdaptation(t[1]), o = x.chromaticAdaptation(t[2]), i = (11 * r + -12 * n + o) / 11, c = (r + n - 2 * o) / 9; return Math.atan2(c, i); } static areInCyclicOrder(e, t, r) { const n = x.sanitizeRadians(t - e), o = x.sanitizeRadians(r - e); return n < o; } /** * Solves the lerp equation. * * @param source The starting number. * @param mid The number in the middle. * @param target The ending number. * @return A number t such that lerp(source, target, t) = mid. */ static intercept(e, t, r) { return (t - e) / (r - e); } static lerpPoint(e, t, r) { return [ e[0] + (r[0] - e[0]) * t, e[1] + (r[1] - e[1]) * t, e[2] + (r[2] - e[2]) * t ]; } /** * Intersects a segment with a plane. * * @param source The coordinates of point A. * @param coordinate The R-, G-, or B-coordinate of the plane. * @param target The coordinates of point B. * @param axis The axis the plane is perpendicular with. (0: R, 1: * G, 2: B) * @return The intersection point of the segment AB with the plane * R=coordinate, G=coordinate, or B=coordinate */ static setCoordinate(e, t, r, n) { const o = x.intercept(e[n], t, r[n]); return x.lerpPoint(e, o, r); } static isBounded(e) { return 0 <= e && e <= 100; } /** * Returns the nth possible vertex of the polygonal intersection. * * @param y The Y value of the plane. * @param n The zero-based index of the point. 0 <= n <= 11. * @return The nth possible vertex of the polygonal intersection * of the y plane and the RGB cube, in linear RGB coordinates, if * it exists. If this possible vertex lies outside of the cube, * [-1.0, -1.0, -1.0] is returned. */ static nthVertex(e, t) { const r = x.Y_FROM_LINRGB[0], n = x.Y_FROM_LINRGB[1], o = x.Y_FROM_LINRGB[2], i = t % 4 <= 1 ? 0 : 100, c = t % 2 === 0 ? 0 : 100; if (t < 4) { const f = i, p = c, h = (e - f * n - p * o) / r; return x.isBounded(h) ? [h, f, p] : [-1, -1, -1]; } else if (t < 8) { const f = i, p = c, h = (e - p * r - f * o) / n; return x.isBounded(h) ? [p, h, f] : [-1, -1, -1]; } else { const f = i, p = c, h = (e - f * r - p * n) / o; return x.isBounded(h) ? [f, p, h] : [-1, -1, -1]; } } /** * Finds the segment containing the desired color. * * @param y The Y value of the color. * @param targetHue The hue of the color. * @return A list of two sets of linear RGB coordinates, each * corresponding to an endpoint of the segment containing the * desired color. */ static bisectToSegment(e, t) { let r = [-1, -1, -1], n = r, o = 0, i = 0, c = !1, f = !0; for (let p = 0; p < 12; p++) { const h = x.nthVertex(e, p); if (h[0] < 0) continue; const y = x.hueOf(h); if (!c) { r = h, n = h, o = y, i = y, c = !0; continue; } (f || x.areInCyclicOrder(o, y, i)) && (f = !1, x.areInCyclicOrder(o, t, y) ? (n = h, i = y) : (r = h, o = y)); } return [r, n]; } static midpoint(e, t) { return [ (e[0] + t[0]) / 2, (e[1] + t[1]) / 2, (e[2] + t[2]) / 2 ]; } static criticalPlaneBelow(e) { return Math.floor(e - 0.5); } static criticalPlaneAbove(e) { return Math.ceil(e - 0.5); } /** * Finds a color with the given Y and hue on the boundary of the * cube. * * @param y The Y value of the color. * @param targetHue The hue of the color. * @return The desired color, in linear RGB coordinates. */ static bisectToLimit(e, t) { const r = x.bisectToSegment(e, t); let n = r[0], o = x.hueOf(n), i = r[1]; for (let c = 0; c < 3; c++) if (n[c] !== i[c]) { let f = -1, p = 255; n[c] < i[c] ? (f = x.criticalPlaneBelow(x.trueDelinearized(n[c])), p = x.criticalPlaneAbove(x.trueDelinearized(i[c]))) : (f = x.criticalPlaneAbove(x.trueDelinearized(n[c])), p = x.criticalPlaneBelow(x.trueDelinearized(i[c]))); for (let h = 0; h < 8 && !(Math.abs(p - f) <= 1); h++) { const y = Math.floor((f + p) / 2), P = x.CRITICAL_PLANES[y], g = x.setCoordinate(n, P, i, c), m = x.hueOf(g); x.areInCyclicOrder(o, t, m) ? (i = g, p = y) : (n = g, o = m, f = y); } } return x.midpoint(n, i); } static inverseChromaticAdaptation(e) { const t = Math.abs(e), r = Math.max(0, 27.13 * t / (400 - t)); return X(e) * Math.pow(r, 1 / 0.42); } /** * Finds a color with the given hue, chroma, and Y. * * @param hueRadians The desired hue in radians. * @param chroma The desired chroma. * @param y The desired Y. * @return The desired color as a hexadecimal integer, if found; 0 * otherwise. */ static findResultByJ(e, t, r) { let n = Math.sqrt(r) * 11; const o = Z.DEFAULT, i = 1 / Math.pow(1.64 - Math.pow(0.29, o.n), 0.73), f = 0.25 * (Math.cos(e + 2) + 3.8) * (5e4 / 13) * o.nc * o.ncb, p = Math.sin(e), h = Math.cos(e); for (let y = 0; y < 5; y++) { const P = n / 100, g = t === 0 || n === 0 ? 0 : t / Math.sqrt(P), m = Math.pow(g * i, 1 / 0.9), T = o.aw * Math.pow(P, 1 / o.c / o.z) / o.nbb, D = 23 * (T + 0.305) * m / (23 * f + 11 * m * h + 108 * m * p), A = D * h, C = D * p, v = (460 * T + 451 * A + 288 * C) / 1403, M = (460 * T - 891 * A - 261 * C) / 1403, O = (460 * T - 220 * A - 6300 * C) / 1403, k = x.inverseChromaticAdaptation(v), F = x.inverseChromaticAdaptation(M), N = x.inverseChromaticAdaptation(O), L = Ie([k, F, N], x.LINRGB_FROM_SCALED_DISCOUNT); if (L[0] < 0 || L[1] < 0 || L[2] < 0) return 0; const U = x.Y_FROM_LINRGB[0], $ = x.Y_FROM_LINRGB[1], Q = x.Y_FROM_LINRGB[2], z = U * L[0] + $ * L[1] + Q * L[2]; if (z <= 0) return 0; if (y === 4 || Math.abs(z - r) < 2e-3) return L[0] > 100.01 || L[1] > 100.01 || L[2] > 100.01 ? 0 : Ne(L); n = n - (z - r) * n / (2 * z); } return 0; } /** * Finds an sRGB color with the given hue, chroma, and L*, if * possible. * * @param hueDegrees The desired hue, in degrees. * @param chroma The desired chroma. * @param lstar The desired L*. * @return A hexadecimal representing the sRGB color. The color * has sufficiently close hue, chroma, and L* to the desired * values, if possible; otherwise, the hue and L* will be * sufficiently close, and chroma will be maximized. */ static solveToInt(e, t, r) { if (t < 1e-4 || r < 1e-4 || r > 99.9999) return rt(r); e = W(e); const n = e / 180 * Math.PI, o = ae(r), i = x.findResultByJ(n, t, o); if (i !== 0) return i; const c = x.bisectToLimit(o, n); return Ne(c); } /** * Finds an sRGB color with the given hue, chroma, and L*, if * possible. * * @param hueDegrees The desired hue, in degrees. * @param chroma The desired chroma. * @param lstar The desired L*. * @return An CAM16 object representing the sRGB color. The color * has sufficiently close hue, chroma, and L* to the desired * values, if possible; otherwise, the hue and L* will be * sufficiently close, and chroma will be maximized. */ static solveToCam(e, t, r) { return q.fromInt(x.solveToInt(e, t, r)); } } x.SCALED_DISCOUNT_FROM_LINRGB = [ [ 0.001200833568784504, 0.002389694492170889, 2795742885861124e-19 ], [ 5891086651375999e-19, 0.0029785502573438758, 3270666104008398e-19 ], [ 10146692491640572e-20, 5364214359186694e-19, 0.0032979401770712076 ] ]; x.LINRGB_FROM_SCALED_DISCOUNT = [ [ 1373.2198709594231, -1100.4251190754821, -7.278681089101213 ], [ -271.815969077903, 559.6580465940733, -32.46047482791194 ], [ 1.9622899599665666, -57.173814538844006, 308.7233197812385 ] ]; x.Y_FROM_LINRGB = [0.2126, 0.7152, 0.0722]; x.CRITICAL_PLANES = [ 0.015176349177441876, 0.045529047532325624, 0.07588174588720938, 0.10623444424209313, 0.13658714259697685, 0.16693984095186062, 0.19729253930674434, 0.2276452376616281, 0.2579979360165119, 0.28835063437139563, 0.3188300904430532, 0.350925934958123, 0.3848314933096426, 0.42057480301049466, 0.458183274052838, 0.4976837250274023, 0.5391024159806381, 0.5824650784040898, 0.6277969426914107, 0.6751227633498623, 0.7244668422128921, 0.775853049866786, 0.829304845476233, 0.8848452951698498, 0.942497089126609, 1.0022825574869039, 1.0642236851973577, 1.1283421258858297, 1.1946592148522128, 1.2631959812511864, 1.3339731595349034, 1.407011200216447, 1.4823302800086415, 1.5599503113873272, 1.6398909516233677, 1.7221716113234105, 1.8068114625156377, 1.8938294463134073, 1.9832442801866852, 2.075074464868551, 2.1693382909216234, 2.2660538449872063, 2.36523901573795, 2.4669114995532007, 2.5710888059345764, 2.6777882626779785, 2.7870270208169257, 2.898822059350997, 3.0131901897720907, 3.1301480604002863, 3.2497121605402226, 3.3718988244681087, 3.4967242352587946, 3.624204428461639, 3.754355295633311, 3.887192587735158, 4.022731918402185, 4.160988767090289, 4.301978482107941, 4.445716283538092, 4.592217266055746, 4.741496401646282, 4.893568542229298, 5.048448422192488, 5.20615066083972, 5.3666897647573375, 5.5300801301023865, 5.696336044816294, 5.865471690767354, 6.037501145825082, 6.212438385869475, 6.390297286737924, 6.571091626112461, 6.7548350853498045, 6.941541251256611, 7.131223617812143, 7.323895587840543, 7.5195704746346665, 7.7182615035334345, 7.919981813454504, 8.124744458384042, 8.332562408825165, 8.543448553206703, 8.757415699253682, 8.974476575321063, 9.194643831691977, 9.417930041841839, 9.644347703669503, 9.873909240696694, 10.106627003236781, 10.342513269534024, 10.58158024687427, 10.8238400726681, 11.069304815507364, 11.317986476196008, 11.569896988756009, 11.825048221409341, 12.083451977536606, 12.345119996613247, 12.610063955123938, 12.878295467455942, 13.149826086772048, 13.42466730586372, 13.702830557985108, 13.984327217668513, 14.269168601521828, 14.55736596900856, 14.848930523210871, 15.143873411576273, 15.44220572664832, 15.743938506781891, 16.04908273684337, 16.35764934889634, 16.66964922287304, 16.985093187232053, 17.30399201960269, 17.62635644741625, 17.95219714852476, 18.281524751807332, 18.614349837764564, 18.95068293910138, 19.290534541298456, 19.633915083172692, 19.98083495742689, 20.331304511189067, 20.685334046541502, 21.042933821039977, 21.404114048223256, 21.76888489811322, 22.137256497705877, 22.50923893145328, 22.884842241736916, 23.264076429332462, 23.6469514538663, 24.033477234264016, 24.42366364919083, 24.817520537484558, 25.21505769858089, 25.61628489293138, 26.021211842414342, 26.429848230738664, 26.842203703840827, 27.258287870275353, 27.678110301598522, 28.10168053274597, 28.529008062403893, 28.96010235337422, 29.39497283293396, 29.83362889318845, 30.276079891419332, 30.722335150426627, 31.172403958865512, 31.62629557157785, 32.08401920991837, 32.54558406207592, 33.010999283389665, 33.4802739966603, 33.953417292456834, 34.430438229418264, 34.911345834551085, 35.39614910352207, 35.88485700094671, 36.37747846067349, 36.87402238606382, 37.37449765026789, 37.87891309649659, 38.38727753828926, 38.89959975977785, 39.41588851594697, 39.93615253289054, 40.460400508064545, 40.98864111053629, 41.520882981230194, 42.05713473317016, 42.597404951718396, 43.141702194811224, 43.6900349931913, 44.24241185063697, 44.798841244188324, 45.35933162437017, 45.92389141541209, 46.49252901546552, 47.065252796817916, 47.64207110610409, 48.22299226451468, 48.808024568002054, 49.3971762874833, 49.9904556690408, 50.587870934119984, 51.189430279724725, 51.79514187861014, 52.40501387947288, 53.0190544071392, 53.637271562750364, 54.259673423945976, 54.88626804504493, 55.517063457223934, 56.15206766869424, 56.79128866487574, 57.43473440856916, 58.08241284012621, 58.734331877617365, 59.39049941699807, 60.05092333227251, 60.715611475655585, 61.38457167773311, 62.057811747619894, 62.7353394731159, 63.417162620860914, 64.10328893648692, 64.79372614476921, 65.48848194977529, 66.18756403501224, 66.89098006357258, 67.59873767827808, 68.31084450182222, 69.02730813691093, 69.74813616640164, 70.47333615344107, 71.20291564160104, 71.93688215501312, 72.67524319850172, 73.41800625771542, 74.16517879925733, 74.9167682708136, 75.67278210128072, 76.43322770089146, 77.1981124613393, 77.96744375590167, 78.74122893956174, 79.51947534912904, 80.30219030335869, 81.08938110306934, 81.88105503125999, 82.67721935322541, 83.4778813166706, 84.28304815182372, 85.09272707154808, 85.90692527145302, 86.72564993000343, 87.54890820862819, 88.3767072518277, 89.2090541872801, 90.04595612594655, 90.88742016217518, 91.73345337380438, 92.58406282226491, 93.43925555268066, 94.29903859396902, 95.16341895893969, 96.03240364439274, 96.9059996312159, 97.78421388448044, 98.6670533535366, 99.55452497210776 ]; class E { static from(e, t, r) { return new E(x.solveToInt(e, t, r)); } /** * @param argb ARGB representation of a color. * @return HCT representation of a color in default viewing conditions */ static fromInt(e) { return new E(e); } toInt() { return this.argb; } /** * A number, in degrees, representing ex. red, orange, yellow, etc. * Ranges from 0 <= hue < 360. */ get hue() { return this.internalHue; } /** * @param newHue 0 <= newHue < 360; invalid values are corrected. * Chroma may decrease because chroma has a different maximum for any given * hue and tone. */ set hue(e) { this.setInternalState(x.solveToInt(e, this.internalChroma, this.internalTone)); } get chroma() { return this.internalChroma; } /** * @param newChroma 0 <= newChroma < ? * Chroma may decrease because chroma has a different maximum for any given * hue and tone. */ set chroma(e) { this.setInternalState(x.solveToInt(this.internalHue, e, this.internalTone)); } /** Lightness. Ranges from 0 to 100. */ get tone() { return this.internalTone; } /** * @param newTone 0 <= newTone <= 100; invalid valids are corrected. * Chroma may decrease because chroma has a different maximum for any given * hue and tone. */ set tone(e) { this.setInternalState(x.solveToInt(this.internalHue, this.internalChroma, e)); } /** Sets a property of the Hct object. */ setValue(e, t) { this[e] = t; } toString() { return `HCT(${this.hue.toFixed(0)}, ${this.chroma.toFixed(0)}, ${this.tone.toFixed(0)})`; } static isBlue(e) { return e >= 250 && e < 270; } static isYellow(e) { return e >= 105 && e < 125; } static isCyan(e) { return e >= 170 && e < 207; } constructor(e) { this.argb = e; const t = q.fromInt(e); this.internalHue = t.hue, this.internalChroma = t.chroma, this.internalTone = Ve(e), this.argb = e; } setInternalState(e) { const t = q.fromInt(e); this.internalHue = t.hue, this.internalChroma = t.chroma, this.internalTone = Ve(e), this.argb = e; } /** * Translates a color into different [ViewingConditions]. * * Colors change appearance. They look different with lights on versus off, * the same color, as in hex code, on white looks different when on black. * This is called color relativity, most famously explicated by Josef Albers * in Interaction of Color. * * In color science, color appearance models can account for this and * calculate the appearance of a color in different settings. HCT is based on * CAM16, a color appearance model, and uses it to make these calculations. * * See [ViewingConditions.make] for parameters affecting color appearance. */ inViewingConditions(e) { const r = q.fromInt(this.toInt()).xyzInViewingConditions(e), n = q.fromXyzInViewingConditions(r[0], r[1], r[2], Z.make()); return E.from(n.hue, n.chroma, ve(r[1])); } } class _ { /** * Returns a contrast ratio, which ranges from 1 to 21. * * @param toneA Tone between 0 and 100. Values outside will be clamped. * @param toneB Tone between 0 and 100. Values outside will be clamped. */ static ratioOfTones(e, t) { return e = G(0, 100, e), t = G(0, 100, t), _.ratioOfYs(ae(e), ae(t)); } static ratioOfYs(e, t) { const r = e > t ? e : t, n = r === t ? e : t; return (r + 5) / (n + 5); } /** * Returns a tone >= tone parameter that ensures ratio parameter. * Return value is between 0 and 100. * Returns -1 if ratio cannot be achieved with tone parameter. * * @param tone Tone return value must contrast with. * Range is 0 to 100. Invalid values will result in -1 being returned. * @param ratio Contrast ratio of return value and tone. * Range is 1 to 21, invalid values have undefined behavior. */ static lighter(e, t) { if (e < 0 || e > 100) return -1; const r = ae(e), n = t * (r + 5) - 5, o = _.ratioOfYs(n, r), i = Math.abs(o - t); if (o < t && i > 0.04) return -1; const c = ve(n) + 0.4; return c < 0 || c > 100 ? -1 : c; } /** * Returns a tone <= tone parameter that ensures ratio parameter. * Return value is between 0 and 100. * Returns -1 if ratio cannot be achieved with tone parameter. * * @param tone Tone return value must contrast with. * Range is 0 to 100. Invalid values will result in -1 being returned. * @param ratio Contrast ratio of return value and tone. * Range is 1 to 21, invalid values have undefined behavior. */ static darker(e, t) { if (e < 0 || e > 100) return -1; const r = ae(e), n = (r + 5) / t - 5, o = _.ratioOfYs(r, n), i = Math.abs(o - t); if (o < t && i > 0.04) return -1; const c = ve(n) - 0.4; return c < 0 || c > 100 ? -1 : c; } /** * Returns a tone >= tone parameter that ensures ratio parameter. * Return value is between 0 and 100. * Returns 100 if ratio cannot be achieved with tone parameter. * * This method is unsafe because the returned value is guaranteed to be in * bounds for tone, i.e. between 0 and 100. However, that value may not reach * the ratio with tone. For example, there is no color lighter than T100. * * @param tone Tone return value must contrast with. * Range is 0 to 100. Invalid values will result in 100 being returned. * @param ratio Desired contrast ratio of return value and tone parameter. * Range is 1 to 21, invalid values have undefined behavior. */ static lighterUnsafe(e, t) { const r = _.lighter(e, t); return r < 0 ? 100 : r; } /** * Returns a tone >= tone parameter that ensures ratio parameter. * Return value is between 0 and 100. * Returns 100 if ratio cannot be achieved with tone parameter. * * This method is unsafe because the returned value is guaranteed to be in * bounds for tone, i.e. between 0 and 100. However, that value may not reach * the [ratio with [tone]. For example, there is no color darker than T0. * * @param tone Tone return value must contrast with. * Range is 0 to 100. Invalid values will result in 0 being returned. * @param ratio Desired contrast ratio of return value and tone parameter. * Range is 1 to 21, invalid values have undefined behavior. */ static darkerUnsafe(e, t) { const r = _.darker(e, t); return r < 0 ? 0 : r; } } class de { /** * Returns true if a color is disliked. * * @param hct A color to be judged. * @return Whether the color is disliked. * * Disliked is defined as a dark yellow-green that is not neutral. */ static isDisliked(e) { const t = Math.round(e.hue) >= 90 && Math.round(e.hue) <= 111, r = Math.round(e.chroma) > 16, n = Math.round(e.tone) < 65; return t && r && n; } /** * If a color is disliked, lighten it to make it likable. * * @param hct A color to be judged. * @return A new color if the original color is disliked, or the original * color if it is acceptable. */ static fixIfDisliked(e) { return de.isDisliked(e) ? E.from(e.hue, e.chroma, 70) : e; } } function at(a, e, t) { if (a.name !== t.name) throw new Error(`Attempting to extend color ${a.name} with color ${t.name} of different name for spec version ${e}.`); if (a.isBackground !== t.isBackground) throw new Error(`Attempting to extend color ${a.name} as a ${a.isBackground ? "background" : "foreground"} with color ${t.name} as a ${t.isBackground ? "background" : "foreground"} for spec version ${e}.`); } function R(a, e, t) { return at(a, e, t), l.fromPalette({ name: a.name, palette: (r) => r.specVersion === e ? t.palette(r) : a.palette(r), tone: (r) => r.specVersion === e ? t.tone(r) : a.tone(r), isBackground: a.isBackground, chromaMultiplier: (r) => { const n = r.specVersion === e ? t.chromaMultiplier : a.chromaMultiplier; return n !== void 0 ? n(r) : 1; }, background: (r) => { const n = r.specVersion === e ? t.background : a.background; return n !== void 0 ? n(r) : void 0; }, secondBackground: (r) => { const n = r.specVersion === e ? t.secondBackground : a.secondBackground; return n !== void 0 ? n(r) : void 0; }, contrastCurve: (r) => { const n = r.specVersion === e ? t.contrastCurve : a.contrastCurve; return n !== void 0 ? n(r) : void 0; }, toneDeltaPair: (r) => { const n = r.specVersion === e ? t.toneDeltaPair : a.toneDeltaPair; return n !== void 0 ? n(r) : void 0; } }); } class l { /** * Create a DynamicColor defined by a TonalPalette and HCT tone. * * @param args Functions with DynamicScheme as input. Must provide a palette * and tone. May provide a background DynamicColor and ToneDeltaPair. */ static fromPalette(e) { return new l(e.name ?? "", e.palette, e.tone ?? l.getInitialToneFromBackground(e.background), e.isBackground ?? !1, e.chromaMultiplier, e.background, e.secondBackground, e.contrastCurve, e.toneDeltaPair); } static getInitialToneFromBackground(e) { return e === void 0 ? (t) => 50 : (t) => e(t) ? e(t).getTone(t) : 50; } /** * The base constructor for DynamicColor. * * _Strongly_ prefer using one of the convenience constructors. This class is * arguably too flexible to ensure it can support any scenario. Functional * arguments allow overriding without risks that come with subclasses. * * For example, the default behavior of adjust tone at max contrast * to be at a 7.0 ratio with its background is principled and * matches accessibility guidance. That does not mean it's the desired * approach for _every_ design system, and every color pairing, * always, in every case. * * @param name The name of the dynamic color. Defaults to empty. * @param palette Function that provides a TonalPalette given DynamicScheme. A * TonalPalette is defined by a hue and chroma, so this replaces the need * to specify hue/chroma. By providing a tonal palette, when contrast * adjustments are made, intended chroma can be preserved. * @param tone Function that provides a tone, given a DynamicScheme. * @param isBackground Whether this dynamic color is a background, with some * other color as the foreground. Defaults to false. * @param chromaMultiplier A factor that multiplies the chroma for this color. * @param background The background of the dynamic color (as a function of a * `DynamicScheme`), if it exists. * @param secondBackground A second background of the dynamic color (as a * function of a `DynamicScheme`), if it exists. * @param contrastCurve A `ContrastCurve` object specifying how its contrast * against its background should behave in various contrast levels * options. * @param toneDeltaPair A `ToneDeltaPair` object specifying a tone delta * constraint between two colors. One of them must be the color being * constructed. */ constructor(e, t, r, n, o, i, c, f, p) { if (this.name = e, this.palette = t, this.tone = r, this.isBackground = n, this.chromaMultiplier = o, this.background = i, this.secondBackground = c, this.contrastCurve = f, this.toneDeltaPair = p, this.hctCache = /* @__PURE__ */ new Map(), !i && c) throw new Error(`Color ${e} has secondBackgrounddefined, but background is not defined.`); if (!i && f) throw new Error(`Color ${e} has contrastCurvedefined, but background is not defined.`); if (i && !f) throw new Error(`Color ${e} has backgrounddefined, but contrastCurve is not defined.`); } /** * Returns a deep copy of this DynamicColor. */ clone() { return l.fromPalette({ name: this.name, palette: this.palette, tone: this.tone, isBackground: this.isBackground, chromaMultiplier: this.chromaMultiplier, background: this.background, secondBackground: this.secondBackground, contrastCurve: this.contrastCurve, toneDeltaPair: this.toneDeltaPair }); } /** * Clears the cache of HCT values for this color. For testing or debugging * purposes. */ clearCache() { this.hctCache.clear(); } /** * Returns a ARGB integer (i.e. a hex code). * * @param scheme Defines the conditions of the user interface, for example, * whether or not it is dark mode or light mode, and what the desired * contrast level is. */ getArgb(e) { return this.getHct(e).toInt(); } /** * Returns a color, expressed in the HCT color space, that this * DynamicColor is under the conditions in scheme. * * @param scheme Defines the conditions of the user interface, for example, * whether or not it is dark mode or light mode, and what the desired * contrast level is. */ getHct(e) { const t = this.hctCache.get(e); if (t != null) return t; const r = _e(e.specVersion).getHct(e, this); return this.hctCache.size > 4 && this.hctCache.clear(), this.hctCache.set(e, r), r; } /** * Returns a tone, T in the HCT color space, that this DynamicColor is under * the conditions in scheme. * * @param scheme Defines the conditions of the user interface, for example, * whether or not it is dark mode or light mode, and what the desired * contrast level is. */ getTone(e) { return _e(e.specVersion).getTone(e, this); } /** * Given a background tone, finds a foreground tone, while ensuring they reach * a contrast ratio that is as close to [ratio] as possible. * * @param bgTone Tone in HCT. Range is 0 to 100, undefined behavior when it * falls outside that range. * @param ratio The contrast ratio desired between bgTone and the return * value. */ static foregroundTone(e, t) { const r = _.lighterUnsafe(e, t), n = _.darkerUnsafe(e, t), o = _.ratioOfTones(r, e), i = _.ratioOfTones(n, e); if (l.tonePrefersLightForeground(e)) { const f = Math.abs(o - i) < 0.1 && o < t && i < t; return o >= t || o >= i || f ? r : n; } else return i >= t || i >= o ? n : r; } /** * Returns whether [tone] prefers a light foreground. * * People prefer white foregrounds on ~T60-70. Observed over time, and also * by Andrew Somers during research for APCA. * * T60 used as to create the smallest discontinuity possible when skipping * down to T49 in order to ensure light foregrounds. * Since `tertiaryContainer` in dark monochrome scheme requires a tone of * 60, it should not be adjusted. Therefore, 60 is excluded here. */ static tonePrefersLightForeground(e) { return Math.round(e) < 60; } /** * Returns whether [tone] can reach a contrast ratio of 4.5 with a lighter * color. */ static toneAllowsLightForeground(e) { return Math.round(e) <= 49; } /** * Adjusts a tone such that white has 4.5 contrast, if the tone is * reasonably close to supporting it. */ static enableLightForeground(e) { return l.tonePrefersLightForeground(e) && !l.toneAllowsLightForeground(e) ? 49 : e; } } class ot { getHct(e, t) { const r = t.getTone(e); return t.palette(e).getHct(r); } getTone(e, t) { const r = e.contrastLevel < 0, n = t.toneDeltaPair ? t.toneDeltaPair(e) : void 0; if (n) { const o = n.roleA, i = n.roleB, c = n.delta, f = n.polarity, p = n.stayTogether, h = f === "nearer" || f === "lighter" && !e.isDark || f === "darker" && e.isDark, y = h ? o : i, P = h ? i : o, g = t.name === y.name, m = e.isDark ? 1 : -1; let d = y.tone(e), T = P.tone(e); if (t.background && y.contrastCurve && P.contrastCurve) { const D = t.background(e), A = y.contrastCurve(e), C = P.contrastCurve(e); if (D && A && C) { const v = D.getTone(e), M = A.get(e.contrastLevel), O = C.get(e.contrastLevel); _.ratioOfTones(v, d) < M && (d = l.foregroundTone(v, M)), _.ratioOfTones(v, T) < O && (T = l.foregroundTone(v, O)), r && (d = l.foregroundTone(v, M), T = l.foregroundTone(v, O)); } } return (T - d) * m < c && (T = G(0, 100, d + c * m), (T - d) * m >= c || (d = G(0, 100, T - c * m))), 50 <= d && d < 60 ? m > 0 ? (d = 60, T = Math.max(T, d + c * m)) : (d = 49, T = Math.min(T, d + c * m)) : 50 <= T && T < 60 && (p ? m > 0 ? (d = 60, T = Math.max(T, d + c * m)) : (d = 49, T = Math.min(T, d + c * m)) : m > 0 ? T = 60 : T = 49), g ? d : T; } else { let o = t.tone(e); if (t.background == null || t.background(e) === void 0 || t.contrastCurve == null || t.contrastCurve(e) === void 0) return o; const i = t.background(e).getTone(e), c = t.contrastCurve(e).get(e.contrastLevel); if (_.ratioOfTones(i, o) >= c || (o = l.foregroundTone(i, c)), r && (o = l.foregroundTone(i, c)), t.isBackground && 50 <= o && o < 60 && (_.ratioOfTones(49, i) >= c ? o = 49 : o = 60), t.secondBackground == null || t.secondBackground(e) === void 0) return o; const [f, p] = [t.background, t.secondBackground], [h, y] = [f(e).getTone(e), p(e).getTone(e)], [P, g] = [Math.max(h, y), Math.min(h, y)]; if (_.ratioOfTones(P, o) >= c && _.ratioOfTones(g, o) >= c) return o; const m = _.lighter(P, c), d = _.darker(g, c), T = []; return m !== -1 && T.push(m), d !== -1 && T.push(d), l.tonePrefersLightForeground(h) || l.tonePrefersLightForeground(y) ? m < 0 ? 100 : m : T.length === 1 ? T[0] : d < 0 ? 0 : d; } } } class it { getHct(e, t) { const r = t.palette(e), n = t.getTone(e), o = r.hue, i = r.chroma * (t.chromaMultiplier ? t.chromaMultiplier(e) : 1); return E.from(o, i, n); } getTone(e, t) { const r = t.toneDeltaPair ? t.toneDeltaPair(e) : void 0; if (r) { const n = r.roleA, o = r.roleB, i = r.polarity, c = r.constraint, f = i === "darker" || i === "relative_lighter" && e.isDark || i === "relative_darker" && !e.isDark ? -r.delta : r.delta, p = t.name === n.name, h = p ? n : o, y = p ? o : n; let P = h.tone(e), g = y.getTone(e); const m = f * (p ? 1 : -1); if (c === "exact" ? P = G(0, 100, g + m) : c === "nearer" ? m > 0 ? P = G(0, 100, G(g, g + m, P)) : P = G(0, 100, G(g + m, g, P)) : c === "farther" && (m > 0 ? P = G(g + m, 100, P) : P = G(0, g + m, P)), t.background && t.contrastCurve) { const d = t.background(e), T = t.contrastCurve(e); if (d && T) { const D = d.getTone(e), A = T.get(e.contrastLevel); P = _.ratioOfTones(D, P) >= A && e.contrastLevel >= 0 ? P : l.foregroundTone(D, A); } } return t.isBackground && !t.name.endsWith("_fixed_dim") && (P >= 57 ? P = G(65, 100, P) : P = G(0, 49, P)), P; } else { let n = t.tone(e); if (t.background == null || t.background(e) === void 0 || t.contrastCurve == null || t.contrastCurve(e) === void 0) return n; const o = t.background(e).getTone(e), i = t.contrastCurve(e).get(e.contrastLevel); if (n = _.ratioOfTones(o, n) >= i && e.contrastLevel >= 0 ? n : l.foregroundTone(o, i), t.isBackground && !t.name.endsWith("_fixed_dim") && (n >= 57 ? n = G(65, 100, n) : n = G(0, 49, n)), t.secondBackground == null || t.secondBackground(e) === void 0) return n; const [c, f] = [t.background, t.secondBackground], [p, h] = [c(e).getTone(e), f(e).getTone(e)], [y, P] = [Math.max(p, h), Math.min(p, h)]; if (_.ratioOfTones(y, n) >= i && _.ratioOfTones(P, n) >= i) return n; const g = _.lighter(y, i), m = _.darker(P, i), d = []; return g !== -1 && d.push(g), m !== -1 && d.push(m), l.tonePrefersLightForeground(p) || l.tonePrefersLightForeground(h) ? g < 0 ? 100 : g : d.length === 1 ? d[0] : m < 0 ? 0 : m; } } } const st = new ot(), ct =