学习《Real Time Rendering》后自己实现的代码

学习《Real Time Rendering》后自己实现的代码:

演示程序下载:http://download.csdn.net/detail/jiangcaiyang123/4007231

程序截图:


这是书上的截图:



考完试后我就开始继续钻研我的游戏开发。前几天我完成了游戏开发的最基础的工作,也就是说
在此基础上进行游戏开发效率更高,速度更快。而且我在看《Real Time Rendering》这本书受到了很多启发。使用类MFC的开发模式可以很好的提高开发的效率。好了,接下来介绍的是我最近在钻研的矩阵变换的问题。


在游戏中一般有三个矩阵:视角矩阵、世界矩阵和投影矩阵。简单地说,视角矩阵就是观察者眼睛所在的矩阵,世界矩阵则是目标物体所在世界的矩阵,投影矩阵则好比为观察者的眼睛的晶状体。通过三个矩阵的相互作用可以模拟出所有三维的场景。在这里我就不再过多地赘述有关矩阵的内容了。因为书没有直接的代码,所以我靠自己的一点知识就实现了书上的例子程序。程序的截图如下:

我在代码中添加了必要的注释,所以代码基本上还是好懂的。


// GameStart.h 游戏开始的场景
// 2012年1月5日11:41:29 最后编辑

#ifndef _GAMESTART_H_
#define _GAMESTART_H_

#include <vector>
#include <d3dx9.h>
#include "../DX框架/Scenario.h"
#include "../DX框架/GameShape.h"
#include "../DX框架/JCYInput.h"

#pragma comment( lib, "d3dx9.lib" )

class CGameStart: public IScenario
{
public:
	CGameStart( TCHAR* pName, HINSTANCE hInst, HWND hWnd, LPDIRECT3DDEVICE9 pDevice );	// 构造函数
	~CGameStart( void );									// 析构函数

	void Draw( void );										// 绘图
	unsigned long Release( void );							// 释放空间
	TCHAR* GetName( void )									// 获取场景名
	{
		return m_Name;
	}

	void InitializeViewport( void );						// 初始化视角
private:
	TCHAR*						m_Name;						// 场景名
	HWND						m_hWnd;						// 窗口句柄
	LPDIRECT3DDEVICE9			m_pDevice;					// D3D设备
	LPDIRECT3DVERTEXBUFFER9		m_pBuffer;					// 顶点缓存
	CInput		m_BufferInput, m_ImmediateInput;			// 输入系统

	D3DXMATRIX					m_WorldMatrix;				// 世界矩阵
	D3DXMATRIX					m_ViewMatrix;				// 视角矩阵
	D3DXMATRIX					m_ProjectMatrix;			// 投影矩阵

	D3DVIEWPORT9				m_RViewport;				// 旋转视角
	D3DVIEWPORT9				m_SRTViewport;				// 比例旋转视角
	D3DVIEWPORT9				m_TRViewport;				// 转置视角
	D3DVIEWPORT9				m_RTRSViewport;				// 旋转转置旋转视角

	struct STVertex											// 定义自己的顶点结构体
	{
		float x, y, z;
		unsigned long color;// 在DirectX中D3DCOLOR被解释成unsigned long
	};
	static const unsigned short POINT_FVF = D3DFVF_XYZ | D3DFVF_DIFFUSE;	// 灵活顶点格式
};

#endif

// GameStart.cpp 游戏开始的场景的实现文件
// NUM_VERTICES12年1月5日12:22:17 最后编辑

#include <d3d9.h>
#include "GameStart.h"

#define NUM_VERTICES 50

CGameStart::CGameStart( TCHAR *pName, HINSTANCE hInst, HWND hWnd, LPDIRECT3DDEVICE9 pDevice )// 构造函数
{
	m_hWnd = hWnd;
	m_pDevice = pDevice;

	m_pDevice->SetRenderState( D3DRS_LIGHTING, FALSE );
	D3DXMatrixIdentity( &m_ViewMatrix );
	m_pDevice->SetTransform( D3DTS_VIEW, &m_ViewMatrix );

	InitializeViewport( );

	// 初始化顶点缓存
	m_pDevice->CreateVertexBuffer( NUM_VERTICES * sizeof( STVertex ), D3DUSAGE_DYNAMIC | D3DUSAGE_POINTS, POINT_FVF,
		D3DPOOL_DEFAULT, &m_pBuffer, NULL );

	STVertex* pVertices;
	m_pBuffer->Lock( 0, NUM_VERTICES * sizeof( STVertex ), (void**)&pVertices, D3DLOCK_DISCARD );
	for ( long i = 0; i < NUM_VERTICES; i++ )
	{
		
		float angle = (float)i / (float)NUM_VERTICES * 2.0f * D3DX_PI;
		pVertices[i].x = 0.3f * cos( angle );
		pVertices[i].y = 0.3f * sin( angle );
		pVertices[i].z = 1.0f;

		pVertices[i].color = D3DCOLOR_XRGB( 255, 255, 255 );
	}
	m_pBuffer->Unlock( );
	m_pDevice->SetStreamSource( 0, m_pBuffer, 0, sizeof( STVertex ) );	// 相同资源的顶点缓存要在一起为好
	m_pDevice->SetFVF( POINT_FVF );

	/*----------初始化输入------------*/
	m_ImmediateInput.Initialize( IMMEDIATE, hInst, m_hWnd );
	m_BufferInput.Initialize( BUFFERED, hInst, m_hWnd );

	m_Name = pName;
}

CGameStart::~CGameStart( void )							// 析构函数
{
	Release( );
}

unsigned long CGameStart::Release( void )				// 释放空间
{
	m_pBuffer->Release( );

	m_ImmediateInput.Release( );
	m_BufferInput.Release( );

	return 0;
}

void CGameStart::Draw( void )							// 绘图
{	
	RECT windowRect;
	GetClientRect( m_hWnd, &windowRect );
	D3DXMatrixPerspectiveFovLH( &m_ProjectMatrix, D3DX_PI / 4, float( windowRect.right - windowRect.left ) / float( windowRect.bottom - windowRect.top ), 1.0f, 100.0f );
	m_pDevice->SetTransform( D3DTS_PROJECTION, &m_ProjectMatrix );

	D3DXMATRIX rotationMatrix1;
	D3DXMATRIX rotationMatrix2;
	D3DXMATRIX translationMatrix;
	D3DXMATRIX scalingMatrix;

	D3DVIEWPORT9 mainViewport;	// 保存原来视角的副本
	m_pDevice->GetViewport( &mainViewport );

	D3DXMatrixRotationZ( &rotationMatrix1, (float)GetTickCount( ) / 1000.0f );
	D3DXMatrixRotationZ( &rotationMatrix2, -(float)GetTickCount( ) / 1000.0f );

	D3DXMatrixTranslation( &translationMatrix, 0.0f, 0.0f, 0.0f );                     // 更改第一个浮点数会出现不同的效果!试试看。
	D3DXMatrixScaling( &scalingMatrix, 1.0f, 0.5f, 1.0f );

	m_pDevice->SetViewport( &m_RViewport );// 左上角图形
	m_WorldMatrix = rotationMatrix1;
	m_pDevice->SetTransform( D3DTS_WORLD, &m_WorldMatrix );
	m_pDevice->DrawPrimitive( D3DPT_POINTLIST, 0, NUM_VERTICES );

	m_pDevice->SetViewport( &m_SRTViewport );// 右上角图形
	m_WorldMatrix = translationMatrix * rotationMatrix1 * scalingMatrix;
	m_pDevice->SetTransform( D3DTS_WORLD, &m_WorldMatrix );
	m_pDevice->DrawPrimitive( D3DPT_POINTLIST, 0, NUM_VERTICES );

	m_pDevice->SetViewport( &m_TRViewport );// 左下角图形
	m_WorldMatrix = rotationMatrix1 * translationMatrix;
	m_pDevice->SetTransform( D3DTS_WORLD, &m_WorldMatrix );
	m_pDevice->DrawPrimitive( D3DPT_POINTLIST, 0, NUM_VERTICES );

	m_pDevice->SetViewport( &m_RTRSViewport );// 右下角图形
	m_WorldMatrix = scalingMatrix * rotationMatrix2 * translationMatrix * rotationMatrix1;
	m_pDevice->SetTransform( D3DTS_WORLD, &m_WorldMatrix );
	m_pDevice->DrawPrimitive( D3DPT_POINTLIST, 0, NUM_VERTICES );

	m_pDevice->SetViewport( &mainViewport );// 还原原来的视角

}

void CGameStart::InitializeViewport( void )				// 初始化视角
{
	D3DVIEWPORT9 mainViewport;
	m_pDevice->GetViewport( &mainViewport );

	// 为一些视角赋值
	m_RViewport.Width = m_SRTViewport.Width = m_TRViewport.Width = m_RTRSViewport.Width = mainViewport.Width / 2;
	m_RViewport.Height = m_SRTViewport.Height = m_TRViewport.Height = m_RTRSViewport.Height = mainViewport.Height / 2;

	m_RViewport.Y = m_SRTViewport.Y = 0;
	m_RViewport.X = m_TRViewport.X = 0;

	m_TRViewport.Y = m_RTRSViewport.Y = mainViewport.Height / 2;
	m_SRTViewport.X = m_RTRSViewport.X = mainViewport.Width / 2;

	m_RViewport.MinZ = m_SRTViewport.MinZ = m_TRViewport.MinZ = m_RTRSViewport.MinZ = 0.0f;
	m_RViewport.MaxZ = m_SRTViewport.MaxZ = m_TRViewport.MaxZ = m_RTRSViewport.MaxZ = 1.0f;

}

要下载程序的代码,请点击下方:


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值