【发布时间】:2015-08-11 09:21:50
【问题描述】:
我创建了这个简单的程序。它创建了两个纹理,一个 2D 和一个 1D 纹理绑定它们,等等。
我可以毫无问题地在我的着色器程序中对 2D 纹理进行采样和绘制。尝试从 1D 纹理中采样和绘制,四边形变成黑色。
如果我不在 if..else.. 语句中的片段着色器中使用 1D 纹理样本,则所有内容都会呈现为黑白。尝试使用示例,它只呈现黑屏。
如果我这样做:
if (i == maxIterations)
{
tcolor = vec4(0.0f, 0.0f, 0.0f, 1.0f);
}
else if(i <= 10)
{
tcolor = vec4(1.0f, 0.0f, 0.0f, 0.0f);
} else if ( i >= 11)
{
tcolor = vec4(1.0f, 1.0f, 0.0f, 0.0f);
}
它也有效.....如何对 1D 纹理进行采样?
源代码如下
glGenTextures(1, &colorTextureID);
glBindTexture(GL_TEXTURE_2D, colorTextureID);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexImage2D(GL_TEXTURE_2D, 0, Mode, colorSurface->w, colorSurface->h, 0, Mode, GL_UNSIGNED_BYTE, colorSurface->pixels);
glGenerateMipmap(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, 0);
free(colorSurface);
//mandi 1d texture
glGenTextures(1, &mandiTextureID);
glBindTexture(GL_TEXTURE_1D, mandiTextureID);
glTexParameteri(GL_TEXTURE_1D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_1D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_1D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_1D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexImage1D(GL_TEXTURE_1D, 0, Mode1, mandiSurface->w, 0, Mode1, GL_UNSIGNED_BYTE, mandiSurface->pixels);
glBindTexture(GL_TEXTURE_1D, 0);
free(mandiSurface);
//render
void render()
{
glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
//glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
glUseProgram(sp);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, colorTextureID);//ourTexture
ourTexture = getUniformLocation(sp, "ourTexture");
glUniform1i(ourTexture, 0);
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_1D, mandiTextureID);//mandiTexture
mandiTexture = getUniformLocation(sp, "mandiTexture");
glUniform1i(mandiTexture, 1);
glBindVertexArray(verticesBuffer);
viewMat = getUniformLocation(sp, "viewMat");
modelMat = getUniformLocation(sp, "modelMat");
projMat = getUniformLocation(sp, "projMat");
maxIterLoc = getUniformLocation(sp, "maxIterations");
centerLoc = getUniformLocation(sp, "center");
scaleLoc = getUniformLocation(sp, "scale");
glUniformMatrix4fv(viewMat, 1, GL_FALSE, vm.m);
glUniformMatrix4fv(projMat, 1, GL_FALSE, opm.m);
glUniformMatrix4fv(modelMat, 1, GL_FALSE, tm.m);
glUniform1i(maxIterLoc, 20);
glUniform1f(scaleLoc, scale);
glUniform2f(centerLoc, cx, cy);
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0);
glBindVertexArray(0);
}
顶点着色器
#version 330 core
layout (location = 0) in vec3 position;
layout (location = 1) in vec3 icolor;
layout (location = 2) in vec2 vTexCoord;
uniform mat4 modelMat;
uniform mat4 viewMat;
uniform mat4 projMat;
out vec4 fcolor;
out vec2 fTexCoord;
out vec2 fCoord;
void main()
{
gl_Position = projMat * viewMat * modelMat * vec4(position, 1.0);
fCoord = vec2(position);
fTexCoord = vTexCoord;
fcolor = vec4(icolor, 1.0f);
}
片段着色器
#version 330 core
in vec4 fcolor;
in vec2 fTexCoord;
in vec2 fCoord;
uniform int maxIterations;
uniform vec2 center;
uniform float scale;
uniform sampler2D ourTexture;
uniform sampler1D mandiTexture;
out vec4 color;
void main()
{
vec2 c, z;
c.x = 1.3333 * (fCoord.x - 0.5) - center.x;
c.y = (fCoord.y - 0.5) - center.y;
int i;
z = c;
for(i=0; i<maxIterations; i++) {
float x = (z.x * z.x - z.y * z.y) + c.x;
float y = (z.y * z.x + z.x * z.y) + c.y;
if((x * x + y * y) > 4.0) break;
z.x = x;
z.y = y;
}
vec4 tcolor;
if (i == maxIterations)
{
tcolor = vec4(0.0f, 0.0f, 0.0f, 1.0f);
}
else
{
/* tcolor = vec4(1.0f, 1.0f, 1.0f, 1.0f); this works but only renders black and white */
tcolor = texture(mandiTexture, float(i)).rgba; /* only renders black screen */
}
/* color = texture(ourTexture, fTexCoord) * fcolor; //this also works */
color = tcolor;
}
【问题讨论】:
-
纹理坐标在 [0,1] 范围内
-
@Olaf 顶点和片段着色器。
-
这不能回答我的问题。
-
@dari 这是答案,但对于新的图形程序员来说,它可能真的很神秘。
-
@Olaf:这里有两种不同的语言:C 和 GLSL。在这个问题中唯一具有主要功能的代码是 GLSL。
void main (void)在 GLSL 中有效,其大部分语法看起来与 C 相同,因此您可能很容易混淆两者。