Direct3D learning (3)

一個簡單的物體旋轉代碼。 便於理解世界矩陣,視圖矩陣以及投影矩陣的意思。目前只有世界矩陣的用法。

#include "stdafx.h"

#include < d3dx9.h >
#include < Mmsystem.h >


LPDIRECT3D9 g_pD3D = NULL;
LPDIRECT3DDEVICE9 g_pD3DDevice = NULL;
LPDIRECT3DVERTEXBUFFER9 g_pVertexBuffer = NULL;

struct CUSTOMVERTEX
{
	FLOAT x, y, z;
	DWORD color;
};

#define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZ | D3DFVF_DIFFUSE)

#define SafeRelease(pObject) /
	if (pObject != NULL) {/
		pObject->Release(); /
		pObject = NULL; /
	}

HRESULT InitializeD3D(HWND hWnd)
{
	g_pD3D = Direct3DCreate9(D3D_SDK_VERSION);
	if (g_pD3D == NULL) {
		return E_FAIL;
	}
	D3DDISPLAYMODE d3ddm;
	if (FAILED( g_pD3D->GetAdapterDisplayMode(D3DADAPTER_DEFAULT, &d3ddm))) {
		return E_FAIL;
	}
	D3DPRESENT_PARAMETERS d3dpp;
	ZeroMemory(&d3dpp, sizeof(d3dpp));
	d3dpp.Windowed = TRUE;
	d3dpp.SwapEffect = D3DSWAPEFFECT_COPY;
	d3dpp.BackBufferFormat = d3ddm.Format;
	if (FAILED(g_pD3D->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
				D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp, &g_pD3DDevice))) {
		return E_FAIL;
	}
	// set cullmode use anti-circle-way
	g_pD3DDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_CCW);
	g_pD3DDevice->SetRenderState(D3DRS_LIGHTING, FALSE);
	return S_OK;
}

HRESULT InitialiseVertexBuffer()
{
	VOID* pVertex;
	CUSTOMVERTEX cvVertex[] = {
		//Top Face
		{-5.0f, 5.0f, -5.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 0 - Blue 
		{-5.0f, 5.0f, 5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 1 - Red 
		{5.0f, 5.0f, -5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 2 - Red 
		{5.0f, 5.0f, 5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 3 - Green 

		//Face 1
		{-5.0f, -5.0f, -5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 4 - Red 
		{-5.0f, 5.0f, -5.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 5 - Blue 
		{5.0f, -5.0f, -5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 6 - Green 
		{5.0f, 5.0f, -5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 7 - Red 

		//Face 2
		{5.0f, -5.0f, 5.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 8 - Blue 
		{5.0f, 5.0f, 5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 9 - Green

		//Face 3
		{-5.0f, -5.0f, 5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 10 - Green 
		{-5.0f, 5.0f, 5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 11 - Red 

		//Face 4
		{-5.0f, -5.0f, -5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 12 - Red 
		{-5.0f, 5.0f, -5.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 13 - Blue

		//Bottom Face
		{5.0f, -5.0f, -5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 14 - Green 
		{5.0f, -5.0f, 5.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 15 - Blue 
		{-5.0f, -5.0f, -5.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 16 - Red 
		{-5.0f, -5.0f, 5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 17 - Green

		{10.0f, 10.0f, 0.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 1 - Blue 
		{15.0f, 10.0f, 0.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 2 - Red 
		{10.0f, 15.0f, 0.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 3 - Green
		{10.0f, 10.0f, 5.0f, D3DCOLOR_XRGB(0, 255, 0),}, //Vertex 4 - Green
		{10.0f, 10.0f, 0.0f, D3DCOLOR_XRGB(0, 0, 255),}, //Vertex 1 - Blue 
		{15.0f, 10.0f, 0.0f, D3DCOLOR_XRGB(255, 0, 0),}, //Vertex 2 - Red 


	};
	if (FAILED(g_pD3DDevice->CreateVertexBuffer(sizeof(cvVertex), 0, D3DFVF_CUSTOMVERTEX,
		D3DPOOL_DEFAULT, &g_pVertexBuffer, NULL))) {
		return E_FAIL;
	}
	if (FAILED(g_pVertexBuffer->Lock(0, sizeof(cvVertex), (void**)&pVertex, 0))) {
		return E_FAIL;
	}
	
	memcpy(pVertex, cvVertex, sizeof(cvVertex));
	g_pVertexBuffer->Unlock();
	return S_OK;
}

void SetupRotation()
{
	//Here we will rotate our world around the x, y and z axis.
	D3DXMATRIX matWorld, matWorldX, matWorldY, matWorldZ;

	//Create the transformation matrices
	D3DXMatrixRotationX(&matWorldX, timeGetTime()/400.0f);
	D3DXMatrixRotationY(&matWorldY, timeGetTime()/400.0f); 
	D3DXMatrixRotationZ(&matWorldZ, timeGetTime()/400.0f); 

	//Combine the transformations by multiplying them together
	D3DXMatrixMultiply(&matWorld, &matWorldX, &matWorldY);
	D3DXMatrixMultiply(&matWorld, &matWorld, &matWorldZ);

	//Apply the tansformation
	g_pD3DDevice->SetTransform(D3DTS_WORLD, &matWorld);
}

void SetupCamera()
{
	//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, 0, -30)
	//Look at Position: (0, 0, 0)
	//Up direction: Y-Axis.
	D3DXMATRIX matView;
	D3DXMatrixLookAtLH(&matView, &D3DXVECTOR3(0.0f, 0.0f,-100.0f), //Camera Position
		&D3DXVECTOR3(0.0f, 0.0f, 0.0f), //Look At Position
		&D3DXVECTOR3(0.0f, 1.0f, 0.0f)); //Up Direction
	g_pD3DDevice->SetTransform(D3DTS_VIEW, &matView);
}

void SetupPerspective()
{
	//Here we specify the field of view, aspect ration and near and
	//far clipping planes.
	D3DXMATRIX matProj;
	D3DXMatrixPerspectiveFovLH(&matProj, D3DX_PI/4, 1.0f, 1.0f, 500.0f);
	g_pD3DDevice->SetTransform(D3DTS_PROJECTION, &matProj);
}

void Render()
{
	if (g_pD3DDevice == NULL) {
		return;
	}
	// background color
	g_pD3DDevice->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 0, 0), 1.0f, 0);
	g_pD3DDevice->BeginScene();

	//SetupRotation();
	SetupCamera();
	SetupPerspective();


	g_pD3DDevice->SetStreamSource(0, g_pVertexBuffer, 0, sizeof(CUSTOMVERTEX));
	g_pD3DDevice->SetFVF(D3DFVF_CUSTOMVERTEX);

	D3DXMATRIX matWorld, matWorldTranLeft10, matWorldTranRight10, matWorldX, matWorldZ;

	//Create the transformation matrices
	D3DXMatrixRotationX(&matWorldX, timeGetTime()/400.0f);
	D3DXMatrixRotationY(&matWorldZ, timeGetTime()/400.0f);
	D3DXMatrixTranslation(&matWorldTranLeft10, -10, 0, 0);
	D3DXMatrixTranslation(&matWorldTranRight10, 10, 0, 0);
	D3DXMatrixMultiply(&matWorld, &matWorldTranLeft10, &matWorldZ);
	D3DXMatrixMultiply(&matWorld, &matWorld, &matWorldTranRight10);

	g_pD3DDevice->SetTransform(D3DTS_WORLD, &matWorldX);
	
	g_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP, 0, 2);
	g_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP, 4, 8);
	g_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP, 14, 2);

	g_pD3DDevice->SetTransform(D3DTS_WORLD, &matWorld);
	g_pD3DDevice->DrawPrimitive(D3DPT_TRIANGLESTRIP, 18, 4);

	g_pD3DDevice->EndScene();
	g_pD3DDevice->Present(NULL, NULL, NULL, NULL);
}

void CleanUp()
{
	SafeRelease(g_pVertexBuffer);
	SafeRelease(g_pD3DDevice);
	SafeRelease(g_pD3D);
}

void GameLoop()
{
	MSG msg;
	BOOL fMessage;
	PeekMessage(&msg, NULL, 0U, 0U, PM_NOREMOVE);
	while(msg.message != WM_QUIT) {
		fMessage = PeekMessage(&msg, NULL, 0U, 0U, PM_REMOVE);
		if (fMessage) {
			TranslateMessage(&msg);
			DispatchMessage(&msg);
		}else {
			Render();
		}
	}
}

LRESULT WINAPI WinProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
	switch(msg) {
	case WM_DESTROY:
		PostQuitMessage(0);
		return 0;
		break;
	case WM_KEYUP:
		switch(wParam) {
		case VK_ESCAPE:
			DestroyWindow(hWnd);
			return 0;
			break;
		}
		break;
	default:
		break;
	}
	return DefWindowProc(hWnd, msg, wParam, lParam);
}

INT WINAPI WinMain(HINSTANCE hInst, HINSTANCE , LPSTR , int )
{
	WNDCLASSEX wc = {sizeof(WNDCLASSEX), CS_CLASSDC, WinProc, 0L, 0L, 
		GetModuleHandle(NULL), NULL, NULL, NULL, NULL,
		"DX Project 1", NULL};
	RegisterClassEx(&wc);
	HWND hWnd = CreateWindow("DX Project 1", "www.andypike.com: Tutorial 1", 
		WS_OVERLAPPEDWINDOW, 50, 50, 500, 500,
		GetDesktopWindow(), NULL, wc.hInstance, NULL);

	if(SUCCEEDED(InitializeD3D(hWnd)))
	{
		//Show our window
		ShowWindow(hWnd, SW_SHOWDEFAULT);
		UpdateWindow(hWnd);
		
		//Start game running: Enter the game loop
		if (SUCCEEDED(InitialiseVertexBuffer())) {
			GameLoop();
		}
	}
	
	CleanUp();
	
    UnregisterClass("DX Project 1", wc.hInstance);
    
    return 0;
}
發佈了19 篇原創文章 · 獲贊 0 · 訪問量 3萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章