纹理采样器 ID 未映射到纹理单元
Texture Sampler IDs not mapping to Texture Units
我正在尝试在一个模型上使用 3 个纹理。我正在使用 SOIL 加载图像并将它们绑定到纹理单元 1、2 和 3。但是由于某种原因,当我将采样器 1、2 和 3 绑定到我的着色器时,1 生成绑定到 GL_TEXTURE2
的图像而 2 和 3 生成绑定到 GL_TEXTURE3
的图像。我在这里遗漏了一些简单的东西吗?
定义:
GLenum baseTextureUnitID = GL_TEXTURE1;
GLenum filterTextureUnitID = GL_TEXTURE2;
GLenum accentTextureUnitID = GL_TEXTURE3;
GLuint baseTextureSamplerValue = 1;
GLuint filterTextureSamplerValue = 2;
GLuint accentTextureSamplerValue = 3;
正在加载图像:
baseTextureID = SOIL_load_OGL_texture(baseImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
filterTextureID = SOIL_load_OGL_texture(filterImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(filterTextureUnitID);
glBindTexture(GL_TEXTURE_2D, filterTextureID);
accentTextureID = SOIL_load_OGL_texture(accentImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(accentTextureUnitID);
glBindTexture(GL_TEXTURE_2D, accentTextureID);
获取统一位置:
baseTextureSamplerID = glGetUniformLocation(shaderProgram, "baseTex");
filterTextureSamplerID = glGetUniformLocation(shaderProgram, "filterTex");
accentTextureSamplerID = glGetUniformLocation(shaderProgram, "accentTex");
设置制服:
glUniform1i(baseTextureSamplerID, baseTextureSamplerValue);
glUniform1i(filterTextureSamplerID, filterTextureSamplerValue);
glUniform1i(accentTextureSamplerID, accentTextureSamplerValue);
现在,如果我从 baseTex 采样,我会得到滤镜图像,而 filterTex 和 accentTex 采样器会生成重音图像
我找到了解决这个问题的方法。当像我这样使用多个纹理时,你必须激活纹理单元,并在为采样器调用glUniform1i
之前再次绑定纹理。
设置制服时,正确的格式是:
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
glUniform1i(baseTextureSamplerID, baseTextureSamplerValue);
glActiveTexture(filterTextureUnitID);
glBindTexture(GL_TEXTURE_2D, filterTextureID);
glUniform1i(filterTextureSamplerID, filterTextureSamplerValue);
glActiveTexture(accentTextureUnitID);
glBindTexture(GL_TEXTURE_2D, accentTextureID);
glUniform1i(accentTextureSamplerID, accentTextureSamplerValue);
您的问题在于加载纹理时的调用顺序。 SOIL_load_OGL_texture()
将更改您当前的纹理绑定。它必须这样做,因为它需要绑定新创建的纹理,以便它可以将数据加载到其中。
想象一下您的代码序列中发生了什么:
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
此时,baseTextureID
已绑定到预期的纹理单元。但是下一行是:
filterTextureID = SOIL_load_OGL_texture(filterImageFile, ...);
在此调用中,新创建的纹理将绑定到当前纹理单元,这是您计划用于基础纹理的单元。这就是您在加载所有纹理结束时绑定错误纹理的原因。
解决这个问题很容易。只需更改图像加载代码中的调用顺序,先加载所有纹理,然后建立所有绑定:
baseTextureID = SOIL_load_OGL_texture(baseImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
filterTextureID = SOIL_load_OGL_texture(filterImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
accentTextureID = SOIL_load_OGL_texture(accentImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
glActiveTexture(filterTextureUnitID);
glBindTexture(GL_TEXTURE_2D, filterTextureID);
glActiveTexture(accentTextureUnitID);
glBindTexture(GL_TEXTURE_2D, accentTextureID);
我正在尝试在一个模型上使用 3 个纹理。我正在使用 SOIL 加载图像并将它们绑定到纹理单元 1、2 和 3。但是由于某种原因,当我将采样器 1、2 和 3 绑定到我的着色器时,1 生成绑定到 GL_TEXTURE2
的图像而 2 和 3 生成绑定到 GL_TEXTURE3
的图像。我在这里遗漏了一些简单的东西吗?
定义:
GLenum baseTextureUnitID = GL_TEXTURE1;
GLenum filterTextureUnitID = GL_TEXTURE2;
GLenum accentTextureUnitID = GL_TEXTURE3;
GLuint baseTextureSamplerValue = 1;
GLuint filterTextureSamplerValue = 2;
GLuint accentTextureSamplerValue = 3;
正在加载图像:
baseTextureID = SOIL_load_OGL_texture(baseImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
filterTextureID = SOIL_load_OGL_texture(filterImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(filterTextureUnitID);
glBindTexture(GL_TEXTURE_2D, filterTextureID);
accentTextureID = SOIL_load_OGL_texture(accentImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(accentTextureUnitID);
glBindTexture(GL_TEXTURE_2D, accentTextureID);
获取统一位置:
baseTextureSamplerID = glGetUniformLocation(shaderProgram, "baseTex");
filterTextureSamplerID = glGetUniformLocation(shaderProgram, "filterTex");
accentTextureSamplerID = glGetUniformLocation(shaderProgram, "accentTex");
设置制服:
glUniform1i(baseTextureSamplerID, baseTextureSamplerValue);
glUniform1i(filterTextureSamplerID, filterTextureSamplerValue);
glUniform1i(accentTextureSamplerID, accentTextureSamplerValue);
现在,如果我从 baseTex 采样,我会得到滤镜图像,而 filterTex 和 accentTex 采样器会生成重音图像
我找到了解决这个问题的方法。当像我这样使用多个纹理时,你必须激活纹理单元,并在为采样器调用glUniform1i
之前再次绑定纹理。
设置制服时,正确的格式是:
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
glUniform1i(baseTextureSamplerID, baseTextureSamplerValue);
glActiveTexture(filterTextureUnitID);
glBindTexture(GL_TEXTURE_2D, filterTextureID);
glUniform1i(filterTextureSamplerID, filterTextureSamplerValue);
glActiveTexture(accentTextureUnitID);
glBindTexture(GL_TEXTURE_2D, accentTextureID);
glUniform1i(accentTextureSamplerID, accentTextureSamplerValue);
您的问题在于加载纹理时的调用顺序。 SOIL_load_OGL_texture()
将更改您当前的纹理绑定。它必须这样做,因为它需要绑定新创建的纹理,以便它可以将数据加载到其中。
想象一下您的代码序列中发生了什么:
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
此时,baseTextureID
已绑定到预期的纹理单元。但是下一行是:
filterTextureID = SOIL_load_OGL_texture(filterImageFile, ...);
在此调用中,新创建的纹理将绑定到当前纹理单元,这是您计划用于基础纹理的单元。这就是您在加载所有纹理结束时绑定错误纹理的原因。
解决这个问题很容易。只需更改图像加载代码中的调用顺序,先加载所有纹理,然后建立所有绑定:
baseTextureID = SOIL_load_OGL_texture(baseImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
filterTextureID = SOIL_load_OGL_texture(filterImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
accentTextureID = SOIL_load_OGL_texture(accentImageFile,
SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_INVERT_Y);
glActiveTexture(baseTextureUnitID);
glBindTexture(GL_TEXTURE_2D, baseTextureID);
glActiveTexture(filterTextureUnitID);
glBindTexture(GL_TEXTURE_2D, filterTextureID);
glActiveTexture(accentTextureUnitID);
glBindTexture(GL_TEXTURE_2D, accentTextureID);