用K计算色温

dog*_*c69 23 php c colors gimp

我已经编写了一个用于处理颜色的库,并试图计算Tc(k).从我在CIE 1931 XYZ色彩空间中工作的阅读是可行的方法,它可以使用xyY.

到目前为止,我已经把一切都弄正确到找出正确的xy来自:

          X                 Y
x = ____________  y = ____________
    ( X + Y + Z)      ( X + Y + Z)
Run Code Online (Sandbox Code Playgroud)

数字多到图表,但不能找到任何细节,你是如何从去xyTc(K)

在此输入图像描述

例如:对于#FF0000,我得到以下内容.

x: 0.64007449945677
y: 0.32997051063169
Run Code Online (Sandbox Code Playgroud)

我已经阅读了很多关于这个主题的论文,并且阅读了所有维基百科的文章.我在SO上遇到的所有问题只是链接到关于颜色的维基文章,没有看到具有实际计算公式的文章Tc(k)

dog*_*c69 1

我对一些开源应用程序进行了一些挖掘,并在 UFRaw 中找到了一些东西。我还不太明白到底发生了什么。

还发现一篇似乎很好地涵盖了该主题的论文

转换为 php,这就是我到目前为止所得到的:

$temp = array(9500, 7000, 5500, 3750, 3000, 2700, 2250, 1800, 1500);
$hex = array('9DBEFF', 'E4EEFF', 'FFE4BE', 'FFA04C', 'FF7A26', 'FF6A19', 'FF500B', 'FF3403', 'FF2300');

echo '<h3>K -> RGB</h3>';
foreach ($temp as $k) {
    $rgb = ColourConverter::temperature2rgb($k);
    echo sprintf('<div style="background-color:rgb(%s); text-align: center; width: 100px; height: 25px; clear: both;">%s</div>', implode(', ', $rgb), $k);
}

echo '<h3>RGB -> K</h3>';
foreach ($hex as $v) {
    $rgb = array_values(ColourConverter::hex2rgb($v));
    $k = round(ColourConverter::rgb2temperature($rgb[0], $rgb[1], $rgb[2]));
    echo sprintf('<div style="background-color:rgb(%s); text-align: center; width: 100px; height: 25px; clear: both;">%s</div>', implode(', ', $rgb), $k);
}
Run Code Online (Sandbox Code Playgroud)

参考

我的输出:

输出

非常接近,但还没有达到 100%。(在我的代码中发现了一个错误,现在它几乎完美了)

  • 颜色从 k -> rgb 略有偏差
  • 执行 k -> rgb -> k 不起作用。您不会恢复到相同的值。

代码

UF原线246-294

void Temperature_to_RGB(double T, double RGB[3])
{
    int c;
    double xD, yD, X, Y, Z, max;
    // Fit for CIE Daylight illuminant
    if (T <= 4000) {
        xD = 0.27475e9 / (T * T * T) - 0.98598e6 / (T * T) + 1.17444e3 / T + 0.145986;
    } else if (T <= 7000) {
        xD = -4.6070e9 / (T * T * T) + 2.9678e6 / (T * T) + 0.09911e3 / T + 0.244063;
    } else {
        xD = -2.0064e9 / (T * T * T) + 1.9018e6 / (T * T) + 0.24748e3 / T + 0.237040;
    }
    yD = -3 * xD * xD + 2.87 * xD - 0.275;

    // Fit for Blackbody using CIE standard observer function at 2 degrees
    //xD = -1.8596e9/(T*T*T) + 1.37686e6/(T*T) + 0.360496e3/T + 0.232632;
    //yD = -2.6046*xD*xD + 2.6106*xD - 0.239156;

    // Fit for Blackbody using CIE standard observer function at 10 degrees
    //xD = -1.98883e9/(T*T*T) + 1.45155e6/(T*T) + 0.364774e3/T + 0.231136;
    //yD = -2.35563*xD*xD + 2.39688*xD - 0.196035;

    X = xD / yD;
    Y = 1;
    Z = (1 - xD - yD) / yD;
    max = 0;
    for (c = 0; c < 3; c++) {
        RGB[c] = X * XYZ_to_RGB[0][c] + Y * XYZ_to_RGB[1][c] + Z * XYZ_to_RGB[2][c];
        if (RGB[c] > max) max = RGB[c];
    }
    for (c = 0; c < 3; c++) RGB[c] = RGB[c] / max;
}

void RGB_to_Temperature(double RGB[3], double *T, double *Green)
{
    double Tmax, Tmin, testRGB[3];
    Tmin = 2000;
    Tmax = 23000;
    for (*T = (Tmax + Tmin) / 2; Tmax - Tmin > 0.1; *T = (Tmax + Tmin) / 2) {
        Temperature_to_RGB(*T, testRGB);
        if (testRGB[2] / testRGB[0] > RGB[2] / RGB[0])
            Tmax = *T;
        else
            Tmin = *T;
    }
    *Green = (testRGB[1] / testRGB[0]) / (RGB[1] / RGB[0]);
    if (*Green < 0.2) *Green = 0.2;
    if (*Green > 2.5) *Green = 2.5;
}
Run Code Online (Sandbox Code Playgroud)

  • 你好朋友,链接已损坏,你可以更新这个答案吗? (4认同)