如何将变量添加到constantbuffer

问题描述:

我工作的支持DirectX C++/CX(通用的Windows)项目。如何将变量添加到constantbuffer

我不是所有的方式,熟悉的DirectX11。

我的代码主要是基于与在UWP使用swapchainpanels渲染的DirectX MSDN上的样本项目。

现在我想一个float变量添加着色器。我相信这必须使用常量缓冲区来完成。目前这如下(和作品):

//c++: 
struct ModelViewProjectionConstantBuffer 
{ 
    DirectX::XMFLOAT4X4 model; 
    DirectX::XMFLOAT4X4 view; 
    DirectX::XMFLOAT4X4 projection; 
    //float distance; 
}; 

//hlsl: 
cbuffer ModelViewProjectionConstantBuffer : register(b0) 
{ 
    matrix model; 
    matrix view; 
    matrix projection; 
    //float distance; 
}; 

现在,当我添加一个浮动,它停止工作。它抛出当我更新的常量缓冲区(每个渲染帧之前恰好)一个例外:

_d3dContext->UpdateSubresource(
    _constantBuffer.Get(), 
    0, 
    NULL, 
    &_constantBufferData, 
    0, 
    0 
); 

唯一的例外是SEHException(所以只要我能找到,这并没有告诉我任何东西)。

我立足这一切以下页面: https://msdn.microsoft.com/en-us/library/ff476896(v=vs.85).aspx

谁能告诉我什么,我做错了什么?其实在16个字节

恒缓冲区大小都一致,当你不得不在最后一个单精度浮点数,你用16抬高不断缓冲区的大小,但在代码方面,你的结构只有4.什么是发生膨胀UpdateSubResource尝试读取这12个额外的字节并产生内存访问冲突。

你应该能够加入这样的

struct ModelViewProjectionConstantBuffer 
{ 
    DirectX::XMFLOAT4X4 model; 
    DirectX::XMFLOAT4X4 view; 
    DirectX::XMFLOAT4X4 projection; 
    float distance; 
    float pad[3] 
}; 

填充你可以在这里阅读有关填充规则有关详细信息,解决的事情:https://msdn.microsoft.com/en-us/library/windows/desktop/bb509632(v=vs.85).aspx

+0

如果你的推理是正确的,这是核心问题,那么使用'XMFLOAT4X4A'代替'XMFLOAT4X4'将会更容易和更安全。因此填充不再是必需的。 – IInspectable

+0

@IInspectable不是真的,有些规则是更微妙的,不能用C++语言重现,即使在OP的情况下,它会做的伎俩。另一种解决方案是将代码对象的大小提供给'UpdateSubResource',但是然后调试层将洪泛日志,并发出一个警告,即您上传的内容小于cbuffer大小(在我们的例子中为100%安全)。 – galop1n

+0

谢谢,是的,修复它。我意识到现在他们正在试图在这些msdn页面上发表意见(但我觉得他们可能已经更清楚了)。 如果异常包含任何有用的信息,它也将是有用的。 :| – Stef