【发布时间】:2019-06-24 20:09:15
【问题描述】:
我有一个灰度图像,我想对其应用伽马校正。手动地,我在不接触黑点或白点的情况下调整 Photoshop 级别的中间滑块,直到直方图的中值达到 127 或接近它的某个位置。我想通过 python 做同样的事情。
我寻找了一个将伽玛值作为输入并生成输出图像的公式。但是,我只找到了一个可以调整低值和高值而不是 gamma(或中间调)的方法。
这里,R 是我的图像中像素的 RGB 红色值,作为一个 numpy 数组,H 是高输入,L 是低输入。我从 L=0 和 H=255 开始,不断向函数传递不同的值,直到返回的图像在直方图上的中位数为 127。
def get_levelcorrected_image(R,H,L):
temp=((R-L)*255.0)/(H-L)
temp[temp<0]=0
temp[temp>255]=255
temp[temp==255]=0 #added this line because for some reason there were a lot of white pixels where it should have been dark
final = temp.astype('uint8')
return final
我尝试在 gimp 文档中搜索 gamma 滑块后面的公式,并找到了一个看起来像这样的代码。
if (gray)
{
gdouble input;
gdouble range;
gdouble inten;
gdouble out_light;
gdouble lightness;
/* Calculate lightness value */
lightness = GIMP_RGB_LUMINANCE (gray->r, gray->g, gray->b);
input = gimp_levels_config_input_from_color (channel, gray);
range = config->high_input[channel] - config->low_input[channel];
if (range <= 0)
goto out;
input -= config->low_input[channel];
if (input < 0)
goto out;
/* Normalize input and lightness */
inten = input / range;
out_light = lightness / range;
/* See bug 622054: picking pure black or white as gamma doesn't
* work. But we cannot compare to 0.0 or 1.0 because cpus and
* compilers are shit. If you try to check out_light using
* printf() it will give exact 0.0 or 1.0 anyway, probably
* because the generated code is different and out_light doesn't
* live in a register. That must be why the cpu/compiler mafia
* invented epsilon and defined this shit to be the programmer's
* responsibility.
*/
if (out_light <= 0.0001 || out_light >= 0.9999)
goto out;
/* Map selected color to corresponding lightness */
config->gamma[channel] = log (inten) / log (out_light);
config->gamma[channel] = CLAMP (config->gamma[channel], 0.1, 10.0);
g_object_notify (G_OBJECT (config), "gamma");
我知道 gamma 输入值应该在 0.1 到 10 之间,并且它可能是一个对数或二次函数。我不确定这是否是正确的代码片段,因为它似乎采用高、低和像素值并产生伽马值(我可能弄错了),而我想输入伽马值并获得校正后的图像。
问题是,虽然用这种方法生成的图像接近我想要的,但它与在 photoshop 或 gimp 中移动 gamma 滑块不同。
我是使用代码处理图像的业余爱好者,这是我在 StackOverFlow 上的第一个问题,所以请原谅我可能提出的任何愚蠢问题。
【问题讨论】:
-
在 Gimp 2.8 和 Gimp 2.10 的非线性模式中,这些值已经“经过伽马校正”(尽管 AFAIK 这不是真正的伽马曲线),所以要正确执行,您将不得不返回线性值,应用您的 gamma 更改,然后将 Gimp 的伪 gamma 曲线重新应用于结果。使用 Gimp 2.10 中的线性模式会更简单。
-
在docs.wand-py.org/en/0.5.0/guide/colorenhancement.html#gamma 上查看 Python Wand 的 gamma。它使用 Imagemagick。
标签: python image-processing gimp