Currently Browsing: Home » Coding a Color Manager with Object-Oriented PHP

Coding a Color Manager with Object-Oriented PHP

Colors are a vital part of web design. They can easily make or break a design. Often times, designers are interested in modifying colors by mixing, fading, or brightening them. This will be the basis for today’s article.

Color Wheel

We’re going to go through the process of creating a simple color manager with object-oriented PHP. Rather than focusing on multiple forms of modification, our color manager will perform one basic function: fading. Given a base color (hexadecimal) and a fade percentage, we will calculate a new, faded color.

View the color manager Download the files

Fading, when taken from a red-green-blue (RGB) color perspective, only involves linear interpolation. In other words, to fade a color from blue rgb( 0, 0, 255 ) to white rgb( 255, 255, 255 ), each color component must be increased by a percentage of the difference to the target component.

To elucidate this statement, consider the following example: if you wanted to fade 10% from blue to white, you would calculate the components as such:

original color (blue) = rgb( 0, 0, 255 )
target color (white)  = rgb( 255, 255, 255 )
fade percent          = 10%

original color's red component = 0
target color's red component   = 255
difference in components       = 255 - 0
                               = 255

new red component = original red component + difference in components * fade percent
new red component = 0 + 255 * .10
                  = 25.5

This process would be repeated with the two other components. The new color (after all calculations) would be:

rgb( 25.5, 25.5, 255 );

If you were to look at this color, it would be a faded blue.

Since we are working with a hexadecimal color, it would be beneficial to convert it to RGB, fade it, and then convert back. Although there are ways to fade directly in hexadecimal format, this path begs the use of object-oriented PHP and does not require a knowledge of bit manipulation.

Hexadecimal

Before starting to code, you must first understand how to convert from hexadecimal to RGB and back. The first two letters/digits in a hex color represent the red component in an RGB color. In like manner, the third and fourth letters/digits represent the green component. Finally, the last two digits represent the blue component. After splitting the hex color into these three sets, each one must be converted from base 16 to base 10 to get the final RGB color:

hex color (white) = FFFFFF

red component = FF (base 16)
              = 255 (base 10)

green component = FF (base 16)
                = 255 (base 10)

blue component = FF (base 16)
               = 255 (base 10)

hex color (white) = rgb( 255, 255, 255 )

To go from RGB to hexadecimal, convert each component to base 16 and concatenate them:

rgb color (white) = ( 255, 255, 255 )

red component = 255 (base 10)
              = FF (base 16)

green component = 255 (base 10)
                = FF (base 16)

blue component = 255 (base 10)
               = FF (base 16)

rgb color (white) = hex FFFFFF

Now we can move on to the implementation. To begin, we will first write a HexColor class, which will hold a $hex variable representing the hex string. This class will provide a function to convert to an RGB color:

class HexColor {
	private $hex;

	public function HexColor( $hex )
	{
		if( strpos( $hex, '#' ) === 0 )
			$this->hex = substr( $hex, 1 );
		else
			$this->hex = $hex;
	}

	public function getHexString()
	{
		return $this->hex;
	}

	public function convertToRGB()
	{
		// first two digits represent red, next two blue, and the last two green
		$red = substr( $this->hex, 0, 2 );
		$green = substr( $this->hex, 2, 2 );
		$blue = substr( $this->hex, 4, 2 );

		// convert from hexadecimal to base 10
		$red = (int) base_convert( $red, 16, 10 );
		$green = (int) base_convert( $green, 16, 10 );
		$blue = (int) base_convert( $blue, 16, 10 );

		return new RGBColor( $red, $green, $blue );
	}

	public static function isValid( $hex )
	{
		return (bool) preg_match( '/^(#)?[a-zA-Z0-9]{6}$/', $hex );
	}

	public function __toString()
	{
		return $this->hex;
	}
}

Note that the isValid function is used to check whether a given string is a valid hex color.

RGB

Next is the RGBColor class, which contains similar functionality and a fadeTo function based off of the calculations explained at the beginning of this article:

class RGBColor {
	private $red, $green, $blue;

	public function RGBColor( $red, $green, $blue )
	{
		$this->red = $this->clamp( $red );
		$this->green = $this->clamp( $green );
		$this->blue = $this->clamp( $blue );
	}

	public function getRed()
	{
		return $this->red;
	}

	public function getGreen()
	{
		return $this->green;
	}

	public function getBlue()
	{
		return $this->blue;
	}

	public function fadeTo( $rgbColor, $percent )
	{
		$newRed = ( 1 - $percent ) * $this->red + $percent * $rgbColor->getRed();
		$newGreen = ( 1 - $percent ) * $this->green + $percent * $rgbColor->getGreen();
		$newBlue = ( 1 - $percent ) * $this->blue + $percent * $rgbColor->getBlue();

		return new RGBColor( (int) $newRed, (int) $newGreen, (int) $newBlue );
	}

	public function convertToHex()
	{
		$newRed = base_convert( $this->red, 10, 16 );
		$newGreen = base_convert( $this->green, 10, 16 );
		$newBlue = base_convert( $this->blue, 10, 16 );

		$newRed = $this->addZero( $newRed );
		$newGreen = $this->addZero( $newGreen );
		$newBlue = $this->addZero( $newBlue );

		return new HexColor( $newRed . $newGreen . $newBlue );
	}

	private function addZero( $colorValue )
	{
		if( strlen( $colorValue ) == 1 )
			$colorValue = '0' . $colorValue;
		return $colorValue;
	}

	private function clamp( $colorValue )
	{
		// clamp colorValue in interval [0, 255]
		return max( 0, min( 255, $colorValue ) );
	}

	public function __toString()
	{
		return '(' . $this->red . ', ' . $this->green . ', ' . $this->blue . ')';
	}
}

Since RGB color values can only be in the 0-255 range, the clamp function is used to ensure this is true. In addition, the addZero function makes sure the hex color is six digits long by prepending the necessary 0s.

Given these classes, a $hex string, and a $fade percentage, the process to fade a hex color is as follows:

  1. Instantiate a HexColor object with the $hex string
  2. Convert it to an RGBColor
  3. Call the fadeTo function with the given $fade percentage and the color white
  4. Convert the RGBColor back to a HexColor and display it

In addition, to make this more flexible, we can change the third step to darken the color (fade to black) if the fade percentage is negative. These instructions lead to the following code:

$hexColor = new HexColor( $hex );

// target color is white by default
$targetColor = new RGBColor( 255, 255, 255 );

// want to darken the color--target is black
if( $fade < 0 ) {
	$targetColor = new RGBColor( 0, 0, 0 );
	$fade = -$fade; // make fade positive
}

$rgbColor = $hexColor->convertToRGB();

// fade / 100 is the percentage
$fadedColor = $rgbColor->fadeTo( $targetColor, $fade / 100 );
echo $fadedColor->convertToHex();

Combined with some AJAX, form handling, and CSS (which I won’t be going over, as this was a lesson in object-oriented PHP), this code ultimately results in a simple color manager, which you may view/download using the buttons below:

View the color manager Download the files

Tags:

This entry was posted on Thursday, June 17th, 2010 at 15:57:17. You can follow any responses to this entry through the RSS 2.0 feed. You can leave a response, or trackback from your own site.

Leave a Reply

Want to be notified when someone replies? Subscribe to this post's comment RSS feed.
Any field marked with a * is required.