Opengl es 片段着色器如何使用先前渲染帧的颜色值?

Opengl es 片段着色器如何使用先前渲染帧的颜色值?,opengl-es,glsl,shader,opengl-es-2.0,fragment-shader,Opengl Es,Glsl,Shader,Opengl Es 2.0,Fragment Shader,我正在学习在OpenGL ES中使用着色器 例如:下面是我的游乐场片段着色器,它采用当前视频帧并使其灰度化: varying highp vec2 textureCoordinate; uniform sampler2D videoFrame; void main() { highp vec4 theColor = texture2D(videoFrame, textureCoordinate); highp float avrg = (theColor[0] + theCo

我正在学习在OpenGL ES中使用着色器

例如:下面是我的游乐场片段着色器,它采用当前视频帧并使其灰度化:

varying highp vec2 textureCoordinate;

uniform sampler2D videoFrame;

void main() {
    highp vec4 theColor = texture2D(videoFrame, textureCoordinate);
    highp float avrg = (theColor[0] + theColor[1] + theColor[2]) / 3.0;
    theColor[0] = avrg; // r
    theColor[1] = avrg; // g
    theColor[2] = avrg; // b
    gl_FragColor = theColor;
}
颜色表示当前像素。在同一个坐标下也可以访问上一个像素,这会很酷

出于好奇,我想将当前像素的颜色与上一渲染帧中像素的颜色相加或相乘

我如何保持前面的像素,并将它们传递到片段着色器中,以便对它们进行处理


注意:它是iPhone上的OpenGL ES 2.0。

您需要使用帧缓冲区对象FBO将前一帧渲染为纹理,然后可以在片段着色器中读取此纹理。

您需要使用帧缓冲区对象FBO将前一帧渲染为纹理,然后可以在片段着色器中读取此纹理。

Damon所指的点内在函数是数学点积的代码实现。我对OpenGL不是非常熟悉,所以我不确定确切的函数调用是什么,但从数学上讲,点积是这样的:

给定向量a和向量b,“点”积a“点”b生成标量结果c:

就这一点而言,大多数现代图形硬件和CPU都能够一次性执行此类操作。在您的特殊情况下,您可以使用点积轻松计算平均值,如下所示:

highp vec4 = (1/3, 1/3, 1/3, 0) //or zero
由于某种原因,我总是得到齐次向量和矩阵中的第四分量

highp float avg = theColor DOT vec4
这将使颜色的每个分量乘以1/3,第四分量乘以0,然后将它们相加。

Damon所指的点固有函数是数学点积的代码实现。我对OpenGL不是非常熟悉,所以我不确定确切的函数调用是什么,但从数学上讲,点积是这样的:

给定向量a和向量b,“点”积a“点”b生成标量结果c:

就这一点而言,大多数现代图形硬件和CPU都能够一次性执行此类操作。在您的特殊情况下,您可以使用点积轻松计算平均值,如下所示:

highp vec4 = (1/3, 1/3, 1/3, 0) //or zero
由于某种原因,我总是得到齐次向量和矩阵中的第四分量

highp float avg = theColor DOT vec4

这将使颜色的每个分量乘以1/3,第四个分量乘以0,然后将它们相加。

正如Matias Valdenegro在下面所述,您需要渲染到FBO。但是,当您这样做并使用着色器渲染时,它将非常明亮,您应该除以3而不是2以获得正确的平均值。转换为灰度时更常用的方法是使用颜色分量的加权和。看看什么重量是好的。谢谢你指出这一点。这是我的代码中的一个输入错误。而且你不应该在一开始就加和除。您应该使用dot instrinsic函数,它映射到一个指令,该指令一步完成,速度更快。我的意思是dot thecolor.xyz,vec30.3333。点积将两个向量相乘,然后将分量相加。这正是你正在做的,除了它是一条单周期指令。请参阅@Damon:它可能是一条单周期指令。它也可以是3条指令,一条向量相乘,两条相依加法。然而,不管它是什么,它仍将优于他的代码。或者在最坏的情况下,它不会变慢,所以他仍然应该这样做。正如Matias Valdenegro在下面所述,您需要向FBO渲染。但是,当您这样做并使用着色器渲染时,它将非常明亮,您应该除以3而不是2以获得正确的平均值。转换为灰度时更常用的方法是使用颜色分量的加权和。看看什么重量是好的。谢谢你指出这一点。这是我的代码中的一个输入错误。而且你不应该在一开始就加和除。您应该使用dot instrinsic函数,它映射到一个指令,该指令一步完成,速度更快。我的意思是dot thecolor.xyz,vec30.3333。点积将两个向量相乘,然后将分量相加。这正是你正在做的,除了它是一条单周期指令。请参阅@Damon:它可能是一条单周期指令。它也可以是3条指令,一条向量相乘,两条相依加法。然而,不管它是什么,它仍将优于他的代码。或者,最坏的情况下,它不会慢下来,所以他仍然应该这样做。你能举一些例子或指出一些涵盖这个主题的好资源吗?你能举一些例子或指出一些涵盖这个主题的好资源吗?