chromonym 1.1.0 → 1.2.0

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.
Files changed (73) hide show
  1. package/NOTICE.md +39 -0
  2. package/README.md +78 -3
  3. package/dist/colorspaces/registry.d.ts +26 -0
  4. package/dist/colorspaces/registry.d.ts.map +1 -0
  5. package/dist/colorspaces/registry.js +36 -0
  6. package/dist/colorspaces/registry.js.map +1 -0
  7. package/dist/conversions/hex.d.ts.map +1 -1
  8. package/dist/conversions/hex.js +6 -5
  9. package/dist/conversions/hex.js.map +1 -1
  10. package/dist/conversions/hsl.d.ts.map +1 -1
  11. package/dist/conversions/hsl.js +34 -52
  12. package/dist/conversions/hsl.js.map +1 -1
  13. package/dist/conversions/hsv.d.ts.map +1 -1
  14. package/dist/conversions/hsv.js +30 -48
  15. package/dist/conversions/hsv.js.map +1 -1
  16. package/dist/conversions/pantone.d.ts +5 -2
  17. package/dist/conversions/pantone.d.ts.map +1 -1
  18. package/dist/conversions/pantone.js +8 -44
  19. package/dist/conversions/pantone.js.map +1 -1
  20. package/dist/conversions/rgb.d.ts +4 -2
  21. package/dist/conversions/rgb.d.ts.map +1 -1
  22. package/dist/conversions/rgb.js +28 -17
  23. package/dist/conversions/rgb.js.map +1 -1
  24. package/dist/convert.d.ts +12 -1
  25. package/dist/convert.d.ts.map +1 -1
  26. package/dist/convert.js +24 -6
  27. package/dist/convert.js.map +1 -1
  28. package/dist/detectFormat.d.ts +8 -0
  29. package/dist/detectFormat.d.ts.map +1 -1
  30. package/dist/detectFormat.js +17 -5
  31. package/dist/detectFormat.js.map +1 -1
  32. package/dist/identify.d.ts +13 -5
  33. package/dist/identify.d.ts.map +1 -1
  34. package/dist/identify.js +20 -35
  35. package/dist/identify.js.map +1 -1
  36. package/dist/index.d.ts +2 -2
  37. package/dist/index.d.ts.map +1 -1
  38. package/dist/index.js +2 -2
  39. package/dist/index.js.map +1 -1
  40. package/dist/indexing.d.ts +44 -0
  41. package/dist/indexing.d.ts.map +1 -0
  42. package/dist/indexing.js +140 -0
  43. package/dist/indexing.js.map +1 -0
  44. package/dist/math/clamp.d.ts +11 -0
  45. package/dist/math/clamp.d.ts.map +1 -0
  46. package/dist/math/clamp.js +18 -0
  47. package/dist/math/clamp.js.map +1 -0
  48. package/dist/math/colorSpace.d.ts +39 -0
  49. package/dist/math/colorSpace.d.ts.map +1 -0
  50. package/dist/math/colorSpace.js +85 -0
  51. package/dist/math/colorSpace.js.map +1 -0
  52. package/dist/math/deltaE.d.ts +47 -0
  53. package/dist/math/deltaE.d.ts.map +1 -0
  54. package/dist/math/deltaE.js +185 -0
  55. package/dist/math/deltaE.js.map +1 -0
  56. package/dist/math/euclideanDistance.d.ts +7 -0
  57. package/dist/math/euclideanDistance.d.ts.map +1 -1
  58. package/dist/math/euclideanDistance.js +13 -4
  59. package/dist/math/euclideanDistance.js.map +1 -1
  60. package/dist/math/hueSector.d.ts +15 -0
  61. package/dist/math/hueSector.d.ts.map +1 -0
  62. package/dist/math/hueSector.js +27 -0
  63. package/dist/math/hueSector.js.map +1 -0
  64. package/dist/resolve.d.ts.map +1 -1
  65. package/dist/resolve.js +11 -34
  66. package/dist/resolve.js.map +1 -1
  67. package/dist/types.d.ts +1 -0
  68. package/dist/types.d.ts.map +1 -1
  69. package/package.json +68 -5
  70. package/dist/math/index.d.ts +0 -2
  71. package/dist/math/index.d.ts.map +0 -1
  72. package/dist/math/index.js +0 -4
  73. package/dist/math/index.js.map +0 -1
package/NOTICE.md ADDED
@@ -0,0 +1,39 @@
1
+ # Notices and Trademarks
2
+
3
+ ## Pantone®
4
+
5
+ **Pantone®** is a registered trademark of **Pantone LLC**. Chromonym is
6
+ **not affiliated with, endorsed by, licensed by, or certified by Pantone
7
+ LLC**.
8
+
9
+ The `pantone` colorspace in this library ships **community-derived sRGB
10
+ approximations** of the Pantone Coated (C) color set, sourced from
11
+ [`color_library`](https://github.com/draganradu/color_library) (MIT © Radu
12
+ Dragan). These values:
13
+
14
+ - Are **not official Pantone measurements** and will not match a licensed
15
+ Pantone reference (physical chips, Pantone Connect, or the Pantone SDK)
16
+ exactly.
17
+ - Are intended for on-screen reference, nearest-name identification, and
18
+ general tooling — **not for print color specification**.
19
+ - Use standard color codes (e.g. `185C`) as **nominative references** to
20
+ publicly identified Pantone colors. No endorsement or claim of accuracy
21
+ is implied.
22
+
23
+ If you need Pantone-certified color values, consult Pantone directly:
24
+ <https://www.pantone.com/>.
25
+
26
+ ## X11 / X.Org
27
+
28
+ The `x11` colorspace is derived from the X.Org `rgb.txt` file, which is in
29
+ the public domain.
30
+
31
+ ## CSS / SVG named colors
32
+
33
+ The `web` colorspace mirrors the CSS Color Module Level 4 named-color
34
+ set, which is a public specification.
35
+
36
+ ## Upstream dependencies
37
+
38
+ See `package.json` for runtime and development dependencies. All are MIT
39
+ or ISC licensed.
package/README.md CHANGED
@@ -1,3 +1,13 @@
1
+ <p align="center">
2
+ <img src=".github/assets/banner.svg" alt="chromonym" width="800" />
3
+ </p>
4
+
5
+ <p align="center">
6
+ <a href="https://simiancraft.github.io/chromonym/">
7
+ <img src="https://img.shields.io/badge/▶%20Live%20demo-scrub%20a%20color%2C%20see%20the%20name-4f46e5?style=for-the-badge" alt="Live demo" />
8
+ </a>
9
+ </p>
10
+
1
11
  # chromonym
2
12
 
3
13
  [![CI](https://github.com/simiancraft/chromonym/actions/workflows/ci.yml/badge.svg)](https://github.com/simiancraft/chromonym/actions/workflows/ci.yml)
@@ -6,7 +16,9 @@
6
16
  [![semantic-release: conventional](https://img.shields.io/badge/semantic--release-conventional-e10079?logo=semantic-release)](https://github.com/semantic-release/semantic-release)
7
17
  [![Checked with Biome](https://img.shields.io/badge/Checked_with-Biome-60a5fa?style=flat&logo=biome)](https://biomejs.dev)
8
18
 
9
- Identify, resolve, and convert colors across CSS, X11, and Pantone colorspaces.
19
+ **Tree-shakeable color naming for TypeScript.** Identify, resolve, and convert colors across CSS, X11, and Pantone — with 5 perceptual distance metrics. Add your own colorspaces and metrics as you need them.
20
+
21
+ Built as a *color-strategy machine*: the identification and resolution mechanism is the same across every colorspace, so plugging in a new set (RAL, HKS, NCS, or a custom brand palette) is one file. For color *manipulation* (mixing, scales, gamut mapping), reach for [`chroma-js`](https://gka.github.io/chroma.js/) or [`color.js`](https://colorjs.io/) — chromonym is the tool for *naming*.
10
22
 
11
23
  ```ts
12
24
  import { identify, resolve, convert } from 'chromonym';
@@ -18,6 +30,10 @@ convert('#ff0000', { format: 'RGB' }) // 'rgb(255, 0, 0)'
18
30
  convert({ r: 255, g: 0, b: 0 }, { format: 'HSL' })// 'hsl(0, 100%, 50%)'
19
31
  ```
20
32
 
33
+ > ### Pantone® trademark notice
34
+ >
35
+ > **Pantone®** is a registered trademark of **Pantone LLC**. Chromonym is **not affiliated with, endorsed by, or certified by Pantone LLC**. The `pantone` colorspace ships **community-derived sRGB approximations** of the Pantone Coated (C) set. Values will **not** match a licensed Pantone reference exactly and are unsuitable for print color specification. See [`NOTICE.md`](./NOTICE.md) for full text.
36
+
21
37
  ## Install
22
38
 
23
39
  ```sh
@@ -31,16 +47,17 @@ Three primary functions. All accept an optional `opts` object; defaults fire whe
31
47
 
32
48
  ### `identify(input, opts?)`
33
49
 
34
- **Color → name.** Finds the nearest-match name in the chosen colorspace using Euclidean distance in RGB.
50
+ **Color → name.** Finds the nearest-match name in the chosen colorspace using the selected perceptual distance metric.
35
51
 
36
52
  ```ts
37
53
  function identify(
38
54
  input: ColorInput,
39
- opts?: { colorspace?: ColorspaceName },
55
+ opts?: { colorspace?: ColorspaceName; metric?: DistanceMetric },
40
56
  ): string | null
41
57
  ```
42
58
 
43
59
  - **Default colorspace**: `'web'`.
60
+ - **Default metric**: picked per colorspace — `'deltaE76'` for web and x11 (well-separated palettes), `'deltaE2000'` for pantone (dense, perceptually-packed). Override freely via `metric`.
44
61
  - Returns the matched name, or `null` if input is unrecognized (`detectFormat` returns `'UNKNOWN'`).
45
62
  - Ties are broken by the first entry encountered in the colorspace data.
46
63
 
@@ -50,6 +67,8 @@ identify([255, 0, 0]) // 'red'
50
67
  identify({ r: 250, g: 20, b: 60 }) // 'crimson' (nearest)
51
68
  identify('#ff0000', { colorspace: 'x11' }) // 'red' (or 'red1', X11 has numbered variants)
52
69
  identify('#ff0000', { colorspace: 'pantone' }) // nearest Pantone C code, e.g. '185C'
70
+ identify('#ff0080', { metric: 'deltaE2000' }) // force perceptual-accurate match
71
+ identify('#ff0000', { metric: 'euclidean-srgb' }) // force fastest (non-perceptual) match
53
72
  ```
54
73
 
55
74
  ### `resolve(name, opts?)`
@@ -120,6 +139,34 @@ import { web, x11, pantone } from 'chromonym';
120
139
  web.crimson // '#dc143c'
121
140
  ```
122
141
 
142
+ ## Distance metrics
143
+
144
+ `identify` picks the nearest-named color by comparing your input to every entry in the chosen colorspace. *How* it measures "nearest" is controlled by `metric`. Five options, roughly ordered from fast-and-approximate to slow-and-correct:
145
+
146
+ | Metric | What it does | When to use |
147
+ |---|---|---|
148
+ | `'euclidean-srgb'` | Raw `sqrt(Δr² + Δg² + Δb²)` in sRGB. Fastest. Not perceptually uniform — a unit of distance doesn't mean a unit of "visual difference." | Tight perf budgets; well-separated palettes where you just need the obvious answer. |
149
+ | `'euclidean-linear'` | Same math, but on linearized (gamma-removed) RGB. Somewhat better in dark regions. Still not perceptual. | Physical-light mixing contexts; incremental upgrade from sRGB Euclidean. |
150
+ | `'deltaE76'` | Euclidean in CIELAB (CIE 1976). Simple perceptual metric. 1 ΔE ≈ "just noticeable difference" for most of the gamut. | **Default for web and x11.** Sweet spot: meaningful perceptual accuracy, low cost. |
151
+ | `'deltaE94'` | ΔE76 + chroma/hue weighting (CIE 1994). Fixes "saturated colors feel too far apart." | When ΔE76 is over-penalizing saturated matches in your use case. |
152
+ | `'deltaE2000'` | Full CIEDE2000 formula with blue/purple rotation correction. Industry standard for print, design tools, Pantone workflows. | **Default for pantone.** Use whenever accuracy matters, especially in the blue region where ΔE76/94 break down. |
153
+ | `'deltaEok'` | Euclidean distance in OKLAB (Björn Ottosson, 2020). OKLAB is perceptually uniform by construction — no weighting formula needed. Strictly more uniform than CIELAB; often a better nearest-match than ΔE2000 in saturated-blue regions, and cheaper to compute. | Modern default if you want perceptual accuracy without the CIEDE2000 rotation-term complexity. |
154
+
155
+ Each metric trades cost for accuracy — the full scan over 907 Pantone entries is well under 1 ms even with ΔE2000, so for interactive UIs there's no practical reason not to use the most accurate metric. Batch-processing millions of colors is where you'd drop down.
156
+
157
+ ```ts
158
+ // Defaults: deltaE76 for web/x11, deltaE2000 for pantone.
159
+ identify('#ff8080') // deltaE76 (web default)
160
+ identify('#ff8080', { colorspace: 'pantone' }) // deltaE2000 (pantone default)
161
+
162
+ // Override per-call:
163
+ identify('#ff8080', { metric: 'euclidean-srgb' }) // fastest
164
+ identify('#ff8080', { metric: 'deltaE2000' }) // most accurate
165
+ identify('#ff8080', { colorspace: 'pantone', metric: 'euclidean-srgb' }) // force fast for Pantone
166
+ ```
167
+
168
+ The low-level `rgbaToPantone` always uses `'deltaE2000'` — appropriate for Pantone matching, where this is what the industry tools use.
169
+
123
170
  ## Formats
124
171
 
125
172
  Format keys are SCREAMING_CAPS — they are used as dispatch keys internally.
@@ -135,6 +182,26 @@ Format keys are SCREAMING_CAPS — they are used as dispatch keys internally.
135
182
 
136
183
  The runtime set `COLOR_FORMATS` is exported for enumeration / membership checks.
137
184
 
185
+ ## Error handling
186
+
187
+ The three dispatchers are asymmetric — chosen deliberately, but worth knowing:
188
+
189
+ | Function | Unrecognized / unknown input | Rationale |
190
+ |---|---|---|
191
+ | `identify(input)` | returns `null` | lookup-flavored; "no match" is a normal outcome |
192
+ | `resolve(name)` | returns `null` | lookup-flavored; name may legitimately not exist |
193
+ | `convert(input)` | **throws** | parser-flavored; malformed color is a caller error |
194
+
195
+ Low-level converters (`hexToRgba`, `rgbToRgba`, `hslToRgba`, `hsvToRgba`, `pantoneToRgba`) all **throw** on malformed input. The `rgbaTo*` direction never throws. The nearest-match returner `rgbaToPantone` always returns *some* Pantone code.
196
+
197
+ If you want a `null`-returning variant of `convert`, wrap it:
198
+
199
+ ```ts
200
+ const tryConvert = (input: ColorInput, opts = {}) => {
201
+ try { return convert(input, opts); } catch { return null; }
202
+ };
203
+ ```
204
+
138
205
  ## Utilities
139
206
 
140
207
  - **`detectFormat(input): DetectedFormat`** — runtime format detection. Returns one of the format keys or `'UNKNOWN'`.
@@ -184,6 +251,14 @@ bun run scripts/generate-pantone.ts # reads color_library (MIT dependency)
184
251
 
185
252
  Each ring is a directory; each leaf is a file. Green is covered, red is gaps.
186
253
 
254
+ ## See also
255
+
256
+ chromonym deliberately limits its scope to color *naming*. For other color-related work, reach for tools that do those things well:
257
+
258
+ - **[color.js](https://colorjs.io/)** — modern, spec-first color library by the CSS Color WG authors. CSS Color 4/5, OKLAB, P3, gamut mapping, interpolation, ΔE.
259
+ - **[chroma.js](https://gka.github.io/chroma.js/)** — color mixing, scales, interpolation, contrast ratios, luminance.
260
+ - **[tinycolor2](https://github.com/bgrins/TinyColor)** — lightweight manipulation (lighten / darken / mix) with CSS-string I/O.
261
+
187
262
  ## License
188
263
 
189
264
  MIT © [the-simian](https://github.com/the-simian)
@@ -0,0 +1,26 @@
1
+ import { type NormalizeFn } from '../indexing';
2
+ import type { Colorspace, ColorspaceName, DistanceMetric } from '../types';
3
+ /**
4
+ * Internal registry of known colorspaces + their normalizers.
5
+ *
6
+ * Tree-shake note: this file imports all three colorspaces, so anything
7
+ * that imports from here pays for all three. It's used by `resolve` and
8
+ * `identify`, both of which need a string-keyed lookup; users who want
9
+ * to tree-shake a single colorspace should import `web`, `x11`, or
10
+ * `pantone` directly from the root barrel.
11
+ */
12
+ export declare const COLORSPACES: Record<ColorspaceName, Colorspace>;
13
+ /** Guards Record indexing against prototype-chain keys like `__proto__`. */
14
+ export declare const COLORSPACE_NAMES: ReadonlySet<ColorspaceName>;
15
+ export declare const NORMALIZERS: Record<ColorspaceName, NormalizeFn>;
16
+ /**
17
+ * Default distance metric per colorspace, picked for the density of each
18
+ * palette. Users can override via `identify(_, { metric })`.
19
+ *
20
+ * web — 148 entries, well-separated; ΔE76 suffices and is cheap.
21
+ * x11 — 658 entries; ΔE76 is the sweet spot (ΔE94/2000 overkill).
22
+ * pantone — 907 entries densely packed in the blue/purple region; ΔE2000
23
+ * is the industry standard and what color-print tools use.
24
+ */
25
+ export declare const DEFAULT_METRICS: Record<ColorspaceName, DistanceMetric>;
26
+ //# sourceMappingURL=registry.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"registry.d.ts","sourceRoot":"","sources":["../../src/colorspaces/registry.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,WAAW,EAAuC,MAAM,aAAa,CAAC;AACpF,OAAO,KAAK,EAAE,UAAU,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,UAAU,CAAC;AAK3E;;;;;;;;GAQG;AAEH,eAAO,MAAM,WAAW,EAAE,MAAM,CAAC,cAAc,EAAE,UAAU,CAAyB,CAAC;AAErF,4EAA4E;AAC5E,eAAO,MAAM,gBAAgB,EAAE,WAAW,CAAC,cAAc,CAAsC,CAAC;AAEhG,eAAO,MAAM,WAAW,EAAE,MAAM,CAAC,cAAc,EAAE,WAAW,CAI3D,CAAC;AAEF;;;;;;;;GAQG;AACH,eAAO,MAAM,eAAe,EAAE,MAAM,CAAC,cAAc,EAAE,cAAc,CAIlE,CAAC"}
@@ -0,0 +1,36 @@
1
+ import { pantoneNormalize, standardNormalize } from '../indexing';
2
+ import { pantone } from './pantone';
3
+ import { web } from './web';
4
+ import { x11 } from './x11';
5
+ /**
6
+ * Internal registry of known colorspaces + their normalizers.
7
+ *
8
+ * Tree-shake note: this file imports all three colorspaces, so anything
9
+ * that imports from here pays for all three. It's used by `resolve` and
10
+ * `identify`, both of which need a string-keyed lookup; users who want
11
+ * to tree-shake a single colorspace should import `web`, `x11`, or
12
+ * `pantone` directly from the root barrel.
13
+ */
14
+ export const COLORSPACES = { web, x11, pantone };
15
+ /** Guards Record indexing against prototype-chain keys like `__proto__`. */
16
+ export const COLORSPACE_NAMES = new Set(['web', 'x11', 'pantone']);
17
+ export const NORMALIZERS = {
18
+ web: standardNormalize,
19
+ x11: standardNormalize,
20
+ pantone: pantoneNormalize,
21
+ };
22
+ /**
23
+ * Default distance metric per colorspace, picked for the density of each
24
+ * palette. Users can override via `identify(_, { metric })`.
25
+ *
26
+ * web — 148 entries, well-separated; ΔE76 suffices and is cheap.
27
+ * x11 — 658 entries; ΔE76 is the sweet spot (ΔE94/2000 overkill).
28
+ * pantone — 907 entries densely packed in the blue/purple region; ΔE2000
29
+ * is the industry standard and what color-print tools use.
30
+ */
31
+ export const DEFAULT_METRICS = {
32
+ web: 'deltaE76',
33
+ x11: 'deltaE76',
34
+ pantone: 'deltaE2000',
35
+ };
36
+ //# sourceMappingURL=registry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"registry.js","sourceRoot":"","sources":["../../src/colorspaces/registry.ts"],"names":[],"mappings":"AAAA,OAAO,EAAoB,gBAAgB,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAEpF,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EAAE,GAAG,EAAE,MAAM,OAAO,CAAC;AAC5B,OAAO,EAAE,GAAG,EAAE,MAAM,OAAO,CAAC;AAE5B;;;;;;;;GAQG;AAEH,MAAM,CAAC,MAAM,WAAW,GAAuC,EAAE,GAAG,EAAE,GAAG,EAAE,OAAO,EAAE,CAAC;AAErF,4EAA4E;AAC5E,MAAM,CAAC,MAAM,gBAAgB,GAAgC,IAAI,GAAG,CAAC,CAAC,KAAK,EAAE,KAAK,EAAE,SAAS,CAAC,CAAC,CAAC;AAEhG,MAAM,CAAC,MAAM,WAAW,GAAwC;IAC9D,GAAG,EAAE,iBAAiB;IACtB,GAAG,EAAE,iBAAiB;IACtB,OAAO,EAAE,gBAAgB;CAC1B,CAAC;AAEF;;;;;;;;GAQG;AACH,MAAM,CAAC,MAAM,eAAe,GAA2C;IACrE,GAAG,EAAE,UAAU;IACf,GAAG,EAAE,UAAU;IACf,OAAO,EAAE,YAAY;CACtB,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"hex.d.ts","sourceRoot":"","sources":["../../src/conversions/hex.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAI/C;;;;GAIG;AACH,wBAAgB,SAAS,CAAC,GAAG,EAAE,QAAQ,GAAG,IAAI,CAsB7C;AAED;;;GAGG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,IAAI,GAAG,QAAQ,CAM9C"}
1
+ {"version":3,"file":"hex.d.ts","sourceRoot":"","sources":["../../src/conversions/hex.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,QAAQ,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAE/C;;;;GAIG;AACH,wBAAgB,SAAS,CAAC,GAAG,EAAE,QAAQ,GAAG,IAAI,CAsB7C;AAMD;;;GAGG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,IAAI,GAAG,QAAQ,CAE9C"}
@@ -1,4 +1,5 @@
1
- const HEX_RE = /^#([0-9a-f]{3}|[0-9a-f]{6}|[0-9a-f]{8})$/i;
1
+ import { HEX_RE } from '../detectFormat';
2
+ import { clamp } from '../math/clamp';
2
3
  /**
3
4
  * Parse a hex color string into the canonical Rgba representation.
4
5
  * Accepts 3-digit (`#rgb`), 6-digit (`#rrggbb`), and 8-digit (`#rrggbbaa`).
@@ -26,14 +27,14 @@ export function hexToRgba(hex) {
26
27
  const a = body.length === 8 ? parseInt(body.slice(6, 8), 16) / 255 : 1;
27
28
  return { r, g, b, a };
28
29
  }
30
+ function channelToHex(n) {
31
+ return clamp(Math.round(n), 0, 255).toString(16).padStart(2, '0');
32
+ }
29
33
  /**
30
34
  * Emit a 6-digit lowercase hex string. Alpha is dropped; out-of-range
31
35
  * channel values are clamped to 0..255; fractional values are rounded.
32
36
  */
33
37
  export function rgbaToHex(rgba) {
34
- const clamp = (n) => Math.max(0, Math.min(255, Math.round(n)))
35
- .toString(16)
36
- .padStart(2, '0');
37
- return `#${clamp(rgba.r)}${clamp(rgba.g)}${clamp(rgba.b)}`;
38
+ return `#${channelToHex(rgba.r)}${channelToHex(rgba.g)}${channelToHex(rgba.b)}`;
38
39
  }
39
40
  //# sourceMappingURL=hex.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"hex.js","sourceRoot":"","sources":["../../src/conversions/hex.ts"],"names":[],"mappings":"AAEA,MAAM,MAAM,GAAG,2CAA2C,CAAC;AAE3D;;;;GAIG;AACH,MAAM,UAAU,SAAS,CAAC,GAAa;IACrC,MAAM,KAAK,GAAG,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAC/B,MAAM,IAAI,GAAG,KAAK,EAAE,CAAC,CAAC,CAAC,CAAC;IACxB,IAAI,CAAC,IAAI;QAAE,MAAM,IAAI,KAAK,CAAC,sBAAsB,GAAG,EAAE,CAAC,CAAC;IAExD,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtB,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACzB,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACzB,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACzB,OAAO;YACL,CAAC,EAAE,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACtB,CAAC,EAAE,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACtB,CAAC,EAAE,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACtB,CAAC,EAAE,CAAC;SACL,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;IACvE,OAAO,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC;AACxB,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,SAAS,CAAC,IAAU;IAClC,MAAM,KAAK,GAAG,CAAC,CAAS,EAAU,EAAE,CAClC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;SACtC,QAAQ,CAAC,EAAE,CAAC;SACZ,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;IACtB,OAAO,IAAI,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,EAAc,CAAC;AACzE,CAAC"}
1
+ {"version":3,"file":"hex.js","sourceRoot":"","sources":["../../src/conversions/hex.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAC;AACzC,OAAO,EAAE,KAAK,EAAE,MAAM,eAAe,CAAC;AAGtC;;;;GAIG;AACH,MAAM,UAAU,SAAS,CAAC,GAAa;IACrC,MAAM,KAAK,GAAG,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAC/B,MAAM,IAAI,GAAG,KAAK,EAAE,CAAC,CAAC,CAAC,CAAC;IACxB,IAAI,CAAC,IAAI;QAAE,MAAM,IAAI,KAAK,CAAC,sBAAsB,GAAG,EAAE,CAAC,CAAC;IAExD,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtB,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACzB,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACzB,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACzB,OAAO;YACL,CAAC,EAAE,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACtB,CAAC,EAAE,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACtB,CAAC,EAAE,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;YACtB,CAAC,EAAE,CAAC;SACL,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IACzC,MAAM,CAAC,GAAG,IAAI,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;IACvE,OAAO,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC;AACxB,CAAC;AAED,SAAS,YAAY,CAAC,CAAS;IAC7B,OAAO,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;AACpE,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,SAAS,CAAC,IAAU;IAClC,OAAO,IAAI,YAAY,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,YAAY,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,YAAY,CAAC,IAAI,CAAC,CAAC,CAAC,EAAc,CAAC;AAC9F,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"hsl.d.ts","sourceRoot":"","sources":["../../src/conversions/hsl.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAK1D;;;GAGG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,CAqD/C;AAED;;;GAGG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,IAAI,GAAG,SAAS,CAyB/C"}
1
+ {"version":3,"file":"hsl.d.ts","sourceRoot":"","sources":["../../src/conversions/hsl.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAK1D;;;GAGG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,CAqC/C;AAED;;;GAGG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,IAAI,GAAG,SAAS,CAyB/C"}
@@ -1,3 +1,5 @@
1
+ import { requireFinite } from '../math/clamp';
2
+ import { hueSectorToPrime } from '../math/hueSector';
1
3
  const HSL_RE = /^hsl\s*\(\s*(-?\d+(?:\.\d+)?)\s*,\s*(-?\d+(?:\.\d+)?)%?\s*,\s*(-?\d+(?:\.\d+)?)%?\s*\)$/i;
2
4
  /**
3
5
  * Parse HSL input (string or object) into canonical Rgba.
@@ -16,45 +18,25 @@ export function hslToRgba(input) {
16
18
  l = Number(match[3]);
17
19
  }
18
20
  else {
19
- h = input.h;
20
- s = input.s;
21
- l = input.l;
21
+ h = requireFinite(input.h, 'h');
22
+ s = requireFinite(input.s, 's');
23
+ l = requireFinite(input.l, 'l');
22
24
  }
23
- const sat = s / 100;
24
- const lig = l / 100;
25
- if (sat === 0) {
26
- const v = Math.round(lig * 255);
27
- return { r: v, g: v, b: v, a: 1 };
28
- }
29
- const c = (1 - Math.abs(2 * lig - 1)) * sat;
30
- const hp = (((h % 360) + 360) % 360) / 60;
31
- const x = c * (1 - Math.abs((hp % 2) - 1));
32
- const m = lig - c / 2;
33
- let r1;
34
- let g1;
35
- let b1;
36
- if (hp < 1) {
37
- [r1, g1, b1] = [c, x, 0];
38
- }
39
- else if (hp < 2) {
40
- [r1, g1, b1] = [x, c, 0];
41
- }
42
- else if (hp < 3) {
43
- [r1, g1, b1] = [0, c, x];
44
- }
45
- else if (hp < 4) {
46
- [r1, g1, b1] = [0, x, c];
47
- }
48
- else if (hp < 5) {
49
- [r1, g1, b1] = [x, 0, c];
50
- }
51
- else {
52
- [r1, g1, b1] = [c, 0, x];
25
+ const saturation = s / 100;
26
+ const lightness = l / 100;
27
+ if (saturation === 0) {
28
+ const gray = Math.round(lightness * 255);
29
+ return { r: gray, g: gray, b: gray, a: 1 };
53
30
  }
31
+ const chroma = (1 - Math.abs(2 * lightness - 1)) * saturation;
32
+ const hueSector = (((h % 360) + 360) % 360) / 60;
33
+ const secondary = chroma * (1 - Math.abs((hueSector % 2) - 1));
34
+ const lightnessOffset = lightness - chroma / 2;
35
+ const [rPrime, gPrime, bPrime] = hueSectorToPrime(hueSector, chroma, secondary);
54
36
  return {
55
- r: Math.round((r1 + m) * 255),
56
- g: Math.round((g1 + m) * 255),
57
- b: Math.round((b1 + m) * 255),
37
+ r: Math.round((rPrime + lightnessOffset) * 255),
38
+ g: Math.round((gPrime + lightnessOffset) * 255),
39
+ b: Math.round((bPrime + lightnessOffset) * 255),
58
40
  a: 1,
59
41
  };
60
42
  }
@@ -63,28 +45,28 @@ export function hslToRgba(input) {
63
45
  * three components are rounded to whole numbers.
64
46
  */
65
47
  export function rgbaToHsl(rgba) {
66
- const rn = rgba.r / 255;
67
- const gn = rgba.g / 255;
68
- const bn = rgba.b / 255;
69
- const max = Math.max(rn, gn, bn);
70
- const min = Math.min(rn, gn, bn);
71
- const l = (max + min) / 2;
48
+ const rNorm = rgba.r / 255;
49
+ const gNorm = rgba.g / 255;
50
+ const bNorm = rgba.b / 255;
51
+ const max = Math.max(rNorm, gNorm, bNorm);
52
+ const min = Math.min(rNorm, gNorm, bNorm);
53
+ const lightness = (max + min) / 2;
72
54
  if (max === min) {
73
- return `hsl(0, 0%, ${Math.round(l * 100)}%)`;
55
+ return `hsl(0, 0%, ${Math.round(lightness * 100)}%)`;
74
56
  }
75
57
  const delta = max - min;
76
- const s = l > 0.5 ? delta / (2 - max - min) : delta / (max + min);
77
- let h;
78
- if (max === rn) {
79
- h = (gn - bn) / delta + (gn < bn ? 6 : 0);
58
+ const saturation = lightness > 0.5 ? delta / (2 - max - min) : delta / (max + min);
59
+ let hue;
60
+ if (max === rNorm) {
61
+ hue = (gNorm - bNorm) / delta + (gNorm < bNorm ? 6 : 0);
80
62
  }
81
- else if (max === gn) {
82
- h = (bn - rn) / delta + 2;
63
+ else if (max === gNorm) {
64
+ hue = (bNorm - rNorm) / delta + 2;
83
65
  }
84
66
  else {
85
- h = (rn - gn) / delta + 4;
67
+ hue = (rNorm - gNorm) / delta + 4;
86
68
  }
87
- h *= 60;
88
- return `hsl(${Math.round(h)}, ${Math.round(s * 100)}%, ${Math.round(l * 100)}%)`;
69
+ hue *= 60;
70
+ return `hsl(${Math.round(hue)}, ${Math.round(saturation * 100)}%, ${Math.round(lightness * 100)}%)`;
89
71
  }
90
72
  //# sourceMappingURL=hsl.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"hsl.js","sourceRoot":"","sources":["../../src/conversions/hsl.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"hsl.js","sourceRoot":"","sources":["../../src/conversions/hsl.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"hsv.d.ts","sourceRoot":"","sources":["../../src/conversions/hsv.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAK1D;;;GAGG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,CA+C/C;AAED;;;GAGG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,IAAI,GAAG,SAAS,CAuB/C"}
1
+ {"version":3,"file":"hsv.d.ts","sourceRoot":"","sources":["../../src/conversions/hsv.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAK1D;;;GAGG;AACH,wBAAgB,SAAS,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,CA+B/C;AAED;;;GAGG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,IAAI,GAAG,SAAS,CAuB/C"}
@@ -1,3 +1,5 @@
1
+ import { requireFinite } from '../math/clamp';
2
+ import { hueSectorToPrime } from '../math/hueSector';
1
3
  const HSV_RE = /^hsv\s*\(\s*(-?\d+(?:\.\d+)?)\s*,\s*(-?\d+(?:\.\d+)?)%?\s*,\s*(-?\d+(?:\.\d+)?)%?\s*\)$/i;
2
4
  /**
3
5
  * Parse HSV input (string or object) into canonical Rgba.
@@ -16,41 +18,21 @@ export function hsvToRgba(input) {
16
18
  v = Number(match[3]);
17
19
  }
18
20
  else {
19
- h = input.h;
20
- s = input.s;
21
- v = input.v;
22
- }
23
- const sat = s / 100;
24
- const val = v / 100;
25
- const c = val * sat;
26
- const hp = (((h % 360) + 360) % 360) / 60;
27
- const x = c * (1 - Math.abs((hp % 2) - 1));
28
- const m = val - c;
29
- let r1;
30
- let g1;
31
- let b1;
32
- if (hp < 1) {
33
- [r1, g1, b1] = [c, x, 0];
34
- }
35
- else if (hp < 2) {
36
- [r1, g1, b1] = [x, c, 0];
37
- }
38
- else if (hp < 3) {
39
- [r1, g1, b1] = [0, c, x];
40
- }
41
- else if (hp < 4) {
42
- [r1, g1, b1] = [0, x, c];
43
- }
44
- else if (hp < 5) {
45
- [r1, g1, b1] = [x, 0, c];
46
- }
47
- else {
48
- [r1, g1, b1] = [c, 0, x];
21
+ h = requireFinite(input.h, 'h');
22
+ s = requireFinite(input.s, 's');
23
+ v = requireFinite(input.v, 'v');
49
24
  }
25
+ const saturation = s / 100;
26
+ const value = v / 100;
27
+ const chroma = value * saturation;
28
+ const hueSector = (((h % 360) + 360) % 360) / 60;
29
+ const secondary = chroma * (1 - Math.abs((hueSector % 2) - 1));
30
+ const valueOffset = value - chroma;
31
+ const [rPrime, gPrime, bPrime] = hueSectorToPrime(hueSector, chroma, secondary);
50
32
  return {
51
- r: Math.round((r1 + m) * 255),
52
- g: Math.round((g1 + m) * 255),
53
- b: Math.round((b1 + m) * 255),
33
+ r: Math.round((rPrime + valueOffset) * 255),
34
+ g: Math.round((gPrime + valueOffset) * 255),
35
+ b: Math.round((bPrime + valueOffset) * 255),
54
36
  a: 1,
55
37
  };
56
38
  }
@@ -59,27 +41,27 @@ export function hsvToRgba(input) {
59
41
  * three components are rounded to whole numbers.
60
42
  */
61
43
  export function rgbaToHsv(rgba) {
62
- const rn = rgba.r / 255;
63
- const gn = rgba.g / 255;
64
- const bn = rgba.b / 255;
65
- const max = Math.max(rn, gn, bn);
66
- const min = Math.min(rn, gn, bn);
44
+ const rNorm = rgba.r / 255;
45
+ const gNorm = rgba.g / 255;
46
+ const bNorm = rgba.b / 255;
47
+ const max = Math.max(rNorm, gNorm, bNorm);
48
+ const min = Math.min(rNorm, gNorm, bNorm);
67
49
  const delta = max - min;
68
- const v = max;
69
- const s = max === 0 ? 0 : delta / max;
70
- let h = 0;
50
+ const value = max;
51
+ const saturation = max === 0 ? 0 : delta / max;
52
+ let hue = 0;
71
53
  if (delta !== 0) {
72
- if (max === rn) {
73
- h = (gn - bn) / delta + (gn < bn ? 6 : 0);
54
+ if (max === rNorm) {
55
+ hue = (gNorm - bNorm) / delta + (gNorm < bNorm ? 6 : 0);
74
56
  }
75
- else if (max === gn) {
76
- h = (bn - rn) / delta + 2;
57
+ else if (max === gNorm) {
58
+ hue = (bNorm - rNorm) / delta + 2;
77
59
  }
78
60
  else {
79
- h = (rn - gn) / delta + 4;
61
+ hue = (rNorm - gNorm) / delta + 4;
80
62
  }
81
- h *= 60;
63
+ hue *= 60;
82
64
  }
83
- return `hsv(${Math.round(h)}, ${Math.round(s * 100)}%, ${Math.round(v * 100)}%)`;
65
+ return `hsv(${Math.round(hue)}, ${Math.round(saturation * 100)}%, ${Math.round(value * 100)}%)`;
84
66
  }
85
67
  //# sourceMappingURL=hsv.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"hsv.js","sourceRoot":"","sources":["../../src/conversions/hsv.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"hsv.js","sourceRoot":"","sources":["../../src/conversions/hsv.ts"],"names":[],"mappings":"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"}
@@ -7,8 +7,11 @@ import type { PantoneCode, Rgba } from '../types';
7
7
  */
8
8
  export declare function pantoneToRgba(code: PantoneCode): Rgba;
9
9
  /**
10
- * Find the nearest Pantone code (Coated) to the given Rgba by
11
- * Euclidean distance in RGB. Alpha is ignored. Always returns a code.
10
+ * Find the nearest Pantone Coated code to the given Rgba. Uses ΔE*00
11
+ * (CIEDE2000) — the industry-standard perceptual metric — by default, since
12
+ * Pantone values cluster densely in the saturated blue/purple region where
13
+ * sRGB Euclidean distance gives visually wrong answers.
14
+ * Alpha is ignored. Always returns a code.
12
15
  */
13
16
  export declare function rgbaToPantone(rgba: Rgba): PantoneCode;
14
17
  //# sourceMappingURL=pantone.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"pantone.d.ts","sourceRoot":"","sources":["../../src/conversions/pantone.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAY,WAAW,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAoC5D;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,WAAW,GAAG,IAAI,CAKrD;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,IAAI,GAAG,WAAW,CAarD"}
1
+ {"version":3,"file":"pantone.d.ts","sourceRoot":"","sources":["../../src/conversions/pantone.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAY,WAAW,EAAE,IAAI,EAAE,MAAM,UAAU,CAAC;AAG5D;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,WAAW,GAAG,IAAI,CAKrD;AAED;;;;;;GAMG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,IAAI,GAAG,WAAW,CAErD"}