From 43d0c2100ef1a5df4b54525e50eb29fe7c39ec16 Mon Sep 17 00:00:00 2001 From: Gangzheng Tong Date: Tue, 8 Jul 2025 23:44:56 -0700 Subject: Convert gfx unit tests and examples to use slang-rhi (#7577) * Port first gfx unit test to slang-rhi * port triangle example to use slang-rhi * port platform-test to slang-rhi * Update platform-test to throttle mouse move events * port gpu-printing example to use slang-rhi * port model-viewer example to use slang-rhi * port ray-tracing example to use slang-rhi * port ray-tracing pipeline example to use slang-rhi * port reflection parameter blocks example to use slang-rhi * port shader-object example to use slang-rhi * port shader-toy example to use slang-rhi * Port most of tests to slang-rhi * port link-time-constant-array-size to use slang-rhi * Fix tests and find matching tests in slang-rhi * port autodiff-texture * remove gfx target; port nv-aftermath-example * update include path for shader-cursor.h * Disabled 2 more ported tests * fix build error * remove gfx test * put slang-rhi (static-lib) before slang (shared) * format code (#7621) Co-authored-by: slangbot <186143334+slangbot@users.noreply.github.com> * add debug callback * format code (#7649) Co-authored-by: slangbot <186143334+slangbot@users.noreply.github.com> * Address review comments; revert back to use SLANG_CHECK_MSG --------- Co-authored-by: slangbot Co-authored-by: slangbot <186143334+slangbot@users.noreply.github.com> --- examples/shader-toy/main.cpp | 106 +++++++++++++++++++++++++------------------ 1 file changed, 62 insertions(+), 44 deletions(-) (limited to 'examples/shader-toy/main.cpp') diff --git a/examples/shader-toy/main.cpp b/examples/shader-toy/main.cpp index 42054beae..549dbef73 100644 --- a/examples/shader-toy/main.cpp +++ b/examples/shader-toy/main.cpp @@ -21,16 +21,16 @@ using Slang::ComPtr; // #include "core/slang-basic.h" #include "examples/example-base/example-base.h" -#include "gfx-util/shader-cursor.h" #include "platform/performance-counter.h" #include "platform/window.h" -#include "slang-gfx.h" +#include "slang-rhi.h" +#include "slang-rhi/shader-cursor.h" #include static const ExampleResources resourceBase("shader-toy"); -using namespace gfx; +using namespace rhi; // In order to display a shader toy effect using rasterization-based shader // execution we need to render a full-screen triangle. We will define a @@ -83,15 +83,15 @@ struct ShaderToyApp : public WindowedAppBase // The main interesting part of the host application code is where we // load, compile, inspect, and compose the Slang shader code. // - Result loadShaderProgram(gfx::IDevice* device, ComPtr& outShaderProgram) + Result loadShaderProgram(IDevice* device, ComPtr& outShaderProgram) { // We need to obatin a compilation session (`slang::ISession`) that will provide // a scope to all the compilation and loading of code we do. // - // Our example application uses the `gfx` graphics API abstraction layer, which already - // creates a Slang compilation session for us, so we just grab and use it here. + // Our example application uses the `slang-rhi` graphics API abstraction layer, which + // already creates a Slang compilation session for us, so we just grab and use it here. ComPtr slangSession; - SLANG_RETURN_ON_FAIL(device->getSlangSession(slangSession.writeRef())); + slangSession = device->getSlangSession(); // Once the session has been obtained, we can start loading code into it. // @@ -269,16 +269,17 @@ struct ShaderToyApp : public WindowedAppBase diagnoseIfNeeded(diagnosticsBlob); SLANG_RETURN_ON_FAIL(result); - gfx::IShaderProgram::Desc programDesc = {}; + ShaderProgramDesc programDesc = {}; programDesc.slangGlobalScope = linkedProgram.get(); - auto shaderProgram = device->createProgram(programDesc); + auto shaderProgram = device->createShaderProgram(programDesc); outShaderProgram = shaderProgram; return SLANG_OK; } ComPtr gShaderProgram; - ComPtr gPipelineState; - ComPtr gVertexBuffer; + ComPtr gPipeline; + ComPtr gVertexBuffer; + const Format format = Format::RG32Float; Result initialize() { @@ -296,7 +297,7 @@ struct ShaderToyApp : public WindowedAppBase } InputElementDesc inputElements[] = { - {"POSITION", 0, Format::R32G32_FLOAT, offsetof(FullScreenTriangle::Vertex, position)}, + {"POSITION", 0, format, offsetof(FullScreenTriangle::Vertex, position)}, }; auto inputLayout = gDevice->createInputLayout( sizeof(FullScreenTriangle::Vertex), @@ -305,29 +306,32 @@ struct ShaderToyApp : public WindowedAppBase if (!inputLayout) return SLANG_FAIL; - IBufferResource::Desc vertexBufferDesc; - vertexBufferDesc.type = IResource::Type::Buffer; - vertexBufferDesc.sizeInBytes = + BufferDesc vertexBufferDesc; + vertexBufferDesc.size = FullScreenTriangle::kVertexCount * sizeof(FullScreenTriangle::Vertex); - vertexBufferDesc.defaultState = ResourceState::VertexBuffer; - gVertexBuffer = - gDevice->createBufferResource(vertexBufferDesc, &FullScreenTriangle::kVertices[0]); + vertexBufferDesc.elementSize = sizeof(FullScreenTriangle::Vertex); + vertexBufferDesc.usage = BufferUsage::VertexBuffer; + gVertexBuffer = gDevice->createBuffer(vertexBufferDesc, &FullScreenTriangle::kVertices[0]); if (!gVertexBuffer) return SLANG_FAIL; SLANG_RETURN_ON_FAIL(loadShaderProgram(gDevice, gShaderProgram)); // Create pipeline. - GraphicsPipelineStateDesc desc; + ColorTargetDesc colorTarget; + colorTarget.format = Format::RGBA8Unorm; + RenderPipelineDesc desc; desc.inputLayout = inputLayout; desc.program = gShaderProgram; - desc.framebufferLayout = gFramebufferLayout; - auto pipelineState = gDevice->createGraphicsPipelineState(desc); - if (!pipelineState) + desc.targetCount = 1; + desc.targets = &colorTarget; + desc.depthStencil.depthTestEnable = false; + desc.depthStencil.depthWriteEnable = false; + desc.primitiveTopology = PrimitiveTopology::TriangleList; + gPipeline = gDevice->createRenderPipeline(desc); + if (!gPipeline) return SLANG_FAIL; - gPipelineState = pipelineState; - return SLANG_OK; } @@ -341,9 +345,9 @@ struct ShaderToyApp : public WindowedAppBase bool firstTime = true; platform::TimePoint startTime; - virtual void renderFrame(int frameIndex) override + virtual void renderFrame(ITexture* texture) override { - auto commandBuffer = gTransientHeaps[frameIndex]->createCommandBuffer(); + auto commandEncoder = gQueue->createCommandEncoder(); if (firstTime) { startTime = platform::PerformanceCounter::now(); @@ -373,29 +377,43 @@ struct ShaderToyApp : public WindowedAppBase } // Encode render commands. - auto encoder = commandBuffer->encodeRenderCommands(gRenderPass, gFramebuffers[frameIndex]); - - gfx::Viewport viewport = {}; - viewport.maxZ = 1.0f; - viewport.extentX = (float)windowWidth; - viewport.extentY = (float)windowHeight; - encoder->setViewportAndScissor(viewport); - auto rootObject = encoder->bindPipeline(gPipelineState); + ComPtr textureView = gDevice->createTextureView(texture, {}); + RenderPassColorAttachment colorAttachment = {}; + colorAttachment.view = textureView; + colorAttachment.loadOp = LoadOp::Clear; + + RenderPassDesc renderPass = {}; + renderPass.colorAttachments = &colorAttachment; + renderPass.colorAttachmentCount = 1; + + auto encoder = commandEncoder->beginRenderPass(renderPass); + + RenderState renderState = {}; + renderState.viewports[0] = Viewport::fromSize(windowWidth, windowHeight); + renderState.viewportCount = 1; + renderState.scissorRects[0] = ScissorRect::fromSize(windowWidth, windowHeight); + renderState.scissorRectCount = 1; + + auto rootObject = encoder->bindPipeline(static_cast(gPipeline.get())); auto constantBuffer = rootObject->getObject(ShaderOffset()); constantBuffer->setData(ShaderOffset(), &uniforms, sizeof(uniforms)); - encoder->setVertexBuffer(0, gVertexBuffer); - encoder->setPrimitiveTopology(PrimitiveTopology::TriangleList); - encoder->draw(3); - encoder->endEncoding(); - commandBuffer->close(); + renderState.vertexBuffers[0] = gVertexBuffer; + renderState.vertexBufferCount = 1; + encoder->setRenderState(renderState); - gQueue->executeCommandBuffer(commandBuffer); + DrawArguments drawArgs = {}; + drawArgs.vertexCount = 3; + encoder->draw(drawArgs); - // We may not have a swapchain if we're running in test mode - SLANG_ASSERT(isTestMode() || gSwapchain); - if (gSwapchain) - gSwapchain->present(); + encoder->end(); + + gQueue->submit(commandEncoder->finish()); + + if (!isTestMode()) + { + gSurface->present(); + } } void handleEvent(const platform::MouseEventArgs& event) -- cgit v1.2.3