Convert RGB to RGBA over white Convert RGB to RGBA over white javascript javascript

Convert RGB to RGBA over white


Take the lowest color component, and convert that to an alpha value. Then scale the color components by subtracting the lowest, and dividing by the alpha value.

Example:

152 converts to an alpha value of (255 - 152) / 255 ~ 0.404152 scales using (152 - 152) / 0.404 = 0177 scales using (177 - 152) / 0.404 ~ 62202 scales using (202 - 152) / 0.404 ~ 123

So, rgb(152, 177, 202) displays as rgba(0, 62, 123, .404).

I have verified in Photoshop that the colors actually match perfectly.


Let r, g, and b be the input values and r', g', b', and a' be the output values, all scaled (for now, as it makes the math prettier) between 1 and 0. Then, by the formula for overlaying colors:

r = a' * r' + 1 - a'g = a' * g' + 1 - a'b = a' * b' + 1 - a'

The 1 - a' terms represent the background contribution, and the other terms represent the foreground. Do some algebra:

r = a' * (r' - 1) + 1r - 1 = a' * (r' - 1)(r - 1) / (r' - 1) = a'(r' - 1) / (r - 1) = 1 / a'r' - 1 = (r - 1) / a'r' = (r - 1) / a' + 1

Intuitively, it seems that the minimum color value will be the limiting factor in the problem, so bind this to m:

m = min(r, g, b)

Set the corresponding output value, m', to zero, as we want to maximize transparency:

0 = (m - 1) / a' + 1-1 = (m - 1) / a'-a' = m - 1a' = 1 - m

So, in javascript (translating from 1 to 255 along the way):

function rgba(r, g, b) {    var a = 1 - Math.min(r, Math.min(g, b)) / 255;    return [255 + (r - 255) / a, 255 + (g - 255) / a, 255 + (b - 255) / a, a];}

Note that I'm assuming that a' is opacity here. It is trivial to change it to transparency - just remove the "1 -" from the formula for a'. Anothing thing to note is that this does not seem to produce exact results - it said that the opacity was 0.498 for the example you gave above (128, 128, 255). However, this is extremely close.


I'd look to RGB<->HSL conversion. I.e. luminosity == amount of white == amount of transparency.

For your example rgb( 128, 128, 255 ), we need to shift RGB values to 0 first by maximum amount, i.e. to rgb( 0, 0, 128 ) - that would be our color with as few of white as possible. And after that, using formula for luminance, we calculate amount of white we need to add to our dark color to get original color - that would be our alpha:

L = (MAX(R,G,B) + MIN(R,G,B))/2L1 = (255 + 128) / 2 = 191.5L2 = (128 + 0) /2 = 64A = (191,5 - 64) / 255 = 0,5;

Hope that makes sense. :)