Skip to content

Instantly share code, notes, and snippets.

@comficker
Created June 6, 2018 01:16
Show Gist options
  • Save comficker/871d378c535854c1c460f7867a191a5a to your computer and use it in GitHub Desktop.
Save comficker/871d378c535854c1c460f7867a191a5a to your computer and use it in GitHub Desktop.
Bellow are javascript code can convert hex to rgb color. Demo: http://aiconverter.com/color/hex-to-rgb
function HEX2RGB (hex) {
"use strict";
if (hex.charAt(0) === '#') {
hex = hex.substr(1);
}
if ((hex.length < 2) || (hex.length > 6)) {
return false;
}
var values = hex.split(''),
r,
g,
b;
if (hex.length === 2) {
r = parseInt(values[0].toString() + values[1].toString(), 16);
g = r;
b = r;
} else if (hex.length === 3) {
r = parseInt(values[0].toString() + values[0].toString(), 16);
g = parseInt(values[1].toString() + values[1].toString(), 16);
b = parseInt(values[2].toString() + values[2].toString(), 16);
} else if (hex.length === 6) {
r = parseInt(values[0].toString() + values[1].toString(), 16);
g = parseInt(values[2].toString() + values[3].toString(), 16);
b = parseInt(values[4].toString() + values[5].toString(), 16);
} else {
return false;
}
return [r, g, b];
}
@dsamarin
Copy link

dsamarin commented Jun 7, 2018

This function supports input like "#d0" to create grayscale values too. Useful.

Out of curiosity why is toString() being used if hex is already assumed to be a string?

@bathos
Copy link

bathos commented Jun 10, 2018

Some issues/suggestions (unsolicited, so forgive me, but I saw this posted publicly as a solution):

  • 2-char values aren’t typically valid RGB notation (though perhaps there is a domain-specific reason to support this?)
  • 4-char and 8-char notations, however, are normally valid, even if the alpha channel is being ignored
  • toString and @@toPrimitive aren’t respected here; String.prototype methods are called without a prior string cast
  • false is a zany return value for malformed input (undefined is idiomatic; throwing is also an option)
  • only some malformed input is being filtered — it checks length, but not the values themselves. it will return NaN or surprise values for some malformed input. e.g. 'ffwwfw' will give [ 255, NaN, 15 ]
  • in the six-digit case, the reconcatenation of the split string is an odd step — could just slice —
  • or one could do the math directly; working with RGB values is an appropriate context for bitwise math
const RGB_HEX = /^#?(?:([\da-f]{3})[\da-f]?|([\da-f]{6})(?:[\da-f]{2})?)$/i;

const hex2RGB = str => {
  const [ , short, long ] = String(str).match(RGB_HEX) || [];

  if (long) {
    const value = Number.parseInt(long, 16);
    return [ value >> 16, value >> 8 & 0xFF, value & 0xFF ];
  } else if (short) {
    return Array.from(short, s => Number.parseInt(s, 16)).map(n => (n << 4) | n);
  }
};

@meodai
Copy link

meodai commented Aug 18, 2020

@bathos Very elegant solution, I love it! I took the liberty to use it for my color-name api: meodai/color-names@bdad76b can I add you as a contributor?

@bathos
Copy link

bathos commented Aug 19, 2020

@meodai Thanks! I wasn’t aware of the context for this — the color names project looks cool. If I recall correctly, I encountered this gist because it was linked to from another site. Re: adding as a contributor — feel free, but not obligated.

@meodai
Copy link

meodai commented Aug 19, 2020

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment