5
votes

Is there a way to easily assign a given hex color code to a more general category (red, gren, blue, yellow, orange, pink, black, white, grey, ...)?

Like #ffcc55 -> orange, #f0f0f0 -> white, ...

EDIT: or even just similar to adobe photoshop finding the nearest web safe color, so it would reduce the number of colors to 256, would be already a great solution!

2
Ahem... finding the nearest color can be done quite easier, I think, especially if you have the table of web-safe color RGB values readyJust calculate the difference (it's hexadecimals, remember), then choose the color with the lowest one.raina77ow

2 Answers

4
votes

This is from http://php.net/manual/en/function.dechex.php, comment from cory at lavacube dot com:

<?php

function color_mkwebsafe ( $in )
{
    // put values into an easy-to-use array
    $vals['r'] = hexdec( substr($in, 0, 2) );
    $vals['g'] = hexdec( substr($in, 2, 2) );
    $vals['b'] = hexdec( substr($in, 4, 2) );

    // loop through
    foreach( $vals as $val )
    {
        // convert value
        $val = ( round($val/51) * 51 );
        // convert to HEX
        $out .= str_pad(dechex($val), 2, '0', STR_PAD_LEFT);
    }

    return $out;
}

?>

Example: color_mkwebsafe('0e5c94'); Produces: 006699

4
votes

I'm not a php guru so there may be more efficient ways of solving this in php, but I'd set up each color as an array, so you've got 3 numbers for each color category. Then find the mathematical distance between your proposed color and each of the others. Save the closest match and return the name of it.

function getcolorname($mycolor) {
    // mycolor should be a 3 element array with the r,g,b values 
    // as ints between 0 and 255. 
    $colors = array(
        "red"       =>array(255,0,0),
        "yellow"    =>array(255,255,0),
        "green"     =>array(0,255,0),
        "cyan"      =>array(0,255,255),
        "blue"      =>array(0,0,255),
        "magenta"   =>array(255,0,255),
        "white"     =>array(255,255,255),
        "grey"      =>array(127,127,127),
        "black"     =>array(0,0,0)
    );

    $tmpdist = 255*3;
    $tmpname = "none";
    foreach($colors as $colorname => $colorset) {        
        $r_dist = (pow($mycolor[0],2) - pow($colorset[0],2));
        $g_dist = (pow($mycolor[1],2) - pow($colorset[1],2));       
        $b_dist = (pow($mycolor[2],2) - pow($colorset[2],2));
        $totaldist = sqrt($r_dist + $g_dist + $b_dist);
        if ($totaldist < $tmpdist) {        
            $tmpname = $colorname;
            $tmpdist = $totaldist;
        }
    }
    return $tmpname;
}