去年参赛做的虚拟漫游程序,使用了DXUT框架,感觉DXUT随然方便但是其结构太为复杂,搞不懂很多原理,从而错过了很多d3d的基础知识。放寒假以来一直在家学习基础知识,打算用自己的思想写出一个框架,可能在结构性能上差一些,但出现问题是可以很容易的解决^_^
一下是使用了shader做了阳光反射的效果:

一开始写对于一些类的封装想了很长时间,这次写出了精灵类,四元数相机类,md2导入类,x导入类,输入类,天空类,字体类。对于md2是看了<Focus on 3D models>这本书,按照教程虽然可以导入一些模型,但是却不能读出md2文件里的纹理信息,因为在建模的时候就根本没有导出纹理信息,Blender,3dsmax,milkshape都试过了,还是搞不懂。。。希望有高手能指点。
还有就是fps的问题,一开始显示的pfs值总是在60以内,好像被限制住了一样,全屏后有变成了70。最后找到了一良方:
d3dpp.PresentationInterval=D3DPRESENT_INTERVAL_IMMEDIATE; //可以显示计算能力之内的fps值(我就使用了这个)
d3dpp.PresentationInterval=D3DPRESENT_INTERVAL_ONE; //只显示当前分辨率时,显示器所固定的刷新率(可以用一些软件比如refreshfix来调整各个分辨率的刷新率)
fps值达到六七百了,这时我的相机移动和旋转就变快了,所以只需对相机移动或旋转的差值乘上每帧之间所流逝的时间即可。
对于每帧之间流逝时间的计算如下:
MSG msg;
ZeroMemory( &msg, sizeof(msg));
__int64 cntsPerSec = 0; //计算流逝时间 程序以count为单位计时,cntsPerSec 为每秒钟所流逝的count数
QueryPerformanceFrequency((LARGE_INTEGER*)&cntsPerSec);
float secsPerCnt = 1.0f / (float)cntsPerSec;//每经过一个count用的时间
__int64 prevTimeStamp = 0;//初始时间(以count为单位)
QueryPerformanceCounter((LARGE_INTEGER*)&prevTimeStamp);
while( msg.message!=WM_QUIT )
{
if( PeekMessage( &msg, NULL, 0U, 0U, PM_REMOVE ) )
{
TranslateMessage( &msg );
DispatchMessage( &msg );
}
else
{
__int64 currTimeStamp = 0;//当前时间
QueryPerformanceCounter((LARGE_INTEGER*)&currTimeStamp);
float deltatime = (currTimeStamp - prevTimeStamp)*secsPerCnt;//相减后得到count差值,再乘
Update(deltatime); //刷新函数
Render(); //渲染函数
prevTimeStamp = currTimeStamp;
}
}
其实得到了时间fps就不难计算了。
void GfxStats::Update(float dt)
{
static float numFrames = 0.0f;
static float timeElapsed = 0.0f;
numFrames += 1.0f;
timeElapsed += dt;
if( timeElapsed >= 1.0f )
{
mFPS = numFrames;
mMilliSecPerFrame = 1000.0f / mFPS;
timeElapsed = 0.0f;
numFrames = 0.0f;
}
}
此函数每次刷新都调用一次,mFPS是类成员,只要返回mFPS值就可以了。
作者分享了自己去年参加比赛时制作虚拟漫游程序的经验,由于DXUT框架过于复杂,决定从零开始构建自己的3D游戏引擎。文章中详细介绍了实现过程中遇到的技术难题及解决方案,包括模型导入、纹理信息读取、fps优化等。
1705

被折叠的 条评论
为什么被折叠?



