`
tiankefeng0520
  • 浏览: 143107 次
  • 性别: Icon_minigender_1
  • 来自: 长春
社区版块
存档分类
最新评论

OpenGL学习三十四:剪裁区域和TGA图像文件的加载

 
阅读更多

(此节内容对应NEHE教程第24课)

 

应用.tga文件作为纹理数据来源进行纹理贴图

 

.tga图像文件数据格式:

 

 

0~~11 头信息  
12~13 图像宽度 byte[13]*256+byte[12]
14~15 图像高度 byte[15]*256+byte[14]
16 图像每像素存储占用位(bit)数 24或32
18~end 图片数据域
数据格式为GBRA,特殊需要需要转换
图片总大小=图像宽度*图像高度*(图像每像素存储占用位(bit)数/8)

 

OpenGL可扩展性描述
glGetString(GL_RENDERER) 获取OpenGL相关信息
GL_VENDOR 销售商
GL_RENDERER OpenGL的实现组织
GL_VERSION 当前版本
GL_EXTENSIONS OpenGL扩展名

 

剪裁区域设置
glScissor函数用来设置剪裁区域,如果启用了GL_SCISSOR_TEST,绘制的内容只能在剪裁区域中显示。

glScissor(x,y,width,heigth);
glEnable(GL_SCISSOR_TEST);

 

                    应用剪裁区域                                                    未应用剪裁区域

 

#include "header.h"

int			scroll;										
int			maxtokens;										
int			swidth;										
int			sheight;										

GLuint		base;											

typedef struct												
{
	GLubyte	*imageData;										
	GLuint	bpp;										
	GLuint	width;										
	GLuint	height;											
	GLuint	texID;											
} TextureImage;												

TextureImage textures[1];								



bool LoadTGA(TextureImage *texture, char *filename)			
{    
	GLubyte		TGAheader[12]={0,0,2,0,0,0,0,0,0,0,0,0};	
	GLubyte		TGAcompare[12];								
	GLubyte		header[6];									
	GLuint		bytesPerPixel;								
	GLuint		imageSize;									
	GLuint		temp;										
	GLuint		type=GL_RGBA;								

	FILE *file = fopen(filename, "rb");						

	if(	file==NULL ||										
		fread(TGAcompare,1,sizeof(TGAcompare),file)!=sizeof(TGAcompare) ||	
		memcmp(TGAheader,TGAcompare,sizeof(TGAheader))!=0				||	
		fread(header,1,sizeof(header),file)!=sizeof(header))				
	{
		if (file == NULL)									
			return false;									
		else
		{
			fclose(file);									
			return false;									
		}
	}

	texture->width  = header[1] * 256 + header[0];			
	texture->height = header[3] * 256 + header[2];			
    
 	if(	texture->width	<=0	||								
		texture->height	<=0	||								
		(header[4]!=24 && header[4]!=32))					
	{
		fclose(file);									
		return false;									
	}

	texture->bpp	= header[4];							
	bytesPerPixel	= texture->bpp/8;						
	imageSize		= texture->width*texture->height*bytesPerPixel;	

	texture->imageData=(GLubyte *)malloc(imageSize);		

	if(	texture->imageData==NULL ||							
		fread(texture->imageData, 1, imageSize, file)!=imageSize)	
	{
		if(texture->imageData!=NULL)					
			free(texture->imageData);						

		fclose(file);										
		return false;										
	}

	for(GLuint i=0; i<int(imageSize); i+=bytesPerPixel)		
	{														
		temp=texture->imageData[i];							
		texture->imageData[i] = texture->imageData[i + 2];	
		texture->imageData[i + 2] = temp;				
	}

	fclose (file);										

	// Build A Texture From The Data
	glGenTextures(1, &texture[0].texID);				

	glBindTexture(GL_TEXTURE_2D, texture[0].texID);			
	glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);	
	glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);	
	
	if (texture[0].bpp==24)								
	{
		type=GL_RGB;									
	}

	glTexImage2D(GL_TEXTURE_2D, 0, type, texture[0].width, texture[0].height, 0, type, GL_UNSIGNED_BYTE, texture[0].imageData);

	return true;											
}

GLvoid BuildFont(GLvoid)									
{
	base=glGenLists(256);									
	glBindTexture(GL_TEXTURE_2D, textures[0].texID);	
	for (int loop1=0; loop1<256; loop1++)					
	{
		float cx=float(loop1%16)/16.0f;					
		float cy=float(loop1/16)/16.0f;					

		glNewList(base+loop1,GL_COMPILE);				
			glBegin(GL_QUADS);							
				glTexCoord2f(cx,1.0f-cy-0.0625f);		
				glVertex2d(0,16);							
				glTexCoord2f(cx+0.0625f,1.0f-cy-0.0625f);
				glVertex2i(16,16);							
				glTexCoord2f(cx+0.0625f,1.0f-cy-0.001f);
				glVertex2i(16,0);							
				glTexCoord2f(cx,1.0f-cy-0.001f);		
				glVertex2i(0,0);						
			glEnd();										
			glTranslated(14,0,0);							
		glEndList();									
	}													
}

GLvoid KillFont(GLvoid)										
{ 
	glDeleteLists(base,256);							
}

GLvoid glPrint(GLint x, GLint y, int set, const char *fmt, ...)	
{
	char		text[1024];									
	va_list		ap;											

	if (fmt == NULL)										
		return;												

	va_start(ap, fmt);										
	    vsprintf(text, fmt, ap);							
	va_end(ap);												

	if (set>1)												
	{
		set=1;												
	}

	glEnable(GL_TEXTURE_2D);								
	glLoadIdentity();										
	glTranslated(x,y,0);									
	glListBase(base-32+(128*set));							

	glScalef(1.0f,2.0f,1.0f);								

	glCallLists(strlen(text),GL_UNSIGNED_BYTE, text);		
	glDisable(GL_TEXTURE_2D);								
}

void ReSizeGLScene(GLsizei width, GLsizei height)			
{
	swidth=width;											
	sheight=height;											
	if (height==0)										
	{
		height=1;										
	}
	glViewport(0,0,width,height);							
	glMatrixMode(GL_PROJECTION);						
	glLoadIdentity();										
	glOrtho(0.0f,640,480,0.0f,-1.0f,1.0f);				
	glMatrixMode(GL_MODELVIEW);								
	glLoadIdentity();										
}

int InitGL(void)											
{
	if (!LoadTGA(&textures[0],"Data/Font.TGA"))				
	{
		return false;										
	}

	BuildFont();										

	glShadeModel(GL_SMOOTH);								
	glClearColor(0.0f, 0.0f, 0.0f, 0.5f);				
	glClearDepth(1.0f);										
	glBindTexture(GL_TEXTURE_2D, textures[0].texID);		

	return TRUE;											
}

void DrawGLScene(void)									
{
	char	*token;											
	int		cnt=0;											

	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);		

	glColor3f(1.0f,0.5f,0.5f);							
	glPrint(50,16,1,"Renderer");						
	glPrint(80,48,1,"Vendor");								
	glPrint(66,80,1,"Version");							

	glColor3f(1.0f,0.7f,0.4f);								
	glPrint(200,16,1,(char *)glGetString(GL_RENDERER));		
	glPrint(200,48,1,(char *)glGetString(GL_VENDOR));		
	glPrint(200,80,1,(char *)glGetString(GL_VERSION));		

	glColor3f(0.5f,0.5f,1.0f);								
	glPrint(192,432,1,"NeHe Productions");					

	glLoadIdentity();										
	glColor3f(1.0f,1.0f,1.0f);								
	glBegin(GL_LINE_STRIP);									
		glVertex2d(639,417);								
		glVertex2d(  0,417);								
		glVertex2d(  0,480);								
		glVertex2d(639,480);								
		glVertex2d(639,128);								
	glEnd();												
	glBegin(GL_LINE_STRIP);									
		glVertex2d(  0,128);								
		glVertex2d(639,128);															
		glVertex2d(639,  1);								
		glVertex2d(  0,  1);								
		glVertex2d(  0,417);								
	glEnd();												

	glScissor(1	,int(0.135416f*sheight),swidth-2,int(0.597916f*sheight));
	glEnable(GL_SCISSOR_TEST);								

	char* text=(char *)malloc(strlen((char *)glGetString(GL_EXTENSIONS))+1);	
	strcpy (text,(char *)glGetString(GL_EXTENSIONS));		

	token=strtok(text," ");									
	while(token!=NULL)										
	{
		cnt++;											
		if (cnt>maxtokens)									
		{
			maxtokens=cnt;									
		}

		glColor3f(0.5f,1.0f,0.5f);							
		glPrint(0,96+(cnt*32)-scroll,0,"%i",cnt);			
		glColor3f(1.0f,1.0f,0.5f);							
		glPrint(50,96+(cnt*32)-scroll,0,token);				
		token=strtok(NULL," ");								
	}

	glDisable(GL_SCISSOR_TEST);							

	free(text);												
	glFlush();											
	
}


void keyboard(unsigned char key,int x,int y)
{
	switch (key)
	{
	case 'W':
		if (scroll>0)
		{
			scroll-=2;		
		}
		glutPostRedisplay();
		break;
	case 'S':
		if (scroll<32*(maxtokens-9))
		{
			scroll+=2;		
		}
		glutPostRedisplay();
		break;
	}
}


int main(int argc,char **argv)
{
	glutInit(&argc,argv);
	glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB|GLUT_DEPTH);
	glutInitWindowSize(800,600);
	glutInitWindowPosition(100,100);
	glutCreateWindow("区域剪裁和TGA图像文件的加载");
	InitGL();
	glutDisplayFunc(DrawGLScene);
	glutKeyboardFunc(keyboard);
	glutReshapeFunc(ReSizeGLScene);
	glutMainLoop();
}

 

  • 大小: 84.9 KB
  • 大小: 46.1 KB
  • 大小: 59.2 KB
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics