14 assert(device !=
nullptr);
16 device->GetImmediateContext(m_deviceContext.GetAddressOf());
18 ConfigureFromBufferType(type);
23 D3D11_USAGE usage, UINT bindFlags, UINT cpuAccessFlags)
26 m_bindFlags(bindFlags),
27 m_cpuAccessFlags(cpuAccessFlags)
29 assert(device !=
nullptr);
31 device->GetImmediateContext(m_deviceContext.GetAddressOf());
37 m_device(std::move(other.m_device)),
38 m_deviceContext(std::move(other.m_deviceContext)),
39 m_buffer(std::move(other.m_buffer)),
40 m_usage(other.m_usage),
41 m_bindFlags(other.m_bindFlags),
42 m_cpuAccessFlags(other.m_cpuAccessFlags),
43 m_mappedResource(other.m_mappedResource)
45 other.m_mappedResource = {};
53 BufferBase::operator=(std::move(other));
54 m_device = std::move(other.m_device);
55 m_deviceContext = std::move(other.m_deviceContext);
56 m_buffer = std::move(other.m_buffer);
57 m_usage = other.m_usage;
58 m_bindFlags = other.m_bindFlags;
59 m_cpuAccessFlags = other.m_cpuAccessFlags;
60 m_mappedResource = other.m_mappedResource;
62 other.m_mappedResource = {};
72void DirectX11Buffer::ConfigureFromBufferType(
BufferType type)
76 m_usage = D3D11_USAGE_DEFAULT;
77 m_bindFlags = D3D11_BIND_VERTEX_BUFFER;
82 m_usage = D3D11_USAGE_DEFAULT;
83 m_bindFlags = D3D11_BIND_INDEX_BUFFER;
88 m_usage = D3D11_USAGE_DEFAULT;
89 m_bindFlags = D3D11_BIND_CONSTANT_BUFFER;
94 m_usage = D3D11_USAGE_DYNAMIC;
95 m_bindFlags = D3D11_BIND_SHADER_RESOURCE;
96 m_cpuAccessFlags = D3D11_CPU_ACCESS_WRITE;
101D3D11_BUFFER_DESC DirectX11Buffer::CreateBufferDesc()
const
103 D3D11_BUFFER_DESC desc = {};
104 desc.ByteWidth =
static_cast<UINT
>(
Size);
105 desc.Usage = m_usage;
106 desc.BindFlags = m_bindFlags;
107 desc.CPUAccessFlags = m_cpuAccessFlags;
109 desc.StructureByteStride = 0;
119 if (!m_device ||
Size == 0)
125 D3D11_SUBRESOURCE_DATA resource;
126 resource.pSysMem = data;
128 auto desc = CreateBufferDesc();
129 HRESULT hr = m_device->CreateBuffer(&desc, data !=
nullptr ? &resource :
nullptr, m_buffer.GetAddressOf());
132 SLEAK_ERROR(
"Failed to create DirectX11 buffer! HRESULT: 0x{:08X}",
static_cast<unsigned int>(hr));
146 m_deviceContext->IASetVertexBuffers(
Slot, 1, m_buffer.GetAddressOf(), &stride, &offset);
149 m_deviceContext->IASetIndexBuffer(m_buffer.Get(),DXGI_FORMAT_R32_UINT,0);
152 m_deviceContext->VSSetConstantBuffers(
Slot,1,m_buffer.GetAddressOf());
153 m_deviceContext->PSSetConstantBuffers(
Slot,1,m_buffer.GetAddressOf());
175 if (!m_buffer || !m_deviceContext ||
bIsMapped)
178 D3D11_MAP mapType = (m_cpuAccessFlags & D3D11_CPU_ACCESS_READ)
180 : (m_usage == D3D11_USAGE_DYNAMIC ? D3D11_MAP_WRITE_DISCARD : D3D11_MAP_WRITE);
182 HRESULT hr = m_deviceContext->Map(m_buffer.Get(), 0, mapType, 0, &m_mappedResource);
185 SLEAK_ERROR(
"Failed to map DirectX11 buffer! HRESULT: 0x{:08X}",
static_cast<unsigned int>(hr));
189 Data = m_mappedResource.pData;
196 if (m_buffer && m_deviceContext &&
bIsMapped) {
197 m_deviceContext->Unmap(m_buffer.Get(), 0);
205 if (!m_buffer || !m_deviceContext || size >
Size || !data)
213 if (m_cpuAccessFlags != 0) {
218 memcpy(
Data, data, size);
223 m_deviceContext->UpdateSubresource(m_buffer.Get(), 0,
nullptr, data, 0, 0);
229 if (!m_buffer || !m_deviceContext) {
235 if (m_cpuAccessFlags & D3D11_CPU_ACCESS_READ) {
248 D3D11_BUFFER_DESC stagingDesc = {};
249 stagingDesc.ByteWidth =
static_cast<UINT
>(
Size);
250 stagingDesc.Usage = D3D11_USAGE_STAGING;
251 stagingDesc.BindFlags = 0;
252 stagingDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ;
253 stagingDesc.MiscFlags = 0;
254 stagingDesc.StructureByteStride = 0;
257 Microsoft::WRL::ComPtr<ID3D11Buffer> stagingBuffer;
259 m_device->CreateBuffer(&stagingDesc,
nullptr, &stagingBuffer);
261 SLEAK_ERROR(
"Failed to create staging buffer! HRESULT: 0x{:08X}",
262 static_cast<unsigned int>(hr));
267 m_deviceContext->CopyResource(stagingBuffer.Get(), m_buffer.Get());
270 D3D11_MAPPED_SUBRESOURCE mappedResource;
271 hr = m_deviceContext->Map(stagingBuffer.Get(), 0, D3D11_MAP_READ, 0,
274 SLEAK_ERROR(
"Failed to map staging buffer! HRESULT: 0x{:08X}",
275 static_cast<unsigned int>(hr));
280 void* data = malloc(
Size);
282 SLEAK_ERROR(
"Failed to allocate memory for buffer data!");
283 m_deviceContext->Unmap(stagingBuffer.Get(), 0);
288 memcpy(data, mappedResource.pData,
Size);
291 m_deviceContext->Unmap(stagingBuffer.Get(), 0);
Backend-agnostic GPU buffer: vertex, index, constant, or resource view target.
void StoreCPUShadowCopy(const void *data, size_t size)
Copies up to 128 bytes into the inline shadow-copy storage, clamping oversized input.
void * GetData() override
Returns CPU-visible data directly for readable buffers, or round-trips GPU-only buffers through a sta...
bool Map() override
Maps the buffer for CPU writes (dynamic usage only).
DirectX11Buffer & operator=(const DirectX11Buffer &)=delete
DirectX11Buffer(ID3D11Device *device, size_t size, BufferType type)
Derives usage/bind/CPU-access flags from the buffer type via ConfigureFromBufferType.
bool Initialize(void *Data) override
Creates the D3D11 buffer resource and uploads initial data, if any.
~DirectX11Buffer() override
Backend-facing rendering layer shared by the four graphics backends.
BufferType
GPU buffer usage kind, drives backend binding flags and layout.
Root namespace for everything the engine exposes.