How to compare colors in JavaScript?

Comparing colors as part of the business logic should be avoided at all cost.

Instead, keep the logic in JavaScript and act according to a state kept somewhere. Then, if you want to send a visual feedback to the user through a change of color, add a class to the element. That way, JavaScript only knows about class names and the styling is always isolated in the CSS as it should.

$(".list").on("click", "li", function(){
    $(this).toggleClass('active');
});
.list {
  width: 100%;
  padding: 0;
}
.list li {
  padding: 5px 10px;
  list-style: none;
  cursor: pointer;
}
.list li:hover {
  background-color: rgba(0, 0, 0, 0.05);
}
.list li.active {
  background-color: #eeeecc;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<ul class="list">
  <li>test 1</li>
  <li>test 2</li>
  <li>test 3</li>
</ul>

That being said, OP’s code works for me with Chrome 17.0.963.56 and Firefox 8.0. When you don’t know what to compare, just use console.log() to see what it looks like.

Note that #ECECF4 is the same color as rgb(236, 236, 244) but in a different representation.

IE7 and IE8 output the HEX value, IE9 and up and other browsers output the RGB format. So comparing color with cross-browser compatibility is a tricky task and the best way to do it isn’t beautiful.

I made a simple function which works for most cases with most browser, even with color set through CSS.

function weekclick() {
    var elemColor = getStyle(this, "backgroundColor"),
        color = "rgb(238, 238, 204)";

    console.log("Broswer returned elem color: ", elemColor);

    // IE7 and IE8 output the hex value
    if (elemColor.slice(0, 1) === '#') elemColor = hexToRgb(elemColor);

    console.log(elemColor, " === ", color, "?", elemColor === color);
}

// Source: https://stackoverflow.com/a/41354868/1218980
// Inspired by: https://stackoverflow.com/a/22744598/1218980
function getStyle(el, prop) {
    return (typeof getComputedStyle !== 'undefined' ?
        getComputedStyle(el, null) :
        el.currentStyle
    )[prop];
}


// Slightly modified version to quickly return a string
// https://stackoverflow.com/a/5624139/1218980
function hexToRgb(hex) {
    // Expand shorthand form (e.g. "03F") to full form (e.g. "0033FF")
    var shorthandRegex = /^#?([a-f\d])([a-f\d])([a-f\d])$/i;
    hex = hex.replace(shorthandRegex, function(m, r, g, b) {
        return r + r + g + g + b + b;
    });

    var result = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex);
    return result ? "rgb(" + [
        parseInt(result[1], 16),
        parseInt(result[2], 16),
        parseInt(result[3], 16)
    ].join(', ') + ")" : null;
}
#css-div {
  background-color: #eeeecc;
}
<div style="Background-color:#eeeecc" onclick="javascript:weekclick.call(this);">#eeeecc</div>
<div style="Background-color:#EEC" onclick="javascript:weekclick.call(this);">#EEC</div>
<div style="background-color:hsla(60, 50%, 86.7%, 1)" onclick="javascript:weekclick.call(this);">hsla(60, 50%, 86.7%, 1)</div>
<div style="background-color:rgb(238, 238, 204)" onclick="javascript:weekclick.call(this);">rgb(238, 238, 204)</div>
<div id="css-div" onclick="javascript:weekclick.call(this);">css</div>

I call the weekclick function with javascript:weekclick.call(this) passing the element itself as the context of the callback, making it easy to access the element with this.

It could be extended to take alpha into account when using HSLA or RGBA.


When I originally wrote this answer back in 2012, I used navigator.appName === "Microsoft Internet Explorer" to know if it was IE7 and the color to compare was changed to its HEX equivalent. Don’t do that as it won’t work today.

Leave a Comment