我正在尝试使用RGBA值加载纹理但是alpha值似乎只是使纹理更白,而不是调整透明度。我已经听说过3D场景的这个问题,但我只是使用OpenGL for 2D。无论如何我可以解决这个问题吗?
我正在用
初始化OpenGLglViewport(0, 0, winWidth, winHeight);
glDisable(GL_TEXTURE_2D);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glDisable(GL_DEPTH_TEST);
glClearColor(0, 0, 0, 0);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluOrtho2D(0, winWidth, 0, winHeight); // set origin to bottom left corner
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glColor3f(1, 1, 1);
截图: 褪色的图像应该是半透明的。黑色比特应该是完全透明的。正如你所看到的,背后有一个图像没有显示出来。
生成该纹理的代码相当冗长,所以我将描述我所做的。它是一个40 * 30 * 4的unsigned char类型数组。每4个字符设置为128(应该是50%透明,对吧?)。
然后我将它传递给这个函数,将数据加载到纹理中:
void Texture::Load(unsigned char* data, GLenum format) {
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, _texID);
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, _w, _h, format, GL_UNSIGNED_BYTE, data);
glDisable(GL_TEXTURE_2D);
}
而且......我想我刚刚发现了这个问题。用这段代码初始化全尺寸纹理:
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, _texID);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, tw, th, 0, GL_LUMINANCE, GL_UNSIGNED_BYTE, NULL);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glDisable(GL_TEXTURE_2D);
但我觉得glTexImage2D也需要GL_RGBA吗?我不能使用两种不同的内部格式?或者至少不是不同大小的(3字节对4字节)? GL_BGR即使在初始化时也能正常工作......
答案 0 :(得分:4)
为了别人的利益,我在这里发布我的解决方案。
问题是虽然我的加载功能是正确的,
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, _w, _h, GL_RGBA, GL_UNSIGNED_BYTE, data);
我正在将GL_RGB传递给此函数
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, tw, th, 0, GL_LUMINANCE, GL_UNSIGNED_BYTE, NULL);
哪个还需要指定正确的字节数(四个)。根据我的理解,你不能为SubImage使用不同的字节数,虽然我认为可以使用不同的格式,如果它具有相同的字节数(即混合GL_RGB
并且GL_BGA
没问题,但不是GL_RGB
和GL_RGBA
)。
答案 1 :(得分:1)
你的场景中是否有重叠的原语?
你知道你正在调用glColor的3参数版本,它将alpha设置为1.0,对吗?
如果您可以发布截图,或者描述当您绘制具有相同颜色和不同alpha的两个基元时会发生什么,这可能会有所帮助。事实上,任何解决问题的代码都可以提供帮助。
编辑:
我认为使用带有GL_RGB
的TexImage(对于 internalformat ,第3个参数)会创建一个3分量纹理,没有隐式初始化为1的alpha或alpha值,无论是什么你提供什么样的像素数据。
GL_BGR
不是此参数的有效值,也许它会欺骗您的实现使用完整的4字节内部格式? (或者是一个2字节的,根据GL_LUMINANCE_ALPHA
)或者你的意思是将GL_BGR
传递给你的Texture :: Load()函数,它与传递GL_RGB
真的不同吗?
答案 2 :(得分:0)
我认为这应该有用,但它假设图像有alpha通道。如果您尝试加载没有Alpha通道的图像,您将收到异常,否则您的应用程序可能会崩溃。对于非Alpha通道图像,在设置GL_RGB
之前,在第二个参数上使用GL_RGBA
而不是GL_UNSIGNED_BYTE
。
void Texture::Load(unsigned char* data) {
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, _texID);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, tw, th, 0, GL_RGBA, GL_UNSIGNED_BYTE, data);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glDisable(GL_TEXTURE_2D);
}