Giant blob of minor changes
[dotfiles/.git] / .config / coc / extensions / node_modules / coc-prettier / node_modules / inquirer / node_modules / color-convert / conversions.js
1 /* MIT license */
2 /* eslint-disable no-mixed-operators */
3 const cssKeywords = require('color-name');
4
5 // NOTE: conversions should only return primitive values (i.e. arrays, or
6 //       values that give correct `typeof` results).
7 //       do not use box values types (i.e. Number(), String(), etc.)
8
9 const reverseKeywords = {};
10 for (const key of Object.keys(cssKeywords)) {
11         reverseKeywords[cssKeywords[key]] = key;
12 }
13
14 const convert = {
15         rgb: {channels: 3, labels: 'rgb'},
16         hsl: {channels: 3, labels: 'hsl'},
17         hsv: {channels: 3, labels: 'hsv'},
18         hwb: {channels: 3, labels: 'hwb'},
19         cmyk: {channels: 4, labels: 'cmyk'},
20         xyz: {channels: 3, labels: 'xyz'},
21         lab: {channels: 3, labels: 'lab'},
22         lch: {channels: 3, labels: 'lch'},
23         hex: {channels: 1, labels: ['hex']},
24         keyword: {channels: 1, labels: ['keyword']},
25         ansi16: {channels: 1, labels: ['ansi16']},
26         ansi256: {channels: 1, labels: ['ansi256']},
27         hcg: {channels: 3, labels: ['h', 'c', 'g']},
28         apple: {channels: 3, labels: ['r16', 'g16', 'b16']},
29         gray: {channels: 1, labels: ['gray']}
30 };
31
32 module.exports = convert;
33
34 // Hide .channels and .labels properties
35 for (const model of Object.keys(convert)) {
36         if (!('channels' in convert[model])) {
37                 throw new Error('missing channels property: ' + model);
38         }
39
40         if (!('labels' in convert[model])) {
41                 throw new Error('missing channel labels property: ' + model);
42         }
43
44         if (convert[model].labels.length !== convert[model].channels) {
45                 throw new Error('channel and label counts mismatch: ' + model);
46         }
47
48         const {channels, labels} = convert[model];
49         delete convert[model].channels;
50         delete convert[model].labels;
51         Object.defineProperty(convert[model], 'channels', {value: channels});
52         Object.defineProperty(convert[model], 'labels', {value: labels});
53 }
54
55 convert.rgb.hsl = function (rgb) {
56         const r = rgb[0] / 255;
57         const g = rgb[1] / 255;
58         const b = rgb[2] / 255;
59         const min = Math.min(r, g, b);
60         const max = Math.max(r, g, b);
61         const delta = max - min;
62         let h;
63         let s;
64
65         if (max === min) {
66                 h = 0;
67         } else if (r === max) {
68                 h = (g - b) / delta;
69         } else if (g === max) {
70                 h = 2 + (b - r) / delta;
71         } else if (b === max) {
72                 h = 4 + (r - g) / delta;
73         }
74
75         h = Math.min(h * 60, 360);
76
77         if (h < 0) {
78                 h += 360;
79         }
80
81         const l = (min + max) / 2;
82
83         if (max === min) {
84                 s = 0;
85         } else if (l <= 0.5) {
86                 s = delta / (max + min);
87         } else {
88                 s = delta / (2 - max - min);
89         }
90
91         return [h, s * 100, l * 100];
92 };
93
94 convert.rgb.hsv = function (rgb) {
95         let rdif;
96         let gdif;
97         let bdif;
98         let h;
99         let s;
100
101         const r = rgb[0] / 255;
102         const g = rgb[1] / 255;
103         const b = rgb[2] / 255;
104         const v = Math.max(r, g, b);
105         const diff = v - Math.min(r, g, b);
106         const diffc = function (c) {
107                 return (v - c) / 6 / diff + 1 / 2;
108         };
109
110         if (diff === 0) {
111                 h = 0;
112                 s = 0;
113         } else {
114                 s = diff / v;
115                 rdif = diffc(r);
116                 gdif = diffc(g);
117                 bdif = diffc(b);
118
119                 if (r === v) {
120                         h = bdif - gdif;
121                 } else if (g === v) {
122                         h = (1 / 3) + rdif - bdif;
123                 } else if (b === v) {
124                         h = (2 / 3) + gdif - rdif;
125                 }
126
127                 if (h < 0) {
128                         h += 1;
129                 } else if (h > 1) {
130                         h -= 1;
131                 }
132         }
133
134         return [
135                 h * 360,
136                 s * 100,
137                 v * 100
138         ];
139 };
140
141 convert.rgb.hwb = function (rgb) {
142         const r = rgb[0];
143         const g = rgb[1];
144         let b = rgb[2];
145         const h = convert.rgb.hsl(rgb)[0];
146         const w = 1 / 255 * Math.min(r, Math.min(g, b));
147
148         b = 1 - 1 / 255 * Math.max(r, Math.max(g, b));
149
150         return [h, w * 100, b * 100];
151 };
152
153 convert.rgb.cmyk = function (rgb) {
154         const r = rgb[0] / 255;
155         const g = rgb[1] / 255;
156         const b = rgb[2] / 255;
157
158         const k = Math.min(1 - r, 1 - g, 1 - b);
159         const c = (1 - r - k) / (1 - k) || 0;
160         const m = (1 - g - k) / (1 - k) || 0;
161         const y = (1 - b - k) / (1 - k) || 0;
162
163         return [c * 100, m * 100, y * 100, k * 100];
164 };
165
166 function comparativeDistance(x, y) {
167         /*
168                 See https://en.m.wikipedia.org/wiki/Euclidean_distance#Squared_Euclidean_distance
169         */
170         return (
171                 ((x[0] - y[0]) ** 2) +
172                 ((x[1] - y[1]) ** 2) +
173                 ((x[2] - y[2]) ** 2)
174         );
175 }
176
177 convert.rgb.keyword = function (rgb) {
178         const reversed = reverseKeywords[rgb];
179         if (reversed) {
180                 return reversed;
181         }
182
183         let currentClosestDistance = Infinity;
184         let currentClosestKeyword;
185
186         for (const keyword of Object.keys(cssKeywords)) {
187                 const value = cssKeywords[keyword];
188
189                 // Compute comparative distance
190                 const distance = comparativeDistance(rgb, value);
191
192                 // Check if its less, if so set as closest
193                 if (distance < currentClosestDistance) {
194                         currentClosestDistance = distance;
195                         currentClosestKeyword = keyword;
196                 }
197         }
198
199         return currentClosestKeyword;
200 };
201
202 convert.keyword.rgb = function (keyword) {
203         return cssKeywords[keyword];
204 };
205
206 convert.rgb.xyz = function (rgb) {
207         let r = rgb[0] / 255;
208         let g = rgb[1] / 255;
209         let b = rgb[2] / 255;
210
211         // Assume sRGB
212         r = r > 0.04045 ? (((r + 0.055) / 1.055) ** 2.4) : (r / 12.92);
213         g = g > 0.04045 ? (((g + 0.055) / 1.055) ** 2.4) : (g / 12.92);
214         b = b > 0.04045 ? (((b + 0.055) / 1.055) ** 2.4) : (b / 12.92);
215
216         const x = (r * 0.4124) + (g * 0.3576) + (b * 0.1805);
217         const y = (r * 0.2126) + (g * 0.7152) + (b * 0.0722);
218         const z = (r * 0.0193) + (g * 0.1192) + (b * 0.9505);
219
220         return [x * 100, y * 100, z * 100];
221 };
222
223 convert.rgb.lab = function (rgb) {
224         const xyz = convert.rgb.xyz(rgb);
225         let x = xyz[0];
226         let y = xyz[1];
227         let z = xyz[2];
228
229         x /= 95.047;
230         y /= 100;
231         z /= 108.883;
232
233         x = x > 0.008856 ? (x ** (1 / 3)) : (7.787 * x) + (16 / 116);
234         y = y > 0.008856 ? (y ** (1 / 3)) : (7.787 * y) + (16 / 116);
235         z = z > 0.008856 ? (z ** (1 / 3)) : (7.787 * z) + (16 / 116);
236
237         const l = (116 * y) - 16;
238         const a = 500 * (x - y);
239         const b = 200 * (y - z);
240
241         return [l, a, b];
242 };
243
244 convert.hsl.rgb = function (hsl) {
245         const h = hsl[0] / 360;
246         const s = hsl[1] / 100;
247         const l = hsl[2] / 100;
248         let t2;
249         let t3;
250         let val;
251
252         if (s === 0) {
253                 val = l * 255;
254                 return [val, val, val];
255         }
256
257         if (l < 0.5) {
258                 t2 = l * (1 + s);
259         } else {
260                 t2 = l + s - l * s;
261         }
262
263         const t1 = 2 * l - t2;
264
265         const rgb = [0, 0, 0];
266         for (let i = 0; i < 3; i++) {
267                 t3 = h + 1 / 3 * -(i - 1);
268                 if (t3 < 0) {
269                         t3++;
270                 }
271
272                 if (t3 > 1) {
273                         t3--;
274                 }
275
276                 if (6 * t3 < 1) {
277                         val = t1 + (t2 - t1) * 6 * t3;
278                 } else if (2 * t3 < 1) {
279                         val = t2;
280                 } else if (3 * t3 < 2) {
281                         val = t1 + (t2 - t1) * (2 / 3 - t3) * 6;
282                 } else {
283                         val = t1;
284                 }
285
286                 rgb[i] = val * 255;
287         }
288
289         return rgb;
290 };
291
292 convert.hsl.hsv = function (hsl) {
293         const h = hsl[0];
294         let s = hsl[1] / 100;
295         let l = hsl[2] / 100;
296         let smin = s;
297         const lmin = Math.max(l, 0.01);
298
299         l *= 2;
300         s *= (l <= 1) ? l : 2 - l;
301         smin *= lmin <= 1 ? lmin : 2 - lmin;
302         const v = (l + s) / 2;
303         const sv = l === 0 ? (2 * smin) / (lmin + smin) : (2 * s) / (l + s);
304
305         return [h, sv * 100, v * 100];
306 };
307
308 convert.hsv.rgb = function (hsv) {
309         const h = hsv[0] / 60;
310         const s = hsv[1] / 100;
311         let v = hsv[2] / 100;
312         const hi = Math.floor(h) % 6;
313
314         const f = h - Math.floor(h);
315         const p = 255 * v * (1 - s);
316         const q = 255 * v * (1 - (s * f));
317         const t = 255 * v * (1 - (s * (1 - f)));
318         v *= 255;
319
320         switch (hi) {
321                 case 0:
322                         return [v, t, p];
323                 case 1:
324                         return [q, v, p];
325                 case 2:
326                         return [p, v, t];
327                 case 3:
328                         return [p, q, v];
329                 case 4:
330                         return [t, p, v];
331                 case 5:
332                         return [v, p, q];
333         }
334 };
335
336 convert.hsv.hsl = function (hsv) {
337         const h = hsv[0];
338         const s = hsv[1] / 100;
339         const v = hsv[2] / 100;
340         const vmin = Math.max(v, 0.01);
341         let sl;
342         let l;
343
344         l = (2 - s) * v;
345         const lmin = (2 - s) * vmin;
346         sl = s * vmin;
347         sl /= (lmin <= 1) ? lmin : 2 - lmin;
348         sl = sl || 0;
349         l /= 2;
350
351         return [h, sl * 100, l * 100];
352 };
353
354 // http://dev.w3.org/csswg/css-color/#hwb-to-rgb
355 convert.hwb.rgb = function (hwb) {
356         const h = hwb[0] / 360;
357         let wh = hwb[1] / 100;
358         let bl = hwb[2] / 100;
359         const ratio = wh + bl;
360         let f;
361
362         // Wh + bl cant be > 1
363         if (ratio > 1) {
364                 wh /= ratio;
365                 bl /= ratio;
366         }
367
368         const i = Math.floor(6 * h);
369         const v = 1 - bl;
370         f = 6 * h - i;
371
372         if ((i & 0x01) !== 0) {
373                 f = 1 - f;
374         }
375
376         const n = wh + f * (v - wh); // Linear interpolation
377
378         let r;
379         let g;
380         let b;
381         /* eslint-disable max-statements-per-line,no-multi-spaces */
382         switch (i) {
383                 default:
384                 case 6:
385                 case 0: r = v;  g = n;  b = wh; break;
386                 case 1: r = n;  g = v;  b = wh; break;
387                 case 2: r = wh; g = v;  b = n; break;
388                 case 3: r = wh; g = n;  b = v; break;
389                 case 4: r = n;  g = wh; b = v; break;
390                 case 5: r = v;  g = wh; b = n; break;
391         }
392         /* eslint-enable max-statements-per-line,no-multi-spaces */
393
394         return [r * 255, g * 255, b * 255];
395 };
396
397 convert.cmyk.rgb = function (cmyk) {
398         const c = cmyk[0] / 100;
399         const m = cmyk[1] / 100;
400         const y = cmyk[2] / 100;
401         const k = cmyk[3] / 100;
402
403         const r = 1 - Math.min(1, c * (1 - k) + k);
404         const g = 1 - Math.min(1, m * (1 - k) + k);
405         const b = 1 - Math.min(1, y * (1 - k) + k);
406
407         return [r * 255, g * 255, b * 255];
408 };
409
410 convert.xyz.rgb = function (xyz) {
411         const x = xyz[0] / 100;
412         const y = xyz[1] / 100;
413         const z = xyz[2] / 100;
414         let r;
415         let g;
416         let b;
417
418         r = (x * 3.2406) + (y * -1.5372) + (z * -0.4986);
419         g = (x * -0.9689) + (y * 1.8758) + (z * 0.0415);
420         b = (x * 0.0557) + (y * -0.2040) + (z * 1.0570);
421
422         // Assume sRGB
423         r = r > 0.0031308
424                 ? ((1.055 * (r ** (1.0 / 2.4))) - 0.055)
425                 : r * 12.92;
426
427         g = g > 0.0031308
428                 ? ((1.055 * (g ** (1.0 / 2.4))) - 0.055)
429                 : g * 12.92;
430
431         b = b > 0.0031308
432                 ? ((1.055 * (b ** (1.0 / 2.4))) - 0.055)
433                 : b * 12.92;
434
435         r = Math.min(Math.max(0, r), 1);
436         g = Math.min(Math.max(0, g), 1);
437         b = Math.min(Math.max(0, b), 1);
438
439         return [r * 255, g * 255, b * 255];
440 };
441
442 convert.xyz.lab = function (xyz) {
443         let x = xyz[0];
444         let y = xyz[1];
445         let z = xyz[2];
446
447         x /= 95.047;
448         y /= 100;
449         z /= 108.883;
450
451         x = x > 0.008856 ? (x ** (1 / 3)) : (7.787 * x) + (16 / 116);
452         y = y > 0.008856 ? (y ** (1 / 3)) : (7.787 * y) + (16 / 116);
453         z = z > 0.008856 ? (z ** (1 / 3)) : (7.787 * z) + (16 / 116);
454
455         const l = (116 * y) - 16;
456         const a = 500 * (x - y);
457         const b = 200 * (y - z);
458
459         return [l, a, b];
460 };
461
462 convert.lab.xyz = function (lab) {
463         const l = lab[0];
464         const a = lab[1];
465         const b = lab[2];
466         let x;
467         let y;
468         let z;
469
470         y = (l + 16) / 116;
471         x = a / 500 + y;
472         z = y - b / 200;
473
474         const y2 = y ** 3;
475         const x2 = x ** 3;
476         const z2 = z ** 3;
477         y = y2 > 0.008856 ? y2 : (y - 16 / 116) / 7.787;
478         x = x2 > 0.008856 ? x2 : (x - 16 / 116) / 7.787;
479         z = z2 > 0.008856 ? z2 : (z - 16 / 116) / 7.787;
480
481         x *= 95.047;
482         y *= 100;
483         z *= 108.883;
484
485         return [x, y, z];
486 };
487
488 convert.lab.lch = function (lab) {
489         const l = lab[0];
490         const a = lab[1];
491         const b = lab[2];
492         let h;
493
494         const hr = Math.atan2(b, a);
495         h = hr * 360 / 2 / Math.PI;
496
497         if (h < 0) {
498                 h += 360;
499         }
500
501         const c = Math.sqrt(a * a + b * b);
502
503         return [l, c, h];
504 };
505
506 convert.lch.lab = function (lch) {
507         const l = lch[0];
508         const c = lch[1];
509         const h = lch[2];
510
511         const hr = h / 360 * 2 * Math.PI;
512         const a = c * Math.cos(hr);
513         const b = c * Math.sin(hr);
514
515         return [l, a, b];
516 };
517
518 convert.rgb.ansi16 = function (args, saturation = null) {
519         const [r, g, b] = args;
520         let value = saturation === null ? convert.rgb.hsv(args)[2] : saturation; // Hsv -> ansi16 optimization
521
522         value = Math.round(value / 50);
523
524         if (value === 0) {
525                 return 30;
526         }
527
528         let ansi = 30
529                 + ((Math.round(b / 255) << 2)
530                 | (Math.round(g / 255) << 1)
531                 | Math.round(r / 255));
532
533         if (value === 2) {
534                 ansi += 60;
535         }
536
537         return ansi;
538 };
539
540 convert.hsv.ansi16 = function (args) {
541         // Optimization here; we already know the value and don't need to get
542         // it converted for us.
543         return convert.rgb.ansi16(convert.hsv.rgb(args), args[2]);
544 };
545
546 convert.rgb.ansi256 = function (args) {
547         const r = args[0];
548         const g = args[1];
549         const b = args[2];
550
551         // We use the extended greyscale palette here, with the exception of
552         // black and white. normal palette only has 4 greyscale shades.
553         if (r === g && g === b) {
554                 if (r < 8) {
555                         return 16;
556                 }
557
558                 if (r > 248) {
559                         return 231;
560                 }
561
562                 return Math.round(((r - 8) / 247) * 24) + 232;
563         }
564
565         const ansi = 16
566                 + (36 * Math.round(r / 255 * 5))
567                 + (6 * Math.round(g / 255 * 5))
568                 + Math.round(b / 255 * 5);
569
570         return ansi;
571 };
572
573 convert.ansi16.rgb = function (args) {
574         let color = args % 10;
575
576         // Handle greyscale
577         if (color === 0 || color === 7) {
578                 if (args > 50) {
579                         color += 3.5;
580                 }
581
582                 color = color / 10.5 * 255;
583
584                 return [color, color, color];
585         }
586
587         const mult = (~~(args > 50) + 1) * 0.5;
588         const r = ((color & 1) * mult) * 255;
589         const g = (((color >> 1) & 1) * mult) * 255;
590         const b = (((color >> 2) & 1) * mult) * 255;
591
592         return [r, g, b];
593 };
594
595 convert.ansi256.rgb = function (args) {
596         // Handle greyscale
597         if (args >= 232) {
598                 const c = (args - 232) * 10 + 8;
599                 return [c, c, c];
600         }
601
602         args -= 16;
603
604         let rem;
605         const r = Math.floor(args / 36) / 5 * 255;
606         const g = Math.floor((rem = args % 36) / 6) / 5 * 255;
607         const b = (rem % 6) / 5 * 255;
608
609         return [r, g, b];
610 };
611
612 convert.rgb.hex = function (args) {
613         const integer = ((Math.round(args[0]) & 0xFF) << 16)
614                 + ((Math.round(args[1]) & 0xFF) << 8)
615                 + (Math.round(args[2]) & 0xFF);
616
617         const string = integer.toString(16).toUpperCase();
618         return '000000'.substring(string.length) + string;
619 };
620
621 convert.hex.rgb = function (args) {
622         const match = args.toString(16).match(/[a-f0-9]{6}|[a-f0-9]{3}/i);
623         if (!match) {
624                 return [0, 0, 0];
625         }
626
627         let colorString = match[0];
628
629         if (match[0].length === 3) {
630                 colorString = colorString.split('').map(char => {
631                         return char + char;
632                 }).join('');
633         }
634
635         const integer = parseInt(colorString, 16);
636         const r = (integer >> 16) & 0xFF;
637         const g = (integer >> 8) & 0xFF;
638         const b = integer & 0xFF;
639
640         return [r, g, b];
641 };
642
643 convert.rgb.hcg = function (rgb) {
644         const r = rgb[0] / 255;
645         const g = rgb[1] / 255;
646         const b = rgb[2] / 255;
647         const max = Math.max(Math.max(r, g), b);
648         const min = Math.min(Math.min(r, g), b);
649         const chroma = (max - min);
650         let grayscale;
651         let hue;
652
653         if (chroma < 1) {
654                 grayscale = min / (1 - chroma);
655         } else {
656                 grayscale = 0;
657         }
658
659         if (chroma <= 0) {
660                 hue = 0;
661         } else
662         if (max === r) {
663                 hue = ((g - b) / chroma) % 6;
664         } else
665         if (max === g) {
666                 hue = 2 + (b - r) / chroma;
667         } else {
668                 hue = 4 + (r - g) / chroma;
669         }
670
671         hue /= 6;
672         hue %= 1;
673
674         return [hue * 360, chroma * 100, grayscale * 100];
675 };
676
677 convert.hsl.hcg = function (hsl) {
678         const s = hsl[1] / 100;
679         const l = hsl[2] / 100;
680
681         const c = l < 0.5 ? (2.0 * s * l) : (2.0 * s * (1.0 - l));
682
683         let f = 0;
684         if (c < 1.0) {
685                 f = (l - 0.5 * c) / (1.0 - c);
686         }
687
688         return [hsl[0], c * 100, f * 100];
689 };
690
691 convert.hsv.hcg = function (hsv) {
692         const s = hsv[1] / 100;
693         const v = hsv[2] / 100;
694
695         const c = s * v;
696         let f = 0;
697
698         if (c < 1.0) {
699                 f = (v - c) / (1 - c);
700         }
701
702         return [hsv[0], c * 100, f * 100];
703 };
704
705 convert.hcg.rgb = function (hcg) {
706         const h = hcg[0] / 360;
707         const c = hcg[1] / 100;
708         const g = hcg[2] / 100;
709
710         if (c === 0.0) {
711                 return [g * 255, g * 255, g * 255];
712         }
713
714         const pure = [0, 0, 0];
715         const hi = (h % 1) * 6;
716         const v = hi % 1;
717         const w = 1 - v;
718         let mg = 0;
719
720         /* eslint-disable max-statements-per-line */
721         switch (Math.floor(hi)) {
722                 case 0:
723                         pure[0] = 1; pure[1] = v; pure[2] = 0; break;
724                 case 1:
725                         pure[0] = w; pure[1] = 1; pure[2] = 0; break;
726                 case 2:
727                         pure[0] = 0; pure[1] = 1; pure[2] = v; break;
728                 case 3:
729                         pure[0] = 0; pure[1] = w; pure[2] = 1; break;
730                 case 4:
731                         pure[0] = v; pure[1] = 0; pure[2] = 1; break;
732                 default:
733                         pure[0] = 1; pure[1] = 0; pure[2] = w;
734         }
735         /* eslint-enable max-statements-per-line */
736
737         mg = (1.0 - c) * g;
738
739         return [
740                 (c * pure[0] + mg) * 255,
741                 (c * pure[1] + mg) * 255,
742                 (c * pure[2] + mg) * 255
743         ];
744 };
745
746 convert.hcg.hsv = function (hcg) {
747         const c = hcg[1] / 100;
748         const g = hcg[2] / 100;
749
750         const v = c + g * (1.0 - c);
751         let f = 0;
752
753         if (v > 0.0) {
754                 f = c / v;
755         }
756
757         return [hcg[0], f * 100, v * 100];
758 };
759
760 convert.hcg.hsl = function (hcg) {
761         const c = hcg[1] / 100;
762         const g = hcg[2] / 100;
763
764         const l = g * (1.0 - c) + 0.5 * c;
765         let s = 0;
766
767         if (l > 0.0 && l < 0.5) {
768                 s = c / (2 * l);
769         } else
770         if (l >= 0.5 && l < 1.0) {
771                 s = c / (2 * (1 - l));
772         }
773
774         return [hcg[0], s * 100, l * 100];
775 };
776
777 convert.hcg.hwb = function (hcg) {
778         const c = hcg[1] / 100;
779         const g = hcg[2] / 100;
780         const v = c + g * (1.0 - c);
781         return [hcg[0], (v - c) * 100, (1 - v) * 100];
782 };
783
784 convert.hwb.hcg = function (hwb) {
785         const w = hwb[1] / 100;
786         const b = hwb[2] / 100;
787         const v = 1 - b;
788         const c = v - w;
789         let g = 0;
790
791         if (c < 1) {
792                 g = (v - c) / (1 - c);
793         }
794
795         return [hwb[0], c * 100, g * 100];
796 };
797
798 convert.apple.rgb = function (apple) {
799         return [(apple[0] / 65535) * 255, (apple[1] / 65535) * 255, (apple[2] / 65535) * 255];
800 };
801
802 convert.rgb.apple = function (rgb) {
803         return [(rgb[0] / 255) * 65535, (rgb[1] / 255) * 65535, (rgb[2] / 255) * 65535];
804 };
805
806 convert.gray.rgb = function (args) {
807         return [args[0] / 100 * 255, args[0] / 100 * 255, args[0] / 100 * 255];
808 };
809
810 convert.gray.hsl = function (args) {
811         return [0, 0, args[0]];
812 };
813
814 convert.gray.hsv = convert.gray.hsl;
815
816 convert.gray.hwb = function (gray) {
817         return [0, 100, gray[0]];
818 };
819
820 convert.gray.cmyk = function (gray) {
821         return [0, 0, 0, gray[0]];
822 };
823
824 convert.gray.lab = function (gray) {
825         return [gray[0], 0, 0];
826 };
827
828 convert.gray.hex = function (gray) {
829         const val = Math.round(gray[0] / 100 * 255) & 0xFF;
830         const integer = (val << 16) + (val << 8) + val;
831
832         const string = integer.toString(16).toUpperCase();
833         return '000000'.substring(string.length) + string;
834 };
835
836 convert.rgb.gray = function (rgb) {
837         const val = (rgb[0] + rgb[1] + rgb[2]) / 3;
838         return [val / 255 * 100];
839 };