hue = $hue; $this->saturation = max(0.0, min(1.0, $saturation)); $this->lightness = max(0.0, min(1.0, $lightness)); $this->alpha = max(0.0, min(1.0, $alpha)); $c = (1 - abs(2 * $lightness - 1)) * $saturation; $x = $c * (1 - abs(fmod($hue / 60, 2) - 1)); $m = $lightness - ($c / 2); $r = $g = $b = 0; if($hue < 60) { $r = $c; $g = $x; } elseif($hue < 120) { $r = $x; $g = $c; } elseif($hue < 180) { $g = $c; $b = $x; } elseif($hue < 240) { $g = $x; $b = $c; } elseif($hue < 300) { $r = $x; $b = $c; } else { $r = $c; $b = $x; } $this->red = (int)round(($r + $m) * 255); $this->green = (int)round(($g + $m) * 255); $this->blue = (int)round(($b + $m) * 255); } public function getRed(): int { return $this->red; } public function getGreen(): int { return $this->green; } public function getBlue(): int { return $this->blue; } public function getHue(): float { return $this->hue; } public function getSaturation(): float { return $this->saturation; } public function getLightness(): float { return $this->lightness; } public function getAlpha(): float { return $this->alpha; } public function shouldInherit(): bool { return false; } public function __toString(): string { if($this->alpha < 1.0) return sprintf('hsla(%.2Fdeg, %d%%, %d%%, %.3F)', $this->hue, $this->saturation * 100, $this->lightness * 100, $this->alpha); return sprintf('hsl(%.2Fdeg, %d%%, %d%%)', $this->hue, $this->saturation * 100, $this->lightness * 100); } public static function convert(Colour $colour): ColourHSL { if($colour instanceof ColourHSL) return $colour; $r = $colour->getRed() / 255.0; $g = $colour->getGreen() / 255.0; $b = $colour->getBlue() / 255.0; $max = max($r, $g, $b); $min = min($r, $g, $b); $h = $s = 0; $l = ($max + $min) / 2; $d = $max - $min; if($d <> 0) { $s = $d / (1 - abs(2 * $l - 1)); if($max == $r) { $h = 60 * fmod((($g - $b) / $d), 6); if($b > $g) $h += 360; } elseif($max == $g) { $h = 60 * (($b - $r) / $d + 2); } else { $h = 60 * (($r - $g) / $d + 4); } } return new ColourHSL( round($h, 3), round($s, 3), round($l, 3), $colour->getAlpha() ); } }