Given a background color, black or white text?

Take a look at this page: Calculating Color Contrast with PHP

Keep in mind that if black and white are your only choices you're bound to have cases where neither of them works particularly great.


Luminosity Contrast algorithm

I think the best way is the Luminosity Contrast algorithm:

function getContrastColor($hexColor)
{
        // hexColor RGB
        $R1 = hexdec(substr($hexColor, 1, 2));
        $G1 = hexdec(substr($hexColor, 3, 2));
        $B1 = hexdec(substr($hexColor, 5, 2));

        // Black RGB
        $blackColor = "#000000";
        $R2BlackColor = hexdec(substr($blackColor, 1, 2));
        $G2BlackColor = hexdec(substr($blackColor, 3, 2));
        $B2BlackColor = hexdec(substr($blackColor, 5, 2));

         // Calc contrast ratio
         $L1 = 0.2126 * pow($R1 / 255, 2.2) +
               0.7152 * pow($G1 / 255, 2.2) +
               0.0722 * pow($B1 / 255, 2.2);

        $L2 = 0.2126 * pow($R2BlackColor / 255, 2.2) +
              0.7152 * pow($G2BlackColor / 255, 2.2) +
              0.0722 * pow($B2BlackColor / 255, 2.2);

        $contrastRatio = 0;
        if ($L1 > $L2) {
            $contrastRatio = (int)(($L1 + 0.05) / ($L2 + 0.05));
        } else {
            $contrastRatio = (int)(($L2 + 0.05) / ($L1 + 0.05));
        }

        // If contrast is more than 5, return black color
        if ($contrastRatio > 5) {
            return '#000000';
        } else { 
            // if not, return white color.
            return '#FFFFFF';
        }
}

// Will return '#FFFFFF'
echo getContrastColor('#FF0000');

Some results:

enter image description here

NOTE: The font color is determined by the previous function. The number in brackets is the contrast ratio.



YIQ algorithm (less precise)

Another simpliest and less precise way called YIQ (because it converts the RGB color space into YIQ):

public function getContrastColor($hexcolor) 
{               
    $r = hexdec(substr($hexcolor, 1, 2));
    $g = hexdec(substr($hexcolor, 3, 2));
    $b = hexdec(substr($hexcolor, 5, 2));
    $yiq = (($r * 299) + ($g * 587) + ($b * 114)) / 1000;
    return ($yiq >= 128) ? 'black' : 'white';
}                   

  function getTextColour($hex){
    list($red, $green, $blue) = sscanf($hex, "#%02x%02x%02x");
    $luma = ($red + $green + $blue)/3;

    if ($luma < 128){
      $textcolour = "white";
    }else{
      $textcolour = "black";
    }
    return $textcolour;
  }

Here is an algorithm that can be used to calculate a luminosity contrast ratio of your text:

http://juicystudio.com/services/aertcolourcontrast.php

You could use this formula with white and black values to calculate which gives you the higher ratio, and thus more readable text.

Tags:

Css

Php

Hex

Colors