game.cpp
来自「对游戏编程感兴趣的 朋友可以 下载下来看看 对DX讲解的很很详细」· C++ 代码 · 共 796 行 · 第 1/2 页
CPP
796 行
return false;
}
else
{
LogInfo("<li>SetRenderState: D3DRS_ZENABLE OK");
}
//Set fill state. Possible values: D3DFILL_POINT, D3DFILL_WIREFRAME, D3DFILL_SOLID
if(FAILED(m_pD3DDevice->SetRenderState(D3DRS_FILLMODE, D3DFILL_SOLID)))
{
LogError("<li>SetRenderState: D3DRS_FILLMODE Failed");
return false;
}
else
{
LogInfo("<li>SetRenderState: D3DRS_FILLMODE OK");
}
//Set the D3DRS_NORMALIZENORMALS render state to fix the problem when scaling the objects get darker
if(FAILED(m_pD3DDevice->SetRenderState(D3DRS_NORMALIZENORMALS, TRUE)))
{
LogError("<li>SetRenderState: D3DRS_NORMALIZENORMALS Failed");
return false;
}
else
{
LogInfo("<li>SetRenderState: D3DRS_NORMALIZENORMALS OK");
}
//Enable alpha blending so we can use transparent textures
if(FAILED(m_pD3DDevice->SetRenderState(D3DRS_ALPHABLENDENABLE, TRUE)))
{
LogError("<li>SetRenderState: D3DRS_ALPHABLENDENABLE Failed");
return false;
}
else
{
//Set how the texture should be blended (use alpha)
m_pD3DDevice->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
m_pD3DDevice->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
LogInfo("<li>SetRenderState: D3DRS_ALPHABLENDENABLE OK");
}
return true;
}
bool CGame::InitialiseLights()
{
LogInfo("<br>Initialise Lights:");
D3DLIGHT8 d3dLight;
//Initialize the light structure.
ZeroMemory(&d3dLight, sizeof(D3DLIGHT8));
d3dLight.Type = D3DLIGHT_POINT;
d3dLight.Position.x = -30.0f;
d3dLight.Position.y = 0.0f;
d3dLight.Position.z = -15.0f;
d3dLight.Attenuation0 = 1.0f;
d3dLight.Attenuation1 = 0.0f;
d3dLight.Attenuation2 = 0.0f;
d3dLight.Range = 1000.0f;
d3dLight.Diffuse.r = 1.0f;
d3dLight.Diffuse.g = 1.0f;
d3dLight.Diffuse.b = 1.0f;
d3dLight.Ambient.r = 0.0f;
d3dLight.Ambient.g = 0.0f;
d3dLight.Ambient.b = 0.0f;
d3dLight.Specular.r = 0.0f;
d3dLight.Specular.g = 0.0f;
d3dLight.Specular.b = 0.0f;
//Assign the point light to our device in poisition (index) 0
if(FAILED(m_pD3DDevice->SetLight(0, &d3dLight)))
{
LogError("<li>SetLight Failed");
return false;
}
else
{
LogInfo("<li>SetLight OK");
}
//Enable our point light in position (index) 0
if(FAILED(m_pD3DDevice->LightEnable(0, TRUE)))
{
LogError("<li>LightEnable Failed");
return false;
}
else
{
LogInfo("<li>LightEnable OK");
}
//Turn on lighting
if(FAILED(m_pD3DDevice->SetRenderState(D3DRS_LIGHTING, TRUE)))
{
LogError("<li>SetRenderState: D3DRS_LIGHTING Failed");
return false;
}
else
{
LogInfo("<li>SetRenderState: D3DRS_LIGHTING OK");
}
//Set ambient light level
if(FAILED(m_pD3DDevice->SetRenderState(D3DRS_AMBIENT, D3DCOLOR_XRGB(100, 100, 100))))
{
LogError("<li>SetRenderState: D3DRS_AMBIENT Failed");
return false;
}
else
{
LogInfo("<li>SetRenderState: D3DRS_AMBIENT OK");
}
return true;
}
LPDIRECT3DDEVICE8 CGame::GetDevice()
{
return m_pD3DDevice;
}
void CGame::GameLoop()
{
//Enter the game loop
MSG msg;
BOOL fMessage;
PeekMessage(&msg, NULL, 0U, 0U, PM_NOREMOVE);
//Game started, so record time
m_dwStartTime = timeGetTime();
while((msg.message != WM_QUIT) && (!m_fQuit))
{
fMessage = PeekMessage(&msg, NULL, 0U, 0U, PM_REMOVE);
if(fMessage)
{
//Process message
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else
{
//No message to process, so render the current scene
Render();
}
}
//Game finished, so record time
m_dwEndTime = timeGetTime();
}
void CGame::Render()
{
if(m_pD3DDevice == NULL)
{
return;
}
//Process keyboard and mouse user input
ProcessKeyboard();
ProcessMouse();
if(!m_fQuit)
{
//Clear the back buffer and depth buffer
m_pD3DDevice->Clear(0, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0, 0, 0), 1.0f, 0);
//Begin the scene
m_pD3DDevice->BeginScene();
//Setup the camera ready for 3D elements
Setup3DCamera();
//Now that the 3D camera is setup, render the 3D objects
Render3D();
//Now render the text
RenderText();
//End the scene
m_pD3DDevice->EndScene();
//Filp the back and front buffers so that whatever has been rendered on the back buffer
//will now be visible on screen (front buffer).
m_pD3DDevice->Present(NULL, NULL, NULL, NULL);
//Count Frames
m_dwFrames++;
}
}
void CGame::Setup2DCamera()
{
D3DXMATRIX matOrtho;
D3DXMATRIX matIdentity;
//Setup the orthogonal projection matrix and the default world/view matrix
D3DXMatrixOrthoLH(&matOrtho, (float)m_nScreenWidth, (float)m_nScreenHeight, 0.0f, 1.0f);
D3DXMatrixIdentity(&matIdentity);
m_pD3DDevice->SetTransform(D3DTS_PROJECTION, &matOrtho);
m_pD3DDevice->SetTransform(D3DTS_WORLD, &matIdentity);
m_pD3DDevice->SetTransform(D3DTS_VIEW, &matIdentity);
//Make sure that the z-buffer and lighting are disabled
m_pD3DDevice->SetRenderState(D3DRS_ZENABLE, D3DZB_FALSE);
m_pD3DDevice->SetRenderState(D3DRS_LIGHTING, FALSE);
}
void CGame::Setup3DCamera()
{
//Here we will setup the camera.
//The camera has three settings: "Camera Position", "Look at Position" and "Up Direction"
//We have set the following:
//Camera Position: (0, 15, -50)
//Look at Position: (0, 0, 0)
//Up direction: Y-Axis.
D3DXMATRIX matView;
D3DXMatrixLookAtLH(&matView, &D3DXVECTOR3(0.0f, 15.0f, -50.0f), //Camera Position
&D3DXVECTOR3(0.0f, 0.0f, 0.0f), //Look At Position
&D3DXVECTOR3(0.0f, 1.0f, 0.0f)); //Up Direction
m_pD3DDevice->SetTransform(D3DTS_VIEW, &matView);
//Here we specify the field of view, aspect ration and near and far clipping planes.
D3DXMATRIX matProj;
D3DXMatrixPerspectiveFovLH(&matProj, D3DX_PI/4, 1.25f, 1.0f, 2000.0f);
m_pD3DDevice->SetTransform(D3DTS_PROJECTION, &matProj);
//Make sure that the z-buffer and lighting are enabled
m_pD3DDevice->SetRenderState(D3DRS_ZENABLE, D3DZB_TRUE);
m_pD3DDevice->SetRenderState(D3DRS_LIGHTING, TRUE);
}
void CGame::Render2D()
{
//Render our 2D objects
}
void CGame::Render3D()
{
//Render our 3D objects
D3DXMATRIX matEarth, matScale, matRotate, matEarthRoll, matEarthMove;
float rMouseSpeed = 20.0f;
//If left mouse button is down, stop the earth from rotating
if(m_nMouseLeft == 1)
{
m_rRotate = 0.0f;
}
//If right mouse button is down, start the earth rotating at default speed
if(m_nMouseRight == 1)
{
m_rRotate = 2.0f;
}
m_rAngle += m_rRotate;
//Create the transformation matrices
D3DXMatrixRotationY(&matRotate, D3DXToRadian(m_rAngle));
D3DXMatrixScaling(&matScale, m_rScale, m_rScale, m_rScale);
D3DXMatrixRotationYawPitchRoll(&matEarthRoll, 0.0f, 0.0f, D3DXToRadian(23.44f));
D3DXMatrixTranslation(&matEarthMove, (m_nMouseX / rMouseSpeed), -(m_nMouseY / rMouseSpeed), 0.0f);
D3DXMatrixMultiply(&matEarth, &matScale, &matRotate);
D3DXMatrixMultiply(&matEarth, &matEarth, &matEarthRoll);
D3DXMatrixMultiply(&matEarth, &matEarth, &matEarthMove);
//Render our objects
m_pD3DDevice->SetTransform(D3DTS_WORLD, &matEarth);
m_dwTotalPolygons += m_pSphere->Render();
}
void CGame::RenderText()
{
//Draw some text at the top of the screen showing stats
char buffer[255];
DWORD dwDuration = (timeGetTime() - m_dwStartTime) / 1000;
if(dwDuration > 0)
{
sprintf(buffer, "Duration: %d seconds. Frames: %d. FPS: %d. Rotation Rate: %f. Angle: %f. Scale: %f. Left: %d. Right: %d. X = %d. Y = %d.", dwDuration, m_dwFrames, (m_dwFrames / dwDuration), m_rRotate, m_rAngle, m_rScale, m_nMouseLeft, m_nMouseRight, m_nMouseX, m_nMouseY);
}
else
{
sprintf(buffer, "Calculating...");
}
m_pFont->DrawText(buffer, 0, 0, D3DCOLOR_XRGB(255, 255, 255));
}
void CGame::ProcessKeyboard()
{
char KeyboardState[256];
if(FAILED(m_pKeyboard->GetDeviceState(sizeof(KeyboardState),(LPVOID)&KeyboardState)))
{
return;
}
if(KEYDOWN(KeyboardState, DIK_ESCAPE))
{
//Escape key pressed. Quit game.
m_fQuit = true;
}
//Rotate Earth
if(KEYDOWN(KeyboardState, DIK_RIGHT))
{
m_rRotate -= 0.5f;
}
else if(KEYDOWN(KeyboardState, DIK_LEFT))
{
m_rRotate += 0.5f;
}
//Set an upper and lower limit for the rotation factor
if(m_rRotate < -20.0f)
{
m_rRotate = -20.0f;
}
else if(m_rRotate > 20.0f)
{
m_rRotate = 20.0f;
}
//Scale Earth
if(KEYDOWN(KeyboardState, DIK_UP))
{
m_rScale += 0.5f;
}
else if (KEYDOWN(KeyboardState, DIK_DOWN))
{
m_rScale -= 0.5f;
}
//Set an upper and lower limit for the scale factor
if(m_rScale < 1.0f)
{
m_rScale = 1.0f;
}
else if(m_rScale > 20.0f)
{
m_rScale = 20.0f;
}
}
void CGame::ProcessMouse()
{
DIMOUSESTATE MouseState;
if(FAILED(m_pMouse->GetDeviceState(sizeof(MouseState),(LPVOID)&MouseState)))
{
return;
}
//Is the left mouse button down?
if(MOUSEBUTTONDOWN(MouseState.rgbButtons[MOUSEBUTTON_LEFT]))
{
m_nMouseLeft = 1;
}
else
{
m_nMouseLeft = 0;
}
//Is the right mouse button down?
if(MOUSEBUTTONDOWN(MouseState.rgbButtons[MOUSEBUTTON_RIGHT]))
{
m_nMouseRight = 1;
}
else
{
m_nMouseRight = 0;
}
m_nMouseX += MouseState.lX;
m_nMouseY += MouseState.lY;
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?