//DirectX3D.CPP
/********************************************************
Description: Game DirectX3D
Date: 1/7/2007
Auther: Shalom Keller
Contact: szkeller@gmail.com
Note: If you find any bugs or you think that some thing
is wrong, Please send me an e-mail on it.
********************************************************/
#include "DirectX3D.h"
#include "externals.h"
#include "MyFile.h"
#include "Dxerr8.h"
#include "MyMath.h"
////////////////////////////////////////////////////
//
////////////////////////////////////////////////////
#define PI 3.141592653589f
#define RAD2DEG(a) ((a) * (180.0f / PI))
#define DEG2RAD(a) ((a) * (PI / 180.0f))
//////////////////////////////////////////////////////////
//
//////////////////////////////////////////////////////////
BOOL DisplayErrorMessage(char *szMessage);
CArray<TextureInfo,TextureInfo&> g_Texturs;
//////////////////////////////////////////////////////////
//
//////////////////////////////////////////////////////////
bool CDirectX3D::InitDirectX3D(HWND hWnd)
{
HRESULT ret;
//-------------------------------------------------
m_pD3D = Direct3DCreate8( D3D_SDK_VERSION ) ;
if(m_pD3D==NULL)
{
MessageBox(hWnd,"Direct3DCreate8 Error creating a 3DDirectX8Interface","ERROR",MB_OK|MB_ICONERROR);
return false;
}
//-------------------------------------------------
D3DDISPLAYMODE d3ddm;
ret = m_pD3D->GetAdapterDisplayMode(
D3DADAPTER_DEFAULT ,
&d3ddm);
//---------------------------------
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"GetAdapterDisplayMode",
"ERROR",
MB_OK|MB_ICONERROR);
Clean_Up();
DestroyWindow(hWnd);
return false;
}
ZeroMemory( &m_d3dpp, sizeof(D3DPRESENT_PARAMETERS));
m_d3dpp.Windowed = TRUE;
//---------------------------------
//For Full-Scene Antialiasing.
// m_d3dpp.MultiSampleType = D3DMULTISAMPLE_2_SAMPLES;
m_d3dpp.BackBufferCount = 1;
m_d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD ;
m_d3dpp.BackBufferFormat = d3ddm.Format;
m_d3dpp.EnableAutoDepthStencil = TRUE;
m_d3dpp.AutoDepthStencilFormat = D3DFMT_D24X8;
//---------------------------------
ret = m_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL,//D3DDEVTYPE_HAL
hWnd,
D3DCREATE_HARDWARE_VERTEXPROCESSING,//D3DCREATE_HARDWARE_VERTEXPROCESSING D3DCREATE_SOFTWARE_VERTEXPROCESSING
&m_d3dpp,
&m_pD3dDevice);
if(ret!=D3D_OK)
{
m_d3dpp.AutoDepthStencilFormat = D3DFMT_D16;
MessageBox(hWnd,"Your Graphics card dosn't support 24 bit depth format.",
"ERROR",MB_OK|MB_ICONERROR);
ret = m_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL,//D3DDEVTYPE_HAL
hWnd,
D3DCREATE_HARDWARE_VERTEXPROCESSING,//D3DCREATE_HARDWARE_VERTEXPROCESSING D3DCREATE_SOFTWARE_VERTEXPROCESSING
&m_d3dpp,
&m_pD3dDevice);
}
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"NO Hardware Support was found \n so turning to software Emulation\n Warnning Software Emulation is Real Slow.",
"ERROR",MB_OK|MB_ICONERROR);
ret = m_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_REF,
hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&m_d3dpp,
&m_pD3dDevice);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"CreateDevice even not Software Emulation",
"ERROR",MB_OK|MB_ICONERROR);
Clean_Up();
DestroyWindow(hWnd);
return false;
}
}
//-------------------------------------------------
ret = m_pD3dDevice->GetDeviceCaps(&m_D3DCAPS8);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"GetDeviceCaps()",
"ERROR",MB_OK|MB_ICONERROR);
Clean_Up();
DestroyWindow(hWnd);
return false;
}
//---------------------------------
// Initialize the Texture list size.
g_Texturs.SetSize(0,2);
//---------------------------------
if(!InitRenderState())
return FALSE;
return true;
}
//////////////////////////////////////////////////////////
//
//////////////////////////////////////////////////////////
bool CDirectX3D::InitDirectX3D_ForFullScreen(HWND hWnd,DWORD dwWidth,DWORD dwHeight,DWORD dwBitsPerPixel)
{
HRESULT ret;
//-------------------------------------------------
m_pD3D = Direct3DCreate8( D3D_SDK_VERSION ) ;
if(m_pD3D==NULL)
{
MessageBox(hWnd,"Direct3DCreate8 Error creating a 3DDirectX8Interface","ERROR",MB_OK|MB_ICONERROR);
return false;
}
//-------------------------------------------------
D3DDISPLAYMODE d3ddm;
ret = m_pD3D->GetAdapterDisplayMode(
D3DADAPTER_DEFAULT ,
&d3ddm);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"GetAdapterDisplayMode",
"ERROR",
MB_OK|MB_ICONERROR);
Clean_Up();
DestroyWindow(hWnd);
return false;
}
ZeroMemory( &m_d3dpp, sizeof(D3DPRESENT_PARAMETERS));
//---------------------------------
//
//For Full Screen.
//
m_d3dpp.Windowed = FALSE;
m_d3dpp.BackBufferWidth = dwWidth;
m_d3dpp.BackBufferHeight = dwHeight;
m_d3dpp.BackBufferCount = 1;
//For Full-Scene Antialiasing.
// m_d3dpp.MultiSampleType = D3DMULTISAMPLE_2_SAMPLES;
m_d3dpp.BackBufferCount =1;
m_d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD ;
m_d3dpp.BackBufferFormat = d3ddm.Format;
m_d3dpp.EnableAutoDepthStencil = TRUE;
m_d3dpp.AutoDepthStencilFormat = D3DFMT_D24X8;
//---------------------------------
ret = m_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL,//D3DDEVTYPE_HAL
hWnd,
D3DCREATE_HARDWARE_VERTEXPROCESSING,//D3DCREATE_HARDWARE_VERTEXPROCESSING D3DCREATE_SOFTWARE_VERTEXPROCESSING
&m_d3dpp,
&m_pD3dDevice);
if(ret!=D3D_OK)
{
m_d3dpp.AutoDepthStencilFormat = D3DFMT_D16;
ret = m_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL,//D3DDEVTYPE_HAL
hWnd,
D3DCREATE_HARDWARE_VERTEXPROCESSING,//D3DCREATE_HARDWARE_VERTEXPROCESSING D3DCREATE_SOFTWARE_VERTEXPROCESSING
&m_d3dpp,
&m_pD3dDevice);
}
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"NO Hardware Support was found \n so turning to software Emulation\n Warnning Software Emulation is Real Slow.",
"ERROR",MB_OK|MB_ICONERROR);
ret = m_pD3D->CreateDevice(D3DADAPTER_DEFAULT,
D3DDEVTYPE_REF,
hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&m_d3dpp,
&m_pD3dDevice);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"CreateDevice even not Software Emulation",
"ERROR",MB_OK|MB_ICONERROR);
Clean_Up();
DestroyWindow(hWnd);
return false;
}
}
//-------------------------------------------------
ret = m_pD3dDevice->GetDeviceCaps(&m_D3DCAPS8);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
MessageBox(hWnd,"GetDeviceCaps()",
"ERROR",MB_OK|MB_ICONERROR);
Clean_Up();
DestroyWindow(hWnd);
return false;
}
//---------------------------------
g_Texturs.SetSize(0,2);
//---------------------------------
if(!InitRenderState())
return FALSE;
return true;
}
///////////////////////////////////
//
///////////////////////////////////
BOOL DisplayDirectXErrorCode(HRESULT ret)
{
sprintf(g_Buffer,"ErrorCode: 0x%08x ()",ret,DXGetErrorString8(ret));
::MessageBox(0,
g_Buffer,
"DirectX ERROR",
MB_OK|MB_ICONERROR);
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::Clean_Up()
{
if(m_pD3dDevice)
m_pD3dDevice->Release();
m_pD3dDevice=NULL;
if(m_pD3D)
m_pD3D->Release();
m_pD3D=NULL;
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::InitRenderState()
{
HRESULT hr;
//------------------------------------------------
//Enable Z Buffer.
hr = m_pD3dDevice->
SetRenderState(D3DRS_ZENABLE,m_bEnableZBuffer);
if(hr!=D3D_OK)
{
DisplayDirectXErrorCode(hr);
DisplayErrorMessage(
"InitRenderState::EnableZBuffer()\nError. ");
}
//------------------------------------------------
//Turns on the Ambient light.
hr = m_pD3dDevice->
SetRenderState(
D3DRS_AMBIENT,m_dwGlobalAmbient);
if(hr!=D3D_OK)
{
DisplayDirectXErrorCode(hr);
DisplayErrorMessage(
"InitRenderState::SetAmbient() \nError ");
}
//------------------------------------------------
//Enable Direct3D lighting.
hr = m_pD3dDevice->
SetRenderState(D3DRS_LIGHTING,m_bEnableDirect3DLighting);
if(hr!=D3D_OK)
{
DisplayDirectXErrorCode(hr);
DisplayErrorMessage(
"RenderState::EnableDirect3Dlighting() \nError ");
}
//------------------------------------------------
/* //Enable antialiasing
hr = m_pD3dDevice->
SetRenderState(D3DRS_EDGEANTIALIAS ,TRUE);
if(hr!=D3D_OK)
{
DisplayDirectXErrorCode(hr);
DisplayErrorMessage(
"RenderState::Enable antialiasing () \nError ");
}*/
//------------------------------------------------
//Show back facing.
if(m_bEnableBackFacing)
{
hr = m_pD3dDevice->
SetRenderState(
D3DRS_CULLMODE ,
D3DCULL_CCW );
}
//Don't show back facing.
else
{
hr = m_pD3dDevice->
SetRenderState(
D3DRS_CULLMODE,
D3DCULL_NONE);
}
//------------------------------------------------
//
this->DisplayLights();
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::Clear_Display(bool bTarget,bool bZBuffer,bool bStencil,int R,int G,int B)
{
DWORD Flags=0;
//---------------------------------
if(bTarget)
{
Flags = D3DCLEAR_TARGET;
}
if(bZBuffer)
{
Flags |= D3DCLEAR_ZBUFFER;
}
if(bStencil)
{
Flags |= D3DCLEAR_STENCIL;
}
//---------------------------------
HRESULT ret = m_pD3dDevice->Clear(0,
0,
D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER,
D3DCOLOR_XRGB(R,G,B),
1.0f,//Z.
0 );//Stencil.
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CDirectX3D::Clean_Display()");
return false;
}
//---------------------------------
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::Flip()
{
//---------------------------------
HRESULT ret = m_pD3dDevice->Present(
NULL,
NULL,
NULL,
NULL );
if(ret!= D3D_OK)
{
if( (ret == D3DERR_DEVICELOST) && (g_GlobalData.bInitWasDone) )
{
m_pD3dDevice->Reset(&m_d3dpp);
}
else
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CDirectX3D::Flip()");
return false;
}
}
//---------------------------------
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::InitVertexBuffer(IN MyMesh *pMesh,OUT VertexBuffer *pVertexBuffer)
{
HRESULT ret;
MyD3DVERTEX *lpVertex=NULL;
//---------------------------------
pVertexBuffer->nVertex = pMesh->nVertex;
if(!pVertexBuffer->nVertex)
return true;
//---------------------------------
memcpy(&pVertexBuffer->material,&pMesh->Material,sizeof(D3DMATERIAL8));
// pVertexBuffer->material.Ambient.r=1.0f;
// pVertexBuffer->material.Ambient.g=1.0f;
// pVertexBuffer->material.Ambient.b=1.0f;
pVertexBuffer->pMesh=pMesh;
//---------------------------------
if(!InitTexture(pMesh,pVertexBuffer))
return false;
//---------------------------------
ret = m_pD3dDevice->CreateVertexBuffer(
(sizeof(MyD3DVERTEX)*(pVertexBuffer->nVertex)),
0,
D3DFVF_MyD3DVERTEX,
D3DPOOL_DEFAULT,
&pVertexBuffer->lpVertexBuffer);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::Init \n\
\r ERROR creating a Vertex Buffer.");
pVertexBuffer->lpVertexBuffer = NULL;
}
//---------------------------------
ret = pVertexBuffer->lpVertexBuffer->Lock(
0,
0,
(BYTE**)&lpVertex,
0);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::FillVertexBuffer\n \
\rcouldn't get a pointer to the vertex buffer.");
return false;
}
//---------------------------------
for(DWORD loop=0;loop<pMesh->nVertex;loop++)
{
lpVertex[loop] = pMesh->pVertex[loop];
}
//---------------------------------
ret = pVertexBuffer->lpVertexBuffer->Unlock();
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::FillVertexBuffer\n\
Error Ulocking Buffer.");
return false;
}
//---------------------------------
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::InitTexture(IN MyMesh *pMesh,OUT VertexBuffer *pVertexBuffer)
{
CMyFile f;
HRESULT ret;
TextureInfo l_TextureInfo;
//---------------------------------
if(!pMesh->nTextureFileName)
{
pVertexBuffer->lpTexture = NULL;
return true;
}
//---------------------------------
for(DWORD loop=0;loop<(DWORD)g_Texturs.GetSize();loop++)
{
l_TextureInfo = g_Texturs.GetAt(loop);
if(strcmp(l_TextureInfo.strTextureName.GetBuffer(strlen(l_TextureInfo.strTextureName)+1),pMesh->szTextureFileName)==0)
{
pVertexBuffer->lpTexture = l_TextureInfo.lpTexture;
return true;
}
}
//---------------------------------
if(!f.Open(pMesh->szTextureFileName,FALSE,FALSE))
{
sprintf(g_Buffer,"Error Opening <%s>",pMesh->szTextureFileName);
ShowWinError(g_Buffer);
}
else
{
f.Close();
}
//---------------------------------
ret = D3DXCreateTextureFromFile(
m_pD3dDevice,
pMesh->szTextureFileName,
&pVertexBuffer->lpTexture);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"CTexture::CreateTexture Error Creating Texture.");
return false;
}
//---------------------------------
l_TextureInfo.strTextureName = pMesh->szTextureFileName;
l_TextureInfo.lpTexture = pVertexBuffer->lpTexture;
//---------------------------------
g_Texturs.Add(l_TextureInfo);
//---------------------------------
return true;
}
///////////////////////////////////
//
///////////////////////////////////
D3DXMATRIX TextureMatScale;
D3DXMATRIX TextureMatTranslate;
bool CDirectX3D::RenderVertexBuffer(IN VertexBuffer *pVertexBuffer)
{
HRESULT ret;
if(!pVertexBuffer->nVertex)
return true;
if(g_GlobalData.bShowBoundingBoxs)
{
if(pVertexBuffer->pMesh->bHasBoundingBox)
{
RenderBoundingBox(&pVertexBuffer->pMesh->BoundingBox);
}
if(!g_GlobalData.bShowWireFrame)
{
m_pD3dDevice->SetRenderState(D3DRS_FILLMODE,D3DFILL_SOLID);
}
}
ret = m_pD3dDevice->SetMaterial(&pVertexBuffer->material);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetMaterial()");
return false;
}
if(pVertexBuffer->lpTexture)
{
ret = m_pD3dDevice->SetTexture(0,pVertexBuffer->lpTexture);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetTexture()");
return false;
}
//Scale Texture.
D3DXMatrixScaling(&TextureMatScale,
pVertexBuffer->pMesh->UTilingData,
pVertexBuffer->pMesh->VTilingData,
1.0f);
//Translate Texture.
D3DXMatrixTranslation(&TextureMatTranslate,
pVertexBuffer->pMesh->UOffsetData,
pVertexBuffer->pMesh->VOffsetData,
0.0f);
D3DXMatrixMultiply(&TextureMatTranslate,
&TextureMatTranslate,
&TextureMatScale
);
ret = m_pD3dDevice->SetTransform( D3DTS_TEXTURE0 , &TextureMatTranslate);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetTransform(D3DTS_TEXTURE0)");
return false;
}
ret = m_pD3dDevice->SetTextureStageState( 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2 );
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetTextureStageState(D3DTSS_TEXTURETRANSFORMFLAGS)");
return false;
}
}
else
{
ret = m_pD3dDevice->SetTexture(
0,
NULL);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetTexture()");
return false;
}
}
ret = m_pD3dDevice->BeginScene();
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::BeginScene()");
return false;
}
//-----
ret = m_pD3dDevice->SetStreamSource(0,
pVertexBuffer->lpVertexBuffer,
sizeof(MyD3DVERTEX));
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetStreamSource()");
return false;
}
//-----
ret = m_pD3dDevice->SetVertexShader(
D3DFVF_MyD3DVERTEX);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetVertexShader()");
return false;
}
//-----
ret = m_pD3dDevice->DrawPrimitive(
D3DPT_TRIANGLELIST,
0,
pVertexBuffer->nVertex/3);
if(ret!= D3D_OK)
{
pVertexBuffer->nVertex;
ASSERT(0);
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::DrawPrimitive()");
return false;
}
//-----
ret = m_pD3dDevice->EndScene();
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::EndScene()");
return false;
}
//-----
return true;
}
///////////////////////////////////
//
///////////////////////////////////
bool CDirectX3D::ReleaseVertexBuffer(IN VertexBuffer *pVertexBuffer)
{
if(!pVertexBuffer->nVertex)
return true;
if(pVertexBuffer->lpVertexBuffer)
{
pVertexBuffer->lpVertexBuffer->Release();
pVertexBuffer->lpVertexBuffer=0;
}
if(pVertexBuffer->lpTexture)
{
pVertexBuffer->lpTexture->Release();
pVertexBuffer->lpTexture=0;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::SetWorldTransform(D3DXMATRIX *matrix)
{
HRESULT ret;
ret = m_pD3dDevice->SetTransform(D3DTS_WORLD,matrix);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("C3DDevice::SetWorldTransform.");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::SetViewTransform(D3DXMATRIX *matrix)
{
HRESULT ret;
ret = m_pD3dDevice->SetTransform(D3DTS_VIEW,matrix);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("C3DDevice::SetViewTransform.");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::SetProjectionTransform(D3DXMATRIX *matrix)
{
HRESULT ret;
ret = m_pD3dDevice->SetTransform(D3DTS_PROJECTION,matrix);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("C3DDevice::SetProjectionTransform.");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::DisplayLights()
{
HRESULT ret;
D3DLIGHT8 light;
//------------------------------------------
ZeroMemory(&light,sizeof(D3DLIGHT8));
light.Type=D3DLIGHT_DIRECTIONAL;
//D3DLIGHT_SPOT ;
//D3DLIGHT_POINT ;
//D3DLIGHT_DIRECTIONAL;
// light.Position=D3DXVECTOR3(0,0,-10);
light.Falloff=1.0;
light.Diffuse.r = 1.0f;
light.Diffuse.g = 1.0f;
light.Diffuse.b = 1.0f;
light.Specular.r = 1.0f;
light.Specular.g = 1.0f;
light.Specular.b = 1.0f;
light.Ambient.r = 1.0f;
light.Ambient.g = 1.0f;
light.Ambient.b = 1.0f;
light.Direction = D3DXVECTOR3(0.0f,
-1.0f,
0.0f) ;//1
light.Range=(float)sqrt(FLT_MAX);
ret=m_pD3dDevice->SetLight(0,&light );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights SetLight");
return false;
}
ret=m_pD3dDevice->LightEnable( 0, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights LightEnable");
return false;
}
//------------------------------------------
/* light.Direction = D3DXVECTOR3(0.0f,
1.0f,
0.0f) ;//1
ret=m_pD3dDevice->SetLight(1,&light );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights SetLight");
return false;
}
// ret=m_pD3dDevice->LightEnable( 1, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights LightEnable");
return false;
}*/
//------------------------------------------
light.Direction = D3DXVECTOR3(-1.0f,
0.0f,
0.0f) ;//1
ret=m_pD3dDevice->SetLight(2,&light );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights SetLight");
return false;
}
ret=m_pD3dDevice->LightEnable( 2, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights LightEnable");
return false;
}
//------------------------------------------
light.Direction = D3DXVECTOR3(1.0f,
0.0f,
0.0f) ;//1
ret=m_pD3dDevice->SetLight(3,&light );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights SetLight");
return false;
}
ret=m_pD3dDevice->LightEnable( 3, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights LightEnable");
return false;
}
//------------------------------------------
light.Direction = D3DXVECTOR3(0.0f,
0.0f,
1.0f) ;//1
ret=m_pD3dDevice->SetLight(4,&light );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights SetLight");
return false;
}
ret=m_pD3dDevice->LightEnable( 4, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights LightEnable");
return false;
}
//------------------------------------------
light.Direction = D3DXVECTOR3(0.0f,
0.0f,
-1.0f) ;//1
ret=m_pD3dDevice->SetLight(5,&light );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights SetLight");
return false;
}
ret=m_pD3dDevice->LightEnable( 5, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("DisplayLights LightEnable");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::RotateMesh(IN VertexBuffer *pVertexBuffer,float ax,float ay,float az)
{
DWORD loop;
HRESULT ret;
MyD3DVERTEX *lpVertex=NULL;
if(!pVertexBuffer->lpVertexBuffer)
{
// DisplayErrorMessage("CVertexBuffer::RotateMesh Invalid Vertex Buffer Interface");
return false;
}
ret = pVertexBuffer->lpVertexBuffer->Lock(
0,
0,
(BYTE**)&lpVertex,
0);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::RotateMesh\n \
\rcouldn't get a pointer to the vertex buffer.");
return false;
}
MyMath math;
for(loop=0;loop<pVertexBuffer->nVertex;loop++)
{
if(ax)
{
math.RotateX(lpVertex[loop],ax);
}
if(ay)
{
math.RotateY(lpVertex[loop],ay);
}
if(az)
{
math.RotateZ(lpVertex[loop],az);
}
}
if(pVertexBuffer->pMesh->bHasBoundingBox)
{
MyMath math;
for(loop=0;loop<8;loop++)
{
if(ax)
{
math.RotateX(pVertexBuffer->pMesh->BoundingBox.Box[loop],ax);
}
if(ay)
{
math.RotateX(pVertexBuffer->pMesh->BoundingBox.Box[loop],ay);
}
if(az)
{
math.RotateX(pVertexBuffer->pMesh->BoundingBox.Box[loop],az);
}
}
}
ret = pVertexBuffer->lpVertexBuffer->Unlock();
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::RotateMesh\n\
Error Ulocking Buffer.");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::InitObject(Object *pObject)
{
pObject->pVertexBuffers = new VertexBuffer[pObject->nMeshs];
if(!pObject->pVertexBuffers)
{
ShowWinError("CDirectX3D::InitObject() -> Out Of Memory!");
return false;
}
for(DWORD loop=0;loop<pObject->nMeshs;loop++)
{
if(!InitVertexBuffer(&pObject->pMeshs[loop],
&pObject->pVertexBuffers[loop]))
return false;
}
CalculateObjectBoundingBox(pObject);
CalculateMaxMinBox(&pObject->BoundingBox,&pObject->MaxMinBox);
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::RenderObject(Object *pObject)
{
for(DWORD loop=0;loop<pObject->nMeshs;loop++)
{
if(!RenderVertexBuffer(&pObject->pVertexBuffers[loop]))
return false;
}
if(g_GlobalData.bShowObjectBoundingBoxs)
{
RenderBoundingBox(&pObject->BoundingBox);
}
if(!g_GlobalData.bShowWireFrame)
{
m_pD3dDevice->SetRenderState(D3DRS_FILLMODE,D3DFILL_SOLID);
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
/*bool CDirectX3D::ReleaseObject(ObjectManager *pObjectManager)
{
return true;
}*/
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::RotateObject(Object *pObject,float ax,float ay,float az)
{
DWORD loop;
for(loop=0;loop<pObject->nMeshs;loop++)
{
if(!RotateMesh(&pObject->pVertexBuffers[loop],ax,ay,az))
return false;
}
MyMath math;
for(loop=0;loop<8;loop++)
{
if(ax)
{
math.RotateX(pObject->BoundingBox.Box[loop],ax);
}
if(ay)
{
math.RotateX(pObject->BoundingBox.Box[loop],ay);
}
if(az)
{
math.RotateX(pObject->BoundingBox.Box[loop],az);
}
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::MoveObject(Object *pObject,float x,float y,float z)
{
DWORD loop;
for(loop=0;loop<pObject->nMeshs;loop++)
{
if(!MoveMesh(&pObject->pVertexBuffers[loop],x,y,z))
return false;
}
for(loop=0;loop<8;loop++)
{
if(x)
{
pObject->BoundingBox.Box[loop].x += x;
}
if(y)
{
pObject->BoundingBox.Box[loop].y += y;
}
if(z)
{
pObject->BoundingBox.Box[loop].z += z;
}
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::MoveMesh(IN VertexBuffer *pVertexBuffer,float x,float y,float z)
{
DWORD loop;
HRESULT ret;
MyD3DVERTEX *lpVertex=NULL;
if(pVertexBuffer->nVertex==0)
return true;
if(!pVertexBuffer->lpVertexBuffer)
{
DisplayErrorMessage("CVertexBuffer::RotateMesh Invalid Vertex Buffer Interface");
return false;
}
//---------------------------------
ret = pVertexBuffer->lpVertexBuffer->Lock(
0,
0,
(BYTE**)&lpVertex,
0);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::RotateMesh\n \
\rcouldn't get a pointer to the vertex buffer.");
return false;
}
//---------------------------------
for(loop=0;loop<pVertexBuffer->nVertex;loop++)
{
if(x)
{
lpVertex[loop].position.x+=x;
}
if(y)
{
lpVertex[loop].position.y+=y;
}
if(z)
{
lpVertex[loop].position.z+=z;
}
}
//---------------------------------
if(pVertexBuffer->pMesh->bHasBoundingBox)
{
for(loop=0;loop<8;loop++)
{
if(x)
{
pVertexBuffer->pMesh->BoundingBox.Box[loop].x += x;
}
if(y)
{
pVertexBuffer->pMesh->BoundingBox.Box[loop].y += y;
}
if(z)
{
pVertexBuffer->pMesh->BoundingBox.Box[loop].z += z;
}
}
}
//---------------------------------
ret = pVertexBuffer->lpVertexBuffer->Unlock();
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::RotateMesh\n\
Error Ulocking Buffer.");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::LockVertexBuffer(IN VertexBuffer *pVertexBuffer,
OUT MyD3DVERTEX **ppMyD3DVERTEX)
{
//---------------------------------
HRESULT ret;
ret = pVertexBuffer->lpVertexBuffer->Lock(
0,
0,
(BYTE**)ppMyD3DVERTEX,
0);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CVertexBuffer::RotateMesh\n\r \
couldn't get a pointer to the vertex buffer.");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::UnlockVertexBuffer(IN VertexBuffer *pVertexBuffer)
{
HRESULT ret;
ret = pVertexBuffer->lpVertexBuffer->Unlock();
//---------------------------------
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CCDirectXInterface::UnLockVertexBuffer()\n\
Error Ulocking Buffer.");
return false;
}
//---------------------------------
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::WorldRotationYawPitchRoll( float Yaw,float Pitch,float Roll)
{
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
D3DMATERIAL8 BoundingBoxMaterial =
{
1.0f,0,0,1.0f,//Diffuse
1.0f,0,0,1.0f,//
1.0f,0,0,1.0f,//
1.0f,0,0,1.0f,//
0.0f
};
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::RenderBoundingBox( Box *pBoundingBox)
{
HRESULT ret;
m_pD3dDevice->SetVertexShader(D3DFVF_XYZ);
m_pD3dDevice->SetRenderState(D3DRS_FILLMODE,D3DFILL_WIREFRAME);
//---------------------------------
ret = m_pD3dDevice->SetMaterial(&BoundingBoxMaterial);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetMaterial()");
return false;
}
//---------------------------------
ret = m_pD3dDevice->SetTexture(
0,
NULL);
if(ret!= D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CRender::SetTexture()");
return false;
}
//---------------------------------
ret = m_pD3dDevice->DrawPrimitiveUP(
D3DPT_TRIANGLESTRIP,
6,
pBoundingBox,
sizeof(D3DXVECTOR3));
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage("CCDirectXInterface::RenderBoundingBox()\n\
DrawPrimitiveUP().");
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::CalculateObjectBoundingBox(IN OUT Object *pObject)
{
Box3 box3;
D3DXVECTOR3 MAX,Min;
box3.pMax = D3DXVECTOR3(0,0,0);
box3.pMin = D3DXVECTOR3(0,0,0);
//---------------------------------
for(DWORD i=0;i<pObject->nMeshs;i++)
{
for(DWORD j=0;j<pObject->pMeshs[i].nVertex;j++)
{
//-----------------------------------------------------------
//Max
if(pObject->pMeshs[i].pVertex[j].position.x > box3.pMax.x)
{
box3.pMax.x = pObject->pMeshs[i].pVertex[j].position.x;
}
//-----------------------------------------------------------
if(pObject->pMeshs[i].pVertex[j].position.y > box3.pMax.y)
{
box3.pMax.y = pObject->pMeshs[i].pVertex[j].position.y;
}
//-----------------------------------------------------------
if(pObject->pMeshs[i].pVertex[j].position.z > box3.pMax.z)
{
box3.pMax.z = pObject->pMeshs[i].pVertex[j].position.z;
}
//-----------------------------------------------------------
//-----------------------------------------------------------
//Min
if(pObject->pMeshs[i].pVertex[j].position.x < box3.pMin.x)
{
box3.pMin.x = pObject->pMeshs[i].pVertex[j].position.x;
}
//-----------------------------------------------------------
if(pObject->pMeshs[i].pVertex[j].position.y < box3.pMin.y)
{
box3.pMin.y = pObject->pMeshs[i].pVertex[j].position.y;
}
//-----------------------------------------------------------
if(pObject->pMeshs[i].pVertex[j].position.z < box3.pMin.z)
{
box3.pMin.z = pObject->pMeshs[i].pVertex[j].position.z;
}
}
}
MAX = box3.pMax;
Min = box3.pMin;
/*
[0] : (min,min,min)
[1] : (max,min,min)
[2] : (min,max,min)
[3] : (max,max,min)
[4] : (min,min,max)
[5] : (max,min,max)
[6] : (min,max,max)
[7] : (max,max,max)
*/
//---------------------------------
pObject->BoundingBox.Box[0] = D3DXVECTOR3( Min.x , Min.y , Min.z );
pObject->BoundingBox.Box[1] = D3DXVECTOR3( MAX.x , Min.y , Min.z );
pObject->BoundingBox.Box[2] = D3DXVECTOR3( Min.x , MAX.y , Min.z );
pObject->BoundingBox.Box[3] = D3DXVECTOR3( MAX.x , MAX.y , Min.z );
pObject->BoundingBox.Box[4] = D3DXVECTOR3( Min.x , Min.y , MAX.z );
pObject->BoundingBox.Box[5] = D3DXVECTOR3( MAX.x , Min.y , MAX.z );
pObject->BoundingBox.Box[6] = D3DXVECTOR3( Min.x , MAX.y , MAX.z );
pObject->BoundingBox.Box[7] = D3DXVECTOR3( MAX.x , MAX.y , MAX.z );
//---------------------------------
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::PickTriangle(Object *pObject,long x,long y,POINT ScreenWidthHeight)
{
//---------------------------------------------------
D3DXVECTOR3 vPickRayDir;
D3DXVECTOR3 vPickRayOrig;
FLOAT m_fPickT, m_fPickU, m_fPickV; // Picking results
D3DXVECTOR3 v0,v1,v2;
if(!m_pD3dDevice)
return false;
//---------------------------------------------------
D3DXMATRIX matProj;
m_pD3dDevice->GetTransform( D3DTS_PROJECTION, &matProj );
POINT ptCursor={x,y};
// Compute the vector of the pick ray in screen space
D3DXVECTOR3 v;
v.x = ( ( ( 2.0f * ptCursor.x ) / ScreenWidthHeight.x ) - 1 ) / matProj._11;
v.y = -( ( ( 2.0f * ptCursor.y ) / ScreenWidthHeight.y ) - 1 ) / matProj._22;
v.z = 1.0f;
// Get the inverse view matrix
D3DXMATRIX matView, m;
m_pD3dDevice->GetTransform( D3DTS_VIEW, &matView );
D3DXMatrixInverse( &m, NULL, &matView );
// Transform the screen space pick ray into 3D space
vPickRayDir.x = v.x*m._11 + v.y*m._21 + v.z*m._31;
vPickRayDir.y = v.x*m._12 + v.y*m._22 + v.z*m._32;
vPickRayDir.z = v.x*m._13 + v.y*m._23 + v.z*m._33;
vPickRayOrig.x = m._41;
vPickRayOrig.y = m._42;
vPickRayOrig.z = m._43;
//---------------------------------------------------
MyD3DVERTEX *pMyD3DVERTEX;
for( DWORD loopMesh=0; loopMesh<pObject->nMeshs; loopMesh++ )
{
if(!LockVertexBuffer(&pObject->pVertexBuffers[loopMesh],&pMyD3DVERTEX))
return false;
for(DWORD i=0;i<(pObject->pMeshs[loopMesh].nVertex/3);i++)
{
v0 = pObject->pMeshs[loopMesh].pVertex[i*3].position;
v1 = pObject->pMeshs[loopMesh].pVertex[i*3+1].position;
v2 = pObject->pMeshs[loopMesh].pVertex[i*3+2].position;
// Check if the pick ray passes through this point
if( IntersectTriangle( vPickRayOrig, vPickRayDir, v0, v1, v2,
&m_fPickT, &m_fPickU, &m_fPickV ) )
{
sprintf(g_Buffer,"v0 = {%f ,%f ,%f}\r\nv1 = {%f ,%f ,%f}\r\nv2 = {%f ,%f ,%f}\r\n",
v0.x,v0.y,v0.z,
v1.x,v1.y,v1.z,
v2.x,v2.y,v2.z);
// sprintf(g_Buffer,"m_fPickT = %f, m_fPickU = %f, m_fPickV = %f",m_fPickT, m_fPickU, m_fPickV);
MessageBox(0,g_Buffer,"IntersectTriangle",MB_OK);
break;
}
}
if(!UnlockVertexBuffer(&pObject->pVertexBuffers[loopMesh]))
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::IntersectTriangle( const D3DXVECTOR3& orig,
const D3DXVECTOR3& dir, D3DXVECTOR3& v0,
D3DXVECTOR3& v1, D3DXVECTOR3& v2,
FLOAT* t, FLOAT* u, FLOAT* v )
{
// Find vectors for two edges sharing vert0
D3DXVECTOR3 edge1 = v1 - v0;
D3DXVECTOR3 edge2 = v2 - v0;
// Begin calculating determinant - also used to calculate U parameter
D3DXVECTOR3 pvec;
D3DXVec3Cross( &pvec, &dir, &edge2 );
// If determinant is near zero, ray lies in plane of triangle
FLOAT det = D3DXVec3Dot( &edge1, &pvec );
if( det < 0.0001f )
return false;
// Calculate distance from vert0 to ray origin
D3DXVECTOR3 tvec = orig - v0;
// Calculate U parameter and test bounds
*u = D3DXVec3Dot( &tvec, &pvec );
if( *u < 0.0f || *u > det )
return false;
// Prepare to test V parameter
D3DXVECTOR3 qvec;
D3DXVec3Cross( &qvec, &tvec, &edge1 );
// Calculate V parameter and test bounds
*v = D3DXVec3Dot( &dir, &qvec );
if( *v < 0.0f || *u + *v > det )
return false;
// Calculate t, scale parameters, ray intersects triangle
*t = D3DXVec3Dot( &edge2, &qvec );
FLOAT fInvDet = 1.0f / det;
*t *= fInvDet;
*u *= fInvDet;
*v *= fInvDet;
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::CalculateMaxMinBox(IN Box *pBox,OUT Box3 *pBox3)
{
pBox3->pMax = D3DXVECTOR3(0,0,0);
pBox3->pMin = D3DXVECTOR3(0,0,0);
for(DWORD loop=0;loop<8;loop++)
{
//-------------------------------------
//Max
if(pBox3->pMax.x < pBox->Box[loop].x)
{
pBox3->pMax.x = pBox->Box[loop].x;
}
if(pBox3->pMax.y < pBox->Box[loop].y)
{
pBox3->pMax.y = pBox->Box[loop].y;
}
if(pBox3->pMax.z < pBox->Box[loop].z)
{
pBox3->pMax.z = pBox->Box[loop].z;
}
//-------------------------------------
//Min
if(pBox3->pMin.x > pBox->Box[loop].x)
{
pBox3->pMin.x = pBox->Box[loop].x;
}
if(pBox3->pMin.y > pBox->Box[loop].y)
{
pBox3->pMin.y = pBox->Box[loop].y;
}
if(pBox3->pMin.z > pBox->Box[loop].z)
{
pBox3->pMin.z = pBox->Box[loop].z;
}
//-------------------------------------
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::IsBoxsIntersect(Box3 *pBox1,Box3 *pBox2)
{
//---------------------------------
if((pBox2->pMax.x < pBox1->pMax.x) && (pBox2->pMax.x > pBox1->pMin.x))
{
if((pBox2->pMax.y < pBox1->pMax.y) && (pBox2->pMax.y > pBox1->pMin.y))
{
if((pBox2->pMax.z < pBox1->pMax.z) && (pBox2->pMax.z > pBox1->pMin.z))
{
return true;
}
}
}
//---------------------------------
if((pBox1->pMax.x < pBox2->pMax.x) && (pBox1->pMax.x > pBox2->pMin.x))
{
if((pBox1->pMax.y < pBox2->pMax.y) && (pBox1->pMax.y > pBox2->pMin.y))
{
if((pBox1->pMax.z < pBox2->pMax.z) && (pBox1->pMax.z > pBox2->pMin.z))
{
return true;
}
}
}
//---------------------------------
return false;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::SetTransformations()
{
//--------------------------------------
//World
D3DXMATRIX matWorld;
D3DXMatrixIdentity( &matWorld );
g_DirectX3D.SetWorldTransform(&matWorld);
//--------------------------------------
//View
D3DXMATRIX matView;
D3DXVECTOR3 EyePoint = D3DXVECTOR3(
g_GlobalData.CameraEyeX,
g_GlobalData.CameraEyeY,
g_GlobalData.CameraEyeZ);
D3DXMATRIX matRotateEyePoint;
D3DXMatrixRotationYawPitchRoll( &matRotateEyePoint ,
DEG2RAD(g_GlobalData.EyeX_Rotation),
DEG2RAD(g_GlobalData.EyeY_Rotation),
DEG2RAD(g_GlobalData.EyeZ_Rotation));
D3DXVec3TransformCoord(&EyePoint,&EyePoint,&matRotateEyePoint);
D3DXMatrixLookAtLH(
&matView,
&D3DXVECTOR3( EyePoint.x, EyePoint.y,EyePoint.z),//Eye point
&D3DXVECTOR3( g_GlobalData.CameraTargetX, g_GlobalData.CameraTargetY, g_GlobalData.CameraTargetZ), //camera look-at target
&D3DXVECTOR3( 0.0f, 1.0f, 0.0f ));
g_DirectX3D.SetViewTransform(&matView);
//--------------------------------------
//Projection
D3DXMATRIX matProj;
D3DXMatrixPerspectiveFovLH( &matProj,
D3DX_PI/4,
1.0f,
1.0f,
100000000.0f );
g_DirectX3D.SetProjectionTransform((D3DXMATRIX*)&matProj);
//--------------------------------------
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::SetRenderState(D3DRENDERSTATETYPE State,DWORD Value)
{
HRESULT hr;
hr = m_pD3dDevice->
SetRenderState(State,Value);
if(hr!=D3D_OK)
{
sprintf(g_Buffer,"Error CDirectX3D::SetRenderState( 0x%x , 0x%x ) \r\nError Code 0x%x ( %s )\r\n",
State,Value,hr,DXGetErrorString8(hr));
DisplayErrorMessage(g_Buffer);
return false;
}
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::WritePC_CapabilitiesToFile(char *szFileName)
{
HRESULT hr;
if(!m_pD3dDevice)
{
DisplayErrorMessage(" DirectX3D Was not Initialized!");
return false;
}
hr = m_pD3dDevice->GetDeviceCaps(&m_D3DCAPS8);
if(hr!=D3D_OK)
{
DisplayErrorMessage("GetDeviceCaps()");
DisplayDirectXErrorCode(hr);
return false;
}
//-----------------------------
FILE *f;
f = fopen(szFileName,"w+");
if(!f)
{
ShowWinError("Error fopen()\r\n");
return false;
}
//-----------------------------
fprintf(f,"==================================\r\n");
fprintf(f,"Your PC Capabilities:\r\n");
fprintf(f,"==================================\r\n\r\n");
fprintf(f,"PixelShaderVersion = %u.%u\r\n",
(m_D3DCAPS8.PixelShaderVersion>>8) & 0xFF,
(m_D3DCAPS8.PixelShaderVersion) & 0xFF);
fprintf(f,"MaxPrimitiveCount = %u\r\n",
m_D3DCAPS8.MaxPrimitiveCount);
fprintf(f,"MaxVertexIndex = %u\r\n",
m_D3DCAPS8.MaxVertexIndex);
fprintf(f,"MaxActiveLights = %u\r\n",
m_D3DCAPS8.MaxActiveLights);
fprintf(f,"MaxTextureWidth = %u\r\n",
m_D3DCAPS8.MaxTextureWidth);
fprintf(f,"MaxTextureHeight = %u\r\n",
m_D3DCAPS8.MaxTextureHeight);
//-----------------------------
fclose(f);
return true;
}
//////////////////////////////////////////
//
//////////////////////////////////////////
bool CDirectX3D::ShowFog()
{
HRESULT ret;
float Start = 1.5f;
float End = 100000.0f;
float Density=0.00002f;
// Enable fog blending.
ret=m_pD3dDevice->SetRenderState(
D3DRS_FOGENABLE, TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGENABLE");
}
// Set the fog color.
ret=m_pD3dDevice->SetRenderState(
D3DRS_FOGCOLOR,
D3DCOLOR_ARGB(0,198,231,255));//0,0,200,0));
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGCOLOR");
}
// Set fog parameters.
if(D3DFOG_LINEAR == D3DFOG_LINEAR )
{
m_pD3dDevice->
SetRenderState(D3DRS_FOGTABLEMODE,
D3DFOG_LINEAR);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGTABLEMODE Pixel-Fog");
}
ret=m_pD3dDevice->SetRenderState(
D3DRS_FOGSTART, *(DWORD *)(&Start));
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGSTART");
}
ret=m_pD3dDevice->SetRenderState(
D3DRS_FOGEND, *(DWORD *)(&End));
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGEND");
}
}
else//D3DRS_FOGVERTEXMODE.
{
ret=m_pD3dDevice->SetRenderState(
D3DRS_FOGTABLEMODE, D3DFOG_EXP );
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGVERTEXMODE");
return false;
}
ret=m_pD3dDevice->SetRenderState(
D3DRS_FOGDENSITY, *(DWORD *)(&Density));
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_FOGDENSITY");
return false;
}
}
// Enable range-based fog if desired (only supported for
// vertex fog). For this example, it is assumed that UseRange
// is set to a nonzero value only if the driver exposes the
// D3DPRASTERCAPS_FOGRANGE capability.
// Note: This is slightly more performance intensive
// than non-range-based fog.
if(TRUE)
{
ret=m_pD3dDevice->SetRenderState(
D3DRS_RANGEFOGENABLE,
TRUE);
if(ret!=D3D_OK)
{
DisplayDirectXErrorCode(ret);
DisplayErrorMessage(
"RenderState::CreateFog() D3DRS_RANGEFOGENABLE");
return false;
}
}
return true;
}