DirectX9 CreateDevice 在 C 中失败,但在 C++ 中成功

Posted

技术标签:

【中文标题】DirectX9 CreateDevice 在 C 中失败,但在 C++ 中成功【英文标题】:DirectX9 CreateDevice fails in C, but succeds in C++ 【发布时间】:2020-12-11 15:22:40 【问题描述】:

我在 C 中创建了一个 d3d9 应用程序,但是当尝试创建一个设备对象时,它在 C 中失败,但它在 C++ 中的对应项可以正常工作并返回 S_OK。 C:

isOk = pD3D->lpVtbl->CreateDevice(pD3D, D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, d3dpParams.hDeviceWindow, D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpParams, &lpDevice);

C++:

isOk = pD3D->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, d3dpParams.hDeviceWindow, D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpParams, &lpDevice);

我的猜测在于 D3DPRESENT_PARAMETERS d3dpParams 在 C++ 中,它使用“= ”进行初始化:

D3DPRESENT_PARAMETERS d3dpParams = ;
d3dpParams.Windowed = false;
d3dpParams.SwapEffect = D3DSWAPEFFECT_DISCARD;
...

在 C 中你只能写“;”:

D3DPRESENT_PARAMETERS d3dpParams;
d3dpParams.Windowed = false;
d3dpParams.SwapEffect = D3DSWAPEFFECT_DISCARD;
...

*pD3D 是由 Direct3DCreate9() 创建的 IDirect3D9*,如果我理解正确,它不会失败。

它最初是用 gcc 完成的,但 msvc 给出的结果完全相同。

【问题讨论】:

= 的 C 等效项是 memset 它的全零字节。试试看。 使用D3DPRESENT_PARAMETERS d3dpParams = 0; 所以我的猜测是正确的,确实有效,我不知道 会将内存归零。 【参考方案1】:

普通 C 结构的 = 初始化只会将内存归零。

Microsoft 在https://docs.microsoft.com/en-us/windows/win32/direct3d9/creating-a-device 的示例为此推荐ZeroMemory

D3DPRESENT_PARAMETERS d3dpp; 

ZeroMemory( &d3dpp, sizeof(d3dpp) );

【讨论】:

【参考方案2】:

C 版本不起作用的根本原因是:

D3DPRESENT_PARAMETERS d3dpParams;

创建一个名为d3dpParams 的未初始化变量。由于它是未初始化的,因此各个成员设置为的任何垃圾数据都将被CreateDevice 函数读取,从而导致不稳定的行为。你在 C++ 中也会遇到同样的问题,所以这并不是真正的 C 与 C++ 的问题。

由于问题是初始化问题之一,因此 C++ 代码通过使用 语法将结构中的所有元素设置为 0 来进行初始化。

由于C没有这样的语法来初始化一个变量,你需要将所有成员设置为0。函数ZeroMemorymemset 和类似的C 函数可用于执行此操作。

ZeroMemory(&d3dpParams, sizeof(d3dpParams));

【讨论】:

【参考方案3】:

C++ 中的零初始化器是:

D3DPRESENT_PARAMETERS d3dpParams = ;

C 中的等价初始化器是:

D3DPRESENT_PARAMETERS d3dpParams = 0;

您不必致电ZeroMemorymemset。请注意,对于符合标准的 C 编译器,C++ 版本将生成编译器警告,因为 C 中不允许使用空的初始值设定项。这就是需要“0”的原因。

【讨论】:

以上是关于DirectX9 CreateDevice 在 C 中失败,但在 C++ 中成功的主要内容,如果未能解决你的问题,请参考以下文章

动画精灵问题 (C++/DirectX9)

DirectX9.0或7以上的在哪下载啊

来自全窗口游戏的 C++ DirectX CreateDevice

D3D->CreateDevice() 在注入的 DLL 中失败

使用 org.bluez.Adapter.CreateDevice 连接到 BT LE 设备失败并出现 org.bluez.Error.Failed:操作取消错误

在 DirectX9 中更改分辨率