`
jgsj
  • 浏览: 962837 次
文章分类
社区版块
存档分类
最新评论

用DirectX设计游戏主角运动

 
阅读更多

用DirectX设计游戏主角运动


今天工作了一整天,就是在弄这个。DirectX的强大之处多得是,只要你肯发掘。像今天我就弄了一个让主角运动的程序,自己还制作了动画呢。画得不好请见谅啊。
程序呢,就是将sprite类简单地封装了一下,变得更加易用。但是遗憾的是,我还没有实现主角的跳跃。怎么办呢?只好再奋斗一天了。
程序是载入八个图像,然后每次显示不同的图像,这样主角的运动就显示出来啦。这就是我动画的奥秘。虽然这个类还有些成员函数是空的,但是总体来说,我对这个自己编写的类还是满意的。因为它有点继承了DIrectX库的特点,这样也比较易用。我会以这个程序为经验,下次开发出更好的程序的。

这是我的PlayerAction.h文件。

Code:
  1. /*---------------------------------------------------------------------------
  2. 蒋轶民制作E-mail:jiangcaiyang123@163.com
  3. 文件名:PlayerAction.h
  4. 作用:让主角运动的实现
  5. ----------------------------------------------------------------------------*/
  6. /*--------------------------------------------------------------------------*/
  7. //条件编译
  8. #ifndef_PLAYERACTION_H_
  9. #define_PLAYERACTION_H_
  10. //定义的宏
  11. #defineSPRITE_WIDTH50
  12. #defineSPRITE_HEIGHT50
  13. //将主角这个类封装起来
  14. classJPlayer
  15. {
  16. public:
  17. JPlayer():xPos(WINDOW_WIDTH*0.5f),yPos(WINDOW_HEIGHT-100),
  18. pPlayerSprite(0),pPlayerTexture(0)
  19. {spriteRect.top=0;}//默认构造函数
  20. ~JPlayer(){}//默认析构函数
  21. boolInitialize(void);//初始化主角
  22. boolGoLeft(void);//向左走
  23. boolGoRight(void);//向右走
  24. boolJump(void);//跳跃
  25. boolDisplay(void);//显示主角
  26. voidRelease(void);//释放空间
  27. private:
  28. floatxPos,yPos;//主角的横纵坐标的位置
  29. RECTspriteRect;//精灵动画的矩形框
  30. LPD3DXSPRITEpPlayerSprite;//主角的子图形指针
  31. LPDIRECT3DTEXTURE9pPlayerTexture;//主角的图像纹理指针
  32. };
  33. typedefJPlayer*LPJPLAYER;//定义主角的指针类型
  34. /*--------------------------------------------------------------------------*/
  35. //初始化主角
  36. boolJPlayer::Initialize(void)
  37. {
  38. //载入纹理图像并使用双线性滤波
  39. if(FAILED(D3DXCreateTextureFromFileEx(g_JDevice,"蘑菇(合图).png",
  40. 200,//我不得不手动设置。D3DPOOL_DEFAULT在纹理中起作用,但是应用在D3DXSPRITE中会产生问题。
  41. 100,//我不得不手动设置。D3DPOOL_DEFAULT在纹理中起作用,但是应用在D3DXSPRITE中会产生问题。
  42. 1,//不要创建mip-map。它在子图形动画中会抛弃像素数学计算
  43. D3DPOOL_DEFAULT,
  44. D3DFMT_UNKNOWN,
  45. D3DPOOL_DEFAULT,
  46. D3DX_DEFAULT,
  47. D3DX_DEFAULT,
  48. D3DCOLOR_XRGB(0,0,0),
  49. NULL,
  50. NULL,
  51. &pPlayerTexture)))
  52. returnfalse;
  53. g_JDevice->SetSamplerState(0,D3DSAMP_MINFILTER,D3DTEXF_LINEAR);
  54. g_JDevice->SetSamplerState(0,D3DSAMP_MAGFILTER,D3DTEXF_LINEAR);
  55. //设置三角形的背面不被剔除
  56. g_JDevice->SetRenderState(D3DRS_CULLMODE,D3DCULL_NONE);
  57. //创建子图形
  58. if(FAILED(D3DXCreateSprite(g_JDevice,&pPlayerSprite)))
  59. returnfalse;
  60. returntrue;
  61. }
  62. /*--------------------------------------------------------------------------*/
  63. //向左走
  64. boolJPlayer::GoLeft(void)
  65. {
  66. xPos-=4.0f;
  67. spriteRect.top=0;
  68. returntrue;
  69. }
  70. /*--------------------------------------------------------------------------*/
  71. //向右走
  72. boolJPlayer::GoRight(void)
  73. {
  74. xPos+=4.0f;
  75. spriteRect.top=50;
  76. returntrue;
  77. }
  78. /*--------------------------------------------------------------------------*/
  79. //跳跃
  80. boolJPlayer::Jump(void)
  81. {
  82. returntrue;
  83. }
  84. /*--------------------------------------------------------------------------*/
  85. //显示主角
  86. boolJPlayer::Display(void)
  87. {
  88. //碰撞检测
  89. if(xPos<0.0f)
  90. xPos=0.0f;
  91. elseif(xPos>WINDOW_WIDTH-SPRITE_WIDTH)
  92. xPos=WINDOW_WIDTH-SPRITE_WIDTH;
  93. //显示每一个子图形
  94. staticfloatframe=0;
  95. spriteRect.left=(long)floor(frame)*50;
  96. spriteRect.bottom=spriteRect.top+50;
  97. spriteRect.right=spriteRect.left+50;
  98. frame+=0.05f;
  99. if(frame>=4.0f)frame=0.0f;
  100. //设置D3DXVECTOR3结构体,在D3DXSPRITE::Draw函数中有应用
  101. D3DXVECTOR3vCenter(0.0f,0.0f,0.0f);
  102. D3DXVECTOR3vPosition(xPos,yPos,0.0f);
  103. //渲染Sprite
  104. pPlayerSprite->Begin(D3DXSPRITE_ALPHABLEND);//以Alpha混合形式进行渲染
  105. pPlayerSprite->Draw(pPlayerTexture,&spriteRect,&vCenter,&vPosition,
  106. D3DCOLOR_XRGB(255,255,255));
  107. pPlayerSprite->End();//结束渲染
  108. returntrue;
  109. }
  110. /*--------------------------------------------------------------------------*/
  111. //释放空间
  112. voidJPlayer::Release(void)
  113. {
  114. if(pPlayerSprite)pPlayerSprite->Release();pPlayerSprite=NULL;
  115. if(pPlayerTexture)pPlayerTexture->Release();pPlayerTexture=NULL;
  116. }
  117. /*--------------------------------------------------------------------------*/
  118. #endif


下面是我的MainFrame.h文件:

Code:
  1. /*---------------------------------------------------------------------------
  2. 蒋轶民制作E-mail:jiangcaiyang123@163.com
  3. 文件名:MainFrame.cpp
  4. 作用:设计主角移动的主框架
  5. ----------------------------------------------------------------------------*/
  6. /*--------------------------------------------------------------------------*/
  7. //头文件
  8. #include<windows.h>
  9. #include<d3d9.h>
  10. #include<d3dx9.h>
  11. #include<stdio.h>
  12. //库文件
  13. #pragmacomment(lib,"d3d9.lib")
  14. #pragmacomment(lib,"d3dx9.lib")
  15. //定义的宏
  16. #defineJCLASSNAME"优化的程序"
  17. #defineJCAPTION"程序演示"
  18. #defineFULLSCREENFALSE//全屏非全屏的标识符
  19. #defineSAFE_RELEASE(p)if(p)p->Release();p=NULL;
  20. //调整编译器设置
  21. #pragmawarning(disable:4100)
  22. #ifFULLSCREEN//全屏非全屏的设置
  23. #defineWINDOW_WIDTH640
  24. #defineWINDOW_HEIGHT480
  25. #defineWINDOW_STYLEWS_EX_TOPMOST|WS_POPUP|WS_VISIBLE
  26. #else
  27. #defineWINDOW_WIDTH320
  28. #defineWINDOW_HEIGHT320
  29. #defineWINDOW_STYLEWS_CAPTION|WS_SYSMENU
  30. #endif
  31. /*----------------------------------------------------------------------------*/
  32. //全局变量
  33. LPDIRECT3D9g_JD3D=NULL;//D3D结构体
  34. LPDIRECT3DDEVICE9g_JDevice=NULL;//D3D装置结构体
  35. LPD3DXFONTg_FPSFont=NULL;//指向FPS字体的指针
  36. RECTg_FPSFontPos={WINDOW_WIDTH-100,WINDOW_HEIGHT-15,
  37. WINDOW_WIDTH,WINDOW_HEIGHT};//FPS所在的矩形框
  38. INTg_FrameCount=0;//帧的计数器
  39. INTg_lastTime=0;//记录上一秒的时间
  40. INTg_currentTime=0;//记录当前的时间
  41. CHARg_FPSstr[25]={0};//记录当前帧率的字符串
  42. IDirect3DSurface9*g_surface=NULL;//平面的指针
  43. /*----------------------------------------------------------------------------*/
  44. //让主角运动的实现的头文件
  45. #include"PlayerAction.h"
  46. //额外的全局变量
  47. LPJPLAYERg_JPlayer;//包含主角这个类的指针
  48. /*----------------------------------------------------------------------------*/
  49. //函数的声明
  50. BOOLInitializeD3D(HWNDhWnd)
  51. {
  52. D3DDISPLAYMODEdisplayMode;
  53. //创建D3D对象
  54. g_JD3D=Direct3DCreate9(D3D_SDK_VERSION);
  55. if(g_JD3D==NULL)
  56. returnFALSE;
  57. //获取显示器的模式
  58. if(FAILED(g_JD3D->GetAdapterDisplayMode(D3DADAPTER_DEFAULT,&displayMode)))
  59. returnFALSE;
  60. //D3D显示的参数
  61. D3DPRESENT_PARAMETERSjd3dpp;
  62. ZeroMemory(&jd3dpp,sizeof(jd3dpp));
  63. //初始化D3DPRESENT_PARAMETERS
  64. jd3dpp.Windowed=!FULLSCREEN;
  65. jd3dpp.BackBufferWidth=WINDOW_WIDTH;
  66. jd3dpp.BackBufferHeight=WINDOW_HEIGHT;
  67. jd3dpp.SwapEffect=D3DSWAPEFFECT_DISCARD;
  68. jd3dpp.BackBufferFormat=displayMode.Format;
  69. jd3dpp.EnableAutoDepthStencil=TRUE;
  70. jd3dpp.AutoDepthStencilFormat=D3DFMT_D16;
  71. //创建设备
  72. if(FAILED(g_JD3D->CreateDevice(D3DADAPTER_DEFAULT,
  73. D3DDEVTYPE_HAL,hWnd,D3DCREATE_SOFTWARE_VERTEXPROCESSING,
  74. &jd3dpp,&g_JDevice)))
  75. returnFALSE;
  76. //设置渲染状态
  77. g_JDevice->SetRenderState(D3DRS_LIGHTING,FALSE);
  78. g_JDevice->SetRenderState(D3DRS_ZENABLE,D3DZB_TRUE);
  79. //创建字体
  80. if(FAILED(D3DXCreateFont(g_JDevice,15,0,1,1,0,DEFAULT_CHARSET,
  81. OUT_DEFAULT_PRECIS,DEFAULT_QUALITY,DEFAULT_PITCH|FF_DONTCARE,
  82. "Impact",&g_FPSFont)))returnFALSE;
  83. //创建离屏平面
  84. if(FAILED(g_JDevice->CreateOffscreenPlainSurface(WINDOW_WIDTH,WINDOW_HEIGHT,
  85. D3DFMT_X8R8G8B8,//平面格式
  86. D3DPOOL_DEFAULT,//内存池格式
  87. &g_surface,//保存结果的缓存
  88. NULL)))//保留参数
  89. returnFALSE;
  90. //载入背景平面图像
  91. if(FAILED(D3DXLoadSurfaceFromFile(g_surface,NULL,NULL,"背景图案.tga",
  92. NULL,D3DX_DEFAULT,0,NULL)))returnFALSE;
  93. //初始化主角
  94. g_JPlayer=newJPlayer;
  95. g_JPlayer->Initialize();
  96. returnTRUE;
  97. }
  98. /*----------------------------------------------------------------------------*/
  99. //释放所有资源
  100. voidReleaseMemory(void)
  101. {
  102. SAFE_RELEASE(g_JD3D);
  103. SAFE_RELEASE(g_JDevice);
  104. SAFE_RELEASE(g_FPSFont);
  105. SAFE_RELEASE(g_surface);
  106. SAFE_RELEASE(g_JPlayer);//释放JPlayer所占的内存
  107. }
  108. /*----------------------------------------------------------------------------*/
  109. //渲染屏幕
  110. voidRenderScene(void)
  111. {
  112. //计数器开始计数(以毫秒计)
  113. g_currentTime=GetTickCount();
  114. if(g_currentTime-g_lastTime>1000)
  115. {
  116. sprintf_s(g_FPSstr,25,"当前FPS:%d",g_FrameCount);
  117. g_lastTime=g_currentTime;
  118. g_FrameCount=0;
  119. }
  120. elseg_FrameCount++;
  121. g_JDevice->Clear(0,NULL,D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER,
  122. D3DCOLOR_XRGB(0,0,0),1.0f,0);//清除屏幕
  123. //载入背景平面图像
  124. IDirect3DSurface9*backbuffer=NULL;
  125. g_JDevice->GetBackBuffer(0,0,D3DBACKBUFFER_TYPE_MONO,
  126. &backbuffer);//获取后台缓存
  127. g_JDevice->StretchRect(g_surface,NULL,
  128. backbuffer,NULL,D3DTEXF_NONE);//将后台矩形放入前景矩形
  129. //开始渲染
  130. g_JDevice->BeginScene();
  131. g_JPlayer->Display();//显示主角
  132. g_FPSFont->DrawText(NULL,g_FPSstr,-1,&g_FPSFontPos,DT_CENTER,
  133. D3DCOLOR_XRGB(0,0,0));//显示字体
  134. //结束渲染
  135. g_JDevice->EndScene();
  136. g_JDevice->Present(NULL,NULL,NULL,NULL);
  137. }
  138. /*----------------------------------------------------------------------------*/
  139. //回调函数,用来处理消息
  140. HRESULTCALLBACKMyAppProc(HWNDhWnd,UINTmsg,WPARAMwParam,LPARAMlParam)
  141. {
  142. if(g_JPlayer==NULL)
  143. return(HRESULT)DefWindowProc(hWnd,msg,wParam,lParam);
  144. switch(msg)
  145. {
  146. caseWM_DESTROY:
  147. PostQuitMessage(0);break;
  148. caseWM_KEYDOWN:
  149. if(wParam==VK_ESCAPE)PostQuitMessage(0);
  150. if(wParam==VK_LEFT)g_JPlayer->GoLeft();
  151. if(wParam==VK_RIGHT)g_JPlayer->GoRight();
  152. break;
  153. caseWM_KEYUP:break;
  154. default:break;
  155. }
  156. return(HRESULT)DefWindowProc(hWnd,msg,wParam,lParam);
  157. };
  158. /*----------------------------------------------------------------------------*/
  159. //程序的入口,主函数
  160. INTWINAPIWinMain(HINSTANCEhInst,HINSTANCEhPrevInst,LPSTRcmd,INTshow)
  161. {
  162. //设置WindowClass结构并且注册它
  163. WNDCLASSEXjWndCls={sizeof(jWndCls),CS_CLASSDC,MyAppProc,0L,0L,hInst,
  164. NULL,LoadCursor(NULL,IDC_ARROW),0,NULL,JCLASSNAME,NULL};
  165. RegisterClassEx(&jWndCls);
  166. //设置窗口并且显示窗口
  167. HWNDhWnd=CreateWindow(JCLASSNAME,JCAPTION,WINDOW_STYLE,100,40,
  168. WINDOW_WIDTH,WINDOW_HEIGHT,GetDesktopWindow(),NULL,jWndCls.hInstance,NULL);
  169. if(hWnd==NULL)
  170. returnFALSE;
  171. ShowWindow(hWnd,SW_SHOWDEFAULT);
  172. UpdateWindow(hWnd);
  173. //初始化设置
  174. if(InitializeD3D(hWnd)==FALSE)
  175. returnFALSE;
  176. //进入消息循环
  177. MSGmsg;
  178. ZeroMemory(&msg,sizeof(msg));
  179. while(msg.message!=WM_QUIT)
  180. {
  181. if(PeekMessage(&msg,NULL,0U,0U,PM_REMOVE))
  182. {
  183. TranslateMessage(&msg);
  184. DispatchMessage(&msg);
  185. }
  186. else
  187. {
  188. //渲染屏幕
  189. RenderScene();
  190. }
  191. }
  192. //程序结束,释放内存所有资源
  193. ReleaseMemory();
  194. //解除窗口注册
  195. UnregisterClass(JCLASSNAME,jWndCls.hInstance);
  196. return(INT)msg.wParam;
  197. }

程序需要载入背景图和纹理图,分别如下:

程序的动态显示如下:

我的更多DirectX文章:

使用DirectX让进行Alpha混合的子图形移动(精灵动画

<shapetype id="_x0000_t75" stroked="f" filled="f" path="m@4@5l@4@11@9@11@9@5xe" o:preferrelative="t" o:spt="75" coordsize="21600,21600"><stroke joinstyle="miter"></stroke><formulas><f eqn="if lineDrawn pixelLineWidth 0"></f><f eqn="sum @0 1 0"></f><f eqn="sum 0 0 @1"></f><f eqn="prod @2 1 2"></f><f eqn="prod @3 21600 pixelWidth"></f><f eqn="prod @3 21600 pixelHeight"></f><f eqn="sum @0 0 1"></f><f eqn="prod @6 1 2"></f><f eqn="prod @7 21600 pixelWidth"></f><f eqn="sum @8 21600 0"></f><f eqn="prod @7 21600 pixelHeight"></f><f eqn="sum @10 21600 0"></f></formulas><path o:connecttype="rect" gradientshapeok="t" o:extrusionok="f"></path><lock aspectratio="t" v:ext="edit"></lock></shapetype><shape id="_x0000_i1025" o:button="t" target="_blank" href="http://student.csdn.net/link.php?url=http://student.csdn.net%2Fspace.php%3Fuid%3D999749%26amp%3Bdo%3Dblog%26amp%3Bid%3D49603" alt="" type="#_x0000_t75" style="width: 12pt; height: 12pt"><imagedata o:href="http://student.csdn.net/image/jian.gif" src="file:///C:/DOCUME~1/%E8%92%8B%E8%BD%B6%E6%B0%91/LOCALS~1/Temp/msohtml1/01/clip_image001.gif"></imagedata></shape>为DirectX游戏计算帧率

设计DirectX游戏开头动画效果设计DirectX游戏开头画面淡入淡出的效果

为自己创作一个好的DirectX程序风格

我的游戏:走迷宫(DirectX版)

怎么样?这个和我心目中的游戏还差得远呢。以后要做比这个更加强大的游戏!!!

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics