//相比之二而言,此程序改变了glLookAt函数的参数,通过一些简单的计算和调用math.h,增加了鼠标的互动来完成摄像机视角的进一步改变。
//写给和我一样的菜鸟,这些代码可以直接运行的。
#include"stdafx.h"
#define GLUT_DISABLE_ATEXIT_HACK
#include <gl/glut.h>
#include<time.h>
#include<math.h>
#pragma comment(lib, "opengl32.lib")
#pragma comment(lib, "glut32.lib")
#pragma comment(lib, "glu32.lib")
#pragma comment(lib, "glut.lib")
static double angle1; //翅膀的扇动角度
static double angle2; //人腿的旋转角度
static double walk; //人走动的速度
static double fly; //鸟飞的速度
static double d = 0.1; //增量
static double e = 0.1; //增量
static double s = 0.001;//增量
static double f = 0.002;
float g_rotateY = 0.0f; // 绕Y轴旋转变量
float g_posX = 0.0f; //横向位移
float g_posY = 0.0f;
float g_posZ = 0.0f;
int camerdire;
static double camerangle; //相机转动的角度
static double cs=0; //相机转动的角度的增幅。
static double cd = 10; //相机距离(0,0,0)的距离
static double cu = 0; //同上
void init(void)
{
glClearColor(0.0, 0.0, 0.0, 0.0);
glShadeModel(GL_FLAT);
}
void cylinder()
{
glPushMatrix();
glTranslatef(0, 0, -0.05);
glScalef(0.05, 0.05, 0.1);
GLUquadricObj *cylinder_obj1;
GLUquadricObj *cylinder_obj2;
//GLUquadricObj *cylinder_obj3;
//然后再初始化
cylinder_obj1 = gluNewQuadric();
cylinder_obj2 = gluNewQuadric();
//cylinder_obj3=gluNewQuadric();
//GL_COLOR_BUFFER_BIT标志用glClearColor设置的颜色清除颜色缓冲区
glColor3f(1.0, 1.0, 0.1); //glColor{34}{b s i f d ub us ui}{v}(....)
//画圆柱体
glPushMatrix();
glRotatef(0, 1.0, 0.0, 0.0);//绕y轴旋转的角度
gluCylinder(cylinder_obj1, 2, 2, 4, 100, 50);
gluDisk(cylinder_obj2, 0, 2, 100, 50);
glPopMatrix();
glPopMatrix();
}
void display(void)
{
glClear(GL_COLOR_BUFFER_BIT);
glColor3f(1.0, 1.0, 1.0);
glLoadIdentity();
//if (camerdire==1) //从左侧观看
//gluLookAt(-10.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -1.0, 0.0); //设置照相机参数,照相机的位置为(-10,0,0),指向(0,0,0),向上为(0,1,0)
//if (camerdire==0) //从前面观看
//gluLookAt(0.0, 0.0, cd, 0.0, 0.0, 0.0, 0.0, -1.0, 0.0); //设置照相机参数,照相机的位置为(0,0,10),指向(0,0,0),向上为(0,1,0)
//if (camerdire==2) //从后面观看
//gluLookAt(0.0, 0.0, -10.0, 0.0, 0.0, 0.0, 0.0, -1.0, 0.0); //设置照相机参数,照相机的位置为(0,0,-10),指向(0,0,0),向上为(0,1,0)
//gluLookAt(cd*cos(cs)-cd*cos(cu), cd*sin(cu), -cd*sin(cs)-cd*cos(cu), 0.0, 0.0, 0.0, 0.0, -1.0, 0.0); //设置照相机参数,照相机的位置为(0,0,10),指向(0,0,0),向上为(0,1,0)
gluLookAt(cd*cos(cu)*sin(cs), cd*sin(cu),cd*cos(cu)*cos(cs), 0.0, 0.0, 0.0, 0.0, -1.0, 0.0); //设置照相机参数,照相机的位置为(0,0,10),指向(0,0,0),向上为(0,1,0)
//gluLookAt(0,-cd, 0, 0.0, 0.0, 0.0, 0.0, -1.0, 0.0); //设置照相机参数,照相机的位置为(0,0,5),指向(0,0,0),向上为(0,1,0)
//----------------------画出地面-------------------
glPushMatrix();
glTranslatef(-g_posX, g_posY, g_posZ+5);
glTranslatef(-2, 6, -6);
glScalef(3, 1, 2);
glColor3f(1.0f, 1.0f, 1.0f);
glBegin(GL_QUADS);
glVertex3f(2.0f, -1.5f, 2.0f);
glVertex3f(-2.0f, -1.5f, 2.0);
glVertex3f(-2.0f, -1.5f, -2.0);
glVertex3f(2.0f, -1.50f, -2.0);
glEnd();
glPopMatrix();
//----------------------以上画出地面----------
//---------------------以下画出飞鸟
glPushMatrix();
glTranslatef(0, -5, 0.3);
glTranslatef(fly+=f, angle1/80+0.1, 0); //飞鸟身躯的上下起伏,左右移动
//一对翅膀(用两个扁长的立方体表示)
glColor3f(0.7, 0.7, 0.7);
glPushMatrix();
glRotatef(angle1, 0, 0, 1);
glTranslatef(-0.5,0,0);
glScalef(1, 0.05, 0.3);
glutSolidCube(1.0);
glPopMatrix();
glPushMatrix();
glRotatef(-angle1, 0, 0, 1);
glTranslatef(0.5, 0, 0);
glScalef(1, 0.05, 0.3);
glutSolidCube(1.0);
glPopMatrix();
//一个身躯(用一个立方体表示)
glColor3f(1.0, 0.0, 0.0);
glPushMatrix();
glScalef(0.3,0.3,0.3);
glutSolidCube(1.0);
glPopMatrix();
glPopMatrix();
//----------------------以上为飞鸟的动画
glColor3f(0, 1, 0);
//-----------------------下面画出一个人走路
glPushMatrix();
glRotatef(-90, 0, 0, 1);
glTranslatef(-4,walk+=s,0); //两腿的前进
glScalef(2.0, 2.0, 2.0); //调整机器人的大小
//---------------------下面是两腿摆动的动画----------
glPushMatrix();
glColor3f(1.0, 0.0, 1.0);
glRotatef(angle2, 0, 0, 1);
glTranslatef(-0.5, 0, 0);
glScalef(1, 0.05, 0.1);
glutSolidCube(1.0);
glPopMatrix();
glPushMatrix();
glRotatef(180, 0, 0, 1);
glRotatef(-angle2, 0, 0, 1);
glTranslatef(0.5, 0, 0.3);
glScalef(1, 0.05, 0.1);
glutSolidCube(1.0);
glPopMatrix();
cylinder();
glPopMatrix();
//-----------------------以上为人走动的动画--------------
glFlush();
}
void reshape(int w,int h)
{
glViewport(0, 0, (GLsizei)w, (GLsizei)h);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glFrustum(-1.0, 1.0, -1.0, 1.0, 1.5, 20.0);
glMatrixMode(GL_MODELVIEW);
}
void myIdle(void)
{
angle1 -= d;
if (angle1 <-70)
d = -d;
else if (angle1>30)
d = -d;
angle2 -= e;
if (angle2 <-30)
e = -e;
else if (angle2>30)
e = -e;
if (walk <-3)
s = -s;
else if (walk>3)
s = -s;
if (fly < -5)
f = -f;
else if (fly>5)
f = -f;
display();
}
void ProcessSpecialKeyboead(int key, int x, int y) //转换摄像视角的方向
{
if (key == GLUT_KEY_RIGHT)//视角向左
{
cs-=0.01;
}
if (key == GLUT_KEY_LEFT)//视角向右
{
cs += 0.01;
}
if (key == GLUT_KEY_DOWN)//视角向前
{
cd += 0.5;
}
if (key == GLUT_KEY_UP)//视角向后
{
cd -= 0.5;
}
if (key == GLUT_KEY_F1)//视角向上
{
cu -= 0.01;
}
if (key == GLUT_KEY_F2)//视角向下
{
cu += 0.01;
}
}
void KeyboardFunc(unsigned char key, int x, int y)
{
switch (key)
{
//---------------------控制地面的移动----------------------------
case 'A':
case 'a':
// 向左移动
g_posX -= 0.05f;
if (g_posX < -4.0f)
{
g_posX = -4.0f;
}
break;
case 'D':
case 'd':
// 向右移动
g_posX += 0.05f;
if (g_posX > 4.0f)
{
g_posX = 4.0f;
}
break;
case 'W':
case 'w':
// 向上移动
g_posY -= 0.05f;
break;
case 'S':
case 's':
// 向上移动
g_posY += 0.05f;
break;
case 'F':
case 'f':
// 向前移动
g_posZ -= 0.05f;
break;
case 'B':
case 'b':
// 向前移动
g_posZ += 0.05f;
break;
default:
break;
}
}
int main(int argc, char * *argv)
{
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB);
glutInitWindowSize(800, 600);
glutInitWindowPosition(100, 100);
glutCreateWindow(argv[0]);
init();
glutDisplayFunc(display);
glutIdleFunc(myIdle);
glutReshapeFunc(reshape);
glutKeyboardFunc(KeyboardFunc);
glutSpecialFunc(ProcessSpecialKeyboead);
glutMainLoop();
return 0;
}