The problem
Need to convert colors between different formats
The solution
const colorConverter = {
// HEX to RGB
hexToRgb(hex) {
hex = hex.replace(/^#/, '');
if (hex.length === 3) {
hex = hex.split('').map(c => c + c).join('');
}
const num = parseInt(hex, 16);
return {
r: (num >> 16) & 255,
g: (num >> 8) & 255,
b: num & 255
};
},
// RGB to HEX
rgbToHex(r, g, b) {
return '#' + ((1 << 24) + (r << 16) + (g << 8) + b)
.toString(16)
.slice(1)
.toUpperCase();
},
// RGB to HSL
rgbToHsl(r, g, b) {
r /= 255;
g /= 255;
b /= 255;
const max = Math.max(r, g, b);
const min = Math.min(r, g, b);
let h, s, l = (max + min) / 2;
if (max === min) {
h = s = 0; // achromatic
} else {
const d = max - min;
s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
switch (max) {
case r: h = (g - b) / d + (g < b ? 6 : 0); break;
case g: h = (b - r) / d + 2; break;
case b: h = (r - g) / d + 4; break;
}
h /= 6;
}
return {
h: Math.round(h * 360),
s: Math.round(s * 100),
l: Math.round(l * 100)
};
},
// HSL to RGB
hslToRgb(h, s, l) {
h /= 360;
s /= 100;
l /= 100;
let r, g, b;
if (s === 0) {
r = g = b = l; // achromatic
} else {
const hue2rgb = (p, q, t) => {
if (t < 0) t += 1;
if (t > 1) t -= 1;
if (t < 1/6) return p + (q - p) * 6 * t;
if (t < 1/2) return q;
if (t < 2/3) return p + (q - p) * (2/3 - t) * 6;
return p;
};
const q = l < 0.5 ? l * (1 + s) : l + s - l * s;
const p = 2 * l - q;
r = hue2rgb(p, q, h + 1/3);
g = hue2rgb(p, q, h);
b = hue2rgb(p, q, h - 1/3);
}
return {
r: Math.round(r * 255),
g: Math.round(g * 255),
b: Math.round(b * 255)
};
},
// Generate random color
randomHex() {
return '#' + Math.floor(Math.random() * 16777215).toString(16).padStart(6, '0');
},
// Darken/Lighten color
adjustLightness(hex, percent) {
const rgb = this.hexToRgb(hex);
const hsl = this.rgbToHsl(rgb.r, rgb.g, rgb.b);
hsl.l = Math.max(0, Math.min(100, hsl.l + percent));
const newRgb = this.hslToRgb(hsl.h, hsl.s, hsl.l);
return this.rgbToHex(newRgb.r, newRgb.g, newRgb.b);
}
};Put it to work
// HEX to RGB
const rgb = colorConverter.hexToRgb('#FF5733');
console.log(rgb); // { r: 255, g: 87, b: 51 }
// RGB to HEX
const hex = colorConverter.rgbToHex(255, 87, 51);
console.log(hex); // "#FF5733"
// RGB to HSL
const hsl = colorConverter.rgbToHsl(255, 87, 51);
console.log(hsl); // { h: 11, s: 100, l: 60 }
// HSL to RGB
const rgbFromHsl = colorConverter.hslToRgb(11, 100, 60);
console.log(rgbFromHsl); // { r: 255, g: 87, b: 51 }
// Adjust color lightness
const darker = colorConverter.adjustLightness('#FF5733', -20);
console.log(darker); // "#CC4629"
const lighter = colorConverter.adjustLightness('#FF5733', 20);
console.log(lighter); // "#FF8566"
// Generate random color
console.log(colorConverter.randomHex()); // "#A1B2C3"