Parse and find named colors

Use CSS names as recognized input or approximate labels without confusing either role with color identity.

Use a CSS name as input when another system supplies that notation. Use a nearest name only as an approximate human label. Store and compare the color value itself, because many colors have no exact CSS name.

Separate values from labels

CSS names are a finite registry of sRGB constants. Parsing hotpink produces the same kind of color object as parsing its hexadecimal value; PHPColor does not retain the original spelling as provenance.

use PhpColor\Color\Color;

$named = Color::parse('hotpink');
$hex = Color::parse('#ff69b4');

echo $named->toHex().PHP_EOL;
echo ($named->equals($hex) ? 'same color' : 'different color').PHP_EOL;
use PhpColor\Color\Color; $named = Color::parse('hotpink'); $hex = Color::parse('#ff69b4'); echo $named->toHex().PHP_EOL; echo ($named->equals($hex) ? 'same color' : 'different color').PHP_EOL;

The output is:

#ff69b4
same color
#ff69b4 same color

Use the registry directly only when the application specifically needs CSS names rather than general color input:

use PhpColor\Color\Css\CssColors;

$color = CssColors::parse('rebeccapurple');
$maybeColor = CssColors::tryParse('not-a-name');
$hexWithoutHash = CssColors::tryHex('rebeccapurple');
$all = CssColors::all();

assert(null === $maybeColor);
assert('663399' === $hexWithoutHash);
use PhpColor\Color\Css\CssColors; $color = CssColors::parse('rebeccapurple'); $maybeColor = CssColors::tryParse('not-a-name'); $hexWithoutHash = CssColors::tryHex('rebeccapurple'); $all = CssColors::all(); assert(null === $maybeColor); assert('663399' === $hexWithoutHash);

Treat a nearest name as an approximation

When a UI needs a readable hint for an arbitrary color, rank the registry with a perceptual distance rather than comparing RGB bytes:

use PhpColor\Color\Color;
use PhpColor\Color\Css\CssColors;
use PhpColor\Color\Distance\ColorDistance;

$target = Color::parse('#3a86ff');
$ranked = [];

foreach (CssColors::all() as $name => $hex) {
    $ranked[$name] = ColorDistance::deltaE(
        $target,
        Color::parse($hex),
    );
}

asort($ranked);
$closest = array_key_first($ranked);
$distance = $ranked[$closest];
use PhpColor\Color\Color; use PhpColor\Color\Css\CssColors; use PhpColor\Color\Distance\ColorDistance; $target = Color::parse('#3a86ff'); $ranked = []; foreach (CssColors::all() as $name => $hex) { $ranked[$name] = ColorDistance::deltaE( $target, Color::parse($hex), ); } asort($ranked); $closest = array_key_first($ranked); $distance = $ranked[$closest];

A closest name is a description, not an equality claim. Keep the measured distance when the approximation matters, and keep the original color as the canonical value.

Do not use the nearest CSS name to collapse user colors into the registry, deduplicate tokens, or decide whether two values are interchangeable. Those decisions need an application-specific threshold and the original coordinates.

Continue with Supported concrete color input, Measure color distance, or CssColors for the registry contract.