简体   繁体   English

GLSL 片段着色器输出类型

[英]GLSL fragment shader output type

Suppose I'm having a problem like this: now I have a framebuffer and a texture only contains one color component(for example, GL_RED) has already binded to it.假设我遇到了这样的问题:现在我有一个帧缓冲区,并且一个纹理只包含一个已经绑定到它的颜色分量(例如,GL_RED)。 What will fragment shader looks like?片段着色器会是什么样子? I guess the answer is:我想答案是:

... out float ex_color; ...出浮动ex_color;

ex_color = ...; ex_color = ...;

Here comes my question : will the shader automatically detect the format of framebuffer and write values to it?我的问题来了:着色器会自动检测帧缓冲区的格式并将值写入其中吗? What if fragment shader outputs float values but framebuffer format is GL_RGBA?如果片段着色器输出浮点值但帧缓冲区格式为 GL_RGBA 怎么办?

By the way, what is the correct approach to create a texture only has one component?顺便说一句,创建只有一个组件的纹理的正确方法是什么? I read examples from g-truc which has a sample like this:我从 g-truc 中阅读了示例,其中有这样的示例:

glTexImage2D(GL_TEXTURE_2D, 0, GL_RED,GLsizei(Texture.dimensions().x), GLsizei(Texture.dimensions().y), 0,GL_RGB, GL_UNSIGNED_BYTE, 0); glTexImage2D(GL_TEXTURE_2D, 0, GL_RED,GLsizei(Texture.dimensions().x), GLsizei(Texture.dimensions().y), 0,GL_RGB, GL_UNSIGNED_BYTE, 0);

What's the meaning of assign GL_RGB as pixel data format?将 GL_RGB 指定为像素数据格式是什么意思?

Just like vertex shader inputs don't have to match the exact size of the data specified by glVertexAttribPointer, fragment shader outputs don't have to match the exact size of the image they're being written to.就像 顶点着色器输入不必与 glVertexAttribPointer 指定的数据的确切大小匹配一样,片段着色器输出不必与它们正在写入的图像的确切大小匹配。 If the output provides more components than the destination image format, then the extra components are ignored.如果输出提供的组件多于目标图像格式,则忽略额外的组件。 If it provides fewer, then the other components have undefined values (unlike vertex inputs, where unspecified values have well-defined values).如果它提供的较少,则其他组件具有未定义的值(与顶点输入不同,其中未指定的值具有明确定义的值)。

What's the meaning of assign GL_RGB as pixel data format?将 GL_RGB 指定为像素数据格式是什么意思?

That's the pixel transfer format .这就是像素传输格式 That describes the format of pixels you're providing to OpenGL, not the format that OpenGL will store them as.这描述了您提供给 OpenGL 的像素格式,而不是 OpenGL 将它们存储为的格式。

You should always use sized internal formats , not unsized ones like GL_RED .您应该始终使用调整大小的内部格式,而不是像GL_RED那样未调整大小的格式

For a decent explanation of the internal format and format, see:有关内部格式和格式的体面解释,请参阅:

http://opengl.org/wiki/Image_Format and http://opengl.org/sdk/docs/man/xhtml/glTexImage2D.xml . http://opengl.org/wiki/Image_Formathttp://opengl.org/sdk/docs/man/xhtml/glTexImage2D.xml

You basically want GL_RED for format and likely want GL_R8 (unsigned normalized 8-bit fixed-point) for the internal format.您基本上需要 GL_RED 作为格式,并且可能需要 GL_R8(无符号标准化 8 位定点)作为内部格式。

A long time ago, luminance textures were the norm for single-channel, but that is a deprecated format in modern GL and red is now the logical "drawable" texture format for single-channels, just as red/green is the most logical format for two-channel.很久以前,亮度纹理是单通道的规范,但这是现代 GL 中不推荐使用的格式,红色现在是单通道的逻辑“可绘制”纹理格式,就像红色/绿色是最合乎逻辑的格式对于双通道。

As for your shader, there are rules for component expansion defined by the core specification.至于你的着色器,核心规范定义了组件扩展规则。 If you have a texture with 1 channel as an input, but sample it as a vec4, it will be equivalent to: vec4 (RED, 0.0, 0.0, 1.0).如果您有一个带有 1 个通道的纹理作为输入,但将其采样为 vec4,则它等效于:vec4 (RED, 0.0, 0.0, 1.0)。

Writing to the texture is a little bit different.写入纹理有点不同。

From the OpenGL 4.4 Spec, section 15.2 (Shader Execution), pp. 441 -- http://www.opengl.org/registry/doc/glspec44.core.pdf来自 OpenGL 4.4 规范,第 15.2 节(着色器执行),第 441 页——http: //www.opengl.org/registry/doc/glspec44.core.pdf

When a fragment shader terminates, the value of each active user-defined output variable is written to components of the fragment color output to which it is bound. The set of fragment color components written is determined according to the variable's data type and component index binding, using the mappings in table 11.1 [pp. 341].

By default, if your fragment shader's output is a float, it is going to write to the x (red) component of your texture.默认情况下,如果片段着色器的输出是浮点数,它将写入纹理的 x(红色)分量。 You could use a layout qualifier (eg layout (component=1) out float color; ) to specify that it should write to y (green), z (blue) or w (alpha) (assuming you have an RGBA texture).您可以使用布局限定符(例如layout (component=1) out float color; )来指定它应该写入 y(绿色)、z(蓝色)或 w(alpha)(假设您有一个 RGBA 纹理)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM