/**
 * @license MIT
 * author: Cube Dev Team
 * @cube-dev/ui-kit v0.0.0-canary-5e810c3
 * Released under the MIT license.
 */

// ============================================================================
// OKHSL to RGB conversion (inlined from okhsl-plugin for static conversion)
// ============================================================================
// OKHSL conversion internals (from texel-color, same as okhsl-plugin)
const OKLab_to_LMS_M = [
    [1.0, 0.3963377773761749, 0.2158037573099136],
    [1.0, -0.1055613458156586, -0.0638541728258133],
    [1.0, -0.0894841775298119, -1.2914855480194092],
];
const LMS_to_linear_sRGB_M = [
    [4.076741636075959, -3.307711539258062, 0.2309699031821041],
    [-1.2684379732850313, 2.6097573492876878, -0.3413193760026569],
    [-0.004196076138675526, -0.703418617935936, 1.7076146940746113],
];
const OKLab_to_linear_sRGB_coefficients = [
    [
        [-1.8817030993265873, -0.8093650129914302],
        [1.19086277, 1.76576728, 0.59662641, 0.75515197, 0.56771245],
    ],
    [
        [1.8144407988010998, -1.194452667805235],
        [0.73956515, -0.45954404, 0.08285427, 0.12541073, -0.14503204],
    ],
    [
        [0.13110757611180954, 1.813339709266608],
        [1.35733652, -0.00915799, -1.1513021, -0.50559606, 0.00692167],
    ],
];
const TAU = 2 * Math.PI;
const K1 = 0.206;
const K2 = 0.03;
const K3 = (1.0 + K1) / (1.0 + K2);
const constrainAngle = (angle) => ((angle % 360) + 360) % 360;
const toeInv = (x) => (x ** 2 + K1 * x) / (K3 * (x + K2));
const dot3 = (a, b) => a[0] * b[0] + a[1] * b[1] + a[2] * b[2];
const dotXY = (a, b) => a[0] * b[0] + a[1] * b[1];
const transform = (input, matrix) => [
    dot3(input, matrix[0]),
    dot3(input, matrix[1]),
    dot3(input, matrix[2]),
];
const cubed3 = (lms) => [lms[0] ** 3, lms[1] ** 3, lms[2] ** 3];
const OKLabToLinearSRGB = (lab) => {
    const lms = transform(lab, OKLab_to_LMS_M);
    return transform(cubed3(lms), LMS_to_linear_sRGB_M);
};
const sRGBLinearToGamma = (val) => {
    const sign = val < 0 ? -1 : 1;
    const abs = Math.abs(val);
    return abs > 0.0031308
        ? sign * (1.055 * Math.pow(abs, 1 / 2.4) - 0.055)
        : 12.92 * val;
};
const computeMaxSaturationOKLC = (a, b) => {
    const okCoeff = OKLab_to_linear_sRGB_coefficients;
    const lmsToRgb = LMS_to_linear_sRGB_M;
    const tmp2 = [a, b];
    const tmp3 = [0, a, b];
    let chnlCoeff;
    let chnlLMS;
    if (dotXY(okCoeff[0][0], tmp2) > 1) {
        chnlCoeff = okCoeff[0][1];
        chnlLMS = lmsToRgb[0];
    }
    else if (dotXY(okCoeff[1][0], tmp2) > 1) {
        chnlCoeff = okCoeff[1][1];
        chnlLMS = lmsToRgb[1];
    }
    else {
        chnlCoeff = okCoeff[2][1];
        chnlLMS = lmsToRgb[2];
    }
    const [k0, k1, k2, k3, k4] = chnlCoeff;
    const [wl, wm, ws] = chnlLMS;
    let sat = k0 + k1 * a + k2 * b + k3 * (a * a) + k4 * a * b;
    const dotYZ = (mat, vec) => mat[1] * vec[1] + mat[2] * vec[2];
    const kl = dotYZ(OKLab_to_LMS_M[0], tmp3);
    const km = dotYZ(OKLab_to_LMS_M[1], tmp3);
    const ks = dotYZ(OKLab_to_LMS_M[2], tmp3);
    let l_ = 1.0 + sat * kl;
    let m_ = 1.0 + sat * km;
    let s_ = 1.0 + sat * ks;
    const l = l_ ** 3;
    const m = m_ ** 3;
    const s = s_ ** 3;
    const lds = 3.0 * kl * l_ * l_;
    const mds = 3.0 * km * m_ * m_;
    const sds = 3.0 * ks * s_ * s_;
    const lds2 = 6.0 * kl * kl * l_;
    const mds2 = 6.0 * km * km * m_;
    const sds2 = 6.0 * ks * ks * s_;
    const f = wl * l + wm * m + ws * s;
    const f1 = wl * lds + wm * mds + ws * sds;
    const f2 = wl * lds2 + wm * mds2 + ws * sds2;
    sat = sat - (f * f1) / (f1 * f1 - 0.5 * f * f2);
    return sat;
};
const findCuspOKLCH = (a, b) => {
    const S_cusp = computeMaxSaturationOKLC(a, b);
    const lab = [1, S_cusp * a, S_cusp * b];
    const rgb_at_max = OKLabToLinearSRGB(lab);
    const L_cusp = Math.cbrt(1 /
        Math.max(Math.max(rgb_at_max[0], rgb_at_max[1]), Math.max(rgb_at_max[2], 0.0)));
    return [L_cusp, L_cusp * S_cusp];
};
const findGamutIntersectionOKLCH = (a, b, l1, c1, l0, cusp) => {
    const lmsToRgb = LMS_to_linear_sRGB_M;
    const tmp3 = [0, a, b];
    const floatMax = Number.MAX_VALUE;
    let t;
    const dotYZ = (mat, vec) => mat[1] * vec[1] + mat[2] * vec[2];
    const dotXYZ = (vec, x, y, z) => vec[0] * x + vec[1] * y + vec[2] * z;
    if ((l1 - l0) * cusp[1] - (cusp[0] - l0) * c1 <= 0.0) {
        const denom = c1 * cusp[0] + cusp[1] * (l0 - l1);
        t = denom === 0 ? 0 : (cusp[1] * l0) / denom;
    }
    else {
        const denom = c1 * (cusp[0] - 1.0) + cusp[1] * (l0 - l1);
        t = denom === 0 ? 0 : (cusp[1] * (l0 - 1.0)) / denom;
        const dl = l1 - l0;
        const dc = c1;
        const kl = dotYZ(OKLab_to_LMS_M[0], tmp3);
        const km = dotYZ(OKLab_to_LMS_M[1], tmp3);
        const ks = dotYZ(OKLab_to_LMS_M[2], tmp3);
        const L = l0 * (1.0 - t) + t * l1;
        const C = t * c1;
        const l_ = L + C * kl;
        const m_ = L + C * km;
        const s_ = L + C * ks;
        const l = l_ ** 3;
        const m = m_ ** 3;
        const s = s_ ** 3;
        const ldt = 3 * (dl + dc * kl) * l_ * l_;
        const mdt = 3 * (dl + dc * km) * m_ * m_;
        const sdt = 3 * (dl + dc * ks) * s_ * s_;
        const ldt2 = 6 * (dl + dc * kl) ** 2 * l_;
        const mdt2 = 6 * (dl + dc * km) ** 2 * m_;
        const sdt2 = 6 * (dl + dc * ks) ** 2 * s_;
        const r_ = dotXYZ(lmsToRgb[0], l, m, s) - 1;
        const r1 = dotXYZ(lmsToRgb[0], ldt, mdt, sdt);
        const r2 = dotXYZ(lmsToRgb[0], ldt2, mdt2, sdt2);
        const ur = r1 / (r1 * r1 - 0.5 * r_ * r2);
        let tr = -r_ * ur;
        const g_ = dotXYZ(lmsToRgb[1], l, m, s) - 1;
        const g1 = dotXYZ(lmsToRgb[1], ldt, mdt, sdt);
        const g2 = dotXYZ(lmsToRgb[1], ldt2, mdt2, sdt2);
        const ug = g1 / (g1 * g1 - 0.5 * g_ * g2);
        let tg = -g_ * ug;
        const b_ = dotXYZ(lmsToRgb[2], l, m, s) - 1;
        const b1 = dotXYZ(lmsToRgb[2], ldt, mdt, sdt);
        const b2 = dotXYZ(lmsToRgb[2], ldt2, mdt2, sdt2);
        const ub = b1 / (b1 * b1 - 0.5 * b_ * b2);
        let tb = -b_ * ub;
        tr = ur >= 0.0 ? tr : floatMax;
        tg = ug >= 0.0 ? tg : floatMax;
        tb = ub >= 0.0 ? tb : floatMax;
        t += Math.min(tr, Math.min(tg, tb));
    }
    return t;
};
const computeSt = (cusp) => [
    cusp[1] / cusp[0],
    cusp[1] / (1 - cusp[0]),
];
const computeStMid = (a, b) => [
    0.11516993 +
        1.0 /
            (7.4477897 +
                4.1590124 * b +
                a *
                    (-2.19557347 +
                        1.75198401 * b +
                        a *
                            (-2.13704948 -
                                10.02301043 * b +
                                a * (-4.24894561 + 5.38770819 * b + 4.69891013 * a)))),
    0.11239642 +
        1.0 /
            (1.6132032 -
                0.68124379 * b +
                a *
                    (0.40370612 +
                        0.90148123 * b +
                        a *
                            (-0.27087943 +
                                0.6122399 * b +
                                a * (0.00299215 - 0.45399568 * b - 0.14661872 * a)))),
];
const getCs = (L, a, b, cusp) => {
    const cMax = findGamutIntersectionOKLCH(a, b, L, 1, L, cusp);
    const stMax = computeSt(cusp);
    const k = cMax / Math.min(L * stMax[0], (1 - L) * stMax[1]);
    const stMid = computeStMid(a, b);
    let ca = L * stMid[0];
    let cb = (1.0 - L) * stMid[1];
    const cMid = 0.9 * k * Math.sqrt(Math.sqrt(1.0 / (1.0 / ca ** 4 + 1.0 / cb ** 4)));
    ca = L * 0.4;
    cb = (1.0 - L) * 0.8;
    const c0 = Math.sqrt(1.0 / (1.0 / ca ** 2 + 1.0 / cb ** 2));
    return [c0, cMid, cMax];
};
const OKHSLToOKLab = (hsl) => {
    let h = hsl[0];
    const s = hsl[1];
    const l = hsl[2];
    let L = toeInv(l);
    let a = 0;
    let b = 0;
    h = constrainAngle(h) / 360.0;
    if (L !== 0.0 && L !== 1.0 && s !== 0) {
        const a_ = Math.cos(TAU * h);
        const b_ = Math.sin(TAU * h);
        const cusp = findCuspOKLCH(a_, b_);
        const Cs = getCs(L, a_, b_, cusp);
        const [c0, cMid, cMax] = Cs;
        const mid = 0.8;
        const midInv = 1.25;
        let t, k0, k1, k2;
        if (s < mid) {
            t = midInv * s;
            k0 = 0.0;
            k1 = mid * c0;
            k2 = 1.0 - k1 / cMid;
        }
        else {
            t = 5 * (s - 0.8);
            k0 = cMid;
            k1 = (0.2 * cMid ** 2 * 1.25 ** 2) / c0;
            k2 = 1.0 - k1 / (cMax - cMid);
        }
        const c = k0 + (t * k1) / (1.0 - k2 * t);
        a = c * a_;
        b = c * b_;
    }
    return [L, a, b];
};
function okhslToSrgbInternal(h, s, l) {
    const oklab = OKHSLToOKLab([h, s, l]);
    const linearRGB = OKLabToLinearSRGB(oklab);
    return [
        sRGBLinearToGamma(linearRGB[0]),
        sRGBLinearToGamma(linearRGB[1]),
        sRGBLinearToGamma(linearRGB[2]),
    ];
}
/**
 * Convert OKHSL color string to RGB.
 * Uses the same algorithm as the okhsl-plugin.
 */
export function okhslToRgb(okhslStr) {
    const match = okhslStr.match(/okhsl\(([^)]+)\)/i);
    if (!match)
        return null;
    const inner = match[1].trim();
    const [colorPart, alphaPart] = inner.split('/');
    const parts = colorPart
        .trim()
        .split(/[,\s]+/)
        .filter(Boolean);
    if (parts.length < 3)
        return null;
    // Parse hue (can have units)
    let h = parseFloat(parts[0]);
    const hueStr = parts[0].toLowerCase();
    if (hueStr.endsWith('turn'))
        h = parseFloat(hueStr) * 360;
    else if (hueStr.endsWith('rad'))
        h = (parseFloat(hueStr) * 180) / Math.PI;
    else if (hueStr.endsWith('deg'))
        h = parseFloat(hueStr);
    // Parse saturation and lightness (percentages)
    const parsePercent = (val) => {
        const num = parseFloat(val);
        return val.includes('%') ? num / 100 : num;
    };
    const s = Math.max(0, Math.min(1, parsePercent(parts[1])));
    const l = Math.max(0, Math.min(1, parsePercent(parts[2])));
    // OKHSL to sRGB conversion
    const [r, g, b] = okhslToSrgbInternal(h, s, l);
    // Convert to 0-255 range
    const r255 = Math.round(Math.max(0, Math.min(1, r)) * 255);
    const g255 = Math.round(Math.max(0, Math.min(1, g)) * 255);
    const b255 = Math.round(Math.max(0, Math.min(1, b)) * 255);
    if (alphaPart) {
        const alpha = parseFloat(alphaPart.trim());
        return `rgba(${r255}, ${g255}, ${b255}, ${alpha})`;
    }
    return `rgb(${r255} ${g255} ${b255})`;
}

        