2

How do I take r,g,b values and compare them to a websafe color palette to find the best match for the r,g,b value?

There's this one: What is the best algorithm for finding the closest color in an array to another color?

But I don't think it's what I need. I just need to compare an r,g,b with a websafe color and find out if the websafe color is the best choice.

Edit1: deleted

Edit2: This is what I have so far.

local r, g, b = HSV2RGB(h, s, v)
local dither = copy(WEB_SAFE)
local lmod
for i, v in ipairs(dither) do
        local r2, g2, b2 = Color2RGBA(v)
        local hh, ss, vv = RGB2HSV(r2, g2, b2)
        local a = hh - h
        local b = ss - s
        local c = vv - v
        local mod = a*a + b*b + c*c
        if not lmod or mod < lmod then
                lmod = mod
                r, g, b = r2, g2,b2
        end
end
texture:SetBackgroundColor(r, g, b)

Edit 3: Is this what it's supposed to look like?

http://imgur.com/LwFGQ

h=1 through 360 at 5 pt steps, s=1 through 100, v = 89

Community
  • 1
  • 1
Scott
  • 5,135
  • 12
  • 57
  • 74
  • 1
    That's exactly what you need. Just put all the web safe colors into one array, compare your color one by one with each color in the array, then take the color which has the lowest difference. I can post example code if you like. – Lambda Fairy Dec 06 '11 at 05:24
  • Do I need to take the difference of each r,g,b value, or h,s,v, or 32bit number? – Scott Dec 06 '11 at 05:28
  • This looks like Lua code to me, so I'm tagging it as such. – Jeffrey Hantin Dec 06 '11 at 06:26
  • 1
    I'm glad you got an answer, but I'm really curious: Why do you need web safe colors in 2011? Can't you rely on everything being at least 16-bit these days? – Steven Fisher Dec 06 '11 at 17:31

1 Answers1

5

I'm not sure that HSV is the best color-space to perform the calculation in -- also it's a cylinder, not a cube, so your distance formula (which would work fine in RGB) would produce inappropriate results for HSV.

In any case, the Web safe palette is itself a simple RGB color cube, with six possible values (0-5) for each component. You shouldn't even need to do something as complex as iterating to derive a Web safe color from an input color: just determine the appropriate Web safe value for each color component (R, G, B) independently.

On the rash assumption that your RGB component values range from 0..255:

local max_color_component_value = 255
local quantum = max_color_component_value / 5

r = quantum * math.floor((r + (quantum / 2)) / quantum)
g = quantum * math.floor((g + (quantum / 2)) / quantum)
b = quantum * math.floor((b + (quantum / 2)) / quantum)

If some other range is used, adjust max_color_component_value appropriately.

Jeffrey Hantin
  • 35,734
  • 7
  • 75
  • 94
  • That got it. Thanks. These are definitely websafe? – Scott Dec 06 '11 at 06:42
  • @Scott Close, really close. Your output color component values are one less than they should be (254 instead of 255, etc). What is the actual max_color_component_value in the formula? – Jeffrey Hantin Dec 06 '11 at 07:09
  • Also, only the rainbow rectangle appears to have been run through the algorithm, not the entire image. Was that originally a smooth gradient, and is the "posterization" a problem? – Jeffrey Hantin Dec 06 '11 at 07:11
  • It was created with a saturation at 100 throughout the image. I was going to give an option to adjust the saturation. I'm not sure what the whole algorithm is though. This is just what I came up with. – Scott Dec 06 '11 at 07:18
  • max_color_compent_value is 255. I tried with 1 because I'm working in a range between 1 and 0, but the top line wasn't right. – Scott Dec 06 '11 at 07:20
  • I need to figure out how to draw the cylinder I think. The image shape changes when I adjust v as opposed to s or s as opposed to v. – Scott Dec 06 '11 at 08:50
  • Here you go. I think this is it. s is 1-100, v is 80, and h is 1-360 at 5 pt steps. http://imgur.com/LwFGQ – Scott Dec 06 '11 at 08:57
  • If your RGB color component value range is 0 to 1 inclusive, then you just need to snap it to the nearest multiple of 0.2 (0, 0.2, 0.4, 0.6, 0.8, 1). That's really all my algorithm is doing. – Jeffrey Hantin Dec 07 '11 at 01:16