使用OpenGL的几何变换

一. OpenGl几何变换的介绍

几何变换是指三维场景中的物体运动的变化,包括物体的平移、旋转、和缩放。

在OpenGL中,可以使用下面三个函数便捷地实现简单图形平移、旋转、缩放变换的功能:

glTranslatef(Type x, Type y, Type z);

glRotatef(Type angle, Type x, Type y, Type z);

glScalef(Type x,Type y,Type z);

虽然直接使用OpenGL中的矩阵操作函数也可以实现几何变换,但是使用变换函数变换的速度要快很多。

 

二. 平移变换

glTranslatef(Type x, Type y, Type z);

作用:使坐标系沿着 X, Y 和 Z 轴移动。

参数说明:x、y、z分别指定平移向量的x、y、z方向的坐标量。

注意在glTranslatef(x, y, z)中,当您移动的时候,您并不是相对屏幕中心移动,而是相对与当前所在的屏幕位置,将你绘点坐标的原点在当前原点的基础上平移一个(x,y,z)向量。

 

三. 旋转变换

glRotatef(Type angle, Type x, Type y, Type z);

作用:将坐标系绕向量(x,y,z)产生一个angle角度的旋转,满足右手定则。

如矩阵模式是GL_MODELVIEW或GL_PROJECTION时,函数glRotate()调用后所有绘制的对象将被旋转。如果(x,y,z)朝向用户方向,旋转将按逆时针方向进行。

函数glRotate()旋转的是坐标系而不是物体,如果参数angle为零,则该函数不产生任何效果。

 

四. 缩放变换

glScalef(Type x,Type y,Type z);

作用:将坐标系进行相应倍数的缩放。

参数:x,y,z分别为模型在x,y,z轴方向的缩放比。参数也可取负数,也可以理解为先关于某轴翻转180°,再缩放。

注意:一个为0的缩放因子将把所有对象的坐标值变为零,因此在使用时一定要小心。

 

五. 另外介绍一个很实用的函数:

glLoadIdentity() 

将当前的用户坐标系的原点移到了屏幕中心:类似于一个复位操作。

 

六. 实例:键盘控制三角形的变换

说明:通过键盘操作,完成一个三角形的平移和缩放。

   比如左键是向左平移,右键向右平移;上键变大,下键缩小。

   R是绕着屏幕中心旋转。

 

 1 #include<gl/glut.h>
 2 
 3 void triangle(void)
 4 {
 5     glClear(GL_COLOR_BUFFER_BIT);
 6     glBegin(GL_TRIANGLES);
 7     glColor3f(1.0,0.0,0.0);
 8     glVertex2f(0.0,0.2);
 9     glVertex2f(0.1732,-0.1);
10     glVertex2f(-0.1732,-0.1);
11     glVertex2f(0.0,0.2);
12     glEnd(); 
13     glFlush();
14 }
15 
16 void keyboard(unsigned int key,int x,int y)
17 {
18     switch(key){
19     case GLUT_KEY_LEFT:
20         glMatrixMode (GL_MODELVIEW);
21         glTranslatef (-0.1, 0.0, 0.0);
22         glutPostRedisplay(); 
23         break;
24     case GLUT_KEY_RIGHT:
25         glMatrixMode (GL_MODELVIEW);
26         glTranslatef (0.1, 0.0, 0.0);
27         glutPostRedisplay(); 
28         break;
29     case GLUT_KEY_UP:
30         glMatrixMode (GL_MODELVIEW);
31         glScalef (1.2, 1.2, 1.0);
32         glutPostRedisplay(); 
33         break;
34     case GLUT_KEY_DOWN:
35         glMatrixMode (GL_MODELVIEW);
36         glScalef (0.8, 0.8, 1.0);
37         glutPostRedisplay(); 
38         break;
39     }
40 }
41 
42 void keyboardR(unsigned char key,int x,int y)
43 {
44     switch(key)
45     {
46         case 'r':
47         glMatrixMode (GL_MODELVIEW);
48         glRotatef (45, 0, 0, -1);
49         glutPostRedisplay(); 
50         break;
51     }
52 }
53     
54 
55 int main(int argc,char *argv[])
56 {
57     glutInit(&argc,argv);
58     glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB );
59     glutInitWindowSize(600, 600);
60     glutCreateWindow("键盘控制三角形变换");
61     glutDisplayFunc(&triangle);
62     glutKeyboardFunc(keyboardR);
63     glutSpecialFunc(keyboard);
64     glutMainLoop();
65     return 0;
66 }
View Code

  

 

 七. 实例:太阳地球月亮

  1 #include <gl/glut.h>    // OpenGL toolkit
  2 #include <math.h>
  3 
  4 // Lighting values
  5 GLfloat  whiteLight[] = { 0.2f, 0.2f, 0.2f, 1.0f };
  6 GLfloat  sourceLight[] = { 0.8f, 0.8f, 0.8f, 1.0f };
  7 GLfloat     lightPos[] = { 0.0f, 0.0f, 0.0f, 1.0f };
  8 
  9 // Called to draw scene
 10 void RenderScene(void)
 11 {
 12     // Earth and Moon angle of revolution
 13     static float fMoonRot = 0.0f;
 14     static float fEarthRot = 0.0f;
 15 
 16     // Clear the window with current clearing color
 17     glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
 18 
 19     // Save the matrix state and do the rotations
 20     glMatrixMode(GL_MODELVIEW);
 21     glPushMatrix();
 22 
 23     // Translate the whole scene out and into view    
 24     glTranslatef(0.0f, 0.0f, -300.0f);    
 25     
 26     // Set material color, Red
 27     // Sun
 28     glDisable(GL_LIGHTING);
 29     glColor3ub(255, 255, 0);
 30     glutSolidSphere(15.0f, 30, 17);
 31         glEnable(GL_LIGHTING);
 32 
 33     // Move the light after we draw the sun!
 34     glLightfv(GL_LIGHT0,GL_POSITION,lightPos);
 35 
 36     // Rotate coordinate system
 37     glRotatef(fEarthRot, 0.0f, 1.0f, 0.0f);
 38 
 39     // Draw the Earth
 40     glColor3ub(0,0,255);
 41     glTranslatef(105.0f,0.0f,0.0f);
 42     glutSolidSphere(15.0f, 30, 17);
 43 
 44     // Rotate from Earth based coordinates and draw Moon
 45     glColor3ub(200,200,200);
 46     glRotatef(fMoonRot,0.0f, 1.0f, 0.0f);
 47     glTranslatef(30.0f, 0.0f, 0.0f);
 48     fMoonRot+= 15.0f;
 49     if(fMoonRot > 360.0f)
 50         fMoonRot = 0.0f;
 51     glutSolidSphere(6.0f, 30, 17);
 52 
 53     // Restore the matrix state
 54     glPopMatrix();    // Modelview matrix
 55     // Step earth orbit 5 degrees
 56     fEarthRot += 5.0f;
 57     if(fEarthRot > 360.0f)
 58         fEarthRot = 0.0f;
 59     // Show the image
 60     glutSwapBuffers();
 61 }
 62 
 63 // This function does any needed initialization on the rendering
 64 // context. 
 65 void SetupRC()
 66 {
 67     // Light values and coordinates
 68     glEnable(GL_DEPTH_TEST);    // Hidden surface removal
 69     glFrontFace(GL_CCW);        // Counter clock-wise polygons face out
 70     glEnable(GL_CULL_FACE);        // Do not calculate inside of jet
 71 
 72     // Enable lighting
 73     glEnable(GL_LIGHTING);
 74 
 75     // Setup and enable light 0
 76     glLightModelfv(GL_LIGHT_MODEL_AMBIENT,whiteLight);
 77     glLightfv(GL_LIGHT0,GL_DIFFUSE,sourceLight);
 78     glLightfv(GL_LIGHT0,GL_POSITION,lightPos);
 79     glEnable(GL_LIGHT0);
 80 
 81     // Enable color tracking
 82     glEnable(GL_COLOR_MATERIAL);
 83     
 84     // Set Material properties to follow glColor values
 85     glColorMaterial(GL_FRONT, GL_AMBIENT_AND_DIFFUSE);
 86 
 87     // Black blue background
 88     glClearColor(0.0f, 0.0f, 0.0f, 1.0f );
 89 }
 90 
 91 void TimerFunc(int value)
 92 {
 93     glutPostRedisplay();
 94     glutTimerFunc(100, TimerFunc, 1);
 95 }
 96 
 97 void ChangeSize(int w, int h)
 98 {
 99     GLfloat fAspect;
100     // Prevent a divide by zero
101     if(h == 0)
102         h = 1;
103     // Set Viewport to window dimensions
104     glViewport(0, 0, w, h);
105 
106     // Calculate aspect ratio of the window
107     fAspect = (GLfloat)w/(GLfloat)h;
108 
109     // Set the perspective coordinate system
110     glMatrixMode(GL_PROJECTION);
111     glLoadIdentity();
112 
113     // field of view of 45 degrees, near and far planes 1.0 and 425
114     gluPerspective(45.0f, fAspect, 1.0, 425.0);
115 
116     // Modelview matrix reset
117     glMatrixMode(GL_MODELVIEW);
118     glLoadIdentity();
119 }
120 
121 int main(int argc, char* argv[])
122 {
123     glutInit(&argc, argv);
124     glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);
125     glutInitWindowSize(800, 600);
126     glutCreateWindow("Earth/Moon/Sun System");
127     glutReshapeFunc(ChangeSize);
128     glutDisplayFunc(RenderScene);
129     glutTimerFunc(250, TimerFunc, 1);
130     SetupRC();
131     glutMainLoop();
132     return 0;
133 }
View Code

运行结果:

posted @ 2016-04-28 12:12  小z1情调  阅读(325)  评论(0编辑  收藏  举报