Direct3D 9的介绍以及Demo演示

1、d3d9的介绍

Direct3D 9(简称 D3D9)是 Microsoft 提供的一种 API,用于在 Windows 操作系统上进行 3D 图形渲染。它是 DirectX 套件的一部分,被广泛应用于游戏开发和其他需要图形渲染的应用程序。以下是对 D3D9 的详细解释:

1. 概述

D3D9 提供了一组 API,允许开发者使用 C++ 编写高性能的 3D 应用程序。通过 D3D9,可以直接访问图形硬件(GPU),以实现复杂的图形效果和高效的渲染。

2. 核心概念

Direct3D 对象:

  • IDirect3D9D3D9 的核心对象,所有的 D3D9 操作都从这个对象开始。你可以使用 Direct3DCreate9 函数来创建这个对象。

设备对象:

  • IDirect3DDevice9 是渲染的核心,它代表了与图形硬件的一个连接。你可以通过 IDirect3D9::CreateDevice 函数来创建设备对象。

交换链:

  • 交换链(Swap Chain)负责管理渲染缓冲区(Back Buffer),并将其呈现到显示器上。IDirect3DSwapChain9 接口表示一个交换链。

顶点缓冲区和索引缓冲区:

  • 顶点缓冲区(Vertex Buffer)和索引缓冲区(Index Buffer)分别存储顶点数据和顶点索引数据,用于描述几何图形。

纹理:

  • 纹理(Texture)是应用于几何图形表面的图像。IDirect3DTexture9 接口表示一个 2D 纹理。

着色器:

  • 着色器(Shader)是用于在 GPU 上运行的小程序,可以控制顶点处理和像素处理。D3D9 支持 HLSL(高阶着色语言)。

3. 初始化和渲染流程

初始化 Direct3D

#include <d3d9.h>

// 初始化 Direct3D 对象
LPDIRECT3D9 d3d = Direct3DCreate9(D3D_SDK_VERSION);

if (d3d == NULL) {
   
    // 错误处理
    return;
}

// 设置设备参数
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory(&d3dpp, sizeof(d3dpp));
d3dpp.Windowed = TRUE; // 窗口模式
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD; // 交换效果
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN; // 后备缓冲区格式

// 创建 Direct3D 设备
LPDIRECT3DDEVICE9 d3ddev;
if (FAILED(d3d->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
                             D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp, &d3ddev))) {
   
    // 错误处理
    d3d->Release();
    return;
}
// 清空缓冲区
d3ddev->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 40, 100), 1.0f, 0);

// 开始渲染
d3ddev->BeginScene();

// 渲染代码
// ...

// 结束渲染
d3ddev->EndScene();

// 显示渲染结果
d3ddev->Present(NULL, NULL, NULL, NULL);

释放资源:

d3ddev->Release();
d3d->Release();

4. 常见用法

渲染三角形:

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

#define CUSTOMFVF (D3DFVF_XYZ | D3DFVF_DIFFUSE)

// 创建顶点缓冲区
LPDIRECT3DVERTEXBUFFER9 v_buffer;
d3ddev->CreateVertexBuffer(3 * sizeof(CUSTOMVERTEX),
                           0,
                           CUSTOMFVF,
                           D3DPOOL_MANAGED,
                           &v_buffer,
                           NULL);

// 定义顶点数据
CUSTOMVERTEX vertices[] = {
   
    {
    0.0f, 1.0f, 0.0f, D3DCOLOR_XRGB(255, 0, 0) },
    {
    1.0f, -1.0f, 0.0f, D3DCOLOR_XRGB(0, 255, 0) },
    {
    -1.0f, -1.0f, 0.0f, D3DCOLOR_XRGB(0, 0, 255) },
};

// 填充顶点缓冲区
void* pVoid;
v_buffer->Lock(0, 0, (void**)&pVoid, 0);
memcpy(pVoid, vertices, sizeof(vertices));
v_buffer->Unlock();

// 渲染顶点缓冲区
d3ddev->SetFVF(CUSTOMFVF);
d3ddev->SetStreamSource(0, v_buffer, 0, sizeof(CUSTOMVERTEX));
d3ddev->DrawPrimitive(D3DPT_TRIANGLELIST, 0, 1);

5. 先进特性

光照和材质:

  • D3D9 支持多种光照模型(如点光源、平行光源)和材质属性,可以实现逼真的光影效果。

着色器和效果:

  • 通过使用 HLSL 编写自定义的顶点着色器和像素着色器,可以实现复杂的图形效果。

多线程渲染:

  • D3D9 提供了一些多线程支持,允许在多个线程中执行图形命令,提高渲染效率。

6. 总结

D3D9 是一个功能强大的图形 API,通过它,你可以创建各种复杂的 3D 图形效果和高性能的图形应用程序。希望这些详细的解释和代码示例能帮助你更好地理解和使用 D3D9。

2、d3d9demo详解

  • 以下是对这段代码的详细解释。这段代码主要实现了一个 Direct3D 9 的应用程序框架,使用 DXUT 框架来管理 Direct3D 设备和窗口。代码还集成了一个名为 IGW 的组件,用于登录和支付功能。

代码如下:

//--------------------------------------------------------------------------------------
// File: EmptyProject.cpp
//
// Empty starting point for new Direct3D applications
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//--------------------------------------------------------------------------------------
#include "dxstdafx.h"
#include "resource.h"
#include <xstring>

#include "interface.h"

#include "DXUTgui.h"
#include "Oleauto.h"
#include "comutil.h"
#include <time.h>
//#pragma comment(lib, "comsupp.lib")

#include "SDOA4Client.h"
#include "SDOADx9.h"

/* 接入相关全局变量  */
HINSTANCE          g_hInstIGWDll = 0;
LPigwInitialize    igwInitialize = NULL;
LPigwGetModule     igwGetModule = NULL;
LPigwTerminal      igwTerminal = NULL;

ISDOADx9*			g_SDOADx9 = NULL;
ISDOAApp3*			g_SDOAApp = NULL;
ISDOLLogin4*		g_SDOLogin = NULL;
ISDOAAppUtils*		g_SDOAAppUtils = NULL;
ISDOAClientService* g_SDOAClientService = NULL;


extern HMODULE LoadModuleEx(LPCWSTR lpszPath);

/* 释放IGW */
void CloseIGW()
{
   
	if (g_SDOADx9)
	{
   
		g_SDOADx9->Release();
		g_SDOADx9 = NULL;
	}

	if (g_SDOAApp)
	{
   
		g_SDOAApp->Release();
		g_SDOAApp = NULL;
	}

	if (g_SDOAAppUtils)
	{
   
		g_SDOAAppUtils->Release();
		g_SDOAAppUtils = NULL;
	}

	if (g_SDOAClientService)
	{
   
		g_SDOAClientService->Release();
		g_SDOAClientService = NULL;
	}

	if(g_SDOLogin)
	{
   
		g_SDOLogin->Release();
		g_SDOLogin = NULL;
	}

	if (igwTerminal)
	{
     // 释放DLL前总是先调用igwTerminal
		igwTerminal();
		igwTerminal = NULL;
	}
	if (g_hInstIGWDll)
	{
   
		FreeLibrary(g_hInstIGWDll);
		g_hInstIGWDll = 0;
	}
	igwInitialize = NULL;
}

/* 加载IGW */
void OpenIGW()
{
   
	WCHAR strExePath[MAX_PATH] = {
   0};
	WCHAR strExeName[MAX_PATH] = {
   0};
	WCHAR* strLastSlash = NULL;
	GetModuleFileNameW( NULL, strExePath, MAX_PATH );
	strExePath[MAX_PATH-1]=0;
	strLastSlash = wcsrchr( strExePath, TEXT('\\') );
	if( strLastSlash )
	{
   	// 得到EXE所在路径
		StringCchCopyW( strExeName, MAX_PATH, &strLastSlash[1] );
		*strLastSlash = 0;
		strLastSlash = wcsrchr( strExeName, TEXT('.') );
		if( strLastSlash )
			*strLastSlash = 0;
	}

	WCHAR strGameWidgetDll[MAX_PATH] = {
   0};
#ifdef _WIN64
	StringCchPrintfW( strGameWidgetDll, MAX_PATH, L"%s\\sdo\\sdologinentry64.dll", strExePath );
#else
	StringCchPrintfW( strGameWidgetDll, MAX_PATH, L"%s\\sdo\\sdologinentry.dll", strExePath );
#endif
// 	if ( !(GetFileAttributesW(strGameWidgetDll) != 0xFFFFFFFF) ) {
   
// 		StringCchPrintfW( strGameWidgetDll, MAX_PATH, L"%s\\GameWidget.dll", strExePath );
// 	};
/*
	if ( !(GetFileAttributesW(strGameWidgetDll) != 0xFFFFFFFF) )
	{ // 如果程序运行路径中不存在则换个路径再试
		StringCchPrintfW( strGameWidgetDll, MAX_PATH, L"%s\\..\\..\\..\\..\\bin\\GameWidget.dll", strExePath );
	}

	if ( !(GetFileAttributesW(strGameWidgetDll) != 0xFFFFFFFF) )
	{ // 如果程序运行路径中不存在则换个路径再试
		StringCchPrintfW( strGameWidgetDll, MAX_PATH, L"E:\\Worke\\Ez\\IGP\\demo&prototype\\allsnap\\bin\\GameWidget.dll" );
	}
*/

	CloseIGW();

	if ( GetFileAttributesW(strGameWidgetDll) != 0xFFFFFFFF )
	{
   	// 找到组件则加载	
		g_hInstIGWDll = LoadModuleEx(strGameWidgetDll);
		if (g_hInstIGWDll)
		{
   
			igwInitialize = (LPigwInitialize)GetProcAddress( g_hInstIGWDll, "igwInitialize" );
			igwGetModule = (LPigwGetModule)GetProcAddress( g_hInstIGWDll, "igwGetModule" );
			igwTerminal = (LPigwTerminal)GetProcAddress( g_hInstIGWDll, "igwTerminal" );
			if ( igwInitialize && igwGetModule && igwTerminal)
			{
   
				// 加载成功

				// 调试方便,可从配置中读取
				int appId = 88;
				FILE* f = fopen("./appid.txt", "r");
				if (f != NULL) {
   
					char value[1024] = {
   0};
					if (fgets(value, 1024, f)) {
   
						appId = atoi(value);
					};
					fclose(f);
				};

				// 注意AppInfo类型所有字段必须填
				AppInfo tmpAppInfo = {
   
					sizeof(AppInfo),       // 结构体大小,方便扩展
					appId,                 // 接入应用ID,从开发者网站中申请
					L"龙潭虎穴OnLine",     // 应用名称
					L"0.1.2.0",            // 应用客户端当前版本号
					SDOA_RENDERTYPE_D3D9,  // 客户端支持的图形引擎类型,这里同时支持d3d9和d3d8
					1,                     // 可同时在一台机器上游戏的最大人数(通常为1,例如:KOF应该是2)
					1,                    // 游戏区ID,不可用时传入-1
					1                     // 游戏组ID,不可用时传入-1
				};

				if (igwInitialize(SDOA_SDK_VERSION, &tmpAppInfo) == SDOA_OK)
				{
   	// 初始化组件成功

					// 获取组件接口					
					igwGetModule(__uuidof(ISDOADx9), (void**)&g_SDOADx9);
					igwGetModule(__uuidof(ISDOAApp3), (void**)&g_SDOAApp);
					igwGetModule(__uuidof(ISDOAAppUtils), (void**)&g_SDOAAppUtils);
					igwGetModule(__uuidof(ISDOAClientService), (void**)&g_SDOAClientService);					
					igwGetModule(__uuidof(ISDOLLogin4), (void**)&g_SDOLogin);

					if ( (!g_SDOADx9) || (!g_SDOAApp) || (!g_SDOAAppUtils) || (!g_SDOAClientService))
						CloseIGW();

				}
				else // 初始化失败清除环境
					CloseIGW();
			}
			else  // 加载DLL失败清除环境
				CloseIGW();
		}
	}
	
	
}

#define IDC_BUTTON_SHOWLOGINDIALOG 1
#define IDC_BUTTON_DOLOGIN 2
#define IDC_BUTTON_LOGOUT 3
#define IDC_BUTTON_CODEPAY 4
#define IDC_BUTTON_CODEPAY2 5

#define IDC_STATIC_LOG 100

#define LOG_LINE_COUNT 5
#define LOG_LINE_HEIGHT 20

void Trace(LPCWSTR format, ...);

BOOL onSDOLogin = false;
BOOL isSDOLogin = false; // 注意一定要是BOOL类型,不能为bool否则可能会导致问题
LoginResult loginResult;

/* 显示SDOLogin登录窗口 */
void Logout()
{
   
	if (g_SDOLogin)
	{
   
		int code = g_SDOLogin->Logout();
		Trace(L"ISDOLLoginEx::Logout result[%d]\n", code);
	}
}

void DoLogin()
{
   
	if(g_SDOLogin)
	{
   
		int code = g_SDOLogin->DoLogin();
		
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

森明帮大于黑虎帮

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值