计算机图形学报告

计算机图形学报告

课程总结体会与相关技术动态

学 院: 软件学院 专业班级:学生姓名: 郑 越 学 号: 101201606

目 录

第1章

第2章 课程总结 ............................................................................................................ 2 虚拟现实技术 .................................................................. 错误!未定义书签。

1.虚拟现实技术简介………………………………………………………………………………...3

2.虚拟现实技术的发展历程………………………………………………………………………..3

3.虚拟现实系统的构成…………………………………………………………………………….3

4.当今虚拟现实技术的应用领域…………………………………………………………..4

4.1娱乐、艺术与教育领域………………………………………………………………..4

4.2军事与航天工业领域…………………………………………………………………….5

4.3 医学领域…………………………………………………………………………………………5

4.4建筑工程领域………………………………………………………………………………….6

5.虚拟现实技术的进一步展望………………………………………………………………..6

第3章 学习体会心得 .................................................................................................... 7

参 考 文 献 ......................................................................................................................... 7

1

第一章 课程总结

本学期我们学习了《计算机图形学》这门课以及在MFC下图形编程。

《计算机图形学》是为计算机科学与技术专业本科生开设的专业课,旨在介绍计算机图形学的基本概念、理论、方法和系统。它向我们讲授图形学的方法和在这一领域的最新成果。“计算机图形学”是计算机科学的重要研究内容之一,它借助数字化手段合成与操作视觉内容,将信息直观地展现给用户,其应用范围覆盖军事仿真、航空航天、文化教育、城市管理、

[1]大众娱乐等诸多领域。简单地说,计算机图形学的主要研究内容就是研究如何在计算机中

表示图形、以及利用计算机进行图形的计算、处理和显示的相关原理与算法。

在本学期的课程中,老师着重向我们介绍了计算机图形学中得一些基本算法,诸如中点画线法,DDA画线法,bresenham,区域填充算法,发走样等等这些经典算法,这不仅是对以前学习的数据结构课程的一次升华,也是对计算机专业同学知识量的一次扩充。任何图形均是由像素点构成,点构成线,线构成面,面构成一个个图形,无论是二维还是三维图形,均是如此。

在第一章中总要学习到计算机图形学的一些基本概念,图形的两种表示方式:参数表示和点阵表示。以及图形的分类:真实感图形和线框图。显示器的分类:光栅扫描显示器,阴极射线管显示器,三维显示器。并简要的介绍了计算机图形学的发展历史,图形学的应用和相关领域的介绍

第二章中,主要讲述了交互式计算机图形设备与系统,交互式图形技术与用户接口,图形输入输出设备和图形软件的标准和发展历史。这一章中着重介绍了图形输入输出设备工作原理,几种输出设备工作方式的区别,什么是用户接口以及设计原则。

在接下来的三个章节中,主要学习到了直线的扫描转换,与之相关的多种算法—DDA画线法,Bresenham画线法,中点画线法。圆与椭圆的扫描转换,圆的三种画法,两种用自带函数的画法和圆的八分画法,即将圆分等分八份,由此引出椭圆的四分画法,圆的扫描转换算法中介绍了两种算法,分别为中点圆和Bresenham画圆法,椭圆的中点画法。由这些算法画出来的图形,在显示的时候会呈现出锯齿状,这是因为线是有一个个像素点构成的,所以再接下来老师介绍了发走样技术,是画出来的图形,如何更细腻,更平滑。后续课程中又学习到了填充技术,如何将画好的图形,通过某种算法为其填充颜色,三种算法分别为扫描转换填充,区域填充,边缘填充,扫描转换填充又分为有效边表法和逐点判别法。在此基础上后续章节又介绍了如何进行多边形的裁剪。分为边界裁剪法,逐边裁剪法,双边裁剪法,双区编码裁剪法。最后学习了坐标的转换方法。

第二章 虚拟现实技术的发展与应用

1.虚拟现实技术简介 虚拟现实(简称VR),又称灵境技术, 是以浸没感、交互性和构想为基本特征的计算机高级人机界面,是迅速发展的一项综合性计算机、图形交互技术。它综合利用了计算机图形学、仿真技术、多媒体技术、人工智能技术、计算机网络技术、并行处理技术和多传感器技术,模拟人的视觉、听觉、触觉等感官功能,使人能够沉浸在计算机生成的虚拟境界中,并能够通过语言、手势等自然的方式与之进行实时交互,创建了一种适人化的多维信息空间。使用者不仅能够通过虚拟现实系统感受到在客观物理世界中所经历的“身临其境”的逼真性,而且

[3]能够突破空间、时间以及其他客观限制,感受到在真实世界中无法亲身经历的体验。

计算机技术的迅速发展为我们提供了许多解决问题的新方法。虚拟现实技术的产生与发 2

展也同样如此,目前虚拟现实系统的研究现状主要涉及到三个研究领域:依靠计算机图形方式建立实时的三维视觉效果、构建对虚拟世界的观察界面和使用虚拟现实技术加强其在现实世界中的应用。

2.虚拟现实技术的发展历程 [3]

19xx年,Sutherland在篇名为<<终极的显示>>的论文中首次提出了包括具有交互图形显示、力反馈设备以及声音提示的虚拟现实系统的基本思想,从此,人们正式开始了对虚拟现实系统的研究探索历程。

随后的19xx年,美国MIT的林肯实验室正式开始了头盔式显示器的研制工作。在这第一个HMD的样机完成不久,研制者又把能模拟力量和触觉的力反馈装置加入到这个系统中。19xx年,出现了第一个功能较齐全的HMD系统。基于从60年代以来所取得的一系列成就,美国的Jaron Lanier 在80年代初正式提出了“Virtual Reality”一词。

80年代,美国宇航局(NASA)及美国国防部组织了一系列有关虚拟现实技术的研究,并取得了令人瞩目的研究成果,从而引起了人们对虚拟现实技术的广泛关注。19xx年,NASA Ames研究中心虚拟行星探测实验室的M.McGreevy 和J.Humphries博士组织开发了用于火星探测的虚拟环境视觉显示器,将火星探测器发回的数据输入计算机,为地面研究人员构造了火星表面的三维虚拟环境。在随后的虚拟交互环境工作站(VIEW)项目中,他们又开发了通用多传感个人仿真器和遥现设备。

进入90年代,迅速发展的计算机硬件技术与不断改进的计算机软件系统相匹配,使得基于大型数据集合的声音和图象的实时动画制作成为可能;人机交互系统的设计不断创新,新颖、实用的输入输出设备不断地进入市场。而这些都为虚拟现实系统的发展打下了良好的基础。例如19xx年的11月,宇航员利用虚拟现实系统成功地完成了从航天飞机的运输舱内取出新的望远镜面板的工作,而用虚拟现实技术设计波音777获得成功,是近年来引起科技界瞩目的又一件工作。可以看出,正是因为虚拟现实系统极其广泛的应用领域,如娱乐、军事、航天、设计、生产制造、信息管理、商贸、建筑、医疗保险、危险及恶劣环境下的遥操作、教育与培训、信息可视化以及远程通讯等,人们对迅速发展中的虚拟现实系统的广阔应用前景充满了憧憬与兴趣。

3.虚拟现实系统的构成[6]

虚拟现实系统的模型表示(如图3-1-1)。用户通过传感装置直接对虚拟环境进行操作,并得到实时三维显示和其它 反馈信息(如触觉、力觉反馈等)。当系统与外部世界通过传感装置构成反馈闭环时,在用户的控制下,用户与虚拟环境间的交互可以对外部世界产生作用(如遥操作等)。

3

图3-1-1虚拟现实系统的模型

虚拟现实系统主要由以下六个模块构成(如图3-1-2)。

计算机图形学报告

图3-1-2虚拟现实系统的构成

1.检测模块:检测用户的操作命令,并通过传感器模块作用于虚拟环境。

2.反馈模块:接受来自传感器模块信息,为用户提供实时反馈。

3.传感器模块:一方面接受来自用户的操作命令,并将其作用于虚拟环境;另一方面 将操作后产生的结果以各种反馈的形式提供给用户。

4.控制模块:对传感器进行控制,使其对用户、虚拟环境和现实世界产生作用。 建模模块:获取现实世界组成部分的三维表示,并由此构成对应的虚拟环境。

4.当今虚拟现实技术的应用领域

虚拟现实技术的应用前景十分广阔。目前在娱乐、教育及艺术领域的应用占据主流,其次是军事与航空、医学领域,机器人和商业领域都占有一定比例,另外在可视化计算、制造业等领域也有相当的比重。下面简要介绍其部分应用。

4.1娱乐、艺术与教育领域

娱乐是虚拟现实技术应用最活跃的一个领域,包括家庭中的桌面游戏、公共场所的各种仿真等,基于虚拟现实技术的游戏主要有驾驶型游戏、作战型游戏和智力型游戏,很多游戏都是联网的,因而允许许多玩游戏的人同时进入一个虚拟境界,相互之间可展开竞争,或者

[2](与计算机生成的对手竞争如下图4-1-1)。

4

计算机图形学报告

图4-1-1

4.2军事与航天工业领域

虚拟作战仿真可以解决部队高质量的训练问题。它不但可以不动用实际装备而使受训人员具有身临其境之感;它可以任意设置战斗环境背景,对作战人员进行同一作战环境,同一作战预案的多次重复训练,还可进行不同作战环境,不同作战预案的训练,使作战人员迅速地积累丰富的作战经验,同时不担任何风险。

模拟演练一直是军事与航天工业中的一个重要课题,有些演练受限于很多方面,在现实中实现是一件很麻烦的事情,比如一个飞行员,在学习玩理论知识后,不可能马上就上飞机就行飞行训练(如下图3-2-1),又如航天员进行飞行训练,不可能总要发射飞船升空,这为就为虚拟现实技术提供了广阔的应用前景。

计算机图形学报告

图4-2-1

4.3 医学领域

虚拟现实技术在医学方面的应用具有十分重要的现实意义。在虚拟环境中,可以建立虚拟的人体模型,借助于跟踪球、HMD、感觉手套,人们可以很容易了解人体内部各器官结构,这比现有的采用教科书的方式要有效得多(如下图4-3-1)。

Pieper及Satara等研究者在90年代初基于两个SGI工作站建立了一个虚拟外科手术训练器,用于腿部及腹部外科手术模拟。这个虚拟的环境包括虚拟的手术台与手术灯,虚拟的外科工具(如手术刀、注射器、手术钳等),虚拟的人体模型与器官等。借助于HMD及感觉手

[4]套,使用者可以对虚拟的人体模型进行手术(如下图4-3-2)。

另外,在远距离遥控外科手术,复杂手术的计划安排,手术过程的信息指导,手术后果预测及改善残疾人生恬状况,乃至新型药物的研制等方面,VR技术都有十分重要的意义。

计算机图形学报告

5

图4-3-1图4-3-2

4.4建筑工程领域

虚拟现实技术在管理工程方面也显示出了无与伦比的优越性。如设计一新型建筑物时,可以在建筑物动工之前用虚拟现实技术技术显示一下,便可把业主带入未来的建筑物里参观,如门的高度、窗户朝向、采光多少、屋内装饰等,都可以感同身受(如下图4-4-2)。它同样可用于旅游景点以及功能众多、用途多样的商品推销(如下图4-4-1)

计算机图形学报告

。因为用虚拟现实技术展现这类商品的魅力,

计算机图形学报告

比单用文字或图片宣传更加有吸引力。先如今很多校园都开设了虚拟校园功能,该功能就是应用虚拟现实技术,模拟出整个校园,让游客身临其境,改变了平面地图带来的缺乏立体感的缺点。

图4-4-1

图4-4-2

5.虚拟现实技术的进一步展望

虚拟现实从其萌芽到今天的日渐成熟已经走过了相当长的一段风雨历程。目前它的研究内容涉及到多项学科领域。它的研究内容涉及到人工智能、计算机科学、电子学、传感器、计算机图形学、智能控制、心理学等我们同时也认识到,这个领域的技术具有巨大的潜力和

计算机图形学报告

6

广阔的应用前景。目前,虚拟现实技术在一些领域获得了比较成熟的实际应用,但它仍处于初级发展阶段,然而对它的研究开发已日渐升温.美国在20xx年前重点发展十项高新电子技术,而居十项技术之首的就是虚拟现实技术。21世纪将是虚拟现实技术的时代,相信在不久

[5]的将来,人们会轻松地遨游于多维化的信息世界中,领略人类高科技的魅力。

第三章《计算机图形学》学习心得与体会

通过这门课程的学习,让我对计算机的应用又有了新的认识,对于图形学中基本图形的生成算法有了一定的了解,图形学是计算机科学与技术学科的活跃前沿学科,被广泛的应用到生物学、物理学、化学、天文学、地球物理学、材料科学等领域。我深深感到这门学科涉及的领域之广是惊人的,可以说博大精深。

我觉得这门课不单是一门介绍 计算机在其他领域应用的课程,更是对我们以前所学知识的一次考察和升华,在这门课程中,学习到了很多与画图有关的算法,在学习这些算法过程中也同时考察了我们的编程思维和动手能力,学习再多的理论知识,不去实践是不行的,所以这门课让我认识到实践的重要性。对于计算机专业的同学来说具备独立思考解决问题的能力是很重要,理论与实践相结合,只有自己独立的去做,反复的调试,才能领悟到这里面的奥秘,在老师布置的画五角星作业中,刚开始也是无从下手,但是冷静下来,恢复以前所学习的知识,运用以前所学习的编程知识,最终还是做了出来,所以,我觉得这门课对我们的提高自己动手实践能力和独立思考能力有很大的帮助。同时,也让我充分的认识到了当今世界是离不开计算机的,计算机活跃在任何领域,在每一个领域中都扮演者举足轻重的角色,这对我们日后的就业提升了很大的空间。学习玩这门课程,也让我感到自己现在所学知识还是远远不够的,但凭课本上和课堂上的知识量,对于一个计算机专业的学生是远远不够的。

这也警醒了我,在掌握基本知识的同时要时时刻刻关注行业动态,多了解计算机行 业的新技术,这对我们将来也是很有帮助的。

参考文献

[1]孔令德.计算机图形学实践教程(Visual C++版)),清华大学出版社,2008

[2]吴家铸,党岗,刘华峰等 视景仿真技术及其应用 西安电子科技大学出版社,2006

[3]汪成为,高文,王行仁 虚拟现实技术的理论、实现及应用 清华大学出版社,2008

[4] 党保生.虚拟现实及其发展趋势.中国现代教育装备,2007

[5] 佟晓妍.虚拟现实技术的应用及其展望. 内蒙古科技与经济,2007

[6]曾建超,俞志和. 虚拟现实的技术及其应用 清华大学出版社,1996

7

 

第二篇:计算机图形学期末报告

《计算机图形学》课程报告 课题名称: Solar System

课题负责人名(学号): 苟丁 0843042229 同组成员名单(角色): 无

指导教师: 李 征 评阅成绩: 评阅意见:

提交报告时间: 2010 年 12 月 20 日

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

Solar System

软件工程 专业

学生 苟 丁 指导老师 李 征

[摘要] 程序的框架使用了面向对象的设计思想,并使用windows API

函数和OpenGL函数模拟太阳系,程序实现了各大行星的公转和自转,并且可以自由控制摄像机的观测位置来漫游太阳系。

关键词:计算机图形学 OpenGL 模拟太阳系

一.序言

虚拟现实(Virtual Reality,简称VR,又译作灵境、幻真)是近年来出现的高新技术,也称灵境技术或人工环境。虚拟现实是利用电脑模拟产生一个三维空间的虚拟世界,提供使用者关于视觉、听觉、触觉等感官的模拟,让使用者如同身历其境一般,可以及时、没有限制地观察三度空间内的事物

早在60年代初,随着CAD技术的发展,人们就开始研究立体声与三维立体显示相结合的计算机系统。80年代,Jaron Lanier提出了"虚拟现实"VR(Virtual Reality)的观点,目的在于建立一种新的用户界面,使用户可以置身于计算机所表示的三维空间资料库环境中,并可以通过眼、手、耳或特殊的空间三维装置在这个环境中"环游",创造出一种"亲临其境"的感觉。

-1-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

二.图形学基本原理

1. 几何变换相关原理

应用于对象几何描述并改变它的位置、方向或大小的操作称为几

何变换。几何变换能用描述动画序列中对象在场景中可以怎样移动或者简单地从另一角度观察他们。

平移、旋转和缩放是所有图形软件包中都含有的几何变换函数. 三维平移:

在三维齐次坐标表示中,任意点P=(x,y,z)通过将平移距离tx,ty,tz加到P的坐标上而平移到位置P’=(x’y’z’):

x’=x+tx, y’=y+ty, z’=z+tz.

三维旋转:

绕z轴旋转的二维旋转很容易推广到三维:

x’

计算机图形学期末报告

=xcos

计算机图形学期末报告

y’

计算机图形学期末报告

=xsin

计算机图形学期末报告

z’=z

相同的原理绕x,y轴与之类似。

一般三维旋转:

可以通过下列变换序列来得到所需的旋转矩阵:

1. 平移对象使其旋转轴与平行与该轴的一个坐标轴重合;

2. 对于该轴完成指定的旋转;

3. 平移对象将其旋转轴移回到原来的位置。

若给定旋转轴和旋转角,我们可以按照5个步骤来完成所需的旋转:

1.

2.

3.

4.

5.

-ysin+ycos 平移对象,使得旋转轴通过坐标原点; 旋转对象使得旋转轴与某一坐标重合; 绕坐标轴完成指定的旋转; 利用逆旋转使得旋转轴回到其原始方向; 利用逆平移使旋转轴回到其原始位置。 -2-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

三维缩放:

点P=(x,y,z)相对于坐标原点的三维缩放是二维缩放的简单扩

充。只要在变换矩阵中引入z坐标缩放参数中:

我们可以使用下列变换序列进行相对于任意给定点(xf,yf,zf)的缩放变换:

1.

2.

3. 平移给定点到原点; 使用上面的等式,相对于坐标原点所放对象; 平移给定点回到原始位置。

2. 几何图形像素化相关原理

1. “走样”的概念

答:光栅是由离散的点组成的,在光栅显示设备上表现直线、多边形等,必须在离散的位置采样,由于采样不充分重建后造成的信息失真,就是走样。

2. 反走样方法

答:首先将象素均匀分割成n个子象素。则每个象素的面积为1/n。计算每个子象素对原象素的贡献,并保存在一张二维的加权表中。然后求出所有中心落于直线段内的子象素。最后计算所有这些子像素对原像素亮度贡献之和∑wi的值,该值乘以最大灰度值作为该象素的显示灰度值。

3.光照模型相关原理

光照模型,主要用于对象表面某光照位置的颜色计算

任一发出辐射能量的对象称为光源,辐射光线从一点光源出发

并在空间传播,光线将会衰减,假设距离为d1。可使用下列公式来

计算机图形学期末报告

-3-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

表现光源强度:

Fradatten(d1)=1/(a0+a1d1+a2d12)

用户可以调整a0,a1,a2的值得到不同的光照效果。

光照模型使用为表面设定的各种光学特性来计算表面光照效果。这些特性包括透明度 、颜色、反射系数以及各种表面纹理参数。 场景中的背景光或环境光是光照模型中必须考虑的另一因素。

三.系统界面与操作说明

(1)系统界面与图形显示示例

计算机图形学期末报告

-4-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

2)操作说明

Up:向前走

Down:向后退

计算机图形学期末报告

-5-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

Left:向左转

Right:向右转

计算机图形学期末报告

-6-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

PgUp:抬头

PgDown:低头

计算机图形学期末报告

-7-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

四.源程序

1.系统总体框架

2..源程序与注释

//Stdafx.h

#pragma once

#include <Windows.h>

#include <iostream>

#include <gl/glut.h>

#include <cmath>

#define NUM_TEXTURES 11

#define DEG_TO_RAD 0.017453

#define KEY_DOWN(vk_code) ((GetAsyncKeyState(vk_code) & 0x8000) ? 1 : 0)

using namespace std;

//DataType.h

#pragma once

/*-------------

类型定义

--------------*/

// 纹理图像结构

struct TEXTUREIMAGE

计算机图形学期末报告

{

-8-

课程名称:计算机图形学

};

// BMP文件头 #pragma pack(2)

struct BMPFILEHEADER {

};

#pragma pack()

// BMP信息头

struct BMPINFOHEADER{

};

// 材质结构

struct MATERIAL {

float ambient[4]; float diffuse[4]; float specular[4]; unsigned long biSize; long long biWidth; biHeight; unsigned short unsigned short unsigned short bfType; int imgWidth; int imgHeight; 学生姓名:苟丁 // 纹理宽度 // 纹理高度 学生学号:0843042229 unsigned char byteCount; // 每个象素对应的字节数,:位图,:带alpha通道的unsigned char *data; // 纹理数据 位图 // 文件类型 // 文件大小 unsigned long bfSize; bfReserved1; // 保留位 bfReserved2; // 保留位 // 数据偏移位置 unsigned long bfOffBits; // 此结构大小 // 图像宽度 // 图像高度 // 调色板数量 unsigned short unsigned short biPlanes; biBitCount; // 每个象素对应的位数,:位图,:带alpha通道// 压缩 // 图像大小 的位图 unsigned long biCompression; unsigned long biSizeImage; long long biXPelsPerMeter; // 横向分辨率 biYPelsPerMeter; // 纵向分辨率 // 颜色使用数 unsigned long biClrUsed; unsigned long biClrImportant; // 重要颜色数 // 环境光反射 // 漫反射 // 镜面反射 -9-

课程名称:计算机图形学

};

// 光照结构 struct LIGHT { };

//CObject.h #pragma once #include "Stdafx.h" #include "DataType.h" class CObject { public:

CObject();

virtual ~CObject(); float lightAmbient[4]; float lightDiffuse[4]; float lightSpecular[4]; float lightPosition[4];

float shininess;

学生姓名:苟丁

// 镜面反射强度

学生学号:0843042229

// 环境光参数 // 漫射光参数 // 镜面光参数 // 光源位置

void SetMaterial(GLfloat* ambient,GLfloat* diffuse,GLfloat* specular,GLfloat

//设置材质

//设置纹理

//设置自转速度 //设置公转速度 //设置半径

//获取距离太阳的长度(太阳

MATERIAL* GetMaterial();

void SetTexture(char* fileName); TEXTUREIMAGE* GetTexture(); GLfloat GetSRotation() const; void SetSRevolution(GLfloat rev); GLfloat GetSRevolution() const; GLfloat GetRadius() const; void SetRadius(GLfloat rad); GLfloat GetDistanceToSun() const;

void SetSRotation(GLfloat rot);

shinness);

在世界坐标的中心) protected: };

-10-

GLfloat radius; GLfloat distanceToSun; MATERIAL material; TEXTUREIMAGE* texture; GLfloat sRotation; GLfloat sRevolution;

课程名称:计算机图形学

//CObject.cpp

#include "CObject.h"

学生姓名:苟丁 学生学号:0843042229

CObject::CObject():radius(0.0f),sRotation(0.0),sRevolution(0.0),distanceToSun(0.0)

{

}

CObject::~CObject()

{

}

void CObject::SetMaterial(GLfloat *ambient, GLfloat *diffuse, GLfloat *specular, GLfloat shinness)

{

}

MATERIAL* CObject::GetMaterial()

{

}

void CObject::SetTexture(char* fileName)

{

int i, j; -11- return &material; for (int i = 0; i < 4; ++i) { } material.shininess = shinness; material.ambient[i] = ambient[i]; material.diffuse[i] = diffuse[i]; material.specular[i] = specular[i]; delete texture; texture = new TEXTUREIMAGE; texture->data = NULL; texture->imgHeight = 0; texture->imgWidth = 0; texture->byteCount = 0;

课程名称:计算机图形学

// 读取文件数据 // 打开文件 file = fopen(fileName, "rb"); if (file == NULL) { } // 获取文件头 rewind(file); return; texture->imgWidth = 0; texture->imgHeight = 0; if (texture->data != NULL) { } delete []texture->data; // 初始化纹理数据 FILE *file; BMPFILEHEADER bmpFile; BMPINFOHEADER bmpInfo; int pixel_size; 学生姓名:苟丁 学生学号:0843042229 fread(&bmpFile, sizeof(BMPFILEHEADER), 1, file); fread(&bmpInfo, sizeof(BMPINFOHEADER), 1, file); // 验证文件类型 if (bmpFile.bfType != 0x4D42) { } // 获取图像色彩数 pixel_size = bmpInfo.biBitCount >> 3; return; texture->data = new unsigned char[bmpInfo.biWidth * bmpInfo.biHeight * pixel_size]; for(i = 0 ; i < bmpInfo.biHeight; i++) { fseek(file, bmpFile.bfOffBits + (bmpInfo.biHeight - i - 1) *

bmpInfo.biWidth * pixel_size, SEEK_SET);

-12-

课程名称:计算机图形学

}

TEXTUREIMAGE* CObject::GetTexture() {

}

return texture; } // 记录图像相关参数 学生姓名:苟丁 学生学号:0843042229 for (j = 0; j < bmpInfo.biWidth; j++) { } // 红色分量 fread(texture->data + (i * bmpInfo.biWidth + j) * pixel_size + 2, // 绿色分量 fread(texture->data + (i * bmpInfo.biWidth + j) * pixel_size + 1, // 蓝色分量 fread(texture->data + (i * bmpInfo.biWidth + j) * pixel_size + 0, // Alpha分量 if (pixel_size == 4) { } fread(texture->data + (i * bmpInfo.biWidth + j) * pixel_size + sizeof(unsigned char), 1, file); sizeof(unsigned char), 1, file); sizeof(unsigned char), 1, file); 3, sizeof(unsigned char), 1, file); texture->imgWidth = bmpInfo.biWidth; texture->imgHeight = bmpInfo.biHeight; texture->byteCount = pixel_size; fclose(file);

void CObject::SetSRevolution(GLfloat rev) {

}

GLfloat CObject::GetSRotation() const {

}

-13- return sRotation; sRevolution -= rev;

课程名称:计算机图形学

学生姓名:苟丁 学生学号:0843042229

void CObject::SetSRotation(GLfloat rot) {

}

GLfloat CObject::GetSRevolution() const {

}

GLfloat CObject::GetRadius() const {

}

void CObject::SetRadius(GLfloat rad) {

}

GLfloat CObject::GetDistanceToSun() const {

}

//Earth.h

#pragma once

#include "CObject.h"

class Earth:public CObject

{

public:

};

//Earth.cpp

#include "Earth.h"

Earth::Earth()

-14- Earth(); ~Earth(); return distanceToSun; radius -= rad; return radius; return sRevolution; sRotation -= rot;

课程名称:计算机图形学

{

}

Earth::~Earth()

{

}

//Jupiter.h

#pragma once

#include "CObject.h"

class Jupiter:public CObject {

public:

};

//Jupiter.cpp

#include "Jupiter.h" Jupiter::Jupiter()

{

radius = 0.7; distanceToSun = -8.0; Jupiter(); ~Jupiter(); radius = 0.6; distanceToSun = -6.0; 学生姓名:苟丁 学生学号:0843042229 MATERIAL materialEarth = //地球 { }; SetMaterial(materialEarth.ambient,materialEarth.diffuse,materialEarth.spec{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0 ular,materialEarth.shininess); MATERIAL materialJupiter = //木星 { }; -15- {0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0

课程名称:计算机图形学

}

Jupiter::~Jupiter() {

}

//Mars.h

#pragma once

#include "CObject.h"

class Mars:public CObject {

public:

};

//Mars.cpp

#include "Mars.h" Mars::Mars()

{

}

Mars::~Mars()

{

}

//Mercu.h

#pragma once

radius = 0.3; distanceToSun = -7.0; Mars(); ~Mars(); 学生姓名:苟丁 学生学号:0843042229 SetMaterial(materialJupiter.ambient,materialJupiter.diffuse,materialJupiter.specular,materialJupiter.shininess); MATERIAL materialMars = //火星 { }; SetMaterial(materialMars.ambient,materialMars.diffuse,materialMars.specula{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0 r,materialMars.shininess); -16-

课程名称:计算机图形学

#include "CObject.h"

class Mercu:public CObject {

public:

};

//Mercu.cpp

#include "Mercu.h" Mercu::Mercu()

{

}

Mercu::~Mercu()

{

}

//Moon.h

#pragma once

#include "CObject.h"

class Moon:public CObject {

public:

};

Moon(); ~Moon(); GLfloat GetDistanceToEarth(); GLfloat distanceToEarth; radius = 0.3; distanceToSun = -3.0f; Mercu(); ~Mercu(); 学生姓名:苟丁 学生学号:0843042229 MATERIAL materialMercu = //水星 { }; SetMaterial(materialMercu.ambient,materialMercu.diffuse,materialMercu.spec{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0 ular,materialMercu.shininess); private: -17-

课程名称:计算机图形学

//Moon.cpp

#include "Moon.h"

Moon::Moon()

{

}

GLfloat Moon::GetDistanceToEarth() {

}

Moon::~Moon()

{

}

//Neptune.h

#pragma once

#include "CObject.h"

class Neptune:public CObject {

public:

};

//Neptune.cpp

#include "Neptune.h"

Neptune(); ~Neptune(); return distanceToEarth; radius = 0.2; distanceToEarth = -0.9; 学生姓名:苟丁 学生学号:0843042229 MATERIAL materialMoon = //月亮 { }; SetMaterial(materialMoon.ambient,materialMoon.diffuse,materialMoon.specula{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 0.0 r,materialMoon.shininess); -18-

课程名称:计算机图形学

Neptune::Neptune() {

}

Neptune::~Neptune() {

}

//Saturn.h

#pragma once

#include "CObject.h"

class Saturn:public CObject {

public:

};

//Saturn.h

#include "Saturn.h" Saturn::Saturn()

{

radius = 0.7; distanceToSun = -9.0; Saturn(); ~Saturn(); radius = 0.6; distanceToSun = -11.0; 学生姓名:苟丁 学生学号:0843042229 MATERIAL materialNeptune = //海王星 { }; SetMaterial(materialNeptune.ambient,materialNeptune.diffuse,materialNeptun{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0 e.specular,materialNeptune.shininess); MATERIAL materialSaturn = //土星 { {0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, -19-

课程名称:计算机图形学

}

Saturn::~Saturn() {

}

//Space.h

#pragma once

#include "CObject.h"

class Space:public CObject {

public:

};

//Space.cpp

#include "Space.h"

Space::Space()

{

}

Space::~Space()

{

}

//Sun.h

#pragma once

radius = 100; Space(); ~Space(); }; 100.0 学生姓名:苟丁 学生学号:0843042229 SetMaterial(materialSaturn.ambient,materialSaturn.diffuse,materialSaturn.specular,materialSaturn.shininess); MATERIAL materialSpace = //空间 { }; SetMaterial(materialSpace.ambient,materialSpace.diffuse,materialSpace.spec{0.4, 0.4, 0.4, 1.0}, {0.0, 0.0, 0.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 0.0 ular,materialSpace.shininess); -20-

课程名称:计算机图形学

#include "CObject.h"

class Sun:public CObject {

public:

};

//Sun.cpp

#include "Sun.h"

Sun::Sun()

{

}

Sun::~Sun()

{

}

//Uranus.h

#pragma once

#include "CObject.h"

class Uranus:public CObject {

public:

};

//Uranus.cpp

#include "Uranus.h" Uranus::Uranus()

{

Uranus(); ~Uranus(); radius = 2; Sun(); ~Sun(); 学生姓名:苟丁 学生学号:0843042229 MATERIAL materialSun = //太阳 { }; SetMaterial(materialSun.ambient,materialSun.diffuse,materialSun.specular,m{100.0, 100.0, 100.0, 20.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 0.0 aterialSun.shininess); -21-

课程名称:计算机图形学

}

Uranus::~Uranus()

{

}

//Venus.h

#pragma once

#include "CObject.h"

class Venus:public CObject

{

public:

};

//Venus.cpp

#include "Venus.h"

Venus::Venus()

{

radius = 0.5; distanceToSun = -4.5; Venus(); ~Venus(); radius = 0.7; distanceToSun = -10.0; 学生姓名:苟丁 学生学号:0843042229 MATERIAL materialUranus = //天王星 { }; SetMaterial(materialUranus.ambient,materialUranus.diffuse,materialUranus.s{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0 pecular,materialUranus.shininess); MATERIAL materialVenus = //金星 { }; SetMaterial(materialVenus.ambient,materialVenus.diffuse,materialVenus.spec{0.1, 0.1, 0.1, 1.0}, {1.0, 1.0, 1.0, 1.0}, {0.0, 0.0, 0.0, 1.0}, 100.0 ular,materialVenus.shininess);

-22-

课程名称:计算机图形学

}

Venus::~Venus() {

}

//Draw.h

#pragma once

#include "Space.h" #include "Sun.h" #include "Mercu.h" #include "Venus.h" #include "Earth.h" #include "Moon.h" #include "Mars.h" #include "Jupiter.h" #include "Saturn.h" #include "Uranus.h" #include "Neptune.h"

class Draw

{

public:

//GLuint CreateDL(); void DrawAll(); void Run(); bool Clean(); ~Draw(); Space* space; Sun* sun; Mercu* mercu; Venus* venus; Earth* earth; Moon* moon; Draw(); bool SetupPixelFormat(HDC hDCO); void LoadTextures(); void InitLight(); 学生姓名:苟丁 学生学号:0843042229 private: -23-

课程名称:计算机图形学

};

//Draw.cpp

#include "Draw.h"

extern HDC hDC;

hWnd; inline void DrawSpace(); inline void DrawSun(); inline void DrawMercu(); inline void DrawVenus(); inline void DrawEarth(); inline void DrawMoon(); inline void DrawMars(); inline void DrawJupiter(); inline void DrawSaturn(); inline void DrawUranus(); inline void DrawNeptune(); Mars* mars; Jupiter* jupiter; Saturn* saturn; Uranus* uranus; Neptune* neptune; 学生姓名:苟丁 学生学号:0843042229 GLuint textureObjects[NUM_TEXTURES]; inline void DrawCircle(GLfloat fRadius, GLint iSlices, GLint iStacks); inline void DrawTrack(CObject* obj); void InitMaterials(CObject* obj); void InitTextures(CObject* obj,GLuint * texName); // GDI设备句柄,将窗口连接到GDI( 图形设备接口) // 保存Windows 分配给程序的窗口句柄 extern HGLRC hRC; // 渲染描述句柄,将OpenGL调用连接到设备描述表 extern HWND

Draw::Draw()

{

space = new Space; sun = new Sun; mercu = new Mercu; venus = new Venus; -24-

课程名称:计算机图形学

earth = new Earth; moon = new Moon; mars = new Mars;

jupiter = new Jupiter; saturn = new Saturn; uranus = new Uranus; neptune = new Neptune; }

Draw::~Draw()

{

if (space)

{

delete space; }

if (sun)

{

delete sun; }

if (mercu)

{

delete mercu; }

if (venus)

{

delete venus; }

if (earth)

{

delete earth; }

if (moon)

{

delete moon; }

if (mars)

{

delete mars; }

if (jupiter)

{

学生姓名:苟丁 学生学号:0843042229 -25-

课程名称:计算机图形学

}

void Draw::LoadTextures() {

/*载入纹理并设置*/ space->SetTexture("space.bmp"); sun->SetTexture("Sun.bmp"); mercu->SetTexture("Mercu.bmp"); venus->SetTexture("Venus.bmp"); earth->SetTexture("Earth.bmp"); moon->SetTexture("Moon.bmp"); mars->SetTexture("Mars.bmp"); } if (saturn) { } if (uranus) { } if (neptune) { } delete neptune; delete uranus; delete saturn; delete jupiter; 学生姓名:苟丁 学生学号:0843042229 jupiter->SetTexture("Jupiter.bmp"); saturn->SetTexture("Saturn.bmp"); uranus->SetTexture("Uranus.bmp"); neptune->SetTexture("Neptune.bmp"); InitTextures(space,&textureObjects[0]); InitTextures(sun,&textureObjects[1]); InitTextures(mercu,&textureObjects[2]); InitTextures(venus,&textureObjects[3]); InitTextures(earth,&textureObjects[4]); InitTextures(moon,&textureObjects[5]); InitTextures(mars,&textureObjects[6]); InitTextures(jupiter,&textureObjects[7]); InitTextures(saturn,&textureObjects[8]); InitTextures(uranus,&textureObjects[9]); InitTextures(neptune,&textureObjects[10]); -26-

课程名称:计算机图形学

}

学生姓名:苟丁 学生学号:0843042229

void Draw::InitTextures(CObject* obj , GLuint * texName) {

}

void Draw::InitMaterials(CObject* obj)

{

}

void Draw::InitLight()

{

}

-27- glEnable(GL_LIGHTING);//启用光照模型 glEnable(GL_LIGHT0);//启用号光源 glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient); glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse); glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular); GLfloat light_ambient[]={1.0, 1.0, 1.0, 1.0}; GLfloat light_diffuse[]={1.0, 1.0, 1.0, 1.0}; GLfloat light_specular[]={1.0, 1.0, 1.0, 1.0}; glMaterialfv(GL_FRONT, GL_SPECULAR,obj->GetMaterial()->specular); glMaterialfv(GL_FRONT, GL_AMBIENT, obj->GetMaterial()->ambient); glMaterialfv(GL_FRONT, GL_DIFFUSE, obj->GetMaterial()->diffuse); glMaterialf(GL_FRONT, GL_SHININESS,obj->GetMaterial()->shininess); glPixelStorei(GL_UNPACK_ALIGNMENT, 1); glGenTextures(1,texName); glBindTexture(GL_TEXTURE_2D , *texName); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, GL_RGB, GL_UNSIGNED_BYTE, obj->GetTexture()->data); obj->GetTexture()->imgWidth,obj->GetTexture()->imgHeight, 0,

课程名称:计算机图形学

bool Draw::SetupPixelFormat(HDC hDCO) {

} int nPixelFormat; hDC=hDCO; PIXELFORMATDESCRIPTOR pfd = { }; 学生姓名:苟丁 学生学号:0843042229 // 象素点格式 sizeof(PIXELFORMATDESCRIPTOR), // pfd结构的大小 1, // 版本号 PFD_DRAW_TO_WINDOW | // 支持在窗口中绘图 PFD_SUPPORT_OPENGL | // 支持OpenGL PFD_DOUBLEBUFFER, // 双缓存模式 PFD_TYPE_RGBA, // RGBA 颜色模式 16, // 16 位颜色深度 0, 0, 0, 0, 0, 0, // 忽略颜色位 0, // 没有非透明度缓存 0, // 忽略移位位 0, // 无累加缓存 0, 0, 0, 0, // 忽略累加位 16, // 16 位深度缓存 0, // 无模板缓存 0, // 无辅助缓存 PFD_MAIN_PLANE, // 主层 0, // 保留 0, 0, 0 // 忽略层,可见性和损毁掩模 if (!(nPixelFormat = ChoosePixelFormat(hDC, &pfd))) { } if (!SetPixelFormat(hDC,nPixelFormat,&pfd))//设置当前设备的像素点格式 { MessageBox(NULL,"设置当前设备的像素点格式失败return FALSE; MessageBox(NULL,"没找到合适的显示模式return FALSE; ","Error",MB_OK|MB_ICONEXCLAMATION); ","Error",MB_OK|MB_ICONEXCLAMATION); if (!(hRC = wglCreateContext(hDC))) //获取渲染描述句柄 { MessageBox(NULL,"获取渲染描述句柄失败","Error",MB_OK|MB_ICONEXCLAMATION);

-28-

课程名称:计算机图形学

}

void Draw::DrawAll()

{

}

void Draw::DrawTrack(CObject* obj) {

}

void Draw::DrawSpace()

{

InitMaterials(space); /*画出轨道*/ glBegin(GL_LINE_LOOP); /*画出所有物体*/ DrawSun(); DrawMercu(); DrawVenus(); DrawEarth(); DrawMoon(); DrawMars(); DrawJupiter(); DrawSaturn(); DrawNeptune(); DrawSpace(); } return FALSE; 学生姓名:苟丁 学生学号:0843042229 if (!wglMakeCurrent(hDC, hRC)) //激活渲染描述句柄 { MessageBox(NULL,"激活渲染描述句柄失败return FALSE; ","Error",MB_OK|MB_ICONEXCLAMATION); } return TRUE; for(int angle=0;angle<=360;angle++) glVertex3f(obj->GetDistanceToSun()*sin(DEG_TO_RAD*angle),0,obj->GetDistanc glEnd(); eToSun()*cos(DEG_TO_RAD*angle)); -29-

课程名称:计算机图形学

}

void Draw::DrawSun() {

}

void Draw::DrawMercu() {

}

void Draw::DrawVenus() {

glPushMatrix(); glColor3f(192,122,24); InitMaterials(venus); DrawTrack(mercu); glPushMatrix(); glColor3f(192,122,24); InitMaterials(mercu); glPushMatrix(); InitMaterials(sun); glPushMatrix(); glRotatef(90.0f,1.0f,1.0f,0.0f); 学生姓名:苟丁 学生学号:0843042229 glBindTexture(GL_TEXTURE_2D,textureObjects[0]); DrawCircle(space->GetRadius(),100,100); glPopMatrix(); glRotatef(sun->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[1]); DrawCircle(sun->GetRadius(),200,200); glPopMatrix(); glRotatef(mercu->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0f,0.0f,mercu->GetDistanceToSun()); glRotatef(mercu->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[2]); DrawCircle(mercu->GetRadius(),150,200); glPopMatrix(); -30-

课程名称:计算机图形学

}

void Draw::DrawEarth() {

}

void Draw::DrawMoon() {

}

void Draw::DrawMars()

InitMaterials(moon); glPushMatrix(); DrawTrack(earth); glPushMatrix(); InitMaterials(earth); DrawTrack(venus); 学生姓名:苟丁 学生学号:0843042229 glRotatef(venus->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0f,0.0f,venus->GetDistanceToSun()); glRotatef(venus->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[3]); DrawCircle(venus->GetRadius(),150,200); glPopMatrix(); glRotatef(earth->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0f,0.0f,earth->GetDistanceToSun()); glRotatef(earth->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[4]); DrawCircle(earth->GetRadius(),100,100); glPopMatrix(); glRotatef(earth->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0f,0.0f,earth->GetDistanceToSun()); glRotatef(moon->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0f,0.0f,moon->GetDistanceToEarth()); glRotatef(moon->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[5]); DrawCircle(moon->GetRadius(),50,20); glPopMatrix(); -31-

课程名称:计算机图形学

{

}

void Draw::DrawJupiter() {

}

void Draw::DrawSaturn() {

glPushMatrix(); InitMaterials(saturn); glColor3f(192,122,24); DrawTrack(jupiter); glPushMatrix(); InitMaterials(jupiter); glColor3f(192,122,24); DrawTrack(mars); glPushMatrix(); InitMaterials(mars); glColor3f(192,122,24); 学生姓名:苟丁 学生学号:0843042229 glRotatef(mars->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0f,0.0f,mars->GetDistanceToSun()); glRotatef(mars->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[6]); DrawCircle(mars->GetRadius(),150,200); glPopMatrix(); glRotatef(jupiter->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0,0.0,jupiter->GetDistanceToSun()); glRotatef(jupiter->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D , textureObjects[7]); DrawCircle(jupiter->GetRadius(),150,200); glPopMatrix(); glRotatef(saturn->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0,0.0,saturn->GetDistanceToSun()); glRotatef(saturn->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D , textureObjects[8]); -32-

课程名称:计算机图形学

}

void Draw::DrawUranus() {

}

void Draw::DrawNeptune() {

}

void Draw::Run() {

sun->SetSRotation(1.0f); DrawTrack(neptune); glPushMatrix(); InitMaterials(neptune); glColor3f(192,122,24); DrawTrack(uranus); glPushMatrix(); InitMaterials(uranus); glColor3f(192,122,24); DrawTrack(saturn); 学生姓名:苟丁 学生学号:0843042229 DrawCircle(saturn->GetRadius(),150,200); glPopMatrix(); glRotatef(uranus->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0,0.0,uranus->GetDistanceToSun()); glRotatef(uranus->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[9]); DrawCircle(uranus->GetRadius(),150,200); glPopMatrix(); glRotatef(neptune->GetSRevolution(),0.0,1.0,0.0); glTranslatef(0.0,0.0,neptune->GetDistanceToSun()); glRotatef(neptune->GetSRotation(),0.0,1.0,0.0); glBindTexture(GL_TEXTURE_2D,textureObjects[10]); DrawCircle(neptune->GetRadius(),150,200); glPopMatrix(); -33-

课程名称:计算机图形学

}

neptune->SetSRotation(40.0f); neptune->SetSRevolution(5.0f); uranus->SetSRotation(70.0f); uranus->SetSRevolution(15.0f); saturn->SetSRotation(90.0f); saturn->SetSRevolution(25.0f); jupiter->SetSRotation(90.0f); jupiter->SetSRevolution(35.0f); mars->SetSRotation(30.0f); mars->SetSRevolution(50.0f); moon->SetSRotation(50.0f); moon->SetSRevolution(200.0f); earth->SetSRotation(100.0f); earth->SetSRevolution(20.0f); venus->SetSRotation(10.0f); venus->SetSRevolution(30.0f); mercu->SetSRotation(15.0f); mercu->SetSRevolution(40.0f); 学生姓名:苟丁 学生学号:0843042229

void Draw::DrawCircle(GLfloat fRadius, GLint iSlices, GLint iStacks) {

GLfloat drho = (GLfloat)(3.141592653589) / (GLfloat) iStacks; GLfloat dtheta = 2.0f * (GLfloat)(3.141592653589) / (GLfloat) iSlices; GLfloat ds = 1.0f / (GLfloat) iSlices; GLfloat dt = 1.0f / (GLfloat) iStacks; GLfloat t = 1.0f; GLfloat s = 0.0f; -34-

课程名称:计算机图形学

}

bool Draw::Clean() {

} } glEnd(); t -= dt; x = stheta * srhodrho; y = ctheta * srhodrho; z = crhodrho; glTexCoord2f(s, t - dt); s += ds; glNormal3f(x, y, z); glTexCoord2f(s, t); glNormal3f(x, y, z); glBegin(GL_TRIANGLE_STRIP); s = 0.0f; for (i = 0; i < iStacks; i++) { GLint i, j; 学生姓名:苟丁 学生学号:0843042229 GLfloat rho = (GLfloat)i * drho; GLfloat srho = (GLfloat)(sin(rho)); GLfloat crho = (GLfloat)(cos(rho)); GLfloat srhodrho = (GLfloat)(sin(rho + drho)); GLfloat crhodrho = (GLfloat)(cos(rho + drho)); for ( j = 0; j <= iSlices; j++) { GLfloat theta = (j == iSlices) ? 0.0f : j * dtheta; GLfloat stheta = (GLfloat)(-sin(theta)); GLfloat ctheta = (GLfloat)(cos(theta)); GLfloat x = stheta * srho; GLfloat y = ctheta * srho; GLfloat z = crho; glVertex3f(x * fRadius, y * fRadius, z * fRadius); glVertex3f(x * fRadius, y * fRadius, z * fRadius); -35-

课程名称:计算机图形学

} 学生姓名:苟丁 学生学号:0843042229 if (!wglMakeCurrent(hDC, NULL)) //清除hdc { } if (!wglDeleteContext(hRC))//清除hrc { } glDeleteTextures(NUM_TEXTURES, textureObjects); return TRUE; MessageBox(NULL,"清除hrc失败","Error",MB_OK|MB_ICONEXCLAMATION); return FALSE; MessageBox(NULL,"清除hdc失败","Error",MB_OK|MB_ICONEXCLAMATION); return FALSE;

//KeyBoard.h

#pragma once

#include "Viewer.h"

class KeyBoard

{

public:

};

//KeyBoard.cpp

#include "KeyBoard.h"

KeyBoard::KeyBoard() {

}

Viewer* KeyBoard::GetViewer() {

}

-36- return viewer; viewer = new Viewer; KeyBoard(); void ProcessKeys(); Viewer* GetViewer(); ~KeyBoard(); Viewer* viewer; //处理按键 private:

课程名称:计算机图形学

KeyBoard::~KeyBoard() {

}

void KeyBoard::ProcessKeys() {

}

//SolarSystem.h

if (KEY_DOWN(VK_LEFT)) { } if (KEY_DOWN(VK_RIGHT)) { } if (KEY_DOWN(VK_UP)) { } if (KEY_DOWN(VK_DOWN)) { } if (KEY_DOWN(VK_PRIOR)) { } if (KEY_DOWN(VK_NEXT)) { } viewer->UpAndDown(-1); viewer->UpAndDown(1); viewer->MoveFlat(-1); viewer->MoveFlat(1); viewer->GetAngle() += 0.1f; viewer->GetAngle() -= 0.1f; if (viewer) { } delete viewer; 学生姓名:苟丁 学生学号:0843042229 viewer->Orient(viewer->GetAngle()); viewer->Orient(viewer->GetAngle()); -37-

课程名称:计算机图形学

#pragma once

#include "Stdafx.h"

#include "Draw.h"

#include "KeyBoard.h"

class SolarSystem

{

public:

};

//SolarSystem.cpp

#include "SolarSystem.h"

GLuint SolarSystem::displayList = 0; extern HDC hDC;

hWnd; SolarSystem(); void Init(); void Resharp(int w,int h); void GameMain(); void CleanUp(); ~SolarSystem(); Draw* drawer; KeyBoard* keyBoard; static GLuint displayList; 学生姓名:苟丁 学生学号:0843042229 private: // GDI设备句柄,将窗口连接到GDI( 图形设备接口) // 保存Windows 分配给程序的窗口句柄 extern HGLRC hRC; // 渲染描述句柄,将OpenGL调用连接到设备描述表 extern HWND

SolarSystem::SolarSystem()

{

}

SolarSystem::~SolarSystem() {

if (drawer) { } -38- delete drawer; drawer = new Draw; keyBoard = new KeyBoard;

课程名称:计算机图形学

}

void SolarSystem::Init() { }

drawer->SetupPixelFormat(hDC); drawer->InitLight(); drawer->LoadTextures();

if (keyBoard) { }

CleanUp();

delete keyBoard;

学生姓名:苟丁 学生学号:0843042229

//设置像素格式

//设置刷新背景色为白色 //初始化光照 //载入纹理 //启用D纹理 //使用平滑着色 //开启深度检测 //启用混合

glClearColor(1.0f,1.0f,1.0f,1.0f);

//displayList = drawer->CreateDL(); glEnable(GL_TEXTURE_2D); glShadeModel(GL_SMOOTH); glEnable(GL_DEPTH_TEST); glEnable(GL_BLEND);

glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);//设置纹理

void SolarSystem::Resharp(int w, int h) { }

void SolarSystem::GameMain() { 阵

glLoadIdentity();

//载入单位矩阵 //设置照相机的光心位

gluLookAt(keyBoard->GetViewer()->GetEysPos()[0] ,keyBoard->GetViewer()->GetEysPos()[1] ,keyBoard->GetViewer()->GetEysPos()[2]

,keyBoard->GetViewer()->GetEysPos()[0]+keyBoard->GetViewer()->GetlaPos()[0

-39-

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // 刷新背景 glMatrixMode(GL_MODELVIEW);

//下面设置模型观察矩

glViewport(0,0,(GLsizei)w,(GLsizei)h); glMatrixMode(GL_PROJECTION); glLoadIdentity();

//下面设置投影矩阵

gluPerspective(60.0f,(GLfloat)w/(GLfloat)h,0.1f,1000.0f);//投影变换,视张

角,宽高比根据窗口的大小设置,近裁剪面为.1,远裁剪面为。

置,观测向量和方向

课程名称:计算机图形学

] ] ] }

void SolarSystem::CleanUp() { }

if (!drawer->Clean()) { }

drawer->Run();

keyBoard->ProcessKeys();

,0,1,0);

学生姓名:苟丁 学生学号:0843042229

,keyBoard->GetViewer()->GetEysPos()[1]+keyBoard->GetViewer()->GetlaPos()[1,keyBoard->GetViewer()->GetEysPos()[2]+keyBoard->GetViewer()->GetlaPos()[2

GLfloat light_position[]={0.0, 0.0, 0.0, 1.0}; //设置光源位置

glLightfv(GL_LIGHT0, GL_POSITION, light_position); //设置光源参数

//处理按键 //开始运动 //画出所有物体

drawer->DrawAll();

//glCallList(displayList); SwapBuffers(hDC);

//交换缓存

MessageBox(NULL,"清除失败","Error",MB_OK|MB_ICONEXCLAMATION);

//Viewer.h #pragma once #include "Stdafx.h" class Viewer { public:

Viewer();

GLfloat* GetEysPos(){return eye;} GLfloat* GetlaPos(){return la;} GLfloat& GetAngle(){return angle;} void Orient(GLfloat ang); void MoveFlat(GLint i); void UpAndDown(GLint i); ~Viewer();

-40-

课程名称:计算机图形学

private:

};

//Viewer.cpp

#include "Viewer.h"

Viewer::Viewer()

{

}

Viewer::~Viewer()

{

}

GLfloat Viewer::angle = 0.0f;

void Viewer::Orient(GLfloat ang) {

}

void Viewer::MoveFlat(GLint i) {

}

la[0] = lx; la[2] = lz; eye[0] = 0; eye[1] = 5; eye[2] = 20; la[0] = 0; la[1] = 0; la[2] = -1; GLfloat eye[3]; GLfloat la[3]; static GLfloat angle; 学生姓名:苟丁 学生学号:0843042229 /*照相机的旋转是观测向量在x,z平面上旋转的结果*/ GLfloat lx = sin(ang); GLfloat lz = -cos(ang); /*i为正则向前走,i为负数则向后退*/ eye[0] += i*la[0]; eye[2] += i*la[2]; -41-

课程名称:计算机图形学

void Viewer::UpAndDown(GLint i) {

}

//WinMain.cpp

#include "SolarSystem.h"

SolarSystem* solarSystem; HDC

HGLRC

int

int

void GameLoop()

{

}

MSG msg; hDC; 学生姓名:苟丁 学生学号:0843042229 la[1] += i*0.1f;//i为正数则表现为抬头,i为负数则表现为低头 // GDI设备句柄,将窗口连接到GDI( 图形设备接口) // 渲染描述句柄,将OpenGL调用连接到设备描述表 // 保存Windows 分配给程序的窗口句柄 hRC=NULL; HWND hWnd=NULL; Width = 800;// 窗口宽 Height= 600;// 窗口高 //DWORD startTime = GetTickCount(); while (1) { } if (PeekMessage(&msg,NULL,NULL,NULL,PM_REMOVE)) { } else solarSystem->GameMain(); //无消息 //while(GetTickCount() - startTime <= 60); if (msg.message == WM_QUIT) { } else { } TranslateMessage(&msg); DispatchMessage(&msg); PostQuitMessage(0); break; -42-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

LRESULT WINAPI MsgProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam )// 消息处理 { }

int WINAPI WinMain(HINSTANCE hInst,HINSTANCE,LPSTR,INT )// WinMain程序入口 {

DWORD DWORD int

dwExStyle; dwStyle; nX=0,nY=0;

-43-

// 使用标准窗口

// WS_OVERLAPPEDWINDOW是有标题

// Window 扩展风格 // Window 窗口风格 // 窗口尺寸

switch(message) {

// 建立窗口

// 获取当前窗口的设备句柄

hDC = GetDC(hWnd); solarSystem->Init(); return 0;

// 关闭窗口 // 结束处理

solarSystem->CleanUp(); PostQuitMessage(0); return 0;

// 窗口尺寸变化 // 窗口的高 // 窗口的宽 // 防止被除

Height = HIWORD(lParam); Width = LOWORD(lParam); if (Height==0) return 0;

// 按ESC退出,全屏模式必需要加入的

Height=1;

case WM_CREATE:

case WM_CLOSE:

case WM_SIZE:

solarSystem->Resharp(Width,Height);

case WM_KEYUP: }

退出方式。

switch (wParam) {

case VK_ESCAPE: }

solarSystem->CleanUp(); PostQuitMessage(0); return 0;

// 结束处理

return (DefWindowProc(hWnd, message, wParam, lParam));

RECT windowRect;

dwExStyle=WS_EX_APPWINDOW|WS_EX_WINDOWEDGE; // 使窗口具有D外观 dwStyle=WS_OVERLAPPEDWINDOW;

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

栏,窗口菜单,最大、小化按钮和可调整尺寸的窗口 }

solarSystem = new SolarSystem; hWnd = CreateWindowEx

( NULL, c,

"SolarSystem",

dwStyle | WS_CLIPCHILDREN|WS_CLIPSIBLINGS, nX, nY,Width, Height, NULL,NULL,hInst,NULL);

// 创建窗口 // 显示窗口 // 刷新窗口 // 进入消息循环

RegisterClassEx( &wc ); char c[]="system"; WNDCLASSEX wc = {

sizeof(WNDCLASSEX), CS_CLASSDC, MsgProc, 0, 0,

GetModuleHandle(NULL), NULL, NULL, NULL, NULL, c, NULL };

int wid=GetSystemMetrics(SM_CXSCREEN); int hei=GetSystemMetrics(SM_CYSCREEN);

// 获取当前屏幕宽 // 获取当前屏幕高

nX = (wid-Width) / 2;nY= (hei-Height) / 2; // 计算窗口居中用

ShowWindow( hWnd, SW_NORMAL ); UpdateWindow( hWnd ); GameLoop(); return 0;

五.总 结

(1)程序一开始使用了显示列表,最后运行时候发现物体不会运动。

-44-

课程名称:计算机图形学 学生姓名:苟丁 学生学号:0843042229

所谓显示列表就是一组预选存储起来的留待以后调用的函数语句。调用此显示列表时就按次序执行其中函数。一旦储存起来,哪怕改变内部参数的值也没用。所以要想使物体运动最后只能把运动和画图分开成2个函数Run()和DrawAll(),先调用Run()再调用DrawAll(),Run()之后改变了行星旋转的角度,这样便产生了动态效果。

(2)先设置像素格式,再载入纹理,不然纹理无效,因为使用纹理需要渲染描述句柄HGLRC。

(3) 照相机的旋转是观测向量在x,z平面上移动的结果,照相机的移动是光心的世界坐标变化的结果。

参考文献

[1] (美)希尔克雷,胡事民.计算机图形学(OpenGL版).清华大学出版社, 2003

[2] [美]Dave Astle,Kevin Hawkins. OpenGL游戏编程. 重庆大学出版社,2006

[3] 思科公司./global/CN/Products/si/casi/ca3500,

2003

-45-

相关推荐