Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

CSS mix-blend-mode:difference inconsistent across browsers and monitors

On a website I'm developing, I'm using mix-blend-mode:difference to give an interesting effect when some elements are positioned over other elements. I noticed recently that in webkit browsers, on my Macbook Pro display, the color of the div with mix-blend-mode:difference on it is much darker than it should be, in some specific scenarios.

See my codepen: https://codepen.io/matt_o_tron_5000/pen/LYxPaLm

HTML:

<div class="background">
  <div class="plain-color"></div>
  <div class="blend-color"></div>
</div>

CSS:

.background {
  background-color: #fff;
}

.plain-color,
.blend-color {
  width: 200px;
  height: 200px;
}

.plain-color {
  background-color: #04f;
}

.blend-color {
  background-color: #fb0;
  mix-blend-mode: difference;
}

In the codepen, one div is using a normal hex color code as the background color, and the other div is using the exact opposite hex code as the background color, with mix-blend-mode:difference applied.

On my external monitor, these two divs are the exact same color (and yes this monitor is reliably color-accurate). But if I move the window to my Macbook Pro display, suddenly the mix-blend-mode div is much darker than the other.

Additionally, when testing in Firefox, the color of the 2 divs match exactly no matter which display I view them on. Only in Safari and Chrome does the div look unexpectedly dark on my Macbook monitor.

I assume this has something to do with the fact that Safari and Chrome use webkit while Firefox uses a different engine (gecko), but... Why the difference between monitors? I am confusion.

Photo examples:

2 divs in Chrome on external display:

2 divs in Chrome on external display

2 divs in Chrome on Macbook display:

2 divs in Chrome on Macbook display

like image 632
Matt Tanner Avatar asked Dec 20 '25 09:12

Matt Tanner


1 Answers

Sorry this is an old question, but this may now be possible to fix by specifying the right color profile using the CSS color() function. This is still behind an experimental flag in most browsers but seems to be supported in Safari and just now in Chrome 111.

Adding the following normalizes the colors for me across supported browsers, and at least between my Macbook and desktop monitors. There is still a slight difference on my desktop but it's much less noticeable. Here's a working pen.

@supports (background-color: color(display-p3 1 1 1)) {
  @media (color-gamut: p3) {
    .background {
      --colorspace: display-p3;
    }
    .plain-color {
      background-color: color(var(--colorspace, srgb) 0 calc(68 / 255) 1);
    }
    .blend-color {
      background-color: color(var(--colorspace, srgb) 1 calc(187 / 255) 0);
    }
  }
  @media (color-gamut: rec2020) {
    .background {
      --colorspace: rec2020;
    }
  }
}

You can mostly get away with just adjusting the color profile of the blended elements, but it's more consistent to adjust all. I assume that the difference between monitors comes down to which color profiles they support.

like image 61
dawaltco Avatar answered Dec 21 '25 23:12

dawaltco



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!