From e9a4b3fd55b2b445fac7553da596b29c3eebdfbe Mon Sep 17 00:00:00 2001 From: Caleb Cornett Date: Wed, 9 Nov 2022 13:56:37 -0500 Subject: [PATCH] add initial set of tests --- .gitignore | 1 + MoonWorks.csproj | 2 +- MoonWorks.sln | 60 +++++++ tests/BasicTriangle/BasicTriangle.csproj | 22 +++ tests/BasicTriangle/BasicTriangleGame.cs | 85 ++++++++++ tests/ClearScreen/ClearScreen.csproj | 15 ++ tests/ClearScreen/ClearScreenGame.cs | 29 ++++ .../ClearScreen_MultiWindow.csproj | 15 ++ .../ClearScreen_MultiWindowGame.cs | 51 ++++++ tests/CullFace/CullFace.csproj | 22 +++ tests/CullFace/CullFaceGame.cs | 144 ++++++++++++++++ tests/MSAA/MSAA.csproj | 22 +++ tests/MSAA/MSAAGame.cs | 159 ++++++++++++++++++ .../Shaders/Compiled/PositionColorVert.spv | Bin 0 -> 1052 bytes .../Shaders/Compiled/RawTriangleVertices.spv | Bin 0 -> 1568 bytes .../Content/Shaders/Compiled/SolidColor.spv | Bin 0 -> 448 bytes .../Compiled/TexturedQuadAnimatedFrag.spv | Bin 0 -> 908 bytes .../Compiled/TexturedQuadAnimatedVert.spv | Bin 0 -> 1384 bytes .../Shaders/Compiled/TexturedQuadFrag.spv | Bin 0 -> 632 bytes .../Shaders/Compiled/TexturedQuadVert.spv | Bin 0 -> 1088 bytes .../Shaders/Source/PositionColorVert.vert | 12 ++ .../Shaders/Source/RawTriangleVertices.vert | 26 +++ .../Content/Shaders/Source/SolidColor.frag | 10 ++ .../Source/TexturedQuadAnimatedFrag.frag | 17 ++ .../Source/TexturedQuadAnimatedVert.vert | 17 ++ .../Shaders/Source/TexturedQuadFrag.frag | 12 ++ .../Shaders/Source/TexturedQuadVert.vert | 12 ++ .../Content/Shaders/compileShaders.ps1 | 5 + .../Content/Textures/ravioli.png | Bin 0 -> 201 bytes .../CopyMoonlibs.targets | 43 +++++ .../MoonWorks.Test.Common.csproj | 16 ++ tests/MoonWorks.Test.Common/TestUtils.cs | 53 ++++++ tests/MoonWorks.Test.Common/VertexTypes.cs | 32 ++++ .../TexturedAnimatedQuad.csproj | 22 +++ .../TexturedAnimatedQuadGame.cs | 121 +++++++++++++ tests/TexturedQuad/TexturedQuad.csproj | 22 +++ tests/TexturedQuad/TexturedQuadGame.cs | 134 +++++++++++++++ .../TriangleVertexBuffer.csproj | 22 +++ .../TriangleVertexBufferGame.cs | 69 ++++++++ 39 files changed, 1271 insertions(+), 1 deletion(-) create mode 100644 tests/BasicTriangle/BasicTriangle.csproj create mode 100644 tests/BasicTriangle/BasicTriangleGame.cs create mode 100644 tests/ClearScreen/ClearScreen.csproj create mode 100644 tests/ClearScreen/ClearScreenGame.cs create mode 100644 tests/ClearScreen_MultiWindow/ClearScreen_MultiWindow.csproj create mode 100644 tests/ClearScreen_MultiWindow/ClearScreen_MultiWindowGame.cs create mode 100644 tests/CullFace/CullFace.csproj create mode 100644 tests/CullFace/CullFaceGame.cs create mode 100644 tests/MSAA/MSAA.csproj create mode 100644 tests/MSAA/MSAAGame.cs create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/PositionColorVert.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/RawTriangleVertices.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/SolidColor.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadAnimatedFrag.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadAnimatedVert.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadFrag.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadVert.spv create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/PositionColorVert.vert create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/RawTriangleVertices.vert create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/SolidColor.frag create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedFrag.frag create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedVert.vert create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadFrag.frag create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadVert.vert create mode 100644 tests/MoonWorks.Test.Common/Content/Shaders/compileShaders.ps1 create mode 100644 tests/MoonWorks.Test.Common/Content/Textures/ravioli.png create mode 100644 tests/MoonWorks.Test.Common/CopyMoonlibs.targets create mode 100644 tests/MoonWorks.Test.Common/MoonWorks.Test.Common.csproj create mode 100644 tests/MoonWorks.Test.Common/TestUtils.cs create mode 100644 tests/MoonWorks.Test.Common/VertexTypes.cs create mode 100644 tests/TexturedAnimatedQuad/TexturedAnimatedQuad.csproj create mode 100644 tests/TexturedAnimatedQuad/TexturedAnimatedQuadGame.cs create mode 100644 tests/TexturedQuad/TexturedQuad.csproj create mode 100644 tests/TexturedQuad/TexturedQuadGame.cs create mode 100644 tests/TriangleVertexBuffer/TriangleVertexBuffer.csproj create mode 100644 tests/TriangleVertexBuffer/TriangleVertexBufferGame.cs diff --git a/.gitignore b/.gitignore index 03c9b93..796b6e5 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,4 @@ bin/ obj/ .vs/ +*.csproj.user diff --git a/MoonWorks.csproj b/MoonWorks.csproj index a20c72a..8c55535 100644 --- a/MoonWorks.csproj +++ b/MoonWorks.csproj @@ -7,7 +7,7 @@ - $(DefaultItemExcludes);lib\**\* + $(DefaultItemExcludes);lib\**\*;tests\**\* diff --git a/MoonWorks.sln b/MoonWorks.sln index 748c5d4..c5e500c 100644 --- a/MoonWorks.sln +++ b/MoonWorks.sln @@ -5,6 +5,26 @@ VisualStudioVersion = 16.0.30717.126 MinimumVisualStudioVersion = 15.0.26124.0 Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MoonWorks", "MoonWorks.csproj", "{DDC9BA9B-4440-4CB3-BDB4-D5F91DE1686B}" EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tests", "Tests", "{734B6C25-40FE-4688-9B3C-7B3D3A343257}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MoonWorks.Test.Common", "tests\MoonWorks.Test.Common\MoonWorks.Test.Common.csproj", "{47BC8A83-B1A5-454C-AED0-461B535D664B}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ClearScreen", "tests\ClearScreen\ClearScreen.csproj", "{C37E4CF1-4899-48BC-BF58-2074420077BC}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "BasicTriangle", "tests\BasicTriangle\BasicTriangle.csproj", "{F34E6D95-887D-49C0-AC74-560EBD0D23C5}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TriangleVertexBuffer", "tests\TriangleVertexBuffer\TriangleVertexBuffer.csproj", "{944D4FDC-1635-46B6-84FA-8161F8E43AC4}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TexturedQuad", "tests\TexturedQuad\TexturedQuad.csproj", "{845DA751-5072-43C8-B9E6-4E2A32D99161}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CullFace", "tests\CullFace\CullFace.csproj", "{96986050-5136-4680-B388-EDD1207F9212}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ClearScreen_MultiWindow", "tests\ClearScreen_MultiWindow\ClearScreen_MultiWindow.csproj", "{F6283B5C-051B-427C-AE7E-9DB9E0313769}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TexturedAnimatedQuad", "tests\TexturedAnimatedQuad\TexturedAnimatedQuad.csproj", "{F022FB5F-FD61-4956-A7CE-7B428DB80A39}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "MSAA", "tests\MSAA\MSAA.csproj", "{D97DED9B-4CC4-45F6-A9A9-E8C589036A85}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|x64 = Debug|x64 @@ -15,10 +35,50 @@ Global {DDC9BA9B-4440-4CB3-BDB4-D5F91DE1686B}.Debug|x64.Build.0 = Debug|x64 {DDC9BA9B-4440-4CB3-BDB4-D5F91DE1686B}.Release|x64.ActiveCfg = Release|x64 {DDC9BA9B-4440-4CB3-BDB4-D5F91DE1686B}.Release|x64.Build.0 = Release|x64 + {47BC8A83-B1A5-454C-AED0-461B535D664B}.Debug|x64.ActiveCfg = Debug|x64 + {47BC8A83-B1A5-454C-AED0-461B535D664B}.Debug|x64.Build.0 = Debug|x64 + {47BC8A83-B1A5-454C-AED0-461B535D664B}.Release|x64.ActiveCfg = Release|x64 + {C37E4CF1-4899-48BC-BF58-2074420077BC}.Debug|x64.ActiveCfg = Debug|x64 + {C37E4CF1-4899-48BC-BF58-2074420077BC}.Debug|x64.Build.0 = Debug|x64 + {C37E4CF1-4899-48BC-BF58-2074420077BC}.Release|x64.ActiveCfg = Release|x64 + {F34E6D95-887D-49C0-AC74-560EBD0D23C5}.Debug|x64.ActiveCfg = Debug|x64 + {F34E6D95-887D-49C0-AC74-560EBD0D23C5}.Debug|x64.Build.0 = Debug|x64 + {F34E6D95-887D-49C0-AC74-560EBD0D23C5}.Release|x64.ActiveCfg = Release|x64 + {944D4FDC-1635-46B6-84FA-8161F8E43AC4}.Debug|x64.ActiveCfg = Debug|x64 + {944D4FDC-1635-46B6-84FA-8161F8E43AC4}.Debug|x64.Build.0 = Debug|x64 + {944D4FDC-1635-46B6-84FA-8161F8E43AC4}.Release|x64.ActiveCfg = Release|x64 + {845DA751-5072-43C8-B9E6-4E2A32D99161}.Debug|x64.ActiveCfg = Debug|x64 + {845DA751-5072-43C8-B9E6-4E2A32D99161}.Debug|x64.Build.0 = Debug|x64 + {845DA751-5072-43C8-B9E6-4E2A32D99161}.Release|x64.ActiveCfg = Release|x64 + {96986050-5136-4680-B388-EDD1207F9212}.Debug|x64.ActiveCfg = Debug|x64 + {96986050-5136-4680-B388-EDD1207F9212}.Debug|x64.Build.0 = Debug|x64 + {96986050-5136-4680-B388-EDD1207F9212}.Release|x64.ActiveCfg = Release|x64 + {F6283B5C-051B-427C-AE7E-9DB9E0313769}.Debug|x64.ActiveCfg = Debug|x64 + {F6283B5C-051B-427C-AE7E-9DB9E0313769}.Debug|x64.Build.0 = Debug|x64 + {F6283B5C-051B-427C-AE7E-9DB9E0313769}.Release|x64.ActiveCfg = Release|x64 + {F022FB5F-FD61-4956-A7CE-7B428DB80A39}.Debug|x64.ActiveCfg = Debug|x64 + {F022FB5F-FD61-4956-A7CE-7B428DB80A39}.Debug|x64.Build.0 = Debug|x64 + {F022FB5F-FD61-4956-A7CE-7B428DB80A39}.Release|x64.ActiveCfg = Release|Any CPU + {F022FB5F-FD61-4956-A7CE-7B428DB80A39}.Release|x64.Build.0 = Release|Any CPU + {D97DED9B-4CC4-45F6-A9A9-E8C589036A85}.Debug|x64.ActiveCfg = Debug|x64 + {D97DED9B-4CC4-45F6-A9A9-E8C589036A85}.Debug|x64.Build.0 = Debug|x64 + {D97DED9B-4CC4-45F6-A9A9-E8C589036A85}.Release|x64.ActiveCfg = Release|Any CPU + {D97DED9B-4CC4-45F6-A9A9-E8C589036A85}.Release|x64.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE EndGlobalSection + GlobalSection(NestedProjects) = preSolution + {47BC8A83-B1A5-454C-AED0-461B535D664B} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {C37E4CF1-4899-48BC-BF58-2074420077BC} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {F34E6D95-887D-49C0-AC74-560EBD0D23C5} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {944D4FDC-1635-46B6-84FA-8161F8E43AC4} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {845DA751-5072-43C8-B9E6-4E2A32D99161} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {96986050-5136-4680-B388-EDD1207F9212} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {F6283B5C-051B-427C-AE7E-9DB9E0313769} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {F022FB5F-FD61-4956-A7CE-7B428DB80A39} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + {D97DED9B-4CC4-45F6-A9A9-E8C589036A85} = {734B6C25-40FE-4688-9B3C-7B3D3A343257} + EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {C3D68FAA-3165-43C7-95B3-D845F0DAA918} EndGlobalSection diff --git a/tests/BasicTriangle/BasicTriangle.csproj b/tests/BasicTriangle/BasicTriangle.csproj new file mode 100644 index 0000000..9538ed1 --- /dev/null +++ b/tests/BasicTriangle/BasicTriangle.csproj @@ -0,0 +1,22 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + + + Content\%(RecursiveDir)%(Filename)%(Extension) + Always + + + + diff --git a/tests/BasicTriangle/BasicTriangleGame.cs b/tests/BasicTriangle/BasicTriangleGame.cs new file mode 100644 index 0000000..2986993 --- /dev/null +++ b/tests/BasicTriangle/BasicTriangleGame.cs @@ -0,0 +1,85 @@ +using MoonWorks; +using MoonWorks.Graphics; + +namespace MoonWorks.Test +{ + class BasicTriangleGame : Game + { + private GraphicsPipeline fillPipeline; + private GraphicsPipeline linePipeline; + private ShaderModule vertShaderModule; + private ShaderModule fragShaderModule; + + private Viewport smallViewport = new Viewport(160, 120, 320, 240); + private Rect scissorRect = new Rect(320, 240, 320, 240); + + private bool useWireframeMode; + private bool useSmallViewport; + private bool useScissorRect; + + public BasicTriangleGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + Logger.LogInfo("Press A to toggle wireframe mode\nPress S to toggle small viewport\nPress D to toggle scissor rect"); + + vertShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("RawTriangleVertices.spv")); + fragShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("SolidColor.spv")); + + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo(vertShaderModule, fragShaderModule); + fillPipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + pipelineCreateInfo.RasterizerState.FillMode = FillMode.Line; + linePipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + } + + protected override void Update(System.TimeSpan delta) + { + if (Inputs.Keyboard.IsPressed(Input.KeyCode.A)) + { + useWireframeMode = !useWireframeMode; + Logger.LogInfo("Using wireframe mode: " + useWireframeMode); + } + + if (Inputs.Keyboard.IsPressed(Input.KeyCode.S)) + { + useSmallViewport = !useSmallViewport; + Logger.LogInfo("Using small viewport: " + useSmallViewport); + } + + if (Inputs.Keyboard.IsPressed(Input.KeyCode.D)) + { + useScissorRect = !useScissorRect; + Logger.LogInfo("Using scissor rect: " + useScissorRect); + } + } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.Black)); + cmdbuf.BindGraphicsPipeline(useWireframeMode ? linePipeline : fillPipeline); + + if (useSmallViewport) + { + cmdbuf.SetViewport(smallViewport); + } + if (useScissorRect) + { + cmdbuf.SetScissor(scissorRect); + } + + cmdbuf.DrawPrimitives(0, 1, 0, 0); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + BasicTriangleGame game = new BasicTriangleGame(); + game.Run(); + } + } +} diff --git a/tests/ClearScreen/ClearScreen.csproj b/tests/ClearScreen/ClearScreen.csproj new file mode 100644 index 0000000..fd2ff3e --- /dev/null +++ b/tests/ClearScreen/ClearScreen.csproj @@ -0,0 +1,15 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + diff --git a/tests/ClearScreen/ClearScreenGame.cs b/tests/ClearScreen/ClearScreenGame.cs new file mode 100644 index 0000000..63ac285 --- /dev/null +++ b/tests/ClearScreen/ClearScreenGame.cs @@ -0,0 +1,29 @@ +using MoonWorks; +using MoonWorks.Graphics; + +namespace MoonWorks.Test +{ + class ClearScreenGame : Game + { + public ClearScreenGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) { } + protected override void Update(System.TimeSpan delta) { } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.CornflowerBlue)); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + ClearScreenGame game = new ClearScreenGame(); + game.Run(); + } + } +} diff --git a/tests/ClearScreen_MultiWindow/ClearScreen_MultiWindow.csproj b/tests/ClearScreen_MultiWindow/ClearScreen_MultiWindow.csproj new file mode 100644 index 0000000..fd2ff3e --- /dev/null +++ b/tests/ClearScreen_MultiWindow/ClearScreen_MultiWindow.csproj @@ -0,0 +1,15 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + diff --git a/tests/ClearScreen_MultiWindow/ClearScreen_MultiWindowGame.cs b/tests/ClearScreen_MultiWindow/ClearScreen_MultiWindowGame.cs new file mode 100644 index 0000000..fa955fd --- /dev/null +++ b/tests/ClearScreen_MultiWindow/ClearScreen_MultiWindowGame.cs @@ -0,0 +1,51 @@ +using MoonWorks; +using MoonWorks.Graphics; + +namespace MoonWorks.Test +{ + class ClearScreen_MultiWindowGame : Game + { + private Window secondaryWindow; + + public ClearScreen_MultiWindowGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + secondaryWindow = new Window( + new WindowCreateInfo("Secondary Window", 640, 480, ScreenMode.Windowed, PresentMode.FIFO, false, false), + GraphicsDevice.WindowFlags + ); + GraphicsDevice.ClaimWindow(secondaryWindow, PresentMode.FIFO); + } + + protected override void Update(System.TimeSpan delta) { } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf; + Texture? backbuffer; + + cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.CornflowerBlue)); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + + cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + backbuffer = cmdbuf.AcquireSwapchainTexture(secondaryWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.Aquamarine)); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + ClearScreen_MultiWindowGame game = new ClearScreen_MultiWindowGame(); + game.Run(); + } + } +} diff --git a/tests/CullFace/CullFace.csproj b/tests/CullFace/CullFace.csproj new file mode 100644 index 0000000..9538ed1 --- /dev/null +++ b/tests/CullFace/CullFace.csproj @@ -0,0 +1,22 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + + + Content\%(RecursiveDir)%(Filename)%(Extension) + Always + + + + diff --git a/tests/CullFace/CullFaceGame.cs b/tests/CullFace/CullFaceGame.cs new file mode 100644 index 0000000..81beb3e --- /dev/null +++ b/tests/CullFace/CullFaceGame.cs @@ -0,0 +1,144 @@ +using MoonWorks; +using MoonWorks.Graphics; +using MoonWorks.Math.Float; + +namespace MoonWorks.Test +{ + internal class CullFaceGame : Game + { + private GraphicsPipeline CW_CullNonePipeline; + private GraphicsPipeline CW_CullFrontPipeline; + private GraphicsPipeline CW_CullBackPipeline; + private GraphicsPipeline CCW_CullNonePipeline; + private GraphicsPipeline CCW_CullFrontPipeline; + private GraphicsPipeline CCW_CullBackPipeline; + private ShaderModule vertShaderModule; + private ShaderModule fragShaderModule; + private Buffer cwVertexBuffer; + private Buffer ccwVertexBuffer; + + private bool useClockwiseWinding; + + public CullFaceGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + Logger.LogInfo("Press A to toggle the winding order of the triangles (default is counter-clockwise)"); + + // Load the shaders + vertShaderModule = new ShaderModule(GraphicsDevice, "Content/Shaders/Compiled/PositionColorVert.spv"); + fragShaderModule = new ShaderModule(GraphicsDevice, "Content/Shaders/Compiled/SolidColor.spv"); + + // Create the graphics pipelines + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo(vertShaderModule, fragShaderModule); + pipelineCreateInfo.VertexInputState = new VertexInputState( + VertexBinding.Create(), + VertexAttribute.Create("Position", 0), + VertexAttribute.Create("Color", 1) + ); + + pipelineCreateInfo.RasterizerState = RasterizerState.CW_CullNone; + CW_CullNonePipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + pipelineCreateInfo.RasterizerState = RasterizerState.CW_CullFront; + CW_CullFrontPipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + pipelineCreateInfo.RasterizerState = RasterizerState.CW_CullBack; + CW_CullBackPipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + pipelineCreateInfo.RasterizerState = RasterizerState.CCW_CullNone; + CCW_CullNonePipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + pipelineCreateInfo.RasterizerState = RasterizerState.CCW_CullFront; + CCW_CullFrontPipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + pipelineCreateInfo.RasterizerState = RasterizerState.CCW_CullBack; + CCW_CullBackPipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + // Create and populate the vertex buffers + cwVertexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Vertex, 3); + ccwVertexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Vertex, 3); + + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + cmdbuf.SetBufferData( + cwVertexBuffer, + new PositionColorVertex[] + { + new PositionColorVertex(new Vector3(0, -1, 0), Color.Blue), + new PositionColorVertex(new Vector3(1, 1, 0), Color.Green), + new PositionColorVertex(new Vector3(-1, 1, 0), Color.Red), + } + ); + cmdbuf.SetBufferData( + ccwVertexBuffer, + new PositionColorVertex[] + { + new PositionColorVertex(new Vector3(-1, 1, 0), Color.Red), + new PositionColorVertex(new Vector3(1, 1, 0), Color.Green), + new PositionColorVertex(new Vector3(0, -1, 0), Color.Blue), + } + ); + GraphicsDevice.Submit(cmdbuf); + GraphicsDevice.Wait(); + } + + protected override void Update(System.TimeSpan delta) + { + if (Inputs.Keyboard.IsPressed(Input.KeyCode.A)) + { + useClockwiseWinding = !useClockwiseWinding; + Logger.LogInfo("Using clockwise winding: " + useClockwiseWinding); + } + } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.Black)); + + if (useClockwiseWinding) + { + cmdbuf.BindVertexBuffers(cwVertexBuffer); + } + else + { + cmdbuf.BindVertexBuffers(ccwVertexBuffer); + } + + cmdbuf.SetViewport(new Viewport(0, 0, 213, 240)); + cmdbuf.BindGraphicsPipeline(CW_CullNonePipeline); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + + cmdbuf.SetViewport(new Viewport(213, 0, 213, 240)); + cmdbuf.BindGraphicsPipeline(CW_CullFrontPipeline); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + + cmdbuf.SetViewport(new Viewport(426, 0, 213, 240)); + cmdbuf.BindGraphicsPipeline(CW_CullBackPipeline); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + + cmdbuf.SetViewport(new Viewport(0, 240, 213, 240)); + cmdbuf.BindGraphicsPipeline(CCW_CullNonePipeline); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + + cmdbuf.SetViewport(new Viewport(213, 240, 213, 240)); + cmdbuf.BindGraphicsPipeline(CCW_CullFrontPipeline); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + + cmdbuf.SetViewport(new Viewport(426, 240, 213, 240)); + cmdbuf.BindGraphicsPipeline(CCW_CullBackPipeline); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + CullFaceGame game = new CullFaceGame(); + game.Run(); + } + } +} diff --git a/tests/MSAA/MSAA.csproj b/tests/MSAA/MSAA.csproj new file mode 100644 index 0000000..9538ed1 --- /dev/null +++ b/tests/MSAA/MSAA.csproj @@ -0,0 +1,22 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + + + Content\%(RecursiveDir)%(Filename)%(Extension) + Always + + + + diff --git a/tests/MSAA/MSAAGame.cs b/tests/MSAA/MSAAGame.cs new file mode 100644 index 0000000..b98e1f5 --- /dev/null +++ b/tests/MSAA/MSAAGame.cs @@ -0,0 +1,159 @@ +using MoonWorks; +using MoonWorks.Math.Float; +using MoonWorks.Graphics; + +namespace MoonWorks.Test +{ + class MSAAGame : Game + { + private GraphicsPipeline[] msaaPipelines = new GraphicsPipeline[4]; + + private ShaderModule triangleVertShaderModule; + private ShaderModule triangleFragShaderModule; + + private GraphicsPipeline blitPipeline; + private ShaderModule blitVertShaderModule; + private ShaderModule blitFragShaderModule; + + private Texture rt; + private Sampler rtSampler; + private Buffer quadVertexBuffer; + private Buffer quadIndexBuffer; + + private SampleCount currentSampleCount = SampleCount.Four; + + public MSAAGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + Logger.LogInfo("Press A and D to cycle between sample counts"); + Logger.LogInfo("Setting sample count to: " + currentSampleCount); + + // Create the MSAA pipelines + triangleVertShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("RawTriangleVertices.spv")); + triangleFragShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("SolidColor.spv")); + + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo( + triangleVertShaderModule, + triangleFragShaderModule + ); + for (int i = 0; i < msaaPipelines.Length; i += 1) + { + pipelineCreateInfo.MultisampleState.MultisampleCount = (SampleCount) i; + msaaPipelines[i] = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + } + + // Create the blit pipeline + blitVertShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuadVert.spv")); + blitFragShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuadFrag.spv")); + + pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo( + blitVertShaderModule, + blitFragShaderModule + ); + pipelineCreateInfo.VertexInputState = new VertexInputState( + VertexBinding.Create(), + VertexAttribute.Create("Position", 0), + VertexAttribute.Create("TexCoord", 1) + ); + pipelineCreateInfo.FragmentShaderInfo.SamplerBindingCount = 1; + blitPipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + // Create the MSAA render texture and sampler + rt = Texture.CreateTexture2D( + GraphicsDevice, + MainWindow.Width, + MainWindow.Height, + TextureFormat.R8G8B8A8, + TextureUsageFlags.ColorTarget | TextureUsageFlags.Sampler + ); + rtSampler = new Sampler(GraphicsDevice, SamplerCreateInfo.PointClamp); + + // Create and populate the vertex and index buffers + quadVertexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Vertex, 4); + quadIndexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Index, 6); + + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + cmdbuf.SetBufferData( + quadVertexBuffer, + new PositionTextureVertex[] + { + new PositionTextureVertex(new Vector3(-1, -1, 0), new Vector2(0, 0)), + new PositionTextureVertex(new Vector3(1, -1, 0), new Vector2(1, 0)), + new PositionTextureVertex(new Vector3(1, 1, 0), new Vector2(1, 1)), + new PositionTextureVertex(new Vector3(-1, 1, 0), new Vector2(0, 1)), + } + ); + cmdbuf.SetBufferData( + quadIndexBuffer, + new ushort[] + { + 0, 1, 2, + 0, 2, 3, + } + ); + GraphicsDevice.Submit(cmdbuf); + GraphicsDevice.Wait(); + } + + protected override void Update(System.TimeSpan delta) + { + SampleCount prevSampleCount = currentSampleCount; + + if (Inputs.Keyboard.IsPressed(Input.KeyCode.A)) + { + currentSampleCount -= 1; + if (currentSampleCount < 0) + { + currentSampleCount = SampleCount.Eight; + } + } + if (Inputs.Keyboard.IsPressed(Input.KeyCode.D)) + { + currentSampleCount += 1; + if (currentSampleCount > SampleCount.Eight) + { + currentSampleCount = SampleCount.One; + } + } + + if (prevSampleCount != currentSampleCount) + { + Logger.LogInfo("Setting sample count to: " + currentSampleCount); + } + } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass( + new ColorAttachmentInfo( + rt, + Color.Black, + currentSampleCount, + StoreOp.DontCare + ) + ); + cmdbuf.BindGraphicsPipeline(msaaPipelines[(int) currentSampleCount]); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + cmdbuf.EndRenderPass(); + + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, LoadOp.DontCare)); + cmdbuf.BindGraphicsPipeline(blitPipeline); + cmdbuf.BindFragmentSamplers(new TextureSamplerBinding(rt, rtSampler)); + cmdbuf.BindVertexBuffers(quadVertexBuffer); + cmdbuf.BindIndexBuffer(quadIndexBuffer, IndexElementSize.Sixteen); + cmdbuf.DrawIndexedPrimitives(0, 0, 2, 0, 0); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + MSAAGame game = new MSAAGame(); + game.Run(); + } + } +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Compiled/PositionColorVert.spv b/tests/MoonWorks.Test.Common/Content/Shaders/Compiled/PositionColorVert.spv new file mode 100644 index 0000000000000000000000000000000000000000..0852ff8b3826a4e091c621dda8075040a39a36d7 GIT binary patch literal 1052 zcmYk4NlODk5QW<$6XU+beT{e&#Dj_;DxxwT0xE*nL6Sil#+i^zL_PW2{8e5A-`7ru zlvJwf)$7{Ea%p$em=QB>rp&hampM}sV$6i8IvX}0oBO@Iy?=Og0At#e9TCoq8FPL` zzpu|WB>q5bI#NiG8lDw*H zL%J-!{&`$Xt%l;7EL`x@B4!^j^5e41=kvsV=0)YF98W)zy&|5L&zlX!GqUst+mgrZ zeg<+Vedc88NuD`~xjPtr>aq+9dO_W_0+ShF>jg%C&)X<4df%%HeKw`M ahfkgvFIAWC#CPT-&g{ESNQ3AQ9-?a1(k!MsT>_p+wQP??*dV@hU%0DM@l-M+m z`gR!ia{DQUH&@}=w3m$gRYF~iYQ4J7NzD&Q^gbTu@#)*NAD=IGp7@UA&&y`5DhsvNm2pWrkZg!^ zUK*bo80ZzyT-cx-|Q^7dbbixd%As#HW{FKIbLb ztd^?7yDT9eID+l(bX7KY^!1xA4#)4mF5B<(+V8)q829!2?>a7b@cWs0wKln#!H#qw zVUZ8NCE+}q^6yJ?cd#u@jG6j=5JTw618MG0oSxwG_Q3YlSI$TOSYW?|)TQAvBfcf( z^jtpkKO_@Ar3j2B{uV62EP?&FFg3Z-lpto zJ-!PtW<$L|nngWg*Cg8#@?iUVO=nY&nNcs0h6mr*yCJ(;@0NTpW=Xv}(k$u`yDb4D z54Nwzto{9%G4(tTU9BHD-`^k2d3f`WB=qZ@`pvu_J4|YVJ#pBSbl1J>UD1x@ zmRYZ6cC@pS?=1t7D;dZ&zP~jV4~)oAx-RSRBV1K=y4pOfskjl}38}f2Ksv~bU2F>$ z`iLRo4m$EMz|Kckkuwf;;HE>PqezGECOI5TRe$A~$!(FD)RtLN+fzneucfm^k{{Ey zKta*=Rid2twv0dD_W8bqA2pn%!5WzJ%@AC~tT*@`Q*zFQn^@d_f_)d<95IES_aUbD z9RD6NUxfVg1=E8Z>jPw5`@c?1PjZi#kbdmN#WUYv6!HsL_8cLoe?^sjiGOhV3GoYe C?<*Pr literal 0 HcmV?d00001 diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadAnimatedFrag.spv b/tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadAnimatedFrag.spv new file mode 100644 index 0000000000000000000000000000000000000000..fa849a9e7064c46059d299fa2940847f3c66f587 GIT binary patch literal 908 zcmYk3%Syvw5QV44*m|p%YQ2|Mmx8!Z5kx^n>~JwDUz5*^2QC4f991>@(xY*yd3E2ryYuQ-ezV*4-+F^6@T0I3_^mJrn!WHn zfLF-y!cH^lx3UCRjI6F}ZmNBqG+r*_C{Cp3YKAGr$4>YhC+&+UZoVoNnon`gxBaLW zcB8@n8^>n2kfE`xc;9Guqaac4rn5Z+AD3~QwBUH+Fmr`Ob|Vg&*v?-N$4N1E0H6BX zayB{2YdT}(XmZbvM|t+1{f_iX+AMWz>6R@$mvx>HR+X=)9{+%xeO2`>D54F1GR&C) ztfDXda|d@?k@{e8$>|?#S^2DDRi2aY4)dbU81Ls4;Zko+n_5()7x-Bli__ zmxd%T^vT%|#%wE!)I$UQsv@<(;ghp3up|8&c)`IxlBFW;hj-z8B=+ ovA-nR0IBo91i&B5Zlz5I^3N}nSF!(sIz1FFAL2>1ONa4 literal 0 HcmV?d00001 diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadAnimatedVert.spv b/tests/MoonWorks.Test.Common/Content/Shaders/Compiled/TexturedQuadAnimatedVert.spv new file mode 100644 index 0000000000000000000000000000000000000000..e43dee242fb9dd64b943cf2263d6a42e298ee9de GIT binary patch literal 1384 zcmZ9K-EPxB5QR5M-IkWNl+qud1g9x~LaMj`goFS=LGDFRTeWa&MUIPBxOQYaC~(Cq z@Jc)tH%Oe%$yyN`O=joJ+1WF*ZZ*3L#x%^5Suu~yWUZT~5M!3jeC31QS?{1I2M14| zJ%O=mS``t_nz>T#=k$Nsw2q2kkPh1;||vp=MeGm{*>DR-FI;d@(@{WOZ}9Frn9 zN|HL~X&%gmg`REsPpQ4g^2>Kg7JUV$HaP2Jzs&9UJnyFk9Gz*Io0F9GUNz%du<$^W z;SJhT4l(aROdm%&!wgv9EQgT?o8{3T7`-?idobQ0P=2L49xTBawp6|-_x1m#<>!=30*l%e!FYn8?#pfPka=zk4dAQ&&r!g}F zBfliykhwgun+x?;6jP7>H}$_N@5@+^r}3Kh)Yw%_kMP0T+A%LzgB-@a*X7Yb9$mzI zD`4DnL*AEBmwSjeWvm^=Tk_OJS6io;DHyePD zoG0cToEEqpnK3`#aNh&%IE$X=dUNhU7YqE45WbODLYebb88d#ZEN?;lRt$9AmZ6ni z;iGX^22PA7UxuDjok7c<%$Kno*45sZHD<8=DTcliDM9Z&8Ry}X@5p|sF1h}%0(kS}({8erQ?};sB zU@~v+J8wQxtz0(D_N-+cJFpl6wdhKuWuO#x5coq3!oJBz%e?)N25*M$6 zx_}J-;N(@GjLiuS-ZSa$(&K*^Q`A{oDFi z^+o9UZT2p?GMSk(=iWIpYqN2>WXv10V%E)xnVn735Ms=#SuB0j?RU@eVsv)#`5Z>e zG)p3!4fD2)7xeoua48AMs%%@fFKgZk!}2sG2C{CyJl?Bvc) z3j3r~=nN;OmgTN+St@j?GEQb4sBgyQ`DwOQr80Q zgWYh@$d2lUiX%o))rs?KxIxXRK6?^7yPQqnFoyeiah#!o!o2Yy>;chkG5U?w&X(@ z=Tnt$DCUg=Yi7XJn{jJ{j)XrPWRa=rr?eRkwS8Sm1Ed{@Rn*Pc9m{2Xn? zaKU+xoZb2Ra6ib5`SYFr$BMX%wo83O_Qi}G@P9%A`L9CR&6io_APb^zNw(TKLx7hff{NKlCnoLm4|_59lC=|Eej!$o>NgL06>! literal 0 HcmV?d00001 diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/PositionColorVert.vert b/tests/MoonWorks.Test.Common/Content/Shaders/Source/PositionColorVert.vert new file mode 100644 index 0000000..99d5237 --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/PositionColorVert.vert @@ -0,0 +1,12 @@ +#version 450 + +layout (location = 0) in vec3 Position; +layout (location = 1) in vec4 Color; + +layout (location = 0) out vec4 outColor; + +void main() +{ + outColor = Color; + gl_Position = vec4(Position, 1); +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/RawTriangleVertices.vert b/tests/MoonWorks.Test.Common/Content/Shaders/Source/RawTriangleVertices.vert new file mode 100644 index 0000000..fba105d --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/RawTriangleVertices.vert @@ -0,0 +1,26 @@ +#version 450 + +layout (location = 0) out vec4 outColor; + +void main() +{ + vec2 pos; + + if (gl_VertexIndex == 0) + { + pos = vec2(-1, 1); + outColor = vec4(1, 0, 0, 1); + } + else if (gl_VertexIndex == 1) + { + pos = vec2(1, 1); + outColor = vec4(0, 1, 0, 1); + } + else if (gl_VertexIndex == 2) + { + pos = vec2(0, -1); + outColor = vec4(0, 0, 1, 1); + } + + gl_Position = vec4(pos, 0, 1); +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/SolidColor.frag b/tests/MoonWorks.Test.Common/Content/Shaders/Source/SolidColor.frag new file mode 100644 index 0000000..ec2d430 --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/SolidColor.frag @@ -0,0 +1,10 @@ +#version 450 + +layout (location = 0) in vec4 Color; + +layout (location = 0) out vec4 FragColor; + +void main() +{ + FragColor = Color; +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedFrag.frag b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedFrag.frag new file mode 100644 index 0000000..5e0db2e --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedFrag.frag @@ -0,0 +1,17 @@ +#version 450 + +layout (location = 0) in vec2 TexCoord; + +layout (location = 0) out vec4 FragColor; + +layout(binding = 0, set = 1) uniform sampler2D Sampler; + +layout (binding = 0, set = 3) uniform UniformBlock +{ + vec4 MultiplyColor; +}; + +void main() +{ + FragColor = MultiplyColor * texture(Sampler, TexCoord); +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedVert.vert b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedVert.vert new file mode 100644 index 0000000..080dfb5 --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadAnimatedVert.vert @@ -0,0 +1,17 @@ +#version 450 + +layout (location = 0) in vec3 Position; +layout (location = 1) in vec2 TexCoord; + +layout (location = 0) out vec2 outTexCoord; + +layout (binding = 0, set = 2) uniform UniformBlock +{ + mat4x4 MatrixTransform; +}; + +void main() +{ + outTexCoord = TexCoord; + gl_Position = MatrixTransform * vec4(Position, 1); +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadFrag.frag b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadFrag.frag new file mode 100644 index 0000000..c4237bd --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadFrag.frag @@ -0,0 +1,12 @@ +#version 450 + +layout (location = 0) in vec2 TexCoord; + +layout (location = 0) out vec4 FragColor; + +layout(binding = 0, set = 1) uniform sampler2D Sampler; + +void main() +{ + FragColor = texture(Sampler, TexCoord); +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadVert.vert b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadVert.vert new file mode 100644 index 0000000..ff0d240 --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/Source/TexturedQuadVert.vert @@ -0,0 +1,12 @@ +#version 450 + +layout (location = 0) in vec3 Position; +layout (location = 1) in vec2 TexCoord; + +layout (location = 0) out vec2 outTexCoord; + +void main() +{ + outTexCoord = TexCoord; + gl_Position = vec4(Position, 1); +} diff --git a/tests/MoonWorks.Test.Common/Content/Shaders/compileShaders.ps1 b/tests/MoonWorks.Test.Common/Content/Shaders/compileShaders.ps1 new file mode 100644 index 0000000..aa16bf5 --- /dev/null +++ b/tests/MoonWorks.Test.Common/Content/Shaders/compileShaders.ps1 @@ -0,0 +1,5 @@ +Get-ChildItem "Source" | +Foreach-Object { + $filename = $_.Basename + glslc $_.FullName -o Compiled/$filename.spv +} diff --git a/tests/MoonWorks.Test.Common/Content/Textures/ravioli.png b/tests/MoonWorks.Test.Common/Content/Textures/ravioli.png new file mode 100644 index 0000000000000000000000000000000000000000..f202cb2ac9a4d4cf8b7330bb82c48d6ff50b85f1 GIT binary patch literal 201 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jP7LeL$-D$|nmt_{Lo9ly zPQEC3K!L-#IlDx2`wO4Ei%aJmt}9$_#&UW(`xDNNhHVp%1WwuUb(WKkATz_e*PO*O ziv`ms+;u$4Wput_>fSjwePk5!=jFEFkpGx-&yO*oc&CbI*dyH;FJ>Ov)AT{K%yEnO z@#+Id1Ql8~*mf|;cSNP9F8*p&@IhPEg*Dz_jyu`njxgN@xNAG}uhD literal 0 HcmV?d00001 diff --git a/tests/MoonWorks.Test.Common/CopyMoonlibs.targets b/tests/MoonWorks.Test.Common/CopyMoonlibs.targets new file mode 100644 index 0000000..c1b4245 --- /dev/null +++ b/tests/MoonWorks.Test.Common/CopyMoonlibs.targets @@ -0,0 +1,43 @@ + + + + + + + + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + + + %(RecursiveDir)%(Filename)%(Extension) + PreserveNewest + + + + diff --git a/tests/MoonWorks.Test.Common/MoonWorks.Test.Common.csproj b/tests/MoonWorks.Test.Common/MoonWorks.Test.Common.csproj new file mode 100644 index 0000000..5c33609 --- /dev/null +++ b/tests/MoonWorks.Test.Common/MoonWorks.Test.Common.csproj @@ -0,0 +1,16 @@ + + + + + + + + library + net6.0 + enable + x64 + + + + + diff --git a/tests/MoonWorks.Test.Common/TestUtils.cs b/tests/MoonWorks.Test.Common/TestUtils.cs new file mode 100644 index 0000000..801b467 --- /dev/null +++ b/tests/MoonWorks.Test.Common/TestUtils.cs @@ -0,0 +1,53 @@ +using MoonWorks.Graphics; + +namespace MoonWorks.Test +{ + public static class TestUtils + { + public static WindowCreateInfo GetStandardWindowCreateInfo() + { + return new WindowCreateInfo( + "Main Window", + 640, + 480, + ScreenMode.Windowed, + PresentMode.FIFO + ); + } + + public static FrameLimiterSettings GetStandardFrameLimiterSettings() + { + return new FrameLimiterSettings( + FrameLimiterMode.Capped, + 60 + ); + } + + public static GraphicsPipelineCreateInfo GetStandardGraphicsPipelineCreateInfo( + ShaderModule vertShaderModule, + ShaderModule fragShaderModule + ) { + return new GraphicsPipelineCreateInfo + { + AttachmentInfo = new GraphicsPipelineAttachmentInfo( + new ColorAttachmentDescription( + TextureFormat.R8G8B8A8, + ColorAttachmentBlendState.Opaque + ) + ), + DepthStencilState = DepthStencilState.Disable, + MultisampleState = MultisampleState.None, + PrimitiveType = PrimitiveType.TriangleList, + RasterizerState = RasterizerState.CW_CullNone, + VertexInputState = VertexInputState.Empty, + VertexShaderInfo = GraphicsShaderInfo.Create(vertShaderModule, "main", 0), + FragmentShaderInfo = GraphicsShaderInfo.Create(fragShaderModule, "main", 0) + }; + } + + public static string GetShaderPath(string shaderName) + { + return SDL2.SDL.SDL_GetBasePath() + "Content/Shaders/Compiled/" + shaderName; + } + } +} diff --git a/tests/MoonWorks.Test.Common/VertexTypes.cs b/tests/MoonWorks.Test.Common/VertexTypes.cs new file mode 100644 index 0000000..fe7c1c9 --- /dev/null +++ b/tests/MoonWorks.Test.Common/VertexTypes.cs @@ -0,0 +1,32 @@ +using System.Runtime.InteropServices; +using MoonWorks.Graphics; +using MoonWorks.Math.Float; + +namespace MoonWorks.Test +{ + [StructLayout(LayoutKind.Sequential)] + public struct PositionColorVertex + { + public Vector3 Position; + public Color Color; + + public PositionColorVertex(Vector3 position, Color color) + { + Position = position; + Color = color; + } + } + + [StructLayout(LayoutKind.Sequential)] + public struct PositionTextureVertex + { + public Vector3 Position; + public Vector2 TexCoord; + + public PositionTextureVertex(Vector3 position, Vector2 texCoord) + { + Position = position; + TexCoord = texCoord; + } + } +} diff --git a/tests/TexturedAnimatedQuad/TexturedAnimatedQuad.csproj b/tests/TexturedAnimatedQuad/TexturedAnimatedQuad.csproj new file mode 100644 index 0000000..e0a93fd --- /dev/null +++ b/tests/TexturedAnimatedQuad/TexturedAnimatedQuad.csproj @@ -0,0 +1,22 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + + + Content\%(RecursiveDir)%(Filename)%(Extension) + Always + + + + diff --git a/tests/TexturedAnimatedQuad/TexturedAnimatedQuadGame.cs b/tests/TexturedAnimatedQuad/TexturedAnimatedQuadGame.cs new file mode 100644 index 0000000..e1ee4d9 --- /dev/null +++ b/tests/TexturedAnimatedQuad/TexturedAnimatedQuadGame.cs @@ -0,0 +1,121 @@ +using System.Runtime.InteropServices; +using MoonWorks; +using MoonWorks.Graphics; +using MoonWorks.Math.Float; + +namespace MoonWorks.Test +{ + class TexturedAnimatedQuadGame : Game + { + private GraphicsPipeline pipeline; + private ShaderModule vertShaderModule; + private ShaderModule fragShaderModule; + private Buffer vertexBuffer; + private Buffer indexBuffer; + private Texture texture; + private Sampler sampler; + + private float t; + + [StructLayout(LayoutKind.Sequential)] + private struct VertexUniforms + { + public Matrix4x4 TransformMatrix; + + public VertexUniforms(Matrix4x4 transformMatrix) + { + TransformMatrix = transformMatrix; + } + } + + [StructLayout(LayoutKind.Sequential)] + private struct FragmentUniforms + { + public Vector4 MultiplyColor; + + public FragmentUniforms(Vector4 multiplyColor) + { + MultiplyColor = multiplyColor; + } + } + + public TexturedAnimatedQuadGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + // Load the shaders + vertShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuadAnimatedVert.spv")); + fragShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuadAnimatedFrag.spv")); + + // Create the graphics pipeline + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo(vertShaderModule, fragShaderModule); + pipelineCreateInfo.VertexInputState = new VertexInputState( + VertexBinding.Create(), + VertexAttribute.Create("Position", 0), + VertexAttribute.Create("TexCoord", 1) + ); + pipelineCreateInfo.VertexShaderInfo = GraphicsShaderInfo.Create(vertShaderModule, "main", 0); + pipelineCreateInfo.FragmentShaderInfo = GraphicsShaderInfo.Create(fragShaderModule, "main", 1); + pipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + // Create and populate the GPU resources + vertexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Vertex, 4); + indexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Index, 6); + sampler = new Sampler(GraphicsDevice, SamplerCreateInfo.PointClamp); + + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + cmdbuf.SetBufferData( + vertexBuffer, + new PositionTextureVertex[] + { + new PositionTextureVertex(new Vector3(-1, -1, 0), new Vector2(0, 0)), + new PositionTextureVertex(new Vector3(1, -1, 0), new Vector2(1, 0)), + new PositionTextureVertex(new Vector3(1, 1, 0), new Vector2(1, 1)), + new PositionTextureVertex(new Vector3(-1, 1, 0), new Vector2(0, 1)), + } + ); + cmdbuf.SetBufferData( + indexBuffer, + new ushort[] + { + 0, 1, 2, + 0, 2, 3, + } + ); + texture = Texture.LoadPNG(GraphicsDevice, cmdbuf, "Content/Textures/ravioli.png"); + GraphicsDevice.Submit(cmdbuf); + GraphicsDevice.Wait(); + } + + protected override void Update(System.TimeSpan delta) + { + t += (float) delta.TotalSeconds; + } + + protected override void Draw(double alpha) + { + VertexUniforms vertUniforms = new VertexUniforms(Matrix4x4.CreateRotationZ(t)); + FragmentUniforms fragUniforms = new FragmentUniforms(new Vector4(1f, 0.5f + System.MathF.Sin(t) * 0.5f, 1f, 1f)); + + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.Black)); + cmdbuf.BindGraphicsPipeline(pipeline); + cmdbuf.BindVertexBuffers(vertexBuffer); + cmdbuf.BindIndexBuffer(indexBuffer, IndexElementSize.Sixteen); + cmdbuf.PushVertexShaderUniforms(vertUniforms); + cmdbuf.BindFragmentSamplers(new TextureSamplerBinding(texture, sampler)); + cmdbuf.PushFragmentShaderUniforms(fragUniforms); + cmdbuf.DrawIndexedPrimitives(0, 0, 2, 0, 0); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + TexturedAnimatedQuadGame game = new TexturedAnimatedQuadGame(); + game.Run(); + } + } +} diff --git a/tests/TexturedQuad/TexturedQuad.csproj b/tests/TexturedQuad/TexturedQuad.csproj new file mode 100644 index 0000000..9538ed1 --- /dev/null +++ b/tests/TexturedQuad/TexturedQuad.csproj @@ -0,0 +1,22 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + + + Content\%(RecursiveDir)%(Filename)%(Extension) + Always + + + + diff --git a/tests/TexturedQuad/TexturedQuadGame.cs b/tests/TexturedQuad/TexturedQuadGame.cs new file mode 100644 index 0000000..e2e3086 --- /dev/null +++ b/tests/TexturedQuad/TexturedQuadGame.cs @@ -0,0 +1,134 @@ +using MoonWorks; +using MoonWorks.Graphics; +using MoonWorks.Math.Float; + +namespace MoonWorks.Test +{ + class TexturedQuadGame : Game + { + private GraphicsPipeline pipeline; + private ShaderModule vertShaderModule; + private ShaderModule fragShaderModule; + private Buffer vertexBuffer; + private Buffer indexBuffer; + private Texture texture; + private Sampler[] samplers = new Sampler[6]; + private string[] samplerNames = new string[] + { + "PointClamp", + "PointWrap", + "LinearClamp", + "LinearWrap", + "AnisotropicClamp", + "AnisotropicWrap" + }; + + private int currentSamplerIndex; + + public TexturedQuadGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + Logger.LogInfo("Press A and D to cycle between sampler states"); + Logger.LogInfo("Setting sampler state to: " + samplerNames[0]); + + // Load the shaders + vertShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuadVert.spv")); + fragShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuadFrag.spv")); + + // Create the graphics pipeline + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo(vertShaderModule, fragShaderModule); + pipelineCreateInfo.VertexInputState = new VertexInputState( + VertexBinding.Create(), + VertexAttribute.Create("Position", 0), + VertexAttribute.Create("TexCoord", 1) + ); + pipelineCreateInfo.FragmentShaderInfo.SamplerBindingCount = 1; + pipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + // Create samplers + samplers[0] = new Sampler(GraphicsDevice, SamplerCreateInfo.PointClamp); + samplers[1] = new Sampler(GraphicsDevice, SamplerCreateInfo.PointWrap); + samplers[2] = new Sampler(GraphicsDevice, SamplerCreateInfo.LinearClamp); + samplers[3] = new Sampler(GraphicsDevice, SamplerCreateInfo.LinearWrap); + samplers[4] = new Sampler(GraphicsDevice, SamplerCreateInfo.AnisotropicClamp); + samplers[5] = new Sampler(GraphicsDevice, SamplerCreateInfo.AnisotropicWrap); + + // Create and populate the GPU resources + vertexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Vertex, 4); + indexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Index, 6); + + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + cmdbuf.SetBufferData( + vertexBuffer, + new PositionTextureVertex[] + { + new PositionTextureVertex(new Vector3(-1, -1, 0), new Vector2(0, 0)), + new PositionTextureVertex(new Vector3(1, -1, 0), new Vector2(4, 0)), + new PositionTextureVertex(new Vector3(1, 1, 0), new Vector2(4, 4)), + new PositionTextureVertex(new Vector3(-1, 1, 0), new Vector2(0, 4)), + } + ); + cmdbuf.SetBufferData( + indexBuffer, + new ushort[] + { + 0, 1, 2, + 0, 2, 3, + } + ); + texture = Texture.LoadPNG(GraphicsDevice, cmdbuf, "Content/Textures/ravioli.png"); + GraphicsDevice.Submit(cmdbuf); + GraphicsDevice.Wait(); + } + + protected override void Update(System.TimeSpan delta) + { + int prevSamplerIndex = currentSamplerIndex; + + if (Inputs.Keyboard.IsPressed(Input.KeyCode.A)) + { + currentSamplerIndex -= 1; + if (currentSamplerIndex < 0) + { + currentSamplerIndex = samplers.Length - 1; + } + } + + if (Inputs.Keyboard.IsPressed(Input.KeyCode.D)) + { + currentSamplerIndex += 1; + if (currentSamplerIndex >= samplers.Length) + { + currentSamplerIndex = 0; + } + } + + if (prevSamplerIndex != currentSamplerIndex) + { + Logger.LogInfo("Setting sampler state to: " + samplerNames[currentSamplerIndex]); + } + } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.Black)); + cmdbuf.BindGraphicsPipeline(pipeline); + cmdbuf.BindVertexBuffers(vertexBuffer); + cmdbuf.BindIndexBuffer(indexBuffer, IndexElementSize.Sixteen); + cmdbuf.BindFragmentSamplers(new TextureSamplerBinding(texture, samplers[currentSamplerIndex])); + cmdbuf.DrawIndexedPrimitives(0, 0, 2, 0, 0); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + TexturedQuadGame game = new TexturedQuadGame(); + game.Run(); + } + } +} diff --git a/tests/TriangleVertexBuffer/TriangleVertexBuffer.csproj b/tests/TriangleVertexBuffer/TriangleVertexBuffer.csproj new file mode 100644 index 0000000..9538ed1 --- /dev/null +++ b/tests/TriangleVertexBuffer/TriangleVertexBuffer.csproj @@ -0,0 +1,22 @@ + + + + + + + + + Exe + net6.0 + enable + x64 + + + + + Content\%(RecursiveDir)%(Filename)%(Extension) + Always + + + + diff --git a/tests/TriangleVertexBuffer/TriangleVertexBufferGame.cs b/tests/TriangleVertexBuffer/TriangleVertexBufferGame.cs new file mode 100644 index 0000000..8e7eab0 --- /dev/null +++ b/tests/TriangleVertexBuffer/TriangleVertexBufferGame.cs @@ -0,0 +1,69 @@ +using MoonWorks; +using MoonWorks.Graphics; +using MoonWorks.Math.Float; + +namespace MoonWorks.Test +{ + class TriangleVertexBufferGame : Game + { + private GraphicsPipeline pipeline; + private ShaderModule vertShaderModule; + private ShaderModule fragShaderModule; + private Buffer vertexBuffer; + + public TriangleVertexBufferGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), 60, true) + { + // Load the shaders + vertShaderModule = new ShaderModule(GraphicsDevice, "Content/Shaders/Compiled/PositionColorVert.spv"); + fragShaderModule = new ShaderModule(GraphicsDevice, "Content/Shaders/Compiled/SolidColor.spv"); + + // Create the graphics pipeline + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo(vertShaderModule, fragShaderModule); + pipelineCreateInfo.VertexInputState = new VertexInputState( + VertexBinding.Create(), + VertexAttribute.Create("Position", 0), + VertexAttribute.Create("Color", 1) + ); + pipeline = new GraphicsPipeline(GraphicsDevice, pipelineCreateInfo); + + // Create and populate the vertex buffer + vertexBuffer = Buffer.Create(GraphicsDevice, BufferUsageFlags.Vertex, 3); + + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + cmdbuf.SetBufferData( + vertexBuffer, + new PositionColorVertex[] + { + new PositionColorVertex(new Vector3(-1, 1, 0), Color.Red), + new PositionColorVertex(new Vector3(1, 1, 0), Color.Lime), + new PositionColorVertex(new Vector3(0, -1, 0), Color.Blue), + } + ); + GraphicsDevice.Submit(cmdbuf); + GraphicsDevice.Wait(); + } + + protected override void Update(System.TimeSpan delta) { } + + protected override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); + if (backbuffer != null) + { + cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, Color.Black)); + cmdbuf.BindGraphicsPipeline(pipeline); + cmdbuf.BindVertexBuffers(vertexBuffer); + cmdbuf.DrawPrimitives(0, 1, 0, 0); + cmdbuf.EndRenderPass(); + } + GraphicsDevice.Submit(cmdbuf); + } + + public static void Main(string[] args) + { + TriangleVertexBufferGame p = new TriangleVertexBufferGame(); + p.Run(); + } + } +} -- 2.25.1