public RenderPassObject(string name, Graphics graphics, RenderPassCreateInfo createInfo) { Name = name; Graphics = graphics; CreateInfo = createInfo; RenderPass = Graphics.Device.CreateRenderPass(createInfo); }
private RenderPass CreateRenderPass(SurfaceFormatKhr surfaceFormat) { var attDesc = new AttachmentDescription { Format = surfaceFormat.Format, Samples = SampleCountFlags.Count1, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.ColorAttachmentOptimal, FinalLayout = ImageLayout.ColorAttachmentOptimal }; var attRef = new AttachmentReference { Layout = ImageLayout.ColorAttachmentOptimal }; var subpassDesc = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachments = new [] { attRef } }; var renderPassCreateInfo = new RenderPassCreateInfo { Attachments = new [] { attDesc }, Subpasses = new [] { subpassDesc } }; return(_device.CreateRenderPass(renderPassCreateInfo)); }
protected RenderPass CreateRenderPass(Format imageFormat) { var imageLayout = ImageLayout.ColorAttachmentOptimal; var attachmentDescriptions = new[] { new AttachmentDescription { Format = imageFormat, Samples = SampleCountFlags.SampleCountFlags1, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = imageLayout, FinalLayout = imageLayout }, }; var colorAttachmentReferences = new[] { new AttachmentReference(0, imageLayout) }; var subpassDescriptions = new[] { new SubpassDescription(PipelineBindPoint.Graphics, null, colorAttachmentReferences, null) }; var createInfo = new RenderPassCreateInfo(attachmentDescriptions, subpassDescriptions, null); return(device.CreateRenderPass(createInfo)); }
private RenderPass CreateRenderPass() { var attachments = new[] { new AttachmentDescription { Samples = SampleCounts.Count1, Format = Format.B8G8R8A8UNorm, InitialLayout = ImageLayout.PresentSrcKhr, FinalLayout = ImageLayout.PresentSrcKhr, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare } }; var subpasses = new[] { new SubpassDescription { ColorAttachments = new[] { new AttachmentReference(0, ImageLayout.ColorAttachmentOptimal) } } }; var createInfo = new RenderPassCreateInfo(subpasses, attachments); return(Device.CreateRenderPass(createInfo)); }
private void CreateDefaultSwapchainRenderPass(Device SelectedLogicalGraphicsDevice) { var anAttachmentDescription = new AttachmentDescription { Format = VulkanRenderer.Surface.SelectedSurfaceFormat.Format, Samples = SampleCountFlags.Count1, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.PresentSrcKHR }; var anAttachmentReference = new AttachmentReference { Layout = ImageLayout.ColorAttachmentOptimal }; var aSubpassDescription = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachments = new AttachmentReference[] { anAttachmentReference } }; var aRenderPassCreateInfo = new RenderPassCreateInfo { Attachments = new AttachmentDescription[] { anAttachmentDescription }, Subpasses = new SubpassDescription[] { aSubpassDescription } }; myBaseRenderPass = SelectedLogicalGraphicsDevice.CreateRenderPass(aRenderPassCreateInfo); }
public void CmdDraw() { var renderPassCreateInfo = new RenderPassCreateInfo(new[] { new SubpassDescription( new[] { new AttachmentReference(0, ImageLayout.ColorAttachmentOptimal) }) }, new[] { new AttachmentDescription { Format = Format.B8G8R8A8UNorm, Samples = SampleCounts.Count1 } }); var imageCreateInfo = new ImageCreateInfo { Usage = ImageUsages.ColorAttachment, Format = Format.B8G8R8A8UNorm, Extent = new Extent3D(2, 2, 1), ImageType = ImageType.Image2D, MipLevels = 1, ArrayLayers = 1, Samples = SampleCounts.Count1 }; var imageViewCreateInfo = new ImageViewCreateInfo( Format.B8G8R8A8UNorm, new ImageSubresourceRange(ImageAspects.Color, 0, 1, 0, 1)); using (ShaderModule vertexShader = Device.CreateShaderModule(new ShaderModuleCreateInfo(ReadAllBytes("Shader.vert.spv")))) using (ShaderModule fragmentShader = Device.CreateShaderModule(new ShaderModuleCreateInfo(ReadAllBytes("Shader.frag.spv")))) using (PipelineLayout pipelineLayout = Device.CreatePipelineLayout()) using (RenderPass renderPass = Device.CreateRenderPass(renderPassCreateInfo)) using (Image image = Device.CreateImage(imageCreateInfo)) { MemoryRequirements imageMemReq = image.GetMemoryRequirements(); int memTypeIndex = PhysicalDeviceMemoryProperties.MemoryTypes.IndexOf(imageMemReq.MemoryTypeBits, MemoryProperties.DeviceLocal); using (DeviceMemory imageMemory = Device.AllocateMemory(new MemoryAllocateInfo(imageMemReq.Size, memTypeIndex))) { image.BindMemory(imageMemory); using (ImageView imageView = image.CreateView(imageViewCreateInfo)) using (Framebuffer framebuffer = renderPass.CreateFramebuffer(new FramebufferCreateInfo(new[] { imageView }, 2, 2))) using (Pipeline pipeline = Device.CreateGraphicsPipeline(new GraphicsPipelineCreateInfo( pipelineLayout, renderPass, 0, new[] { new PipelineShaderStageCreateInfo(ShaderStages.Vertex, vertexShader, "main"), new PipelineShaderStageCreateInfo(ShaderStages.Fragment, fragmentShader, "main") }, new PipelineInputAssemblyStateCreateInfo(), new PipelineVertexInputStateCreateInfo(), new PipelineRasterizationStateCreateInfo { RasterizerDiscardEnable = true, LineWidth = 1.0f }))) { CommandBuffer.Begin(); CommandBuffer.CmdBeginRenderPass(new RenderPassBeginInfo(framebuffer, new Rect2D(0, 0, 2, 2))); CommandBuffer.CmdBindPipeline(PipelineBindPoint.Graphics, pipeline); CommandBuffer.CmdDraw(3); CommandBuffer.CmdEndRenderPass(); CommandBuffer.End(); } } } }
public void CreateRenderPass() { var createInfo = new RenderPassCreateInfo( new[] { new SubpassDescription() } ); using (Device.CreateRenderPass(createInfo)) { } using (Device.CreateRenderPass(createInfo, CustomAllocator)) { } }
RenderPass CreateRenderPass(Format imageFormat) { // A `RenderPass` represents a collection of attachments, subpasses, and dependencies // between the subpasses, and describes how the attachments are used over the course of // the subpasses. // Optimal layout when image is only used for color attachment read/write var imageLayout = ImageLayout.ColorAttachmentOptimal; // An `AttachmentDescription` describes the properties of an attachment including its // format, sample count, and how its contents are treated at the beginning and end of // each `RenderPass` instance. var attachmentDescriptions = new[] { new AttachmentDescription { Format = imageFormat, Samples = SampleCountFlags.SampleCountFlags1, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = imageLayout, FinalLayout = imageLayout }, }; // A subpass represents a phase of rendering that reads and writes a subset of the // attachments in a `RenderPass`. Rendering commands are recorded into a particular subpass // of a `RenderPass` instance. // `colorAttachmentReferences` lists which of the `RenderPass`’s attachments will be used // as color attachments in the subpass, and what layout the attachment images will be in // during the subpass. Each element of the array correponds to a fragment shader output // location, i.e. if the shader declared an output variable `layout(location=X)` then it // uses the attachment provided in `colorAttachmentReferences[X]`. var colorAttachmentReferences = new[] { new AttachmentReference(0, imageLayout) }; // A `SubpassDescription` describes the subset of attachments that is involved in the // execution of a subpass. Each subpass can read from some attachments as input attachments, // write to some as color attachments or depth/stencil attachments, and do resolve // operations to others as resolve attachments. A subpass description can also include a // set of preserve attachments, which are attachments that are not read or written by the // subpass but whose contents must be preserved throughout the subpass. var subpassDescriptions = new[] { new SubpassDescription(PipelineBindPoint.Graphics, null, colorAttachmentReferences, null) }; var createInfo = new RenderPassCreateInfo(attachmentDescriptions, subpassDescriptions, null); return(device.CreateRenderPass(createInfo)); }
public void CreateFramebuffer() { var renderPassCreateInfo = new RenderPassCreateInfo( new[] { new SubpassDescription() } ); using (RenderPass renderPass = Device.CreateRenderPass(renderPassCreateInfo)) { var framebufferCreateInfo = new FramebufferCreateInfo(null, 2, 2); using (renderPass.CreateFramebuffer(framebufferCreateInfo)) { } using (renderPass.CreateFramebuffer(framebufferCreateInfo, CustomAllocator)) { } } }
public RenderPass(FrameBuffer myFrameBuffer, SubPass[] mySubpasses = null) { List <AttachmentDescription> GBufferSupportedTypes = new List <AttachmentDescription>(); List <AttachmentReference> attachmentColorReferences = new List <AttachmentReference>(); AttachmentReference myDepthBuffer; SubpassDescription GeometryBufferSubpassDescription = new SubpassDescription() { PipelineBindPoint = PipelineBindPoint.Graphics }; foreach (var Attachment in myFrameBuffer.GetAttachments()) { GBufferSupportedTypes.Add(Attachment.AttachmentDescription); if (Attachment.AttachmentReference.Layout != ImageLayout.DepthStencilAttachmentOptimal) { attachmentColorReferences.Add(Attachment.AttachmentReference); } else { GeometryBufferSubpassDescription.DepthStencilAttachment = Attachment.AttachmentReference; } } GeometryBufferSubpassDescription.ColorAttachments = attachmentColorReferences.ToArray(); //Above is for the Geometry Buffer to intialize. uint starting = 1; uint ending = 2; List <SubpassDependency> myIncomingDependencies = new List <SubpassDependency>(); List <SubpassDescription> mySubpassDescriptions = new List <SubpassDescription>(); if (mySubpasses != null) { for (int i = 0; i < mySubpasses.Length; i++) { myIncomingDependencies.AddRange(mySubpasses[i].GetSubpassDependencies()); mySubpassDescriptions.Add(mySubpasses[i].GetSubpassDescription()); } ; } var aRenderPassCreateInfo = new RenderPassCreateInfo { Attachments = GBufferSupportedTypes.ToArray(), Subpasses = mySubpassDescriptions.ToArray(), Dependencies = myIncomingDependencies.ToArray() }; myFrameBuffer.SetRenderPass(this); CreateRenderPass(aRenderPassCreateInfo); }
private void CreateRenderPass() { var colorAttachment = new AttachmentDescription() { Format = vkSwapChainImageFormat, Samples = SampleCountFlags.Count1, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.PresentSrcKhr, }; var colorAttachmentRef = new AttachmentReference() { Attachment = 0, Layout = Vulkan.ImageLayout.ColorAttachmentOptimal, }; var subpass = new SubpassDescription() { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = 1, ColorAttachments = new AttachmentReference[] { colorAttachmentRef }, }; var dependency = new SubpassDependency() { SrcSubpass = VK_SUBPASS_EXTERNAL, SrcStageMask = PipelineStageFlags.ColorAttachmentOutput, SrcAccessMask = 0, DstSubpass = 0, DstStageMask = PipelineStageFlags.ColorAttachmentOutput, DstAccessMask = AccessFlags.ColorAttachmentRead | AccessFlags.ColorAttachmentWrite, }; var renderPassInfo = new RenderPassCreateInfo() { AttachmentCount = 1, Attachments = new AttachmentDescription[] { colorAttachment }, SubpassCount = 1, Subpasses = new SubpassDescription[] { subpass }, DependencyCount = 1, Dependencies = new SubpassDependency[] { dependency }, }; vkRenderPass = vkDevice.CreateRenderPass(renderPassInfo); }
void CreateRenderPass() { var attachment_descriptions = new AttachmentDescription { flags = (AttachmentDescriptionFlagBits)0, // VkAttachmentDescriptionFlagBits flags format = GetSwapChain.Format, // VkFormat format samples = SampleCountFlagBits._1Bit, // VkSampleCountFlagBits samples loadOperation = AttachmentLoadOperation.Clear, // VkAttachmentLoadOp loadOp storeOperation = AttachmentStoreOperation.Store, // VkAttachmentStoreOp storeOp stencilLoadOperation = AttachmentLoadOperation.DontCare, // VkAttachmentLoadOp stencilLoadOp stencilStoreOperation = AttachmentStoreOperation.DontCare, // VkAttachmentStoreOp stencilStoreOp initialLayout = ImageLayout.Undefined, // VkImageLayout initialLayout; finalLayout = ImageLayout.PresentSourceKhr // VkImageLayout finalLayout }; var color_attachment_references = new AttachmentReference { attachment = 0, // uint32_t attachment layout = ImageLayout.ColorAttachmentOptimal // VkImageLayout layout }; var subpass_descriptions = new SubpassDescription { flags = 0, // VkSubpassDescriptionFlagBits flags pipelineBindPoint = PipelineBindPoint.Graphics, // VkPipelineBindPoint pipelineBindPoint inputAttachmentCount = 0, // uint32_t inputAttachmentCount pInputAttachments = (AttachmentReference *)0, // const VkAttachmentReference *pInputAttachments colorAttachmentCount = 1, // uint32_t colorAttachmentCount pColorAttachments = &color_attachment_references, // const VkAttachmentReference *pColorAttachments pResolveAttachments = (AttachmentReference *)0, // const VkAttachmentReference *pResolveAttachments pDepthStencilAttachment = (AttachmentReference *)0, // const VkAttachmentReference *pDepthStencilAttachment preserveAttachmentCount = 0, // uint32_t preserveAttachmentCount pPreserveAttachments = (uint *)0 // const uint32_t* pPreserveAttachments }; var render_pass_create_info = new RenderPassCreateInfo { sType = StructureType.RenderPassCreateInfo, // VkStructureType sType pNext = IntPtr.Zero, // const void *pNext flags = 0, // VkRenderPassCreateFlagBits flags attachmentCount = 1, // uint32_t attachmentCount pAttachments = &attachment_descriptions, // const VkAttachmentDescription *pAttachments subpassCount = 1, // uint32_t subpassCount pSubpasses = &subpass_descriptions, // const VkSubpassDescription *pSubpasses dependencyCount = 0, // uint32_t dependencyCount pDependencies = (SubpassDependency *)0 // const VkSubpassDependency *pDependencies }; vk.CreateRenderPass(GetDevice, ref render_pass_create_info, (AllocationCallbacks *)0, out Vulkan.RenderPass).CheckError(); }
protected void CreateRenderPass() { var colorAttachment = new AttachmentDescription { Format = format.Format, Samples = SampleCountFlags.Count1, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.PresentSrcKhr }; var colorAttachmentRef = new AttachmentReference { Attachment = 0, Layout = ImageLayout.ColorAttachmentOptimal }; var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = 1, ColorAttachments = new AttachmentReference[] { colorAttachmentRef }, }; var dependency = new SubpassDependency { SrcSubpass = VK_SUBPASS_INTERNAL, DstSubpass = 0, SrcStageMask = PipelineStageFlags.ColorAttachmentOutput, SrcAccessMask = 0, DstStageMask = PipelineStageFlags.ColorAttachmentOutput, DstAccessMask = AccessFlags.ColorAttachmentRead | AccessFlags.ColorAttachmentWrite }; var renderPassInfo = new RenderPassCreateInfo { AttachmentCount = 1, Attachments = new AttachmentDescription[] { colorAttachment }, SubpassCount = 1, Subpasses = new SubpassDescription[] { subpass }, DependencyCount = 1, Dependencies = new SubpassDependency[] { dependency } }; renderPass = device.CreateRenderPass(renderPassInfo); }
private void CreateRenderPass() { var colorAttachmentReference = new AttachmentReference { Attachment = 0, Layout = ImageLayout.ColorAttachmentOptimal }; var depthStencilAttachmentReference = new AttachmentReference { Attachment = 1, Layout = ImageLayout.DepthStencilAttachmentOptimal }; var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = 1, ColorAttachments = new IntPtr(&colorAttachmentReference), }; var attachments = new[] { new AttachmentDescription { Format = backBufferFormat, Samples = SampleCountFlags.Sample1, LoadOperation = AttachmentLoadOperation.Load, StoreOperation = AttachmentStoreOperation.Store, StencilLoadOperation = AttachmentLoadOperation.DontCare, StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.ColorAttachmentOptimal, FinalLayout = ImageLayout.ColorAttachmentOptimal }, }; fixed(AttachmentDescription *attachmentsPointer = &attachments[0]) { var createInfo = new RenderPassCreateInfo { StructureType = StructureType.RenderPassCreateInfo, AttachmentCount = (uint)attachments.Length, Attachments = new IntPtr(attachmentsPointer), SubpassCount = 1, Subpasses = new IntPtr(&subpass) }; renderPass = device.CreateRenderPass(ref createInfo); } }
private unsafe void CreateRenderPass(PipelineStateDescription pipelineStateDescription) { bool hasDepthStencilAttachment = pipelineStateDescription.Output.DepthStencilFormat != PixelFormat.None; var renderTargetCount = pipelineStateDescription.Output.RenderTargetCount; var attachmentCount = renderTargetCount; if (hasDepthStencilAttachment) attachmentCount++; var attachments = new AttachmentDescription[attachmentCount]; var colorAttachmentReferences = new AttachmentReference[renderTargetCount]; fixed (PixelFormat* renderTargetFormat = &pipelineStateDescription.Output.RenderTargetFormat0) fixed (BlendStateRenderTargetDescription* blendDescription = &pipelineStateDescription.BlendState.RenderTarget0) { for (int i = 0; i < renderTargetCount; i++) { var currentBlendDesc = pipelineStateDescription.BlendState.IndependentBlendEnable ? (blendDescription + i) : blendDescription; attachments[i] = new AttachmentDescription { Format = VulkanConvertExtensions.ConvertPixelFormat(*(renderTargetFormat + i)), Samples = SampleCountFlags.Sample1, LoadOperation = currentBlendDesc->BlendEnable ? AttachmentLoadOperation.Load : AttachmentLoadOperation.DontCare, // TODO VULKAN: Only if any destination blend? StoreOperation = AttachmentStoreOperation.Store, StencilLoadOperation = AttachmentLoadOperation.DontCare, StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.ColorAttachmentOptimal, FinalLayout = ImageLayout.ColorAttachmentOptimal, }; colorAttachmentReferences[i] = new AttachmentReference { Attachment = (uint)i, Layout = ImageLayout.ColorAttachmentOptimal, }; } } if (hasDepthStencilAttachment) { attachments[attachmentCount - 1] = new AttachmentDescription { Format = Texture.GetFallbackDepthStencilFormat(GraphicsDevice, VulkanConvertExtensions.ConvertPixelFormat(pipelineStateDescription.Output.DepthStencilFormat)), Samples = SampleCountFlags.Sample1, LoadOperation = AttachmentLoadOperation.Load, // TODO VULKAN: Only if depth read enabled? StoreOperation = AttachmentStoreOperation.Store, // TODO VULKAN: Only if depth write enabled? StencilLoadOperation = AttachmentLoadOperation.DontCare, // TODO VULKAN: Handle stencil StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.DepthStencilAttachmentOptimal, FinalLayout = ImageLayout.DepthStencilAttachmentOptimal, }; } var depthAttachmentReference = new AttachmentReference { Attachment = (uint)attachments.Length - 1, Layout = ImageLayout.DepthStencilAttachmentOptimal, }; var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = (uint)renderTargetCount, ColorAttachments = colorAttachmentReferences.Length > 0 ? new IntPtr(Interop.Fixed(colorAttachmentReferences)) : IntPtr.Zero, DepthStencilAttachment = hasDepthStencilAttachment ? new IntPtr(&depthAttachmentReference) : IntPtr.Zero, }; var renderPassCreateInfo = new RenderPassCreateInfo { StructureType = StructureType.RenderPassCreateInfo, AttachmentCount = (uint)attachmentCount, Attachments = attachments.Length > 0 ? new IntPtr(Interop.Fixed(attachments)) : IntPtr.Zero, SubpassCount = 1, Subpasses = new IntPtr(&subpass) }; NativeRenderPass = GraphicsDevice.NativeDevice.CreateRenderPass(ref renderPassCreateInfo); }
private unsafe void CreateRenderPass(PipelineStateDescription pipelineStateDescription) { bool hasDepthStencilAttachment = pipelineStateDescription.Output.DepthStencilFormat != PixelFormat.None; var renderTargetCount = pipelineStateDescription.Output.RenderTargetCount; var attachmentCount = renderTargetCount; if (hasDepthStencilAttachment) { attachmentCount++; } var attachments = new AttachmentDescription[attachmentCount]; var colorAttachmentReferences = new AttachmentReference[renderTargetCount]; fixed(PixelFormat *renderTargetFormat = &pipelineStateDescription.Output.RenderTargetFormat0) fixed(BlendStateRenderTargetDescription * blendDescription = &pipelineStateDescription.BlendState.RenderTarget0) { for (int i = 0; i < renderTargetCount; i++) { var currentBlendDesc = pipelineStateDescription.BlendState.IndependentBlendEnable ? (blendDescription + i) : blendDescription; attachments[i] = new AttachmentDescription { Format = VulkanConvertExtensions.ConvertPixelFormat(*(renderTargetFormat + i)), Samples = SampleCountFlags.Sample1, LoadOperation = currentBlendDesc->BlendEnable ? AttachmentLoadOperation.Load : AttachmentLoadOperation.DontCare, // TODO VULKAN: Only if any destination blend? StoreOperation = AttachmentStoreOperation.Store, StencilLoadOperation = AttachmentLoadOperation.DontCare, StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.ColorAttachmentOptimal, FinalLayout = ImageLayout.ColorAttachmentOptimal, }; colorAttachmentReferences[i] = new AttachmentReference { Attachment = (uint)i, Layout = ImageLayout.ColorAttachmentOptimal, }; } } if (hasDepthStencilAttachment) { attachments[attachmentCount - 1] = new AttachmentDescription { Format = Texture.GetFallbackDepthStencilFormat(GraphicsDevice, VulkanConvertExtensions.ConvertPixelFormat(pipelineStateDescription.Output.DepthStencilFormat)), Samples = SampleCountFlags.Sample1, LoadOperation = AttachmentLoadOperation.Load, // TODO VULKAN: Only if depth read enabled? StoreOperation = AttachmentStoreOperation.Store, // TODO VULKAN: Only if depth write enabled? StencilLoadOperation = AttachmentLoadOperation.DontCare, // TODO VULKAN: Handle stencil StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.DepthStencilAttachmentOptimal, FinalLayout = ImageLayout.DepthStencilAttachmentOptimal, }; } var depthAttachmentReference = new AttachmentReference { Attachment = (uint)attachments.Length - 1, Layout = ImageLayout.DepthStencilAttachmentOptimal, }; var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = (uint)renderTargetCount, ColorAttachments = colorAttachmentReferences.Length > 0 ? new IntPtr(Interop.Fixed(colorAttachmentReferences)) : IntPtr.Zero, DepthStencilAttachment = hasDepthStencilAttachment ? new IntPtr(&depthAttachmentReference) : IntPtr.Zero, }; var renderPassCreateInfo = new RenderPassCreateInfo { StructureType = StructureType.RenderPassCreateInfo, AttachmentCount = (uint)attachmentCount, Attachments = attachments.Length > 0 ? new IntPtr(Interop.Fixed(attachments)) : IntPtr.Zero, SubpassCount = 1, Subpasses = new IntPtr(&subpass) }; NativeRenderPass = GraphicsDevice.NativeDevice.CreateRenderPass(ref renderPassCreateInfo); }
private void CreateRenderPass() { var colorAttachmentReference = new AttachmentReference { Attachment = 0, Layout = ImageLayout.ColorAttachmentOptimal }; var depthStencilAttachmentReference = new AttachmentReference { Attachment = 1, Layout = ImageLayout.DepthStencilAttachmentOptimal }; var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = 1, ColorAttachments = new IntPtr(&colorAttachmentReference), }; var attachments = new[] { new AttachmentDescription { Format = backBufferFormat, Samples = SampleCountFlags.Sample1, LoadOperation = AttachmentLoadOperation.Load, StoreOperation = AttachmentStoreOperation.Store, StencilLoadOperation = AttachmentLoadOperation.DontCare, StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.ColorAttachmentOptimal, FinalLayout = ImageLayout.ColorAttachmentOptimal }, }; fixed (AttachmentDescription* attachmentsPointer = &attachments[0]) { var createInfo = new RenderPassCreateInfo { StructureType = StructureType.RenderPassCreateInfo, AttachmentCount = (uint)attachments.Length, Attachments = new IntPtr(attachmentsPointer), SubpassCount = 1, Subpasses = new IntPtr(&subpass) }; renderPass = device.CreateRenderPass(ref createInfo); } }
public static RenderPass CreateRenderPass(Graphics g, bool clearDepthOnBeginPass) { var subpasses = new[] { new SubpassDescription( new[] { new AttachmentReference(0, VulkanCore.ImageLayout.ColorAttachmentOptimal) }, new AttachmentReference(1, VulkanCore.ImageLayout.DepthStencilAttachmentOptimal)) }; var samples = g.Samples == 64 ? SampleCounts.Count64 : g.Samples == 32 ? SampleCounts.Count32 : g.Samples == 16 ? SampleCounts.Count16 : g.Samples == 8 ? SampleCounts.Count8 : g.Samples == 4 ? SampleCounts.Count4 : g.Samples == 2 ? SampleCounts.Count2 : SampleCounts.Count1; var attachments = new[] { new AttachmentDescription { Format = g.Context.Swapchain.Format, Samples = samples, LoadOp = AttachmentLoadOp.Load, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = VulkanCore.ImageLayout.Undefined, FinalLayout = VulkanCore.ImageLayout.PresentSrcKhr }, new AttachmentDescription { Format = g.Context.DepthStencilFormat, Samples = samples, LoadOp = clearDepthOnBeginPass ? AttachmentLoadOp.Clear : AttachmentLoadOp.Load, StoreOp = AttachmentStoreOp.DontCare, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = VulkanCore.ImageLayout.Undefined, FinalLayout = VulkanCore.ImageLayout.DepthStencilAttachmentOptimal } }; var dependencies = new[] { new SubpassDependency { SrcSubpass = Constant.SubpassExternal, DstSubpass = 0, SrcStageMask = PipelineStages.BottomOfPipe, DstStageMask = PipelineStages.ColorAttachmentOutput, SrcAccessMask = Accesses.MemoryRead, DstAccessMask = Accesses.ColorAttachmentRead | Accesses.ColorAttachmentWrite, DependencyFlags = Dependencies.ByRegion }, new SubpassDependency { SrcSubpass = 0, DstSubpass = Constant.SubpassExternal, SrcStageMask = PipelineStages.ColorAttachmentOutput, DstStageMask = PipelineStages.BottomOfPipe, SrcAccessMask = Accesses.ColorAttachmentRead | Accesses.ColorAttachmentWrite, DstAccessMask = Accesses.MemoryRead, DependencyFlags = Dependencies.ByRegion } }; var createInfo = new RenderPassCreateInfo(subpasses, attachments, dependencies); return(g.Context.Device.CreateRenderPass(createInfo)); }
public void CreateGraphicsPipeline() { var attachment = new AttachmentDescription { Samples = SampleCounts.Count1, Format = Format.B8G8R8A8UNorm, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.PresentSrcKhr, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare }; var subpass = new SubpassDescription(new[] { new AttachmentReference(0, ImageLayout.ColorAttachmentOptimal) }); var createInfo = new RenderPassCreateInfo(new[] { subpass }, new[] { attachment }); using (PipelineCache cache = Device.CreatePipelineCache()) using (RenderPass renderPass = Device.CreateRenderPass(createInfo)) using (PipelineLayout layout = Device.CreatePipelineLayout()) using (ShaderModule vertexShader = Device.CreateShaderModule(new ShaderModuleCreateInfo(ReadAllBytes("Shader.vert.spv")))) using (ShaderModule fragmentShader = Device.CreateShaderModule(new ShaderModuleCreateInfo(ReadAllBytes("Shader.frag.spv")))) { var shaderStageCreateInfos = new[] { new PipelineShaderStageCreateInfo(ShaderStages.Vertex, vertexShader, "main"), new PipelineShaderStageCreateInfo(ShaderStages.Fragment, fragmentShader, "main") }; var vertexInputStateCreateInfo = new PipelineVertexInputStateCreateInfo(); var inputAssemblyStateCreateInfo = new PipelineInputAssemblyStateCreateInfo(PrimitiveTopology.TriangleList); var viewportStateCreateInfo = new PipelineViewportStateCreateInfo( new Viewport(0, 0, 32, 32), new Rect2D(0, 0, 32, 32)); var rasterizationStateCreateInfo = new PipelineRasterizationStateCreateInfo { PolygonMode = PolygonMode.Fill, CullMode = CullModes.Back, FrontFace = FrontFace.CounterClockwise, LineWidth = 1.0f }; var tessellationStateCreateInfo = new PipelineTessellationStateCreateInfo(4); var multisampleStateCreateInfo = new PipelineMultisampleStateCreateInfo { RasterizationSamples = SampleCounts.Count1, MinSampleShading = 1.0f }; var colorBlendAttachmentState = new PipelineColorBlendAttachmentState { SrcColorBlendFactor = BlendFactor.One, DstColorBlendFactor = BlendFactor.Zero, ColorBlendOp = BlendOp.Add, SrcAlphaBlendFactor = BlendFactor.One, DstAlphaBlendFactor = BlendFactor.Zero, AlphaBlendOp = BlendOp.Add, ColorWriteMask = ColorComponents.All }; var depthStencilStateCreateInfo = new PipelineDepthStencilStateCreateInfo(); var colorBlendStateCreateInfo = new PipelineColorBlendStateCreateInfo( new[] { colorBlendAttachmentState }); var dynamicStateCreateInfo = new PipelineDynamicStateCreateInfo(DynamicState.LineWidth); var pipelineCreateInfo = new GraphicsPipelineCreateInfo( layout, renderPass, 0, shaderStageCreateInfos, inputAssemblyStateCreateInfo, vertexInputStateCreateInfo, rasterizationStateCreateInfo, tessellationStateCreateInfo, viewportStateCreateInfo, multisampleStateCreateInfo, depthStencilStateCreateInfo, colorBlendStateCreateInfo, dynamicStateCreateInfo); using (Device.CreateGraphicsPipelines(new[] { pipelineCreateInfo })[0]) { } using (Device.CreateGraphicsPipelines(new[] { pipelineCreateInfo }, cache)[0]) { } using (Device.CreateGraphicsPipelines(new[] { pipelineCreateInfo }, allocator: CustomAllocator)[0]) { } using (Device.CreateGraphicsPipelines(new[] { pipelineCreateInfo }, cache, CustomAllocator)[0]) { } using (Device.CreateGraphicsPipeline(pipelineCreateInfo)) { } using (Device.CreateGraphicsPipeline(pipelineCreateInfo, allocator: CustomAllocator)) { } using (Device.CreateGraphicsPipeline(pipelineCreateInfo, cache)) { } using (Device.CreateGraphicsPipeline(pipelineCreateInfo, cache, CustomAllocator)) { } } }
//[HandleProcessCorruptedStateExceptionsAttribute, SecurityCriticalAttribute] private unsafe void Recreate() { errorDuringCreate = false; if (Description.RootSignature == null) { return; } PipelineShaderStageCreateInfo[] stages; // create render pass bool hasDepthStencilAttachment = Description.Output.DepthStencilFormat != PixelFormat.None; var renderTargetCount = Description.Output.RenderTargetCount; var attachmentCount = renderTargetCount; if (hasDepthStencilAttachment) { attachmentCount++; } var attachments = new AttachmentDescription[attachmentCount]; var colorAttachmentReferences = new AttachmentReference[renderTargetCount]; fixed(PixelFormat *renderTargetFormat = &Description.Output.RenderTargetFormat0) fixed(BlendStateRenderTargetDescription * blendDescription = &Description.BlendState.RenderTarget0) { for (int i = 0; i < renderTargetCount; i++) { var currentBlendDesc = Description.BlendState.IndependentBlendEnable ? (blendDescription + i) : blendDescription; attachments[i] = new AttachmentDescription { Format = VulkanConvertExtensions.ConvertPixelFormat(*(renderTargetFormat + i)), Samples = SampleCountFlags.Sample1, LoadOperation = currentBlendDesc->BlendEnable ? AttachmentLoadOperation.Load : AttachmentLoadOperation.DontCare, // TODO VULKAN: Only if any destination blend? StoreOperation = AttachmentStoreOperation.Store, StencilLoadOperation = AttachmentLoadOperation.DontCare, StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.ColorAttachmentOptimal, FinalLayout = ImageLayout.ColorAttachmentOptimal, }; colorAttachmentReferences[i] = new AttachmentReference { Attachment = (uint)i, Layout = ImageLayout.ColorAttachmentOptimal, }; } } if (hasDepthStencilAttachment) { attachments[attachmentCount - 1] = new AttachmentDescription { Format = Texture.GetFallbackDepthStencilFormat(GraphicsDevice, VulkanConvertExtensions.ConvertPixelFormat(Description.Output.DepthStencilFormat)), Samples = SampleCountFlags.Sample1, LoadOperation = AttachmentLoadOperation.Load, // TODO VULKAN: Only if depth read enabled? StoreOperation = AttachmentStoreOperation.Store, // TODO VULKAN: Only if depth write enabled? StencilLoadOperation = AttachmentLoadOperation.DontCare, // TODO VULKAN: Handle stencil StencilStoreOperation = AttachmentStoreOperation.DontCare, InitialLayout = ImageLayout.DepthStencilAttachmentOptimal, FinalLayout = ImageLayout.DepthStencilAttachmentOptimal, }; } var depthAttachmentReference = new AttachmentReference { Attachment = (uint)attachments.Length - 1, Layout = ImageLayout.DepthStencilAttachmentOptimal, }; var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = (uint)renderTargetCount, ColorAttachments = colorAttachmentReferences.Length > 0 ? new IntPtr(Interop.Fixed(colorAttachmentReferences)) : IntPtr.Zero, DepthStencilAttachment = hasDepthStencilAttachment ? new IntPtr(&depthAttachmentReference) : IntPtr.Zero, }; var renderPassCreateInfo = new RenderPassCreateInfo { StructureType = StructureType.RenderPassCreateInfo, AttachmentCount = (uint)attachmentCount, Attachments = attachments.Length > 0 ? new IntPtr(Interop.Fixed(attachments)) : IntPtr.Zero, SubpassCount = 1, Subpasses = new IntPtr(&subpass) }; // create pipeline layout // Remap descriptor set indices to those in the shader. This ordering generated by the ShaderCompiler var resourceGroups = Description.EffectBytecode.Reflection.ResourceBindings.Select(x => x.ResourceGroup ?? "Globals").Distinct().ToList(); ResourceGroupCount = resourceGroups.Count; var layouts = Description.RootSignature.EffectDescriptorSetReflection.Layouts; // Get binding indices used by the shader var destinationBindings = Description.EffectBytecode.Stages .SelectMany(x => BinarySerialization.Read <ShaderInputBytecode>(x.Data).ResourceBindings) .GroupBy(x => x.Key, x => x.Value) .ToDictionary(x => x.Key, x => x.First()); var maxBindingIndex = destinationBindings.Max(x => x.Value); var destinationEntries = new DescriptorSetLayoutBuilder.Entry[maxBindingIndex + 1]; DescriptorBindingMapping = new List <DescriptorSetInfo>(); for (int i = 0; i < resourceGroups.Count; i++) { var resourceGroupName = resourceGroups[i] == "Globals" ? Description.RootSignature.EffectDescriptorSetReflection.DefaultSetSlot : resourceGroups[i]; var layoutIndex = resourceGroups[i] == null ? 0 : layouts.FindIndex(x => x.Name == resourceGroupName); // Check if the resource group is used by the shader if (layoutIndex == -1) { continue; } var sourceEntries = layouts[layoutIndex].Layout.Entries; for (int sourceBinding = 0; sourceBinding < sourceEntries.Count; sourceBinding++) { var sourceEntry = sourceEntries[sourceBinding]; int destinationBinding; if (destinationBindings.TryGetValue(sourceEntry.Key.Name, out destinationBinding)) { destinationEntries[destinationBinding] = sourceEntry; // No need to umpdate immutable samplers if (sourceEntry.Class == EffectParameterClass.Sampler && sourceEntry.ImmutableSampler != null) { continue; } DescriptorBindingMapping.Add(new DescriptorSetInfo { SourceSet = layoutIndex, SourceBinding = sourceBinding, DestinationBinding = destinationBinding, DescriptorType = VulkanConvertExtensions.ConvertDescriptorType(sourceEntry.Class, sourceEntry.Type) }); } } } // Create default sampler, used by texture and buffer loads destinationEntries[0] = new DescriptorSetLayoutBuilder.Entry { Class = EffectParameterClass.Sampler, Type = EffectParameterType.Sampler, ImmutableSampler = GraphicsDevice.SamplerStates.PointWrap, ArraySize = 1, }; // Create descriptor set layout NativeDescriptorSetLayout = DescriptorSetLayout.CreateNativeDescriptorSetLayout(GraphicsDevice, destinationEntries, out DescriptorTypeCounts); // Create pipeline layout var nativeDescriptorSetLayout = NativeDescriptorSetLayout; var pipelineLayoutCreateInfo = new PipelineLayoutCreateInfo { StructureType = StructureType.PipelineLayoutCreateInfo, SetLayoutCount = 1, SetLayouts = new IntPtr(&nativeDescriptorSetLayout) }; // Create shader stages Dictionary <int, string> inputAttributeNames; // Note: important to pin this so that stages[x].Name is valid during this whole function void *defaultEntryPointData = Interop.Fixed(defaultEntryPoint); stages = CreateShaderStages(Description, out inputAttributeNames); var inputAttributes = new VertexInputAttributeDescription[Description.InputElements.Length]; int inputAttributeCount = 0; var inputBindings = new VertexInputBindingDescription[inputAttributes.Length]; int inputBindingCount = 0; for (int inputElementIndex = 0; inputElementIndex < inputAttributes.Length; inputElementIndex++) { var inputElement = Description.InputElements[inputElementIndex]; var slotIndex = inputElement.InputSlot; if (inputElement.InstanceDataStepRate > 1) { throw new NotImplementedException(); } Format format; int size; bool isCompressed; VulkanConvertExtensions.ConvertPixelFormat(inputElement.Format, out format, out size, out isCompressed); var location = inputAttributeNames.FirstOrDefault(x => x.Value == inputElement.SemanticName && inputElement.SemanticIndex == 0 || x.Value == inputElement.SemanticName + inputElement.SemanticIndex); if (location.Value != null) { inputAttributes[inputAttributeCount++] = new VertexInputAttributeDescription { Format = format, Offset = (uint)inputElement.AlignedByteOffset, Binding = (uint)inputElement.InputSlot, Location = (uint)location.Key }; } inputBindings[slotIndex].Binding = (uint)slotIndex; inputBindings[slotIndex].InputRate = inputElement.InputSlotClass == InputClassification.Vertex ? VertexInputRate.Vertex : VertexInputRate.Instance; // TODO VULKAN: This is currently an argument to Draw() overloads. if (inputBindings[slotIndex].Stride < inputElement.AlignedByteOffset + size) { inputBindings[slotIndex].Stride = (uint)(inputElement.AlignedByteOffset + size); } if (inputElement.InputSlot >= inputBindingCount) { inputBindingCount = inputElement.InputSlot + 1; } } var inputAssemblyState = new PipelineInputAssemblyStateCreateInfo { StructureType = StructureType.PipelineInputAssemblyStateCreateInfo, Topology = VulkanConvertExtensions.ConvertPrimitiveType(Description.PrimitiveType), PrimitiveRestartEnable = VulkanConvertExtensions.ConvertPrimitiveRestart(Description.PrimitiveType), }; // TODO VULKAN: Tessellation and multisampling var multisampleState = new PipelineMultisampleStateCreateInfo { StructureType = StructureType.PipelineMultisampleStateCreateInfo, RasterizationSamples = SampleCountFlags.Sample1 }; //var tessellationState = new PipelineTessellationStateCreateInfo(); var rasterizationState = new PipelineRasterizationStateCreateInfo { StructureType = StructureType.PipelineRasterizationStateCreateInfo, CullMode = VulkanConvertExtensions.ConvertCullMode(Description.RasterizerState.CullMode), FrontFace = Description.RasterizerState.FrontFaceCounterClockwise ? FrontFace.CounterClockwise : FrontFace.Clockwise, PolygonMode = VulkanConvertExtensions.ConvertFillMode(Description.RasterizerState.FillMode), DepthBiasEnable = true, // TODO VULKAN DepthBiasConstantFactor = Description.RasterizerState.DepthBias, DepthBiasSlopeFactor = Description.RasterizerState.SlopeScaleDepthBias, DepthBiasClamp = Description.RasterizerState.DepthBiasClamp, LineWidth = 1.0f, DepthClampEnable = !Description.RasterizerState.DepthClipEnable, RasterizerDiscardEnable = false, }; var depthStencilState = new PipelineDepthStencilStateCreateInfo { StructureType = StructureType.PipelineDepthStencilStateCreateInfo, DepthTestEnable = Description.DepthStencilState.DepthBufferEnable, StencilTestEnable = Description.DepthStencilState.StencilEnable, DepthWriteEnable = Description.DepthStencilState.DepthBufferWriteEnable, MinDepthBounds = 0.0f, MaxDepthBounds = 1.0f, DepthCompareOperation = VulkanConvertExtensions.ConvertComparisonFunction(Description.DepthStencilState.DepthBufferFunction), Front = new StencilOperationState { CompareOperation = VulkanConvertExtensions.ConvertComparisonFunction(Description.DepthStencilState.FrontFace.StencilFunction), DepthFailOperation = VulkanConvertExtensions.ConvertStencilOperation(Description.DepthStencilState.FrontFace.StencilDepthBufferFail), FailOperation = VulkanConvertExtensions.ConvertStencilOperation(Description.DepthStencilState.FrontFace.StencilFail), PassOperation = VulkanConvertExtensions.ConvertStencilOperation(Description.DepthStencilState.FrontFace.StencilPass), CompareMask = Description.DepthStencilState.StencilMask, WriteMask = Description.DepthStencilState.StencilWriteMask }, Back = new StencilOperationState { CompareOperation = VulkanConvertExtensions.ConvertComparisonFunction(Description.DepthStencilState.BackFace.StencilFunction), DepthFailOperation = VulkanConvertExtensions.ConvertStencilOperation(Description.DepthStencilState.BackFace.StencilDepthBufferFail), FailOperation = VulkanConvertExtensions.ConvertStencilOperation(Description.DepthStencilState.BackFace.StencilFail), PassOperation = VulkanConvertExtensions.ConvertStencilOperation(Description.DepthStencilState.BackFace.StencilPass), CompareMask = Description.DepthStencilState.StencilMask, WriteMask = Description.DepthStencilState.StencilWriteMask } }; var description = Description.BlendState; var colorBlendAttachments = new PipelineColorBlendAttachmentState[renderTargetCount]; var renderTargetBlendState = &description.RenderTarget0; for (int i = 0; i < renderTargetCount; i++) { colorBlendAttachments[i] = new PipelineColorBlendAttachmentState { BlendEnable = renderTargetBlendState->BlendEnable, AlphaBlendOperation = VulkanConvertExtensions.ConvertBlendFunction(renderTargetBlendState->AlphaBlendFunction), ColorBlendOperation = VulkanConvertExtensions.ConvertBlendFunction(renderTargetBlendState->ColorBlendFunction), DestinationAlphaBlendFactor = VulkanConvertExtensions.ConvertBlend(renderTargetBlendState->AlphaDestinationBlend), DestinationColorBlendFactor = VulkanConvertExtensions.ConvertBlend(renderTargetBlendState->ColorDestinationBlend), SourceAlphaBlendFactor = VulkanConvertExtensions.ConvertBlend(renderTargetBlendState->AlphaSourceBlend), SourceColorBlendFactor = VulkanConvertExtensions.ConvertBlend(renderTargetBlendState->ColorSourceBlend), ColorWriteMask = VulkanConvertExtensions.ConvertColorWriteChannels(renderTargetBlendState->ColorWriteChannels), }; if (description.IndependentBlendEnable) { renderTargetBlendState++; } } var viewportState = new PipelineViewportStateCreateInfo { StructureType = StructureType.PipelineViewportStateCreateInfo, ScissorCount = 1, ViewportCount = 1, }; fixed(void *dynamicStatesPointer = dynamicStates.Length == 0?null : dynamicStates, inputAttributesPointer = inputAttributes.Length == 0?null : inputAttributes, inputBindingsPointer = inputBindings.Length == 0?null : inputBindings, colorBlendAttachmentsPointer = colorBlendAttachments.Length == 0?null : colorBlendAttachments, stagesPointer = stages.Length == 0?null : stages) { var vertexInputState = new PipelineVertexInputStateCreateInfo { StructureType = StructureType.PipelineVertexInputStateCreateInfo, VertexAttributeDescriptionCount = (uint)inputAttributeCount, VertexAttributeDescriptions = (IntPtr)inputAttributesPointer, VertexBindingDescriptionCount = (uint)inputBindingCount, VertexBindingDescriptions = (IntPtr)inputBindingsPointer, }; var colorBlendState = new PipelineColorBlendStateCreateInfo { StructureType = StructureType.PipelineColorBlendStateCreateInfo, AttachmentCount = (uint)renderTargetCount, Attachments = (IntPtr)colorBlendAttachmentsPointer, }; var dynamicState = new PipelineDynamicStateCreateInfo { StructureType = StructureType.PipelineDynamicStateCreateInfo, DynamicStateCount = (uint)dynamicStates.Length, DynamicStates = (IntPtr)dynamicStatesPointer, }; var createInfo = new GraphicsPipelineCreateInfo { StructureType = StructureType.GraphicsPipelineCreateInfo, StageCount = (uint)stages.Length, Stages = (IntPtr)stagesPointer, //TessellationState = new IntPtr(&tessellationState), VertexInputState = new IntPtr(&vertexInputState), InputAssemblyState = new IntPtr(&inputAssemblyState), RasterizationState = new IntPtr(&rasterizationState), MultisampleState = new IntPtr(&multisampleState), DepthStencilState = new IntPtr(&depthStencilState), ColorBlendState = new IntPtr(&colorBlendState), DynamicState = new IntPtr(&dynamicState), ViewportState = new IntPtr(&viewportState), Subpass = 0, }; using (GraphicsDevice.QueueLock.ReadLock()) { NativeRenderPass = GraphicsDevice.NativeDevice.CreateRenderPass(ref renderPassCreateInfo); NativeLayout = GraphicsDevice.NativeDevice.CreatePipelineLayout(ref pipelineLayoutCreateInfo); createInfo.Layout = NativeLayout; createInfo.RenderPass = NativeRenderPass; try { NativePipeline = GraphicsDevice.NativeDevice.CreateGraphicsPipelines(PipelineCache.Null, 1, &createInfo); } catch (Exception e) { errorDuringCreate = true; NativePipeline = Pipeline.Null; } } } // Cleanup shader modules for (int i = 0; i < stages.Length; i++) { GraphicsDevice.NativeDevice.DestroyShaderModule(stages[i].Module); } }
public unsafe RenderPass(Api api, SwapChain swapChain, DepthBuffer depthBuffer, AttachmentLoadOp colorBufferLoadOp, AttachmentLoadOp depthBufferLoadOp) { _api = api; var colorAttachment = new AttachmentDescription(); colorAttachment.Format = swapChain.Format; colorAttachment.Samples = SampleCountFlags.SampleCount1Bit; colorAttachment.LoadOp = colorBufferLoadOp; colorAttachment.StoreOp = AttachmentStoreOp.Store; colorAttachment.StencilLoadOp = AttachmentLoadOp.DontCare; colorAttachment.StencilStoreOp = AttachmentStoreOp.DontCare; colorAttachment.InitialLayout = colorBufferLoadOp == AttachmentLoadOp.Clear ? ImageLayout.Undefined : ImageLayout.PresentSrcKhr; colorAttachment.FinalLayout = ImageLayout.PresentSrcKhr; var depthAttachment = new AttachmentDescription(); depthAttachment.Format = depthBuffer.Format; depthAttachment.Samples = SampleCountFlags.SampleCount1Bit; depthAttachment.LoadOp = depthBufferLoadOp; depthAttachment.StoreOp = AttachmentStoreOp.DontCare; depthAttachment.StencilLoadOp = AttachmentLoadOp.DontCare; depthAttachment.StencilStoreOp = AttachmentStoreOp.DontCare; depthAttachment.InitialLayout = depthBufferLoadOp == AttachmentLoadOp.Clear ? ImageLayout.Undefined : ImageLayout.DepthStencilAttachmentOptimal; depthAttachment.FinalLayout = ImageLayout.DepthStencilAttachmentOptimal; var colorAttachmentRef = new AttachmentReference(); colorAttachmentRef.Attachment = 0; colorAttachmentRef.Layout = ImageLayout.ColorAttachmentOptimal; var depthAttachmentRef = new AttachmentReference(); depthAttachmentRef.Attachment = 1; depthAttachmentRef.Layout = ImageLayout.DepthStencilAttachmentOptimal; var subpass = new SubpassDescription(); subpass.PipelineBindPoint = PipelineBindPoint.Graphics; subpass.ColorAttachmentCount = 1; subpass.PColorAttachments = (AttachmentReference *)Unsafe.AsPointer(ref colorAttachmentRef); subpass.PDepthStencilAttachment = (AttachmentReference *)Unsafe.AsPointer(ref depthAttachmentRef); var dependency = new SubpassDependency(); dependency.SrcSubpass = Vk.SubpassExternal; dependency.DstSubpass = 0; dependency.SrcStageMask = PipelineStageFlags.PipelineStageColorAttachmentOutputBit; dependency.SrcAccessMask = 0; dependency.DstStageMask = PipelineStageFlags.PipelineStageColorAttachmentOutputBit; dependency.DstAccessMask = AccessFlags.AccessColorAttachmentReadBit | AccessFlags.AccessColorAttachmentWriteBit; Span <AttachmentDescription> attachments = stackalloc AttachmentDescription[] { colorAttachment, depthAttachment }; var renderPassInfo = new RenderPassCreateInfo(); renderPassInfo.SType = StructureType.RenderPassCreateInfo; renderPassInfo.AttachmentCount = (uint)attachments.Length; renderPassInfo.PAttachments = (AttachmentDescription *)Unsafe.AsPointer(ref attachments[0]); renderPassInfo.SubpassCount = 1; renderPassInfo.PSubpasses = (SubpassDescription *)Unsafe.AsPointer(ref subpass); renderPassInfo.DependencyCount = 1; renderPassInfo.PDependencies = (SubpassDependency *)Unsafe.AsPointer(ref dependency); Util.Verify( _api.Vk.CreateRenderPass(_api.Vk.CurrentDevice.Value, renderPassInfo, default, out _vkRenderPass),
public unsafe RenderPass CreateRenderPass(ref RenderPassCreateInfo createInfo, AllocationCallbacks* allocator = null) { RenderPass renderPass; fixed (RenderPassCreateInfo* __createInfo__ = &createInfo) { vkCreateRenderPass(this, __createInfo__, allocator, &renderPass).CheckError(); } return renderPass; }
private RenderPass CreateRenderPass() { var attachments = new[] { // Color attachment. new AttachmentDescription { Format = Swapchain.Format, Samples = SampleCounts.Count1, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.PresentSrcKhr }, // Depth attachment. new AttachmentDescription { Format = _depthStencilBuffer.Format, Samples = SampleCounts.Count1, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.DontCare, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.DepthStencilAttachmentOptimal } }; var subpasses = new[] { new SubpassDescription( new[] { new AttachmentReference(0, ImageLayout.ColorAttachmentOptimal) }, new AttachmentReference(1, ImageLayout.DepthStencilAttachmentOptimal)) }; var dependencies = new[] { new SubpassDependency { SrcSubpass = Constant.SubpassExternal, DstSubpass = 0, SrcStageMask = PipelineStages.BottomOfPipe, DstStageMask = PipelineStages.ColorAttachmentOutput, SrcAccessMask = Accesses.MemoryRead, DstAccessMask = Accesses.ColorAttachmentRead | Accesses.ColorAttachmentWrite, DependencyFlags = Dependencies.ByRegion }, new SubpassDependency { SrcSubpass = 0, DstSubpass = Constant.SubpassExternal, SrcStageMask = PipelineStages.ColorAttachmentOutput, DstStageMask = PipelineStages.BottomOfPipe, SrcAccessMask = Accesses.ColorAttachmentRead | Accesses.ColorAttachmentWrite, DstAccessMask = Accesses.MemoryRead, DependencyFlags = Dependencies.ByRegion } }; var createInfo = new RenderPassCreateInfo(subpasses, attachments, dependencies); return(Context.Device.CreateRenderPass(createInfo)); }
private RenderPass CreateRenderpass() { AttachmentDescription *pAttachments = stackalloc AttachmentDescription[2] { //Color Attachment new AttachmentDescription { Format = SwapchainImageFormat, Samples = SampleCountFlags.SampleCount1Bit, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.Store, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.PresentSrcKhr }, //Depth Attachment new AttachmentDescription { Format = DepthFormat, Samples = SampleCountFlags.SampleCount1Bit, LoadOp = AttachmentLoadOp.Clear, StoreOp = AttachmentStoreOp.DontCare, StencilLoadOp = AttachmentLoadOp.DontCare, StencilStoreOp = AttachmentStoreOp.DontCare, InitialLayout = ImageLayout.Undefined, FinalLayout = ImageLayout.DepthStencilAttachmentOptimal } }; var colorAttachmentRef = new AttachmentReference(0, ImageLayout.ColorAttachmentOptimal); var depthAttachmentRef = new AttachmentReference(1, ImageLayout.DepthStencilAttachmentOptimal); var subpass = new SubpassDescription { PipelineBindPoint = PipelineBindPoint.Graphics, ColorAttachmentCount = 1, PColorAttachments = &colorAttachmentRef, PDepthStencilAttachment = &depthAttachmentRef }; var dependency = new SubpassDependency { SrcSubpass = Vk.SubpassExternal, DstSubpass = 0, SrcStageMask = PipelineStageFlags.PipelineStageColorAttachmentOutputBit, SrcAccessMask = 0, DstStageMask = PipelineStageFlags.PipelineStageColorAttachmentOutputBit, DstAccessMask = AccessFlags.AccessColorAttachmentReadBit | AccessFlags.AccessColorAttachmentWriteBit }; var renderPassInfo = new RenderPassCreateInfo { SType = StructureType.RenderPassCreateInfo, AttachmentCount = 2, PAttachments = pAttachments, SubpassCount = 1, PSubpasses = &subpass, DependencyCount = 1, PDependencies = &dependency }; RenderPass rPass; var res = VkApi.CreateRenderPass(Device, &renderPassInfo, null, &rPass); if (res != Result.Success) { throw new VMASharp.VulkanResultException("Failed to create RenderPass!", res); } return(rPass); } }
public bool Create(string vsName, string fsName, VertexInputBindingDescription [] vbind, VertexInputAttributeDescription [] vatts) { Device dv = mDevices.GetLogicalDevice(); PipelineShaderStageCreateInfo plssciv = new PipelineShaderStageCreateInfo( ShaderStages.Vertex, mShaders[vsName], "main", null); PipelineShaderStageCreateInfo plsscif = new PipelineShaderStageCreateInfo( ShaderStages.Fragment, mShaders[fsName], "main", null); PipelineVertexInputStateCreateInfo plvisci = new PipelineVertexInputStateCreateInfo( vbind, vatts); PipelineInputAssemblyStateCreateInfo pliasci = new PipelineInputAssemblyStateCreateInfo( PrimitiveTopology.TriangleList); Viewport vp = new Viewport(0, 0, 1280, 720, 0f, 1f); Rect2D scissor = new Rect2D(Offset2D.Zero, mDevices.GetChainExtent()); PipelineViewportStateCreateInfo plvpsci = new PipelineViewportStateCreateInfo( new Viewport[1] { vp }, new Rect2D[1] { scissor }); PipelineRasterizationStateCreateInfo plrsci = new PipelineRasterizationStateCreateInfo(); plrsci.LineWidth = 1; PipelineMultisampleStateCreateInfo plmssci = new PipelineMultisampleStateCreateInfo(); plmssci.RasterizationSamples = SampleCounts.Count1; PipelineColorBlendAttachmentState plcbas = new PipelineColorBlendAttachmentState(); plcbas.ColorWriteMask = ColorComponents.All; plcbas.BlendEnable = false; PipelineColorBlendStateCreateInfo plcbsci = new PipelineColorBlendStateCreateInfo(); plcbsci.LogicOpEnable = false; plcbsci.LogicOp = LogicOp.Copy; plcbsci.Attachments = new PipelineColorBlendAttachmentState[1] { plcbas }; plcbsci.BlendConstants = ColorF4.Zero; PipelineLayoutCreateInfo pllci = new PipelineLayoutCreateInfo( mDevices.GetDSLs()); mPipeLayout = dv.CreatePipelineLayout(pllci); AttachmentDescription ad = new AttachmentDescription(); ad.Format = Format.B8G8R8A8UNorm; ad.Samples = SampleCounts.Count1; ad.LoadOp = AttachmentLoadOp.Clear; ad.StoreOp = AttachmentStoreOp.Store; ad.StencilLoadOp = AttachmentLoadOp.DontCare; ad.StencilStoreOp = AttachmentStoreOp.DontCare; ad.InitialLayout = ImageLayout.Undefined; ad.FinalLayout = ImageLayout.PresentSrcKhr; AttachmentReference ar = new AttachmentReference(0, ImageLayout.ColorAttachmentOptimal); SubpassDescription spd = new SubpassDescription(); spd.ColorAttachments = new AttachmentReference[1] { ar }; SubpassDependency spdc = new SubpassDependency(); spdc.SrcSubpass = Constant.SubpassExternal; spdc.DstSubpass = 0; spdc.SrcStageMask = PipelineStages.ColorAttachmentOutput; spdc.SrcAccessMask = 0; spdc.DstStageMask = PipelineStages.ColorAttachmentOutput; spdc.DstAccessMask = Accesses.ColorAttachmentRead | Accesses.ColorAttachmentWrite; RenderPassCreateInfo rpci = new RenderPassCreateInfo( new SubpassDescription[1] { spd }, new AttachmentDescription[1] { ad }, new SubpassDependency[1] { spdc }); mRenderPass = dv.CreateRenderPass(rpci); GraphicsPipelineCreateInfo gplci = new GraphicsPipelineCreateInfo(); gplci.Stages = new PipelineShaderStageCreateInfo[2] { plssciv, plsscif }; gplci.VertexInputState = plvisci; gplci.InputAssemblyState = pliasci; gplci.ViewportState = plvpsci; gplci.RasterizationState = plrsci; gplci.MultisampleState = plmssci; gplci.DepthStencilState = null; gplci.ColorBlendState = plcbsci; gplci.DynamicState = null; gplci.Layout = mPipeLayout; gplci.RenderPass = mRenderPass; gplci.Subpass = 0; gplci.BasePipelineHandle = null; gplci.BasePipelineIndex = -1; mPipe = dv.CreateGraphicsPipeline(gplci); CreateSyncObjects(); return(true); }
public static unsafe DisposableRenderPass ToRenderPass(this ProgramPipelineState state, VulkanRenderer gd, Device device) { const int MaxAttachments = Constants.MaxRenderTargets + 1; AttachmentDescription[] attachmentDescs = null; var subpass = new SubpassDescription() { PipelineBindPoint = PipelineBindPoint.Graphics }; AttachmentReference *attachmentReferences = stackalloc AttachmentReference[MaxAttachments]; Span <int> attachmentIndices = stackalloc int[MaxAttachments]; Span <Silk.NET.Vulkan.Format> attachmentFormats = stackalloc Silk.NET.Vulkan.Format[MaxAttachments]; int attachmentCount = 0; int colorCount = 0; int maxColorAttachmentIndex = 0; for (int i = 0; i < state.AttachmentEnable.Length; i++) { if (state.AttachmentEnable[i]) { maxColorAttachmentIndex = i; attachmentFormats[attachmentCount] = gd.FormatCapabilities.ConvertToVkFormat(state.AttachmentFormats[i]); attachmentIndices[attachmentCount++] = i; colorCount++; } } if (state.DepthStencilEnable) { attachmentFormats[attachmentCount++] = gd.FormatCapabilities.ConvertToVkFormat(state.DepthStencilFormat); } if (attachmentCount != 0) { attachmentDescs = new AttachmentDescription[attachmentCount]; for (int i = 0; i < attachmentCount; i++) { int bindIndex = attachmentIndices[i]; attachmentDescs[i] = new AttachmentDescription( 0, attachmentFormats[i], TextureStorage.ConvertToSampleCountFlags((uint)state.SamplesCount), AttachmentLoadOp.Load, AttachmentStoreOp.Store, AttachmentLoadOp.Load, AttachmentStoreOp.Store, ImageLayout.General, ImageLayout.General); } int colorAttachmentsCount = colorCount; if (colorAttachmentsCount > MaxAttachments - 1) { colorAttachmentsCount = MaxAttachments - 1; } if (colorAttachmentsCount != 0) { int maxAttachmentIndex = Constants.MaxRenderTargets - 1; subpass.ColorAttachmentCount = (uint)maxAttachmentIndex + 1; subpass.PColorAttachments = &attachmentReferences[0]; // Fill with VK_ATTACHMENT_UNUSED to cover any gaps. for (int i = 0; i <= maxAttachmentIndex; i++) { subpass.PColorAttachments[i] = new AttachmentReference(Vk.AttachmentUnused, ImageLayout.Undefined); } for (int i = 0; i < colorAttachmentsCount; i++) { int bindIndex = attachmentIndices[i]; subpass.PColorAttachments[bindIndex] = new AttachmentReference((uint)i, ImageLayout.General); } } if (state.DepthStencilEnable) { uint dsIndex = (uint)attachmentCount - 1; subpass.PDepthStencilAttachment = &attachmentReferences[MaxAttachments - 1]; *subpass.PDepthStencilAttachment = new AttachmentReference(dsIndex, ImageLayout.General); } } var subpassDependency = new SubpassDependency( 0, 0, PipelineStageFlags.PipelineStageAllGraphicsBit, PipelineStageFlags.PipelineStageAllGraphicsBit, AccessFlags.AccessMemoryReadBit | AccessFlags.AccessMemoryWriteBit, AccessFlags.AccessMemoryReadBit | AccessFlags.AccessMemoryWriteBit, 0); fixed(AttachmentDescription *pAttachmentDescs = attachmentDescs) { var renderPassCreateInfo = new RenderPassCreateInfo() { SType = StructureType.RenderPassCreateInfo, PAttachments = pAttachmentDescs, AttachmentCount = attachmentDescs != null ? (uint)attachmentDescs.Length : 0, PSubpasses = &subpass, SubpassCount = 1, PDependencies = &subpassDependency, DependencyCount = 1 }; gd.Api.CreateRenderPass(device, renderPassCreateInfo, null, out var renderPass).ThrowOnError(); return(new DisposableRenderPass(gd.Api, device, renderPass)); } }
internal static unsafe extern Result vkCreateRenderPass(Device device, RenderPassCreateInfo* createInfo, AllocationCallbacks* allocator, RenderPass* renderPass);