现在的位置: 首页 > 综合 > 正文

从图片加载纹理-使用glut工具

2017年12月11日 ⁄ 综合 ⁄ 共 3222字 ⁄ 字号 评论关闭
#include <Windows.h>
#include <gl/GLU.h>
#include <gl/glaux.h>
#include <GL/glut.h>
#include <stdio.h>

static GLuint texName;

AUX_RGBImageRec * CreateTextureFromBmp()
{
	FILE *File=NULL;
	const char *Filename= "hehua.bmp";
	File=fopen(Filename,"r");
	if (!File)
		return 0;
	fclose(File);
	return auxDIBImageLoad(Filename);
	
}
void init(void)
{
	glClearColor (0.0, 0.0, 0.0, 0.0);
	glShadeModel(GL_FLAT);
	glEnable(GL_DEPTH_TEST);

	AUX_RGBImageRec * imageRec = CreateTextureFromBmp();
	if (!imageRec)
		exit(EXIT_FAILURE);
	
	glPixelStorei(GL_UNPACK_ALIGNMENT, 1);

	glGenTextures(1, &texName);
	glBindTexture(GL_TEXTURE_2D, texName);

	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_MAG_FILTER, GL_NEAREST);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, imageRec->sizeX, imageRec->sizeX, 
							0, GL_RGB, GL_UNSIGNED_BYTE, imageRec->data);

}
void display(void)
{
	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
	glEnable(GL_TEXTURE_2D);
	glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
	glBindTexture(GL_TEXTURE_2D, texName);

	glBegin(GL_QUADS);
	glTexCoord2f(0.0, 0.0); glVertex3f(-2.0, -1.0, 0.0);
	glTexCoord2f(0.0, 1.0); glVertex3f(-2.0, 1.0, 0.0);
	glTexCoord2f(1.0, 1.0); glVertex3f(0.0, 1.0, 0.0);
	glTexCoord2f(1.0, 0.0); glVertex3f(0.0, -1.0, 0.0);

	glTexCoord2f(0.0, 0.0); glVertex3f(1.0, -1.0, 0.0);
	glTexCoord2f(0.0, 1.0); glVertex3f(1.0, 1.0, 0.0);
	glTexCoord2f(1.0, 1.0); glVertex3f(2.41421, 1.0, -1.41421);
	glTexCoord2f(1.0, 0.0); glVertex3f(2.41421, -1.0, -1.41421);
	glEnd();
	glFlush();
	glDisable(GL_TEXTURE_2D);
}

void reshape(int w, int h)
{
	glViewport(0, 0, (GLsizei) w, (GLsizei) h);
	glMatrixMode(GL_PROJECTION);
	glLoadIdentity();
	gluPerspective(60.0, (GLfloat) w/(GLfloat) h, 1.0, 30.0);
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();
	glTranslatef(0.0, 0.0, -3.6);
}
int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB | GLUT_DEPTH);
	glutInitWindowSize(250, 250);
	glutInitWindowPosition(100, 100);
	glutCreateWindow(argv[0]);
	init();
	glutDisplayFunc(display);
	glutReshapeFunc(reshape);
	glutMainLoop();
	return 0; 
}

程序截图

将GL_NEAREST改成GL_LINEAR,效图如下图。左边为NEARST,右边为LINEAR。

可见使用后者,图片锯齿能少很多。

函数解释

void glTexImage2D(	GLenum  	target,
 	GLint  	level,
 	GLint  	internalFormat,
 	GLsizei  	width,
 	GLsizei  	height,
 	GLint  	border,
 	GLenum  	format,
 	GLenum  	type,
 	const GLvoid *  	data);

参数data

此函数从data加载纹理数据,生成一个纹理。最近一次绑定的纹理ID指向了这个纹理。在此例中即是纹理ID texName指向由glTexImage2D生成的纹理。OpenGL是一个状态机,学习OpenGL时要时刻记着这一点。data的来源可以是内存中的一个数组,也可以是一幅位图的像素部分。如果使用的是位图,来填充data,那么可能会浪费一些空间。因为位图可以大幅压缩。所以可以internalFormat来指定压缩纹理。

参数level

提供纹理图像的数量,在使用多重细节时,使用此值。不使用多重细节时,值为0。

internalFormat 指定纹理的颜色格式。GL_RGBA  颜色格式为(红,绿,蓝,透明度),GL_RGB 颜色格式为(红,绿,蓝)。也可以使用压缩纹理。GL_COMPRESSED_*枚举值。具体参数含义可参看如下链接
参数含义

参数表示纹理图像的宽度和高度。参数表示边框的宽度,它只能是0或者是1.width和height的值都必须是2^m+2b,其中m是非负的整数。height可以使用不同的m值。b是border值。纹理图像的最大值取决于OpenGl实现,但它至少是64x64如果有边框至少是66x66。另外,OpenGL2.0取消了纹理图像必须是2的整数次方的限制。

format

指定了像素格式。可使用的值有GL_COLOR_INDEX, GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA, GL_RGB, GL_BGR, GL_RGBA等。

它与internalFormat的区别.internalFormat 可以指定R、G、B各元素的大小。如R可以是3,4,58,...Bit。

type

指定像素的数据类型。可以是GL_FLOAT,GL_UNSIGNED_BYTE等。对于位图来说,一定是GL_UNSIGNED_BYTE.
data

指定图像所在内存的指针。

GL_TEXTURE_WRAP_S GL_TEXTURE_WRAP_T

其中S、T是纹理空间内的两个参数坐标。如下图所示

GL_REPEAT含义:当纹理空间与贴图所用的空间不一致时,重复纹理。glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);即在s向重复,如下图所示

抱歉!评论已关闭.