From 5bb0b94550ec46bf5a3cf3d0f05dbe6c24e18c41 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Jean-Philippe=20Bruy=C3=A8re?= Date: Wed, 8 Dec 2021 21:54:48 +0100 Subject: [PATCH] update with vk.net 0.4.0-beta --- .vscode/launch.json | 14 + .vscode/tasks.json | 14 + .../EnvironmentPipeline.cs | 14 +- addons/gltfLoader/glTFLoader.cs | 10 +- samples/DistanceFieldFontTest/Program.cs | 2 +- samples/ExternalMemmories/Program.cs | 8 +- samples/ImmutableSampler/main.cs | 2 +- samples/Tesselation/main.cs | 186 ----------- samples/Textured/main.cs | 2 +- samples/TexturedCube/main.cs | 2 +- samples/Triangle/main.cs | 2 +- .../{Tesselation => VulkanContext}/README.md | 0 .../VulkanContext.csproj} | 0 samples/VulkanContext/main.cs | 21 ++ .../shaders/main.frag | 0 .../shaders/main.vert | 0 samples/common/SampleBase.cs | 4 +- samples/deferred/DeferredPbrRenderer.cs | 2 +- samples/deferred/main.cs | 2 +- samples/deferred/shadowMapRenderer.cs | 4 +- samples/pbr/main.cs | 2 +- samples/shadow/DeferredPbrRenderer.cs | 2 +- samples/shadow/EnvironmentPipeline.cs | 14 +- samples/shadow/main-crow.cs | 2 +- samples/shadow/main.cs | 2 +- samples/shadow/mainShadow.cs | 2 +- samples/shadow/mainWithDebugDrawer.cs | 2 +- samples/shadow/shadowMapRenderer.cs | 2 +- vke.net.sln | 22 +- vke/src/Camera.cs | 2 +- vke/src/ExtensionMethods.cs | 36 ++- vke/src/MemoryPool.cs | 4 +- vke/src/ShaderInfo.cs | 4 +- vke/src/Utils.cs | 290 +++++++++--------- vke/src/VkFormatSize.cs | 7 +- vke/src/VkWindow.cs | 2 +- vke/src/base/Activable.cs | 3 +- vke/src/base/Buffer.cs | 9 +- vke/src/base/CommandBuffer.cs | 19 +- vke/src/base/CommandPool.cs | 17 +- vke/src/base/ComputePipeline.cs | 5 +- vke/src/base/DebugReport.cs | 7 +- vke/src/base/DebugUtilsMessenger.cs | 5 +- vke/src/base/DescriptorPool.cs | 15 +- vke/src/base/DescriptorSetLayout.cs | 3 +- vke/src/base/DescriptorSetWrites.cs | 9 +- vke/src/base/Device.cs | 30 +- vke/src/base/Fence.cs | 5 +- vke/src/base/FrameBuffer.cs | 9 +- vke/src/base/GraphicPipeline.cs | 15 +- vke/src/base/GraphicPipelineConfig.cs | 10 +- vke/src/base/Image.cs | 27 +- vke/src/base/Instance.cs | 9 +- vke/src/base/PhysicalDevice.cs | 5 +- vke/src/base/PipelineCache.cs | 9 +- vke/src/base/PipelineLayout.cs | 5 +- vke/src/base/QueryPool.cs | 11 +- vke/src/base/Queue.cs | 7 +- vke/src/base/RenderPass.cs | 18 +- vke/src/base/Resource.cs | 15 +- vke/src/base/SwapChain.cs | 11 +- vke/src/base/VulkanContext.cs | 254 +++++++++++++++ 62 files changed, 686 insertions(+), 530 deletions(-) delete mode 100644 samples/Tesselation/main.cs rename samples/{Tesselation => VulkanContext}/README.md (100%) rename samples/{Tesselation/Tesselation.csproj => VulkanContext/VulkanContext.csproj} (100%) create mode 100644 samples/VulkanContext/main.cs rename samples/{Tesselation => VulkanContext}/shaders/main.frag (100%) rename samples/{Tesselation => VulkanContext}/shaders/main.vert (100%) create mode 100644 vke/src/base/VulkanContext.cs diff --git a/.vscode/launch.json b/.vscode/launch.json index dfc6833..39584b8 100644 --- a/.vscode/launch.json +++ b/.vscode/launch.json @@ -4,6 +4,20 @@ // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 "version": "0.2.0", "configurations": [ + { + "name": ".NET Core Launch (VulkanContext)", + "type": "coreclr", + "request": "launch", + "preLaunchTask": "build VulkanContext", + "program": "${workspaceFolder}/build/Debug/netcoreapp3.1/VulkanContext", + "args": [], + "cwd": "${workspaceFolder}/build/Debug/netcoreapp3.1/", + "stopAtEntry": false, + "console": "internalConsole", + "env": { + "VK_INSTANCE_LAYERS": "VK_LAYER_KHRONOS_validation" + } + }, { "name": ".NET Core Launch (ClearScreen)", "type": "coreclr", diff --git a/.vscode/tasks.json b/.vscode/tasks.json index 4da8453..b58cf5b 100644 --- a/.vscode/tasks.json +++ b/.vscode/tasks.json @@ -15,6 +15,20 @@ ], "problemMatcher": "$msCompile" }, + { + "label": "build VulkanContext", + "command": "dotnet", + "type": "process", + "args": [ + "build", + "${workspaceFolder}/samples/VulkanContext/VulkanContext.csproj", + "/property:GenerateFullPaths=true", + "/property:SolutionDir=${workspaceFolder}/", + "/property:Configuration=Debug", + "/consoleloggerparameters:NoSummary" + ], + "problemMatcher": "$msCompile" + }, { "label": "build Triangle", "command": "dotnet", diff --git a/addons/EnvironmentPipeline/EnvironmentPipeline.cs b/addons/EnvironmentPipeline/EnvironmentPipeline.cs index ec56cb0..a63ffd4 100644 --- a/addons/EnvironmentPipeline/EnvironmentPipeline.cs +++ b/addons/EnvironmentPipeline/EnvironmentPipeline.cs @@ -206,17 +206,17 @@ namespace vke.Environment { Matrix4x4[] matrices = { // POSITIVE_X - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Utils.DegreesToRadians(90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Helpers.DegreesToRadians(90)), // NEGATIVE_X - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Utils.DegreesToRadians(-90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Helpers.DegreesToRadians(-90)), // POSITIVE_Y - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(-90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(-90)), // NEGATIVE_Y - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(90)), // POSITIVE_Z - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(180)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(180)), // NEGATIVE_Z - Matrix4x4.CreateRotationZ(Utils.DegreesToRadians(180)) + Matrix4x4.CreateRotationZ(Helpers.DegreesToRadians(180)) }; VkImageSubresourceRange subRes = new VkImageSubresourceRange (VkImageAspectFlags.Color, 0, numMips, 0, 6); @@ -250,7 +250,7 @@ namespace vke.Environment { float viewPortSize = (float)Math.Pow (0.5, m) * dim; cmd.SetViewport (viewPortSize, viewPortSize); cmd.PushConstant (pl.Layout, VkShaderStageFlags.Vertex | VkShaderStageFlags.Fragment, - matrices[f] * Matrix4x4.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (90), 1f, 0.1f, 512f)); + matrices[f] * Matrix4x4.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (90), 1f, 0.1f, 512f)); if (target == CBTarget.IRRADIANCE) { cmd.PushConstant (pl.Layout, VkShaderStageFlags.Vertex | VkShaderStageFlags.Fragment, deltaPhi, (uint)Marshal.SizeOf ()); cmd.PushConstant (pl.Layout, VkShaderStageFlags.Vertex | VkShaderStageFlags.Fragment, deltaTheta, (uint)Marshal.SizeOf () + 4); diff --git a/addons/gltfLoader/glTFLoader.cs b/addons/gltfLoader/glTFLoader.cs index 9a08362..d73b841 100644 --- a/addons/gltfLoader/glTFLoader.cs +++ b/addons/gltfLoader/glTFLoader.cs @@ -384,11 +384,11 @@ namespace vke.glTF { } if (gltfNode.Translation != null) - FromFloatArray (ref translation, gltfNode.Translation); + Helpers.FromFloatArray (ref translation, gltfNode.Translation); if (gltfNode.Translation != null) - FromFloatArray (ref rotation, gltfNode.Rotation); + Helpers.FromFloatArray (ref rotation, gltfNode.Rotation); if (gltfNode.Translation != null) - FromFloatArray (ref scale, gltfNode.Scale); + Helpers.FromFloatArray (ref scale, gltfNode.Scale); localTransform *= Matrix4x4.CreateScale (scale) * @@ -555,7 +555,7 @@ namespace vke.glTF { pbr.alphaCutoff = mat.AlphaCutoff; pbr.alphaMode = (AlphaMode)mat.AlphaMode; - FromFloatArray (ref pbr.emissiveFactor, mat.EmissiveFactor); + Helpers.FromFloatArray (ref pbr.emissiveFactor, mat.EmissiveFactor); if (mat.EmissiveTexture != null) { pbr.emissiveTexture = mat.EmissiveTexture.Index; @@ -588,7 +588,7 @@ namespace vke.glTF { pbr.availableAttachments |= AttachmentType.Color; } - FromFloatArray (ref pbr.baseColorFactor, mat.PbrMetallicRoughness.BaseColorFactor); + Helpers.FromFloatArray (ref pbr.baseColorFactor, mat.PbrMetallicRoughness.BaseColorFactor); if (mat.PbrMetallicRoughness.MetallicRoughnessTexture != null) { pbr.metallicRoughnessTexture = mat.PbrMetallicRoughness.MetallicRoughnessTexture.Index; diff --git a/samples/DistanceFieldFontTest/Program.cs b/samples/DistanceFieldFontTest/Program.cs index 8a3e064..31990cd 100644 --- a/samples/DistanceFieldFontTest/Program.cs +++ b/samples/DistanceFieldFontTest/Program.cs @@ -239,7 +239,7 @@ namespace DistanceFieldFontTest { public override void UpdateView () { - matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); + matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); matrices.view = Matrix4x4.CreateTranslation (0, 0, -2.5f * zoom); matrices.model = Matrix4x4.CreateFromAxisAngle (Vector3.UnitZ, rotZ) * diff --git a/samples/ExternalMemmories/Program.cs b/samples/ExternalMemmories/Program.cs index 2a9f404..2526b49 100644 --- a/samples/ExternalMemmories/Program.cs +++ b/samples/ExternalMemmories/Program.cs @@ -82,11 +82,11 @@ namespace ExternalMemmories Console.ResetColor(); - VkPhysicalDeviceImageFormatInfo2 imgFormatInfo2 = VkPhysicalDeviceImageFormatInfo2.New(); - VkImageFormatProperties2 imgProps2 = VkImageFormatProperties2.New(); + VkPhysicalDeviceImageFormatInfo2 imgFormatInfo2 = default; + VkImageFormatProperties2 imgProps2 = default; - VkPhysicalDeviceExternalImageFormatInfo extImgFormatInfo = VkPhysicalDeviceExternalImageFormatInfo.New(); - VkExternalImageFormatProperties extProps = VkExternalImageFormatProperties.New (); + VkPhysicalDeviceExternalImageFormatInfo extImgFormatInfo = default; + VkExternalImageFormatProperties extProps = default; imgFormatInfo2.format = format; imgFormatInfo2.tiling = VkImageTiling.Optimal; diff --git a/samples/ImmutableSampler/main.cs b/samples/ImmutableSampler/main.cs index 6496adb..3a9bf68 100644 --- a/samples/ImmutableSampler/main.cs +++ b/samples/ImmutableSampler/main.cs @@ -148,7 +148,7 @@ namespace Textured { void updateMatrices () { - matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); + matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); matrices.view = Matrix4x4.CreateTranslation (0, 0, -2.5f * zoom); matrices.model = Matrix4x4.CreateFromAxisAngle (Vector3.UnitZ, rotZ) * diff --git a/samples/Tesselation/main.cs b/samples/Tesselation/main.cs deleted file mode 100644 index 6f95779..0000000 --- a/samples/Tesselation/main.cs +++ /dev/null @@ -1,186 +0,0 @@ -// Copyright (c) 2019 Jean-Philippe Bruyère -// -// This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) -using System; -using System.Numerics; -using System.Runtime.InteropServices; -using vke; -using Vulkan; -using Glfw; - -namespace Tesselation { - class Program : SampleBase { - static void Main (string[] args) { -#if DEBUG - Instance.VALIDATION = true; -#endif - using (Program vke = new Program ()) { - vke.Run (); - } - } - - const float rotSpeed = 0.01f, zoomSpeed = 0.01f; - float rotX, rotY, zoom = 1f; - - //vertex structure - [StructLayout(LayoutKind.Sequential)] - struct Vertex { - Vector3 position; - Vector3 color; - - public Vertex (float x, float y, float z, float r, float g, float b) { - position = new Vector3 (x, y, z); - color = new Vector3 (r, g, b); - } - } - - Matrix4x4 mvp; //the model view projection matrix - - HostBuffer ibo; //a host mappable buffer to hold the indices. - HostBuffer vbo; //a host mappable buffer to hold vertices. - HostBuffer uboMats; //a host mappable buffer for mvp matrice. - - DescriptorPool descriptorPool; - DescriptorSet descriptorSet;//descriptor set for the mvp matrice. - - FrameBuffers frameBuffers; //the frame buffer collection coupled to the swapchain images - GraphicPipeline pipeline; //the triangle rendering pipeline - - //triangle vertices (position + color per vertex) and indices. - Vertex[] vertices = { - new Vertex (-1.0f, -1.0f, 0.0f , 1.0f, 0.0f, 0.0f), - new Vertex ( 1.0f, -1.0f, 0.0f , 0.0f, 1.0f, 0.0f), - new Vertex ( 0.0f, 1.0f, 0.0f , 0.0f, 0.0f, 1.0f), - }; - ushort[] indices = new ushort[] { 0, 1, 2 }; - - protected override void initVulkan () { - base.initVulkan (); - - //first create the needed buffers - vbo = new HostBuffer (dev, VkBufferUsageFlags.VertexBuffer, vertices); - ibo = new HostBuffer (dev, VkBufferUsageFlags.IndexBuffer, indices); - //because mvp matrice may be updated by mouse move, we keep it mapped after creation. - uboMats = new HostBuffer (dev, VkBufferUsageFlags.UniformBuffer, mvp, true); - - //a descriptor pool to allocate the mvp matrice descriptor from. - descriptorPool = new DescriptorPool (dev, 1, new VkDescriptorPoolSize (VkDescriptorType.UniformBuffer)); - - //Graphic pipeline configuration are predefined by the GraphicPipelineConfig class, which ease sharing config for several pipelines having lots in common. - using (GraphicPipelineConfig cfg = GraphicPipelineConfig.CreateDefault (VkPrimitiveTopology.TriangleList, VkSampleCountFlags.SampleCount1, false)) { - //Create the pipeline layout, it will be automatically activated on pipeline creation, so that sharing layout among different pipelines will benefit - //from the reference counting to automatically dispose unused layout on pipeline clean up. It's the same for DescriptorSetLayout. - cfg.Layout = new PipelineLayout (dev, - new DescriptorSetLayout (dev, new VkDescriptorSetLayoutBinding (0, VkShaderStageFlags.Vertex, VkDescriptorType.UniformBuffer))); - //create a default renderpass with just a color attachment for the swapchain image, a default subpass is automatically created and the renderpass activation - //will follow the pipeline life cicle and will be automatically disposed when no longuer used. - cfg.RenderPass = new RenderPass (dev, swapChain.ColorFormat, cfg.Samples); - //configuration of vertex bindings and attributes - cfg.AddVertexBinding (0); - cfg.AddVertexAttributes (0, VkFormat.R32g32b32Sfloat, VkFormat.R32g32b32Sfloat);//position + color - - //shader are automatically compiled by SpirVTasks if added to the project. The resulting shaders are automatically embedded in the assembly. - //To specifiy that the shader path is a resource name, put the '#' prefix. Else the path will be search on disk. - cfg.AddShaders ( - new ShaderInfo (dev, VkShaderStageFlags.Vertex, "#shaders.main.vert.spv"), - new ShaderInfo (dev, VkShaderStageFlags.Fragment, "#shaders.main.frag.spv") - ); - - //create and activate the pipeline with the configuration we've just done. - pipeline = new GraphicPipeline (cfg); - } - - //because descriptor layout used for a pipeline are only activated on pipeline activation, descriptor set must not be allocated before, except if the layout has been manually activated, - //but in this case, layout will need also to be explicitly disposed. - descriptorSet = descriptorPool.Allocate (pipeline.Layout.DescriptorSetLayouts[0]); - - //Write the content of the descriptor, the mvp matrice. - DescriptorSetWrites uboUpdate = new DescriptorSetWrites (descriptorSet, pipeline.Layout.DescriptorSetLayouts[0]); - //Descriptor property of the mvp buffer will return a default descriptor with no offset of the full size of the buffer. - uboUpdate.Write (dev, uboMats.Descriptor); - - //allocate the default VkWindow buffers, one per swapchain image. Their will be only reset when rebuilding and not reallocated. - cmds = cmdPool.AllocateCommandBuffer (swapChain.ImageCount); - } - - //view update override, see base method for more informations. - public override void UpdateView () { - mvp = - Matrix4x4.CreateFromAxisAngle (Vector3.UnitY, rotY) * - Matrix4x4.CreateFromAxisAngle (Vector3.UnitX, rotX) * - Matrix4x4.CreateTranslation (0, 0, -3f * zoom) * - Utils.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (45f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); - - uboMats.Update (mvp, (uint)Marshal.SizeOf ()); - base.UpdateView (); - } - protected override void onMouseMove (double xPos, double yPos) { - double diffX = lastMouseX - xPos; - double diffY = lastMouseY - yPos; - if (GetButton (MouseButton.Left) == InputAction.Press) { - rotY -= rotSpeed * (float)diffX; - rotX += rotSpeed * (float)diffY; - updateViewRequested = true; - } else if (GetButton (MouseButton.Right) == InputAction.Press) { - zoom += zoomSpeed * (float)diffY; - updateViewRequested = true; - } - } - - void buildCommandBuffers() { - cmdPool.Reset (VkCommandPoolResetFlags.ReleaseResources); - - for (int i = 0; i < swapChain.ImageCount; ++i) { - FrameBuffer fb = frameBuffers[i]; - cmds[i].Start (); - - pipeline.RenderPass.Begin (cmds[i], fb); - - cmds[i].SetViewport (swapChain.Width, swapChain.Height); - cmds[i].SetScissor (swapChain.Width, swapChain.Height); - - cmds[i].BindDescriptorSet (pipeline.Layout, descriptorSet); - - cmds[i].BindPipeline (pipeline); - - cmds[i].BindVertexBuffer (vbo); - cmds[i].BindIndexBuffer (ibo, VkIndexType.Uint16); - cmds[i].DrawIndexed ((uint)indices.Length); - - pipeline.RenderPass.End (cmds[i]); - - cmds[i].End (); - } - } - - protected override void OnResize () { - base.OnResize (); - UpdateView (); - - frameBuffers?.Dispose(); - frameBuffers = pipeline.RenderPass.CreateFrameBuffers(swapChain); - - buildCommandBuffers (); - } - //clean up - protected override void Dispose (bool disposing) { - dev.WaitIdle (); - if (disposing) { - if (!isDisposed) { - //pipeline clean up will dispose PipelineLayout, DescriptorSet layouts and render pass automatically. If their reference count is zero, their handles will be destroyed. - pipeline.Dispose (); - //frame buffers are automatically activated on creation as for resources, so it requests an explicit call to dispose. - frameBuffers?.Dispose(); - //the descriptor pool - descriptorPool.Dispose (); - //resources have to be explicityly disposed. - vbo.Dispose (); - ibo.Dispose (); - uboMats.Dispose (); - } - } - - base.Dispose (disposing); - } - } -} diff --git a/samples/Textured/main.cs b/samples/Textured/main.cs index 15e6567..f9ffd8b 100644 --- a/samples/Textured/main.cs +++ b/samples/Textured/main.cs @@ -176,7 +176,7 @@ namespace Textured { } void updateMatrices () { - matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); + matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); matrices.view = Matrix4x4.CreateTranslation (0, 0, -2.5f * zoom); matrices.model = Matrix4x4.CreateFromAxisAngle (Vector3.UnitZ, rotZ) * diff --git a/samples/TexturedCube/main.cs b/samples/TexturedCube/main.cs index 5b00644..257a0fd 100644 --- a/samples/TexturedCube/main.cs +++ b/samples/TexturedCube/main.cs @@ -192,7 +192,7 @@ namespace TextureCube { nextTexture = null; } void updateMatrices () { - matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 5.0f); + matrices.projection = Matrix4x4.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (60f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 5.0f); matrices.view = Matrix4x4.CreateFromAxisAngle (Vector3.UnitZ, rotZ) * Matrix4x4.CreateFromAxisAngle (Vector3.UnitY, rotY) * diff --git a/samples/Triangle/main.cs b/samples/Triangle/main.cs index 075f9f3..aabed92 100644 --- a/samples/Triangle/main.cs +++ b/samples/Triangle/main.cs @@ -111,7 +111,7 @@ namespace Triangle { Matrix4x4.CreateFromAxisAngle (Vector3.UnitY, rotY) * Matrix4x4.CreateFromAxisAngle (Vector3.UnitX, rotX) * Matrix4x4.CreateTranslation (0, 0, -3f * zoom) * - Utils.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (45f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); + Helpers.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (45f), (float)swapChain.Width / (float)swapChain.Height, 0.1f, 256.0f); base.UpdateView (); } diff --git a/samples/Tesselation/README.md b/samples/VulkanContext/README.md similarity index 100% rename from samples/Tesselation/README.md rename to samples/VulkanContext/README.md diff --git a/samples/Tesselation/Tesselation.csproj b/samples/VulkanContext/VulkanContext.csproj similarity index 100% rename from samples/Tesselation/Tesselation.csproj rename to samples/VulkanContext/VulkanContext.csproj diff --git a/samples/VulkanContext/main.cs b/samples/VulkanContext/main.cs new file mode 100644 index 0000000..b15e4bc --- /dev/null +++ b/samples/VulkanContext/main.cs @@ -0,0 +1,21 @@ +// Copyright (c) 2019 Jean-Philippe Bruyère +// +// This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) +using System; +using Vulkan; +using static Vulkan.Vk; +using static Vulkan.Utils; +using Version = Vulkan.Version; +using Context = vke.Context; +using Glfw; + +namespace Tesselation { + class Program { + static void Main (string[] args) { + using (Context ctx = new Context()) { + ctx.Run(); + + } + } + } +} diff --git a/samples/Tesselation/shaders/main.frag b/samples/VulkanContext/shaders/main.frag similarity index 100% rename from samples/Tesselation/shaders/main.frag rename to samples/VulkanContext/shaders/main.frag diff --git a/samples/Tesselation/shaders/main.vert b/samples/VulkanContext/shaders/main.vert similarity index 100% rename from samples/Tesselation/shaders/main.vert rename to samples/VulkanContext/shaders/main.vert diff --git a/samples/common/SampleBase.cs b/samples/common/SampleBase.cs index 959d821..2104a69 100644 --- a/samples/common/SampleBase.cs +++ b/samples/common/SampleBase.cs @@ -6,7 +6,7 @@ namespace vke public abstract class SampleBase : VkWindow { public SampleBase (string name = "VkWindow", uint _width = 800, uint _height = 600, bool vSync = false) : base (name, _width, _height, vSync){} - /*protected override void initVulkan() + protected override void initVulkan() { base.initVulkan(); #if DEBUG @@ -16,6 +16,6 @@ namespace vke Console.ResetColor (); } #endif - }*/ + } } } diff --git a/samples/deferred/DeferredPbrRenderer.cs b/samples/deferred/DeferredPbrRenderer.cs index e1f394a..e37deb4 100644 --- a/samples/deferred/DeferredPbrRenderer.cs +++ b/samples/deferred/DeferredPbrRenderer.cs @@ -408,7 +408,7 @@ namespace deferred { camera.AspectRatio = (float)width / height; matrices.projection = camera.Projection; - //matrices.projection = Utils.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (60), 1, 0.1f, 16f); + //matrices.projection = Utils.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (60), 1, 0.1f, 16f); matrices.view = camera.View; //matrices.view = Matrix4x4.CreateLookAt (lights[0].position.ToVector3 (), Vector3.Zero, Vector3.UnitY); matrices.model = camera.Model; diff --git a/samples/deferred/main.cs b/samples/deferred/main.cs index 5d23027..ecdc687 100644 --- a/samples/deferred/main.cs +++ b/samples/deferred/main.cs @@ -81,7 +81,7 @@ namespace deferred { VkDebugUtilsMessageSeverityFlagsEXT.VerboseEXT); #endif - camera = new Camera (Utils.DegreesToRadians (45f), 1f, 0.1f, 16f); + camera = new Camera (Helpers.DegreesToRadians (45f), 1f, 0.1f, 16f); camera.SetPosition (0, 0, -2); //renderer = new DeferredPbrRenderer (presentQueue, cubemapPathes[2], swapChain.Width, swapChain.Height, camera.NearPlane, camera.FarPlane); diff --git a/samples/deferred/shadowMapRenderer.cs b/samples/deferred/shadowMapRenderer.cs index 511d387..df42f2a 100644 --- a/samples/deferred/shadowMapRenderer.cs +++ b/samples/deferred/shadowMapRenderer.cs @@ -23,7 +23,7 @@ namespace deferred { public float depthBiasConstant = 1.5f; public float depthBiasSlope = 1.75f; - float lightFOV = Utils.DegreesToRadians (60); + float lightFOV = Helpers.DegreesToRadians (60); float lightFarPlane; @@ -112,7 +112,7 @@ namespace deferred { } public void update_light_matrices () { - Matrix4x4 proj = Utils.CreatePerspectiveFieldOfView (lightFOV, 1, 0.1f, lightFarPlane); + Matrix4x4 proj = Helpers.CreatePerspectiveFieldOfView (lightFOV, 1, 0.1f, lightFarPlane); for (int i = 0; i < renderer.lights.Length; i++) { Matrix4x4 view = Matrix4x4.CreateLookAt (renderer.lights[i].position.ToVector3 (), Vector3.Zero, Vector3.UnitY); renderer.lights[i].mvp = view * proj; diff --git a/samples/pbr/main.cs b/samples/pbr/main.cs index a49b701..d0e43bf 100644 --- a/samples/pbr/main.cs +++ b/samples/pbr/main.cs @@ -52,7 +52,7 @@ namespace pbrSample { base.initVulkan (); //UpdateFrequency = 20; - camera = new Camera (Utils.DegreesToRadians (45f), 1f, 0.1f, 64f); + camera = new Camera (Helpers.DegreesToRadians (45f), 1f, 0.1f, 64f); camera.SetPosition (0, 0, -2); pbrPipeline = new PBRPipeline (presentQueue, diff --git a/samples/shadow/DeferredPbrRenderer.cs b/samples/shadow/DeferredPbrRenderer.cs index 0668628..6f6ddea 100644 --- a/samples/shadow/DeferredPbrRenderer.cs +++ b/samples/shadow/DeferredPbrRenderer.cs @@ -410,7 +410,7 @@ namespace deferred { camera.AspectRatio = (float)width / height; matrices.projection = camera.Projection; - //matrices.projection = Utils.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (60), 1, 0.1f, 16f); + //matrices.projection = Utils.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (60), 1, 0.1f, 16f); matrices.view = camera.View; //matrices.view = Matrix4x4.CreateLookAt (lights[0].position.ToVector3 (), Vector3.Zero, Vector3.UnitY); matrices.model = camera.Model; diff --git a/samples/shadow/EnvironmentPipeline.cs b/samples/shadow/EnvironmentPipeline.cs index 32f8e6a..8fde7a0 100644 --- a/samples/shadow/EnvironmentPipeline.cs +++ b/samples/shadow/EnvironmentPipeline.cs @@ -200,17 +200,17 @@ namespace vke { Matrix4x4[] matrices = { // POSITIVE_X - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Utils.DegreesToRadians(90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Helpers.DegreesToRadians(90)), // NEGATIVE_X - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Utils.DegreesToRadians(-90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(180)) * Matrix4x4.CreateRotationY(Helpers.DegreesToRadians(-90)), // POSITIVE_Y - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(-90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(-90)), // NEGATIVE_Y - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(90)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(90)), // POSITIVE_Z - Matrix4x4.CreateRotationX(Utils.DegreesToRadians(180)), + Matrix4x4.CreateRotationX(Helpers.DegreesToRadians(180)), // NEGATIVE_Z - Matrix4x4.CreateRotationZ(Utils.DegreesToRadians(180)) + Matrix4x4.CreateRotationZ(Helpers.DegreesToRadians(180)) }; VkImageSubresourceRange subRes = new VkImageSubresourceRange (VkImageAspectFlags.Color, 0, numMips, 0, 6); @@ -244,7 +244,7 @@ namespace vke { float viewPortSize = (float)Math.Pow (0.5, m) * dim; cmd.SetViewport (viewPortSize, viewPortSize); cmd.PushConstant (pl.Layout, VkShaderStageFlags.Vertex | VkShaderStageFlags.Fragment, - matrices[f] * Matrix4x4.CreatePerspectiveFieldOfView (Utils.DegreesToRadians (90), 1f, 0.1f, 512f)); + matrices[f] * Matrix4x4.CreatePerspectiveFieldOfView (Helpers.DegreesToRadians (90), 1f, 0.1f, 512f)); if (target == CBTarget.IRRADIANCE) { cmd.PushConstant (pl.Layout, VkShaderStageFlags.Vertex | VkShaderStageFlags.Fragment, deltaPhi, (uint)Marshal.SizeOf ()); cmd.PushConstant (pl.Layout, VkShaderStageFlags.Vertex | VkShaderStageFlags.Fragment, deltaTheta, (uint)Marshal.SizeOf () + 4); diff --git a/samples/shadow/main-crow.cs b/samples/shadow/main-crow.cs index f90efcb..ed73ba3 100644 --- a/samples/shadow/main-crow.cs +++ b/samples/shadow/main-crow.cs @@ -150,7 +150,7 @@ namespace deferred { ); #endif - camera = new Camera (Utils.DegreesToRadians (45f), 1f, 0.1f, 16f); + camera = new Camera (Helpers.DegreesToRadians (45f), 1f, 0.1f, 16f); camera.SetPosition (0, 0, 2); renderer = new DeferredPbrRenderer (dev, swapChain, presentQueue, cubemapPathes[2], camera.NearPlane, camera.FarPlane); diff --git a/samples/shadow/main.cs b/samples/shadow/main.cs index 56ba57f..a414854 100644 --- a/samples/shadow/main.cs +++ b/samples/shadow/main.cs @@ -100,7 +100,7 @@ namespace deferred { VkDebugUtilsMessageSeverityFlagsEXT.VerboseEXT); #endif - camera = new Camera (Utils.DegreesToRadians (45f), 1f, 0.1f, 16f); + camera = new Camera (Helpers.DegreesToRadians (45f), 1f, 0.1f, 16f); camera.SetPosition (0, 0, -2); //renderer = new DeferredPbrRenderer (presentQueue, cubemapPathes[2], swapChain.Width, swapChain.Height, camera.NearPlane, camera.FarPlane); diff --git a/samples/shadow/mainShadow.cs b/samples/shadow/mainShadow.cs index 0bc3103..31473ec 100644 --- a/samples/shadow/mainShadow.cs +++ b/samples/shadow/mainShadow.cs @@ -47,7 +47,7 @@ namespace deferredShadow { } Program () : base(true) { - //camera.Model = Matrix4x4.CreateRotationX (Utils.DegreesToRadians (-90)) * Matrix4x4.CreateRotationY (Utils.DegreesToRadians (180)); + //camera.Model = Matrix4x4.CreateRotationX (Helpers.DegreesToRadians (-90)) * Matrix4x4.CreateRotationY (Helpers.DegreesToRadians (180)); //camera.SetRotation (-0.1f,-0.4f); camera.SetPosition (0, 0, -3); diff --git a/samples/shadow/mainWithDebugDrawer.cs b/samples/shadow/mainWithDebugDrawer.cs index f95ed0a..a36e1f7 100644 --- a/samples/shadow/mainWithDebugDrawer.cs +++ b/samples/shadow/mainWithDebugDrawer.cs @@ -44,7 +44,7 @@ namespace deferredDebug { } Program () : base(true) { - camera.Model = Matrix4x4.CreateRotationX (Utils.DegreesToRadians (-90)) * Matrix4x4.CreateRotationY (Utils.DegreesToRadians (180)); + camera.Model = Matrix4x4.CreateRotationX (Helpers.DegreesToRadians (-90)) * Matrix4x4.CreateRotationY (Helpers.DegreesToRadians (180)); camera.SetRotation (-0.1f,-0.4f); camera.SetPosition (0, 0, -3); diff --git a/samples/shadow/shadowMapRenderer.cs b/samples/shadow/shadowMapRenderer.cs index 875e11c..4ce637b 100644 --- a/samples/shadow/shadowMapRenderer.cs +++ b/samples/shadow/shadowMapRenderer.cs @@ -23,7 +23,7 @@ namespace deferred { public float depthBiasConstant = 1.5f; public float depthBiasSlope = 1.75f; - float lightFOV = Utils.DegreesToRadians (60); + float lightFOV = Helpers.DegreesToRadians (60); float lightFarPlane; diff --git a/vke.net.sln b/vke.net.sln index 5d4ccbe..0e5ac98 100644 --- a/vke.net.sln +++ b/vke.net.sln @@ -44,10 +44,10 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "deferred", "samples\deferre EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "pbr", "samples\pbr\pbr.csproj", "{7EB2430B-6BC0-4AE9-B1FA-57C3DB2AE1C5}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Tesselation", "samples\Tesselation\Tesselation.csproj", "{FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}" -EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ExternalMemmories", "samples\ExternalMemmories\ExternalMemmories.csproj", "{85CD9813-E182-4ED1-8D2C-38467657BEF3}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "VulkanContext", "samples\VulkanContext\VulkanContext.csproj", "{CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution BuildPackages|Any CPU = BuildPackages|Any CPU @@ -141,14 +141,6 @@ Global {7EB2430B-6BC0-4AE9-B1FA-57C3DB2AE1C5}.Release|Any CPU.ActiveCfg = Release|Any CPU {7EB2430B-6BC0-4AE9-B1FA-57C3DB2AE1C5}.Release|Any CPU.Build.0 = Release|Any CPU {7EB2430B-6BC0-4AE9-B1FA-57C3DB2AE1C5}.ReleaseSpirVTasks|Any CPU.ActiveCfg = Release|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.BuildPackages|Any CPU.ActiveCfg = Debug|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.BuildPackages|Any CPU.Build.0 = Debug|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.Debug|Any CPU.Build.0 = Debug|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.Release|Any CPU.ActiveCfg = Release|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.Release|Any CPU.Build.0 = Release|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.ReleaseSpirVTasks|Any CPU.ActiveCfg = Debug|Any CPU - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D}.ReleaseSpirVTasks|Any CPU.Build.0 = Debug|Any CPU {85CD9813-E182-4ED1-8D2C-38467657BEF3}.BuildPackages|Any CPU.ActiveCfg = Debug|Any CPU {85CD9813-E182-4ED1-8D2C-38467657BEF3}.BuildPackages|Any CPU.Build.0 = Debug|Any CPU {85CD9813-E182-4ED1-8D2C-38467657BEF3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU @@ -157,6 +149,14 @@ Global {85CD9813-E182-4ED1-8D2C-38467657BEF3}.Release|Any CPU.Build.0 = Release|Any CPU {85CD9813-E182-4ED1-8D2C-38467657BEF3}.ReleaseSpirVTasks|Any CPU.ActiveCfg = Debug|Any CPU {85CD9813-E182-4ED1-8D2C-38467657BEF3}.ReleaseSpirVTasks|Any CPU.Build.0 = Debug|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.BuildPackages|Any CPU.ActiveCfg = Debug|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.BuildPackages|Any CPU.Build.0 = Debug|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.Debug|Any CPU.Build.0 = Debug|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.Release|Any CPU.ActiveCfg = Release|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.Release|Any CPU.Build.0 = Release|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.ReleaseSpirVTasks|Any CPU.ActiveCfg = Debug|Any CPU + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD}.ReleaseSpirVTasks|Any CPU.Build.0 = Debug|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -173,8 +173,8 @@ Global {8185163E-A67C-4C0E-8548-67E2A9F16309} = {16439374-B8DB-4643-8116-EB3358B49A12} {D9A41382-444E-44ED-B638-3D8F06F2FBC2} = {16439374-B8DB-4643-8116-EB3358B49A12} {7EB2430B-6BC0-4AE9-B1FA-57C3DB2AE1C5} = {16439374-B8DB-4643-8116-EB3358B49A12} - {FCE58652-47B9-4A3C-90B0-3B2EE2C8042D} = {16439374-B8DB-4643-8116-EB3358B49A12} {85CD9813-E182-4ED1-8D2C-38467657BEF3} = {16439374-B8DB-4643-8116-EB3358B49A12} + {CF8755E1-9E8B-4AD2-A7D1-D66D797004AD} = {16439374-B8DB-4643-8116-EB3358B49A12} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {1360F94D-CF3C-4121-A8D7-E227F41668F1} diff --git a/vke/src/Camera.cs b/vke/src/Camera.cs index 383e700..739e4cf 100644 --- a/vke/src/Camera.cs +++ b/vke/src/Camera.cs @@ -164,7 +164,7 @@ namespace vke { /// in sync with the parameters. It's automatically called after rotation, move, etc... /// void update () { - Projection = Vulkan.Utils.CreatePerspectiveFieldOfView (fov, aspectRatio, zNear, zFar); + Projection = Helpers.CreatePerspectiveFieldOfView (fov, aspectRatio, zNear, zFar); Matrix4x4 translation = Matrix4x4.CreateTranslation (position * zoom); if (Type == CamType.LookAt) { diff --git a/vke/src/ExtensionMethods.cs b/vke/src/ExtensionMethods.cs index 6c94a66..20fbc35 100644 --- a/vke/src/ExtensionMethods.cs +++ b/vke/src/ExtensionMethods.cs @@ -9,6 +9,7 @@ using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { public static class ExtensionMethods { @@ -31,7 +32,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.CommandBuffer, (ulong)obj.Handle.ToInt64 ()) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } public static void SetDebugMarkerName (this VkImageView obj, Device dev, string name) { @@ -39,7 +40,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.ImageView, (ulong)obj.Handle) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } public static void SetDebugMarkerName (this VkSampler obj, Device dev, string name) { @@ -47,7 +48,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.Sampler, (ulong)obj.Handle) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } public static void SetDebugMarkerName (this VkPipeline obj, Device dev, string name) { @@ -55,7 +56,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.Pipeline, obj.Handle) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } public static void SetDebugMarkerName (this VkDescriptorSet obj, Device dev, string name) { @@ -63,7 +64,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.DescriptorSet, (ulong)obj.Handle) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } public static void SetDebugMarkerName (this VkSemaphore obj, Device dev, string name) { @@ -71,7 +72,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.Semaphore, (ulong)obj.Handle) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } public static void SetDebugMarkerName (this VkFence obj, Device dev, string name) { @@ -79,7 +80,7 @@ namespace vke { return; VkDebugUtilsObjectNameInfoEXT dmo = new VkDebugUtilsObjectNameInfoEXT (VkObjectType.Fence, (ulong)obj.Handle) { pObjectName = name.Pin () }; - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (dev.Handle, ref dmo)); name.Unpin (); } #endregion @@ -107,5 +108,26 @@ namespace vke { } #endregion + public static VkSurfaceKHR CreateSurface (this VkInstance inst, IntPtr hWindow) { + ulong surf; + CheckResult ((VkResult)Glfw.Glfw3.CreateWindowSurface (inst.Handle, hWindow, IntPtr.Zero, out surf), "Create Surface Failed."); + return surf; + } + + public static VkSurfaceFormatKHR [] GetSurfaceFormats (this VkPhysicalDevice phy, VkSurfaceKHR surf) + { + vkGetPhysicalDeviceSurfaceFormatsKHR (phy, surf, out uint count, IntPtr.Zero); + VkSurfaceFormatKHR [] formats = new VkSurfaceFormatKHR [count]; + vkGetPhysicalDeviceSurfaceFormatsKHR (phy, surf, out count, formats.Pin ()); + formats.Unpin (); + return formats; + } + public static VkPresentModeKHR[] GetSurfacePresentModes (this VkPhysicalDevice phy, VkSurfaceKHR surf) { + vkGetPhysicalDeviceSurfacePresentModesKHR (phy, surf, out uint count, IntPtr.Zero); + int[] modes = new int[count]; + vkGetPhysicalDeviceSurfacePresentModesKHR (phy, surf, out count, modes.Pin ()); + modes.Unpin (); + return modes.Cast().ToArray(); + } } } diff --git a/vke/src/MemoryPool.cs b/vke/src/MemoryPool.cs index 76a1901..0a9450d 100644 --- a/vke/src/MemoryPool.cs +++ b/vke/src/MemoryPool.cs @@ -46,7 +46,7 @@ namespace vke { bufferImageGranularity = dev.phy.Limits.bufferImageGranularity; memInfo.allocationSize = size; memInfo.memoryTypeIndex = memoryTypeIndex; - Utils.CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); + CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); } /// /// Allocate memory for a new resource in this memory pool. @@ -140,7 +140,7 @@ namespace vke { /// Size. /// Offset. public void Map (ulong size = Vk.WholeSize, ulong offset = 0) { - Utils.CheckResult (vkMapMemory (Dev.Handle, vkMemory, offset, size, 0, ref mappedPointer)); + CheckResult (vkMapMemory (Dev.Handle, vkMemory, offset, size, 0, ref mappedPointer)); } /// /// Unmap previously mapped memory of this pool. diff --git a/vke/src/ShaderInfo.cs b/vke/src/ShaderInfo.cs index c3fcea1..34138b5 100644 --- a/vke/src/ShaderInfo.cs +++ b/vke/src/ShaderInfo.cs @@ -9,7 +9,7 @@ namespace vke { /// This class is a helper class for VkPipelineShaderStageCreateInfo creation. /// public class ShaderInfo : IDisposable { - protected VkPipelineShaderStageCreateInfo info = VkPipelineShaderStageCreateInfo.New (); + protected VkPipelineShaderStageCreateInfo info; protected Device dev; public VkShaderStageFlags Stage => info.stage; @@ -42,7 +42,7 @@ namespace vke { /// vke Device /// Stage flags. /// - /// Path to a compiled SpirV Shader on disk or as embedded ressource. See for more information. + /// Path to a compiled SpirV Shader on disk or as embedded ressource. See for more information. /// /// Specialization info /// shader entry point, 'main' by default. diff --git a/vke/src/Utils.cs b/vke/src/Utils.cs index f7786d5..86d026b 100644 --- a/vke/src/Utils.cs +++ b/vke/src/Utils.cs @@ -7,15 +7,13 @@ using System.Linq; using System.Numerics; using System.Reflection; using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; using System.Xml.Serialization; +using Vulkan; -namespace Vulkan { - public static partial class Utils { +namespace vke { + public static partial class Helpers { /// Throw an erro if VkResult != Success. - public static void CheckResult (VkResult result, string errorString = "Call failed") { - if (result != VkResult.Success) - throw new InvalidOperationException (errorString + ": " + result.ToString ()); - } static void xmlMakeTypeFieldsAsAttributes (Type t, ref XmlAttributeOverrides overrides) { foreach (FieldInfo fi in t.GetFields (BindingFlags.Public | BindingFlags.Instance)) @@ -84,8 +82,8 @@ namespace Vulkan { } /// Convert angle from degree to radian. public static float DegreesToRadians (float degrees) { - return degrees * (float)Math.PI / 180f; - } + return degrees * (float)Math.PI / 180f; + } /// /// Populate a Vector3 with values from a float array @@ -97,7 +95,7 @@ namespace Vulkan { /// Populate a Vector4 with values from a float array /// public static void FromFloatArray (ref Vector4 v, float[] floats) { - v = Unsafe.As(ref floats)[0]; + MemoryMarshal.Cast(floats.AsSpan()); } /// /// Populate a Quaternion with values from a float array @@ -110,7 +108,7 @@ namespace Vulkan { /// public static void FromByteArray (ref Vector2 v, byte[] byteArray, int offset) { v = Unsafe.As(ref Unsafe.AsRef(byteArray.SubArray(offset, 8)))[0]; - } + } /// /// Populate a Vector3 with values from a byte array starting at offset /// @@ -151,142 +149,142 @@ namespace Vulkan { // Fixed sub resource on first mip level and layer public static void setImageLayout ( - VkCommandBuffer cmdbuffer, - VkImage image, - VkImageAspectFlags aspectMask, - VkImageLayout oldImageLayout, - VkImageLayout newImageLayout, - VkPipelineStageFlags srcStageMask = VkPipelineStageFlags.AllCommands, - VkPipelineStageFlags dstStageMask = VkPipelineStageFlags.AllCommands) { - VkImageSubresourceRange subresourceRange = new VkImageSubresourceRange { - aspectMask = aspectMask, - baseMipLevel = 0, - levelCount = 1, - layerCount = 1, - }; - setImageLayout (cmdbuffer, image, aspectMask, oldImageLayout, newImageLayout, subresourceRange); - } - - // Create an image memory barrier for changing the layout of - // an image and put it into an active command buffer - // See chapter 11.4 "Image Layout" for details - - public static void setImageLayout ( - VkCommandBuffer cmdbuffer, - VkImage image, - VkImageAspectFlags aspectMask, - VkImageLayout oldImageLayout, - VkImageLayout newImageLayout, - VkImageSubresourceRange subresourceRange, - VkPipelineStageFlags srcStageMask = VkPipelineStageFlags.AllCommands, - VkPipelineStageFlags dstStageMask = VkPipelineStageFlags.AllCommands) { - // Create an image barrier object - VkImageMemoryBarrier imageMemoryBarrier = VkImageMemoryBarrier.New(); - imageMemoryBarrier.srcQueueFamilyIndex = Vk.QueueFamilyIgnored; - imageMemoryBarrier.dstQueueFamilyIndex = Vk.QueueFamilyIgnored; - imageMemoryBarrier.oldLayout = oldImageLayout; - imageMemoryBarrier.newLayout = newImageLayout; - imageMemoryBarrier.image = image; - imageMemoryBarrier.subresourceRange = subresourceRange; - - // Source layouts (old) - // Source access mask controls actions that have to be finished on the old layout - // before it will be transitioned to the new layout - switch (oldImageLayout) { - case VkImageLayout.Undefined: - // Image layout is undefined (or does not matter) - // Only valid as initial layout - // No flags required, listed only for completeness - imageMemoryBarrier.srcAccessMask = 0; - break; - - case VkImageLayout.Preinitialized: - // Image is preinitialized - // Only valid as initial layout for linear images, preserves memory contents - // Make sure host writes have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.HostWrite; - break; - - case VkImageLayout.ColorAttachmentOptimal: - // Image is a color attachment - // Make sure any writes to the color buffer have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.ColorAttachmentWrite; - break; - - case VkImageLayout.DepthStencilAttachmentOptimal: - // Image is a depth/stencil attachment - // Make sure any writes to the depth/stencil buffer have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.DepthStencilAttachmentWrite; - break; - - case VkImageLayout.TransferSrcOptimal: - // Image is a transfer source - // Make sure any reads from the image have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.TransferRead; - break; - - case VkImageLayout.TransferDstOptimal: - // Image is a transfer destination - // Make sure any writes to the image have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.TransferWrite; - break; - - case VkImageLayout.ShaderReadOnlyOptimal: - // Image is read by a shader - // Make sure any shader reads from the image have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.ShaderRead; - break; - } - - // Target layouts (new) - // Destination access mask controls the dependency for the new image layout - switch (newImageLayout) { - case VkImageLayout.TransferDstOptimal: - // Image will be used as a transfer destination - // Make sure any writes to the image have been finished - imageMemoryBarrier.dstAccessMask = VkAccessFlags.TransferWrite; - break; - - case VkImageLayout.TransferSrcOptimal: - // Image will be used as a transfer source - // Make sure any reads from and writes to the image have been finished - imageMemoryBarrier.srcAccessMask = imageMemoryBarrier.srcAccessMask | VkAccessFlags.TransferRead; - imageMemoryBarrier.dstAccessMask = VkAccessFlags.TransferRead; - break; - - case VkImageLayout.ColorAttachmentOptimal: - // Image will be used as a color attachment - // Make sure any writes to the color buffer have been finished - imageMemoryBarrier.srcAccessMask = VkAccessFlags.TransferRead; - imageMemoryBarrier.dstAccessMask = VkAccessFlags.ColorAttachmentWrite; - break; - - case VkImageLayout.DepthStencilAttachmentOptimal: - // Image layout will be used as a depth/stencil attachment - // Make sure any writes to depth/stencil buffer have been finished - imageMemoryBarrier.dstAccessMask = imageMemoryBarrier.dstAccessMask | VkAccessFlags.DepthStencilAttachmentWrite; - break; - - case VkImageLayout.ShaderReadOnlyOptimal: - // Image will be read in a shader (sampler, input attachment) - // Make sure any writes to the image have been finished - if (imageMemoryBarrier.srcAccessMask == 0) { - imageMemoryBarrier.srcAccessMask = VkAccessFlags.HostWrite | VkAccessFlags.TransferWrite; - } - imageMemoryBarrier.dstAccessMask = VkAccessFlags.ShaderRead; - break; - } - - // Put barrier inside setup command buffer - Vk.vkCmdPipelineBarrier ( - cmdbuffer, - srcStageMask, - dstStageMask, - 0, - 0, IntPtr.Zero, - 0, IntPtr.Zero, - 1, ref imageMemoryBarrier); - } + VkCommandBuffer cmdbuffer, + VkImage image, + VkImageAspectFlags aspectMask, + VkImageLayout oldImageLayout, + VkImageLayout newImageLayout, + VkPipelineStageFlags srcStageMask = VkPipelineStageFlags.AllCommands, + VkPipelineStageFlags dstStageMask = VkPipelineStageFlags.AllCommands) { + VkImageSubresourceRange subresourceRange = new VkImageSubresourceRange { + aspectMask = aspectMask, + baseMipLevel = 0, + levelCount = 1, + layerCount = 1, + }; + setImageLayout (cmdbuffer, image, aspectMask, oldImageLayout, newImageLayout, subresourceRange); + } + + // Create an image memory barrier for changing the layout of + // an image and put it into an active command buffer + // See chapter 11.4 "Image Layout" for details + + public static void setImageLayout ( + VkCommandBuffer cmdbuffer, + VkImage image, + VkImageAspectFlags aspectMask, + VkImageLayout oldImageLayout, + VkImageLayout newImageLayout, + VkImageSubresourceRange subresourceRange, + VkPipelineStageFlags srcStageMask = VkPipelineStageFlags.AllCommands, + VkPipelineStageFlags dstStageMask = VkPipelineStageFlags.AllCommands) { + // Create an image barrier object + VkImageMemoryBarrier imageMemoryBarrier = default; + imageMemoryBarrier.srcQueueFamilyIndex = Vk.QueueFamilyIgnored; + imageMemoryBarrier.dstQueueFamilyIndex = Vk.QueueFamilyIgnored; + imageMemoryBarrier.oldLayout = oldImageLayout; + imageMemoryBarrier.newLayout = newImageLayout; + imageMemoryBarrier.image = image; + imageMemoryBarrier.subresourceRange = subresourceRange; + + // Source layouts (old) + // Source access mask controls actions that have to be finished on the old layout + // before it will be transitioned to the new layout + switch (oldImageLayout) { + case VkImageLayout.Undefined: + // Image layout is undefined (or does not matter) + // Only valid as initial layout + // No flags required, listed only for completeness + imageMemoryBarrier.srcAccessMask = 0; + break; + + case VkImageLayout.Preinitialized: + // Image is preinitialized + // Only valid as initial layout for linear images, preserves memory contents + // Make sure host writes have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.HostWrite; + break; + + case VkImageLayout.ColorAttachmentOptimal: + // Image is a color attachment + // Make sure any writes to the color buffer have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.ColorAttachmentWrite; + break; + + case VkImageLayout.DepthStencilAttachmentOptimal: + // Image is a depth/stencil attachment + // Make sure any writes to the depth/stencil buffer have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.DepthStencilAttachmentWrite; + break; + + case VkImageLayout.TransferSrcOptimal: + // Image is a transfer source + // Make sure any reads from the image have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.TransferRead; + break; + + case VkImageLayout.TransferDstOptimal: + // Image is a transfer destination + // Make sure any writes to the image have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.TransferWrite; + break; + + case VkImageLayout.ShaderReadOnlyOptimal: + // Image is read by a shader + // Make sure any shader reads from the image have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.ShaderRead; + break; + } + + // Target layouts (new) + // Destination access mask controls the dependency for the new image layout + switch (newImageLayout) { + case VkImageLayout.TransferDstOptimal: + // Image will be used as a transfer destination + // Make sure any writes to the image have been finished + imageMemoryBarrier.dstAccessMask = VkAccessFlags.TransferWrite; + break; + + case VkImageLayout.TransferSrcOptimal: + // Image will be used as a transfer source + // Make sure any reads from and writes to the image have been finished + imageMemoryBarrier.srcAccessMask = imageMemoryBarrier.srcAccessMask | VkAccessFlags.TransferRead; + imageMemoryBarrier.dstAccessMask = VkAccessFlags.TransferRead; + break; + + case VkImageLayout.ColorAttachmentOptimal: + // Image will be used as a color attachment + // Make sure any writes to the color buffer have been finished + imageMemoryBarrier.srcAccessMask = VkAccessFlags.TransferRead; + imageMemoryBarrier.dstAccessMask = VkAccessFlags.ColorAttachmentWrite; + break; + + case VkImageLayout.DepthStencilAttachmentOptimal: + // Image layout will be used as a depth/stencil attachment + // Make sure any writes to depth/stencil buffer have been finished + imageMemoryBarrier.dstAccessMask = imageMemoryBarrier.dstAccessMask | VkAccessFlags.DepthStencilAttachmentWrite; + break; + + case VkImageLayout.ShaderReadOnlyOptimal: + // Image will be read in a shader (sampler, input attachment) + // Make sure any writes to the image have been finished + if (imageMemoryBarrier.srcAccessMask == 0) { + imageMemoryBarrier.srcAccessMask = VkAccessFlags.HostWrite | VkAccessFlags.TransferWrite; + } + imageMemoryBarrier.dstAccessMask = VkAccessFlags.ShaderRead; + break; + } + + // Put barrier inside setup command buffer + Vk.vkCmdPipelineBarrier ( + cmdbuffer, + srcStageMask, + dstStageMask, + 0, + 0, IntPtr.Zero, + 0, IntPtr.Zero, + 1, ref imageMemoryBarrier); + } /// /// Find usage flags and aspect flag from image layout /// diff --git a/vke/src/VkFormatSize.cs b/vke/src/VkFormatSize.cs index 9f816f4..6495575 100644 --- a/vke/src/VkFormatSize.cs +++ b/vke/src/VkFormatSize.cs @@ -2,8 +2,9 @@ // // This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) using System; +using Vulkan; -namespace Vulkan { +namespace vke { [Flags] public enum VkFormatSizeFlag { SizePacked = 0x00000001, @@ -12,7 +13,7 @@ namespace Vulkan { SizeDepth = 0x00000008, SizeStencil = 0x00000010, }; - + public struct VkFormatSize { public VkFormatSizeFlag flags; public uint paletteSizeInBits; @@ -23,7 +24,7 @@ namespace Vulkan { }; - public static partial class Utils { + public static partial class Helpers { public static void vkGetFormatSize(VkFormat format, out VkFormatSize pFormatSize ) { switch ( format ) diff --git a/vke/src/VkWindow.cs b/vke/src/VkWindow.cs index 65dd3dd..1fa6203 100644 --- a/vke/src/VkWindow.cs +++ b/vke/src/VkWindow.cs @@ -45,7 +45,7 @@ namespace vke { public IntPtr WindowHandle => hWin; /**Default camera initialized with a Field of view of 40° and and aspect ratio of 1. */ - protected Camera camera = new Camera (Utils.DegreesToRadians (45f), 1f); + protected Camera camera = new Camera (Helpers.DegreesToRadians (45f), 1f); public Modifier KeyModifiers = 0; IntPtr currentCursor; diff --git a/vke/src/base/Activable.cs b/vke/src/base/Activable.cs index 02dec89..81a88b7 100644 --- a/vke/src/base/Activable.cs +++ b/vke/src/base/Activable.cs @@ -5,6 +5,7 @@ using System; using System.Xml.Serialization; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -74,7 +75,7 @@ namespace vke { VkDebugUtilsObjectNameInfoEXT dmo = DebugUtilsInfo; dmo.pObjectName = name.Pin(); - Utils.CheckResult (vkSetDebugUtilsObjectNameEXT (Dev.Handle, ref dmo)); + CheckResult (vkSetDebugUtilsObjectNameEXT (Dev.Handle, ref dmo)); name.Unpin (); } /// diff --git a/vke/src/base/Buffer.cs b/vke/src/base/Buffer.cs index 74f74bc..c252575 100644 --- a/vke/src/base/Buffer.cs +++ b/vke/src/base/Buffer.cs @@ -4,6 +4,7 @@ using System; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { @@ -12,7 +13,7 @@ namespace vke { /// public class Buffer : Resource { internal VkBuffer handle; - protected VkBufferCreateInfo createInfo = VkBufferCreateInfo.New (); + protected VkBufferCreateInfo createInfo; /// Native handle of this vulkan buffer. /// The handle. public VkBuffer Handle => handle; @@ -47,7 +48,7 @@ namespace vke { /// public sealed override void Activate () { if (state != ActivableState.Activated) { - Utils.CheckResult (vkCreateBuffer (Dev.Handle, ref createInfo, IntPtr.Zero, out handle)); + CheckResult (vkCreateBuffer (Dev.Handle, ref createInfo, IntPtr.Zero, out handle)); #if MEMORY_POOLS Dev.resourceManager.Add (this); #else @@ -66,9 +67,9 @@ namespace vke { internal override void bindMemory () { #if MEMORY_POOLS - Utils.CheckResult (vkBindBufferMemory (Dev.Handle, handle, memoryPool.vkMemory, poolOffset)); + CheckResult (vkBindBufferMemory (Dev.Handle, handle, memoryPool.vkMemory, poolOffset)); #else - Utils.CheckResult (vkBindBufferMemory (Dev.Handle, handle, vkMemory, 0)); + CheckResult (vkBindBufferMemory (Dev.Handle, handle, vkMemory, 0)); #endif } #endregion diff --git a/vke/src/base/CommandBuffer.cs b/vke/src/base/CommandBuffer.cs index a25b23a..aaad0f5 100644 --- a/vke/src/base/CommandBuffer.cs +++ b/vke/src/base/CommandBuffer.cs @@ -6,6 +6,7 @@ using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { public class SecondaryCommandBuffer : CommandBuffer { @@ -13,7 +14,7 @@ namespace vke { } public void Start (VkCommandBufferUsageFlags usage = 0, RenderPass rp = null, uint subpass = 0, FrameBuffer fb = null, bool occlusionQueryEnable = false, VkQueryControlFlags queryFlags = 0, VkQueryPipelineStatisticFlags statFlags = 0) { - VkCommandBufferInheritanceInfo inheri = VkCommandBufferInheritanceInfo.New (); + VkCommandBufferInheritanceInfo inheri = default; inheri.renderPass = rp == null ? 0 : rp.handle; inheri.subpass = subpass; inheri.framebuffer = fb == null ? 0 : fb.handle; @@ -22,7 +23,7 @@ namespace vke { inheri.pipelineStatistics = statFlags; VkCommandBufferBeginInfo cmdBufInfo = new VkCommandBufferBeginInfo (usage); cmdBufInfo.pInheritanceInfo = inheri; - Utils.CheckResult (vkBeginCommandBuffer (handle, ref cmdBufInfo)); + CheckResult (vkBeginCommandBuffer (handle, ref cmdBufInfo)); cmdBufInfo.Dispose(); } } @@ -37,7 +38,7 @@ namespace vke { /// Signal. /// Fence. public void Submit (VkQueue queue, VkSemaphore wait = default, VkSemaphore signal = default, Fence fence = null) { - VkSubmitInfo submit_info = VkSubmitInfo.New (); + VkSubmitInfo submit_info = default; submit_info.pWaitDstStageMask = VkPipelineStageFlags.ColorAttachmentOutput; if (signal == VkSemaphore.Null) submit_info.pSignalSemaphores = null; @@ -50,7 +51,7 @@ namespace vke { submit_info.pWaitSemaphores = wait; submit_info.pCommandBuffers = handle; - Utils.CheckResult (vkQueueSubmit (queue, 1, ref submit_info, fence)); + CheckResult (vkQueueSubmit (queue, 1, submit_info, fence)); submit_info.Dispose(); } /// @@ -59,7 +60,7 @@ namespace vke { /// optional command buffer usage flags. public void Start (VkCommandBufferUsageFlags usage = 0) { VkCommandBufferBeginInfo cmdBufInfo = new VkCommandBufferBeginInfo (usage); - Utils.CheckResult (vkBeginCommandBuffer (handle, ref cmdBufInfo)); + CheckResult (vkBeginCommandBuffer (handle, ref cmdBufInfo)); } /// /// Execute secondary command buffers. @@ -116,7 +117,7 @@ namespace vke { /// Put the command buffer in the executable state if no errors are present in the recording. /// public void End () { - Utils.CheckResult (vkEndCommandBuffer (handle)); + CheckResult (vkEndCommandBuffer (handle)); } /// /// Update dynamic viewport state @@ -199,7 +200,7 @@ namespace vke { } public void SetMemoryBarrier (VkPipelineStageFlags srcStageMask, VkPipelineStageFlags dstStageMask, VkAccessFlags srcAccessMask, VkAccessFlags dstAccessMask, VkDependencyFlags dependencyFlags = VkDependencyFlags.ByRegion) { - VkMemoryBarrier memoryBarrier = VkMemoryBarrier.New (); + VkMemoryBarrier memoryBarrier = default; memoryBarrier.srcAccessMask = srcAccessMask; memoryBarrier.dstAccessMask = dstAccessMask; Vk.vkCmdPipelineBarrier (Handle, srcStageMask, dstStageMask, @@ -208,7 +209,7 @@ namespace vke { public void BeginRegion (string name, float r = 1f, float g = 0.1f, float b=0.1f, float a = 1f) { if (!Device.debugUtilsEnabled) return; - VkDebugMarkerMarkerInfoEXT info = VkDebugMarkerMarkerInfoEXT.New(); + VkDebugMarkerMarkerInfoEXT info = default; info.pMarkerName = name.Pin (); info.color.X = r; info.color.Y = g; @@ -220,7 +221,7 @@ namespace vke { public void InsertDebugMarker (string name, float r = 1f, float g = 0.1f, float b=0.1f, float a = 1f) { if (!Device.debugUtilsEnabled) return; - VkDebugMarkerMarkerInfoEXT info = VkDebugMarkerMarkerInfoEXT.New(); + VkDebugMarkerMarkerInfoEXT info = default; info.pMarkerName = name.Pin (); info.color.X = r; info.color.Y = g; diff --git a/vke/src/base/CommandPool.cs b/vke/src/base/CommandPool.cs index 1278fa6..55f0f97 100644 --- a/vke/src/base/CommandPool.cs +++ b/vke/src/base/CommandPool.cs @@ -5,6 +5,7 @@ using System; using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -46,10 +47,10 @@ namespace vke { public override void Activate () { if (state != ActivableState.Activated) { - VkCommandPoolCreateInfo infos = VkCommandPoolCreateInfo.New(); + VkCommandPoolCreateInfo infos = default; infos.queueFamilyIndex = QFamIndex; infos.flags = Flags; - Utils.CheckResult (vkCreateCommandPool (Dev.Handle, ref infos, IntPtr.Zero, out handle)); + CheckResult (vkCreateCommandPool (Dev.Handle, ref infos, IntPtr.Zero, out handle)); } base.Activate (); } @@ -60,12 +61,12 @@ namespace vke { /// The command buffer in the Init state. public PrimaryCommandBuffer AllocateCommandBuffer () { VkCommandBuffer buff; - VkCommandBufferAllocateInfo infos = VkCommandBufferAllocateInfo.New(); + VkCommandBufferAllocateInfo infos = default; infos.commandPool = handle; infos.level = VkCommandBufferLevel.Primary; infos.commandBufferCount = 1; - Utils.CheckResult (vkAllocateCommandBuffers (Dev.Handle, ref infos, out buff)); + CheckResult (vkAllocateCommandBuffers (Dev.Handle, ref infos, out buff)); return new PrimaryCommandBuffer (Dev.Handle, this, buff); } @@ -76,12 +77,12 @@ namespace vke { /// The command buffer in the Init state. public SecondaryCommandBuffer AllocateSecondaryCommandBuffer () { VkCommandBuffer buff; - VkCommandBufferAllocateInfo infos = VkCommandBufferAllocateInfo.New (); + VkCommandBufferAllocateInfo infos = default; infos.commandPool = handle; infos.level = VkCommandBufferLevel.Secondary; infos.commandBufferCount = 1; - Utils.CheckResult (vkAllocateCommandBuffers (Dev.Handle, ref infos, out buff)); + CheckResult (vkAllocateCommandBuffers (Dev.Handle, ref infos, out buff)); return new SecondaryCommandBuffer (Dev.Handle, this, buff); } @@ -92,12 +93,12 @@ namespace vke { /// An array of command buffers alloocated from this pool. /// Buffer count to create. public PrimaryCommandBuffer[] AllocateCommandBuffer (uint count) { - VkCommandBufferAllocateInfo infos = VkCommandBufferAllocateInfo.New (); + VkCommandBufferAllocateInfo infos = default; infos.commandPool = handle; infos.level = VkCommandBufferLevel.Primary; infos.commandBufferCount = count; VkCommandBuffer[] buffs = new VkCommandBuffer[count]; - Utils.CheckResult (vkAllocateCommandBuffers (Dev.Handle, ref infos, buffs.Pin())); + CheckResult (vkAllocateCommandBuffers (Dev.Handle, ref infos, buffs.Pin())); buffs.Unpin (); PrimaryCommandBuffer[] cmds = new PrimaryCommandBuffer[count]; for (int i = 0; i < count; i++) diff --git a/vke/src/base/ComputePipeline.cs b/vke/src/base/ComputePipeline.cs index a202f11..efea103 100644 --- a/vke/src/base/ComputePipeline.cs +++ b/vke/src/base/ComputePipeline.cs @@ -5,6 +5,7 @@ using System; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { public sealed class ComputePipeline : Pipeline { @@ -32,13 +33,13 @@ namespace vke { Cache?.Activate (); using (ShaderInfo shader = new ShaderInfo (Dev, VkShaderStageFlags.Compute, SpirVPath)) { - VkComputePipelineCreateInfo info = VkComputePipelineCreateInfo.New (); + VkComputePipelineCreateInfo info = default; info.layout = layout.Handle; info.stage = shader.Info; info.basePipelineHandle = 0; info.basePipelineIndex = 0; - Utils.CheckResult (Vk.vkCreateComputePipelines (Dev.Handle, Cache == null ? VkPipelineCache.Null : Cache.handle, 1, ref info, IntPtr.Zero, out handle)); + CheckResult (Vk.vkCreateComputePipelines (Dev.Handle, Cache == null ? VkPipelineCache.Null : Cache.handle, 1, ref info, IntPtr.Zero, out handle)); } } base.Activate (); diff --git a/vke/src/base/DebugReport.cs b/vke/src/base/DebugReport.cs index e5e8e88..0fddb68 100644 --- a/vke/src/base/DebugReport.cs +++ b/vke/src/base/DebugReport.cs @@ -5,10 +5,11 @@ using System; using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { [Obsolete("Use the new VK_EXT_debug_utils extension")] - public class DebugReport : IDisposable { + public class DebugReport : IDisposable { VkDebugReportCallbackEXT handle; Instance inst; @@ -52,7 +53,7 @@ namespace vke { Console.ForegroundColor = ConsoleColor.White; return VkBool32.False; } - + public DebugReport (Instance instance, VkDebugReportFlagsEXT flags = VkDebugReportFlagsEXT.ErrorEXT | VkDebugReportFlagsEXT.WarningEXT) { inst = instance; @@ -62,7 +63,7 @@ namespace vke { pfnCallback = Marshal.GetFunctionPointerForDelegate (debugCallbackDelegate) }; - Utils.CheckResult (vkCreateDebugReportCallbackEXT (inst.Handle, ref dbgInfo, IntPtr.Zero, out handle)); + CheckResult (vkCreateDebugReportCallbackEXT (inst.Handle, ref dbgInfo, IntPtr.Zero, out handle)); } #region IDisposable Support diff --git a/vke/src/base/DebugUtilsMessenger.cs b/vke/src/base/DebugUtilsMessenger.cs index 67f13d9..1cd8935 100644 --- a/vke/src/base/DebugUtilsMessenger.cs +++ b/vke/src/base/DebugUtilsMessenger.cs @@ -6,6 +6,7 @@ using System.Runtime.InteropServices; using System.Text; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke.DebugUtils { /// @@ -73,13 +74,13 @@ namespace vke.DebugUtils { VkDebugUtilsMessageSeverityFlagsEXT.ErrorEXT | VkDebugUtilsMessageSeverityFlagsEXT.WarningEXT) { inst = instance; - VkDebugUtilsMessengerCreateInfoEXT info = VkDebugUtilsMessengerCreateInfoEXT.New (); + VkDebugUtilsMessengerCreateInfoEXT info = default; info.messageType = typeMask; info.messageSeverity = severityMask; info.pfnUserCallback = Marshal.GetFunctionPointerForDelegate (onMessageDelegate); info.pUserData = IntPtr.Zero; - Utils.CheckResult (vkCreateDebugUtilsMessengerEXT (inst.VkInstance, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateDebugUtilsMessengerEXT (inst.VkInstance, ref info, IntPtr.Zero, out handle)); } /// /// Create a new debug utils messenger with default message callback outputing to Console. diff --git a/vke/src/base/DescriptorPool.cs b/vke/src/base/DescriptorPool.cs index b832f6a..604332d 100644 --- a/vke/src/base/DescriptorPool.cs +++ b/vke/src/base/DescriptorPool.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { [Serializable] @@ -43,11 +44,11 @@ namespace vke { public sealed override void Activate () { if (state != ActivableState.Activated) { - VkDescriptorPoolCreateInfo info = VkDescriptorPoolCreateInfo.New(); + VkDescriptorPoolCreateInfo info = default; info.pPoolSizes = PoolSizes; info.maxSets = MaxSets; - Utils.CheckResult (vkCreateDescriptorPool (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateDescriptorPool (Dev.Handle, ref info, IntPtr.Zero, out handle)); info.Dispose(); } base.Activate (); @@ -63,24 +64,24 @@ namespace vke { return ds; } public void Allocate (DescriptorSet descriptorSet) { - VkDescriptorSetAllocateInfo allocInfo = VkDescriptorSetAllocateInfo.New(); + VkDescriptorSetAllocateInfo allocInfo = default; allocInfo.descriptorPool = handle; allocInfo.pSetLayouts = descriptorSet.descriptorSetLayouts; - Utils.CheckResult (vkAllocateDescriptorSets (Dev.Handle, ref allocInfo, out descriptorSet.handle)); + CheckResult (vkAllocateDescriptorSets (Dev.Handle, ref allocInfo, out descriptorSet.handle)); allocInfo.Dispose(); } public void FreeDescriptorSet (params DescriptorSet[] descriptorSets) { if (descriptorSets.Length == 1) { - Utils.CheckResult (vkFreeDescriptorSets (Dev.Handle, handle, 1, ref descriptorSets[0].handle)); + CheckResult (vkFreeDescriptorSets (Dev.Handle, handle, 1, ref descriptorSets[0].handle)); return; } - Utils.CheckResult (vkFreeDescriptorSets (Dev.Handle, handle, (uint)descriptorSets.Length, descriptorSets.Pin())); + CheckResult (vkFreeDescriptorSets (Dev.Handle, handle, (uint)descriptorSets.Length, descriptorSets.Pin())); descriptorSets.Unpin (); } public void Reset () { - Utils.CheckResult (vkResetDescriptorPool (Dev.Handle, handle, 0)); + CheckResult (vkResetDescriptorPool (Dev.Handle, handle, 0)); } public override string ToString () { diff --git a/vke/src/base/DescriptorSetLayout.cs b/vke/src/base/DescriptorSetLayout.cs index 3b29edc..291db74 100644 --- a/vke/src/base/DescriptorSetLayout.cs +++ b/vke/src/base/DescriptorSetLayout.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -38,7 +39,7 @@ namespace vke { public override void Activate () { if (state != ActivableState.Activated) { VkDescriptorSetLayoutCreateInfo info = new VkDescriptorSetLayoutCreateInfo (Flags, (uint)Bindings.Count, Bindings.Pin()); - Utils.CheckResult (vkCreateDescriptorSetLayout (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateDescriptorSetLayout (Dev.Handle, ref info, IntPtr.Zero, out handle)); Bindings.Unpin (); } base.Activate (); diff --git a/vke/src/base/DescriptorSetWrites.cs b/vke/src/base/DescriptorSetWrites.cs index b6fdeca..9260798 100644 --- a/vke/src/base/DescriptorSetWrites.cs +++ b/vke/src/base/DescriptorSetWrites.cs @@ -62,7 +62,7 @@ namespace vke { /// with another descriptorSet in parametters /// public void AddWriteInfo (DescriptorSet destSet, VkDescriptorSetLayoutBinding binding) { - VkWriteDescriptorSet wds = VkWriteDescriptorSet.New(); + VkWriteDescriptorSet wds = default; wds.descriptorType = binding.descriptorType; wds.descriptorCount = binding.descriptorCount; wds.dstBinding = binding.binding; @@ -82,7 +82,7 @@ namespace vke { /// provide a desDescriptor! /// public void AddWriteInfo (VkDescriptorSetLayoutBinding binding) { - VkWriteDescriptorSet wds = VkWriteDescriptorSet.New(); + VkWriteDescriptorSet wds = default; wds.descriptorType = binding.descriptorType; wds.descriptorCount = binding.descriptorCount; wds.dstBinding = binding.binding; @@ -107,6 +107,7 @@ namespace vke { while (i < descriptors.Length) { int firstDescriptor = i; VkWriteDescriptorSet wds = WriteDescriptorSets[wdsPtr]; + wds.sType = VkStructureType.WriteDescriptorSet; if (dstSetOverride != null) wds.dstSet = dstSetOverride.Value.Handle; @@ -177,7 +178,7 @@ namespace vke { public void AddWriteInfo (DescriptorSet destSet, VkDescriptorSetLayoutBinding binding, VkDescriptorBufferInfo descriptor) { if (!descriptors.Contains (descriptor)) descriptors.Add (descriptor); - VkWriteDescriptorSet wds = VkWriteDescriptorSet.New(); + VkWriteDescriptorSet wds = default; wds.descriptorType = binding.descriptorType; wds.descriptorCount = binding.descriptorCount; wds.dstBinding = binding.binding; @@ -189,7 +190,7 @@ namespace vke { public void AddWriteInfo (DescriptorSet destSet, VkDescriptorSetLayoutBinding binding, VkDescriptorImageInfo descriptor) { if (!descriptors.Contains (descriptor)) descriptors.Add (descriptor); - VkWriteDescriptorSet wds = VkWriteDescriptorSet.New(); + VkWriteDescriptorSet wds = default; wds.descriptorType = binding.descriptorType; wds.descriptorCount = binding.descriptorCount; wds.dstBinding = binding.binding; diff --git a/vke/src/base/Device.cs b/vke/src/base/Device.cs index cd47146..8020b35 100644 --- a/vke/src/base/Device.cs +++ b/vke/src/base/Device.cs @@ -9,7 +9,7 @@ using System.Reflection; using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; - +using static Vulkan.Utils; namespace vke { /// @@ -73,7 +73,7 @@ namespace vke { Console.WriteLine ($"Unsupported device extension: {extensions[i]}"); } - VkDeviceCreateInfo deviceCreateInfo = VkDeviceCreateInfo.New (); + VkDeviceCreateInfo deviceCreateInfo = new VkDeviceCreateInfo (); deviceCreateInfo.pQueueCreateInfos = qInfos; deviceCreateInfo.pEnabledFeatures = enabledFeatures; @@ -82,7 +82,7 @@ namespace vke { deviceCreateInfo.ppEnabledExtensionNames = deviceExtensions.Pin (); } - Utils.CheckResult (vkCreateDevice (phy.Handle, ref deviceCreateInfo, IntPtr.Zero, out dev)); + CheckResult (vkCreateDevice (phy.Handle, ref deviceCreateInfo, IntPtr.Zero, out dev)); deviceCreateInfo.Dispose(); foreach (VkDeviceQueueCreateInfo qI in qInfos) @@ -106,8 +106,8 @@ namespace vke { /// The semaphore native handle public VkSemaphore CreateSemaphore () { VkSemaphore tmp; - VkSemaphoreCreateInfo info = VkSemaphoreCreateInfo.New (); - Utils.CheckResult (vkCreateSemaphore (dev, ref info, IntPtr.Zero, out tmp)); + VkSemaphoreCreateInfo info = default; + CheckResult (vkCreateSemaphore (dev, ref info, IntPtr.Zero, out tmp)); return tmp; } public void DestroySemaphore (VkSemaphore semaphore) { @@ -123,24 +123,24 @@ namespace vke { /// Wait for this logical device to enter the idle state. /// public void WaitIdle () { - Utils.CheckResult (vkDeviceWaitIdle (dev)); + CheckResult (vkDeviceWaitIdle (dev)); } public VkRenderPass CreateRenderPass (VkRenderPassCreateInfo info) { VkRenderPass renderPass; - Utils.CheckResult (vkCreateRenderPass (dev, ref info, IntPtr.Zero, out renderPass)); + CheckResult (vkCreateRenderPass (dev, ref info, IntPtr.Zero, out renderPass)); return renderPass; } public VkImageView CreateImageView (VkImage image, VkFormat format, VkImageViewType viewType = VkImageViewType.ImageView2D, VkImageAspectFlags aspectFlags = VkImageAspectFlags.Color) { VkImageView view; - VkImageViewCreateInfo infos = VkImageViewCreateInfo.New (); + VkImageViewCreateInfo infos = default; infos.image = image; infos.viewType = viewType; infos.format = format; infos.components = new VkComponentMapping { r = VkComponentSwizzle.R, g = VkComponentSwizzle.G, b = VkComponentSwizzle.B, a = VkComponentSwizzle.A }; infos.subresourceRange = new VkImageSubresourceRange (aspectFlags); - Utils.CheckResult (vkCreateImageView (dev, ref infos, IntPtr.Zero, out view)); + CheckResult (vkCreateImageView (dev, ref infos, IntPtr.Zero, out view)); return view; } public void DestroyImageView (VkImageView view) { @@ -191,7 +191,7 @@ namespace vke { /// the vulkan shader module. /// path of the spv shader. public VkShaderModule CreateShaderModule (string filename) { - using (Stream stream = Utils.GetStreamFromPath (filename)) { + using (Stream stream = Helpers.GetStreamFromPath (filename)) { using (BinaryReader br = new BinaryReader (stream)) { byte[] shaderCode = br.ReadBytes ((int)stream.Length); UIntPtr shaderSize = (UIntPtr)shaderCode.Length; @@ -208,12 +208,10 @@ namespace vke { /// the call to this method. /// spirv code byte size. public VkShaderModule CreateShaderModule (uint[] code, UIntPtr codeSize) { - VkShaderModuleCreateInfo moduleCreateInfo = VkShaderModuleCreateInfo.New (); - moduleCreateInfo.codeSize = codeSize; - moduleCreateInfo.pCode = code; - Utils.CheckResult (vkCreateShaderModule (Handle, ref moduleCreateInfo, IntPtr.Zero, out VkShaderModule shaderModule)); - moduleCreateInfo.Dispose(); - return shaderModule; + using (VkShaderModuleCreateInfo moduleCreateInfo = new VkShaderModuleCreateInfo (codeSize, code)) { + CheckResult (vkCreateShaderModule (Handle, moduleCreateInfo, IntPtr.Zero, out VkShaderModule shaderModule)); + return shaderModule; + } } #region IDisposable Support diff --git a/vke/src/base/Fence.cs b/vke/src/base/Fence.cs index ab04404..6d4ef6b 100644 --- a/vke/src/base/Fence.cs +++ b/vke/src/base/Fence.cs @@ -6,6 +6,7 @@ using System.Collections.ObjectModel; using System.Linq; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -13,7 +14,7 @@ namespace vke { /// public class Fence : Activable { internal VkFence handle; - VkFenceCreateInfo info = VkFenceCreateInfo.New (); + VkFenceCreateInfo info = default; public Fence (Device dev, bool signaled = false, string name = "fence") : base (dev, name) { info.flags = signaled ? VkFenceCreateFlags.Signaled : 0; @@ -25,7 +26,7 @@ namespace vke { public sealed override void Activate () { if (state != ActivableState.Activated) { - Utils.CheckResult (vkCreateFence (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateFence (Dev.Handle, ref info, IntPtr.Zero, out handle)); } base.Activate (); } diff --git a/vke/src/base/FrameBuffer.cs b/vke/src/base/FrameBuffer.cs index 5cb9332..e6319aa 100644 --- a/vke/src/base/FrameBuffer.cs +++ b/vke/src/base/FrameBuffer.cs @@ -7,6 +7,7 @@ using System.Linq; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { @@ -18,7 +19,7 @@ namespace vke { RenderPass renderPass; public List attachments = new List (); - VkFramebufferCreateInfo createInfo = VkFramebufferCreateInfo.New (); + VkFramebufferCreateInfo createInfo; /// Framebuffer width. public uint Width => createInfo.width; /// Framebuffer height. @@ -65,8 +66,8 @@ namespace vke { VkImageUsageFlags usage = 0; VkImageAspectFlags aspectFlags = 0; - Utils.QueryLayoutRequirements (ad.initialLayout, ref usage, ref aspectFlags); - Utils.QueryLayoutRequirements (ad.finalLayout, ref usage, ref aspectFlags); + Helpers.QueryLayoutRequirements (ad.initialLayout, ref usage, ref aspectFlags); + Helpers.QueryLayoutRequirements (ad.finalLayout, ref usage, ref aspectFlags); foreach (SubPass sp in renderPass.SubPasses) { //TODO:check subpass usage } @@ -92,7 +93,7 @@ namespace vke { if (PNext != null) createInfo.pNext = PNext.GetPointer(); - Utils.CheckResult (vkCreateFramebuffer (renderPass.Dev.Handle, ref createInfo, IntPtr.Zero, out handle)); + CheckResult (vkCreateFramebuffer (renderPass.Dev.Handle, ref createInfo, IntPtr.Zero, out handle)); createInfo.Dispose(); diff --git a/vke/src/base/GraphicPipeline.cs b/vke/src/base/GraphicPipeline.cs index 01a8ef4..c20cd1f 100644 --- a/vke/src/base/GraphicPipeline.cs +++ b/vke/src/base/GraphicPipeline.cs @@ -6,6 +6,7 @@ using System.Collections.Generic; using Vulkan; using System.Linq; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { public class GraphicPipeline : Pipeline { @@ -53,20 +54,20 @@ namespace vke { using (PinnedObjects pctx = new PinnedObjects ()) { - VkPipelineColorBlendStateCreateInfo colorBlendInfo = VkPipelineColorBlendStateCreateInfo.New (); + VkPipelineColorBlendStateCreateInfo colorBlendInfo = default; colorBlendInfo.logicOpEnable = cfg.ColorBlendLogicOpEnable; colorBlendInfo.logicOp = cfg.ColorBlendLogicOp; colorBlendInfo.blendConstants = cfg.ColorBlendConstants; colorBlendInfo.pAttachments = cfg.blendAttachments; - VkPipelineDynamicStateCreateInfo dynStatesInfo = VkPipelineDynamicStateCreateInfo.New (); + VkPipelineDynamicStateCreateInfo dynStatesInfo = default; dynStatesInfo.pDynamicStates = cfg.dynamicStates; - VkPipelineVertexInputStateCreateInfo vertInputInfo = VkPipelineVertexInputStateCreateInfo.New (); + VkPipelineVertexInputStateCreateInfo vertInputInfo = default; vertInputInfo.pVertexBindingDescriptions = cfg.vertexBindings; vertInputInfo.pVertexAttributeDescriptions = cfg.vertexAttributes; - VkPipelineViewportStateCreateInfo viewportState = VkPipelineViewportStateCreateInfo.New (); + VkPipelineViewportStateCreateInfo viewportState = default; if (cfg.Viewports.Count > 0) { viewportState.pViewports = cfg.Viewports; } else @@ -77,7 +78,7 @@ namespace vke { } else viewportState.scissorCount = 1; - VkGraphicsPipelineCreateInfo info = VkGraphicsPipelineCreateInfo.New (); + VkGraphicsPipelineCreateInfo info = default; info.renderPass = RenderPass.handle; info.layout = Layout.handle; info.pVertexInputState = vertInputInfo; @@ -92,12 +93,12 @@ namespace vke { info.subpass = cfg.SubpassIndex; if (enableTesselation) { - VkPipelineTessellationStateCreateInfo tessellationInfo = VkPipelineTessellationStateCreateInfo.New(); + VkPipelineTessellationStateCreateInfo tessellationInfo = default; tessellationInfo.patchControlPoints = cfg.TessellationPatchControlPoints; info.pTessellationState = tessellationInfo; } - Utils.CheckResult (vkCreateGraphicsPipelines (Dev.Handle, Cache == null ? VkPipelineCache.Null : Cache.handle, 1, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateGraphicsPipelines (Dev.Handle, Cache == null ? VkPipelineCache.Null : Cache.handle, 1, ref info, IntPtr.Zero, out handle)); vertInputInfo.Dispose(); viewportState.Dispose(); diff --git a/vke/src/base/GraphicPipelineConfig.cs b/vke/src/base/GraphicPipelineConfig.cs index 97be93b..1e656a1 100644 --- a/vke/src/base/GraphicPipelineConfig.cs +++ b/vke/src/base/GraphicPipelineConfig.cs @@ -35,12 +35,12 @@ namespace vke { /// VkPipelineBindPoint.Graphics is set by default, /// public VkPipelineBindPoint bindPoint = VkPipelineBindPoint.Graphics; - public VkPipelineInputAssemblyStateCreateInfo inputAssemblyState = VkPipelineInputAssemblyStateCreateInfo.New (); - public VkPipelineRasterizationStateCreateInfo rasterizationState = VkPipelineRasterizationStateCreateInfo.New (); + public VkPipelineInputAssemblyStateCreateInfo inputAssemblyState; + public VkPipelineRasterizationStateCreateInfo rasterizationState; public List Viewports = new List (); public List Scissors = new List (); - public VkPipelineDepthStencilStateCreateInfo depthStencilState = VkPipelineDepthStencilStateCreateInfo.New (); - public VkPipelineMultisampleStateCreateInfo multisampleState = VkPipelineMultisampleStateCreateInfo.New (); + public VkPipelineDepthStencilStateCreateInfo depthStencilState; + public VkPipelineMultisampleStateCreateInfo multisampleState; public List blendAttachments = new List (); public List dynamicStates = new List (); public List vertexBindings = new List (); @@ -122,7 +122,7 @@ namespace vke { for (uint i = 0; i < attribsDesc.Length; i++) { vertexAttributes.Add (new VkVertexInputAttributeDescription (binding, i + currentAttributeIndex, attribsDesc[i], currentAttributeoffset)); VkFormatSize fs; - Utils.vkGetFormatSize (attribsDesc[i], out fs); + Helpers.vkGetFormatSize (attribsDesc[i], out fs); currentAttributeoffset += fs.blockSizeInBits / 8; } currentAttributeIndex += (uint)attribsDesc.Length; diff --git a/vke/src/base/Image.cs b/vke/src/base/Image.cs index 821053a..7cdfb37 100644 --- a/vke/src/base/Image.cs +++ b/vke/src/base/Image.cs @@ -7,6 +7,7 @@ using System.Diagnostics; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -24,7 +25,7 @@ namespace vke { public static VkFormat DefaultTextureFormat = VkFormat.R8g8b8a8Unorm; internal VkImage handle; - VkImageCreateInfo info = VkImageCreateInfo.New (); + VkImageCreateInfo info; uint[] queuesFamillies; /// @@ -436,14 +437,14 @@ namespace vke { } internal override void bindMemory () { #if MEMORY_POOLS - Utils.CheckResult (vkBindImageMemory (Dev.Handle, handle, memoryPool.vkMemory, poolOffset)); + CheckResult (vkBindImageMemory (Dev.Handle, handle, memoryPool.vkMemory, poolOffset)); #else - Utils.CheckResult (vkBindImageMemory (Dev.Handle, handle, vkMemory, 0)); + CheckResult (vkBindImageMemory (Dev.Handle, handle, vkMemory, 0)); #endif } public sealed override void Activate () { if (state != ActivableState.Activated) { - VkExternalMemoryImageCreateInfo externalImgInfo = VkExternalMemoryImageCreateInfo.New (); + VkExternalMemoryImageCreateInfo externalImgInfo = default; if (importExportHandleTypes > 0 && importedHandle != IntPtr.Zero) { externalImgInfo.handleTypes = importExportHandleTypes; info.pNext = externalImgInfo.Pin (); @@ -452,9 +453,9 @@ namespace vke { if (info.sharingMode == VkSharingMode.Concurrent && queuesFamillies?.Length > 0) { info.queueFamilyIndexCount = (uint)queuesFamillies.Length; info.pQueueFamilyIndices = queuesFamillies; - Utils.CheckResult (vkCreateImage (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateImage (Dev.Handle, ref info, IntPtr.Zero, out handle)); } else - Utils.CheckResult (vkCreateImage (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreateImage (Dev.Handle, ref info, IntPtr.Zero, out handle)); if (importExportHandleTypes > 0 && importedHandle != IntPtr.Zero) externalImgInfo.Unpin (); @@ -473,7 +474,7 @@ namespace vke { } public Image ExportTo (Device targetdev, VkExternalMemoryHandleTypeFlags handleTypes) { - VkMemoryHostPointerPropertiesEXT hostPointerProps = VkMemoryHostPointerPropertiesEXT.New(); + VkMemoryHostPointerPropertiesEXT hostPointerProps = default; VkResult res = vkGetMemoryHostPointerPropertiesEXT (Dev.Handle, handleTypes, importedHandle, out hostPointerProps); if (res != VkResult.Success) return null; @@ -496,7 +497,7 @@ namespace vke { layerCount = 1; VkImageView view = default (VkImageView); - VkImageViewCreateInfo viewInfo = VkImageViewCreateInfo.New (); + VkImageViewCreateInfo viewInfo = default; viewInfo.image = handle; viewInfo.viewType = type; viewInfo.format = Format; @@ -510,7 +511,7 @@ namespace vke { viewInfo.subresourceRange.baseArrayLayer = baseArrayLayer; viewInfo.subresourceRange.layerCount = layerCount < 0 ? info.arrayLayers : (uint)layerCount; - Utils.CheckResult (vkCreateImageView (Dev.Handle, ref viewInfo, IntPtr.Zero, out view)); + CheckResult (vkCreateImageView (Dev.Handle, ref viewInfo, IntPtr.Zero, out view)); if (Descriptor.imageView.Handle != 0) Dev.DestroyImageView (Descriptor.imageView); @@ -536,7 +537,7 @@ namespace vke { VkSamplerMipmapMode mipmapMode = VkSamplerMipmapMode.Linear, VkSamplerAddressMode addressMode = VkSamplerAddressMode.Repeat, float maxAnisotropy = 1.0f, float minLod = 0.0f, float maxLod = -1f) { VkSampler sampler; - VkSamplerCreateInfo sampInfo = VkSamplerCreateInfo.New (); + VkSamplerCreateInfo sampInfo = default; sampInfo.maxAnisotropy = maxAnisotropy; sampInfo.maxAnisotropy = 1.0f;// device->enabledFeatures.samplerAnisotropy ? device->properties.limits.maxSamplerAnisotropy : 1.0f; //samplerInfo.anisotropyEnable = device->enabledFeatures.samplerAnisotropy; @@ -551,7 +552,7 @@ namespace vke { sampInfo.compareOp = VkCompareOp.Never; sampInfo.borderColor = VkBorderColor.FloatOpaqueWhite; - Utils.CheckResult (vkCreateSampler (Dev.Handle, ref sampInfo, IntPtr.Zero, out sampler)); + CheckResult (vkCreateSampler (Dev.Handle, ref sampInfo, IntPtr.Zero, out sampler)); if (Descriptor.sampler.Handle != 0) Dev.DestroySampler (Descriptor.sampler); @@ -616,7 +617,7 @@ namespace vke { uint srcQueueFamilyIndex = Vk.QueueFamilyIgnored, uint dstQueueFamilyIndex = Vk.QueueFamilyIgnored) { - VkImageMemoryBarrier imageMemoryBarrier = VkImageMemoryBarrier.New (); + VkImageMemoryBarrier imageMemoryBarrier = default; imageMemoryBarrier.srcQueueFamilyIndex = srcQueueFamilyIndex; imageMemoryBarrier.dstQueueFamilyIndex = dstQueueFamilyIndex; imageMemoryBarrier.oldLayout = oldImageLayout; @@ -649,7 +650,7 @@ namespace vke { uint srcQueueFamilyIndex = Vk.QueueFamilyIgnored, uint dstQueueFamilyIndex = Vk.QueueFamilyIgnored) { // Create an image barrier object - VkImageMemoryBarrier imageMemoryBarrier = VkImageMemoryBarrier.New (); + VkImageMemoryBarrier imageMemoryBarrier = default; imageMemoryBarrier.srcQueueFamilyIndex = srcQueueFamilyIndex; imageMemoryBarrier.dstQueueFamilyIndex = dstQueueFamilyIndex; imageMemoryBarrier.oldLayout = oldImageLayout; diff --git a/vke/src/base/Instance.cs b/vke/src/base/Instance.cs index de1fe5b..966383a 100644 --- a/vke/src/base/Instance.cs +++ b/vke/src/base/Instance.cs @@ -7,6 +7,7 @@ using System.Linq; using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -85,7 +86,7 @@ namespace vke { pEngineName = APPLICATION_NAME, }; - VkInstanceCreateInfo instanceCreateInfo = VkInstanceCreateInfo.New (); + VkInstanceCreateInfo instanceCreateInfo = default; instanceCreateInfo.pApplicationInfo = appInfo; if (instanceExtensions.Count > 0) { @@ -109,11 +110,11 @@ namespace vke { } public static string[] SupportedExtensions () => SupportedExtensions (IntPtr.Zero); public static string[] SupportedExtensions (IntPtr layer) { - Utils.CheckResult (vkEnumerateInstanceExtensionProperties (layer, out uint count, IntPtr.Zero)); + CheckResult (vkEnumerateInstanceExtensionProperties (layer, out uint count, IntPtr.Zero)); int sizeStruct = Marshal.SizeOf (); IntPtr ptrSupExts = Marshal.AllocHGlobal (sizeStruct * (int)count); - Utils.CheckResult (vkEnumerateInstanceExtensionProperties (layer, out count, ptrSupExts)); + CheckResult (vkEnumerateInstanceExtensionProperties (layer, out count, ptrSupExts)); string[] result = new string[count]; IntPtr tmp = ptrSupExts; @@ -132,7 +133,7 @@ namespace vke { /// public VkSurfaceKHR CreateSurface (IntPtr hWindow) { ulong surf; - Utils.CheckResult ((VkResult)Glfw.Glfw3.CreateWindowSurface (inst.Handle, hWindow, IntPtr.Zero, out surf), "Create Surface Failed."); + CheckResult ((VkResult)Glfw.Glfw3.CreateWindowSurface (inst.Handle, hWindow, IntPtr.Zero, out surf), "Create Surface Failed."); return surf; } public void GetDelegate (string name, out T del) { diff --git a/vke/src/base/PhysicalDevice.cs b/vke/src/base/PhysicalDevice.cs index 1ab1d48..859f129 100644 --- a/vke/src/base/PhysicalDevice.cs +++ b/vke/src/base/PhysicalDevice.cs @@ -89,7 +89,6 @@ namespace vke { vkGetPhysicalDeviceQueueFamilyProperties (phy, out queueFamilyCount, QueueFamilies.Pin ()); QueueFamilies.Unpin (); - Console.WriteLine("PhysicalDeviceCollection"); HasSwapChainSupport = GetDeviceExtensionSupported (Ext.D.VK_KHR_swapchain); } @@ -168,10 +167,10 @@ namespace vke { return result == VkResult.Success; } public VkPhysicalDeviceToolPropertiesEXT[] GetToolProperties () { - Utils.CheckResult (vkGetPhysicalDeviceToolPropertiesEXT (phy , out uint count, IntPtr.Zero)); + CheckResult (vkGetPhysicalDeviceToolPropertiesEXT (phy , out uint count, IntPtr.Zero)); int sizeStruct = Marshal.SizeOf (); IntPtr ptrTools = Marshal.AllocHGlobal (sizeStruct * (int)count); - Utils.CheckResult (vkGetPhysicalDeviceToolPropertiesEXT (phy , out count, ptrTools)); + CheckResult (vkGetPhysicalDeviceToolPropertiesEXT (phy , out count, ptrTools)); VkPhysicalDeviceToolPropertiesEXT[] result = new VkPhysicalDeviceToolPropertiesEXT[count]; IntPtr tmp = ptrTools; diff --git a/vke/src/base/PipelineCache.cs b/vke/src/base/PipelineCache.cs index abc739b..0ec2e48 100644 --- a/vke/src/base/PipelineCache.cs +++ b/vke/src/base/PipelineCache.cs @@ -9,6 +9,7 @@ using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -54,7 +55,7 @@ namespace vke { string path = Path.Combine (globalConfigPath, cacheFile); if (state != ActivableState.Activated) { - VkPipelineCacheCreateInfo info = VkPipelineCacheCreateInfo.New (); + VkPipelineCacheCreateInfo info = default; if (File.Exists (path) && LoadOnActivation) { using (FileStream fs = File.Open (path, FileMode.Open)) { @@ -67,7 +68,7 @@ namespace vke { } } - Utils.CheckResult (vkCreatePipelineCache (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreatePipelineCache (Dev.Handle, ref info, IntPtr.Zero, out handle)); if (info.pInitialData != IntPtr.Zero) Marshal.FreeHGlobal (info.pInitialData); @@ -95,9 +96,9 @@ namespace vke { File.Delete (path); UIntPtr dataSize; - Utils.CheckResult (vkGetPipelineCacheData (Dev.Handle, handle, out dataSize, IntPtr.Zero)); + CheckResult (vkGetPipelineCacheData (Dev.Handle, handle, out dataSize, IntPtr.Zero)); byte[] pData = new byte[(int)dataSize]; - Utils.CheckResult (vkGetPipelineCacheData (Dev.Handle, handle, out dataSize, pData.Pin ())); + CheckResult (vkGetPipelineCacheData (Dev.Handle, handle, out dataSize, pData.Pin ())); pData.Unpin (); using (FileStream fs = File.Open (path, FileMode.CreateNew)) diff --git a/vke/src/base/PipelineLayout.cs b/vke/src/base/PipelineLayout.cs index 42a0975..7227097 100644 --- a/vke/src/base/PipelineLayout.cs +++ b/vke/src/base/PipelineLayout.cs @@ -6,6 +6,7 @@ using System.Collections.Generic; using System.Linq; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { public sealed class PipelineLayout : Activable { @@ -46,7 +47,7 @@ namespace vke { if (state != ActivableState.Activated) { foreach (DescriptorSetLayout dsl in DescriptorSetLayouts) dsl.Activate (); - VkPipelineLayoutCreateInfo info = VkPipelineLayoutCreateInfo.New(); + VkPipelineLayoutCreateInfo info = default; VkDescriptorSetLayout[] dsls = DescriptorSetLayouts.Select (dsl => dsl.handle).ToArray (); if (dsls.Length > 0) { @@ -55,7 +56,7 @@ namespace vke { if (PushConstantRanges.Count > 0) { info.pPushConstantRanges = PushConstantRanges; } - Utils.CheckResult (vkCreatePipelineLayout (Dev.Handle, ref info, IntPtr.Zero, out handle)); + CheckResult (vkCreatePipelineLayout (Dev.Handle, ref info, IntPtr.Zero, out handle)); info.Dispose(); diff --git a/vke/src/base/QueryPool.cs b/vke/src/base/QueryPool.cs index f17c46b..53987e2 100644 --- a/vke/src/base/QueryPool.cs +++ b/vke/src/base/QueryPool.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { public class TimestampQueryPool : QueryPool { @@ -87,7 +88,7 @@ namespace vke { } } - public abstract class QueryPool : Activable { + public abstract class QueryPool : Activable { protected VkQueryPool handle; protected readonly VkQueryPoolCreateInfo createInfos; public readonly VkQueryType QueryType; @@ -97,7 +98,7 @@ namespace vke { protected QueryPool (Device device, VkQueryType queryType, VkQueryPipelineStatisticFlags statisticFlags, uint count = 1) : base(device) { - createInfos = VkQueryPoolCreateInfo.New (queryType, statisticFlags, count); + createInfos = VkQueryPoolCreateInfo.CreateNew (queryType, statisticFlags, count); //Activate (); } @@ -109,8 +110,8 @@ namespace vke { public override void Activate () { if (state != ActivableState.Activated) { - VkQueryPoolCreateInfo infos = createInfos; - Utils.CheckResult (vkCreateQueryPool (Dev.Handle, ref infos, IntPtr.Zero, out handle)); + VkQueryPoolCreateInfo infos = createInfos; + CheckResult (vkCreateQueryPool (Dev.Handle, ref infos, IntPtr.Zero, out handle)); } base.Activate (); } @@ -123,7 +124,7 @@ namespace vke { return results; } - + public override string ToString () { return string.Format ($"{base.ToString ()}[0x{handle.Handle.ToString("x")}]"); } diff --git a/vke/src/base/Queue.cs b/vke/src/base/Queue.cs index 13fa8c5..8325bcb 100644 --- a/vke/src/base/Queue.cs +++ b/vke/src/base/Queue.cs @@ -5,6 +5,7 @@ using System; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { @@ -36,10 +37,10 @@ namespace vke { } public void Present (VkPresentInfoKHR present) { - Utils.CheckResult (vkQueuePresentKHR (handle, ref present)); + CheckResult (vkQueuePresentKHR (handle, ref present)); } public void Present (SwapChain swapChain, VkSemaphore wait) { - VkPresentInfoKHR present = VkPresentInfoKHR.New(); + VkPresentInfoKHR present = default; uint idx = swapChain.currentImageIndex; VkSwapchainKHR sc = swapChain.Handle; @@ -89,7 +90,7 @@ namespace vke { cmd.Submit (handle, wait, signal, fence); } public void WaitIdle () { - Utils.CheckResult (vkQueueWaitIdle (handle)); + CheckResult (vkQueueWaitIdle (handle)); } uint searchQFamily (VkQueueFlags requestedFlags) { diff --git a/vke/src/base/RenderPass.cs b/vke/src/base/RenderPass.cs index ea9cda9..95683fd 100644 --- a/vke/src/base/RenderPass.cs +++ b/vke/src/base/RenderPass.cs @@ -104,7 +104,7 @@ namespace vke { foreach (SubPass sp in subpasses) spDescs.Add (sp.SubpassDescription); - VkRenderPassCreateInfo renderPassInfo = VkRenderPassCreateInfo.New(); + VkRenderPassCreateInfo renderPassInfo = default; renderPassInfo.pAttachments = attachments; renderPassInfo.pSubpasses = spDescs; renderPassInfo.pDependencies = dependencies; @@ -198,16 +198,16 @@ namespace vke { /// public void Begin (PrimaryCommandBuffer cmd, FrameBuffer frameBuffer, uint width, uint height, VkSubpassContents contents = VkSubpassContents.Inline) { - VkRenderPassBeginInfo info = VkRenderPassBeginInfo.New(); - info.renderPass = handle; - info.renderArea.extent.width = width; - info.renderArea.extent.height = height; - info.pClearValues = ClearValues; - info.framebuffer = frameBuffer.handle; + using (VkRenderPassBeginInfo info = new VkRenderPassBeginInfo { + renderPass = handle, + renderArea = new VkRect2D (default, new VkExtent2D (width, height)), + pClearValues = ClearValues, + framebuffer = frameBuffer.handle + }){ - vkCmdBeginRenderPass (cmd.Handle, ref info, contents); + vkCmdBeginRenderPass (cmd.Handle, info, contents); - info.Dispose (); + } } /// /// Switch to next subpass diff --git a/vke/src/base/Resource.cs b/vke/src/base/Resource.cs index 77a8d4d..dfb2df0 100644 --- a/vke/src/base/Resource.cs +++ b/vke/src/base/Resource.cs @@ -8,6 +8,7 @@ using System.Runtime.InteropServices; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -66,7 +67,7 @@ namespace vke { #if !MEMORY_POOLS protected uint importedMemoryTypeBits = 0; protected void allocateMemory () { - VkMemoryAllocateInfo memInfo = VkMemoryAllocateInfo.New (); + VkMemoryAllocateInfo memInfo = default; memInfo.allocationSize = memReqs.size; /*if (importedMemoryTypeBits > 0) memReqs.memoryTypeBits = importedMemoryTypeBits;*/ @@ -74,22 +75,22 @@ namespace vke { if (importExportHandleTypes > 0) { if (importedHandle != IntPtr.Zero) { - VkImportMemoryHostPointerInfoEXT importInfo = VkImportMemoryHostPointerInfoEXT.New (); + VkImportMemoryHostPointerInfoEXT importInfo = default; importInfo.pHostPointer = importedHandle.Pin(); importInfo.handleType = importExportHandleTypes; memInfo.pNext = importInfo.Pin (); - Utils.CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); + CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); importedHandle.Unpin(); importInfo.Unpin (); } else { - VkExportMemoryAllocateInfo exportInfo = VkExportMemoryAllocateInfo.New (); + VkExportMemoryAllocateInfo exportInfo = default; exportInfo.handleTypes = importExportHandleTypes; memInfo.pNext = exportInfo.Pin (); - Utils.CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); + CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); exportInfo.Unpin (); } } else - Utils.CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); + CheckResult (vkAllocateMemory (Dev.Handle, ref memInfo, IntPtr.Zero, out vkMemory)); } #endif public bool IsMapped => mappedData != IntPtr.Zero; @@ -99,7 +100,7 @@ namespace vke { memoryPool.Map (); mappedData = new IntPtr (memoryPool.MappedData.ToInt64 () + (long)(poolOffset + offset)); #else - Utils.CheckResult (vkMapMemory (Dev.Handle, vkMemory, offset, AllocatedDeviceMemorySize, 0, ref mappedData)); + CheckResult (vkMapMemory (Dev.Handle, vkMemory, offset, AllocatedDeviceMemorySize, 0, ref mappedData)); #endif } public void Unmap () { diff --git a/vke/src/base/SwapChain.cs b/vke/src/base/SwapChain.cs index d87e461..aa916b1 100644 --- a/vke/src/base/SwapChain.cs +++ b/vke/src/base/SwapChain.cs @@ -5,6 +5,7 @@ using System; using Vulkan; using static Vulkan.Vk; +using static Vulkan.Utils; namespace vke { /// @@ -56,7 +57,7 @@ namespace vke { : base (_presentableQueue.dev) { presentQueue = _presentableQueue; - createInfos = VkSwapchainCreateInfoKHR.New (); + createInfos = default; VkSurfaceFormatKHR[] formats = Dev.phy.GetSurfaceFormats (presentQueue.Surface); for (int i = 0; i < formats.Length; i++) { @@ -120,7 +121,7 @@ namespace vke { } else createInfos.imageExtent = capabilities.currentExtent; - Utils.CheckResult (vkCreateSwapchainKHR (Dev.Handle, ref createInfos, IntPtr.Zero, out VkSwapchainKHR newSwapChain)); + CheckResult (vkCreateSwapchainKHR (Dev.Handle, ref createInfos, IntPtr.Zero, out VkSwapchainKHR newSwapChain)); if (Handle.Handle != 0) _destroy (); @@ -129,11 +130,11 @@ namespace vke { presentComplete.SetDebugMarkerName (Dev, "Semaphore PresentComplete"); Handle = newSwapChain; - Utils.CheckResult (vkGetSwapchainImagesKHR (Dev.Handle, Handle, out uint imageCount, IntPtr.Zero)); + CheckResult (vkGetSwapchainImagesKHR (Dev.Handle, Handle, out uint imageCount, IntPtr.Zero)); if (imageCount == 0) throw new Exception ("Swapchain image count is 0."); VkImage[] imgs = new VkImage[imageCount]; - Utils.CheckResult (vkGetSwapchainImagesKHR (Dev.Handle, Handle, out imageCount, imgs.Pin ())); + CheckResult (vkGetSwapchainImagesKHR (Dev.Handle, Handle, out imageCount, imgs.Pin ())); imgs.Unpin (); images = new Image[imgs.Length]; @@ -155,7 +156,7 @@ namespace vke { Create (); return -1; } - Utils.CheckResult (res); + CheckResult (res); return (int)currentImageIndex; } diff --git a/vke/src/base/VulkanContext.cs b/vke/src/base/VulkanContext.cs new file mode 100644 index 0000000..df6d2fe --- /dev/null +++ b/vke/src/base/VulkanContext.cs @@ -0,0 +1,254 @@ +// Copyright (c) 2021 Jean-Philippe Bruyère +// +// This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) +using System; +using System.Runtime.InteropServices; +using System.Runtime.CompilerServices; +using Vulkan; +using static Vulkan.Vk; +using static Vulkan.Utils; +using System.Linq; +using System.Collections.Generic; +using Glfw; + +namespace vke { + public class Context : IDisposable { + /** GLFW callback may return a custom pointer, this list makes the link between the GLFW window pointer and the + manage VkWindow instance. */ + static Dictionary windows = new Dictionary(); + /** GLFW window native pointer. */ + IntPtr hWin; + /**Vulkan Surface */ + protected VkSurfaceKHR hSurf; + VkInstance inst; + VkPhysicalDevice phy; + VkDevice dev; + VkQueue queue; + VkSwapchainCreateInfoKHR createInfos; + VkSwapchainKHR swapchainHandle; + + public VkInstance Inst => inst; + public VkPhysicalDevice Phy => phy; + public VkDevice Dev=> dev; + public VkQueue Queue => queue; + public uint Width { get; private set; } + public uint Height { get; private set; } + public bool VSync { get; private set; } + + VkPresentModeKHR presentMode => VSync ? VkPresentModeKHR.FifoKHR : VkPresentModeKHR.MailboxKHR; + + public Context (uint width = 800, uint height = 600, VkFormat format = VkFormat.B8g8r8a8Unorm, + VkImageUsageFlags IMAGES_USAGE = VkImageUsageFlags.ColorAttachment, + string windowName = "vulkan") { + + Width = width; + Height = height; + + Glfw3.Init (); + + Glfw3.WindowHint (WindowAttribute.ClientApi, 0); + Glfw3.WindowHint (WindowAttribute.Resizable, 1); + + hWin = Glfw3.CreateWindow ((int)Width, (int)Height, windowName, MonitorHandle.Zero, IntPtr.Zero); + windows.Add (hWin, this); + + if (hWin == IntPtr.Zero) + throw new Exception ("[GLFW3] Unable to create vulkan Window"); + + Glfw3.SetKeyCallback (hWin, HandleKeyDelegate); + Glfw3.SetMouseButtonPosCallback (hWin, HandleMouseButtonDelegate); + Glfw3.SetCursorPosCallback (hWin, HandleCursorPosDelegate); + Glfw3.SetScrollCallback (hWin, HandleScrollDelegate); + Glfw3.SetCharCallback (hWin, HandleCharDelegate); + + string[] exts = Glfw3.GetRequiredInstanceExtensions (); + + IntPtr[] extensions = new IntPtr[exts.Length]; + for (int i = 0; i < exts.Length; i++) + extensions[i] = exts[i].PinPointer(); + + using (VkApplicationInfo ai = new VkApplicationInfo ()) { + using (VkInstanceCreateInfo ci = new VkInstanceCreateInfo { + pApplicationInfo = ai, + enabledExtensionCount = (uint)extensions.Length, + ppEnabledExtensionNames = extensions.Pin() }){ + CheckResult (vkCreateInstance (ci, IntPtr.Zero, out inst)); + } + } + extensions.Unpin(); + for (int i = 0; i < extensions.Length; i++) + extensions[i].Unpin(); + + Vk.LoadInstanceFunctionPointers (inst); + + hSurf = inst.CreateSurface (hWin); + + if (!inst.TryGetPhysicalDevice (VkPhysicalDeviceType.DiscreteGpu, out phy)) + if (!inst.TryGetPhysicalDevice (VkPhysicalDeviceType.IntegratedGpu, out phy)) + if (!inst.TryGetPhysicalDevice (VkPhysicalDeviceType.Cpu, out phy)) + throw new Exception ("no suitable physical device found"); + + VkQueueFamilyProperties[] qFamProps = phy.GetQueueFamilyProperties (); + + uint qFamIndex = (uint)qFamProps.Select((qFam, index) => (qFam, index)) + .First (qfp=>qfp.qFam.queueFlags.HasFlag (VkQueueFlags.Graphics)).index; + + float[] priorities = {0}; + + exts = new string[] { Ext.D.VK_KHR_swapchain }; + extensions = new IntPtr[exts.Length]; + for (int i = 0; i < exts.Length; i++) + extensions[i] = exts[i].PinPointer(); + + using (VkDeviceQueueCreateInfo qInfo = new VkDeviceQueueCreateInfo (qFamIndex,1,priorities)) { + using (VkDeviceCreateInfo deviceCreateInfo = new VkDeviceCreateInfo () { + pQueueCreateInfos = qInfo, + enabledExtensionCount = (uint)extensions.Length, + ppEnabledExtensionNames = extensions.Pin() }) { + + CheckResult (vkCreateDevice (phy, deviceCreateInfo, IntPtr.Zero, out dev)); + + } + } + Vk.LoadDeviceFunctionPointers (dev); + vkGetDeviceQueue (dev, qFamIndex, 0, out VkQueue gQ); + + VkSurfaceFormatKHR[] formats = phy.GetSurfaceFormats (hSurf); + for (int i = 0; i < formats.Length; i++) { + if (formats[i].format == format) { + createInfos.imageFormat = format; + createInfos.imageColorSpace = formats[i].colorSpace; + break; + } + } + if (createInfos.imageFormat == VkFormat.Undefined) + throw new Exception ("Invalid format for swapchain: " + format); + + VkPresentModeKHR[] presentModes = phy.GetSurfacePresentModes (hSurf); + for (int i = 0; i < presentModes.Length; i++) { + if (presentModes[i] == presentMode) { + createInfos.presentMode = presentMode; + break; + } + } + if (createInfos.presentMode != presentMode) + throw new Exception ("Invalid presentMode for swapchain: " + presentMode); + + createInfos.surface = hSurf; + createInfos.imageExtent = new VkExtent2D (Width, Height); + createInfos.imageArrayLayers = 1; + createInfos.imageUsage = IMAGES_USAGE; + createInfos.imageSharingMode = VkSharingMode.Exclusive; + createInfos.compositeAlpha = VkCompositeAlphaFlagsKHR.OpaqueKHR; + createInfos.presentMode = presentMode; + createInfos.clipped = 1; + vkGetPhysicalDeviceSurfaceCapabilitiesKHR (phy, hSurf, out VkSurfaceCapabilitiesKHR capabilities); + createInfos.minImageCount = capabilities.minImageCount; + createInfos.preTransform = capabilities.currentTransform; + + CreateSwapChain(); + } + + internal void CreateSwapChain () { + vkDeviceWaitIdle (dev); + vkGetPhysicalDeviceSurfaceCapabilitiesKHR (phy, hSurf, out VkSurfaceCapabilitiesKHR caps); + createInfos.oldSwapchain = swapchainHandle; + + if (caps.currentExtent.width == 0xFFFFFFFF) { + if (createInfos.imageExtent.width < caps.minImageExtent.width) + createInfos.imageExtent.width = caps.minImageExtent.width; + else if (createInfos.imageExtent.width > caps.maxImageExtent.width) + createInfos.imageExtent.width = caps.maxImageExtent.width; + + if (createInfos.imageExtent.height < caps.minImageExtent.height) + createInfos.imageExtent.height = caps.minImageExtent.height; + else if (createInfos.imageExtent.height > caps.maxImageExtent.height) + createInfos.imageExtent.height = caps.maxImageExtent.height; + } else + createInfos.imageExtent = caps.currentExtent; + + CheckResult (vkCreateSwapchainKHR (dev, ref createInfos, IntPtr.Zero, out VkSwapchainKHR newSwapChain)); + + if (swapchainHandle != VkSwapchainKHR.Null) + vkDestroySwapchainKHR (dev, swapchainHandle, IntPtr.Zero); + + swapchainHandle = newSwapChain; + } + + public virtual void Run () { + + + while (!Glfw3.WindowShouldClose (hWin)) { + + Glfw3.PollEvents (); + } + } + + #region events + protected double lastMouseX { get; private set; } + protected double lastMouseY { get; private set; } + protected virtual void onScroll (double xOffset, double yOffset) { } + protected virtual void onMouseMove (double xPos, double yPos) { + } + protected virtual void onMouseButtonDown (MouseButton button) { } + protected virtual void onMouseButtonUp (MouseButton button) { } + protected virtual void onKeyDown (Key key, int scanCode, Modifier modifiers) { + switch (key) { + case Key.Escape: + Glfw3.SetWindowShouldClose (hWin, 1); + break; + } + } + protected virtual void onKeyUp (Key key, int scanCode, Modifier modifiers) { } + protected virtual void onChar (CodePoint cp) { } + static CursorPosDelegate HandleCursorPosDelegate = (window, xPosition, yPosition) => { + windows[window].onMouseMove (xPosition, yPosition); + windows[window].lastMouseX = xPosition; + windows[window].lastMouseY = yPosition; + }; + static MouseButtonDelegate HandleMouseButtonDelegate = (IntPtr window, Glfw.MouseButton button, InputAction action, Modifier mods) => { + if (action == InputAction.Press) + windows[window].onMouseButtonDown (button); + else + windows[window].onMouseButtonUp (button); + }; + static ScrollDelegate HandleScrollDelegate = (IntPtr window, double xOffset, double yOffset) => { + windows[window].onScroll (xOffset, yOffset); + }; + static KeyDelegate HandleKeyDelegate = (IntPtr window, Key key, int scanCode, InputAction action, Modifier modifiers) => { + if (action == InputAction.Press || action == InputAction.Repeat) { + windows[window].onKeyDown (key, scanCode, modifiers); + } else { + windows[window].onKeyUp (key, scanCode, modifiers); + } + }; + static CharDelegate HandleCharDelegate = (IntPtr window, CodePoint codepoint) => { + windows[window].onChar (codepoint); + }; + #endregion + #region IDisposable implementation + bool disposedValue; + protected virtual void Dispose(bool disposing) + { + if (!disposedValue) + { + if (disposing) + { + // TODO: dispose managed state (managed objects) + } + + vkDestroyDevice (dev, IntPtr.Zero); + vkDestroyInstance (inst, IntPtr.Zero); + disposedValue = true; + } + } + ~Context() { + Dispose(disposing: false); + } + public void Dispose() { + Dispose(disposing: true); + GC.SuppressFinalize(this); + } + #endregion + } +} -- 2.47.3