ImageVerifierCode 换一换
格式:DOCX , 页数:27 ,大小:1.79MB ,
资源ID:4725068      下载积分:3 金币
快捷下载
登录下载
邮箱/手机:
温馨提示:
快捷下载时,用户名和密码都是您填写的邮箱或者手机号,方便查询和重复下载(系统自动生成)。 如填写123,账号就是123,密码也是123。
特别说明:
请自助下载,系统不会自动发送文件的哦; 如果您已付费,想二次下载,请登录后访问:我的下载记录
支付方式: 支付宝    微信支付   
验证码:   换一换

加入VIP,免费下载
 

温馨提示:由于个人手机设置不同,如果发现不能下载,请复制以下地址【https://www.bdocx.com/down/4725068.html】到电脑端继续下载(重复下载不扣费)。

已注册用户请登录:
账号:
密码:
验证码:   换一换
  忘记密码?
三方登录: 微信登录   QQ登录  

下载须知

1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。
2: 试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。
3: 文件的所有权益归上传用户所有。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 本站仅提供交流平台,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

版权提示 | 免责声明

本文(计算机图形学实验报告2.docx)为本站会员(b****6)主动上传,冰豆网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知冰豆网(发送邮件至service@bdocx.com或直接QQ联系客服),我们立即给予删除!

计算机图形学实验报告2.docx

1、计算机图形学实验报告2计算机图形学实验报告实验二、 三维网格模型光顺一、实验目的与基本要求:(1)掌握Obj文件的读入;(2)利用给定的数据结构类,建立读入网格模型数据结构;(3)利用OpenGL类库,对三维模型进行绘制;(4)利用OpenGL类库,增加采用鼠标交互方式对三维模型进行旋转、放缩、平移等操作;(5)实现Laplacian方法的三维模型光顺操作,并观察三维模型光顺过程;二、实验设备(环境)及要求1. 操作系统:Windows XP 或 Windows 72. 编程环境:Microsoft Visual Studio 2010,OpenGL 库函数3. 界面框架:Win32,MFC,

2、QT选择其中一种三、实验内容与步骤实验分为以下几个步骤:(1)掌握Obj文件的读入顶点和面的个数;(2)建立数组存储点的坐标及面上的点数;(3)存储顶点的邻接面数,并记录每个顶点周围的邻接点(4)计算每个面的法向利用OpenGL类库,增加采用鼠标交互方式对三维模型进行旋转、放缩、平移等操作;(5)利用面法向及顶点坐标进行绘制几何体(6)实现鼠标对物体旋转、平移、缩放的算法(7)实现Laplacian方法的三维模型光顺操作,并观察三维模型光顺过程;4、实现过程说明及成果展示:(1)掌握Obj文件的读入顶点和面的个数;由于obj文件的存储形式是v x1 x2 x3;f v1 v2 v3;这种形式,

3、所以在记录点和面的数量时,只需按行读取,然后再判断首字母是v/f即可实现代码如下:(2)建立数组存储点的坐标及面上的点数;数组的大小由点数和面数决定,点数组和面数组均由0开始记录,故后面再用面对应点的时候,由于面上点是从1开始记录,故需要减1然后使用,代码如下:(3)存储顶点的邻接面数,并记录每个顶点周围的邻接点记录点邻接面的是新建一个数组,在读面的时候,将该面的序号存入对应点的数组中,然后再在每个面上取一点,记录到点的邻接点数组中,在每个面上取得的点为向外右手方向的下一个点,实现代码如下:(4)计算每个面的法向计算面的法向方式为面上右手方向上的两向量的叉乘得到,即所用代码为:(8)利用面法向

4、及顶点坐标进行绘制几何体用法向绘制的方式是先用glNormal3fv(v)指出面的法向;再用glVertex3f传入面上点的坐标;由于我将glNormal3fv(v)中写在算法向所以我直接对此直接调用即可,代码如下:(9)实现鼠标对物体旋转、平移、缩放的算法平移:利用Transform函数和键盘事件来改变参数,w,s,a,d分别控制绘制的kitty猫的上下左右的移动:实现代码如下:旋转:利用gllookat();函数设定了观察角度,并用鼠标事件改变参数,用实现观察视角的变化实现物体的旋转,代码如下:缩放:运用glScalef方法和键盘事件改变参数,实现物体的放大和缩小,代码如下:(10)实现L

5、aplacian方法的三维模型光顺操作,并观察三维模型光顺过程;Laplacian方法的原理是利用目标点与其所有邻接点平均后的点的差向量,对目标点的坐标进行变换的过程,具体方法是:建立每个点的邻接顶点数组,存储每个点的邻接点对每个顶点的邻接点进行求平均,即将邻接点的坐标求和后除以邻接点个数,从而得到邻接平均点得到优化向量优化向量 = 邻接平均点 - 目标点设定优化度参数,得到优化后的新坐标新坐标 = 目标点 + *优化向量在程序中,对于第num个顶点,我设定的变量为目标点vArr邻接平均点v0优化向量l新坐标数组vNewArr具体代码如下:5、结果展示及说明计算面法向后直接绘制(未光顺):光顺

6、进行一次后光顺多次后利用点绘制结果为旋转后缩放后平移后6、心得体会(1)计算面法向时法向量的方向没有运用右手方向,导致有的面法向向里,从而出现雪花(2)在运用Laplacian算法进行求邻接平均点时未初始化邻接平均点数组,导致平均点的累加从而出现越光顺越粗糙的现象(3)在obj文件中面对应顶点数和顶点数组的标号相差1.在运用的时候需减1,面从1开始记顶点,顶点数组从0开始记顶点7、实验代码#defineGLUT_DISABLE_ATEXIT_HACK#include#include#include#include#include#include#include#include#includeu

7、singnamespace std;int v_num = 0; /记录点的数量int f_num = 0; /记录面的数量int vn_num = 0;/记录法向量的数量int vt_num = 0;GLfloat *vArr; /存放点的二维数组GLfloat *vNewArr;/存放点的二维数组int *fvArr; /存放面顶点的二维数组GLfloat *fnArr;/存放面法向量的二维数组int *ftArr;int *vfArr;/存放顶点临接的面数的数组int *nextVArr;/存放下一个临界顶点的数组GLfloat *vnArr;/存放点法向量的二维数组string s1,

8、 s2, s3, s4;GLfloat f2, f3, f4;int num1, num2, num3;typedefGLfloatpoint33;point3 x, y,l;/平面上的两个向量x,y和拉普拉斯向量lstaticGLfloat theta = 0.0,0.0,0.0 ;staticGLint axis = 2;staticGLdouble viewer = 0.0, 0.0, 5.0 ; /* initial viewer location */staticGLdouble Tran = 0.0,0.0,0.0 ;staticGLdouble sca = 1.0;void ge

9、tLineNum(stringaddrstr) /获取点和面的数量 ifstream infile(addrstr.c_str(); /打开指定文件 if (!infile) cout open error! endl; exit(1); string sline;/每一行 int i = 0, j = 0; while (getline(infile, sline) /从指定文件逐行读取 if (sline0 = v) v_num+; if (sline0 = f) f_num+; int readfile(stringaddrstr) /将文件内容读到数组中去 /getLineNum(ad

10、drstr); /new二维数组 vArr = newGLfloat*v_num; for (int i = 0; i v_num; i+) vArri = newGLfloat3; vNewArr = newGLfloat*v_num; for (int i = 0; i v_num; i+) vNewArri = newGLfloat3; vnArr = newGLfloat*vn_num; for (int i = 0; i vn_num; i+) vnArri = newGLfloat3; vfArr = newint*v_num; for (int i = 0; i v_num; i

11、+) vfArri = newint10; for (int j = 0; j 10; j+) vfArrij = -1; nextVArr = newint*v_num; for (int i = 0; i v_num; i+) nextVArri = newint10; for (int j = 0; j 10; j+) nextVArrij = -1; fvArr = newint*f_num; fnArr = newGLfloat*f_num; ftArr = newint*f_num; for (int i = 0; i f_num; i+) fvArri = newint3; fn

12、Arri = newGLfloat3; ftArri = newint10; ifstream infile(addrstr.c_str(); if (!infile) cout open error! s1 f2 f3 f4; vArrii0 = f2; vArrii1 = f3; vArrii2 = f4; ii+; if (sline0 = f) /存储面 istringstream in(sline); GLfloat a; in s1num1num2num3;/去掉f fvArrkk0 = num1; fvArrkk1 = num2; fvArrkk2 = num3; for (in

13、t i = 0; i 10; i+) if (vfArrnum1-1i = -1) vfArrnum1-1i = kk; nextVArrnum1-1i = num2; break; for (int j = 0; j 10; j+) if (vfArrnum2-1j = -1) vfArrnum2-1j = kk; nextVArrnum2-1j = num3; break; for (int i = 0; i 10; i+) if (vfArrnum3-1i = -1) vfArrnum3-1i = kk; nextVArrnum3-1i = num1; break; kk+; retur

14、n 0;/计算面法向void nomal(point3p) /*矢量的归一化*/ /double sqrt(); float d = 0.0; int i; for (i = 0; i 0.0) for (i = 0; i 3; i+) pi /= d;void getFaceNormal(point3A, point3B, point3C) x0 = C0 - A0; x1 = C1 - A1; x2 = C2 - A2; y0 = A0 - B0; y1 = A1 - B1; y2 = A2 - B2; point3 v; v0 = x1 * y2 - x2 * y1; v1 = x2 *

15、 y0 - x0 * y2; v2 = x0 * y1 - x1 * y0; nomal(v); glNormal3fv(v);void Laplacian() for (int num = 0; num v_num; num+) int m = 0; /求得点的邻接面数 for (int i = 0; i 10; i+) if (nextVArrnumi != -1) m+; else break; point3 v0; for (int i = 0; i 3; i+) v0i = 0; for (int i = 0; i m; i+) v00 += vArrnextVArrnumi - 1

16、0; v01 += vArrnextVArrnumi - 11; v02 += vArrnextVArrnumi - 12; if (m != 0) for (int i = 0; i 3; i+) v0i /= m; l0 = v00 - vArrnum0; l1 = v01 - vArrnum1; l2 = v02 - vArrnum2; vNewArrnum0 = vArrnum0 + l0 * 0.3; vNewArrnum1 = vArrnum1 + l1 * 0.3; vNewArrnum2 = vArrnum2 + l2 * 0.3; for (int i = 0; i v_nu

17、m; i+) vArri0 = vNewArri0; vArri1 = vNewArri1; vArri2 = vNewArri2; void init(void) getLineNum(H:kitten_noisy.obj); readfile(H:kitten_noisy.obj); double viewer = 0.0, 0.0, 8.0 ; /* initial viewer location */ GLfloat mat_specular = 1.0, 1.0, 1.0, 1.0 ; GLfloat mat_shininess = 50.0 ;/材料的镜面指数,其值越大越精细 GL

18、float light_position = 1.0, 1.0f, 1.0, 0.0 ; GLfloat white_light = 1.0, 1.0, 1.0, 1.0 ; GLfloat lmodel_ambient = 0.1, 0.1, 0.1, 1.0 ; glClearColor(0.0, 0.0, 0.0, 0.0); glShadeModel(GL_SMOOTH); glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess); glL

19、ightfv(GL_LIGHT0, GL_POSITION, light_position);/光源位置 glLightfv(GL_LIGHT0, GL_DIFFUSE, white_light);/漫反射光源 glLightfv(GL_LIGHT0, GL_SPECULAR, white_light);/镜面反射光源 glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient);/环境光源/ glEnable(glMaterialf); glEnable(GL_LIGHTING);/启动光照 glEnable(GL_LIGHT0);/启用0度光

20、源 glEnable(GL_DEPTH_TEST);/启动深度测试 /* glShadeModel(GL_SMOOTH); / Enable Smooth Shading glClearColor(0.0f, 0.0f, 0.0f, 0.5f); / 黑色背景 glClearDepth(1.0f); / 深度缓冲区设置 glEnable(GL_DEPTH_TEST); / 允许深度测试 glDepthFunc(GL_LEQUAL); / 定义深度测试类型 glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); / Really Nice Persp

21、ective Calculation */void display(void) glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glLoadIdentity(); gluLookAt(viewer0, viewer1, viewer2, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0); /设置观察的位置 glRotatef(theta0, 1.0, 0.0, 0.0); glRotatef(theta1, 0.0, 1.0, 0.0); /glRotatef(theta2, 0.0, 0.0, 1.0); glTranslat

22、ef(Tran0, Tran1, Tran2); glScalef(sca, sca, sca); /glPolygonMode(GL_FRONT_AND_BACK, GLU_FILL); glBegin(GL_TRIANGLES); /getFaceNormals(); for (int i = 0; if_num; i+) getFaceNormal(vArrfvArri0 - 1, vArrfvArri1 - 1, vArrfvArri2 - 1); glVertex3f(vArrfvArri0 - 10, vArrfvArri0 - 11, vArrfvArri0 - 12); glV

23、ertex3f(vArrfvArri1 - 10, vArrfvArri1 - 11, vArrfvArri1 - 12); glVertex3f(vArrfvArri2 - 10, vArrfvArri2 - 11, vArrfvArri2 - 12); glEnd(); /* glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); glBegin(GL_POINTS); glColor3f(1.0, 1.0, 1.0); for (int i = 0; i v_num; i+) glVertex3fv(vArri); glNormal3fv(fnArri); glEnd(); */ glFlush();/强制绘图 glutSwapBuffers();void reshape(intw, inth) glViewport(0, 0, (GLsizei)w, (GLsizei)h); /视口设置 glMatrixMode(GL_PROJECTION); glLoadIdentity(); if (w 360.0) thetaaxis -= 360.0; display();void keys(unsignedcharkey, intx, inty) if (key = a) Tran0 -= 0.2; i

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1