D3D的第一个例子

玩了2天NBA live08,最后一场和网友打了4个加时,还是输了。吃完饭时在想,我玩NBA到底收获了什么,感觉虚度了2天光阴啊~ 好好学习吧!我如是想到。

今天看书写了第一个D3D的例子,写篇博客以示纪念,一个旋转的立方体,没什么技术含量,无非是调用一些MS的API,可是内部怎么执行的我还是不知道,打算这学期看完LaMothe的<<3D游戏编程大师技巧>>搞清楚相关数学原理,任重而道远啊!

代码清单:

  1. //////////////////////////////////////////////////////////////////////////////////////////////////
  2. //
  3. // File: cube.cpp
  4. // by tianzhihen 
  5. // 2008.10.12
  6. // MSVC++ 8.0
  7. //////////////////////////////////////////////////////////////////////////////////////////////////
  8. #include "d3dUtility.h"
  9. //
  10. //  全局变量
  11. //
  12. IDirect3DDevice9* Device = 0;
  13. const int Width  = 640;
  14. const int Height = 480;
  15. IDirect3DVertexBuffer9* VB = 0;
  16. IDirect3DIndexBuffer9*  IB = 0;
  17. //
  18. // 类和结构体
  19. //
  20. struct Vertex 
  21. {
  22.     Vertex(){}
  23.     Vertex(float x,float y,float z)
  24.     {
  25.         _x = x; _y = y; _z = z;
  26.     }
  27.     float _x,_y,_z;
  28.     static const DWORD FVF;
  29. };
  30. const DWORD Vertex::FVF = D3DFVF_XYZ;
  31. //
  32. // 框架函数
  33. //
  34. bool Setup()
  35. {
  36.     //
  37.     // 创建顶点/索引缓存
  38.     //  
  39.     Device->CreateVertexBuffer(
  40.         8*sizeof(Vertex),
  41.         D3DUSAGE_WRITEONLY, // 只写
  42.         Vertex::FVF,
  43.         D3DPOOL_MANAGED,
  44.         &VB,
  45.         0);
  46.     Device->CreateIndexBuffer(
  47.         36*sizeof(WORD),
  48.         D3DUSAGE_WRITEONLY,
  49.         D3DFMT_INDEX16,
  50.         D3DPOOL_MANAGED,
  51.         &IB,
  52.         0);
  53.     //
  54.     // 用立方体数据填充缓存
  55.     //
  56.     Vertex* vertices;
  57.     VB->Lock(0,0,(void**)&vertices,0);
  58.         
  59.     vertices[0] = Vertex(-1.0f, -1.0f, -1.0f);
  60.     vertices[1] = Vertex(-1.0f,  1.0f, -1.0f);
  61.     vertices[2] = Vertex( 1.0f,  1.0f, -1.0f);
  62.     vertices[3] = Vertex( 1.0f, -1.0f, -1.0f);
  63.     vertices[4] = Vertex(-1.0f, -1.0f,  1.0f);
  64.     vertices[5] = Vertex(-1.0f,  1.0f,  1.0f);
  65.     vertices[6] = Vertex( 1.0f,  1.0f,  1.0f);
  66.     vertices[7] = Vertex( 1.0f, -1.0f,  1.0f);
  67.     VB->Unlock();
  68.     WORD* indices = 0;
  69.     IB->Lock(0,0,(void**)&indices,0);
  70.     // front side
  71.     indices[0]  = 0; indices[1]  = 1; indices[2]  = 2;
  72.     indices[3]  = 0; indices[4]  = 2; indices[5]  = 3;
  73.     // back side
  74.     indices[6]  = 4; indices[7]  = 6; indices[8]  = 5;
  75.     indices[9]  = 4; indices[10] = 7; indices[11] = 6;
  76.     // left side
  77.     indices[12] = 4; indices[13] = 5; indices[14] = 1;
  78.     indices[15] = 4; indices[16] = 1; indices[17] = 0;
  79.     // right side
  80.     indices[18] = 3; indices[19] = 2; indices[20] = 6;
  81.     indices[21] = 3; indices[22] = 6; indices[23] = 7;
  82.     // top
  83.     indices[24] = 1; indices[25] = 5; indices[26] = 6;
  84.     indices[27] = 1; indices[28] = 6; indices[29] = 2;
  85.     // bottom
  86.     indices[30] = 4; indices[31] = 0; indices[32] = 3;
  87.     indices[33] = 4; indices[34] = 3; indices[35] = 7;
  88.     IB->Unlock();
  89.     //
  90.     // 创建取景变换矩阵
  91.     //
  92.     D3DXVECTOR3 position(0.0f,0.0f,-5.0f);
  93.     D3DXVECTOR3 target(0.0f,0.0f,0.0f);
  94.     D3DXVECTOR3 up(0.0f,1.0f,0.0f);
  95.     D3DXMATRIX V;
  96.     D3DXMatrixLookAtLH(&V,&position,&target,&up);
  97.     Device->SetTransform(D3DTS_VIEW,&V);
  98.     //
  99.     // 设置投影矩阵
  100.     //
  101.     D3DXMATRIX proj;
  102.     D3DXMatrixPerspectiveFovLH(
  103.                 &proj,
  104.                 D3DX_PI*0.5f,
  105.                 (float)Width/(float)Height,
  106.                 1.0f,
  107.                 1000.0f);
  108.     Device->SetTransform(D3DTS_PROJECTION,&proj);
  109.     //
  110.     // 选择绘制状态(线框状态)
  111.     //
  112.     Device->SetRenderState(D3DRS_FILLMODE,D3DFILL_WIREFRAME);
  113.     return true;
  114. }
  115. void Cleanup()
  116. {
  117.     d3d::Release<IDirect3DVertexBuffer9*>(VB);
  118.     d3d::Release<IDirect3DIndexBuffer9*>(IB);
  119. }
  120. bool Display(float timeDelta)
  121. {
  122.     if (Device)
  123.     {
  124.         //
  125.         // 旋转矩阵
  126.         //
  127.         D3DXMATRIX Rx,Ry;
  128.         // 绕 x 方向每帧转45度
  129.         D3DXMatrixRotationX(&Rx,3.14f/4.0f);
  130.         // 绕 y 方向每帧递增角度
  131.         static float y = 0.0f;
  132.         D3DXMatrixRotationY(&Ry,y);
  133.         y += timeDelta;
  134.         // 角度达到360度后归零
  135.         if (y>=6.28f)
  136.         {
  137.             y = 0.0f;
  138.         }
  139.         // 结合x and y 方向的旋转角度
  140.         D3DXMATRIX p = Rx * Ry;
  141.         Device->SetTransform(D3DTS_WORLD,&p);
  142.         //
  143.         // 绘制场景
  144.         //
  145.         Device->Clear(0,0,D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER , 0xffffffff,1.0f,0);
  146.         Device->BeginScene();
  147.         Device->SetStreamSource(0,VB,0,sizeof(Vertex));
  148.         Device->SetIndices(IB);
  149.         Device->SetFVF(Vertex::FVF);
  150.         // 绘制立方体
  151.         Device->DrawIndexedPrimitive(D3DPT_TRIANGLELIST,0,0,8,0,12);
  152.         Device->EndScene();
  153.         Device->Present(0,0,0,0);
  154.     }
  155.     return true;
  156. }
  157. //
  158. // WndProc
  159. //
  160. LRESULT CALLBACK d3d::WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam )
  161. {
  162.     switch(msg)
  163.     {
  164.     case WM_DESTROY:
  165.         ::PostQuitMessage(0);
  166.         break;
  167.     case WM_KEYDOWN:
  168.         if(wParam == VK_ESCAPE)
  169.             ::DestroyWindow(hwnd);
  170.         break;
  171.     }
  172.     return ::DefWindowProc(hwnd,msg,wParam,lParam);
  173. }
  174. //
  175. //  WinMain
  176. //
  177. int WINAPI WinMain(HINSTANCE hInstance,
  178.                    HINSTANCE hPrevInstance, 
  179.                    LPSTR lpCmdLine,
  180.                    int nShowCmd )
  181. {
  182.     //程序入口地址
  183.     //初始化D3D
  184.     if (!d3d::InitD3D(hInstance,640,480,true,D3DDEVTYPE_HAL,&Device))
  185.     {
  186.         ::MessageBox(0, "InitD3D() - FAILED", 0, 0);
  187.         return 0;
  188.     }
  189.     //分配资源
  190.     if (!Setup())
  191.     {
  192.         ::MessageBox(0, "Setup() - FAILED", 0, 0);
  193.         return 0;
  194.     }
  195.     //进入消息循环
  196.     d3d::EnterMsgLoop(Display);
  197.     //清理资源
  198.     Cleanup();
  199.     Device->Release();
  200.     return 0;
  201. }

需要注意的一点是: 本例中是用世界变换来指定立方体的方向。因为设置顶点格式时将顶点的位置属性设置为不能改变。

                                    const DWORD Vertex::FVF = D3DFVF_XYZ;

 

用的是上一篇文章中的框架,只是修改了d3dUtility.cpp里面的三个函数:Setup() Display() Clean() ,框架确实好用。过段时间研究下MS的DXUT。附图:

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值