为什么我的常量缓冲区没有更新?

Why is my constant buffer not being updated?

波纹管是缓冲区的 cpu 边声明我遇到了问题:

struct PSMaterialTransform {
        float Alpha;
        bool WrapUV;
        XMFLOAT2 padding;
    } static m_PSMaterialTransformDesc;

下面是缓冲区的 gpu 端声明:

cbuffer MaterialTransform: register(b1) {
float Alpha;
bool WrapUV;
float2 padding;
};

这就是我创建所有常量缓冲区的方式:

template<typename T>
bool Seraph::ShaderManager<T>::Create(ID3D11Device* pDevice) {
D3D11_BUFFER_DESC bd;
ZeroMemory(&bd, sizeof(D3D11_BUFFER_DESC));

bd.ByteWidth = sizeof(T);
bd.Usage = D3D11_USAGE_DYNAMIC;
bd.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
bd.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;

hr = pDevice->CreateBuffer(&bd, nullptr, &m_pBuffer);
if (FAILED(hr))
    return Log("Failed to create constant buffer.");
return true;
}

最后,这是我用来更新常量缓冲区的代码:

template<typename T>
bool Seraph::ShaderManager<T>::SetPS(ID3D11DeviceContext* pDeviceContext, T& Data, int ID) {
D3D11_MAPPED_SUBRESOURCE ms;
ZeroMemory(&ms, sizeof(D3D11_MAPPED_SUBRESOURCE));

hr = pDeviceContext->Map(m_pBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &ms);
if (FAILED(hr))
    return Log("Failed to update constant buffer.");

*(T*)ms.pData = Data;

pDeviceContext->Unmap(m_pBuffer, 0);
pDeviceContext->PSSetConstantBuffers(ID, 1, &m_pBuffer);

return true;
}

变量ID代表声明buffer的slot,我已经检查了3次ID对于MaterialTransform是1,但无所谓我发送到 gpu 的值,布尔值 WrapUV 总是 TRUE,即使浮点数 Alpha 似乎正常更新。

HLSL 中 bool 的大小是 4 个字节,所以你的 CPU 结构应该是这样的

struct PSMaterialTransform 
{
        float Alpha;
        int32_t WrapUV; //or uint32_t
        XMFLOAT2 padding;
} 

如果需要,您可以像这样使用 typedef/using 别名:

typedef int32_t bool32; //or
using bool32 = int32_t;

那你可以写成bool32 WrapUV;