diff --git a/Examples/TexturedQuadExample.cs b/Examples/TexturedQuadExample.cs new file mode 100644 index 0000000..134c477 --- /dev/null +++ b/Examples/TexturedQuadExample.cs @@ -0,0 +1,205 @@ +using System; +using MoonWorks; +using MoonWorks.Graphics; +using MoonWorks.Input; +using MoonWorks.Math.Float; + +namespace MoonWorksGraphicsTests; + +class TexturedQuadExample : Example +{ + private GraphicsPipeline pipeline; + private GpuBuffer vertexBuffer; + private GpuBuffer indexBuffer; + private Sampler[] samplers = new Sampler[6]; + private string[] samplerNames = new string[] + { + "PointClamp", + "PointWrap", + "LinearClamp", + "LinearWrap", + "AnisotropicClamp", + "AnisotropicWrap" + }; + + private int currentSamplerIndex; + + private Texture[] textures = new Texture[4]; + private string[] imageLoadFormatNames = new string[] + { + "PNG from file", + "PNG from memory", + "QOI from file", + "QOI from memory" + }; + + private int currentTextureIndex; + + private System.Diagnostics.Stopwatch stopwatch = new System.Diagnostics.Stopwatch(); + + public override void Init(Window window, GraphicsDevice graphicsDevice, Inputs inputs) + { + Window = window; + GraphicsDevice = graphicsDevice; + Inputs = inputs; + + Window.SetTitle("TexturedQuad"); + + Logger.LogInfo("Press Left and Right to cycle between sampler states"); + Logger.LogInfo("Setting sampler state to: " + samplerNames[0]); + + Logger.LogInfo("Press Down to cycle between image load formats"); + Logger.LogInfo("Setting image format to: " + imageLoadFormatNames[0]); + + var pngBytes = System.IO.File.ReadAllBytes(TestUtils.GetTexturePath("ravioli.png")); + var qoiBytes = System.IO.File.ReadAllBytes(TestUtils.GetTexturePath("ravioli.qoi")); + + Logger.LogInfo(pngBytes.Length.ToString()); + Logger.LogInfo(qoiBytes.Length.ToString()); + + // Load the shaders + Shader vertShader = new Shader( + GraphicsDevice, + TestUtils.GetShaderPath("TexturedQuad.vert"), + "main", + ShaderStage.Vertex, + ShaderFormat.SPIRV + ); + + Shader fragShader = new Shader( + GraphicsDevice, + TestUtils.GetShaderPath("TexturedQuad.frag"), + "main", + ShaderStage.Fragment, + ShaderFormat.SPIRV + ); + + // Create the graphics pipeline + GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo( + Window.SwapchainFormat, + vertShader, + fragShader + ); + pipelineCreateInfo.VertexInputState = VertexInputState.CreateSingleBinding(); + pipelineCreateInfo.FragmentShaderResourceInfo = new GraphicsPipelineResourceInfo + { + SamplerCount = 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); + + var vertexData = new Span([ + 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)), + ]); + + var indexData = new Span([ + 0, 1, 2, + 0, 2, 3, + ]); + + // Create and populate the GPU resources + + var resourceUploader = new ResourceUploader(GraphicsDevice); + + vertexBuffer = resourceUploader.CreateBuffer(vertexData, BufferUsageFlags.Vertex); + indexBuffer = resourceUploader.CreateBuffer(indexData, BufferUsageFlags.Index); + + textures[0] = resourceUploader.CreateTexture2DFromCompressed(TestUtils.GetTexturePath("ravioli.png")); + textures[1] = resourceUploader.CreateTexture2DFromCompressed(pngBytes); + textures[2] = resourceUploader.CreateTexture2DFromCompressed(TestUtils.GetTexturePath("ravioli.qoi")); + textures[3] = resourceUploader.CreateTexture2DFromCompressed(qoiBytes); + + resourceUploader.Upload(); + resourceUploader.Dispose(); + } + + public override void Update(System.TimeSpan delta) + { + int prevSamplerIndex = currentSamplerIndex; + + if (TestUtils.CheckButtonPressed(Inputs, TestUtils.ButtonType.Left)) + { + currentSamplerIndex -= 1; + if (currentSamplerIndex < 0) + { + currentSamplerIndex = samplers.Length - 1; + } + } + + if (TestUtils.CheckButtonPressed(Inputs, TestUtils.ButtonType.Right)) + { + currentSamplerIndex += 1; + if (currentSamplerIndex >= samplers.Length) + { + currentSamplerIndex = 0; + } + } + + if (prevSamplerIndex != currentSamplerIndex) + { + Logger.LogInfo("Setting sampler state to: " + samplerNames[currentSamplerIndex]); + } + + int prevTextureIndex = currentTextureIndex; + + if (TestUtils.CheckButtonPressed(Inputs, TestUtils.ButtonType.Bottom)) + { + currentTextureIndex = (currentTextureIndex + 1) % imageLoadFormatNames.Length; + } + + if (prevTextureIndex != currentTextureIndex) + { + Logger.LogInfo("Setting texture format to: " + imageLoadFormatNames[currentTextureIndex]); + } + } + + public override void Draw(double alpha) + { + CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); + Texture swapchainTexture = cmdbuf.AcquireSwapchainTexture(Window); + if (swapchainTexture != null) + { + var renderPass = cmdbuf.BeginRenderPass( + new ColorAttachmentInfo( + swapchainTexture, + false, + Color.Black + ) + ); + renderPass.BindGraphicsPipeline(pipeline); + renderPass.BindVertexBuffer(vertexBuffer); + renderPass.BindIndexBuffer(indexBuffer, IndexElementSize.Sixteen); + renderPass.BindFragmentSampler(new TextureSamplerBinding(textures[currentTextureIndex], samplers[currentSamplerIndex])); + renderPass.DrawIndexedPrimitives(0, 0, 2); + cmdbuf.EndRenderPass(renderPass); + } + GraphicsDevice.Submit(cmdbuf); + } + + public override void Destroy() + { + pipeline.Dispose(); + vertexBuffer.Dispose(); + indexBuffer.Dispose(); + + for (var i = 0; i < samplers.Length; i += 1) + { + samplers[i].Dispose(); + } + + for (var i = 0; i < textures.Length; i += 1) + { + textures[i].Dispose(); + } + } +} diff --git a/Examples/TexturedQuadGame.cs b/Examples/TexturedQuadGame.cs deleted file mode 100644 index 6be5efb..0000000 --- a/Examples/TexturedQuadGame.cs +++ /dev/null @@ -1,165 +0,0 @@ -using System; -using MoonWorks.Graphics; -using MoonWorks.Math.Float; - -namespace MoonWorks.Test -{ - class TexturedQuadGame : Game - { - private GraphicsPipeline pipeline; - private GpuBuffer vertexBuffer; - private GpuBuffer indexBuffer; - private Sampler[] samplers = new Sampler[6]; - private string[] samplerNames = new string[] - { - "PointClamp", - "PointWrap", - "LinearClamp", - "LinearWrap", - "AnisotropicClamp", - "AnisotropicWrap" - }; - - private int currentSamplerIndex; - - private Texture[] textures = new Texture[4]; - private string[] imageLoadFormatNames = new string[] - { - "PNG from file", - "PNG from memory", - "QOI from file", - "QOI from memory" - }; - - private int currentTextureIndex; - - private System.Diagnostics.Stopwatch stopwatch = new System.Diagnostics.Stopwatch(); - - public TexturedQuadGame() : base(TestUtils.GetStandardWindowCreateInfo(), TestUtils.GetStandardFrameLimiterSettings(), TestUtils.PreferredBackends, 60, true) - { - Logger.LogInfo("Press Left and Right to cycle between sampler states"); - Logger.LogInfo("Setting sampler state to: " + samplerNames[0]); - - Logger.LogInfo("Press Down to cycle between image load formats"); - Logger.LogInfo("Setting image format to: " + imageLoadFormatNames[0]); - - var pngBytes = System.IO.File.ReadAllBytes(TestUtils.GetTexturePath("ravioli.png")); - var qoiBytes = System.IO.File.ReadAllBytes(TestUtils.GetTexturePath("ravioli.qoi")); - - Logger.LogInfo(pngBytes.Length.ToString()); - Logger.LogInfo(qoiBytes.Length.ToString()); - - // Load the shaders - ShaderModule vertShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuad.vert")); - ShaderModule fragShaderModule = new ShaderModule(GraphicsDevice, TestUtils.GetShaderPath("TexturedQuad.frag")); - - // Create the graphics pipeline - GraphicsPipelineCreateInfo pipelineCreateInfo = TestUtils.GetStandardGraphicsPipelineCreateInfo( - MainWindow.SwapchainFormat, - vertShaderModule, - fragShaderModule - ); - pipelineCreateInfo.VertexInputState = VertexInputState.CreateSingleBinding(); - 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); - - var vertexData = new Span([ - 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)), - ]); - - var indexData = new Span([ - 0, 1, 2, - 0, 2, 3, - ]); - - // Create and populate the GPU resources - - var resourceUploader = new ResourceUploader(GraphicsDevice); - - vertexBuffer = resourceUploader.CreateBuffer(vertexData, BufferUsageFlags.Vertex); - indexBuffer = resourceUploader.CreateBuffer(indexData, BufferUsageFlags.Index); - - textures[0] = resourceUploader.CreateTexture2DFromCompressed(TestUtils.GetTexturePath("ravioli.png")); - textures[1] = resourceUploader.CreateTexture2DFromCompressed(pngBytes); - textures[2] = resourceUploader.CreateTexture2DFromCompressed(TestUtils.GetTexturePath("ravioli.qoi")); - textures[3] = resourceUploader.CreateTexture2DFromCompressed(qoiBytes); - - resourceUploader.Upload(); - resourceUploader.Dispose(); - } - - protected override void Update(System.TimeSpan delta) - { - int prevSamplerIndex = currentSamplerIndex; - - if (TestUtils.CheckButtonPressed(Inputs, TestUtils.ButtonType.Left)) - { - currentSamplerIndex -= 1; - if (currentSamplerIndex < 0) - { - currentSamplerIndex = samplers.Length - 1; - } - } - - if (TestUtils.CheckButtonPressed(Inputs, TestUtils.ButtonType.Right)) - { - currentSamplerIndex += 1; - if (currentSamplerIndex >= samplers.Length) - { - currentSamplerIndex = 0; - } - } - - if (prevSamplerIndex != currentSamplerIndex) - { - Logger.LogInfo("Setting sampler state to: " + samplerNames[currentSamplerIndex]); - } - - int prevTextureIndex = currentTextureIndex; - - if (TestUtils.CheckButtonPressed(Inputs, TestUtils.ButtonType.Bottom)) - { - currentTextureIndex = (currentTextureIndex + 1) % imageLoadFormatNames.Length; - } - - if (prevTextureIndex != currentTextureIndex) - { - Logger.LogInfo("Setting texture format to: " + imageLoadFormatNames[currentTextureIndex]); - } - } - - protected override void Draw(double alpha) - { - CommandBuffer cmdbuf = GraphicsDevice.AcquireCommandBuffer(); - Texture? backbuffer = cmdbuf.AcquireSwapchainTexture(MainWindow); - if (backbuffer != null) - { - cmdbuf.BeginRenderPass(new ColorAttachmentInfo(backbuffer, WriteOptions.Cycle, Color.Black)); - cmdbuf.BindGraphicsPipeline(pipeline); - cmdbuf.BindVertexBuffers(vertexBuffer); - cmdbuf.BindIndexBuffer(indexBuffer, IndexElementSize.Sixteen); - cmdbuf.BindFragmentSamplers(new TextureSamplerBinding(textures[currentTextureIndex], samplers[currentSamplerIndex])); - cmdbuf.DrawIndexedPrimitives(0, 0, 2); - cmdbuf.EndRenderPass(); - } - GraphicsDevice.Submit(cmdbuf); - } - - public static void Main(string[] args) - { - TexturedQuadGame game = new TexturedQuadGame(); - game.Run(); - } - } -} diff --git a/MoonWorksGraphicsTests.csproj b/MoonWorksGraphicsTests.csproj index a9aabdc..629316a 100644 --- a/MoonWorksGraphicsTests.csproj +++ b/MoonWorksGraphicsTests.csproj @@ -48,6 +48,7 @@ + diff --git a/Program.cs b/Program.cs index adbae26..3c4bd97 100644 --- a/Program.cs +++ b/Program.cs @@ -31,7 +31,8 @@ class Program : Game new StoreLoadExample(), new Texture3DCopyExample(), new Texture3DExample(), - new TexturedAnimatedQuadExample() + new TexturedAnimatedQuadExample(), + new TexturedQuadExample() ]; int ExampleIndex = 0;