实验十三3DS模型的显示new.docx
- 文档编号:3182778
- 上传时间:2023-05-05
- 格式:DOCX
- 页数:37
- 大小:138.40KB
实验十三3DS模型的显示new.docx
《实验十三3DS模型的显示new.docx》由会员分享,可在线阅读,更多相关《实验十三3DS模型的显示new.docx(37页珍藏版)》请在冰点文库上搜索。
实验十三3DS模型的显示new
实验十三3DS模型的显示
一、实验目的
1.实现3DS模型在程序中的显示与漫游
2.实现MDL模型在程序中的显示与漫游
3.了解3DS模型尺寸与OpenGL绘图坐标之间的关系
二、实验环境
硬件要求:
PC机,主流配置,最好为独立显卡,显存512M以上。
软件环境:
操作系统:
WindowsXP。
语言开发工具:
MicrosoftVisualstudio2005/2008,VisualC++。
三、实验内容与要求:
要求:
实验所有步骤所生成的效果截图拷贝到实验报告文档里备查,并附上相应的代码。
WORD文档命名方式:
学号姓名-实验序号-实验名称。
内容:
1.铲车模型显示程序
图1·铲车模型程序效果
仔细研读程序,修改程序,将模型放入上次实验的场景中
在场景中尝试添加其他模型,并查看效果
1.如果屏蔽深度检测代码,模型显示会怎样变化?
2.模型的纹理对场景的效果会有影响吗?
提供的模型(参见实验文件夹3DSModel):
1.汽车(分普通轿车和宝马车)
2.飞机
3.铲车
(如发现贴图有问题,请立即告诉老师,同学们也可自行到网上搜寻模型)
五、设置参考
1)3DS模型导入设置
1.工程文件准备
1)添加头文件
#include"3ds.h"
#include"texture.h"
2)添加源程序
3ds.cpp,
texture.cpp
2.主程序修改步骤
1.变量定义C3DSModeldraw3ds[5];//有多少个模型,数组就定义多大
2.//调入模型文件一般设置init()中,例如
draw3ds[0].Load(“car.3ds”);
draw3ds[1].Load(“house.3ds”);
//模型调入后,位置处在世界坐标系的原点
3.//显示写在显示回调函数Display()中
glEnable(GL_LIGHTING);//启用光源
glEnable(GL_TEXTURE_2D);//启用纹理
//通过图形变换使得模型原来的尺寸和世界坐标系得尺寸保持一致
图形变换glScalef(x,y,z);
draw3ds[0].Render();//显示模型1
draw3ds[1].Render();//显示模型2
glDisable(GL_LIGHTING);//使用后关闭光源
glDisable(GL_TEXTURE_2D);//使用后关闭纹理
4.//释放资源,释放内存
draw3ds[0].Release();
draw3ds[1].Release();
6.注意:
要启用深度检测
六、思考题
哪几个因素影响3DS模型的显示效果?
如果想调用不同大小的模型都能在同一个程序正确地显示,程序应该怎样修改?
七、加分题
在网上查找模型或者自己设计模型,调入自己设计的带光照的3D新场景(须有OpenGL绘制的其他物体)中。
八、演示程序
1)3DSModel_chanche.exe//3DS模型铲车效果演示
九、附属程序
1.铲车模型显示主程序3DSModel(带mp3音乐播放功能)
#include"stdafx.h"
#include
#include
#include"3ds.h"
#include"Texture.h"
#include
#include"fmod.h"////音频库的头文件
#pragmacomment(lib,"fmodvc.lib")//音频库的静态链接库
FSOUND_STREAM*mp3back;
voidinit(void);
voidDisplay(void);
voidKeyboard(intkey,intx,inty);
voiddraw3DSModel();
voidReshape(GLsizeiw,GLsizeih);
voidmyidle();
C3DSModeldraw3ds[5];//有多少个模型,数组就定义多大
floateyex=0,eyey=0,eyez=100,atx=0,aty=0,atz=0;
floatrotatex,rotatey;
intAPIENTRY_tWinMain(HINSTANCEhInstance,
HINSTANCEhPrevInstance,
LPTSTRlpCmdLine,
intnCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);
char*argv[]={"hello",""};
intargc=2;//must/shouldmatchthenumberofstringsinargv
glutInit(&argc,argv);//初始化GLUT库;
glutInitDisplayMode(GLUT_DOUBLE|GLUT_RGB);//设置显示模式;(缓冲,颜色类型)
glutInitWindowSize(500,500);
glutInitWindowPosition(1024/2-250,768/2-250);
glutCreateWindow("3D-cubetexture");//创建窗口,标题为“Rotating3DWorld”;
glutReshapeFunc(Reshape);
init();
glutDisplayFunc(Display);//用于绘制当前窗口;
glutIdleFunc(myidle);
glutMainLoop();//表示开始运行程序,用于程序的结尾;
return0;
}
voidinit()
{
//调入模型文件一般设置init()中,例如
draw3ds[0].Load("chanche.3ds");
glClearColor(1,1,1,1);
glEnable(GL_DEPTH_TEST);//启用深度测试
if(FSOUND_Init(44100,32,0))//把声音初始化为khz
{
//载入文件bgmusic.mp3
mp3back=FSOUND_Stream_OpenFile("1.mp3",FSOUND_LOOP_NORMAL,0);
}
FSOUND_Stream_Play(FSOUND_FREE,mp3back);
}
voidDisplay(void)
{
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(eyex,eyey,eyez,atx,aty,atz,0,1,0);
glRotatef(rotatex,1,0,0);
glRotatef(rotatey,0,1,0);
glScalef(0.5,0.5,0.5);
draw3DSModel();//绘制玩物
glutSwapBuffers();
}
voiddraw3DSModel()
{
glEnable(GL_TEXTURE_2D);
glPushMatrix();
draw3ds[0].Render();
glPopMatrix();
glDisable(GL_TEXTURE_2D);
}
voidspecialkeyboard(intkey,intx,inty)
{
if(key==GLUT_KEY_UP)
{
eyey+=5;aty+=5;
}
if(key==GLUT_KEY_DOWN)
{
eyey-=5;aty-=5;
}
glutPostRedisplay();
}
voidKeyboard(unsignedcharkey,intx,inty)
{
switch(key)
{
case'w':
eyez-=5;
atz-=5;
break;
case's':
eyez+=5;
atz+=5;
break;
case'a':
//eyex-=5;
eyex-=5;
atx-=5;
break;
case'd':
//eyex+=5;
eyex+=5;
atx+=5;
break;
}
glutPostRedisplay();
}
voidReshape(GLsizeiw,GLsizeih)
{
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(90,w/h,2,2500);
glViewport(0,0,w,h);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
}
voidmyidle()
{
Sleep(100);
rotatex+=0.1;
rotatey+=0.1;
glutPostRedisplay();
}
2.读取3DS模型程序3ds.cpp
#include"stdafx.h"
#include"3ds.h"
#include"Texture.h"
#include"glaux.h"
//构造函数
C3DSModel:
:
C3DSModel()
{
//初始化文件指针
m_FilePtr=NULL;
//定义一个默认的材质(灰色)
tMaterialdefaultMat;
defaultMat.isTexMat=false;
strcpy(defaultMat.matName.string,"5DG_Default");
defaultMat.color[0]=192;
defaultMat.color[1]=192;
defaultMat.color[2]=192;
m_3DModel.pMaterials.push_back(defaultMat);
//初始化保存DS模型的结构体
m_3DModel.numOfMaterials=1;
m_3DModel.numOfObjects=0;
}
//析构函数
C3DSModel:
:
~C3DSModel()
{
m_3DModel.pMaterials.clear();
m_3DModel.pObject.clear();
}
//载入ds文件
BOOLC3DSModel:
:
Load(char*strFileName)
{
charstrMessage[128]={0};
tChunkchunk={0};
//打开文件
m_FilePtr=fopen(strFileName,"rb");
//如果文件打开失败
if(!
m_FilePtr)
{
sprintf(strMessage,"3DS文件%s不存在!
",strFileName);
MessageBoxA(NULL,strMessage,"Error",MB_OK);
returnfalse;
}
//读取ds文件的第一个Chunk
ReadChunk(&chunk);
//检查是否是ds文件
if(chunk.ID!
=PRIMARY)
{
sprintf(strMessage,"读取文件%s失败!
",strFileName);
MessageBoxA(NULL,strMessage,"Error",MB_OK);
fclose(m_FilePtr);
returnfalse;
}
//开始读取ds文件
ReadPrimary(chunk.length-6);
//计算每个顶点的法线量
ComputeNormals();
//关闭打开的文件
fclose(m_FilePtr);
m_FilePtr=NULL;
//对有纹理的材质载入该纹理
for(inti=0;i { if(m_3DModel.pMaterials[i].isTexMat) { if(! BuildTexture(m_3DModel.pMaterials[i].mapName.string,m_3DModel.pMaterials[i].texureId)) { //纹理载入失败 sprintf(strMessage,"3DS纹理文件载入失败: %s! ",m_3DModel.pMaterials[i].mapName.string); MessageBoxA(NULL,strMessage,"Error",MB_OK); } } } returntrue; } //从文件中读取个字节 BYTEC3DSModel: : ReadByte(void) { BYTEresult=0; fread(&result,1,1,m_FilePtr); returnresult; } //从文件中读取个字节 WORDC3DSModel: : ReadWord(void) { returnReadByte()+(ReadByte()<<8); } //从文件中读取个字节 UINTC3DSModel: : ReadUint(void) { returnReadWord()+(ReadWord()<<16); } //从文件中读取浮点数 floatC3DSModel: : ReadFloat(void) { floatresult; fread(&result,sizeof(float),1,m_FilePtr); returnresult; } //从文件中读取字符串(返回字符串长度) UINTC3DSModel: : ReadString(STRING*pStr) { intn=0; while((pStr->string[n++]=ReadByte())! =0) ; returnn; } //读取ds的一个Chunk信息 voidC3DSModel: : ReadChunk(tChunk*pChunk) { fread(&pChunk->ID,1,2,m_FilePtr); fread(&pChunk->length,1,4,m_FilePtr); } //读取ds文件主要Chunk UINTC3DSModel: : ReadPrimary(UINTn) { UINTcount=0;//该Chunk内容已读取的字节计数 tChunkchunk={0};//用以保存子Chunk的内容 while(count { ReadChunk(&chunk); switch(chunk.ID) { casePRIM_EDIT: ReadEdit(chunk.length-6); break; //casePRIM_KEY: //ReadKeyframe(chunk.length-6); //break; default: fseek(m_FilePtr,chunk.length-6,SEEK_CUR); break; } count+=chunk.length; } returncount; } //读取ds物体主编辑Chunk UINTC3DSModel: : ReadEdit(UINTn) { UINTcount=0; tChunkchunk={0}; while(count { ReadChunk(&chunk); switch(chunk.ID) { caseEDIT_MAT: ReadMaterial(chunk.length-6); break; caseEDIT_OBJECT: ReadObject(chunk.length-6); break; default: fseek(m_FilePtr,chunk.length-6,SEEK_CUR); break; } count+=chunk.length; } returncount; } //读取ds对象 UINTC3DSModel: : ReadObject(UINTn) { UINTcount=0; tChunkchunk={0}; //新的ds对象 t3DObjectnewObject={0}; count+=ReadString(&newObject.objName); m_3DModel.numOfObjects++; while(count { ReadChunk(&chunk); switch(chunk.ID) { caseOBJECT_INFO: ReadObjectInfo(&newObject,n-count-6); break; default: fseek(m_FilePtr,chunk.length-6,SEEK_CUR); break; } count+=chunk.length; } //保存ds对象 m_3DModel.pObject.push_back(newObject); returncount; } //读取ds对象信息 UINTC3DSModel: : ReadObjectInfo(t3DObject*pObj,UINTn) { UINTcount=0; tChunkchunk={0}; while(count { ReadChunk(&chunk); switch(chunk.ID) { caseOBJECT_VERTEX: { pObj->numOfVerts=ReadWord(); pObj->pVerts=newVector3[pObj->numOfVerts]; memset(pObj->pVerts,0,sizeof(Vector3)*pObj->numOfVerts); //按块读取顶点坐标值 fread(pObj->pVerts,1,chunk.length-8,m_FilePtr); //调换y、z坐标值(由于dMAX坐标系方向与OpenGL不同) floatfTempY; for(inti=0;i { fTempY=pObj->pVerts[i].y; pObj->pVerts[i].y=pObj->pVerts[i].z; pObj->pVerts[i].z=-fTempY; } break; } caseOBJECT_FACET: ReadFacetInfo(pObj,chunk.length-6); break; caseOBJECT_UV: pObj->numTexVertex=ReadWord(); pObj->pTexVerts=newVector2[pObj->numTexVertex]; memset(pObj->pTexVerts,0,sizeof(Vector2)*pObj->numTexVertex); //按块读取纹理坐标值 fread(pObj->pTexVerts,1,chunk.length-8,m_FilePtr); break; default: fseek(m_FilePtr,chunk.length-6,SEEK_CUR); break; } count+=chunk.length; } returncount; } //读取面信息 UINTC3DSModel: : ReadFacetInfo(t3DObject*pObj,UINTn) { UINTcount=0; tChunkchunk={0}; pObj->numOfFaces=ReadWord(); pObj->pFaces=newtFace[pObj->numOfFaces]; memset(pObj->pFaces,0,sizeof(tFace)*pObj->numOfFaces); //读取面索引值(第个值为dMAX使用的参数,舍弃) for(inti=0;i { pObj->pFaces[i].vertIndex[0]=ReadWord(); pObj->pFaces[i].vertIndex[1]=ReadWord(); pObj->pFaces[i].vertIndex[2]=ReadWord(); ReadWord(); } count+=2+pObj->numOfFaces*8; STRINGmatName; intt; intmatID=0; while(count { ReadChunk(&chunk); switch(chunk.ID) { caseFACET_MAT: { ReadString(&matName);//材质名称 t=ReadWord();//材质对应的面个数 //查找对应的材质 for(inti=1;i<=m_3DModel.numOfMaterials;i++) {
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 实验十三 3DS模型的显示new 实验 十三 DS 模型 显示 new