color-value-tools 1.2.0 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cjs/index.js CHANGED
@@ -1365,8 +1365,13 @@ function isReadableOnBackground(textColor, background, options) {
1365
1365
  const level = (_a = options === null || options === void 0 ? void 0 : options.level) !== null && _a !== void 0 ? _a : 'AA';
1366
1366
  const large = (_b = options === null || options === void 0 ? void 0 : options.largeText) !== null && _b !== void 0 ? _b : false;
1367
1367
  const minRequired = level === 'AAA' ? (large ? 4.5 : 7) : (large ? 3 : 4.5);
1368
+ // The specific effective background color that minRatio was actually
1369
+ // computed against — wcagLevel below is derived from this same color
1370
+ // (never a hardcoded '#ffffff') so it can't disagree with minRatio/readable.
1368
1371
  let minRatio;
1372
+ let effectiveBackground;
1369
1373
  if (typeof background === 'string') {
1374
+ effectiveBackground = background;
1370
1375
  minRatio = contrastRatio(textColor, background);
1371
1376
  }
1372
1377
  else if (background.type === 'semi-transparent') {
@@ -1377,13 +1382,24 @@ function isReadableOnBackground(textColor, background, options) {
1377
1382
  const cr = Math.round(((_e = fg.r) !== null && _e !== void 0 ? _e : 0) * alpha + ((_f = bg.r) !== null && _f !== void 0 ? _f : 255) * (1 - alpha));
1378
1383
  const cg = Math.round(((_g = fg.g) !== null && _g !== void 0 ? _g : 0) * alpha + ((_h = bg.g) !== null && _h !== void 0 ? _h : 255) * (1 - alpha));
1379
1384
  const cb = Math.round(((_j = fg.b) !== null && _j !== void 0 ? _j : 0) * alpha + ((_k = bg.b) !== null && _k !== void 0 ? _k : 255) * (1 - alpha));
1380
- minRatio = contrastRatio(textColor, rgbToHex({ r: cr, g: cg, b: cb }));
1385
+ effectiveBackground = rgbToHex({ r: cr, g: cg, b: cb });
1386
+ minRatio = contrastRatio(textColor, effectiveBackground);
1381
1387
  }
1382
1388
  else {
1383
- const ratios = background.stops.map(stop => contrastRatio(textColor, stop));
1384
- minRatio = Math.min(...ratios);
1389
+ // The worst-case stop (lowest ratio) drives both minRatio and wcagLevel.
1390
+ let worstStop = background.stops[0];
1391
+ let worstRatio = Infinity;
1392
+ for (const stop of background.stops) {
1393
+ const ratio = contrastRatio(textColor, stop);
1394
+ if (ratio < worstRatio) {
1395
+ worstRatio = ratio;
1396
+ worstStop = stop;
1397
+ }
1398
+ }
1399
+ effectiveBackground = worstStop;
1400
+ minRatio = worstRatio;
1385
1401
  }
1386
- const wLevel = wcagLevel(textColor, typeof background === 'string' ? background : '#ffffff');
1402
+ const wLevel = wcagLevel(textColor, effectiveBackground);
1387
1403
  return { readable: minRatio >= minRequired, minContrastRatio: +minRatio.toFixed(2), wcagLevel: wLevel };
1388
1404
  }
1389
1405
  function bestContrastPalette(background, palettes, options) {
@@ -1365,8 +1365,13 @@ function isReadableOnBackground(textColor, background, options) {
1365
1365
  const level = (_a = options === null || options === void 0 ? void 0 : options.level) !== null && _a !== void 0 ? _a : 'AA';
1366
1366
  const large = (_b = options === null || options === void 0 ? void 0 : options.largeText) !== null && _b !== void 0 ? _b : false;
1367
1367
  const minRequired = level === 'AAA' ? (large ? 4.5 : 7) : (large ? 3 : 4.5);
1368
+ // The specific effective background color that minRatio was actually
1369
+ // computed against — wcagLevel below is derived from this same color
1370
+ // (never a hardcoded '#ffffff') so it can't disagree with minRatio/readable.
1368
1371
  let minRatio;
1372
+ let effectiveBackground;
1369
1373
  if (typeof background === 'string') {
1374
+ effectiveBackground = background;
1370
1375
  minRatio = contrastRatio(textColor, background);
1371
1376
  }
1372
1377
  else if (background.type === 'semi-transparent') {
@@ -1377,13 +1382,24 @@ function isReadableOnBackground(textColor, background, options) {
1377
1382
  const cr = Math.round(((_e = fg.r) !== null && _e !== void 0 ? _e : 0) * alpha + ((_f = bg.r) !== null && _f !== void 0 ? _f : 255) * (1 - alpha));
1378
1383
  const cg = Math.round(((_g = fg.g) !== null && _g !== void 0 ? _g : 0) * alpha + ((_h = bg.g) !== null && _h !== void 0 ? _h : 255) * (1 - alpha));
1379
1384
  const cb = Math.round(((_j = fg.b) !== null && _j !== void 0 ? _j : 0) * alpha + ((_k = bg.b) !== null && _k !== void 0 ? _k : 255) * (1 - alpha));
1380
- minRatio = contrastRatio(textColor, rgbToHex({ r: cr, g: cg, b: cb }));
1385
+ effectiveBackground = rgbToHex({ r: cr, g: cg, b: cb });
1386
+ minRatio = contrastRatio(textColor, effectiveBackground);
1381
1387
  }
1382
1388
  else {
1383
- const ratios = background.stops.map(stop => contrastRatio(textColor, stop));
1384
- minRatio = Math.min(...ratios);
1389
+ // The worst-case stop (lowest ratio) drives both minRatio and wcagLevel.
1390
+ let worstStop = background.stops[0];
1391
+ let worstRatio = Infinity;
1392
+ for (const stop of background.stops) {
1393
+ const ratio = contrastRatio(textColor, stop);
1394
+ if (ratio < worstRatio) {
1395
+ worstRatio = ratio;
1396
+ worstStop = stop;
1397
+ }
1398
+ }
1399
+ effectiveBackground = worstStop;
1400
+ minRatio = worstRatio;
1385
1401
  }
1386
- const wLevel = wcagLevel(textColor, typeof background === 'string' ? background : '#ffffff');
1402
+ const wLevel = wcagLevel(textColor, effectiveBackground);
1387
1403
  return { readable: minRatio >= minRequired, minContrastRatio: +minRatio.toFixed(2), wcagLevel: wLevel };
1388
1404
  }
1389
1405
  function bestContrastPalette(background, palettes, options) {
package/dist/esm/index.js CHANGED
@@ -1265,8 +1265,13 @@ export function isReadableOnBackground(textColor, background, options) {
1265
1265
  const level = (_a = options === null || options === void 0 ? void 0 : options.level) !== null && _a !== void 0 ? _a : 'AA';
1266
1266
  const large = (_b = options === null || options === void 0 ? void 0 : options.largeText) !== null && _b !== void 0 ? _b : false;
1267
1267
  const minRequired = level === 'AAA' ? (large ? 4.5 : 7) : (large ? 3 : 4.5);
1268
+ // The specific effective background color that minRatio was actually
1269
+ // computed against — wcagLevel below is derived from this same color
1270
+ // (never a hardcoded '#ffffff') so it can't disagree with minRatio/readable.
1268
1271
  let minRatio;
1272
+ let effectiveBackground;
1269
1273
  if (typeof background === 'string') {
1274
+ effectiveBackground = background;
1270
1275
  minRatio = contrastRatio(textColor, background);
1271
1276
  }
1272
1277
  else if (background.type === 'semi-transparent') {
@@ -1277,13 +1282,24 @@ export function isReadableOnBackground(textColor, background, options) {
1277
1282
  const cr = Math.round(((_e = fg.r) !== null && _e !== void 0 ? _e : 0) * alpha + ((_f = bg.r) !== null && _f !== void 0 ? _f : 255) * (1 - alpha));
1278
1283
  const cg = Math.round(((_g = fg.g) !== null && _g !== void 0 ? _g : 0) * alpha + ((_h = bg.g) !== null && _h !== void 0 ? _h : 255) * (1 - alpha));
1279
1284
  const cb = Math.round(((_j = fg.b) !== null && _j !== void 0 ? _j : 0) * alpha + ((_k = bg.b) !== null && _k !== void 0 ? _k : 255) * (1 - alpha));
1280
- minRatio = contrastRatio(textColor, rgbToHex({ r: cr, g: cg, b: cb }));
1285
+ effectiveBackground = rgbToHex({ r: cr, g: cg, b: cb });
1286
+ minRatio = contrastRatio(textColor, effectiveBackground);
1281
1287
  }
1282
1288
  else {
1283
- const ratios = background.stops.map(stop => contrastRatio(textColor, stop));
1284
- minRatio = Math.min(...ratios);
1289
+ // The worst-case stop (lowest ratio) drives both minRatio and wcagLevel.
1290
+ let worstStop = background.stops[0];
1291
+ let worstRatio = Infinity;
1292
+ for (const stop of background.stops) {
1293
+ const ratio = contrastRatio(textColor, stop);
1294
+ if (ratio < worstRatio) {
1295
+ worstRatio = ratio;
1296
+ worstStop = stop;
1297
+ }
1298
+ }
1299
+ effectiveBackground = worstStop;
1300
+ minRatio = worstRatio;
1285
1301
  }
1286
- const wLevel = wcagLevel(textColor, typeof background === 'string' ? background : '#ffffff');
1302
+ const wLevel = wcagLevel(textColor, effectiveBackground);
1287
1303
  return { readable: minRatio >= minRequired, minContrastRatio: +minRatio.toFixed(2), wcagLevel: wLevel };
1288
1304
  }
1289
1305
  export function bestContrastPalette(background, palettes, options) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "color-value-tools",
3
- "version": "1.2.0",
3
+ "version": "1.2.1",
4
4
  "description": "Parse, convert and manipulate colors across hex, RGB, HSL, Lab, LCH, OKLCH and CMYK, with WCAG contrast checks and CSS variables. Zero dependencies.",
5
5
  "author": "macrulez <macrulezru@gmail.com> (https://macrulez.ru/en)",
6
6
  "license": "MIT",