Skip to content

Instantly share code, notes, and snippets.

@burdiuz
Last active December 5, 2016 18:56
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save burdiuz/bca61f39fc4819768eb55a7c812f7e52 to your computer and use it in GitHub Desktop.
Save burdiuz/bca61f39fc4819768eb55a7c812f7e52 to your computer and use it in GitHub Desktop.
Set of JavaScript classes were created for color manipulations. With these classes you can change color components independently.

Color

Set of JavaScript classes were created for color manipulations. With these classes you can change color components independently. Original transformation algorithm between HSL <> RGB and HSB <> RGB you can grab here.

Installation

via npm

npm install gist:bca61f39fc4819768eb55a7c812f7e52 --save

via git

git clone https://gist.github.com/burdiuz/bca61f39fc4819768eb55a7c812f7e52 Pixels

API

RGBA

  • new RGBA(color:uint) - Class constructor accepts RGBA color value
  • get/set r:byte - red component of RGBA color value. Accepts values between 0 and 255.
  • get/set g:byte - green component of RGBA color value. Accepts values between 0 and 255.
  • get/set b:byte - blue component of RGBA color value. Accepts values between 0 and 255.
  • get/set a:byte - alpha/opacity component of RGBA color value. Accepts values between 0 and 255.
  • get/set value:uint - get/set RGBA color value.
  • static getRed(color:uint):byte - get red component from RGBA color value.
  • static getGreen(color:uint):byte - get green component from RGBA color value.
  • static getBlue(color:uint):byte - get blue component from RGBA color value.
  • static getAlpha(color:uint):byte - get alpha/opacity component from RGBA color value.
  • static setRed(color:uint, red:byte):uint - set red component value to RGBA color.
  • static setGreen(color:uint, green:byte):uint - set green component value to RGBA color.
  • static setBlue(color:uint, blue:byte):uint - set blue component value to RGBA color.
  • static setAlpha(color:uint, alpha:byte):uint - set alpha/opacity component value to RGBA color.

HSLA

  • new HSLA(color:uint) - Class constructor accepts RGBA color value.
  • get/set h:float - hue component of RGBA color value. Accepts values between 0 and 1.
  • get/set s:float - saturation component of RGBA color value. Accepts values between 0 and 1.
  • get/set l:float - light component of RGBA color value. Accepts values between 0 and 1.
  • get/set a:float - alpha/opacity component of RGBA color value. Accepts values between 0 and 1.
  • get/set value:uint - get/set RGBA color value.
  • static toRGBA(h:float, s:float, l:float, a:float = 1):uint - Combine hue, saturation, light and opacity to transform into RGBA color value.

HSBA/HSVA

  • new HSBA(color:uint) - Class constructor accepts RGBA color value.
  • get/set h:float - hue component of RGBA color value. Accepts values between 0 and 1.
  • get/set s:float - saturation component of HSBA color value. Accepts values between 0 and 1.
  • get/set b:float - brightness component of RGBA color value. Accepts values between 0 and 1.
  • get/set a:float - alpha/opacity component of RGBA color value. Accepts values between 0 and 1.
  • get/set value:uint - get/set RGBA color value.
  • static toRGBA(h:float, s:float, b:float, a:float = 1):uint - Combine hue, saturation, brightness and opacity to transform into RGBA color value.
'use strict';
/**
* Original HSL <> RGB, HSV <> RGB transformation algorithms can be found here:
* https://gist.github.com/mjackson/5311256
*/
const COLOR_PART = 1 / 0xff;
const HUE_PART = 1 / 6;
class /*abstract*/ Color {
get value() {
// abstract
throw new Error('absctract accessor');
}
set value(color) {
// abstract
throw new Error('absctract mutator');
}
}
export class HSLA extends Color {
/*
_h = 0;
_s = 0;
_l = 0;
_a = 0;
_value = 0;
*/
constructor(color) {
super();
if (color !== undefined) {
this.value = color;
}
}
get value() {
if (this._value === undefined) {
this._value = HSLA.toRGBA(this._h, this._s, this._l, this._a);
}
return this._value;
}
set value(color) {
HSLA.applyColor(this, color || 0);
}
get h() {
return this._h;
}
set h(value) {
this._h = value;
this._value = undefined;
}
get s() {
return this._s;
}
set s(value) {
this._s = value;
this._value = undefined;
}
get l() {
return this._l;
}
set l(value) {
this._l = value;
this._value = undefined;
}
get a() {
return this._a;
}
set a(value) {
this._a = value;
this._value = undefined;
}
static applyColor(hsla, color) {
const r = RGBA.getRed(color) * COLOR_PART;
const g = RGBA.getGreen(color) * COLOR_PART;
const b = RGBA.getBlue(color) * COLOR_PART;
const max = Math.max(r, g, b);
const min = Math.min(r, g, b);
const l = (max + min) / 2;
let h = 0, s = 0; // achromatic
if (max !== min) {
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 *= HUE_PART;
}
hsla._h = h;
hsla._s = s;
hsla._l = l;
hsla._a = RGBA.getAlpha(color) * COLOR_PART;
hsla._value = color;
return hsla;
}
static _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;
}
static toRGBA(h, s, l, a = 1) {
let red, green, blue;
if (s === 0) {
red = green = blue = l; // achromatic
} else {
const q = l < 0.5 ? l * (1 + s) : l + s - l * s;
const p = 2 * l - q;
red = HSLA._hue2rgb(p, q, h + 1 / 3);
green = HSLA._hue2rgb(p, q, h);
blue = HSLA._hue2rgb(p, q, h - 1 / 3);
}
return red * 0xff << 24 | green * 0xff << 16 | blue * 0xff << 8 | a * 0xff;
}
}
export class HSBA extends Color {
/*
_h = 0;
_s = 0;
_b = 0;
_a = 0;
_value = 0;
*/
constructor(color) {
super();
if (color !== undefined) {
this.value = color;
}
}
get value() {
if (this._value === undefined) {
this._value = HSBA.toRGBA(this._h, this._s, this._b, this._a);
}
return this._value;
}
set value(color) {
HSBA.applyColor(this, color || 0);
}
get h() {
return this._h;
}
set h(value) {
this._h = value;
this._value = undefined;
}
get s() {
return this._s;
}
set s(value) {
this._s = value;
this._value = undefined;
}
get b() {
return this._b;
}
set b(value) {
this._b = value;
this._value = undefined;
}
get a() {
return this._a;
}
set a(value) {
this._a = value;
this._value = undefined;
}
static applyColor(hsba, color) {
const r = RGBA.getRed(color) * COLOR_PART;
const g = RGBA.getGreen(color) * COLOR_PART;
const b = RGBA.getBlue(color) * COLOR_PART;
const max = Math.max(r, g, b);
const min = Math.min(r, g, b);
const d = max - min;
let h = 0;
if (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 *= HUE_PART;
}
hsba._h = h;
hsba._s = max == 0 ? 0 : d / max;
hsba._b = max;
hsba._a = RGBA.getAlpha(color) * COLOR_PART;
hsba._value = color;
return hsba;
}
static toRGBA(h, s, b, a = 1) {
let red, green, blue;
const i = Math.floor(h * 6);
const f = h * 6 - i;
const p = b * (1 - s);
const q = b * (1 - f * s);
const t = b * (1 - (1 - f) * s);
switch (i % 6) {
case 0:
red = b, green = t, blue = p;
break;
case 1:
red = q, green = b, blue = p;
break;
case 2:
red = p, green = b, blue = t;
break;
case 3:
red = p, green = q, blue = b;
break;
case 4:
red = t, green = p, blue = b;
break;
case 5:
red = b, green = p, blue = q;
break;
}
return red * 0xff << 24 | green * 0xff << 16 | blue * 0xff << 8 | a * 0xff;
}
}
export class RGBA extends Color {
constructor(color) {
super();
if (color !== undefined) {
this.value = color;
}
}
get r() {
return RGBA.getRed(this.value);
}
set r(value) {
this.value = RGBA.setRed(this.value, value);
}
get g() {
return RGBA.getGreen(this.value);
}
set g(value) {
this.value = RGBA.setGreen(this.value, value);
}
get b() {
return RGBA.getBlue(this.value);
}
set b(value) {
this.value = RGBA.setBlue(this.value, value);
}
get a() {
return RGBA.getAlpha(this.value);
}
set a(value) {
this.value = RGBA.setAlpha(this.value, value);
}
static getRed(color) {
return color >>> 24 & 0xff;
}
static getGreen(color) {
return color >>> 16 & 0xff;
}
static getBlue(color) {
return color >>> 8 & 0xff;
}
static getAlpha(color) {
return color & 0xff;
}
static setRed(color, red) {
return color ^ 0xff << 24 | (red & 0xff) << 24;
}
static setGreen(color, green) {
return color ^ 0xff << 16 | (green & 0xff) << 16;
}
static setBlue(color, blue) {
return color ^ 0xff << 8 | (blue & 0xff) << 8;
}
static setAlpha(color, alpha) {
return color ^ 0xff | (alpha & 0xff);
}
}
{
"name": "Color",
"version": "0.0.1",
"main": "Color.js"
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment