Fix gamma correction (#1825)

* corrected gamma function

* uncorrect color temperature to work with new gamma

* Adjust gamma corrected expectation for self test
This commit is contained in:
Jesse Campbell 2025-10-06 03:30:16 -04:00 committed by GitHub
parent 6279bcd07a
commit 883e85e4cc
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 46 additions and 17 deletions

View File

@ -408,20 +408,23 @@ float led_gamma_correction (int color, float iVal) { // apply LED gamma and RGB
}
// apply LED gamma correction:
float ch_bright_min = g_cfg.led_corr.rgb_bright_min / 100;
if (color > 2) {
ch_bright_min = g_cfg.led_corr.cw_bright_min / 100;
}
float oVal = (powf (brightnessNormalized0to1, g_cfg.led_corr.led_gamma) * (1 - ch_bright_min) + ch_bright_min) * iVal;
// this gamma correction function does not properly calculate gamma
// float ch_bright_min = g_cfg.led_corr.rgb_bright_min / 100;
// if (color > 2) {
// ch_bright_min = g_cfg.led_corr.cw_bright_min / 100;
// }
// float oVal = (powf (brightnessNormalized0to1, g_cfg.led_corr.led_gamma) * (1 - ch_bright_min) + ch_bright_min) * iVal;
// color value adjusted to float 0-1, modified by brightness
float brightnessCorrectedColor = iVal / 255.0f * brightnessNormalized0to1;
// gamma correct the color value
float oVal = powf (brightnessCorrectedColor, g_cfg.led_corr.led_gamma) * 255.0f;
// apply RGB level correction:
if (color < 3) {
rgb_used_corr[color] = g_cfg.led_corr.rgb_cal[color];
// boost gain to get full brightness when one RGB base color is dominant:
float sum_other_colors = led_baseColors[0] + led_baseColors[1] + led_baseColors[2] - led_baseColors[color];
if (led_baseColors[color] > sum_other_colors) {
rgb_used_corr[color] += (1.0f - rgb_used_corr[color]) * (1.0f - sum_other_colors / led_baseColors[color]);
}
oVal *= rgb_used_corr[color];
}
@ -832,14 +835,31 @@ float LED_GetTemperature0to1Range() {
}
void LED_SetTemperature(int tmpInteger, bool bApply) {
float f;
float ww,cw,max_cw_ww;
led_temperature_current = tmpInteger;
f = LED_GetTemperature0to1Range();
ww = LED_GetTemperature0to1Range();
cw = 1 - ww;
//normalize to have a local max of 100%
if (ww > cw)
max_cw_ww = ww;
else
max_cw_ww = cw;
ww = ww / max_cw_ww;
cw = cw / max_cw_ww;
//uncorrect for gamma to allow gamma correcting brightness later
if (g_cfg.led_corr.led_gamma >= 1 && g_cfg.led_corr.led_gamma <= 3) {
ww = powf(ww, 1 / g_cfg.led_corr.led_gamma);
cw = powf(cw, 1 / g_cfg.led_corr.led_gamma);
}
led_baseColors[3] = (255.0f) * cw;
led_baseColors[4] = (255.0f) * ww;
led_baseColors[3] = (255.0f) * (1-f);
led_baseColors[4] = (255.0f) * f;
if(bApply) {
if (CFG_HasFlag(OBK_FLAG_LED_AUTOENABLE_ON_ANY_ACTION)) {
@ -1253,9 +1273,18 @@ void LED_SetFinalRGBW(byte r, byte g, byte b, byte w) {
led_baseColors[0] = r;
led_baseColors[1] = g;
led_baseColors[2] = b;
// half between Cool and Warm
led_baseColors[3] = w / 2;
led_baseColors[4] = w / 2;
float w_half = w / 2 / 255.0f;
LED_SetTemperature0to1Range(0.5f);
//uncorrect for gamma to allow gamma correcting brightness later
if (g_cfg.led_corr.led_gamma >= 1 && g_cfg.led_corr.led_gamma <= 3) {
w_half = powf(w_half, 1 / g_cfg.led_corr.led_gamma);
}
led_baseColors[3] = (255.0f) * w_half;
led_baseColors[4] = (255.0f) * w_half;
RGBtoHSV(led_baseColors[0] / 255.0f, led_baseColors[1] / 255.0f, led_baseColors[2] / 255.0f, &g_hsv_h, &g_hsv_s, &g_hsv_v);

View File

@ -213,7 +213,7 @@ void Test_Http_LED_RGB() {
SELFTEST_ASSERT_JSON_VALUE_INTEGER("StatusSTS", "Dimmer", 100);
SELFTEST_ASSERT_JSON_VALUE_STRING("StatusSTS", "POWER", "ON");
// Tasmota colors are scalled by Dimmer in this case. Confirmed.
SELFTEST_ASSERT_JSON_VALUE_STRING("StatusSTS", "Color", "127,255,0");
SELFTEST_ASSERT_JSON_VALUE_STRING("StatusSTS", "Color", "55,255,0");
// check Tasmota HSBColor
/*
NOTE: