我想使用opengl及其着色器在剪辑工作室上模拟"辉光躲避"效果。所以我发现下面的方程式就是"辉光躲避"的工作原理。
final.rgb = dest.rgb / (1 - source.rgb)
然后我想出了两种实际的方法,但这两种方法似乎都不起作用。
第一个是在着色器中计算1 / (1 - source.rgb)
,并使用glBlendfunc(GL_ZERO, GL_SRC_COLOR)
或glBlendfunc(GL_DST_COLOR, GL_ZERO)
进行乘法混合。
但正如khronos-page所说,所有的比例因子都在0到1之间。这意味着我不能把数字乘以1。所以我不能用这个方法,因为大多数情况下都超过1。
第二种方法是使用glReadPixel()
引入背景纹理,然后计算着色器中的所有内容,然后使用glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA)
进行相加混合。
不管我能得到什么结果,glReadPixel()
本身即使使用30 x 30的texel区域也会花费太多时间。所以我不能用这个方法。
我想知道是否还有其他方法可以像光晕躲避混合模式那样获得结果。
使用EXT_shader_framebuffer_fetch扩展,可以读取帧缓冲区中的值:
此扩展提供了一种机制,片段着色器可以通过该机制读取现有的帧缓冲区数据作为输入。这可以用于实现合成操作,而这些操作对于固定函数混合来说是不方便或不可能的。它还可以用于将函数应用于帧缓冲区颜色,方法是编写一个着色器,该着色器使用现有帧缓冲区的颜色作为其唯一输入。
该扩展可用于dektopOpenGL和OpenGL ES。必须启用OpenGL扩展(请参阅核心语言(GLSL(-扩展(。片段颜色可以通过内置变量gl_LastFragData
来检索。例如:
#version 400
#extension GL_EXT_shader_framebuffer_fetch : require
out vec4 fragColor;
# [...]
void main
{
# [...]
fragColor = vec4(gl_LastFragData[0].rgb / (1.0 - source.rgb), 1.0);
}