【DirectX 2D游戏编程基础】DirectX环境的搭建

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/shangdi712/article/details/47455311
        首先,我们先回顾下我上个博客,关于手动建立一个win32 窗口的博客,在这里,我再写一遍昨天的代码,并且在这里面加几个函数,关于windows窗口的建立这部分代码,注释我就不写了,只是为了展示我的几个函数所加的位置
        本博客实例代码地址:http://download.csdn.net/detail/shangdi712/9052045
utility.h

//-------Windows头及库文件-------
#ifndef WINDOWS_PLATFORM_
#define WINDOWS_PLATFORM_

#include <Windows.h>
#include <mmsystem.h>
#pragma comment(lib,"Winmm.lib")

#endif

//-------D3D头及库文件-------
#ifndef D3D_USEFUL_H_
#define D3D_USEFUL_H_

#include <d3d9.h>
#pragma comment(lib,"d3d9.lib")
#include <d3dx9.h>
#pragma comment(lib,"d3dx9.lib")

#endif

//-------SAFE_DELETE_----------
#ifndef SAFE_DELETE_T_
#define SAFE_DELETE_T_

template<typename T>inline void Safe_Delete(T* &  p)
{
	if (p){ delete p; p = nullptr; }
}

template<typename T>inline void Safe_Release(T* & p)
{
	if (p){ p->Release(); p = nullptr; }
}

#endif

      这里稍微解释一下utility.h的代码,开始先引入window.h mmsystem.h两个头文件,和Winmm.lib 这个库的作用是为了生成windows窗口所用
      之后引入directx 所需要的库和头文件
      好了,重点来了,后面两个函数模板的作用是用来安全释放的,前一个用来释放普通指针,后一个用来释放directx定义的复杂指针,将安全释放的函数写成模板,之后随调随用,增强了代码的简洁性
      好了,下面就是WinMain中的内容了
     
#include "Utility.h"

HWND g_hWnd = 0;
HINSTANCE g_hInstance = 0;

/*
绘图窗口改造的步骤:
1、包含头文件及库文件,见Utility.h文件
2、声明变量
3、创建D3D接口指针
4、创建D3D设备指针
5、创建Sprite精灵指针
6、改造onRender函数
*/

//COM:组件对象模型

LPDIRECT3D9 g_pD3D = nullptr;			//D3D的接口指针,为了创建设备指针
LPDIRECT3DDEVICE9 g_pDevice = nullptr;	//D3D的设备指针,为了创建精灵指针
LPD3DXSPRITE g_pSprite = nullptr;		//D3D的精灵指针,为了画图


LRESULT CALLBACK WndProc(HWND hWnd ,UINT uMsg,
						 WPARAM wParam,LPARAM lParam);
 
VOID onInit()
{
	//3、创建D3D接口指针
	g_pD3D = Direct3DCreate9(D3D_SDK_VERSION);
	D3DDISPLAYMODE d3ddm;		//D3D显示模式结构体
	ZeroMemory(&d3ddm, sizeof(d3ddm));

	//获取当前显卡的显示模式
	g_pD3D->GetAdapterDisplayMode(
		D3DADAPTER_DEFAULT,		//哪张显卡的显示模式
		&d3ddm);				//获取到的显示模式的存储位置
	
	//4、创建D3D的设备指针
	D3DPRESENT_PARAMETERS d3dpp;	//描述D3D设备的能力
	ZeroMemory(&d3dpp, sizeof(d3dpp));

	d3dpp.BackBufferCount = 1;	//后台缓冲区的个数(双缓冲技术)

	//-----窗口模式的写发-----
	d3dpp.Windowed = TRUE;		//当前窗口是否为"窗口模式"

	////-----全屏模式的写发-----
	//d3dpp.Windowed = FALSE;
	//d3dpp.BackBufferWidth = d3ddm.Width;
	//d3dpp.BackBufferHeight = d3ddm.Height;

	d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;	//翻转效果:抛弃

	//创建设备指针
	g_pD3D->CreateDevice(
		D3DADAPTER_DEFAULT,		//默认显卡
		D3DDEVTYPE_HAL,			//硬件抽象层
		g_hWnd,					//所依附的窗口(要改造的窗口)
		D3DCREATE_SOFTWARE_VERTEXPROCESSING,	//顶点软件处理模式
		&d3dpp,		//设备的能力
		&g_pDevice	//返回的设备指针
		);


	//5、创建精灵指针
	D3DXCreateSprite(
		g_pDevice,		//设备指针
		&g_pSprite);	//返回的精灵指针

}
VOID onLogic(float fElapsedTime)
{

}
VOID onRender(float fElapsedTime)
{
	g_pDevice->Clear(
		0,			//清空矩形的数量
		nullptr,	//清空矩形的临接信息
		D3DCLEAR_TARGET,	//要清空颜色缓冲区
		D3DCOLOR_XRGB(102,204,255),	//清成什么颜色   由于我喜欢洛天依,我每次都清成天依蓝
		1.0f,	//深度缓冲区的初始值
		0		//模板缓冲区的初始值
		);
	g_pDevice->BeginScene();		//获取绘制权限
	//---------------------------------------
	//		渲染代码
	//---------------------------------------
	g_pDevice->EndScene();		//结束绘制
	//前后台缓冲区交换的"源动力"
	g_pDevice->Present(nullptr, nullptr, 0, nullptr);
}
VOID onDestroy()
{
	Safe_Release(g_pSprite);
	Safe_Release(g_pDevice);
	Safe_Release(g_pD3D);
}

INT WINAPI WinMain( __in HINSTANCE hInstance, 
				   __in_opt HINSTANCE hPrevInstance,
				   __in_opt LPSTR lpCmdLine, 
				   __in int nShowCmd )
{
	WNDCLASS wc;
	ZeroMemory(&wc,sizeof(wc));
	wc.cbClsExtra = NULL;
	wc.cbWndExtra = NULL;
	wc.hbrBackground = (HBRUSH)GetStockObject(GRAY_BRUSH);
	wc.hCursor = LoadCursor(0,IDC_ARROW);
	wc.hIcon = LoadIcon(0,IDI_APPLICATION);
	wc.hInstance = hInstance;
	wc.lpfnWndProc = WndProc;
	wc.lpszClassName = TEXT("Alibaba");
	wc.lpszMenuName = NULL;
	wc.style = CS_HREDRAW | CS_VREDRAW;

	RegisterClass(&wc);

	g_hWnd = CreateWindow(wc.lpszClassName,
		TEXT("Linimass"),WS_OVERLAPPEDWINDOW,
		50,20,800,600,NULL,NULL,hInstance,NULL);

	if(g_hWnd)
	{
		g_hInstance = hInstance;
		
		onInit();

		ShowWindow(g_hWnd,SW_SHOWNORMAL);
		UpdateWindow(g_hWnd);
	}

	MSG msg;
	ZeroMemory(&msg,sizeof(msg));
	while ( msg.message!=WM_QUIT)
	{
		if(PeekMessage(&msg,NULL,0,0,PM_REMOVE))
		{
			TranslateMessage(&msg);
			DispatchMessage(&msg);
		}
		else
		{
			static DWORD dwTime = timeGetTime();
			DWORD dwCurrentTime = timeGetTime();
			DWORD dwElapsedTime = dwCurrentTime - dwTime;
			float fElapsedTime = dwElapsedTime * 0.001f;
			onLogic(fElapsedTime);
			onRender(fElapsedTime);
			if (dwElapsedTime < 1000 / 60)
				Sleep(1000 / 60 - dwElapsedTime);
			dwTime = dwCurrentTime;
		}
	}
	onDestroy();
	UnregisterClass(wc.lpszClassName, hInstance);
	return 0;
}

LRESULT CALLBACK WndProc(HWND hWnd ,UINT uMsg,
						 WPARAM wParam,LPARAM lParam)
{
	switch(uMsg)
	{
	case WM_KEYDOWN:
		if(wParam == VK_ESCAPE)
			DestroyWindow(hWnd);
		break;
	case WM_CLOSE:
		DestroyWindow(hWnd);
		break;
	case WM_DESTROY:
		PostQuitMessage(0);
		break;
	}
	return DefWindowProc(hWnd,uMsg,wParam,lParam);
}

         但是,问题来了,如果你按照我的代码写,甚至是把整个代码复制进去,运行的时候还是会有错的,如果你用的是高版本的visual stdio的话,估计在导入d3dx9.h的时候就会有一个红色的波浪线挥之不去,为什么呢,当然是没有安装directx的SDK啊,安装完directx 的SDK 并且把他导入VS里就可以了,具体步骤如下:
1.安装SDK
      下载SDK,双击,然后一路下一步,然后直到安装完成
2.在VS中导入库和包含文件
打开vs 然后在你的项目上右击属性,会进入属性界面,左侧点击VC++目录,如图,
在包含文件和库文件位置分别作相应设置,首先是包含文件,点击向下小箭头,然后再点编辑,会出现如下界面
点击上方新建文件夹那个黄黄的图标,地下框里会出现一行可编辑区域,右侧有一个方框里面有三个点,就点那个方框然后选择directx所在位置,默认情况下
64位所在位置:C:\Program Files (x86)\Microsoft DirectX SDK (June 2008)\Include
32位所在位置:C:\Program Files \Microsoft DirectX SDK (June 2008)\Include
把Include这个文件夹包含进来就可以了,
库文件相同道理,库文件所在位置
64位系统所在位置:C:\Program Files (x86)\Microsoft DirectX SDK (June 2008)\Lib\x86
32位系统所在位置:C:\Program Files \Microsoft DirectX SDK (June 2008)\Lib\x86

然后确定确定,大功告成,然后你就会发现d3dx9.h下面那个阴魂不散的小红波浪线没有了,但是,在一些个别情况,还有这样的错误


1>c:\program files (x86)\windows kits\8.1\include\um\propidl.h(1304): error C2061: 语法错误: 标识符“__RPC__inout_xcount”
1>c:\program files (x86)\windows kits\8.1\include\um\propidl.h(1305): error C2061: 语法错误: 标识符“__RPC__in_xcount”

没错,就是这货,可讨厌了,这个问题怎么解决呢
好办,首先,让我们打开刚才包含文件那个名叫Include的文件夹,然后在里面找到名为rpcsal.h的文件,打开它,然后随便找个合适的位置输入以下几行代码:
在Rpcsal.h中添加cxyc预编译指令
#define __RPC__out_xcount_part(size,length)
#define __RPC__in_xcount(size)
#define __RPC__in_xcount_full(size)
#define __RPC__in_range(min,max)
#define __RPC__inout_xcount(size)
然后保存,如果系统说你没有权限,那你就先另存为到桌面上,然后复制进去,替换就好,这回可是真真的没有问题了
运行结果如下
对,就是一个窗口,看起来,跟原版windows窗口只有颜色不一样,然而,除此之外,这个窗口是3D的,可以渲染3D图形。

      总之,这篇博客上的direct的内容很基础,我之后还会再写一篇关于direct的文章,也很基础,逻辑上很简单,但是要记忆的东西比较多



猜你喜欢

转载自blog.csdn.net/shangdi712/article/details/47455311