public void CreateShaderResources() { // Create the output resource. The dimensions and format should match the swap-chain ResourceDescription resDesc = new ResourceDescription(); resDesc.DepthOrArraySize = 1; resDesc.Dimension = ResourceDimension.Texture2D; resDesc.Format = Format.R8G8B8A8_UNorm; // The backbuffer is actually DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, but sRGB formats can't be used with UAVs. We will convert to sRGB ourselves in the shader resDesc.Flags = ResourceFlags.AllowUnorderedAccess; resDesc.Height = mSwapChainRect.Height; resDesc.Layout = TextureLayout.Unknown; resDesc.MipLevels = 1; resDesc.SampleDescription = new SampleDescription(1, 0); resDesc.Width = mSwapChainRect.Width; mpOutputResource = mpDevice.CreateCommittedResource(AccelerationStructures.kDefaultHeapProps, HeapFlags.None, resDesc, ResourceStates.CopySource, null); // Starting as copy-source to simplify onFrameRender() // Create an SRV/UAV/VertexSRV/IndexSRV descriptor heap. Need 5 entries - 1 SRV for the scene, 1 UAV for the output, 1 SRV for VertexBuffer, 1 SRV for IndexBuffer, 1 SceneContantBuffer, 1 primitiveConstantBuffer mpSrvUavHeap = this.context.CreateDescriptorHeap(mpDevice, 6, DescriptorHeapType.ConstantBufferViewShaderResourceViewUnorderedAccessView, true); // Create the UAV. Based on the root signature we created it should be the first entry UnorderedAccessViewDescription uavDesc = new UnorderedAccessViewDescription(); uavDesc.ViewDimension = UnorderedAccessViewDimension.Texture2D; mpDevice.CreateUnorderedAccessView(mpOutputResource, null, uavDesc, mpSrvUavHeap.GetCPUDescriptorHandleForHeapStart()); // Create the TLAS SRV right after the UAV. Note that we are using a different SRV desc here ShaderResourceViewDescription srvDesc = new ShaderResourceViewDescription(); srvDesc.ViewDimension = ShaderResourceViewDimension.RaytracingAccelerationStructure; srvDesc.Shader4ComponentMapping = D3D12DefaultShader4ComponentMapping; srvDesc.RaytracingAccelerationStructure = new RaytracingAccelerationStructureShaderResourceView(); srvDesc.RaytracingAccelerationStructure.Location = mpTopLevelAS.GPUVirtualAddress; CpuDescriptorHandle srvHandle = mpSrvUavHeap.GetCPUDescriptorHandleForHeapStart(); srvHandle.Ptr += mpDevice.GetDescriptorHandleIncrementSize(DescriptorHeapType.ConstantBufferViewShaderResourceViewUnorderedAccessView); mpDevice.CreateShaderResourceView(null, srvDesc, srvHandle); // Index SRV var indexSRVDesc = new ShaderResourceViewDescription() { ViewDimension = ShaderResourceViewDimension.Buffer, Shader4ComponentMapping = D3D12DefaultShader4ComponentMapping, Format = Format.R32_Typeless, Buffer = { NumElements = (int)(this.acs.IndexCount * 2 / 4), Flags = BufferShaderResourceViewFlags.Raw, StructureByteStride = 0, } }; srvHandle.Ptr += mpDevice.GetDescriptorHandleIncrementSize(DescriptorHeapType.ConstantBufferViewShaderResourceViewUnorderedAccessView); indexSRVHandle = srvHandle; mpDevice.CreateShaderResourceView(this.acs.IndexBuffer, indexSRVDesc, indexSRVHandle); // Vertex SRV var vertexSRVDesc = new ShaderResourceViewDescription() { ViewDimension = ShaderResourceViewDimension.Buffer, Shader4ComponentMapping = D3D12DefaultShader4ComponentMapping, Format = Format.Unknown, Buffer = { NumElements = (int)this.acs.VertexCount, Flags = BufferShaderResourceViewFlags.None, StructureByteStride = Unsafe.SizeOf <VertexPositionNormalTangentTexture>(), } }; srvHandle.Ptr += mpDevice.GetDescriptorHandleIncrementSize(DescriptorHeapType.ConstantBufferViewShaderResourceViewUnorderedAccessView); vertexSRVHandle = srvHandle; mpDevice.CreateShaderResourceView(this.acs.VertexBuffer, vertexSRVDesc, vertexSRVHandle); // CB Scene Vector3 cameraPosition = new Vector3(0, 1, -7); Matrix4x4 view = Matrix4x4.CreateLookAt(cameraPosition, Vector3.Zero, Vector3.UnitY); Matrix4x4 proj = Matrix4x4.CreatePerspectiveFieldOfView(MathHelper.PiOver4, (float)mSwapChainRect.Width / mSwapChainRect.Height, 0.1f, 1000f); Matrix4x4 viewProj = Matrix4x4.Multiply(view, proj); Matrix4x4.Invert(viewProj, out Matrix4x4 projectionToWorld); SceneConstantBuffer sceneConstantBuffer = new SceneConstantBuffer() { projectionToWorld = Matrix4x4.Transpose(projectionToWorld), cameraPosition = cameraPosition, lightPosition = new Vector3(0.0f, 1.0f, -2.0f), lightDiffuseColor = new Vector4(0.5f, 0.5f, 0.5f, 1.0f), lightAmbientColor = new Vector4(0.1f, 0.1f, 0.1f, 1.0f), backgroundColor = new Vector4(0.4f, 0.6f, 0.2f, 1.0f), MaxRecursionDepth = 4, }; sceneCB = this.acs.CreateBuffer(mpDevice, (uint)Unsafe.SizeOf <SceneConstantBuffer>(), ResourceFlags.None, ResourceStates.GenericRead, AccelerationStructures.kUploadHeapProps); IntPtr pData; pData = sceneCB.Map(0, null); Helpers.MemCpy(pData, sceneConstantBuffer, (uint)Unsafe.SizeOf <SceneConstantBuffer>()); sceneCB.Unmap(0, null); var sceneCBV = new ConstantBufferViewDescription() { BufferLocation = sceneCB.GPUVirtualAddress, SizeInBytes = (Unsafe.SizeOf <SceneConstantBuffer>() + 255) & ~255, }; srvHandle.Ptr += mpDevice.GetDescriptorHandleIncrementSize(DescriptorHeapType.ConstantBufferViewShaderResourceViewUnorderedAccessView); sceneCBVHandle = srvHandle; mpDevice.CreateConstantBufferView(sceneCBV, sceneCBVHandle); // CB Primitive PrimitiveConstantBuffer primitiveConstantBuffer = new PrimitiveConstantBuffer() { diffuseColor = new Vector4(0.8f, 0f, 0f, 1.0f), inShadowRadiance = 0.35f, diffuseCoef = 0.1f, specularCoef = 0.7f, specularPower = 50, reflectanceCoef = 0.7f, }; ID3D12Resource primitiveCB = this.acs.CreateBuffer(mpDevice, (uint)Unsafe.SizeOf <PrimitiveConstantBuffer>(), ResourceFlags.None, ResourceStates.GenericRead, AccelerationStructures.kUploadHeapProps); IntPtr pData2; pData2 = primitiveCB.Map(0, null); Helpers.MemCpy(pData2, primitiveConstantBuffer, (uint)Unsafe.SizeOf <PrimitiveConstantBuffer>()); primitiveCB.Unmap(0, null); var primitiveCBV = new ConstantBufferViewDescription() { BufferLocation = primitiveCB.GPUVirtualAddress, SizeInBytes = (Unsafe.SizeOf <PrimitiveConstantBuffer>() + 255) & ~255, }; srvHandle.Ptr += mpDevice.GetDescriptorHandleIncrementSize(DescriptorHeapType.ConstantBufferViewShaderResourceViewUnorderedAccessView); var primitiveCBVHandle = srvHandle; mpDevice.CreateConstantBufferView(primitiveCBV, primitiveCBVHandle); }