RGB do HSV w PHP
W PHP, jaki jest najprostszy sposób na konwersję trypletu RGB na wartości HSV?
16
3 answers
<?php
function RGB_TO_HSV ($R, $G, $B) // RGB Values:Number 0-255
{ // HSV Results:Number 0-1
$HSL = array();
$var_R = ($R / 255);
$var_G = ($G / 255);
$var_B = ($B / 255);
$var_Min = min($var_R, $var_G, $var_B);
$var_Max = max($var_R, $var_G, $var_B);
$del_Max = $var_Max - $var_Min;
$V = $var_Max;
if ($del_Max == 0)
{
$H = 0;
$S = 0;
}
else
{
$S = $del_Max / $var_Max;
$del_R = ( ( ( $var_Max - $var_R ) / 6 ) + ( $del_Max / 2 ) ) / $del_Max;
$del_G = ( ( ( $var_Max - $var_G ) / 6 ) + ( $del_Max / 2 ) ) / $del_Max;
$del_B = ( ( ( $var_Max - $var_B ) / 6 ) + ( $del_Max / 2 ) ) / $del_Max;
if ($var_R == $var_Max) $H = $del_B - $del_G;
else if ($var_G == $var_Max) $H = ( 1 / 3 ) + $del_R - $del_B;
else if ($var_B == $var_Max) $H = ( 2 / 3 ) + $del_G - $del_R;
if ($H<0) $H++;
if ($H>1) $H--;
}
$HSL['H'] = $H;
$HSL['S'] = $S;
$HSL['V'] = $V;
return $HSL;
}
15
Author: Jacob,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-12-21 21:39:43
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-12-21 21:39:43
Oto prosta metoda, która zwraca wartości HSV jako stopnie i procenty, czyli to, czego używa próbnik kolorów Photoshopa.
Zwróć uwagę, że wartości zwrotne nie są zaokrąglane, możesz to zrobić samodzielnie, jeśli jest to wymagane. Należy pamiętać, że H(360) == H(0)
, Więc H
wartości 359.5
i większe powinny zaokrąglać się do 0
Mocno udokumentowane w celach edukacyjnych.
/**
* Licensed under the terms of the BSD License.
* (Basically, this means you can do whatever you like with it,
* but if you just copy and paste my code into your app, you
* should give me a shout-out/credit :)
*/
<?php
function RGBtoHSV($R, $G, $B) // RGB values: 0-255, 0-255, 0-255
{ // HSV values: 0-360, 0-100, 0-100
// Convert the RGB byte-values to percentages
$R = ($R / 255);
$G = ($G / 255);
$B = ($B / 255);
// Calculate a few basic values, the maximum value of R,G,B, the
// minimum value, and the difference of the two (chroma).
$maxRGB = max($R, $G, $B);
$minRGB = min($R, $G, $B);
$chroma = $maxRGB - $minRGB;
// Value (also called Brightness) is the easiest component to calculate,
// and is simply the highest value among the R,G,B components.
// We multiply by 100 to turn the decimal into a readable percent value.
$computedV = 100 * $maxRGB;
// Special case if hueless (equal parts RGB make black, white, or grays)
// Note that Hue is technically undefined when chroma is zero, as
// attempting to calculate it would cause division by zero (see
// below), so most applications simply substitute a Hue of zero.
// Saturation will always be zero in this case, see below for details.
if ($chroma == 0)
return array(0, 0, $computedV);
// Saturation is also simple to compute, and is simply the chroma
// over the Value (or Brightness)
// Again, multiplied by 100 to get a percentage.
$computedS = 100 * ($chroma / $maxRGB);
// Calculate Hue component
// Hue is calculated on the "chromacity plane", which is represented
// as a 2D hexagon, divided into six 60-degree sectors. We calculate
// the bisecting angle as a value 0 <= x < 6, that represents which
// portion of which sector the line falls on.
if ($R == $minRGB)
$h = 3 - (($G - $B) / $chroma);
elseif ($B == $minRGB)
$h = 1 - (($R - $G) / $chroma);
else // $G == $minRGB
$h = 5 - (($B - $R) / $chroma);
// After we have the sector position, we multiply it by the size of
// each sector's arc (60 degrees) to obtain the angle in degrees.
$computedH = 60 * $h;
return array($computedH, $computedS, $computedV);
}
?>
30
Author: Unsigned,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-08-03 23:36:50
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-08-03 23:36:50
Oto mój spin na nim, wraz z testem jednostkowym. Ponieważ wartości S
i V
są procentami, ten kod zwraca je jako liczby całkowite (0, 100) W przeciwieństwie do (0, 1) - Przykład, 75
zamiast 0.75
.
final class MathService
{
/**
* Converts an RGB point into HSV
*
* @param int $r
* @param int $g
* @param int $b
* @return array
*/
public function rgbToHsv(int $r, int $g, int $b): array
{
$rPrime = $r / 255;
$gPrime = $g / 255;
$bPrime = $b / 255;
$max = max([$rPrime, $gPrime, $bPrime]);
$min = min([$rPrime, $gPrime, $bPrime]);
$delta = $max - $min;
// Calculate H
if ($delta == 0) {
$h = 0;
} else {
if ($max === $rPrime) {
$h = 60 * ((($gPrime - $bPrime) / $delta) % 6);
}
if ($max === $gPrime) {
$h = 60 * ((($bPrime - $rPrime) / $delta) + 2);
}
if ($max === $bPrime) {
$h = 60 * ((($rPrime - $gPrime) / $delta) + 4);
}
}
// Calculate S
if ($max == 0) {
$s = 0;
} else {
$s = $delta / $max;
}
// Calculate V
$v = $max;
return [$h, (int)($s * 100), (int)($v * 100)];
}
}
PHPUnit test case with PHP 7.2
/**
* @test
*/
public function rgbToHsv_ComputesCorrectValues(): void
{
$service = new MathService();
$samples = [
// [R, G, B, H, S, V]
[0, 0, 0, 0, 0, 0],
[255, 255, 255, 0, 0, 100],
[255, 0, 0, 0, 100, 100],
[0, 255, 0, 120, 100, 100],
[0, 0, 255, 240, 100, 100],
[255, 255, 0, 60, 100, 100],
[0, 255, 255, 180, 100, 100],
[255, 0, 255, 300, 100, 100],
[192, 192, 192, 0, 0, 75],
[128, 128, 128, 0, 0, 50],
[128, 0, 0, 0, 100, 50],
[128, 128, 0, 60, 100, 50],
[0, 128, 0, 120, 100, 50],
[128, 0, 128, 300, 100, 50],
[0, 128, 128, 180, 100, 50],
[0, 0, 128, 240, 100, 50],
];
foreach ($samples as $sample) {
list($r, $g, $b) = array_slice($sample, 0, 3);
$expected = array_slice($sample, 3);
$hsv = $service->rgbToHsv($r, $g, $b);
list($h, $s, $v) = $hsv;
self::assertEquals($expected, $hsv, "Error converting ({$r}, ${g}, ${b}). Got ({$h}, {$s}, {$v})");
}
}
0
Author: rodrigo-silveira,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-03-27 12:24:47
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-03-27 12:24:47