【问题标题】:OpenGL GLSL: How to implement the concept of gradient map in photoshop using fragment shader?OpenGL GLSL:如何使用片段着色器在 Photoshop 中实现渐变图的概念?
【发布时间】:2015-08-29 04:32:44
【问题描述】:

这可能不是 stackoverflow 的完美问题,但我已经在 stackexchange 的图形设计网络中问过这个问题,但没有得到任何答案,所以在这里发布。 我正在尝试使用 glsl 片段着色器以编程方式实现 Photoshop 的渐变图。考虑下面显示的渐变图,其中所有白色分量都被绿色替换,黑色被蓝色替换。对于其他颜色成分,Photoshop 根据蓝色和绿色之间的线性渐变进行计算。我知道这个计算背后有一个数学。有谁知道找到特定输入颜色值的输出颜色的公式吗?

【问题讨论】:

    标签: image-processing glsl photoshop


    【解决方案1】:

    根据图像和描述,看起来这是将图像的原始灰度值映射到蓝绿色渐变。

    有多种方法可以将颜色转换为灰度,具体取决于所使用的颜色系统。许多简单的只是RGB分量的加权和。例如,一个广泛使用的将 RGB 转换为亮度的公式 (Y) 是:

    Y = 0.299 * R + 0.587 * G + 0.114 * B
    

    有关该主题和所有不同选项的更多背景信息,请参阅Grayscale wikipedia page

    然后你可以使用以灰度值作为参数的蓝色和绿色的线性插值。无论如何,这方面的数学计算很容易,但 GLSL 甚至为此目的内置了一个 mix() 函数。

    一些可能的 GLSL 代码片段,基于使用纹理坐标 TexCoord 从纹理 Tex 读取原始颜色:

    uniform sampler2D Tex;
    in vec2 TexCoord;
    out vec4 FragColor;
    ...
        vec4 origColor = texture(Tex, TexCoord);
        float grayscaleValue = dot(origColor.rgb, vec3(0.299, 0.587, 0.114));
        FragColor = mix(vec4(0.0, 0.0, 1.0, 1.0), vec4(0.0, 1.0, 0.0, 1.0), grayscaleValue);
    

    在此代码中,vec3(0.299, 0.587, 0.114) 包含从 RGB 到上述灰度(亮度)公式的系数。 mix() 函数的前两个参数是渐变的开始和结束颜色:

    • 蓝色:vec4(0.0, 0.0, 1.0, 1.0)
    • 绿色:vec4(0.0, 1.0, 0.0, 1.0)

    请注意,在 RGB 空间中两种颜色之间的简单线性插值并不理想,尤其是在颜色非常不同的情况下。通过在 HLS 等不同的色彩空间中操作,您可以使其更精细,并有可能获得更好的质量。

    另一个可能改善视觉外观的选项是使用两种以上的颜色来指定渐变。例如,您可以将蓝色指定为亮度 0.0,将青色指定为亮度 0.5,将绿色指定为亮度 1.0。它比上面的 GLSL 代码需要更多的逻辑,但它只是相同原理的扩展。

    【讨论】:

    • 效果很好,但需要澄清一点。这是用于蓝绿色渐变,但如果我想要不同的颜色渐变怎么办。你是怎么得到vec3(0.299, 0.587, 0.114)这个值的?
    • 我添加了更多解释。这些数字已经在答案中进一步解释,在将 RGB 转换为灰度的公式中。
    • 谢谢先生。我现在明白了..现在我对 RGB 很好,因为我不知道 HLS.. 开始阅读有关图像处理的内容。您是否写过任何关于此类事情的博客,或者您可以向我推荐任何此类博客或书籍以供阅读?
    • 我通过使用 Photoshop 渐变图和此处给出的公式处理简单图像进行了一些测试,但它们不匹配。例如,如果您将白色到黑色的线性渐变作为起始图像,并在 Photoshop 中应用蓝色到绿色的渐变映射,黑色仍然是黑色,白色仍然是白色,并且中间的每个灰色阴影都会转换为蓝色和蓝色之间的渐变。绿色。这背后的数学原理是什么?
    • 请注意,启用“平滑度”后,渐变实际上不是线性的。为了使 Photoshop 渐变与着色器效果相匹配,您需要使用平滑度为 0% 的渐变或找出平滑算法。
    【解决方案2】:

    我在 Photoshop 中尝试了不同的渐变贴图,我的设置接缝与 OP 的设置接缝不同。在我的例子中,将渐变映射滤镜应用于黑白渐变图像显示黑色保持黑色,白色保持白色。之间的每一种灰色阴影都被绿色和蓝色之间的某种颜色所取代。如果将灰色阴影直接映射到线性渐变,黑色和白色将消失。 Photoshop 渐变贴图接缝以保留原始颜色的发光。

    这是我为我的设置匹配 Photoshop 渐变映射的公式。

    给定(Rg1,Gg1,Bg1)(Rg2,Gg2,Bg2) 渐变值,(Ro,Go,Bo) 原始颜色值和(Rr,Gr,Br) 结果颜色。

    1. 在HSL空间中获取要转换的颜色:

    (Ho, So, Lo) = rgb2hsl(Ro, Go, Bo)

    1. 计算 Lo 值的梯度线性插值(以 RGB 为单位):

    (Rt,Gt,Bt) = (Rg1+[Rg2-Rg1]*Lo, Gg1+[Gg2-Gg1]*Lo), Bg1+[Bg2-Bg1]*Lo)

    1. 在 HSL 空间中获取此值:

    (Ht,St,Lt) = rgb2hsl(Rt, Gt, Bt)

    1. 保留原始颜色的 L 值

    (Rr,Gr,Br) = hsl2rgb(Ht,St,Lo)

    rgb2hsl 和 hsl2rgb 代码示例可以在这里找到:HSL to RGB color conversion

    【讨论】:

    • 非常感谢。我会在java中尝试一下,然后告诉你它是怎么回事。
    猜你喜欢
    • 1970-01-01
    • 2023-03-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-07-21
    • 2016-01-08
    • 1970-01-01
    • 2017-04-12
    相关资源
    最近更新 更多