private T Reduce <T>(UploadBuffer data, ReduceShader shader) where T : struct { Console.WriteLine("num groups: " + Utility.DivideRoundUp(data.ByteSize / 4, ReduceShader.ElementsPerGroup)); using (var buf = new GpuBuffer(4, data.ByteSize / 4)) { buf.CopyFrom(data); using (var timer = new GpuTimer()) { timer.Start(); //for(int i = 0; i < 100; ++i) shader.Run(buf, data.ByteSize / 4); timer.Stop(); Console.WriteLine(timer.GetDelta()); } using (var res = new DownloadBuffer(4)) { res.CopyFrom(buf, Marshal.SizeOf <T>()); var resData = res.GetData <T>(); return(resData); } } }
public void Run(UploadBuffer buffer, Matrix transform, Vector4 crop, float multiplier, bool useAbs, ShaderResourceView texture, SamplerState sampler, int xaxis = 0, int yaxis = 1, int zvalue = 0) { buffer.SetData(new ViewBufferData { Transform = transform, Crop = crop, Multiplier = multiplier, UseAbs = useAbs?1:0, XAxis = xaxis, YAxis = yaxis, ZValue = zvalue }); var dev = Device.Get(); BindShader(dev); dev.Vertex.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetShaderResource(0, texture); dev.Pixel.SetSampler(0, sampler); dev.DrawQuad(); // unbind dev.Pixel.SetShaderResource(0, null); UnbindShader(dev); }
// executes a 3x3 gauss kernel on the given texture mipmap public void Run(ITexture texSrc, ITexture texDst, int mipmap, bool hasAlpha, UploadBuffer upload) { Debug.Assert(texSrc.NumLayers == texDst.NumLayers); Debug.Assert(texSrc.NumMipmaps == texDst.NumMipmaps); Debug.Assert(texSrc.Size == texDst.Size); var dev = Device.Get(); dev.Compute.Set(texSrc.Is3D ? Shader3D.Compute : Shader.Compute); var builder = texSrc.Is3D ? ShaderBuilder.Builder3D : ShaderBuilder.Builder2D; var data = new BufferData { Size = texSrc.Size.GetMip(mipmap), HasAlpha = hasAlpha?1:0, }; foreach (var lm in texSrc.LayerMipmap.LayersOfMipmap(mipmap)) { data.Layer = lm.Layer; upload.SetData(data); dev.Compute.SetConstantBuffer(0, upload.Handle); dev.Compute.SetShaderResource(0, texSrc.GetSrView(lm)); dev.Compute.SetUnorderedAccessView(0, texDst.GetUaView(mipmap)); dev.Dispatch( Utility.Utility.DivideRoundUp(data.Size.Width, builder.LocalSizeX), Utility.Utility.DivideRoundUp(data.Size.Height, builder.LocalSizeY), Utility.Utility.DivideRoundUp(data.Size.Depth, builder.LocalSizeZ) ); } dev.Compute.SetShaderResource(0, null); dev.Compute.SetUnorderedAccessView(0, null); }
public SharedModel() { Upload = new UploadBuffer(256); // big enough for 4 matrix4 Download = new DownloadBuffer(256); ScaleShader = new MitchellNetravaliScaleShader(QuadShader, Upload); Convert = new ConvertFormatShader(QuadShader, Upload); }
public BoxOverlay(Models models) { this.images = models.Images; this.cbuffer = models.SharedModel.Upload; Boxes.CollectionChanged += BoxesOnCollectionChanged; images.PropertyChanged += ImagesOnPropertyChanged; }
/// <summary> /// copies the values of the +4th mipmap into the specified mipmap /// </summary> /// <param name="tex"></param> /// <param name="lm">dst layer/mipmap</param> /// <param name="upload"></param> public void RunCopy(ITexture tex, LayerMipmapSlice lm, UploadBuffer upload) { var size = tex.Size.GetMip(lm.SingleMipmap); var nMipmaps = tex.NumMipmaps - lm.Mipmap; if (nMipmaps == 1) { return; // already finished } upload.SetData(new BufferData { Layer = lm.SingleLayer, Size = size }); var dev = Device.Get(); var builder = tex.Is3D ? ShaderBuilder.Builder3D : ShaderBuilder.Builder2D; dev.Compute.Set(tex.Is3D ? CopyShader3D.Compute : CopyShader.Compute); dev.Compute.SetConstantBuffer(0, upload.Handle); dev.Compute.SetSampler(0, sampler); dev.Compute.SetUnorderedAccessView(0, tex.GetUaView(lm.Mipmap)); dev.Compute.SetShaderResource(0, tex.GetSrView(lm.AddMipmap(Math.Min(4, nMipmaps - 1)))); dev.Dispatch( Utility.Utility.DivideRoundUp(size.X, builder.LocalSizeX), Utility.Utility.DivideRoundUp(size.Y, builder.LocalSizeY), Utility.Utility.DivideRoundUp(size.Z, builder.LocalSizeZ) ); dev.Compute.SetShaderResource(0, null); dev.Compute.SetUnorderedAccessView(0, null); }
public void Run(UploadBuffer buffer, Matrix transform, float multiplier, float farplane, bool useAbs, ShaderResourceView texture, SamplerState sampler) { buffer.SetData(new ViewBufferData { Transform = transform, Multiplier = multiplier, Farplane = farplane, UseAbs = useAbs ? 1 : 0 }); var dev = Device.Get(); BindShader(dev); dev.Vertex.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetShaderResource(0, texture); dev.Pixel.SetSampler(0, sampler); dev.DrawQuad(); // unbind dev.Pixel.SetShaderResource(0, null); UnbindShader(dev); }
public FrameResource(Device device, int passCount, int objectCount) { CmdListAlloc = device.CreateCommandAllocator(CommandListType.Direct); PassCB = new UploadBuffer <PassConstants>(device, passCount, true); ObjectCB = new UploadBuffer <ObjectConstants>(device, objectCount, true); }
public void SSIMMultiscaleLuminance() { var s = new MultiscaleSSIMShader(); var toRed = new ImageFramework.Model.Shader.TransformShader("return value.r;", "float4", "float"); var fromRed = new ImageFramework.Model.Shader.TransformShader("return float4(value, value, value, 1.0);", "float", "float4"); var tex = IO.LoadImageTexture(TestData.Directory + "checkers.dds"); var redTex = new TextureArray2D(tex.LayerMipmap, tex.Size, Format.R32_Float, true); var dstTex = new TextureArray2D(tex.LayerMipmap, tex.Size, Format.R32G32B32A32_Float, true); var upload = new UploadBuffer(256); Assert.AreEqual(tex.NumMipmaps, 3); var expected = tex.GetPixelColors(LayerMipmapSlice.Mip2)[0]; // copy checkers red channel only foreach (var lm in tex.LayerMipmap.Range) { toRed.Run(tex, redTex, lm, upload); } // this should copy lowest resolution mipmap to first mipmap s.RunCopy(redTex, LayerMipmapSlice.Mip0, upload); // copy back foreach (var lm in tex.LayerMipmap.Range) { fromRed.Run(redTex, dstTex, lm, upload); } var actual = dstTex.GetPixelColors(LayerMipmapSlice.Mip0); foreach (var color in actual) { Assert.IsTrue(color.Equals(expected, Color.Channel.R, 0.0011f)); } }
public void Run(ImagesModel images, UploadBuffer constantBuffer, ITexture target) { var dev = Device.Get(); dev.Compute.Set(shader.Compute); // src images for (int i = 0; i < images.NumImages; ++i) { dev.Compute.SetShaderResource(i, images.Images[i].Image.View); } for (int curMipmap = 0; curMipmap < images.NumMipmaps; ++curMipmap) { var size = images.GetSize(curMipmap); // dst image dev.Compute.SetUnorderedAccessView(0, target.GetUaView(curMipmap)); for (int curLayer = 0; curLayer < images.NumLayers; ++curLayer) { constantBuffer.SetData(new LayerLevelFilter { Layer = curLayer, Level = curMipmap }); dev.Compute.SetConstantBuffer(0, constantBuffer.Handle); dev.Dispatch( Utility.Utility.DivideRoundUp(size.Width, builder.LocalSizeX), Utility.Utility.DivideRoundUp(size.Height, builder.LocalSizeY), Utility.Utility.DivideRoundUp(size.Depth, builder.LocalSizeZ)); } } // remove images from unordered acces view slots (otherwise they can't be bound as srv later) dev.Compute.SetUnorderedAccessView(0, null); }
/// <summary> /// shader used for statistics calculation /// </summary> /// <param name="returnValue">one of the values declared above this function (*Value)</param> public StatisticsShader(UploadBuffer upload, string returnValue) { this.returnValue = returnValue; cbuffer = upload; shader = new DirectX.Shader(DirectX.Shader.Type.Compute, GetSource(ShaderBuilder.Builder2D), "StatisticsShader"); shader3d = new DirectX.Shader(DirectX.Shader.Type.Compute, GetSource(ShaderBuilder.Builder3D), "StatisticsShader"); }
public void TestSmall() { var upload = new UploadBuffer(4 * 4); upload.SetData(new int[] { 1, 2, 3, 4 }); Assert.AreEqual(10, Reduce <int>(upload, new ReduceShader(new UploadBuffer(256), "a+b", "0", "int"))); }
/// <summary> /// Reads the contents of a <see cref="UploadBuffer{T}"/> instance and writes them into a target <see cref="StructuredBuffer{T}"/> instance. /// </summary> /// <typeparam name="T">The type of items stored on the buffer.</typeparam> /// <param name="source">The input <see cref="UploadBuffer{T}"/> instance to read data from.</param> /// <param name="destination">The target <see cref="StructuredBuffer{T}"/> instance to write data to.</param> /// <param name="sourceOffset">The offset to start reading data from.</param> /// <param name="destinationOffset">The starting offset within <paramref name="destination"/> to write data to.</param> /// <param name="count">The number of items to read.</param> public static void CopyTo <T>(this UploadBuffer <T> source, StructuredBuffer <T> destination, int sourceOffset, int destinationOffset, int count) where T : unmanaged { Guard.IsNotNull(source); Guard.IsNotNull(destination); destination.CopyFrom(source, sourceOffset, destinationOffset, count); }
/// <summary> /// Reads the contents of a <see cref="UploadBuffer{T}"/> instance and writes them into a target <see cref="StructuredBuffer{T}"/> instance. /// </summary> /// <typeparam name="T">The type of items stored on the buffer.</typeparam> /// <param name="source">The input <see cref="UploadBuffer{T}"/> instance to read data from.</param> /// <param name="destination">The target <see cref="StructuredBuffer{T}"/> instance to write data to.</param> public static void CopyTo <T>(this UploadBuffer <T> source, StructuredBuffer <T> destination) where T : unmanaged { Guard.IsNotNull(source); Guard.IsNotNull(destination); destination.CopyFrom(source, 0, 0, source.Length); }
public PixelValueShader(SharedModel shared) { shader2D = new DirectX.Shader(DirectX.Shader.Type.Compute, GetSource(ShaderBuilder.Builder2D), "PixelValueShader"); shader3D = new DirectX.Shader(DirectX.Shader.Type.Compute, GetSource(ShaderBuilder.Builder3D), "PixelValueShader"); readBuffer = shared.Download; cbuffer = shared.Upload; dstBuffer = new GpuBuffer(4 * 4, 1); }
public ReduceShader(UploadBuffer upload, string reduceOp = "a+b", string defaultValue = "0.0", string type = "float") { this.type = type; this.reduceOp = reduceOp; this.defaultValue = defaultValue; shader = new DirectX.Shader(DirectX.Shader.Type.Compute, GetSource(), "ReduceShader"); numBuffer = upload; }
public ConvertFormatShader(QuadShader quad, UploadBuffer upload) { var dev = DirectX.Device.Get(); convert2D = new DirectX.Shader(DirectX.Shader.Type.Pixel, GetSource(ShaderBuilder.Builder2D), "ConvertFormatShader2D"); convert3D = new DirectX.Shader(DirectX.Shader.Type.Pixel, GetSource(ShaderBuilder.Builder3D), "ConvertFormatShader3D"); this.quad = quad; cbuffer = upload; }
public void TestNotSoSmallButStillSmall() { var upload = new UploadBuffer(4 * 13); upload.SetData(new int[] { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }); Assert.AreEqual(13, Reduce <int>(upload, new ReduceShader(new UploadBuffer(256), "a+b", "0", "int"))); upload.SetData(new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13 }); Assert.AreEqual(91, Reduce <int>(upload, new ReduceShader(new UploadBuffer(256), "a+b", "0", "int"))); }
public SharedModel() { Upload = new UploadBuffer(256); // big enough for 4 matrix4 Download = new DownloadBuffer(256); ScaleShader = new MitchellNetravaliScaleShader(QuadShader, Upload); Convert = new ConvertFormatShader(QuadShader, Upload); Sync = new SyncQuery(); LinearSampler = CreateSamplerState(true); PointSampler = CreateSamplerState(false); }
internal unsafe void AllocateOneTimeUploadBuffer(int size, out UploadBuffer uploadBuffer) { var bufferCreateInfo = new VkBufferCreateInfo { sType = VkStructureType.BufferCreateInfo, size = (ulong)size, flags = VkBufferCreateFlags.None, usage = VkBufferUsageFlags.TransferSrc, }; uploadBuffer = new UploadBuffer { size = size }; vkCreateBuffer(NativeDevice, &bufferCreateInfo, null, out uploadBuffer.buffer); // figure out the memory type if (properType == uint.MaxValue) { VkMemoryPropertyFlags memoryProperties = VkMemoryPropertyFlags.HostVisible | VkMemoryPropertyFlags.HostCoherent; vkGetBufferMemoryRequirements(nativeDevice, uploadBuffer.buffer, out var memoryRequirements); vkGetPhysicalDeviceMemoryProperties(NativePhysicalDevice, out var physicalDeviceMemoryProperties); var typeBits = memoryRequirements.memoryTypeBits; for (uint i = 0; i < physicalDeviceMemoryProperties.memoryTypeCount; i++) { if ((typeBits & 1) == 1) { // Type is available, does it match user properties? var memoryType = *(&physicalDeviceMemoryProperties.memoryTypes_0 + i); if ((memoryType.propertyFlags & memoryProperties) == memoryProperties) { properType = i; break; } } typeBits >>= 1; } } var allocateInfo = new VkMemoryAllocateInfo { sType = VkStructureType.MemoryAllocateInfo, allocationSize = (ulong)size, memoryTypeIndex = properType }; fixed(VkDeviceMemory *nativeUploadBufferMemoryPtr = &uploadBuffer.memory) vkAllocateMemory(NativeDevice, &allocateInfo, null, nativeUploadBufferMemoryPtr); vkBindBufferMemory(NativeDevice, uploadBuffer.buffer, uploadBuffer.memory, 0); fixed(IntPtr *nativeUploadBufferStartPtr = &uploadBuffer.address) vkMapMemory(NativeDevice, uploadBuffer.memory, 0, (ulong)size, VkMemoryMapFlags.None, (void **)nativeUploadBufferStartPtr); }
public FilterShader(FilterModel parent, string source, int groupSize, FilterLoader.Type kernel, IShaderBuilder builder) { localSize = groupSize; this.parent = parent; is3D = builder.Is3D; shader = new DirectX.Shader(DirectX.Shader.Type.Compute, GetShaderHeader(kernel, builder) + "\n#line 1\n" + source, parent.Filename); if (parent.Parameters.Count != 0) { paramBuffer = new UploadBuffer(4 * parent.Parameters.Count); UpdateParamBuffer(); } }
private void ExecuteDimension(ref BufferData bufferData, UploadBuffer buffer, bool is3D, int dim, Size3 srcSize, ShaderResourceView srcTexture, UnorderedAccessView dstTexture) { // filter x direction bufferData.Dir = new Size3(0, 0, 0) { [dim] = 1 }; bufferData.NumSrcPixelsTotal = srcSize[dim]; var dev = Device.Get(); var iFilterSize = srcSize[dim] / bufferData.DstSize[dim]; if (srcSize[dim] == bufferData.DstSize[dim]) // same size { dev.Compute.Set(is3D ? CopyShader3D.Compute : CopyShader.Compute); // just copy } else if (srcSize[dim] % bufferData.DstSize[dim] == 0 && // integer division possible? !(Odd(iFilterSize) && !Odd(kernelStretch))) // stretch does not result in half samples? { bufferData.NumSrcPixels = iFilterSize; dev.Compute.Set(is3D ? FastShader3D.Compute : FastShader.Compute); } else { bufferData.FilterSize = srcSize[dim] / (float)bufferData.DstSize[dim]; dev.Compute.Set(is3D ? SlowShader3D.Compute : SlowShader.Compute); } // bind stuff buffer.SetData(bufferData); dev.Compute.SetConstantBuffer(0, buffer.Handle); dev.Compute.SetShaderResource(0, srcTexture); dev.Compute.SetUnorderedAccessView(0, dstTexture); BindAdditionalResources(dev); var builder = is3D ? ShaderBuilder.Builder3D : ShaderBuilder.Builder2D; dev.Dispatch( Utility.Utility.DivideRoundUp(bufferData.DstSize.X, builder.LocalSizeX), Utility.Utility.DivideRoundUp(bufferData.DstSize.Y, builder.LocalSizeY), Utility.Utility.DivideRoundUp(bufferData.DstSize.Z, builder.LocalSizeZ) ); // unbind stuff dev.Compute.SetShaderResource(0, null); dev.Compute.SetUnorderedAccessView(0, null); UnbindAdditionalResources(dev); }
private void Dispatch(Int3 direction, int iteration, Size3 size, UploadBuffer uploadBuffer) { var dev = Device.Get(); uploadBuffer.SetData(new DirBufferData { dir = direction, dim = size, iteration = iteration }); dev.Compute.SetConstantBuffer(0, uploadBuffer.Handle); dev.Dispatch(Utility.DivideRoundUp(size.X, workgroupSize.X), Utility.DivideRoundUp(size.Y, workgroupSize.Y), Utility.DivideRoundUp(size.Z, workgroupSize.Z)); }
public void Allocate_UploadBuffer_Copy_Full(Device device) { using UploadBuffer <int> uploadBuffer = device.Get().AllocateUploadBuffer <int>(4096); new Random(42).NextBytes(uploadBuffer.Span.AsBytes()); using ReadOnlyBuffer <int> readOnlyBuffer = device.Get().AllocateReadOnlyBuffer <int>(uploadBuffer.Length); uploadBuffer.CopyTo(readOnlyBuffer); int[] result = readOnlyBuffer.ToArray(); Assert.AreEqual(uploadBuffer.Length, result.Length); Assert.IsTrue(uploadBuffer.Span.SequenceEqual(result)); }
public void Allocate_UploadBuffer_Copy_Range(Device device, int destinationOffset, int bufferOffset, int count) { using UploadBuffer <int> uploadBuffer = device.Get().AllocateUploadBuffer <int>(4096); new Random(42).NextBytes(uploadBuffer.Span.AsBytes()); using ReadOnlyBuffer <int> readOnlyBuffer = device.Get().AllocateReadOnlyBuffer <int>(uploadBuffer.Length); uploadBuffer.CopyTo(readOnlyBuffer, destinationOffset, bufferOffset, count); int[] result = readOnlyBuffer.ToArray(destinationOffset, count); Assert.AreEqual(result.Length, count); Assert.IsTrue(uploadBuffer.Span.Slice(bufferOffset, count).SequenceEqual(result)); }
public void TestMultipleDispatch() { var upload = new UploadBuffer(4 * (ReduceShader.ElementsPerGroup + ReduceShader.ElementsPerGroup / 2 + 1)); var count = upload.ByteSize / 4; var data = new int[count]; for (int i = 0; i < data.Length; ++i) { data[i] = i + 1; } upload.SetData(data); int expected = (count * (count + 1)) / 2; Assert.AreEqual(expected, Reduce <int>(upload, new ReduceShader(new UploadBuffer(256), "a+b", "0", "int"))); }
public void VeryLarge() { // 400 mb of data var upload = new UploadBuffer(4 * 1024 * 1024 * 100); var count = upload.ByteSize / 4; var data = new float[count]; for (int i = 0; i < count; ++i) { data[i] = (float)(i + 1); } upload.SetData(data); float expected = (float)count; Assert.AreEqual(expected, Reduce <float>(upload, new ReduceShader(new UploadBuffer(256), "max(a,b)"))); }
public PipelineController(Models models) { this.models = models; this.models.Images.PropertyChanged += ImagesOnPropertyChanged; foreach (var pipe in models.Pipelines) { pipe.PropertyChanged += (sender, e) => PipelineOnPropertyChanged(pipe, e); pipe.Color.PropertyChanged += (sender, e) => PipelineFormulaOnPropertyChanged(pipe, pipe.Color, e); pipe.Alpha.PropertyChanged += (sender, e) => PipelineFormulaOnPropertyChanged(pipe, pipe.Alpha, e); } layerLevelBuffer = models.SharedModel.Upload; syncQuery = new SyncQuery(); this.models.Filter.PropertyChanged += FilterOnPropertyChanged; this.models.Filter.ParameterChanged += FilterOnParameterChanged; }
public void Run(UploadBuffer buffer, Matrix projection, Matrix model, float multiplier, bool useAbs, ShaderResourceView texture, SamplerState sampler, Size3 imgSize) { // determine which axis should be used for slices var zDir = new Vector4(0.0f, 0.0f, 1.0f, 0.0f); Vector4.Transform(ref zDir, ref model, out var outDir); int fixedAxis = 0; for (int i = 1; i < 3; ++i) { if (Math.Abs(outDir[i]) > Math.Abs(outDir[fixedAxis])) { fixedAxis = i; } } buffer.SetData(new ViewBufferData { Transform = model * projection, UseAbs = useAbs?1:0, Multiplier = multiplier, FixedAxis = fixedAxis, FixedAxisDim = imgSize[fixedAxis], Aspects = new Vector2(imgSize.X / (float)imgSize.Y, imgSize.Z / (float)imgSize.Y) }); // bind resources var dev = Device.Get(); BindShader(dev); dev.Vertex.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetShaderResource(0, texture); dev.Pixel.SetSampler(0, sampler); dev.DrawQuad(imgSize[fixedAxis]); // unbind dev.Pixel.SetShaderResource(0, null); UnbindShader(dev); }
public void Run(UploadBuffer buffer, Matrix transform, SettingsModel.AlphaType background) { buffer.SetData(new BufferData { Transform = transform, ThemeColor = themeColor, Type = (int)background }); var dev = Device.Get(); dev.Vertex.Set(vertex.Vertex); dev.Pixel.Set(pixel.Pixel); dev.Vertex.SetConstantBuffer(0, buffer.Handle); dev.Pixel.SetConstantBuffer(0, buffer.Handle); dev.DrawQuad(); }