openGL+VS2010的例程--空间摄影机+灯光渲染成型(三维)

效果图如上:

步骤:略

实现代码如下:

1、main.cpp

  1 /**********************************************************************
  2 
  3   Lighting and depth testing
  4 
  5   June, 11th, 2000
  6 
  7   This tutorial was written by Philipp Crocoll
  8   Contact: 
  9     philipp.crocoll@web.de
 10     www.codecolony.de
 11 
 12   Every comment would be appreciated.
 13 
 14   If you want to use parts of any code of mine:
 15     let me know and
 16     use it!
 17 
 18 ***********************************************************************
 19 
 20 ESC    : Exit
 21  
 22 CAMERA movement:
 23 w : forwards
 24 s : backwards
 25 a : turn left
 26 d : turn right
 27 x : turn up
 28 y : turn down
 29 v : strafe right
 30 c : strafe left
 31 r : move up
 32 f : move down
 33 
 34 
 35 **********************************************************************/
 36    
 37 #include <GL\glut.h>        //includes gl.h and glu.h
 38 #include <windows.h>
 39 #include "camera.h"
 40 
 41 CCamera Camera;
 42 bool LightEnabled = true;
 43 float TorusRotated = 0.0;
 44 
 45 static GLfloat MatSpec[] = {1.0,1.0,1.0,1.0}; 
 46 static GLfloat MatShininess[] = {50.0};  // 设置材料反射指数
 47 //其中,LightPosition也是一个四维数组,四维数组的前3项依次为光源位置的X,Y,Z分量,第四个值很特殊,一般为1或-1。当
 48 //LightPosition[4]=-1的时候,表示光源位于距离场景无限远的地方,无论前面设置的X,Y,Z是什么值。当LightPosition[4]=1
 49 //时,光源的位置就是前三项所指定的位置。
 50 static GLfloat LightPos[] = {-2.0,2.0,3.0,0.0};
 51 
 52 void Display(void)
 53 {
 54     glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);  //Don't forget the depth buffer!
 55     glLoadIdentity();    //Load a new modelview matrix -> we can apply new transformations
 56     Camera.Render();  // 移动新视点的矩阵 
 57     glLightfv(GL_LIGHT0, GL_POSITION, LightPos); // 设置光源在场景中的位置
 58     glutSolidSphere(1.0,40,40); //  设置球体1
 59 
 60     glTranslatef(2.0,0.0,0.0); 
 61     glutSolidSphere(0.8,40,40); //  设置球体2
 62 
 63     glPushMatrix(); // 压栈1
 64         glTranslatef(0.0,2.0,0.0);
 65         glutSolidSphere(1.2,40,40); //  设置球体3
 66     glPopMatrix(); // 出栈1
 67 
 68     glTranslatef(0.0,0.0,2.0);
 69     glutSolidSphere(0.5,40,40);  //  设置球体4
 70 
 71     glTranslatef(-4.0,0.0,0.0);
 72     glRotatef(TorusRotated, 0.0,1.0,0.0);
 73     glutSolidTorus(0.3,1.0,16,32);  // glutWireTorus  绘制线框圆环 glutSolidTorus 绘制实心圆环
 74 
 75     glFlush();            //Finish rendering
 76     glutSwapBuffers();    //Swap the buffers ->make the result of rendering visible
 77 }
 78 
 79 void Reshape(int x, int y)
 80 {
 81     if (y == 0 || x == 0) return;  //Nothing is visible then, so return
 82     //Set a new projection matrix
 83     glMatrixMode(GL_PROJECTION);  
 84     glLoadIdentity();
 85     //Angle of view:40 degrees
 86     //Near clipping plane distance: 0.5
 87     //Far clipping plane distance: 20.0
 88     gluPerspective(40.0,(GLdouble)x/(GLdouble)y,0.5,20.0);
 89     glMatrixMode(GL_MODELVIEW);
 90     glViewport(0,0,x,y);  //Use the whole window for rendering
 91     //Adjust point size to window size
 92     glPointSize(GLfloat(x)/200.0);
 93 }
 94 void KeyDown(unsigned char key, int x, int y)
 95 //Note: because there is an Idle-func, we don't have to call Display here
 96 {    
 97     switch(key)
 98     {
 99     case 27:    //ESC
100         exit(0);
101         break;
102     case 97:        //a
103         Camera.RotateY(5.0);
104         break;
105     case 100:        //d
106         Camera.RotateY(-5.0);
107         break;
108     case 119:        //w
109         Camera.MoveForwards( -0.1 ) ;
110         break;
111     case 115:        //s
112         Camera.MoveForwards( 0.1 ) ;
113         break;
114     case 120:        //x
115         Camera.RotateX(5.0);
116         break;
117     case 121:        //y
118         Camera.RotateX(-5.0);
119         break;
120     case 99:        //c
121         Camera.StrafeRight(-0.1);
122         break;
123     case 118:        //v
124         Camera.StrafeRight(0.1);
125         break;
126     case 'l':
127         LightEnabled = !LightEnabled;
128         if (LightEnabled) glEnable(GL_LIGHTING);
129             else glDisable(GL_LIGHTING);
130         break;
131     }
132 }
133 static long long times = 0;
134 void Idle(void)
135 {
136     times++; // 延迟
137     if(times>500000)
138         times =0;
139     if(times% 500000== 0)
140     {
141         TorusRotated += 2.0;
142         Display();
143     }
144 }
145 
146 int main(int argc, char **argv)
147 {    
148     //Initialize GLUT
149     glutInit(&argc, argv);
150     //Lets use doublebuffering, RGB(A)-mode and a depth buffer
151     glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH); // 新增“深度缓冲”
152     glutInitWindowSize(600,600);
153     //Create a window with rendering context and everything else we need
154     glutCreateWindow("Lighting and depth testing");
155     //Assign the event-handling routines
156     glutDisplayFunc(Display);
157     glutReshapeFunc(Reshape);
158     glutKeyboardFunc(KeyDown);
159     glutIdleFunc(Idle); // 新增“空闲任务”
160     Camera.Move(F3dVector(0.0,0.0,15.0)); // 摄影机的位置
161     //Lighting stuff:
162     glShadeModel(GL_SMOOTH);    //GL_FLAT would look much worse GL_SMOOTH // 平滑过渡颜色
163     glEnable(GL_DEPTH_TEST); // 开启深度测试,比较在z轴上的点是否最靠前。
164     // GL_DIFFUSE 漫射光   GL_SPECULAR  镜面光
165     glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, MatSpec);   // 镜面光的颜色 -- 缺省值 
166     glMaterialfv(GL_FRONT_AND_BACK, GL_SHININESS, MatShininess);  // 称为 镜面指数 ,取值范围是0到128。 
167 
168     glEnable(GL_LIGHTING); // 打开光照效果
169     glEnable(GL_LIGHT0); // 使用默认的0号灯
170 
171     //Let GLUT get the msgs and tell us the ones we need
172     glutMainLoop();
173     return 0;
174 }

 

2、camera.cpp

  1 #include "camera.h"
  2 #include "math.h"
  3 #include <iostream>
  4 #include "windows.h"
  5 SF3dVector F3dVector ( GLfloat x, GLfloat y, GLfloat z )
  6 {
  7     SF3dVector tmp;
  8     tmp.x = x;
  9     tmp.y = y;
 10     tmp.z = z;
 11     return tmp;
 12 }
 13 SF3dVector AddF3dVectors (SF3dVector* u, SF3dVector* v)
 14 {
 15     SF3dVector result;
 16     result.x = u->x + v->x;
 17     result.y = u->y + v->y;
 18     result.z = u->z + v->z;
 19     return result;
 20 }
 21 void AddF3dVectorToVector ( SF3dVector * Dst, SF3dVector * V2)
 22 {
 23     Dst->x += V2->x;
 24     Dst->y += V2->y;
 25     Dst->z += V2->z;
 26 }
 27 
 28 
 29 /***************************************************************************************/
 30 
 31 CCamera::CCamera()
 32 {
 33     //Init with standard OGL values:
 34     Position = F3dVector (    0.0, 
 35                             0.0,
 36                             0.0);
 37     ViewDir = F3dVector(    0.0,
 38                             0.0,
 39                             -1.0);
 40     ViewDirChanged = false;
 41     //Only to be sure:
 42     RotatedX = RotatedY = RotatedZ = 0.0;
 43 }
 44 
 45 void CCamera::GetViewDir( void )
 46 {
 47     SF3dVector Step1, Step2;
 48     //Rotate around Y-axis:
 49     Step1.x = cos( (RotatedY + 90.0) * PIdiv180);
 50     Step1.z = -sin( (RotatedY + 90.0) * PIdiv180);
 51     //Rotate around X-axis:
 52     double cosX = cos (RotatedX * PIdiv180);
 53     Step2.x = Step1.x * cosX;
 54     Step2.z = Step1.z * cosX;
 55     Step2.y = sin(RotatedX * PIdiv180);
 56     //Rotation around Z-axis not yet implemented, so:
 57     ViewDir = Step2;
 58 }
 59 void CCamera::Move (SF3dVector Direction)
 60 {
 61     AddF3dVectorToVector(&Position, &Direction );
 62 }
 63 
 64 void CCamera::RotateY (GLfloat Angle)
 65 {
 66     RotatedY += Angle;
 67     ViewDirChanged = true;
 68 }
 69 
 70 void CCamera::RotateX (GLfloat Angle)
 71 {
 72     RotatedX += Angle;
 73     ViewDirChanged = true;
 74 }
 75 
 76 void CCamera::Render( void )
 77 {
 78     glRotatef(-RotatedX , 1.0, 0.0, 0.0);
 79     glRotatef(-RotatedY , 0.0, 1.0, 0.0);
 80     glRotatef(-RotatedZ , 0.0, 0.0, 1.0);
 81     glTranslatef( -Position.x, -Position.y, -Position.z );
 82 }
 83 
 84 void CCamera::MoveForwards( GLfloat Distance )
 85 {
 86     if (ViewDirChanged) GetViewDir();
 87     SF3dVector MoveVector;
 88     MoveVector.x = ViewDir.x * -Distance;
 89     MoveVector.y = ViewDir.y * -Distance;
 90     MoveVector.z = ViewDir.z * -Distance;
 91     AddF3dVectorToVector(&Position, &MoveVector );
 92 }
 93 
 94 void CCamera::StrafeRight ( GLfloat Distance )
 95 {
 96     if (ViewDirChanged) GetViewDir();
 97     SF3dVector MoveVector;
 98     MoveVector.z = -ViewDir.x * -Distance;
 99     MoveVector.y = 0.0;
100     MoveVector.x = ViewDir.z * -Distance;
101     AddF3dVectorToVector(&Position, &MoveVector );
102 }

3、camera.h

 1 #include <gl\glut.h>        // Need to include it here because the GL* types are required
 2 #define PI 3.1415265359
 3 #define PIdiv180 3.1415265359/180.0
 4 
 5 /
 6 //Note: All angles in degrees  //
 7 /
 8 
 9 struct SF3dVector  //Float 3d-vect, normally used
10 {
11     GLfloat x,y,z;
12 };
13 struct SF2dVector
14 {
15     GLfloat x,y;
16 };
17 
18 class CCamera
19 {
20 private:
21     SF3dVector Position;
22     SF3dVector ViewDir;        /*Not used for rendering the camera, but for "moveforwards"
23                             So it is not necessary to "actualize" it always. It is only
24                             actualized when ViewDirChanged is true and moveforwards is called*/
25     bool ViewDirChanged;
26     GLfloat RotatedX, RotatedY, RotatedZ;    
27     void GetViewDir ( void );
28 public:
29     CCamera();                //inits the values (Position: (0|0|0) Target: (0|0|-1) )
30     void Render ( void );    //executes some glRotates and a glTranslate command
31                             //Note: You should call glLoadIdentity before using Render
32     void Move ( SF3dVector Direction );
33     void RotateX ( GLfloat Angle );
34     void RotateY ( GLfloat Angle );
35     void RotateZ ( GLfloat Angle );
36     void RotateXYZ ( SF3dVector Angles );
37     void MoveForwards ( GLfloat Distance );
38     void StrafeRight ( GLfloat Distance );
39 };
40 
41 
42 SF3dVector F3dVector ( GLfloat x, GLfloat y, GLfloat z );
43 SF3dVector AddF3dVectors ( SF3dVector * u, SF3dVector * v);
44 void AddF3dVectorToVector ( SF3dVector * Dst, SF3dVector * V2);

代码来源地址:http://www.codecolony.de/

 

转载于:https://www.cnblogs.com/yuwl26/p/4227805.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
STM32F4X7是一款高性能的微控制器,支持uC/OS、FreeRTOS、LWIP、SSL和MQTT等多种工具。它通过使用MDK5开发工具,能够提供稳定可靠的开发环境。 W5500是一款硬件模块,是一种以太网控制器,用于实现物联网设备的网络连接。它能够与STM32F4X7微控制器结合使用,实现MQTT协议的通信。在这个例程中,W5500与STM32F4X7通过SPI接口进行通信,使用MQTT协议实现设备之间的数据传输。 在这个例程和说明中,首先需要配置W5500模块的网络参数,包括IP地址、子网掩码、网关和DNS服务器等。然后,通过MQTT协议连接到MQTT服务器。在连接成功后,可以通过MQTT协议发布和订阅主题,进行设备之间的数据交换。 MQTT是一种轻量级的消息队列传输协议,它具有低带宽和低功耗的特点,适用于物联网设备的通信。通过使用MQTT协议,设备可以以发布订阅的方式进行消息传递,实现设备之间的数据交互。 这个例程和说明提供了详细的配置和使用指南,帮助开发者快速上手使用W5500和MQTT协议。同时,MDK5开发工具提供了丰富的调试和分析功能,帮助开发者进行代码的验证和调试,保证系统稳定可靠。 总而言之,STM32F4X7与uC/OS、FreeRTOS、LWIP、SSL和MQTT等工具的结合使用,以及W5500和MQTT协议的应用,能够提供稳定可靠的物联网解决方案。通过使用MDK5开发工具,开发者可以快速开发和验证自己的物联网应用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值