正投影:将物体直接投影到屏幕上,不改变其大小
glOrtho (GLdouble left, GLdouble right, GLdouble bottom, GLdouble top, GLdouble zNear, GLdouble zFar);透视投影:远处的东西看起来要小一些,近处的东西看起来会大一些,这就是透视原理
gluPerspective(GLdouble fovy,GLdouble aspect,GLdouble zNear,GLdouble zFar)
首先得设置gluPerspective,来看看它的参数都表示什么意思
fovy,这个最难理解,我的理解是,眼睛睁开的角度,即,视角的大小,如果设置为0,相当你闭上眼睛了,所以什么也看不到,如果为180,那么可以认为你的视界很广阔,
aspect,这个好理解,就是实际窗口的纵横比,即x/y
zNear,这个呢,表示你近处剪裁面
zFar表示远处剪裁面
glViewport(0,0,600,480); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(45.0f,(GLfloat)600/(GLfloat)480,0.1f,100.0f); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); 窗口的大小是800*600 视口的大小是600*480,可以看出视口是以窗口的左下角为原点的一个区域 glTranslatef(0.0f,0.0f,-3.0f); glBindTexture(GL_TEXTURE_2D, texture[0]); glColor3f(1.0f,1.0f,0.0f);//黄色图形 glBegin(GL_QUADS) glTexCoord2f(0.0f, 0.0f); glVertex3f(0.0f,0.0f,0.0f); glTexCoord2f(1.0f,0.0f); glVertex3f(1.0f, 0.0f,0.0f); glTexCoord2f(1.0f,1.0f);glVertex3f(1.0f, 1.0f, 0.0f); glTexCoord2f(0.0f,1.0f);glVertex3f(0.0f, 1.0f, 0.0f); glEnd(); glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity() glOrtho(0,800,0,600,-1,1); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glLoadIdentity() glColor3f(0.0f,1.0f,0.0f);//绿色图形 glBegin(GL_QUADS) glTexCoord2f(0.0f, 0.0f); glVertex3i(10, 30, 0); glTexCoord2f(1.0f,0.0f); glVertex3i(110, 30, 0); glTexCoord2f(1.0f,1.0f);glVertex3i(110, 130, 0); glTexCoord2f(0.0f,1.0f);glVertex3i(10, 130, 0); glEnd(); glMatrixMode(GL_PROJECTION); glPopMatrix() glMatrixMode(GL_MODELVIEW); glPopMatrix(); 建立right=800,top=600的正投影。可以看到正投影以左下角为原点(虽然视口是600*400,此处会按照比例进行缩放) glMatrixMode(GL_PROJECTION) glPushMatrix(); glLoadIdentity(); glOrtho(0,800,600,0,-1,1); glMatrixMode(GL_MODELVIEW); glPushMatrix() glLoadIdentity(); glScaled(2,2,2); glColor3f(1.0f,0.0f,0.0f);//红色图形 glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f);glVertex3i(10, 30, 0); glTexCoord2f(1.0f,0.0f);glVertex3i(110, 30, 0); glTexCoord2f(1.0f,1.0f);glVertex3i(110, 130, 0); glTexCoord2f(0.0f,1.0f);glVertex3i(10, 130, 0); glEnd(); glMatrixMode(GL_PROJECTION) glPopMatrix(); glMatrixMode(GL_MODELVIEW) glPopMatrix()
建立right=800,bottom=600的正投影。可以看到正投影以左上角为原点(虽然视口是600*400,此处会按照比例进行缩放)glScaled可以对正投影进行缩放,glTranslatef可对透视投影进行缩放
建立left=800,bottom=600的正投影。可以看到正投影以右上角为原点
建立left=800,top=600的正投影。可以看到正投影以右上角为原点
正投影是以原比例进行显示不会随着Z轴的变化而变化
视口:viewport当我们投影完成以后投影内容会按照视口的比例进行拉伸和缩放
举例:视口的大小是800*600 假设我们正投影设置为 width 8 height 6 那么显示出来的效果就是物体宽高都拉伸100倍
glViewport(0,0,800,600);
glOrtho(0,200,0,150,-1,1);
glBegin(GL_QUADS);
glTexCoord2f(0.0f, 0.0f); glVertex3f(0, 0, 0);
glTexCoord2f(1.0f,0.0f); glVertex3f(100, 0, 0);
glTexCoord2f(1.0f,1.0f);glVertex3f(100, 100, 0);
glTexCoord2f(0.0f,1.0f);glVertex3f(0, 100, 0);
glEnd()
分析:可知四边形宽度和高度都是100,乘以系数 分别为weight(100*800/200),height(100*600/150)
#include "header.h" GLuint texture[3]; AUX_RGBImageRec *LoadBMP(char *Filename) { FILE *File=NULL; if (!Filename) { return NULL; } File=fopen(Filename,"r"); if (File) { fclose(File); return auxDIBImageLoad(Filename); } return NULL; } int LoadGLTextures() { int Status=FALSE; AUX_RGBImageRec *TextureImage[3]; memset(TextureImage,0,sizeof(void *)*3); if ((TextureImage[0]=LoadBMP("Data/logo.bmp") )&& (TextureImage[1]=LoadBMP("Data/mask1.bmp"))&& (TextureImage[2]=LoadBMP("Data/image1.bmp"))) { Status=TRUE; glGenTextures(3, &texture[0]); glBindTexture(GL_TEXTURE_2D, texture[0]); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, TextureImage[0]->sizeX, TextureImage[0]->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, TextureImage[0]->data); glBindTexture(GL_TEXTURE_2D, texture[1]); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, TextureImage[1]->sizeX, TextureImage[1]->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, TextureImage[1]->data); glBindTexture(GL_TEXTURE_2D, texture[2]); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, TextureImage[2]->sizeX, TextureImage[2]->sizeY, 0, GL_RGB, GL_UNSIGNED_BYTE, TextureImage[2]->data); } if (TextureImage[0]) { if (TextureImage[0]->data) { free(TextureImage[0]->data); } free(TextureImage[0]); } return Status; } GLvoid ReSizeGLScene(GLsizei width, GLsizei height) { if (height==0) { height=1; } glViewport(0,0,600,480); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(90.0f,(GLfloat)600/(GLfloat)480,0.1f,100.0f); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); } int InitGL(GLvoid) { if (!LoadGLTextures()) { return FALSE; } glClearColor(1.0f, 1.0f, 1.0f, 0.0f); glClearDepth(1.0); glEnable(GL_DEPTH_TEST); // glShadeModel(GL_SMOOTH); glEnable(GL_TEXTURE_2D); return TRUE; } void DrawGLScene(GLvoid) { glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glLoadIdentity(); glTranslatef(0.0f,0.0f,-3.0f); glBindTexture(GL_TEXTURE_2D, texture[0]); glColor3f(1.0f,1.0f,0.0f); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f); glVertex3f(0.0f,0.0f,0.0f); glTexCoord2f(1.0f,0.0f); glVertex3f(1.0f, 0.0f,0.0f); glTexCoord2f(1.0f,1.0f);glVertex3f(1.0f, 1.0f, 0.0f); glTexCoord2f(0.0f,1.0f);glVertex3f(0.0f, 1.0f, 0.0f); glEnd(); glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); glOrtho(0,800,0,600,-1,1); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glLoadIdentity(); glColor3f(0.0f,1.0f,0.0f); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f); glVertex3i(10, 30, 0); glTexCoord2f(1.0f,0.0f); glVertex3i(110, 30, 0); glTexCoord2f(1.0f,1.0f);glVertex3i(110, 130, 0); glTexCoord2f(0.0f,1.0f);glVertex3i(10, 130, 0); glEnd(); glMatrixMode(GL_PROJECTION); glPopMatrix(); glMatrixMode(GL_MODELVIEW); glPopMatrix(); glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); glOrtho(0,800,600,0,-1,1); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glLoadIdentity(); glScaled(2,2,2); glColor3f(1.0f,0.0f,0.0f); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f);glVertex3i(10, 30, 0); glTexCoord2f(1.0f,0.0f);glVertex3i(110, 30, 0); glTexCoord2f(1.0f,1.0f);glVertex3i(110, 130, 0); glTexCoord2f(0.0f,1.0f);glVertex3i(10, 130, 0); glEnd(); glMatrixMode(GL_PROJECTION); glPopMatrix(); glMatrixMode(GL_MODELVIEW); glPopMatrix(); glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); glOrtho(800,0,600,0,-1,1); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glLoadIdentity(); glColor3f(0.8f,0.5f,0.0f); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f);glVertex3i(10, 30, 0); glTexCoord2f(1.0f,0.0f);glVertex3i(110, 30, 0); glTexCoord2f(1.0f,1.0f);glVertex3i(110, 130, 0); glTexCoord2f(0.0f,1.0f);glVertex3i(10, 130, 0); glEnd(); glMatrixMode(GL_PROJECTION); glPopMatrix(); glMatrixMode(GL_MODELVIEW); glPopMatrix(); glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); glOrtho(800,0,0,600,-1,1); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glLoadIdentity(); glColor3f(0.3f,0.5f,1.0f); glBegin(GL_QUADS); glTexCoord2f(0.0f, 0.0f);glVertex3i(10, 30, 0); glTexCoord2f(1.0f,0.0f);glVertex3i(110, 30, 0); glTexCoord2f(1.0f,1.0f);glVertex3i(110, 130, 0); glTexCoord2f(0.0f,1.0f);glVertex3i(10, 130, 0); glEnd(); glMatrixMode(GL_PROJECTION); glPopMatrix(); glMatrixMode(GL_MODELVIEW); glPopMatrix(); glFlush(); } int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB | GLUT_DEPTH); glutInitWindowSize(640,480); glutCreateWindow("视口,正投影,透视投影"); glutReshapeFunc(ReSizeGLScene); glutDisplayFunc(DrawGLScene); InitGL(); glutMainLoop(); return 0; }