public void Allocate_ReadBackTexture3D_Copy_Range(Device device, int x, int y, int z, int width, int height, int depth) { int[,,] source = new int[16, 256, 256]; for (int i = 0; i < 16; i++) { for (int j = 0; j < 256; j++) { new Random(i * 5381 + j).NextBytes(source.AsSpan2D(i).GetRowSpan(j).AsBytes()); } } using ReadOnlyTexture3D <int> readOnlyTexture3D = device.Get().AllocateReadOnlyTexture3D(source); using ReadBackTexture3D <int> readBackTexture3D = device.Get().AllocateReadBackTexture3D <int>(256, 256, 16); readOnlyTexture3D.CopyTo(readBackTexture3D, x, y, z, width, height, depth); for (int i = 0; i < depth; i++) { for (int j = 0; j < height; j++) { Span <int> sourceRow = source.AsSpan2D(i + z).GetRowSpan(j + y).Slice(x, width); Span <int> destinationRow = readBackTexture3D.View.GetRowSpan(j, i).Slice(0, width); Assert.IsTrue(sourceRow.SequenceEqual(destinationRow)); } } }
public void Allocate_ReadBackTexture3D_Copy_Full(Device device) { int[,,] source = new int[16, 256, 256]; for (int i = 0; i < 16; i++) { for (int j = 0; j < 256; j++) { new Random(i * 5381 + j).NextBytes(source.AsSpan2D(i).GetRowSpan(j).AsBytes()); } } using ReadOnlyTexture3D <int> readOnlyTexture3D = device.Get().AllocateReadOnlyTexture3D(source); using ReadBackTexture3D <int> readBackTexture3D = device.Get().AllocateReadBackTexture3D <int>(256, 256, 16); readOnlyTexture3D.CopyTo(readBackTexture3D); Assert.AreEqual(readBackTexture3D.Width, 256); Assert.AreEqual(readBackTexture3D.Height, 256); Assert.AreEqual(readBackTexture3D.Depth, 16); for (int i = 0; i < readBackTexture3D.Depth; i++) { for (int j = 0; j < readBackTexture3D.Height; j++) { Span <int> sourceRow = source.AsSpan2D(i).GetRowSpan(j); Span <int> destinationRow = readBackTexture3D.View.GetRowSpan(j, i); Assert.IsTrue(sourceRow.SequenceEqual(destinationRow)); } } }
public unsafe void Allocate_ReadBackTexture3D_Copy_Range(Device device, int x, int y, int z, int width, int height, int depth) { int[,,] source = new int[16, 256, 256]; fixed(int *p = source) { new Random(42).NextBytes(new Span <int>(p, source.Length).AsBytes()); } using ReadOnlyTexture3D <int> readOnlyTexture3D = device.Get().AllocateReadOnlyTexture3D(source); using ReadBackTexture3D <int> readBackTexture3D = device.Get().AllocateReadBackTexture3D <int>(256, 256, 16); readOnlyTexture3D.CopyTo(readBackTexture3D, x, y, z, width, height, depth); fixed(int *p = source) { for (int i = 0; i < depth; i++) { for (int j = 0; j < height; j++) { Span <int> sourceRow = new Span <int>(Unsafe.AsPointer(ref source[i + z, j + y, 0]), source.GetLength(2)).Slice(x, width); Span <int> destinationRow = readBackTexture3D.View.GetRowSpan(j, i).Slice(0, width); Assert.IsTrue(sourceRow.SequenceEqual(destinationRow)); } } } }
public unsafe void Allocate_ReadBackTexture3D_Copy_Full(Device device) { int[,,] source = new int[16, 256, 256]; fixed(int *p = source) { new Random(42).NextBytes(new Span <int>(p, source.Length).AsBytes()); } using ReadOnlyTexture3D <int> readOnlyTexture3D = device.Get().AllocateReadOnlyTexture3D(source); using ReadBackTexture3D <int> readBackTexture3D = device.Get().AllocateReadBackTexture3D <int>(256, 256, 16); readOnlyTexture3D.CopyTo(readBackTexture3D); Assert.AreEqual(readBackTexture3D.Width, 256); Assert.AreEqual(readBackTexture3D.Height, 256); Assert.AreEqual(readBackTexture3D.Depth, 16); fixed(int *p = source) { for (int i = 0; i < readBackTexture3D.Depth; i++) { for (int j = 0; j < readBackTexture3D.Height; j++) { Span <int> sourceRow = new(Unsafe.AsPointer(ref source[i, j, 0]), source.GetLength(2)); Span <int> destinationRow = readBackTexture3D.View.GetRowSpan(j, i); Assert.IsTrue(sourceRow.SequenceEqual(destinationRow)); } } } }
/// <summary> /// Reads the contents of the specified range from the current <see cref="Texture3D{T}"/> instance and writes them into a <see cref="ReadBackTexture3D{T}"/> instance. /// </summary> /// <param name="destination">The target <see cref="ReadBackTexture3D{T}"/> instance to write data to.</param> /// <param name="destinationX">The horizontal offset within <paramref name="destination"/>.</param> /// <param name="destinationY">The vertical offset within <paramref name="destination"/>.</param> /// <param name="destinationZ">The depthwise offset within <paramref name="destination"/>.</param> /// <param name="sourceX">The horizontal offset in the source texture.</param> /// <param name="sourceY">The vertical offset in the source texture.</param> /// <param name="sourceZ">The depthwise offset in the source texture.</param> /// <param name="width">The width of the memory area to copy.</param> /// <param name="height">The height of the memory area to copy.</param> /// <param name="depth">The depth of the memory area to copy.</param> internal void CopyTo(ReadBackTexture3D <T> destination, int destinationX, int destinationY, int destinationZ, int sourceX, int sourceY, int sourceZ, int width, int height, int depth) { GraphicsDevice.ThrowIfDisposed(); ThrowIfDisposed(); destination.ThrowIfDeviceMismatch(GraphicsDevice); destination.ThrowIfDisposed(); Guard.IsInRange(destinationX, 0, destination.Width, nameof(destinationX)); Guard.IsInRange(destinationY, 0, destination.Height, nameof(destinationY)); Guard.IsInRange(destinationZ, 0, destination.Depth, nameof(destinationZ)); Guard.IsInRange(sourceX, 0, Width, nameof(sourceX)); Guard.IsInRange(sourceY, 0, Height, nameof(sourceY)); Guard.IsInRange(sourceZ, 0, Depth, nameof(sourceZ)); Guard.IsBetweenOrEqualTo(width, 1, Width, nameof(width)); Guard.IsBetweenOrEqualTo(height, 1, Height, nameof(height)); Guard.IsBetweenOrEqualTo(depth, 1, Depth, nameof(depth)); Guard.IsBetweenOrEqualTo(width, 1, destination.Width, nameof(width)); Guard.IsBetweenOrEqualTo(height, 1, destination.Height, nameof(height)); Guard.IsBetweenOrEqualTo(depth, 1, destination.Depth, nameof(depth)); Guard.IsBetweenOrEqualTo(destinationX + width, 1, destination.Width, nameof(destinationX)); Guard.IsBetweenOrEqualTo(destinationY + height, 1, destination.Height, nameof(destinationY)); Guard.IsBetweenOrEqualTo(destinationZ + depth, 1, destination.Depth, nameof(destinationZ)); Guard.IsLessThanOrEqualTo(sourceX + width, Width, nameof(sourceX)); Guard.IsLessThanOrEqualTo(sourceY + height, Height, nameof(sourceY)); Guard.IsLessThanOrEqualTo(sourceZ + depth, Depth, nameof(sourceZ)); using CommandList copyCommandList = new(GraphicsDevice, this.d3D12CommandListType); if (copyCommandList.D3D12CommandListType == D3D12_COMMAND_LIST_TYPE_COMPUTE) { copyCommandList.D3D12GraphicsCommandList->ResourceBarrier(D3D12Resource, this.d3D12ResourceState, D3D12_RESOURCE_STATE_COPY_SOURCE); } fixed(D3D12_PLACED_SUBRESOURCE_FOOTPRINT *d3D12PlacedSubresourceFootprintDestination = &destination.D3D12PlacedSubresourceFootprint) { copyCommandList.D3D12GraphicsCommandList->CopyTextureRegion( d3D12ResourceDestination: destination.D3D12Resource, d3D12PlacedSubresourceFootprintDestination, (uint)destinationX, (uint)destinationY, (ushort)destinationZ, d3D12ResourceSource: D3D12Resource, (uint)sourceX, (uint)sourceY, (ushort)sourceZ, (uint)width, (uint)height, (ushort)depth); } if (copyCommandList.D3D12CommandListType == D3D12_COMMAND_LIST_TYPE_COMPUTE) { copyCommandList.D3D12GraphicsCommandList->ResourceBarrier(D3D12Resource, D3D12_RESOURCE_STATE_COPY_SOURCE, this.d3D12ResourceState); } copyCommandList.ExecuteAndWaitForCompletion(); }
/// <summary> /// Reads the contents of a <see cref="Texture3D{T}"/> instance and writes them into a target <see cref="ReadBackTexture3D{T}"/> instance. /// </summary> /// <typeparam name="T">The type of items stored on the texture.</typeparam> /// <param name="source">The input <see cref="Texture3D{T}"/> instance to read data from.</param> /// <param name="destination">The target <see cref="ReadBackTexture3D{T}"/> instance to write data to.</param> /// <param name="sourceOffsetX">The horizontal offset in the source texture.</param> /// <param name="sourceOffsetY">The vertical offset in the source texture.</param> /// <param name="sourceOffsetZ">The depthwise offset in the source texture.</param> /// <param name="destinationOffsetX">The horizontal offset in the destination texture.</param> /// <param name="destinationOffsetY">The vertical offset in the destination texture.</param> /// <param name="destinationOffsetZ">The depthwise offset in the destination texture.</param> /// <param name="width">The width of the memory area to copy.</param> /// <param name="height">The height of the memory area to copy.</param> /// <param name="depth">The depth of the memory area to copy.</param> public static void CopyTo <T>(this Texture3D <T> source, ReadBackTexture3D <T> destination, int sourceOffsetX, int sourceOffsetY, int sourceOffsetZ, int destinationOffsetX, int destinationOffsetY, int destinationOffsetZ, int width, int height, int depth) where T : unmanaged { Guard.IsNotNull(source); Guard.IsNotNull(destination); source.CopyTo(destination, sourceOffsetX, sourceOffsetY, sourceOffsetZ, destinationOffsetX, destinationOffsetY, destinationOffsetZ, width, height, depth); }
/// <summary> /// Reads the contents of a <see cref="Texture3D{T}"/> instance and writes them into a target <see cref="ReadBackTexture3D{T}"/> instance. /// </summary> /// <typeparam name="T">The type of items stored on the texture.</typeparam> /// <param name="source">The input <see cref="Texture3D{T}"/> instance to read data from.</param> /// <param name="destination">The target <see cref="ReadBackTexture3D{T}"/> instance to write data to.</param> public static void CopyTo <T>(this Texture3D <T> source, ReadBackTexture3D <T> destination) where T : unmanaged { Guard.IsNotNull(source); Guard.IsNotNull(destination); source.CopyTo(destination, 0, 0, 0, 0, 0, 0, source.Width, source.Height, source.Depth); }
/// <summary> /// Reads the contents of a <see cref="Texture3D{T}"/> instance and writes them into a target <see cref="ReadBackTexture3D{T}"/> instance. /// </summary> /// <typeparam name="T">The type of items stored on the texture.</typeparam> /// <param name="destination">The target <see cref="ReadBackTexture3D{T}"/> instance to write data to.</param> /// <param name="source">The input <see cref="Texture3D{T}"/> instance to read data from.</param> /// <param name="sourceOffsetX">The horizontal offset in the source texture.</param> /// <param name="sourceOffsetY">The vertical offset in the source texture.</param> /// <param name="sourceOffsetZ">The depthwise offset in the source texture.</param> /// <param name="destinationOffsetX">The horizontal offset in the destination texture.</param> /// <param name="destinationOffsetY">The vertical offset in the destination texture.</param> /// <param name="destinationOffsetZ">The depthwise offset in the destination texture.</param> /// <param name="width">The width of the memory area to copy.</param> /// <param name="height">The height of the memory area to copy.</param> /// <param name="depth">The depth of the memory area to copy.</param> public static void CopyFrom <T>(this ReadBackTexture3D <T> destination, Texture3D <T> source, int sourceOffsetX, int sourceOffsetY, int sourceOffsetZ, int destinationOffsetX, int destinationOffsetY, int destinationOffsetZ, int width, int height, int depth) where T : unmanaged { source.CopyTo(destination, sourceOffsetX, sourceOffsetY, sourceOffsetZ, destinationOffsetX, destinationOffsetY, destinationOffsetZ, width, height, depth); }
/// <summary> /// Reads the contents of a <see cref="Texture3D{T}"/> instance and writes them into a target <see cref="ReadBackTexture3D{T}"/> instance. /// </summary> /// <typeparam name="T">The type of items stored on the texture.</typeparam> /// <param name="destination">The target <see cref="ReadBackTexture3D{T}"/> instance to write data to.</param> /// <param name="source">The input <see cref="Texture3D{T}"/> instance to read data from.</param> public static void CopyFrom <T>(this ReadBackTexture3D <T> destination, Texture3D <T> source) where T : unmanaged { source.CopyTo(destination, 0, 0, 0, 0, 0, 0, source.Width, source.Height, source.Depth); }