CameraClass

CameraClass.h

 1 //=============================================================================
 2 // Name: CameraClass.h
 3 //    Des: 一个封装了实现虚拟摄像机的类的头文件
 4 //=============================================================================
 5 #pragma once
 6 #include <d3d9.h>
 7 #include <d3dx9.h>
 8 
 9 class CameraClass
10 {
11 private:
12     //成员变量的申明
13     D3DXVECTOR3             m_vRightVector;// 右分量向量
14     D3DXVECTOR3                m_vUpVector;           // 上分量向量
15     D3DXVECTOR3                m_vLookVector;         // 观察方向向量
16     D3DXVECTOR3                m_vCameraPosition;// 摄像机位置的向量
17     D3DXVECTOR3                m_vTargetPosition;        //目标观察位置的向量
18     D3DXMATRIX                m_matView;          // 取景变换矩阵
19     D3DXMATRIX                m_matProj;          // 投影变换矩阵   
20     LPDIRECT3DDEVICE9        m_pd3dDevice;  //Direct3D设备对象
21 public:
22         //一个计算取景变换的函数
23     VOID CalculateViewMatrix(D3DXMATRIX *pMatrix);    //计算取景变换矩阵
24         //三个Get系列函数
25     VOID GetProjMatrix(D3DXMATRIX *pMatrix)  { *pMatrix = m_matProj; }  //返回当前投影矩阵
26     VOID GetCameraPosition(D3DXVECTOR3 *pVector)  { *pVector = m_vCameraPosition; } //返回当前摄像机位置矩阵
27     VOID GetLookVector(D3DXVECTOR3 *pVector) { *pVector = m_vLookVector; }  //返回当前的观察矩阵
28 
29         //四个Set系列函数,注意他们都参数都有默认值NULL的,调用时不写参数也可以
30     VOID SetTargetPosition(D3DXVECTOR3 *pLookat = NULL);  //设置摄像机的目标观察位置向量
31     VOID SetCameraPosition(D3DXVECTOR3 *pVector = NULL); //设置摄像机所在的位置向量
32     VOID SetViewMatrix(D3DXMATRIX *pMatrix = NULL);  //设置取景变换矩阵
33     VOID SetProjMatrix(D3DXMATRIX *pMatrix = NULL);  //设置投影变换矩阵
34  
35 
36 
37 public:
38         // 沿各分量平移的三个函数
39     VOID MoveAlongRightVec(FLOAT fUnits);   // 沿right向量移动
40     VOID MoveAlongUpVec(FLOAT fUnits);      // 沿up向量移动
41     VOID MoveAlongLookVec(FLOAT fUnits);    // 沿look向量移动
42  
43     // 绕各分量旋转的三个函数
44     VOID RotationRightVec(FLOAT fAngle);    // 绕right向量选择
45     VOID RotationUpVec(FLOAT fAngle);       // 绕up向量旋转
46     VOID RotationLookVec(FLOAT fAngle);     // 绕look向量旋转
47 public:
48     CameraClass(IDirect3DDevice9 *pd3dDevice);
49     virtual ~CameraClass(void);
50 };
View Code

CameraClass.cpp

  1 //=============================================================================
  2 // Name: CameraClass.cpp
  3 //    Des: 一个封装了实现虚拟摄像机的类的源文件
  4 //=============================================================================
  5 #include "CameraClass.h"
  6  
  7 #ifndef WINDOW_WIDTH
  8 #define WINDOW_WIDTH    800                        //为窗口宽度定义的宏,以方便在此处修改窗口宽度
  9 #define WINDOW_HEIGHT    600                    //为窗口高度定义的宏,以方便在此处修改窗口高度
 10 #endif
 11  
 12 //-----------------------------------------------------------------------------
 13 // Desc: 构造函数
 14 //-----------------------------------------------------------------------------
 15 CameraClass::CameraClass(IDirect3DDevice9 *pd3dDevice)
 16 {
 17     m_pd3dDevice = pd3dDevice;
 18     m_vRightVector  = D3DXVECTOR3(1.0f, 0.0f, 0.0f);   // 默认右向量与X正半轴重合
 19     m_vUpVector     = D3DXVECTOR3(0.0f, 1.0f, 0.0f);   // 默认上向量与Y正半轴重合
 20     m_vLookVector   = D3DXVECTOR3(0.0f, 0.0f, 1.0f);   // 默认观察向量与Z正半轴重合
 21     m_vCameraPosition  = D3DXVECTOR3(0.0f, 0.0f, -250.0f);   // 默认摄像机坐标为(0.0f, 0.0f, -250.0f)
 22     m_vTargetPosition    = D3DXVECTOR3(0.0f, 0.0f, 0.0f);//默认观察目标位置为(0.0f, 0.0f, 0.0f);
 23  
 24 }
 25  
 26  
 27 //-----------------------------------------------------------------------------
 28 // Name:CameraClass::CalculateViewMatrix( )
 29 // Desc: 根据给定的矩阵计算出取景变换矩阵
 30 //-----------------------------------------------------------------------------
 31 VOID CameraClass::CalculateViewMatrix(D3DXMATRIX *pMatrix) 
 32 {
 33     //1.先把3个向量都规范化并使其相互垂直,成为一组正交矩阵
 34     D3DXVec3Normalize(&m_vLookVector, &m_vLookVector);  //规范化观察分量
 35     D3DXVec3Cross(&m_vUpVector, &m_vLookVector, &m_vRightVector);    // 上向量与观察向量垂直
 36     D3DXVec3Normalize(&m_vUpVector, &m_vUpVector);                // 规范化上向量
 37     D3DXVec3Cross(&m_vRightVector, &m_vUpVector, &m_vLookVector);    // 右向量与上向量垂直
 38     D3DXVec3Normalize(&m_vRightVector, &m_vRightVector);          // 规范化右向量
 39  
 40  
 41     // 2.创建出取景变换矩阵
 42     //依次写出取景变换矩阵的第一行
 43     pMatrix->_11 = m_vRightVector.x;           // Rx
 44     pMatrix->_12 = m_vUpVector.x;              // Ux
 45     pMatrix->_13 = m_vLookVector.x;            // Lx
 46     pMatrix->_14 = 0.0f;
 47     //依次写出取景变换矩阵的第二行
 48     pMatrix->_21 = m_vRightVector.y;           // Ry
 49     pMatrix->_22 = m_vUpVector.y;              // Uy
 50     pMatrix->_23 = m_vLookVector.y;            // Ly
 51     pMatrix->_24 = 0.0f;
 52     //依次写出取景变换矩阵的第三行
 53     pMatrix->_31 = m_vRightVector.z;           // Rz
 54     pMatrix->_32 = m_vUpVector.z;              // Uz
 55     pMatrix->_33 = m_vLookVector.z;            // Lz
 56     pMatrix->_34 = 0.0f;
 57     //依次写出取景变换矩阵的第四行
 58     pMatrix->_41 = -D3DXVec3Dot(&m_vRightVector, &m_vCameraPosition);    // -P*R
 59     pMatrix->_42 = -D3DXVec3Dot(&m_vUpVector, &m_vCameraPosition);       // -P*U
 60     pMatrix->_43 = -D3DXVec3Dot(&m_vLookVector, &m_vCameraPosition);     // -P*L
 61     pMatrix->_44 = 1.0f;
 62 }
 63  
 64  
 65 //-----------------------------------------------------------------------------
 66 // Name:CameraClass::SetTargetPosition( )
 67 // Desc: 设置摄像机的观察位置
 68 //-----------------------------------------------------------------------------
 69 VOID CameraClass::SetTargetPosition(D3DXVECTOR3 *pLookat) 
 70 {
 71     //先看看pLookat是否为默认值NULL
 72     if (pLookat != NULL)  m_vTargetPosition = (*pLookat);
 73     else m_vTargetPosition = D3DXVECTOR3(0.0f, 0.0f, 1.0f);
 74  
 75     m_vLookVector = m_vTargetPosition - m_vCameraPosition;//观察点位置减摄像机位置,得到观察方向向量
 76     D3DXVec3Normalize(&m_vLookVector, &m_vLookVector);//规范化m_vLookVector向量
 77  
 78     //正交并规范化m_vUpVector和m_vRightVector
 79     D3DXVec3Cross(&m_vUpVector, &m_vLookVector, &m_vRightVector);
 80     D3DXVec3Normalize(&m_vUpVector, &m_vUpVector);
 81     D3DXVec3Cross(&m_vRightVector, &m_vUpVector, &m_vLookVector);
 82     D3DXVec3Normalize(&m_vRightVector, &m_vRightVector);
 83 }
 84  
 85 //-----------------------------------------------------------------------------
 86 // Name:CameraClass::SetCameraPosition( )
 87 // Desc: 设置摄像机所在的位置
 88 //-----------------------------------------------------------------------------
 89 VOID CameraClass::SetCameraPosition(D3DXVECTOR3 *pVector) 
 90 {
 91     D3DXVECTOR3 V = D3DXVECTOR3(0.0f, 0.0f, -250.0f);
 92     m_vCameraPosition = pVector ? (*pVector) : V;//三目运算符,如果pVector为真的话,
 93                                                                         //返回*pVector的值(即m_vCameraPosition=*pVector),
 94                                                                         //否则返回V的值(即m_vCameraPosition=V)
 95 }
 96  
 97 //-----------------------------------------------------------------------------
 98 // Name:CameraClass::SetViewMatrix( )
 99 // Desc: 设置取景变换矩阵
100 //-----------------------------------------------------------------------------
101 VOID CameraClass::SetViewMatrix(D3DXMATRIX *pMatrix) 
102 {
103     //根据pMatrix的值先做一下判断
104     if (pMatrix) m_matView = *pMatrix;
105     else CalculateViewMatrix(&m_matView);
106     m_pd3dDevice->SetTransform(D3DTS_VIEW, &m_matView);
107     //把取景变换矩阵的值分下来分别给右分量,上分量,和观察分量
108     m_vRightVector = D3DXVECTOR3(m_matView._11, m_matView._12, m_matView._13);
109     m_vUpVector    = D3DXVECTOR3(m_matView._21, m_matView._22, m_matView._23);
110     m_vLookVector  = D3DXVECTOR3(m_matView._31, m_matView._32, m_matView._33);
111 }
112  
113 //-----------------------------------------------------------------------------
114 // Name:CameraClass::SetProjMatrix( )
115 // Desc: 设置投影变换矩阵
116 //-----------------------------------------------------------------------------
117 VOID CameraClass::SetProjMatrix(D3DXMATRIX *pMatrix) 
118 {
119     //判断值有没有,没有的话就计算一下
120     if (pMatrix != NULL) m_matProj = *pMatrix;
121     else D3DXMatrixPerspectiveFovLH(&m_matProj, D3DX_PI / 4.0f, (float)((double)WINDOW_WIDTH/WINDOW_HEIGHT), 1.0f, 30000.0f);//视截体远景设为30000.0f,这样就不怕看不到远处的物体了
122     m_pd3dDevice->SetTransform(D3DTS_PROJECTION, &m_matProj);//设置投影变换矩阵
123 }
124  
125 //-----------------------------------------------------------------------------
126 // Name:CameraClass::MoveAlongRightVec( )
127 // Desc: 沿右向量平移fUnits个单位
128 //-----------------------------------------------------------------------------
129 VOID CameraClass::MoveAlongRightVec(FLOAT fUnits) 
130 {
131     //直接乘以fUnits的量来累加就行了
132     m_vCameraPosition += m_vRightVector * fUnits;
133     m_vTargetPosition   += m_vRightVector * fUnits;
134 }
135  
136 //-----------------------------------------------------------------------------
137 // Name:CameraClass::MoveAlongUpVec( )
138 // Desc:  沿上向量平移fUnits个单位
139 //-----------------------------------------------------------------------------
140 VOID CameraClass::MoveAlongUpVec(FLOAT fUnits) 
141 {
142     //直接乘以fUnits的量来累加就行了
143     m_vCameraPosition += m_vUpVector * fUnits;
144     m_vTargetPosition   += m_vUpVector * fUnits;
145 }
146  
147 //-----------------------------------------------------------------------------
148 // Name:CameraClass::MoveAlongLookVec( )
149 // Desc:  沿观察向量平移fUnits个单位
150 //-----------------------------------------------------------------------------
151 VOID CameraClass::MoveAlongLookVec(FLOAT fUnits) 
152 {
153     //直接乘以fUnits的量来累加就行了
154     m_vCameraPosition += m_vLookVector * fUnits;
155     m_vTargetPosition   += m_vLookVector * fUnits;
156 }
157  
158 //-----------------------------------------------------------------------------
159 // Name:CameraClass::RotationRightVec( )
160 // Desc:  沿右向量旋转fAngle个弧度单位的角度
161 //-----------------------------------------------------------------------------
162 VOID CameraClass::RotationRightVec(FLOAT fAngle) 
163 {
164     D3DXMATRIX R;
165     D3DXMatrixRotationAxis(&R, &m_vRightVector, fAngle);//创建出绕m_vRightVector旋转fAngle个角度的R矩阵
166     D3DXVec3TransformCoord(&m_vUpVector, &m_vUpVector, &R);//让m_vUpVector向量绕m_vRightVector旋转fAngle个角度
167     D3DXVec3TransformCoord(&m_vLookVector, &m_vLookVector, &R);//让m_vLookVector向量绕m_vRightVector旋转fAngle个角度
168  
169     m_vTargetPosition = m_vLookVector * D3DXVec3Length(&m_vCameraPosition);//更新一下观察点的新位置(方向乘以模=向量)
170 }
171  
172 //-----------------------------------------------------------------------------
173 // Name:CameraClass::RotationUpVec( )
174 // Desc:  沿上向量旋转fAngle个弧度单位的角度
175 //-----------------------------------------------------------------------------
176 VOID CameraClass::RotationUpVec(FLOAT fAngle) 
177 {
178     D3DXMATRIX R;
179     D3DXMatrixRotationAxis(&R, &m_vUpVector, fAngle);//创建出绕m_vUpVector旋转fAngle个角度的R矩阵
180     D3DXVec3TransformCoord(&m_vRightVector, &m_vRightVector, &R);//让m_vRightVector向量绕m_vUpVector旋转fAngle个角度
181     D3DXVec3TransformCoord(&m_vLookVector, &m_vLookVector, &R);//让m_vLookVector向量绕m_vUpVector旋转fAngle个角度
182  
183     m_vTargetPosition = m_vLookVector * D3DXVec3Length(&m_vCameraPosition);//更新一下观察点的新位置(方向乘以模=向量)
184 }
185  
186 //-----------------------------------------------------------------------------
187 // Name:CameraClass::RotationLookVec( )
188 // Desc:  沿观察向量旋转fAngle个弧度单位的角度
189 //-----------------------------------------------------------------------------
190 VOID CameraClass::RotationLookVec(FLOAT fAngle) 
191 {
192     D3DXMATRIX R;
193     D3DXMatrixRotationAxis(&R, &m_vLookVector, fAngle);//创建出绕m_vLookVector旋转fAngle个角度的R矩阵
194     D3DXVec3TransformCoord(&m_vRightVector, &m_vRightVector, &R);//让m_vRightVector向量绕m_vLookVector旋转fAngle个角度
195     D3DXVec3TransformCoord(&m_vUpVector, &m_vUpVector, &R);//让m_vUpVector向量绕m_vLookVector旋转fAngle个角度
196  
197     m_vTargetPosition = m_vLookVector * D3DXVec3Length(&m_vCameraPosition);//更新一下观察点的新位置(方向乘以模=向量)
198 }
199  
200  
201 //-----------------------------------------------------------------------------
202 // Desc: 析构函数
203 //-----------------------------------------------------------------------------
204 CameraClass::~CameraClass(void)
205 {
206 }
View Code

 

main.cpp

//-----------------------------------【宏定义部分】--------------------------------------------
#define WINDOW_WIDTH    800
#define WINDOW_HEIGHT    600
#define WINDOW_TITLE    L"安康学院数字媒体技术"


//-----------------------------------【头文件包含部分】---------------------------------------
#include<d3d9.h>
#include <d3dx9.h>
#include <tchar.h>
#include <time.h>
#include "DirectInputClass.h"
//第1步,添加cameraclass.h头文件
#include "CameraClass.h"

//-----------------------------------【库文件包含部分】---------------------------------------
#pragma comment(lib,"winmm.lib") 
#pragma comment(lib,"d3d9.lib")
#pragma comment(lib,"d3dx9.lib")
#pragma comment(lib, "dinput8.lib") 
#pragma comment(lib,"dxguid.lib")

//第2步:定义顶点结构体
struct CUSTOMVERTEX
{
    FLOAT _x,  _y,  _z;
    FLOAT _nx, _ny, _nz;
    FLOAT _u,  _v;
    CUSTOMVERTEX(FLOAT x, FLOAT y, FLOAT z, 
        FLOAT nx, FLOAT ny, FLOAT nz, FLOAT u, FLOAT v)
    {
        _x  = x,  _y  = y,  _z  = z;
        _nx = nx, _ny = ny, _nz = nz;
        _u  = u,  _v  = v;
    }
};
#define D3DFVF_CUSTOMVERTEX  (D3DFVF_XYZ | D3DFVF_NORMAL | D3DFVF_TEX1)

//-----------------------------------【全局变量声明部分】-------------------------------------
LPDIRECT3DDEVICE9       g_pd3dDevice            = NULL; 
LPD3DXFONT                g_pTextFPS                =NULL;
LPD3DXFONT                g_pTextAdaperName       = NULL;
LPD3DXFONT                g_pTextHelper           = NULL; 
LPD3DXFONT                g_pTextInfor            = NULL;
float                   g_FPS=0.0f;
wchar_t                    g_strFPS[50]={0}; 
wchar_t                    g_strAdapterName[60]={0};
D3DXMATRIX                g_matWorld;
DInputClass*            g_pDInput = NULL;         //一个DInputClass类的指针
//第3步:定义CameraClass类的指针
CameraClass*            g_pCamera               = NULL;
LPD3DXMESH                g_pMesh     = NULL; 
D3DMATERIAL9*            g_pMaterials    = NULL; 
LPDIRECT3DTEXTURE9*        g_pTextures     = NULL;
DWORD                    g_dwNumMtrls    = 0; 
//第4步:定义柱子网格对象,草地对象
LPD3DXMESH                            g_cylinder = NULL;     //柱子网格对象
D3DMATERIAL9                            g_MaterialCylinder; //材质
LPDIRECT3DVERTEXBUFFER9        g_pVertexBuffer           = NULL;  //绘制草地的顶点缓存对象
LPDIRECT3DTEXTURE9                g_pTexture             = NULL;  //绘制草地的纹理对象

//-----------------------------------【全局函数声明部分】-------------------------------------
LRESULT CALLBACK    WndProc( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam );
HRESULT                    Direct3D_Init(HWND hwnd,HINSTANCE hInstance);
HRESULT                    Objects_Init();
void                    Direct3D_Render(HWND hwnd);
void                    Direct3D_Update(HWND hwnd);
void                    Direct3D_CleanUp( );
float                    Get_FPS();
//第5步:注销 Matrix_Set(),定义HelpText_Render
//void                    Matrix_Set();
void                    HelpText_Render(HWND hwnd);



//-----------------------------------【WinMain( )函数】--------------------------------------
//    描述:Windows应用程序的入口函数,我们的程序从这里开始
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,LPSTR lpCmdLine, int nShowCmd)
{
    //【1】开始设计一个完整的窗口类
    WNDCLASSEX wndClass = { 0 };
    wndClass.cbSize = sizeof( WNDCLASSEX ) ;
    wndClass.style = CS_HREDRAW | CS_VREDRAW;
    wndClass.lpfnWndProc = WndProc;
    wndClass.cbClsExtra        = 0;
    wndClass.cbWndExtra        = 0;
    wndClass.hInstance = hInstance;    
    wndClass.hIcon=(HICON)::LoadImage(NULL,L"icon.ico",IMAGE_ICON,0,0,LR_DEFAULTSIZE|LR_LOADFROMFILE);
    wndClass.hCursor = LoadCursor( NULL, IDC_ARROW );
    wndClass.hbrBackground=(HBRUSH)GetStockObject(GRAY_BRUSH);
    wndClass.lpszMenuName = NULL;
    wndClass.lpszClassName = L"ForTheDreamOfGameDevelop";

    //【2】注册窗口类
    if( !RegisterClassEx( &wndClass ) )    
        return -1;

    //【3】正式创建窗口
    HWND hwnd = CreateWindow( L"ForTheDreamOfGameDevelop",WINDOW_TITLE,    
        WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, WINDOW_WIDTH,
        WINDOW_HEIGHT, NULL, NULL, hInstance, NULL );

    if (!(S_OK==Direct3D_Init (hwnd,hInstance)))
    {
        MessageBox(hwnd, _T("Direct3D初始化失败~!"), _T("消息窗口"), 0); //使用MessageBox函数,创建一个消息窗口 
    }


    //【4】窗口的移动、显示与更新
    MoveWindow(hwnd,250,80,WINDOW_WIDTH,WINDOW_HEIGHT,true);
    ShowWindow(hwnd, nShowCmd );
    UpdateWindow(hwnd);

    g_pDInput = new DInputClass();
    g_pDInput->Init(hwnd,hInstance,DISCL_FOREGROUND | DISCL_NONEXCLUSIVE,DISCL_FOREGROUND | DISCL_NONEXCLUSIVE);
    //第6步:换歌曲
    PlaySound(L"雅尼 - 兰花.wav", NULL, SND_FILENAME | SND_ASYNC|SND_LOOP); //循环播放背景音乐 


    //【5】消息循环过程
    MSG msg = { 0 };
    while( msg.message != WM_QUIT )
        {
        if( PeekMessage( &msg, 0, 0, 0, PM_REMOVE ) )   //查看应用程序消息队列,有消息时将队列中的消息派发出去。
        {
            TranslateMessage( &msg );        //将虚拟键消息转换为字符消息
            DispatchMessage( &msg );        //该函数分发一个消息给窗口程序。
        }
        else
        {
//第6步 添加调用更新函数,进行画面的更新
            Direct3D_Update(hwnd);            //调用更新函数,进行画面的更新
            Direct3D_Render(hwnd);   //进行渲染
        }
    }

    //【6】窗口类的注销
    UnregisterClass(L"ForTheDreamOfGameDevelop", wndClass.hInstance); 
        return 0;  
}

//-----------------------------------【WndProc( )函数】--------------------------------------
LRESULT CALLBACK WndProc( HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam )      
{
    switch( message )
    {
        case WM_PAINT:
            Direct3D_Render(hwnd);
            ValidateRect(hwnd, NULL);
            break;

        case WM_KEYDOWN:
            if (wParam == VK_ESCAPE)
                DestroyWindow(hwnd);
            break;

        case WM_DESTROY:
            Direct3D_CleanUp();
            PostQuitMessage( 0 );
            break;    

        default:
            return DefWindowProc( hwnd, message, wParam, lParam );
    }
    return 0;
}

//-----------------------------------【Direct3D_Init( )函数】--------------------------------------
//第4步:对应修改Direct3D_Init参数
HRESULT    Direct3D_Init(HWND hwnd,HINSTANCE hInstance)
{
    //Direct3D初始化,第一步
    LPDIRECT3D9 pD3D=NULL;
    if(NULL==(pD3D=Direct3DCreate9(D3D_SDK_VERSION)))
        return E_FAIL;

    //Direct3D初始化,第二步
    D3DCAPS9 caps; int vp = 0;
    if( FAILED( pD3D->GetDeviceCaps( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, &caps ) ) )
    {
        return E_FAIL;
    }
    if( caps.DevCaps & D3DDEVCAPS_HWTRANSFORMANDLIGHT )

        vp = D3DCREATE_HARDWARE_VERTEXPROCESSING; 
    else
        vp = D3DCREATE_SOFTWARE_VERTEXPROCESSING;


    //Direct3D初始化,第三步,D3DPRESENT_PARAMETERS结构体

    D3DPRESENT_PARAMETERS d3dpp; 
    ZeroMemory(&d3dpp, sizeof(d3dpp));
    d3dpp.BackBufferWidth            = WINDOW_WIDTH;
    d3dpp.BackBufferHeight           = WINDOW_HEIGHT;
    d3dpp.BackBufferFormat           = D3DFMT_A8R8G8B8;
    d3dpp.BackBufferCount            = 2;
    d3dpp.MultiSampleType            = D3DMULTISAMPLE_NONE;
    d3dpp.MultiSampleQuality         = 0;
    d3dpp.SwapEffect                 = D3DSWAPEFFECT_DISCARD; 
    d3dpp.hDeviceWindow              = hwnd;
    d3dpp.Windowed                   = true;
    d3dpp.EnableAutoDepthStencil     = true; 
    d3dpp.AutoDepthStencilFormat     = D3DFMT_D24S8;
    d3dpp.Flags                      = 0;
    d3dpp.FullScreen_RefreshRateInHz = 0;
    d3dpp.PresentationInterval       = D3DPRESENT_INTERVAL_IMMEDIATE;

    //Direct3D初始化,第四步

    if(FAILED(pD3D->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, 
        hwnd, vp, &d3dpp, &g_pd3dDevice)))
        return E_FAIL;

    wchar_t TempName[60]=L"当前显卡型号:";
    D3DADAPTER_IDENTIFIER9 Adapter;
    pD3D->GetAdapterIdentifier(0,0,&Adapter);
    int len = MultiByteToWideChar(CP_ACP,0, Adapter.Description, -1, NULL, 0);
    MultiByteToWideChar(CP_ACP, 0, Adapter.Description, -1, g_strAdapterName, len);
    wcscat_s(TempName,g_strAdapterName);
    wcscpy_s(g_strAdapterName,TempName);

    if(!(S_OK==Objects_Init())) return E_FAIL;
    SAFE_RELEASE(pD3D); 
    return S_OK;

}


//-----------------------------------【Object_Init( )函数】--------------------------------------
    HRESULT Objects_Init()
{
        D3DXCreateFont(g_pd3dDevice, 36, 0, 0, 1000, false, DEFAULT_CHARSET, 
        OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, 0, _T("Calibri"), &g_pTextFPS);

        D3DXCreateFont(g_pd3dDevice, 20, 0, 1000, 0, false, DEFAULT_CHARSET, 
        OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, 0, L"华文中宋", &g_pTextAdaperName); 

        D3DXCreateFont(g_pd3dDevice, 23, 0, 1000, 0, false, DEFAULT_CHARSET, 
        OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, 0, L"微软雅黑", &g_pTextHelper); 
    
        D3DXCreateFont(g_pd3dDevice, 26, 0, 1000, 0, false, DEFAULT_CHARSET, 
        OUT_DEFAULT_PRECIS, DEFAULT_QUALITY, 0, L"黑体", &g_pTextInfor); 


    // 从X文件中加载网格数据
    LPD3DXBUFFER pAdjBuffer  = NULL;
    LPD3DXBUFFER pMtrlBuffer = NULL;
    //第7步:换模型
        //D3DXLoadMeshFromX(L"Optimus.x", D3DXMESH_MANAGED, g_pd3dDevice, 
        D3DXLoadMeshFromX(L"WYJ.X", D3DXMESH_MANAGED, g_pd3dDevice, 
        &pAdjBuffer, &pMtrlBuffer, NULL, &g_dwNumMtrls, &g_pMesh);
    // 读取材质和纹理数据
    D3DXMATERIAL *pMtrls = (D3DXMATERIAL*)pMtrlBuffer->GetBufferPointer();//创建一个D3DXMATERIAL结构体用于读取材质和纹理信息
    g_pMaterials = new D3DMATERIAL9[g_dwNumMtrls];
    g_pTextures  = new LPDIRECT3DTEXTURE9[g_dwNumMtrls];

    for (DWORD i=0; i<g_dwNumMtrls; i++) 
    {
        //获取材质,并设置一下环境光的颜色值
        g_pMaterials[i] = pMtrls[i].MatD3D;
        g_pMaterials[i].Ambient = g_pMaterials[i].Diffuse;
        //创建一下纹理对象
        g_pTextures[i]  = NULL;
        D3DXCreateTextureFromFileA(g_pd3dDevice, pMtrls[i].pTextureFilename, &g_pTextures[i]);
    }
    pAdjBuffer->Release();
    pMtrlBuffer->Release();


    //第8步:初始化草地,柱子,灯光,摄像机
    // 设置渲染状态
    //g_pd3dDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_CCW);   //开启背面消隐
    //g_pd3dDevice->SetRenderState(D3DRS_AMBIENT, D3DXCOLOR(1.0f, 1.0f, 1.0f, 1.0f)); //设置环境光

    //Matrix_Set();//调用封装了四大变换的函数,对Direct3D世界变换,取景变换,投影变换,视口变换进行设置
    
    // 创建一片草坪,50X50=250张纹理
    g_pd3dDevice->CreateVertexBuffer(4 * sizeof(CUSTOMVERTEX), 0, 
    D3DFVF_CUSTOMVERTEX, D3DPOOL_MANAGED, &g_pVertexBuffer, 0);

    CUSTOMVERTEX *pVertices = NULL;
    g_pVertexBuffer->Lock(0, 0, (void**)&pVertices, 0);
    pVertices[0] = CUSTOMVERTEX(-500.0f, 0.0f, -500.0f, 0.0f, 1.0f, 0.0f, 0.0f, 50.0f);
    pVertices[1] = CUSTOMVERTEX(-500.0f, 0.0f,  500.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f);
    pVertices[2] = CUSTOMVERTEX( 500.0f, 0.0f, -500.0f, 0.0f, 1.0f, 0.0f, 50.0f, 50.0f);
    pVertices[3] = CUSTOMVERTEX( 500.0f, 0.0f,  500.0f, 0.0f, 1.0f, 0.0f, 50.0f, 0.0f);
    g_pVertexBuffer->Unlock();

    // 创建地板纹理
    D3DXCreateTextureFromFile(g_pd3dDevice, L"grass.jpg", &g_pTexture);

    //创建柱子
    D3DXCreateCylinder(g_pd3dDevice, 10.0f, 10.0f, 500.0f, 60, 60,  &g_cylinder, 0);
    g_MaterialCylinder.Ambient  = D3DXCOLOR(0.9f, 0.0f, 0.8f, 1.0f);  
    g_MaterialCylinder.Diffuse  = D3DXCOLOR(0.9f, 0.0f, 0.8f, 1.0f);  
    g_MaterialCylinder.Specular = D3DXCOLOR(0.9f, 0.2f, 0.9f, 0.9f);  
    g_MaterialCylinder.Emissive = D3DXCOLOR(0.0f, 0.0f, 0.9f, 1.0f);

    // 设置光照  
    D3DLIGHT9 light;  
    ::ZeroMemory(&light, sizeof(light));  
    light.Type          = D3DLIGHT_DIRECTIONAL;  
    light.Ambient       = D3DXCOLOR(0.7f, 0.7f, 0.7f, 1.0f);  
    light.Diffuse       = D3DXCOLOR(1.0f, 1.0f, 1.0f, 1.0f);  
    light.Specular      = D3DXCOLOR(0.5f, 0.5f, 0.5f, 1.0f);  
    light.Direction     = D3DXVECTOR3(1.0f, 0.0f, 0.0f);  
    g_pd3dDevice->SetLight(0, &light);  
    g_pd3dDevice->LightEnable(0, true);  
    g_pd3dDevice->SetRenderState(D3DRS_NORMALIZENORMALS, true);  
    g_pd3dDevice->SetRenderState(D3DRS_SPECULARENABLE, true);

    // 创建并初始化虚拟摄像机
    g_pCamera = new CameraClass(g_pd3dDevice);
    g_pCamera->SetCameraPosition(&D3DXVECTOR3(0.0f, 200.0f, -300.0f));  //设置摄像机所在的位置
    g_pCamera->SetTargetPosition(&D3DXVECTOR3(0.0f, 300.0f, 0.0f));  //设置目标观察点所在的位置
    g_pCamera->SetViewMatrix();  //设置取景变换矩阵
    g_pCamera->SetProjMatrix();  //设置投影变换矩阵

    // 设置纹理过滤和纹理寻址方式
    g_pd3dDevice->SetSamplerState(0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR);
    g_pd3dDevice->SetSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR);
    g_pd3dDevice->SetSamplerState(0, D3DSAMP_MIPFILTER, D3DTEXF_LINEAR);
    return S_OK;
}
    //第9步:注销掉Matrix_Set( )函数
    //-----------------------------------【Matrix_Set( )函数】--------------------------------------
//void Matrix_Set()
//{
////第11步 世界变换矩阵的设置,改动到鼠标键盘操作后对世界变换矩阵修改
//
//    //--------------------------------------------------------------------------------------
//    //【四大变换之一】:世界变换矩阵的设置
//    //--------------------------------------------------------------------------------------
//
//    //--------------------------------------------------------------------------------------
//    //【四大变换之二】:取景变换矩阵的设置
//    //--------------------------------------------------------------------------------------
//    D3DXMATRIX matView; //定义一个矩阵
//    
//    D3DXVECTOR3 vEye(0.0f, 0.0f, -1300.0f);  //摄像机的位置
//    D3DXVECTOR3 vAt(0.0f, 0.0f, 0.0f); //观察点的位置
//    D3DXVECTOR3 vUp(0.0f, 1.0f, 0.0f);//向上的向量
//    D3DXMatrixLookAtLH(&matView, &vEye, &vAt, &vUp); //计算出取景变换矩阵
//    g_pd3dDevice->SetTransform(D3DTS_VIEW, &matView); //应用取景变换矩阵
//
//    //--------------------------------------------------------------------------------------
//    //【四大变换之三】:投影变换矩阵的设置
//    //--------------------------------------------------------------------------------------
//    D3DXMATRIX matProj; //定义一个矩阵
//    D3DXMatrixPerspectiveFovLH(&matProj, D3DX_PI / 4.0f,(float)((double)WINDOW_WIDTH/WINDOW_HEIGHT),1.0f, 10000.0f); //计算投影变换矩阵
//    g_pd3dDevice->SetTransform(D3DTS_PROJECTION, &matProj);  //设置投影变换矩阵
//
//    //--------------------------------------------------------------------------------------
//    //【四大变换之四】:视口变换的设置
//    //--------------------------------------------------------------------------------------
//    D3DVIEWPORT9 vp; //实例化一个D3DVIEWPORT9结构体,然后做填空题给各个参数赋值就可以了
//    vp.X      = 0;        //表示视口相对于窗口的X坐标
//    vp.Y      = 0;        //视口相对对窗口的Y坐标
//    vp.Width  = WINDOW_WIDTH;    //视口的宽度
//    vp.Height = WINDOW_HEIGHT; //视口的高度
//    vp.MinZ   = 0.0f; //视口在深度缓存中的最小深度值
//    vp.MaxZ   = 1.0f;    //视口在深度缓存中的最大深度值
//    g_pd3dDevice->SetViewport(&vp); //视口的设置
//}

//-----------------------------------【Direct3D_Update( )函数】--------------------------------
//    描述:不是即时渲染代码但是需要即时调用的,如按键后的坐标的更改,都放在这里
//--------------------------------------------------------------------------------------------------
void    Direct3D_Update( HWND hwnd)
{

        g_pDInput->GetInput();

//第10步:注销掉以前的键鼠控制代码
    //// 按住鼠标左键并拖动,为平移操作
    //
    //static FLOAT fPosX = 0.0f, fPosY = 0.0f, fPosZ = 0.0f;
    //if (g_pDInput->IsMouseButtonDown(0))
    //{
    //    fPosX += (g_pDInput->MouseDX())*  0.08f;
    //    fPosY += (g_pDInput->MouseDY()) * -0.08f;
    //}

    ////鼠标滚轮,为观察点收缩操作
    //fPosZ +=(g_pDInput->MouseDZ())* 0.02f;// g_diMouseState.lZ * 0.02f;

    //// 平移物体
    //if (g_pDInput->IsKeyDown(DIK_A)) fPosX -= 0.005f;
    //if (g_pDInput->IsKeyDown(DIK_D)) fPosX += 0.005f;
    //if (g_pDInput->IsKeyDown(DIK_W)) fPosY += 0.005f;
    //if (g_pDInput->IsKeyDown(DIK_S)) fPosY -= 0.005f;


    //D3DXMatrixTranslation(&g_matWorld, fPosX, fPosY, fPosZ);


    //// 按住鼠标右键并拖动,为旋转操作
    //static float fAngleX = 0.0f, fAngleY =0.0f;
    //if (g_pDInput->IsMouseButtonDown(1)) 
    //{
    //    fAngleX += (g_pDInput->MouseDY())* -0.01f;
    //    fAngleY += (g_pDInput->MouseDX()) * -0.01f;
    //}
    //// 旋转物体
    //if (g_pDInput->IsKeyDown(DIK_UP)) fAngleX += 0.005f;
    //if (g_pDInput->IsKeyDown(DIK_DOWN)) fAngleX -= 0.005f;
    //if (g_pDInput->IsKeyDown(DIK_LEFT)) fAngleY -= 0.005f;
    //if (g_pDInput->IsKeyDown(DIK_RIGHT)) fAngleY += 0.005f;


    //D3DXMATRIX Rx, Ry;
    //D3DXMatrixRotationX(&Rx, fAngleX);
    //D3DXMatrixRotationY(&Ry, fAngleY);

    ////得到最终的矩阵并设置
    //g_matWorld = Rx * Ry * g_matWorld;//得到最终的矩阵
    //g_pd3dDevice->SetTransform(D3DTS_WORLD, &g_matWorld);//设置世界矩阵
//第11步:重新编写键鼠控制代码
            // 沿摄像机各分量移动视角
    if (g_pDInput->IsKeyDown(DIK_A))  g_pCamera->MoveAlongRightVec(-0.3f);
    if (g_pDInput->IsKeyDown(DIK_D))  g_pCamera->MoveAlongRightVec( 0.3f);
    if (g_pDInput->IsKeyDown(DIK_W)) g_pCamera->MoveAlongLookVec( 0.3f);
    if (g_pDInput->IsKeyDown(DIK_S))  g_pCamera->MoveAlongLookVec(-0.3f);
    if (g_pDInput->IsKeyDown(DIK_R))  g_pCamera->MoveAlongUpVec( 0.3f);
    if (g_pDInput->IsKeyDown(DIK_F))  g_pCamera->MoveAlongUpVec(-0.3f);

    //沿摄像机各分量旋转视角
    if (g_pDInput->IsKeyDown(DIK_LEFT))  g_pCamera->RotationUpVec(-0.003f);
    if (g_pDInput->IsKeyDown(DIK_RIGHT))  g_pCamera->RotationUpVec( 0.003f);
    if (g_pDInput->IsKeyDown(DIK_UP))  g_pCamera->RotationRightVec(-0.003f);
    if (g_pDInput->IsKeyDown(DIK_DOWN))  g_pCamera->RotationRightVec( 0.003f);
    if (g_pDInput->IsKeyDown(DIK_Q)) g_pCamera->RotationLookVec( 0.001f);
    if (g_pDInput->IsKeyDown(DIK_E)) g_pCamera->RotationLookVec(-0.001f);


    //鼠标控制右向量和上向量的旋转
    g_pCamera->RotationUpVec(g_pDInput->MouseDX()* 0.001f);
    g_pCamera->RotationRightVec(g_pDInput->MouseDY() * 0.001f);

//鼠标滚轮控制观察点收缩操作
    static FLOAT fPosZ=0.0f;
    fPosZ += g_pDInput->MouseDZ()*0.03f;

    //计算并设置取景变换矩阵
    D3DXMATRIX matView;
    g_pCamera->CalculateViewMatrix(&matView);
    g_pd3dDevice->SetTransform(D3DTS_VIEW, &matView);

    //把正确的世界变换矩阵存到g_matWorld中
    D3DXMatrixTranslation(&g_matWorld, 0.0f, 0.0f, fPosZ);

    //以下这段代码用于限制鼠标光标移动区域
    POINT lt,rb;
    RECT rect;
    GetClientRect(hwnd,&rect);  //取得窗口内部矩形
    //将矩形左上点坐标存入lt中
    lt.x = rect.left;
    lt.y = rect.top;
    //将矩形右下坐标存入rb中
    rb.x = rect.right;
    rb.y = rect.bottom;
    //将lt和rb的窗口坐标转换为屏幕坐标
    ClientToScreen(hwnd,&lt);
    ClientToScreen(hwnd,&rb);
    //以屏幕坐标重新设定矩形区域
    rect.left = lt.x;
    rect.top = lt.y;
    rect.right = rb.x;
    rect.bottom = rb.y;
    //限制鼠标光标移动区域
    ClipCursor(&rect);

    ShowCursor(false);        //隐藏鼠标光标
}

//-----------------------------------【Direct3D_Render( )函数】--------------------------------------
void Direct3D_Render(HWND hwnd)
{//1
    //第12步:修改清屏操作
    //g_pd3dDevice->Clear(0, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(100, 100, 100), 1.0f, 0);
    //RECT formatRect;
    //GetClientRect(hwnd, &formatRect);
    g_pd3dDevice->Clear(0, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER|D3DCLEAR_STENCIL, D3DCOLOR_XRGB(50, 100, 250), 1.0f, 0);
    //2
    g_pd3dDevice->BeginScene();   
    //3
    //第13步:绘制人物
    g_pd3dDevice->SetTransform(D3DTS_WORLD, &g_matWorld);//设置模型的世界矩阵,为绘制做准备
    // 用一个for循环,进行模型的网格各个部分的绘制
    for (DWORD i = 0; i < g_dwNumMtrls; i++)
            {
                g_pd3dDevice->SetMaterial(&g_pMaterials[i]);//设置此部分的材质
                g_pd3dDevice->SetTexture(0, g_pTextures[i]);//设置此部分的纹理
                g_pMesh->DrawSubset(i);//绘制此部分
            }
    //第14步:注销屏幕信息
            //int charCount = swprintf_s(g_strFPS, 20, _T("FPS:%0.3f"), Get_FPS() );
            //g_pTextFPS->DrawText(NULL, g_strFPS, charCount , &formatRect, DT_TOP | DT_RIGHT, D3DCOLOR_RGBA(0,239,136,255));
    
      //      g_pTextAdaperName->DrawText(NULL,g_strAdapterName, -1, &formatRect, 
            //    DT_TOP | DT_LEFT, D3DXCOLOR(1.0f, 0.5f, 0.0f, 1.0f));

   //         formatRect.top = 30;
            //static wchar_t strInfo[256] = {0};
            //swprintf_s(strInfo,-1, L"模型坐标: (%.2f, %.2f, %.2f)", g_matWorld._41, g_matWorld._42, g_matWorld._43);
            //g_pTextHelper->DrawText(NULL, strInfo, -1, &formatRect, DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(135,239,136,255));



         //   formatRect.left = 0,formatRect.top = 380;
            //g_pTextInfor->DrawText(NULL, L"控制说明:", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(235,123,230,255));
            //formatRect.top += 35;
            //g_pTextHelper->DrawText(NULL, L"    按住鼠标左键并拖动:平移模型", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
            //formatRect.top += 25;
            //g_pTextHelper->DrawText(NULL, L"    按住鼠标右键并拖动:旋转模型", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
            //formatRect.top += 25;
            //g_pTextHelper->DrawText(NULL, L"    滑动鼠标滚轮:拉伸模型", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
            //formatRect.top += 25;
            //g_pTextHelper->DrawText(NULL, L"    W、S、A、D键:平移模型 ", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
            //formatRect.top += 25;
            //g_pTextHelper->DrawText(NULL, L"    上、下、左、右方向键:旋转模型 ", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
            //formatRect.top += 25;
            //g_pTextHelper->DrawText(NULL, L"    ESC键 : 退出程序", -1, &formatRect, 
            //    DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    //第15步:绘制草坪,柱子,调用屏幕信息函数
        // 绘制草坪
    D3DXMATRIX matWorld;
    D3DXMatrixTranslation(&matWorld, 0.0f, 0.0f, 0.0f);
    g_pd3dDevice->SetTransform(D3DTS_WORLD, &matWorld);
    g_pd3dDevice->SetTexture(0, g_pTexture);
    g_pd3dDevice->SetStreamSource(0, g_pVertexBuffer, 0, sizeof(CUSTOMVERTEX));
    g_pd3dDevice->SetFVF(D3DFVF_CUSTOMVERTEX);
    g_pd3dDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP, 0, 2);
    
    //绘制柱子
    D3DXMATRIX TransMatrix, RotMatrix, FinalMatrix;
    D3DXMatrixRotationX(&RotMatrix, -D3DX_PI * 0.5f);
    g_pd3dDevice->SetMaterial(&g_MaterialCylinder);
    for(int i = 0; i < 6; i++)
    {
        D3DXMatrixTranslation(&TransMatrix, -100.0f, 0.0f, -150.0f + (i * 75.0f));
        FinalMatrix = RotMatrix * TransMatrix ;
        g_pd3dDevice->SetTransform(D3DTS_WORLD, &FinalMatrix);
        g_cylinder->DrawSubset(0);

        D3DXMatrixTranslation(&TransMatrix, 100.0f, 0.0f, -150.0f + (i * 75.0f));
        FinalMatrix = RotMatrix * TransMatrix ;
        g_pd3dDevice->SetTransform(D3DTS_WORLD, &FinalMatrix);
        g_cylinder->DrawSubset(0);
    }

    HelpText_Render(hwnd);
    //4
    g_pd3dDevice->EndScene(); 
    //5
    g_pd3dDevice->Present(NULL, NULL, NULL, NULL); 
}

//第16步:添加帮助信息的函数
//-----------------------------------【HelpText_Render( )函数】-------------------------------
//    描述:封装了帮助信息的函数
//--------------------------------------------------------------------------------------------------
void HelpText_Render(HWND hwnd)
{
    //定义一个矩形,用于获取主窗口矩形
    RECT formatRect;
    GetClientRect(hwnd, &formatRect);

    //在窗口右上角处,显示每秒帧数
    formatRect.top = 5;
    int charCount = swprintf_s(g_strFPS, 20, _T("FPS:%0.3f"), Get_FPS() );
    g_pTextFPS->DrawText(NULL, g_strFPS, charCount , &formatRect, DT_TOP | DT_RIGHT, D3DCOLOR_RGBA(0,239,136,255));

    //显示显卡类型名
    g_pTextAdaperName->DrawText(NULL,g_strAdapterName, -1, &formatRect, 
        DT_TOP | DT_LEFT, D3DXCOLOR(1.0f, 0.5f, 0.0f, 1.0f));

    // 输出帮助信息
    formatRect.left = 0,formatRect.top = 380;
    g_pTextInfor->DrawText(NULL, L"控制说明:", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(235,123,230,255));
    formatRect.top += 35;
    g_pTextHelper->DrawText(NULL, L"    W:向前飞翔     S:向后飞翔 ", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    formatRect.top += 25;
    g_pTextHelper->DrawText(NULL, L"    A:向左飞翔     D:向右飞翔", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    formatRect.top += 25;
    g_pTextHelper->DrawText(NULL, L"    R:垂直向上飞翔     F:垂直向下飞翔", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    formatRect.top += 25;
    g_pTextHelper->DrawText(NULL, L"    Q:向左倾斜       E:向右倾斜", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    formatRect.top += 25;
    g_pTextHelper->DrawText(NULL, L"    上、下、左、右方向键、鼠标移动:视角变化 ", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    formatRect.top += 25;
    g_pTextHelper->DrawText(NULL, L"     鼠标滚轮:人物模型Y轴方向移动", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
    formatRect.top += 25;
    g_pTextHelper->DrawText(NULL, L"    ESC键 : 退出程序", -1, &formatRect, 
        DT_SINGLELINE | DT_NOCLIP | DT_LEFT, D3DCOLOR_RGBA(255,200,0,255));
}


//-----------------------------------【Get_FPS( )函数】------------------------------------------
float    Get_FPS()
{
    static float  fps = 0;//fps值
    static int     frameCount = 0;//帧数
    static float  currentTime =0.0f;//当前时间
    static float  lastTime = 0.0f;//持续时间

    frameCount++;
    currentTime=timeGetTime()*0.001f;//获取系统时间

    if(currentTime-lastTime>1.0f)
    {
        fps = (float)frameCount /(currentTime - lastTime);
        lastTime=currentTime;
        frameCount=0;

    }
    return fps;

}


//-----------------------------------【Direct3D_CleanUp( )函数】--------------------------------
void Direct3D_CleanUp()
{
    //第17步:释放COM接口对象
    for (DWORD i = 0; i<g_dwNumMtrls; i++) 
        SAFE_RELEASE(g_pTextures[i]);
    SAFE_DELETE(g_pTextures); 
    SAFE_DELETE(g_pMaterials); 
    SAFE_DELETE(g_pDInput);
    SAFE_RELEASE(g_cylinder);
    SAFE_RELEASE(g_pMesh);
    SAFE_RELEASE(g_pd3dDevice);

    SAFE_RELEASE(g_pTextAdaperName)
    SAFE_RELEASE(g_pTextHelper)
    SAFE_RELEASE(g_pTextInfor)
    SAFE_RELEASE(g_pTextFPS)
    SAFE_RELEASE(g_pd3dDevice)
}
View Code

 

 

posted @ 2022-05-17 16:02  szmtjs10  阅读(147)  评论(0编辑  收藏  举报