/// <inheritdoc cref="Copy(GraphicsTexture, GraphicsBuffer)" /> public void Copy(D3D12GraphicsTexture destination, D3D12GraphicsBuffer source) { ThrowIfNull(destination, nameof(destination)); ThrowIfNull(source, nameof(source)); var device = Device.D3D12Device; var commandList = D3D12GraphicsCommandList; var destinationCpuAccess = destination.CpuAccess; var sourceCpuAccess = source.CpuAccess; var d3d12DestinationResource = destination.D3D12Resource; var d3d12SourceResource = source.D3D12Resource; var d3d12DestinationResourceState = destination.D3D12ResourceState; var d3d12SourceResourceState = source.D3D12ResourceState; BeginCopy(); D3D12_PLACED_SUBRESOURCE_FOOTPRINT sourceFootprint; var destinationDesc = d3d12DestinationResource->GetDesc(); device->GetCopyableFootprints(&destinationDesc, FirstSubresource: 0, NumSubresources: 1, BaseOffset: 0, &sourceFootprint, pNumRows: null, pRowSizeInBytes: null, pTotalBytes: null); var d3d12DestinationTextureCopyLocation = new D3D12_TEXTURE_COPY_LOCATION(d3d12DestinationResource, Sub: 0); var d3d12SourceTextureCopyLocation = new D3D12_TEXTURE_COPY_LOCATION(d3d12SourceResource, in sourceFootprint); commandList->CopyTextureRegion(&d3d12DestinationTextureCopyLocation, DstX: 0, DstY: 0, DstZ: 0, &d3d12SourceTextureCopyLocation, pSrcBox: null); EndCopy(); void BeginCopy() { var resourceBarriers = stackalloc D3D12_RESOURCE_BARRIER[2]; var numResourceBarriers = 0u; if (destinationCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12DestinationResource, stateBefore: d3d12DestinationResourceState, stateAfter: D3D12_RESOURCE_STATE_COPY_DEST ); numResourceBarriers++; } if (sourceCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12SourceResource, stateBefore: d3d12SourceResourceState, stateAfter: D3D12_RESOURCE_STATE_COPY_SOURCE ); numResourceBarriers++; } if (numResourceBarriers != 0) { commandList->ResourceBarrier(numResourceBarriers, resourceBarriers); } } void EndCopy() { var resourceBarriers = stackalloc D3D12_RESOURCE_BARRIER[2]; var numResourceBarriers = 0u; if (sourceCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12SourceResource, stateBefore: D3D12_RESOURCE_STATE_COPY_SOURCE, stateAfter: d3d12SourceResourceState ); numResourceBarriers++; } if (destinationCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12DestinationResource, stateBefore: D3D12_RESOURCE_STATE_COPY_DEST, stateAfter: d3d12DestinationResourceState ); numResourceBarriers++; } if (numResourceBarriers != 0) { commandList->ResourceBarrier(numResourceBarriers, resourceBarriers); } } }
/// <inheritdoc cref="Copy(GraphicsBuffer, GraphicsBuffer)" /> public void Copy(D3D12GraphicsBuffer destination, D3D12GraphicsBuffer source) { ThrowIfNull(destination, nameof(destination)); ThrowIfNull(source, nameof(source)); var commandList = D3D12GraphicsCommandList; var destinationCpuAccess = destination.CpuAccess; var sourceCpuAccess = source.CpuAccess; var d3d12DestinationResource = destination.D3D12Resource; var d3d12SourceResource = source.D3D12Resource; var d3d12DestinationResourceState = destination.D3D12ResourceState; var d3d12SourceResourceState = source.D3D12ResourceState; BeginCopy(); commandList->CopyResource(d3d12DestinationResource, d3d12SourceResource); EndCopy(); void BeginCopy() { var resourceBarriers = stackalloc D3D12_RESOURCE_BARRIER[2]; var numResourceBarriers = 0u; if (destinationCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12DestinationResource, stateBefore: d3d12DestinationResourceState, stateAfter: D3D12_RESOURCE_STATE_COPY_DEST ); numResourceBarriers++; } if (sourceCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12SourceResource, stateBefore: d3d12SourceResourceState, stateAfter: D3D12_RESOURCE_STATE_COPY_SOURCE ); numResourceBarriers++; } if (numResourceBarriers != 0) { commandList->ResourceBarrier(numResourceBarriers, resourceBarriers); } } void EndCopy() { var resourceBarriers = stackalloc D3D12_RESOURCE_BARRIER[2]; var numResourceBarriers = 0u; if (sourceCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12SourceResource, stateBefore: D3D12_RESOURCE_STATE_COPY_SOURCE, stateAfter: d3d12SourceResourceState ); numResourceBarriers++; } if (destinationCpuAccess == GraphicsResourceCpuAccess.None) { resourceBarriers[numResourceBarriers] = D3D12_RESOURCE_BARRIER.InitTransition( d3d12DestinationResource, stateBefore: D3D12_RESOURCE_STATE_COPY_DEST, stateAfter: d3d12DestinationResourceState ); numResourceBarriers++; } if (numResourceBarriers != 0) { commandList->ResourceBarrier(numResourceBarriers, resourceBarriers); } } }