OpenGL如何使用长宽非2次方的纹理

也许在某些显卡上面,直接用glTexImage2D是可以使用非2次方纹理的。但是在我的机子上,直接用出现运行错误了。有没有办法让我们的程序同时支持2次方纹理和非二次方纹理了,并且我们还不需要改变纹理坐标了。
有,我们可以判断纹理的宽和高是不是都为2次方的。如果都是,那么直接使用就行了。如果不是,我们先用glTexImage2D申请2次方的纹理,然后用glTexSubImage2D把我们的数据放进去,再计算纹理坐标的变化因子,最后用glMatrixMode进入纹理堆栈操作,用glScaled设置坐标变化因子,这一切做完之后就可以按照非二次方纹理使用了。
下面提供部分代码,大致可以看出操作方法。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
if (m_nBytesPerPixel == 3)
{
nFormat = GL_BGR_EXT;
}
else if (m_nBytesPerPixel == 4)
{
nFormat = GL_BGRA_EXT;//bitmap内部数据是bgra格式,所以输入格式必须变化下
}

if (nWidthPowerOfTwo == m_nWidth nHeightPowerOfTwo == m_nHeight)
{
//输出格式必须是GL_RGB,写成GL_BGR_EXT会出现空白
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, nWidthPowerOfTwo, nHeightPowerOfTwo,
0, nFormat, GL_UNSIGNED_BYTE, m_byData);
}
else
{
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, nWidthPowerOfTwo, nHeightPowerOfTwo,
0, nFormat, GL_UNSIGNED_BYTE, NULL);
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, m_nWidth, m_nHeight,
nFormat, GL_UNSIGNED_BYTE, m_byData);
fTexScaleX = 1.0 * m_nWidth / nWidthPowerOfTwo;
fTexScaleY = 1.0 * m_nHeight / nHeightPowerOfTwo;
//设置纹理堆栈
glMatrixMode(GL_TEXTURE);
glLoadIdentity();
glScaled(fTexScaleX, fTexScaleY, 1.0);
}