一个比较综合的各种变换的例子.
参考了别人写的多视口例子 ,根据自己对 视口变换,投影变换,模型视图变换的理解, 做了一些小改动.包含 3d 2d 混合渲染等内容.
关于 glutDisplayFunc() 的回调函数 paintGL 和 glutPostRedisplay() 函数罗嗦两句:
glutDisplayFunc() 的 callback 函数,并不是每一帧都会去绘制的,只有当窗口发生变化或者被覆盖了,才会调用。
有点类似 WM_PAINT.
其他地方修改了显示图形,必须要调用 glutPostRedisplay() 才行,类似 InvalideRect().
glFrame.h
#include <GL/glut.h>
void initGL();
void paintGL();
void resizeGL(int width,int height);
void mousePress(int button,int state,int width,int height);
void mouseMove(int x,int y);
main.cpp
#include "glFrame.h"
int main( int argc,char** argv)
{
glutInit( &argc,argv);
glutInitDisplayMode( GLUT_SINGLE | GLUT_RGB );
glutInitWindowSize( 800,600 );
glutInitWindowPosition( 100,100 );
glutCreateWindow("Multiple viewports");
glutReshapeFunc( resizeGL);
glutDisplayFunc( paintGL);
glutMouseFunc( mousePress);
glutMotionFunc( mouseMove);
glutMainLoop();
return 0;
}
mulview.cpp
#include "glFrame.h"
// do display functions declarations
void paintCenter();
void paintViewportA();
void paintViewportB();
int width = 0;
int height = 0;
bool bBorderVisible = true;
void initGL()
{
glShadeModel(GL_FLAT);
glClearColor( 0.0f,0.0f,0.0f,0.0f);
}
void paintGL()
{
glClear( GL_COLOR_BUFFER_BIT );
paintViewportA();
paintCenter();
paintViewportB();
glFlush();
}
void resizeGL(int w,int h)
{
// init matrix is unnecessary,cause each viewport will set them again.
/*glMatrixMode( GL_PROJECTION );
glLoadIdentity();
gluOrtho2D(0,1,0,1);
glMatrixMode( GL_MODELVIEW );
glLoadIdentity();*/
//glViewport( 0,0,width,height);
width = w;
height = h;
}
void mousePress(int button,int state,int width,int height)
{
if( button == GLUT_LEFT_BUTTON && state == GLUT_DOWN )
{
bBorderVisible = !bBorderVisible;
}
glutPostRedisplay();
}
void mouseMove(int x,int y)
{
glutPostRedisplay();
}
// center viewport
void paintCenter()
{
int _width = width / 4;
int _height = height / 3;
glViewport(0, 0, 3*_width, 3*_height);
// center viewport, cube 1
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(50,(GLfloat)width/(GLfloat)height,1.5,20.0);
glColor3f(1,0,0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(0,0,4,0,0,0,0,1,0);
glTranslatef(-0.3, 0.3 ,2);
glRotatef(30,0,0,1);
glRotatef(30,0,1,0);
glutWireCube(0.5);
// center viewport, cube 2
glColor3f(0,1,0);
glLoadIdentity();
gluLookAt(0,0,4,0,0,0,0,1,0);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(50,(GLfloat)width/(GLfloat)height,1.5,20.0);
glMatrixMode(GL_MODELVIEW);
glTranslatef(-0.5,-0.5,2);
glRotatef(30,0,0,1);
glRotatef(30,0,1,0);
glutWireCube(0.1);
// center viewport, cube 3
glColor3f(0,0,1);
glLoadIdentity();
gluLookAt(0,0,4,0,0,0,0,1,0);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(50,(GLfloat)width/(GLfloat)height,1.5,20.0);
glMatrixMode(GL_MODELVIEW);
glTranslatef(0.2,-0.5,2);
glRotatef(30,0,0,1);
glRotatef(30,0,1,0);
glutWireCube(0.2);
}
void paintViewportA()
{
int _width = width/4;
int _height = height/3;
glViewport( 3*_width,2*_height,_width,_height);
//glViewport( 0*_width,2*_height,_width,_height);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective( 60.0f,(GLfloat)width/(GLfloat)height,1.5,20.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt( 0,0,4,0,0,0,0,1,0);
glColor3f( 1,0,0);
glTranslatef( 0,0,2);
glRotatef(30,0,0,1);
glRotatef(30,0,1,0);
glutWireCube(0.5f);
if(bBorderVisible)
{
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluOrtho2D(0,1,0,1);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glColor3f( 1,1,0);
glBegin(GL_LINES);
glVertex2f(0.1,0.1); // Notice: gluOrtho2D(0,1,0,1),so line (0,0) to (0,1) is not in viewport area,we can't see it
glVertex2f(0.1,0.9);
glVertex2f(0.1,0.1);
glVertex2f(0.9,0.1);
glEnd();
}
}
void paintViewportB()
{
int _width = width/4;
int _height = height/3;
glViewport( 3*_width,1*_height,_width,_height);
glMatrixMode( GL_PROJECTION);
glLoadIdentity();
gluPerspective( 60.0f,(GLfloat)width/(GLfloat)height,0.01,100);
glMatrixMode( GL_MODELVIEW);
glLoadIdentity();
gluLookAt( 0,0,4,0,0,0,0,1,0);
glColor3f( 1,0,1);
glRotatef( 65,1,0,0);
glutWireSphere( 2.0f,10,10);
if(bBorderVisible)
{
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluOrtho2D(0,1,0,1);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glColor3f( 1,1,0);
glBegin(GL_LINES);
glVertex2f(0.1,0.1); // Notice: gluOrtho2D(0,1,0,1),so line (0,0) to (0,1) is not in viewport area,we can't see it
glVertex2f(0.1,0.9);
glVertex2f(0.1,0.1);
glVertex2f(0.9,0.1);
glEnd();
}
}