DirectD3D-网格(一)

 由于关于DirectD3D的很多基础知识在浅墨的博客http://blog.csdn.net/zhmxy555/article/category/1091031/2上都有详细的讲解,这里我只对自己学到的东西的进行简单的讲解。


本章我们主要学习如何用简单的使用ID3DXMesh接口来自定义网格图形。本章将绘制一个魔方


先定义一些全局变量

LPDIRECT3DTEXTURE9				g_pTexture[6]={0};		// 纹理接口对象,用于渐进纹理的存放
ID3DXMesh						*g_pMesh=NULL;			//网格接口
const DWORD	g_NumSubsets	=	6;	//网格子集数



首先我们自定义顶点信息


typedef struct MyVecter
{
	float _x,_y,_z;
	float _nx,_ny,_nz;
	float _u,_v;

	MyVecter(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){}


	static const DWORD FVF_XYZ_NORMAL_TEX1;

}*LPMYVECTER;

const DWORD MyVecter::FVF_XYZ_NORMAL_TEX1=D3DFVF_XYZ|D3DFVF_NORMAL|D3DFVF_TEX1;


可以根据自己的需求来修改顶点信息


接着我们用D3DXCreateMeshFVF来创建一个空的网格对象D3DXCreateMeshFVF定义入下:

HRESULT WINAPI D3DXCreateMeshFVF(  
    DWORD NumFaces,         // 网格所具有的面片个数  
    DWORD NumVertices,      // 网格所具有的顶点个数  
    DWORD Options,          // 创建网格时所使用的创建标记  
    DWORD FVF,          // 顶点的顶点灵活格式  
    LPDIRECT3DDEVICE9 pDevice,  // 与该网格相关的设备指针  
    LPD3DXMESH *ppMesh      // 所创建的网格对象的指针  
);  

用法:

D3DXCreateMeshFVF(
		12,24,D3DXMESH_MANAGED,MyVecter::FVF_XYZ_NORMAL_TEX1,
		g_pD3DDevice,&g_pMesh)


接着我们来填网格的充顶点缓存

//填充顶点缓存
	MyVecter* v=0;
	g_pMesh->LockVertexBuffer(0,(void**)&v);

	// 正面
	v[0] = MyVecter(-1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f);
	v[1] = MyVecter(-1.0f,  1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 3.0f);
	v[2] = MyVecter( 1.0f,  1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 3.0f, 3.0f);
	v[3] = MyVecter( 1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 3.0f, 0.0f);

	// 背面
	v[4] = MyVecter(-1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f);
	v[5] = MyVecter( 1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 3.0f);
	v[6] = MyVecter( 1.0f,  1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 3.0f, 3.0f);
	v[7] = MyVecter(-1.0f,  1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 3.0f, 0.0f);

	// 顶面
	v[8]  = MyVecter(-1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f);
	v[9]  = MyVecter(-1.0f, 1.0f,  1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 3.0f);
	v[10] = MyVecter( 1.0f, 1.0f,  1.0f, 0.0f, 1.0f, 0.0f, 3.0f, 3.0f);
	v[11] = MyVecter( 1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 3.0f, 0.0f);

	// 底面
	v[12] = MyVecter(-1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f);
	v[13] = MyVecter( 1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 3.0f);
	v[14] = MyVecter( 1.0f, -1.0f,  1.0f, 0.0f, -1.0f, 0.0f, 3.0f, 3.0f);
	v[15] = MyVecter(-1.0f, -1.0f,  1.0f, 0.0f, -1.0f, 0.0f, 3.0f, 0.0f);

	// 左面
	v[16] = MyVecter(-1.0f, -1.0f,  1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f);
	v[17] = MyVecter(-1.0f,  1.0f,  1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 3.0f);
	v[18] = MyVecter(-1.0f,  1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 3.0f, 3.0f);
	v[19] = MyVecter(-1.0f, -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 3.0f, 0.0f);

	// 右面
	v[20] = MyVecter( 1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f);
	v[21] = MyVecter( 1.0f,  1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 3.0f);
	v[22] = MyVecter( 1.0f,  1.0f,  1.0f, 1.0f, 0.0f, 0.0f, 3.0f, 3.0f);
	v[23] = MyVecter( 1.0f, -1.0f,  1.0f, 1.0f, 0.0f, 0.0f, 3.0f, 0.0f);

	g_pMesh->UnlockVertexBuffer();


索引缓存填充

//填充索引缓存
	WORD* i=0;//这里用的不是DWORD是WORD
	g_pMesh->LockIndexBuffer(0,(void**)&i);

	// 正面
	i[0] = 0; i[1] = 1; i[2] = 2;
	i[3] = 0; i[4] = 2; i[5] = 3;

	// 背面
	i[6] = 4; i[7]  = 5; i[8]  = 6;
	i[9] = 4; i[10] = 6; i[11] = 7;

	// 顶面
	i[12] = 8; i[13] =  9; i[14] = 10;
	i[15] = 8; i[16] = 10; i[17] = 11;

	// 底面
	i[18] = 12; i[19] = 13; i[20] = 14;
	i[21] = 12; i[22] = 14; i[23] = 15;

	// 左面
	i[24] = 16; i[25] = 17; i[26] = 18;
	i[27] = 16; i[28] = 18; i[29] = 19;

	// 右面
	i[30] = 20; i[31] = 21; i[32] = 22;
	i[33] = 20; i[34] = 22; i[35] = 23;

	g_pMesh->UnlockIndexBuffer();

填充领接信息

//填充领接信息
	DWORD* attributeBuffer=0;
	int isubset=0;//子集序号
	g_pMesh->LockAttributeBuffer(0,&attributeBuffer);
	
	for (int i = 0; i < 12; i++)
	{
			attributeBuffer[i]=isubset;
			if ( ( (i+1) % 2) == 0 )
			{
				isubset++;
			}
	}

	g_pMesh->UnlockAttributeBuffer();



网格优化(可以不要,为了让大家了解一下所以写了出来)

//网格优化
	std::vector<DWORD> adjacencyBuffer(g_pMesh->GetNumFaces()*3);
	g_pMesh->GenerateAdjacency(0.1f,&adjacencyBuffer[0]);

	HR(g_pMesh->OptimizeInplace(
		//三角形单元排序生存一个属性表,移除网格无用顶点,提高顶点高速缓存的命中率
		D3DXMESHOPT_ATTRSORT|D3DXMESHOPT_COMPACT|D3DXMESHOPT_VERTEXCACHE,
		&adjacencyBuffer[0],
		0,0,0));

绘制
//网格绘制
	for (int i=0;i<g_NumSubsets;i++)
	{
		g_pMesh->DrawSubset(i);
	}


经过上面几步就可以绘制出一个正方体。




这样看来来只有干粑粑的正方体。我们可以给他加上纹理

//纹理创建(不加EX的方法不能使用多级渐进纹理)
	D3DXCreateTextureFromFile(g_pD3DDevice,L"blue.png",&g_pTexture[0]);
	D3DXCreateTextureFromFile(g_pD3DDevice,L"green.png",&g_pTexture[1]);
	D3DXCreateTextureFromFile(g_pD3DDevice,L"red.png",&g_pTexture[2]);
	D3DXCreateTextureFromFile(g_pD3DDevice,L"yellow.png",&g_pTexture[3]);
	D3DXCreateTextureFromFile(g_pD3DDevice,L"purple.png",&g_pTexture[4]);
	D3DXCreateTextureFromFile(g_pD3DDevice,L"Grey.png",&g_pTexture[5]);

这里我加载了6张纹理图片.

然后有个地方要改下:

//网格绘制
	for (int i=0;i<g_NumSubsets;i++)
	{
		g_pD3DDevice->SetTexture(0,g_pTexture[i]);
		g_pMesh->DrawSubset(i);
	}

这个前面也讲过,要对哪个物体绘制纹理,就在那个物体之前用SetTexture();来绘制;

效果图


对上面的总结。

1.用D3DXCreateMeshFVF()来创建一个空网格。

2.填充网格的顶点信息。

3.访问属性缓存LockAttributeBuffer()和UnlockAttributeBuffer();

4.网格优化(看需求一般都要,可以不要)

5.绘制纹理(看需求,可以不要)

6.绘制。


由于时间关系博主没详细介绍各个方法和结构,想了解的可以参考《DIRECTX.9.0.3D游戏开发编程基础》:网格(一)的内容或者看看浅墨的博客http://blog.csdn.net/zhmxy555/article/category/1091031/2,写的很好。




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值