Support texture SRVs with swizzle/planeslice parameters on D3D12

This commit is contained in:
baldurk
2018-12-11 19:57:21 +00:00
parent 5e2971a79f
commit ab89b074d2
6 changed files with 111 additions and 46 deletions
+2 -1
View File
@@ -197,7 +197,8 @@ float4 main() : SV_Target0
ID3D12ResourcePtr bb = StartUsingBackbuffer(cmd, D3D12_RESOURCE_STATE_RENDER_TARGET);
D3D12_CPU_DESCRIPTOR_HANDLE rtv = MakeRTV(bb).Format(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB).Create(0);
D3D12_CPU_DESCRIPTOR_HANDLE rtv =
MakeRTV(bb).Format(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB).CreateCPU(0);
ClearRenderTargetView(cmd, rtv, {0.4f, 0.5f, 0.6f, 1.0f});
+80 -35
View File
@@ -370,6 +370,8 @@ D3D12ViewCreator::D3D12ViewCreator(D3D12GraphicsTest *test, ID3D12DescriptorHeap
D3D12_RESOURCE_DESC resdesc = res->GetDesc();
D3D12_RESOURCE_DIMENSION dim = resdesc.Dimension;
Shader4ComponentMapping = D3D12_DEFAULT_SHADER_4_COMPONENT_MAPPING;
if(dim == D3D12_RESOURCE_DIMENSION_BUFFER)
{
SetupDescriptors(viewType, ResourceType::Buffer);
@@ -500,130 +502,130 @@ void D3D12ViewCreator::SetupDescriptors(ViewType viewType, ResourceType resType)
}
}
UINT *pointers[4][8][4] = {
UINT *pointers[4][8][5] = {
// SRV
{
// &firstMip, &numMips, &firstSlice, &numSlices
// &firstMip, &numMips, &firstSlice, &numSlices, &planeSlice
{NULL, NULL, NULL, NULL, NULL},
{
NULL, NULL, NULL, NULL,
},
{
&desc.srv.Texture1D.MostDetailedMip, &desc.srv.Texture1D.MipLevels, NULL, NULL,
&desc.srv.Texture1D.MostDetailedMip, &desc.srv.Texture1D.MipLevels, NULL, NULL, NULL,
},
{
&desc.srv.Texture1DArray.MostDetailedMip, &desc.srv.Texture1DArray.MipLevels,
&desc.srv.Texture1DArray.FirstArraySlice, &desc.srv.Texture1DArray.ArraySize,
&desc.srv.Texture1DArray.FirstArraySlice, &desc.srv.Texture1DArray.ArraySize, NULL,
},
{
&desc.srv.Texture2D.MostDetailedMip, &desc.srv.Texture2D.MipLevels, NULL, NULL,
&desc.srv.Texture2D.PlaneSlice,
},
{
&desc.srv.Texture2DArray.MostDetailedMip, &desc.srv.Texture2DArray.MipLevels,
&desc.srv.Texture2DArray.FirstArraySlice, &desc.srv.Texture2DArray.ArraySize,
&desc.srv.Texture2DArray.PlaneSlice,
},
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
NULL, NULL, &desc.srv.Texture2DMSArray.FirstArraySlice,
&desc.srv.Texture2DMSArray.ArraySize,
&desc.srv.Texture2DMSArray.ArraySize, NULL,
},
{
&desc.srv.Texture3D.MostDetailedMip, &desc.srv.Texture2D.MipLevels, NULL, NULL,
&desc.srv.Texture3D.MostDetailedMip, &desc.srv.Texture2D.MipLevels, NULL, NULL, NULL,
},
},
// RTV
{
// &firstMip, &numMips, &firstSlice, &numSlices
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
&desc.rtv.Texture1D.MipSlice, NULL, NULL, NULL,
&desc.rtv.Texture1D.MipSlice, NULL, NULL, NULL, NULL,
},
{
&desc.rtv.Texture1DArray.MipSlice, NULL, &desc.rtv.Texture1DArray.FirstArraySlice,
&desc.rtv.Texture1DArray.ArraySize,
&desc.rtv.Texture1DArray.ArraySize, NULL,
},
{
&desc.rtv.Texture2D.MipSlice, NULL, NULL, NULL,
&desc.rtv.Texture2D.MipSlice, NULL, NULL, NULL, &desc.rtv.Texture2D.PlaneSlice,
},
{
&desc.rtv.Texture2DArray.MipSlice, NULL, &desc.rtv.Texture2DArray.FirstArraySlice,
&desc.rtv.Texture2DArray.ArraySize,
&desc.rtv.Texture2DArray.ArraySize, &desc.rtv.Texture2DArray.PlaneSlice,
},
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
NULL, NULL, &desc.rtv.Texture2DMSArray.FirstArraySlice,
&desc.rtv.Texture2DMSArray.ArraySize,
&desc.rtv.Texture2DMSArray.ArraySize, NULL,
},
{
&desc.rtv.Texture3D.MipSlice, NULL, &desc.rtv.Texture3D.FirstWSlice,
&desc.rtv.Texture3D.WSize,
&desc.rtv.Texture3D.WSize, NULL,
},
},
// DSV
{
// &firstMip, &numMips, &firstSlice, &numSlices
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
&desc.dsv.Texture1D.MipSlice, NULL, NULL, NULL,
&desc.dsv.Texture1D.MipSlice, NULL, NULL, NULL, NULL,
},
{
&desc.dsv.Texture1DArray.MipSlice, NULL, &desc.dsv.Texture1DArray.FirstArraySlice,
&desc.dsv.Texture1DArray.ArraySize,
&desc.dsv.Texture1DArray.ArraySize, NULL,
},
{
&desc.dsv.Texture2D.MipSlice, NULL, NULL, NULL,
&desc.dsv.Texture2D.MipSlice, NULL, NULL, NULL, NULL,
},
{
&desc.dsv.Texture2DArray.MipSlice, NULL, &desc.dsv.Texture2DArray.FirstArraySlice,
&desc.dsv.Texture2DArray.ArraySize,
&desc.dsv.Texture2DArray.ArraySize, NULL,
},
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
NULL, NULL, &desc.dsv.Texture2DMSArray.FirstArraySlice,
&desc.dsv.Texture2DMSArray.ArraySize,
&desc.dsv.Texture2DMSArray.ArraySize, NULL,
},
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
},
// UAV
{
// &firstMip, &numMips, &firstSlice, &numSlices
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
&desc.uav.Texture1D.MipSlice, NULL, NULL, NULL,
&desc.uav.Texture1D.MipSlice, NULL, NULL, NULL, NULL,
},
{
&desc.uav.Texture1DArray.MipSlice, NULL, &desc.uav.Texture1DArray.FirstArraySlice,
&desc.uav.Texture1DArray.ArraySize,
&desc.uav.Texture1DArray.ArraySize, NULL,
},
{
&desc.uav.Texture2D.MipSlice, NULL, NULL, NULL,
&desc.uav.Texture2D.MipSlice, NULL, NULL, NULL, &desc.uav.Texture2D.PlaneSlice,
},
{
&desc.uav.Texture2DArray.MipSlice, NULL, &desc.uav.Texture2DArray.FirstArraySlice,
&desc.uav.Texture2DArray.ArraySize,
&desc.uav.Texture2DArray.ArraySize, &desc.uav.Texture2DArray.PlaneSlice,
},
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL,
},
{
&desc.uav.Texture3D.MipSlice, NULL, &desc.uav.Texture3D.FirstWSlice,
&desc.uav.Texture3D.WSize,
&desc.uav.Texture3D.WSize, NULL,
},
},
};
@@ -634,6 +636,7 @@ void D3D12ViewCreator::SetupDescriptors(ViewType viewType, ResourceType resType)
numMips = pointers[(int)viewType][(int)resType][1];
firstSlice = pointers[(int)viewType][(int)resType][2];
numSlices = pointers[(int)viewType][(int)resType][3];
planeSlice = pointers[(int)viewType][(int)resType][4];
if(numMips)
*numMips = ~0U;
@@ -723,6 +726,21 @@ D3D12ViewCreator &D3D12ViewCreator::NumSlices(UINT num)
return *this;
}
D3D12ViewCreator &D3D12ViewCreator::Swizzle(UINT swizzle)
{
Shader4ComponentMapping = swizzle;
return *this;
}
D3D12ViewCreator &D3D12ViewCreator::PlaneSlice(UINT plane)
{
if(planeSlice)
*planeSlice = plane;
else
TEST_ERROR("This view & resource doesn't support NumSlices");
return *this;
}
D3D12ViewCreator &D3D12ViewCreator::ReadOnlyDepth()
{
desc.dsv.Flags |= D3D12_DSV_FLAG_READ_ONLY_DEPTH;
@@ -735,7 +753,8 @@ D3D12ViewCreator &D3D12ViewCreator::ReadOnlyStencil()
return *this;
}
D3D12_CPU_DESCRIPTOR_HANDLE D3D12ViewCreator::Create(ID3D12DescriptorHeap *heap, uint32_t descriptor)
D3D12_CPU_DESCRIPTOR_HANDLE D3D12ViewCreator::CreateCPU(ID3D12DescriptorHeap *heap,
uint32_t descriptor)
{
static UINT increment[] = {
m_Test->dev->GetDescriptorHandleIncrementSize(D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV),
@@ -776,6 +795,8 @@ D3D12_CPU_DESCRIPTOR_HANDLE D3D12ViewCreator::Create(ID3D12DescriptorHeap *heap,
desc.srv.Buffer.NumElements = UINT(bufdesc.Width / std::max(elementStride, 1U));
}
desc.srv.Shader4ComponentMapping = Shader4ComponentMapping;
cpu.ptr += increment[D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV] * descriptor;
m_Test->dev->CreateShaderResourceView(m_Res, &desc.srv, cpu);
}
@@ -804,6 +825,30 @@ D3D12_CPU_DESCRIPTOR_HANDLE D3D12ViewCreator::Create(ID3D12DescriptorHeap *heap,
return cpu;
}
D3D12_GPU_DESCRIPTOR_HANDLE D3D12ViewCreator::CreateGPU(ID3D12DescriptorHeap *heap,
uint32_t descriptor)
{
CreateCPU(heap, descriptor);
static UINT increment[] = {
m_Test->dev->GetDescriptorHandleIncrementSize(D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV),
0, // D3D12_DESCRIPTOR_HEAP_TYPE_SAMPLER
m_Test->dev->GetDescriptorHandleIncrementSize(D3D12_DESCRIPTOR_HEAP_TYPE_RTV),
m_Test->dev->GetDescriptorHandleIncrementSize(D3D12_DESCRIPTOR_HEAP_TYPE_DSV),
};
D3D12_GPU_DESCRIPTOR_HANDLE gpu = heap->GetGPUDescriptorHandleForHeapStart();
if(m_Type == ViewType::DSV)
gpu.ptr += increment[D3D12_DESCRIPTOR_HEAP_TYPE_DSV] * descriptor;
else if(m_Type == ViewType::RTV)
gpu.ptr += increment[D3D12_DESCRIPTOR_HEAP_TYPE_RTV] * descriptor;
else
gpu.ptr += increment[D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV] * descriptor;
return gpu;
}
D3D12PSOCreator::D3D12PSOCreator(D3D12GraphicsTest *test) : m_Test(test)
{
GraphicsDesc.RasterizerState.FillMode = D3D12_FILL_MODE_SOLID;
+18 -3
View File
@@ -198,14 +198,26 @@ public:
D3D12ViewCreator &FirstSlice(UINT mip);
D3D12ViewCreator &NumSlices(UINT num);
// TODO plane slice, swizzle, ResourceMinLODClamp
// TODO ResourceMinLODClamp
D3D12ViewCreator &Swizzle(UINT swizzle);
D3D12ViewCreator &PlaneSlice(UINT plane);
// depth stencil only
D3D12ViewCreator &ReadOnlyDepth();
D3D12ViewCreator &ReadOnlyStencil();
D3D12_CPU_DESCRIPTOR_HANDLE Create(ID3D12DescriptorHeap *heap, uint32_t descriptor);
D3D12_CPU_DESCRIPTOR_HANDLE Create(uint32_t descriptor) { return Create(m_Heap, descriptor); }
D3D12_CPU_DESCRIPTOR_HANDLE CreateCPU(ID3D12DescriptorHeap *heap, uint32_t descriptor);
D3D12_GPU_DESCRIPTOR_HANDLE CreateGPU(ID3D12DescriptorHeap *heap, uint32_t descriptor);
D3D12_CPU_DESCRIPTOR_HANDLE CreateCPU(uint32_t descriptor)
{
return CreateCPU(m_Heap, descriptor);
}
D3D12_GPU_DESCRIPTOR_HANDLE CreateGPU(uint32_t descriptor)
{
return CreateGPU(m_Heap, descriptor);
}
private:
void SetupDescriptors(ViewType viewType, ResourceType resType);
@@ -227,8 +239,11 @@ private:
D3D12_UNORDERED_ACCESS_VIEW_DESC uav;
} desc;
UINT Shader4ComponentMapping;
UINT64 *firstElement = NULL;
UINT *numElements = NULL;
UINT *planeSlice = NULL;
UINT *firstMip = NULL, *numMips = NULL;
UINT *firstSlice = NULL, *numSlices = NULL;
};
+3 -2
View File
@@ -147,7 +147,8 @@ struct D3D12_Overlay_Test : D3D12GraphicsTest
ID3D12ResourcePtr bb = StartUsingBackbuffer(cmd, D3D12_RESOURCE_STATE_RENDER_TARGET);
D3D12_CPU_DESCRIPTOR_HANDLE rtv = MakeRTV(bb).Format(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB).Create(0);
D3D12_CPU_DESCRIPTOR_HANDLE rtv =
MakeRTV(bb).Format(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB).CreateCPU(0);
cmd->IASetPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
@@ -158,7 +159,7 @@ struct D3D12_Overlay_Test : D3D12GraphicsTest
cmd, {10.0f, 10.0f, (float)screenWidth - 20.0f, (float)screenHeight - 20.0f, 0.0f, 1.0f});
RSSetScissorRect(cmd, {0, 0, screenWidth, screenHeight});
OMSetRenderTargets(cmd, {rtv}, MakeDSV(dsv).Create(0));
OMSetRenderTargets(cmd, {rtv}, MakeDSV(dsv).CreateCPU(0));
ClearRenderTargetView(cmd, rtv, {0.4f, 0.5f, 0.6f, 1.0f});
ClearDepthStencilView(cmd, dsv, D3D12_CLEAR_FLAG_DEPTH | D3D12_CLEAR_FLAG_STENCIL, 1.0f, 0);
@@ -55,7 +55,8 @@ struct D3D12_Simple_Triangle : D3D12GraphicsTest
ID3D12ResourcePtr bb = StartUsingBackbuffer(cmd, D3D12_RESOURCE_STATE_RENDER_TARGET);
D3D12_CPU_DESCRIPTOR_HANDLE rtv = MakeRTV(bb).Format(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB).Create(0);
D3D12_CPU_DESCRIPTOR_HANDLE rtv =
MakeRTV(bb).Format(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB).CreateCPU(0);
ClearRenderTargetView(cmd, rtv, {0.4f, 0.5f, 0.6f, 1.0f});
+6 -4
View File
@@ -214,6 +214,8 @@ bool D3D12GraphicsTest::Init(int argc, char **argv)
m_DSV->SetName(L"DSV heap");
desc.Flags = D3D12_DESCRIPTOR_HEAP_FLAG_SHADER_VISIBLE;
desc.NumDescriptors = 8;
desc.Type = D3D12_DESCRIPTOR_HEAP_TYPE_SAMPLER;
@@ -669,7 +671,7 @@ void D3D12GraphicsTest::IASetVertexBuffer(ID3D12GraphicsCommandListPtr cmd, ID3D
void D3D12GraphicsTest::ClearRenderTargetView(ID3D12GraphicsCommandListPtr cmd,
ID3D12ResourcePtr rt, Vec4f col)
{
cmd->ClearRenderTargetView(MakeRTV(rt).Create(0), &col.x, 0, NULL);
cmd->ClearRenderTargetView(MakeRTV(rt).CreateCPU(0), &col.x, 0, NULL);
}
void D3D12GraphicsTest::ClearRenderTargetView(ID3D12GraphicsCommandListPtr cmd,
@@ -681,7 +683,7 @@ void D3D12GraphicsTest::ClearRenderTargetView(ID3D12GraphicsCommandListPtr cmd,
void D3D12GraphicsTest::ClearDepthStencilView(ID3D12GraphicsCommandListPtr cmd, ID3D12ResourcePtr dsv,
D3D12_CLEAR_FLAGS flags, float depth, UINT8 stencil)
{
MakeDSV(dsv).Create(0);
MakeDSV(dsv).CreateCPU(0);
cmd->ClearDepthStencilView(m_DSV->GetCPUDescriptorHandleForHeapStart(), flags, depth, stencil, 0,
NULL);
}
@@ -703,10 +705,10 @@ void D3D12GraphicsTest::OMSetRenderTargets(ID3D12GraphicsCommandListPtr cmd,
std::vector<D3D12_CPU_DESCRIPTOR_HANDLE> handles;
handles.resize(rtvs.size());
for(size_t i = 0; i < rtvs.size(); i++)
handles[i] = MakeRTV(rtvs[i]).Create((uint32_t)i);
handles[i] = MakeRTV(rtvs[i]).CreateCPU((uint32_t)i);
if(dsv)
OMSetRenderTargets(cmd, handles, MakeDSV(dsv).Create(0));
OMSetRenderTargets(cmd, handles, MakeDSV(dsv).CreateCPU(0));
else
OMSetRenderTargets(cmd, handles, {});
}