From c1448536b412d5ee725beb0ae0d90ed1bb9fa787 Mon Sep 17 00:00:00 2001 From: David Steele Date: Thu, 8 Apr 2021 19:30:52 +0100 Subject: [PATCH] Syncing test harness Change-Id: I204c191c5a54e198996557bdfbae12212f9e0c96 --- .../src/dali-scene-loader-internal/CMakeLists.txt | 1 + .../src/dali-scene-loader/CMakeLists.txt | 1 + .../src/dali-toolkit-internal/CMakeLists.txt | 1 + .../src/dali-toolkit-styling/CMakeLists.txt | 1 + .../src/dali-toolkit-third-party/CMakeLists.txt | 1 + automated-tests/src/dali-toolkit/CMakeLists.txt | 1 + .../dali-toolkit-test-utils/test-actor-utils.cpp | 13 +- .../dali-toolkit-test-utils/test-actor-utils.h | 5 +- .../test-gl-abstraction.cpp | 27 +- .../dali-toolkit-test-utils/test-gl-abstraction.h | 5 + .../test-graphics-command-buffer.cpp | 23 + .../test-graphics-command-buffer.h | 144 ++++- .../test-graphics-controller.cpp | 591 +++++++++++++-------- .../test-graphics-controller.h | 54 ++ .../test-graphics-framebuffer.cpp | 165 ++++++ .../test-graphics-framebuffer.h | 49 ++ .../test-graphics-pipeline.cpp | 5 +- .../test-graphics-render-pass.h | 41 ++ .../test-graphics-render-target.h | 44 ++ .../test-graphics-texture.h | 16 + .../toolkit-scene-holder-impl.h | 8 +- 21 files changed, 926 insertions(+), 270 deletions(-) create mode 100644 automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp create mode 100644 automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.h create mode 100644 automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-pass.h create mode 100644 automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-target.h diff --git a/automated-tests/src/dali-scene-loader-internal/CMakeLists.txt b/automated-tests/src/dali-scene-loader-internal/CMakeLists.txt index 16f96f0..eee1059 100755 --- a/automated-tests/src/dali-scene-loader-internal/CMakeLists.txt +++ b/automated-tests/src/dali-scene-loader-internal/CMakeLists.txt @@ -46,6 +46,7 @@ SET(TEST_HARNESS_SOURCES ${TEST_HARNESS_DIR}/test-graphics-buffer.cpp ${TEST_HARNESS_DIR}/test-graphics-command-buffer.cpp ${TEST_HARNESS_DIR}/test-graphics-controller.cpp + ${TEST_HARNESS_DIR}/test-graphics-framebuffer.cpp ${TEST_HARNESS_DIR}/test-graphics-texture.cpp ${TEST_HARNESS_DIR}/test-graphics-sampler.cpp ${TEST_HARNESS_DIR}/test-graphics-pipeline.cpp diff --git a/automated-tests/src/dali-scene-loader/CMakeLists.txt b/automated-tests/src/dali-scene-loader/CMakeLists.txt index f0d84fb..108a3c4 100755 --- a/automated-tests/src/dali-scene-loader/CMakeLists.txt +++ b/automated-tests/src/dali-scene-loader/CMakeLists.txt @@ -59,6 +59,7 @@ SET(TEST_HARNESS_SOURCES ${TEST_HARNESS_DIR}/test-gl-sync-abstraction.cpp ${TEST_HARNESS_DIR}/test-graphics-buffer.cpp ${TEST_HARNESS_DIR}/test-graphics-command-buffer.cpp + ${TEST_HARNESS_DIR}/test-graphics-framebuffer.cpp ${TEST_HARNESS_DIR}/test-graphics-controller.cpp ${TEST_HARNESS_DIR}/test-graphics-texture.cpp ${TEST_HARNESS_DIR}/test-graphics-sampler.cpp diff --git a/automated-tests/src/dali-toolkit-internal/CMakeLists.txt b/automated-tests/src/dali-toolkit-internal/CMakeLists.txt index cc18fe6..e90e147 100755 --- a/automated-tests/src/dali-toolkit-internal/CMakeLists.txt +++ b/automated-tests/src/dali-toolkit-internal/CMakeLists.txt @@ -83,6 +83,7 @@ SET(TEST_HARNESS_SOURCES ../dali-toolkit/dali-toolkit-test-utils/test-graphics-buffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp + ../dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-program.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp diff --git a/automated-tests/src/dali-toolkit-styling/CMakeLists.txt b/automated-tests/src/dali-toolkit-styling/CMakeLists.txt index cc1488e..e3d235b 100644 --- a/automated-tests/src/dali-toolkit-styling/CMakeLists.txt +++ b/automated-tests/src/dali-toolkit-styling/CMakeLists.txt @@ -49,6 +49,7 @@ SET(TEST_HARNESS_SOURCES ../dali-toolkit/dali-toolkit-test-utils/test-graphics-buffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp + ../dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-program.cpp diff --git a/automated-tests/src/dali-toolkit-third-party/CMakeLists.txt b/automated-tests/src/dali-toolkit-third-party/CMakeLists.txt index 820a4a5..d8638a2 100644 --- a/automated-tests/src/dali-toolkit-third-party/CMakeLists.txt +++ b/automated-tests/src/dali-toolkit-third-party/CMakeLists.txt @@ -35,6 +35,7 @@ SET(TEST_HARNESS_SOURCES ../dali-toolkit/dali-toolkit-test-utils/test-graphics-buffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp + ../dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sampler.cpp ../dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp diff --git a/automated-tests/src/dali-toolkit/CMakeLists.txt b/automated-tests/src/dali-toolkit/CMakeLists.txt index c3ab255..080fd8d 100755 --- a/automated-tests/src/dali-toolkit/CMakeLists.txt +++ b/automated-tests/src/dali-toolkit/CMakeLists.txt @@ -116,6 +116,7 @@ SET(TEST_HARNESS_SOURCES dali-toolkit-test-utils/test-graphics-buffer.cpp dali-toolkit-test-utils/test-graphics-command-buffer.cpp dali-toolkit-test-utils/test-graphics-controller.cpp + dali-toolkit-test-utils/test-graphics-framebuffer.cpp dali-toolkit-test-utils/test-graphics-texture.cpp dali-toolkit-test-utils/test-graphics-pipeline.cpp dali-toolkit-test-utils/test-graphics-program.cpp diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.cpp index 2db4dbc..756deb5 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.cpp +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * Copyright (c) 2021 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -91,4 +91,15 @@ Actor CreateRenderableActor(Texture texture, const std::string& vertexShader, co return actor; } +Texture CreateTexture(TextureType::Type type, Pixel::Format format, int width, int height) +{ + Texture texture = Texture::New(type, format, width, height); + + int bufferSize = width * height * 2; + uint8_t* buffer = reinterpret_cast(malloc(bufferSize)); + PixelData pixelData = PixelData::New(buffer, bufferSize, width, height, format, PixelData::FREE); + texture.Upload(pixelData, 0u, 0u, 0u, 0u, width, height); + return texture; +} + } // namespace Dali diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.h index be085bf..523fea5 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.h +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.h @@ -2,7 +2,7 @@ #define DALI_TEST_ACTOR_UTILS_H /* - * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * Copyright (c) 2021 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -19,6 +19,7 @@ */ // EXTERNAL INCLUDES +#include #include namespace Dali @@ -49,6 +50,8 @@ Actor CreateRenderableActor(Texture texture); */ Actor CreateRenderableActor(Texture texture, const std::string& vertexShader, const std::string& fragmentShader); +Texture CreateTexture(TextureType::Type type, Pixel::Format format, int width, int height); + } // namespace Dali #endif // DALI_TEST_ACTOR_UTILS_H diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp index f2086d6..ddeb1d9 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp @@ -18,21 +18,24 @@ #include "test-gl-abstraction.h" #include "test-trace-call-stack.h" +static const bool TRACE{ + false}; + namespace Dali { TestGlAbstraction::TestGlAbstraction() -: mBufferTrace(true, std::string("gl")), - mCullFaceTrace(true, "gl"), - mEnableDisableTrace(true, "gl"), - mShaderTrace(true, "gl"), - mTextureTrace(true, std::string("gl")), - mTexParameterTrace(true, "gl"), - mDrawTrace(true, "gl"), - mDepthFunctionTrace(true, "gl"), - mStencilFunctionTrace(true, "gl"), - mScissorTrace(true, "gl"), - mSetUniformTrace(true, "Uniform "), - mViewportTrace(true, "gl") +: mBufferTrace(TRACE, std::string("gl")), + mCullFaceTrace(TRACE, "gl"), + mEnableDisableTrace(TRACE, "gl"), + mShaderTrace(TRACE, "gl"), + mTextureTrace(TRACE, std::string("gl")), + mTexParameterTrace(TRACE, "gl"), + mDrawTrace(TRACE, "gl"), + mDepthFunctionTrace(TRACE, "gl"), + mStencilFunctionTrace(TRACE, "gl"), + mScissorTrace(TRACE, "gl"), + mSetUniformTrace(TRACE, "Uniform "), + mViewportTrace(TRACE, "gl") { Initialize(); } diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.h index 9357803..760f678 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.h +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.h @@ -621,6 +621,11 @@ public: { mFramebufferStencilAttached = true; } + else if(attachment == GL_DEPTH_STENCIL_ATTACHMENT) + { + mFramebufferStencilAttached = true; + mFramebufferDepthAttached = true; + } } inline void FramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level) override diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp index ed63416..78c6fbb 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp @@ -73,4 +73,27 @@ std::vector TestGraphicsCommandBuffer::GetCommandsByType(CommandTypeMa return mCommandStack; } +std::vector TestGraphicsCommandBuffer::GetChildCommandsByType(CommandTypeMask mask) +{ + std::vector mCommandStack{}; + for(auto& cmd : mCommands) + { + if(uint32_t(cmd.type) == (mask & uint32_t(cmd.type))) + { + mCommandStack.emplace_back(&cmd); + } + if(cmd.type == CommandType::EXECUTE_COMMAND_BUFFERS) + { + for(auto secondaryCB : cmd.data.executeCommandBuffers.buffers) + { + for(auto command : secondaryCB->GetChildCommandsByType(mask)) + { + mCommandStack.push_back(command); + } + } + } + } + return mCommandStack; +} + } // namespace Dali diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.h index c10c3f1..bc1ea7b 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.h +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.h @@ -32,25 +32,29 @@ namespace Dali { class TestGraphicsTexture; class TestGraphicsBuffer; +class TestGraphicsCommandBuffer; class TestGraphicsSampler; class TestGraphicsPipeline; enum class CommandType { - FLUSH = 1 << 0, - BIND_TEXTURES = 1 << 1, - BIND_SAMPLERS = 1 << 2, - BIND_VERTEX_BUFFERS = 1 << 3, - BIND_INDEX_BUFFER = 1 << 4, - BIND_UNIFORM_BUFFER = 1 << 5, - BIND_PIPELINE = 1 << 6, - DRAW = 1 << 7, - DRAW_INDEXED = 1 << 8, - DRAW_INDEXED_INDIRECT = 1 << 9, - SET_SCISSOR = 1 << 10, - SET_SCISSOR_TEST = 1 << 11, - SET_VIEWPORT = 1 << 12, - SET_VIEWPORT_TEST = 1 << 13 + FLUSH = 1 << 0, + BIND_TEXTURES = 1 << 1, + BIND_SAMPLERS = 1 << 2, + BIND_VERTEX_BUFFERS = 1 << 3, + BIND_INDEX_BUFFER = 1 << 4, + BIND_UNIFORM_BUFFER = 1 << 5, + BIND_PIPELINE = 1 << 6, + DRAW = 1 << 7, + DRAW_INDEXED = 1 << 8, + DRAW_INDEXED_INDIRECT = 1 << 9, + SET_SCISSOR = 1 << 10, + SET_SCISSOR_TEST = 1 << 11, + SET_VIEWPORT = 1 << 12, + SET_VIEWPORT_TEST = 1 << 13, + BEGIN_RENDER_PASS = 1 << 14, + END_RENDER_PASS = 1 << 15, + EXECUTE_COMMAND_BUFFERS = 1 << 16 }; using CommandTypeMask = uint32_t; @@ -160,8 +164,37 @@ struct Command { } + Command(CommandType type) + : type(type) + { + // do non-trivial initialization + switch(type) + { + case CommandType::BEGIN_RENDER_PASS: + { + new(&data.beginRenderPass) CommandData::BeginRenderPassDescriptor(); + break; + } + default: + { + } + } + } + ~Command() { + switch(type) + { + case CommandType::BEGIN_RENDER_PASS: + { + data.beginRenderPass.~BeginRenderPassDescriptor(); + break; + } + default: + { + break; + } + } } /** @@ -172,6 +205,22 @@ struct Command { switch(rhs.type) { + case CommandType::BEGIN_RENDER_PASS: + { + new(&data.beginRenderPass) CommandData::BeginRenderPassDescriptor(rhs.data.beginRenderPass); + break; + } + case CommandType::END_RENDER_PASS: + { + data.endRenderPass = rhs.data.endRenderPass; + break; + } + case CommandType::EXECUTE_COMMAND_BUFFERS: + { + data.executeCommandBuffers = rhs.data.executeCommandBuffers; + break; + } + case CommandType::BIND_VERTEX_BUFFERS: { data.bindVertexBuffers = rhs.data.bindVertexBuffers; @@ -257,6 +306,21 @@ struct Command { switch(rhs.type) { + case CommandType::BEGIN_RENDER_PASS: + { + new(&data.beginRenderPass) CommandData::BeginRenderPassDescriptor(std::move(rhs.data.beginRenderPass)); + break; + } + case CommandType::END_RENDER_PASS: + { + data.endRenderPass = std::move(rhs.data.endRenderPass); + break; + } + case CommandType::EXECUTE_COMMAND_BUFFERS: + { + data.executeCommandBuffers = std::move(rhs.data.executeCommandBuffers); + break; + } case CommandType::BIND_VERTEX_BUFFERS: { data.bindVertexBuffers = std::move(rhs.data.bindVertexBuffers); @@ -398,6 +462,24 @@ struct Command { bool enable; } viewportTest; + + struct BeginRenderPassDescriptor + { + Graphics::RenderPass* renderPass; + Graphics::RenderTarget* renderTarget; + Graphics::Rect2D renderArea; + std::vector clearValues; + } beginRenderPass; + + struct + { + } endRenderPass; + + struct + { + std::vector buffers; + } executeCommandBuffers; + } data; }; @@ -509,12 +591,23 @@ public: } void BeginRenderPass( - Graphics::RenderPass& renderPass, - Graphics::RenderTarget& renderTarget, - Graphics::Extent2D renderArea, + Graphics::RenderPass* renderPass, + Graphics::RenderTarget* renderTarget, + Graphics::Rect2D renderArea, std::vector clearValues) override { - mCallStack.PushCall("BeginRenderPass", ""); + mCommands.emplace_back(CommandType::BEGIN_RENDER_PASS); + auto& cmd = mCommands.back(); + cmd.data.beginRenderPass.renderPass = renderPass; + cmd.data.beginRenderPass.renderTarget = renderTarget; + cmd.data.beginRenderPass.renderArea = renderArea; + cmd.data.beginRenderPass.clearValues = clearValues; + + TraceCallStack::NamedParams namedParams; + namedParams["renderPass"] << std::hex << renderPass; + namedParams["renderTarget"] << std::hex << renderTarget; + namedParams["renderArea"] << renderArea.width << ", " << renderArea.height; + mCallStack.PushCall("BeginRenderPass", namedParams.str(), namedParams); } /** @@ -531,6 +624,19 @@ public: mCallStack.PushCall("EndRenderPass", ""); } + void ExecuteCommandBuffers(std::vector&& commandBuffers) override + { + mCommands.emplace_back(); + auto& cmd = mCommands.back(); + cmd.type = CommandType::EXECUTE_COMMAND_BUFFERS; + cmd.data.executeCommandBuffers.buffers.reserve(commandBuffers.size()); + for(auto&& item : commandBuffers) + { + cmd.data.executeCommandBuffers.buffers.emplace_back(static_cast(item)); + } + mCallStack.PushCall("ExecuteCommandBuffers", ""); + } + void Draw( uint32_t vertexCount, uint32_t instanceCount, @@ -664,6 +770,8 @@ public: */ std::vector GetCommandsByType(CommandTypeMask mask); + std::vector GetChildCommandsByType(CommandTypeMask mask); + private: TraceCallStack& mCallStack; TestGlAbstraction& mGlAbstraction; diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp index 51f0721..c42d372 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp @@ -18,7 +18,10 @@ #include "test-graphics-buffer.h" #include "test-graphics-command-buffer.h" +#include "test-graphics-framebuffer.h" #include "test-graphics-reflection.h" +#include "test-graphics-render-pass.h" +#include "test-graphics-render-target.h" #include "test-graphics-sampler.h" #include "test-graphics-shader.h" #include "test-graphics-texture.h" @@ -30,36 +33,6 @@ namespace Dali { -template -T* Uncast(const Graphics::CommandBuffer* object) -{ - return const_cast(static_cast(object)); -} - -template -T* Uncast(const Graphics::Texture* object) -{ - return const_cast(static_cast(object)); -} - -template -T* Uncast(const Graphics::Sampler* object) -{ - return const_cast(static_cast(object)); -} - -template -T* Uncast(const Graphics::Buffer* object) -{ - return const_cast(static_cast(object)); -} - -template -T* Uncast(const Graphics::Shader* object) -{ - return const_cast(static_cast(object)); -} - std::ostream& operator<<(std::ostream& o, const Graphics::BufferCreateInfo& bufferCreateInfo) { return o << "usage:" << std::hex << bufferCreateInfo.usage << ", size:" << std::dec << bufferCreateInfo.size; @@ -173,72 +146,37 @@ std::ostream& operator<<(std::ostream& o, const Graphics::SamplerCreateInfo& cre return o; } -class TestGraphicsMemory : public Graphics::Memory +std::ostream& operator<<(std::ostream& o, const Graphics::ColorAttachment& colorAttachment) { -public: - TestGraphicsMemory(TraceCallStack& callStack, TestGraphicsBuffer& buffer, uint32_t mappedOffset, uint32_t mappedSize) - : mCallStack(callStack), - mBuffer(buffer), - mMappedOffset(mappedOffset), - mMappedSize(mappedSize), - mLockedOffset(0u), - mLockedSize(0u) - { - } - - void* LockRegion(uint32_t offset, uint32_t size) override - { - std::ostringstream o; - o << offset << ", " << size; - mCallStack.PushCall("Memory::LockRegion", o.str()); - - if(offset > mMappedOffset + mMappedSize || - size + offset > mMappedOffset + mMappedSize) - { - fprintf(stderr, "TestGraphics.Memory::LockRegion() Out of bounds"); - mBuffer.memory.resize(mMappedOffset + offset + size); // Grow to prevent memcpy from crashing - } - mLockedOffset = offset; - mLockedSize = size; - return &mBuffer.memory[mMappedOffset + offset]; - } + o << "attachmentId:" << colorAttachment.attachmentId + << " layerId:" << colorAttachment.layerId + << " levelId:" << colorAttachment.levelId + << " texture:" << colorAttachment.texture; + return o; +} - void Unlock(bool flush) override - { - mCallStack.PushCall("Memory::Unlock", (flush ? "Flush" : "NoFlush")); - if(flush) - { - Flush(); - } - } +std::ostream& operator<<(std::ostream& o, const Graphics::DepthStencilAttachment& depthStencilAttachment) +{ + o << "depthTexture:" << depthStencilAttachment.depthTexture + << "depthLevel:" << depthStencilAttachment.depthLevel + << "stencilTexture:" << depthStencilAttachment.stencilTexture + << "stencilLevel:" << depthStencilAttachment.stencilLevel; + return o; +} - void Flush() override +std::ostream& operator<<(std::ostream& o, const Graphics::FramebufferCreateInfo& createInfo) +{ + o << "colorAttachments:"; + for(auto i = 0u; i < createInfo.colorAttachments.size(); ++i) { - mCallStack.PushCall("Memory::Flush", ""); - mBuffer.Bind(); - mBuffer.Upload(mMappedOffset + mLockedOffset, mLockedSize); - mBuffer.Unbind(); + o << "[" << i << "]=" << createInfo.colorAttachments[i] << " "; } - - TraceCallStack& mCallStack; - TestGraphicsBuffer& mBuffer; - uint32_t mMappedOffset; - uint32_t mMappedSize; - uint32_t mLockedOffset; - uint32_t mLockedSize; -}; - -TestGraphicsController::TestGraphicsController() -: mCallStack(true, "TestGraphicsController."), - mCommandBufferCallStack(true, "TestCommandBuffer.") -{ - mCallStack.Enable(true); - mCommandBufferCallStack.Enable(true); - auto& trace = mGl.GetTextureTrace(); - trace.Enable(true); - trace.EnableLogging(true); + o << "depthStencilAttachment:" << createInfo.depthStencilAttachment; + o << "size: " << createInfo.size; + return o; } + int GetNumComponents(Graphics::VertexInputFormat vertexFormat) { switch(vertexFormat) @@ -447,6 +385,75 @@ GLenum GetBlendOp(Graphics::BlendOp blendOp) return op; } + +class TestGraphicsMemory : public Graphics::Memory +{ +public: + TestGraphicsMemory(TraceCallStack& callStack, TestGraphicsBuffer& buffer, uint32_t mappedOffset, uint32_t mappedSize) + : mCallStack(callStack), + mBuffer(buffer), + mMappedOffset(mappedOffset), + mMappedSize(mappedSize), + mLockedOffset(0u), + mLockedSize(0u) + { + } + + void* LockRegion(uint32_t offset, uint32_t size) override + { + std::ostringstream o; + o << offset << ", " << size; + mCallStack.PushCall("Memory::LockRegion", o.str()); + + if(offset > mMappedOffset + mMappedSize || + size + offset > mMappedOffset + mMappedSize) + { + fprintf(stderr, "TestGraphics.Memory::LockRegion() Out of bounds"); + mBuffer.memory.resize(mMappedOffset + offset + size); // Grow to prevent memcpy from crashing + } + mLockedOffset = offset; + mLockedSize = size; + return &mBuffer.memory[mMappedOffset + offset]; + } + + void Unlock(bool flush) override + { + mCallStack.PushCall("Memory::Unlock", (flush ? "Flush" : "NoFlush")); + if(flush) + { + Flush(); + } + } + + void Flush() override + { + mCallStack.PushCall("Memory::Flush", ""); + mBuffer.Bind(); + mBuffer.Upload(mMappedOffset + mLockedOffset, mLockedSize); + mBuffer.Unbind(); + } + + TraceCallStack& mCallStack; + TestGraphicsBuffer& mBuffer; + uint32_t mMappedOffset; + uint32_t mMappedSize; + uint32_t mLockedOffset; + uint32_t mLockedSize; +}; + +TestGraphicsController::TestGraphicsController() +: mCallStack(true, "TestGraphicsController."), + mCommandBufferCallStack(true, "TestCommandBuffer."), + mFrameBufferCallStack(true, "TestFrameBuffer.") +{ + mCallStack.Enable(true); + mCommandBufferCallStack.Enable(true); + auto& trace = mGl.GetTextureTrace(); + trace.Enable(true); + trace.EnableLogging(true); +} + + void TestGraphicsController::SubmitCommandBuffers(const Graphics::SubmitInfo& submitInfo) { TraceCallStack::NamedParams namedParams; @@ -460,193 +467,308 @@ void TestGraphicsController::SubmitCommandBuffers(const Graphics::SubmitInfo& su for(auto& graphicsCommandBuffer : submitInfo.cmdBuffer) { auto commandBuffer = Uncast(graphicsCommandBuffer); + ProcessCommandBuffer(*commandBuffer); + } +} + +void TestGraphicsController::ProcessCommandBuffer(TestGraphicsCommandBuffer& commandBuffer) +{ + bool scissorEnabled = false; + TestGraphicsFramebuffer* currentFramebuffer{nullptr}; + TestGraphicsPipeline* currentPipeline{nullptr}; - auto value = commandBuffer->GetCommandsByType(0 | CommandType::BIND_TEXTURES); - if(!value.empty()) + for(auto& cmd : commandBuffer.GetCommands()) + { + // process command + switch(cmd.type) { - // must be fixed - for(auto& binding : value[0]->data.bindTextures.textureBindings) + case CommandType::FLUSH: + { + // Nothing to do here + break; + } + case CommandType::BIND_TEXTURES: { - if(binding.texture) + for(auto& binding : cmd.data.bindTextures.textureBindings) { - auto texture = Uncast(binding.texture); - - texture->Bind(binding.binding); - - if(binding.sampler) + if(binding.texture) { - auto sampler = Uncast(binding.sampler); - if(sampler) + auto texture = Uncast(binding.texture); + texture->Bind(binding.binding); + + if(binding.sampler) { - sampler->Apply(texture->GetTarget()); + auto sampler = Uncast(binding.sampler); + if(sampler) + { + sampler->Apply(texture->GetTarget()); + } } - } - texture->Prepare(); // Ensure native texture is ready + texture->Prepare(); // Ensure native texture is ready + } } + break; } - } - - // IndexBuffer binding, - auto bindIndexBufferCmds = commandBuffer->GetCommandsByType(0 | CommandType::BIND_INDEX_BUFFER); - if(!bindIndexBufferCmds.empty()) - { - auto& indexBufferBinding = bindIndexBufferCmds[0]->data.bindIndexBuffer; - if(indexBufferBinding.buffer) + case CommandType::BIND_VERTEX_BUFFERS: { - auto buffer = Uncast(indexBufferBinding.buffer); - buffer->Bind(); + for(auto& binding : cmd.data.bindVertexBuffers.vertexBufferBindings) + { + auto graphicsBuffer = binding.buffer; + auto vertexBuffer = Uncast(graphicsBuffer); + vertexBuffer->Bind(); + } + break; } - } - - // VertexBuffer binding, - auto bindVertexBufferCmds = commandBuffer->GetCommandsByType(0 | CommandType::BIND_VERTEX_BUFFERS); - if(!bindVertexBufferCmds.empty()) - { - for(auto& binding : bindVertexBufferCmds[0]->data.bindVertexBuffers.vertexBufferBindings) + case CommandType::BIND_INDEX_BUFFER: { - auto graphicsBuffer = binding.buffer; - auto vertexBuffer = Uncast(graphicsBuffer); - vertexBuffer->Bind(); + auto& indexBufferBinding = cmd.data.bindIndexBuffer; + if(indexBufferBinding.buffer) + { + auto buffer = Uncast(indexBufferBinding.buffer); + buffer->Bind(); + } + break; } - } - - bool scissorEnabled = false; - - auto scissorTestList = commandBuffer->GetCommandsByType(0 | CommandType::SET_SCISSOR_TEST); - if(!scissorTestList.empty()) - { - if(scissorTestList[0]->data.scissorTest.enable) + case CommandType::BIND_UNIFORM_BUFFER: { - mGl.Enable(GL_SCISSOR_TEST); - scissorEnabled = true; + auto& bindings = cmd.data.bindUniformBuffers; + auto buffer = bindings.standaloneUniformsBufferBinding; + + // based on reflection, issue gl calls + buffer.buffer->BindAsUniformBuffer(static_cast(currentPipeline->programState.program)); + break; } - else + case CommandType::BIND_SAMPLERS: { - mGl.Disable(GL_SCISSOR_TEST); + break; } - } - - auto scissorList = commandBuffer->GetCommandsByType(0 | CommandType::SET_SCISSOR); - if(!scissorList.empty() && scissorEnabled) - { - auto& rect = scissorList[0]->data.scissor.region; - mGl.Scissor(rect.x, rect.y, rect.width, rect.height); - } - - auto viewportList = commandBuffer->GetCommandsByType(0 | CommandType::SET_VIEWPORT); - if(!viewportList.empty()) - { - mGl.Viewport(viewportList[0]->data.viewport.region.x, viewportList[0]->data.viewport.region.y, viewportList[0]->data.viewport.region.width, viewportList[0]->data.viewport.region.height); - } - - // ignore viewport enable + case CommandType::BIND_PIPELINE: + { + currentPipeline = Uncast(cmd.data.bindPipeline.pipeline); - // Pipeline attribute setup - auto bindPipelineCmds = commandBuffer->GetCommandsByType(0 | CommandType::BIND_PIPELINE); - if(!bindPipelineCmds.empty()) - { - auto pipeline = bindPipelineCmds[0]->data.bindPipeline.pipeline; - auto& vi = pipeline->vertexInputState; - for(auto& attribute : vi.attributes) + // Bind framebuffer if different. @todo Move to RenderPass + auto framebuffer = currentPipeline->framebufferState.framebuffer; + if(framebuffer && framebuffer != currentFramebuffer) + { + auto graphicsFramebuffer = Uncast(framebuffer); + graphicsFramebuffer->Bind(); + } + else + { + if(currentFramebuffer) + currentFramebuffer->Bind(); + else + mGl.BindFramebuffer(GL_FRAMEBUFFER, 0); + } + BindPipeline(currentPipeline); + break; + } + case CommandType::DRAW: { - mGl.EnableVertexAttribArray(attribute.location); - uint32_t attributeOffset = attribute.offset; - GLsizei stride = vi.bufferBindings[attribute.binding].stride; - - mGl.VertexAttribPointer(attribute.location, - GetNumComponents(attribute.format), - GetGlType(attribute.format), - GL_FALSE, // Not normalized - stride, - reinterpret_cast(attributeOffset)); + mGl.DrawArrays(GetTopology(currentPipeline->inputAssemblyState.topology), + 0, + cmd.data.draw.draw.vertexCount); + break; } - - // Cull face setup - auto& rasterizationState = pipeline->rasterizationState; - if(rasterizationState.cullMode == Graphics::CullMode::NONE) + case CommandType::DRAW_INDEXED: { - mGl.Disable(GL_CULL_FACE); + mGl.DrawElements(GetTopology(currentPipeline->inputAssemblyState.topology), + static_cast(cmd.data.draw.drawIndexed.indexCount), + GL_UNSIGNED_SHORT, + reinterpret_cast(cmd.data.draw.drawIndexed.firstIndex)); + break; } - else + case CommandType::DRAW_INDEXED_INDIRECT: { - mGl.Enable(GL_CULL_FACE); - mGl.CullFace(GetCullFace(rasterizationState.cullMode)); + mGl.DrawElements(GetTopology(currentPipeline->inputAssemblyState.topology), + static_cast(cmd.data.draw.drawIndexed.indexCount), + GL_UNSIGNED_SHORT, + reinterpret_cast(cmd.data.draw.drawIndexed.firstIndex)); + break; } - - mGl.FrontFace(GetFrontFace(rasterizationState.frontFace)); - // We don't modify glPolygonMode in our context/abstraction from GL_FILL (the GL default), - // so it isn't present in the API (and won't have any tests!) - - // Blending setup - auto& colorBlendState = pipeline->colorBlendState; - if(colorBlendState.blendEnable) + case CommandType::SET_SCISSOR: { - mGl.Enable(GL_BLEND); - - mGl.BlendFuncSeparate(GetBlendFactor(colorBlendState.srcColorBlendFactor), - GetBlendFactor(colorBlendState.dstColorBlendFactor), - GetBlendFactor(colorBlendState.srcAlphaBlendFactor), - GetBlendFactor(colorBlendState.dstAlphaBlendFactor)); - if(colorBlendState.colorBlendOp != colorBlendState.alphaBlendOp) + if(scissorEnabled) { - mGl.BlendEquationSeparate(GetBlendOp(colorBlendState.colorBlendOp), GetBlendOp(colorBlendState.alphaBlendOp)); + auto& rect = cmd.data.scissor.region; + mGl.Scissor(rect.x, rect.y, rect.width, rect.height); + } + break; + } + case CommandType::SET_SCISSOR_TEST: + { + if(cmd.data.scissorTest.enable) + { + mGl.Enable(GL_SCISSOR_TEST); + scissorEnabled = true; } else { - mGl.BlendEquation(GetBlendOp(colorBlendState.colorBlendOp)); + mGl.Disable(GL_SCISSOR_TEST); + scissorEnabled = false; } - mGl.BlendColor(colorBlendState.blendConstants[0], - colorBlendState.blendConstants[1], - colorBlendState.blendConstants[2], - colorBlendState.blendConstants[3]); + break; } - else + case CommandType::SET_VIEWPORT_TEST: { - mGl.Disable(GL_BLEND); + break; } - - // draw call - auto topology = pipeline->inputAssemblyState.topology; - - // UniformBuffer binding (once we know pipeline) - auto bindUniformBuffersCmds = commandBuffer->GetCommandsByType(0 | CommandType::BIND_UNIFORM_BUFFER); - if(!bindUniformBuffersCmds.empty()) + case CommandType::SET_VIEWPORT: // @todo Consider correcting for orientation here? { - auto buffer = bindUniformBuffersCmds[0]->data.bindUniformBuffers.standaloneUniformsBufferBinding; - - // based on reflection, issue gl calls - buffer.buffer->BindAsUniformBuffer(static_cast(pipeline->programState.program)); + auto& rect = cmd.data.viewport.region; + mGl.Viewport(rect.x, rect.y, rect.width, rect.height); + break; } - - auto drawCmds = commandBuffer->GetCommandsByType(0 | - CommandType::DRAW | - CommandType::DRAW_INDEXED_INDIRECT | - CommandType::DRAW_INDEXED); - - if(!drawCmds.empty()) + case CommandType::EXECUTE_COMMAND_BUFFERS: + { + // Process secondary command buffers + for(auto& buf : cmd.data.executeCommandBuffers.buffers) + { + ProcessCommandBuffer(*static_cast(buf)); + } + break; + } + case CommandType::BEGIN_RENDER_PASS: { - if(drawCmds[0]->data.draw.type == DrawCallDescriptor::Type::DRAW_INDEXED) + auto renderTarget = Uncast(cmd.data.beginRenderPass.renderTarget); + + if(renderTarget) { - mGl.DrawElements(GetTopology(topology), - static_cast(drawCmds[0]->data.draw.drawIndexed.indexCount), - GL_UNSIGNED_SHORT, - reinterpret_cast(drawCmds[0]->data.draw.drawIndexed.firstIndex)); + auto fb = renderTarget->mCreateInfo.framebuffer; + if(fb) + { + if(currentFramebuffer != fb) + { + currentFramebuffer = Uncast(fb); + currentFramebuffer->Bind(); + } + } + else + { + mGl.BindFramebuffer(GL_FRAMEBUFFER, 0); + } } else { - mGl.DrawArrays(GetTopology(topology), 0, drawCmds[0]->data.draw.draw.vertexCount); + mGl.BindFramebuffer(GL_FRAMEBUFFER, 0); + } + + auto& clearValues = cmd.data.beginRenderPass.clearValues; + if(clearValues.size() > 0) + { + const auto renderPass = static_cast(cmd.data.beginRenderPass.renderPass); + if(renderPass) + { + const auto& color0 = renderPass->attachments[0]; + GLuint mask = 0; + if(color0.loadOp == Graphics::AttachmentLoadOp::CLEAR) + { + mask |= GL_COLOR_BUFFER_BIT; + + // Set clear color (todo: cache it!) + // Something goes wrong here if Alpha mask is GL_TRUE + mGl.ColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_FALSE); + mGl.ClearColor(clearValues[0].color.r, + clearValues[0].color.g, + clearValues[0].color.b, + clearValues[0].color.a); + } + + // check for depth stencil + if(renderPass->attachments.size() > 1) + { + const auto& depthStencil = renderPass->attachments.back(); + if(depthStencil.loadOp == Graphics::AttachmentLoadOp::CLEAR) + { + mask |= GL_DEPTH_BUFFER_BIT; + } + if(depthStencil.stencilLoadOp == Graphics::AttachmentLoadOp::CLEAR) + { + mask |= GL_STENCIL_BUFFER_BIT; + } + } + + if(mask != 0) + { + mGl.Clear(mask); + } + } + else + { + DALI_ASSERT_DEBUG(0 && "BeginRenderPass has no render pass"); + } } + break; } - // attribute clear - for(auto& attribute : vi.attributes) + case CommandType::END_RENDER_PASS: { - mGl.DisableVertexAttribArray(attribute.location); + break; } } } } +void TestGraphicsController::BindPipeline(TestGraphicsPipeline* pipeline) +{ + auto& vi = pipeline->vertexInputState; + for(auto& attribute : vi.attributes) + { + mGl.EnableVertexAttribArray(attribute.location); + uint32_t attributeOffset = attribute.offset; + GLsizei stride = vi.bufferBindings[attribute.binding].stride; + + mGl.VertexAttribPointer(attribute.location, + GetNumComponents(attribute.format), + GetGlType(attribute.format), + GL_FALSE, // Not normalized + stride, + reinterpret_cast(attributeOffset)); + } + + // Cull face setup + auto& rasterizationState = pipeline->rasterizationState; + if(rasterizationState.cullMode == Graphics::CullMode::NONE) + { + mGl.Disable(GL_CULL_FACE); + } + else + { + mGl.Enable(GL_CULL_FACE); + mGl.CullFace(GetCullFace(rasterizationState.cullMode)); + } + + mGl.FrontFace(GetFrontFace(rasterizationState.frontFace)); + + // Blending setup + auto& colorBlendState = pipeline->colorBlendState; + if(colorBlendState.blendEnable) + { + mGl.Enable(GL_BLEND); + + mGl.BlendFuncSeparate(GetBlendFactor(colorBlendState.srcColorBlendFactor), + GetBlendFactor(colorBlendState.dstColorBlendFactor), + GetBlendFactor(colorBlendState.srcAlphaBlendFactor), + GetBlendFactor(colorBlendState.dstAlphaBlendFactor)); + if(colorBlendState.colorBlendOp != colorBlendState.alphaBlendOp) + { + mGl.BlendEquationSeparate(GetBlendOp(colorBlendState.colorBlendOp), GetBlendOp(colorBlendState.alphaBlendOp)); + } + else + { + mGl.BlendEquation(GetBlendOp(colorBlendState.colorBlendOp)); + } + mGl.BlendColor(colorBlendState.blendConstants[0], + colorBlendState.blendConstants[1], + colorBlendState.blendConstants[2], + colorBlendState.blendConstants[3]); + } + else + { + mGl.Disable(GL_BLEND); + } +} + /** * @brief Presents render target * @param renderTarget render target to present @@ -770,7 +892,7 @@ Graphics::UniquePtr TestGraphicsController::CreateComma Graphics::UniquePtr TestGraphicsController::CreateRenderPass(const Graphics::RenderPassCreateInfo& renderPassCreateInfo, Graphics::UniquePtr&& oldRenderPass) { mCallStack.PushCall("CreateRenderPass", ""); - return nullptr; + return Graphics::MakeUnique(mGl, renderPassCreateInfo); } Graphics::UniquePtr TestGraphicsController::CreateTexture(const Graphics::TextureCreateInfo& textureCreateInfo, Graphics::UniquePtr&& oldTexture) @@ -782,10 +904,15 @@ Graphics::UniquePtr TestGraphicsController::CreateTexture(con return Graphics::MakeUnique(mGl, textureCreateInfo); } -Graphics::UniquePtr TestGraphicsController::CreateFramebuffer(const Graphics::FramebufferCreateInfo& framebufferCreateInfo, Graphics::UniquePtr&& oldFramebuffer) +Graphics::UniquePtr TestGraphicsController::CreateFramebuffer( + const Graphics::FramebufferCreateInfo& createInfo, + Graphics::UniquePtr&& oldFramebuffer) { - mCallStack.PushCall("CreateFramebuffer", ""); - return nullptr; + TraceCallStack::NamedParams namedParams; + namedParams["framebufferCreateInfo"] << createInfo; + mCallStack.PushCall("Controller::CreateFramebuffer", namedParams.str(), namedParams); + + return Graphics::MakeUnique(mFrameBufferCallStack, mGl, createInfo); } Graphics::UniquePtr TestGraphicsController::CreatePipeline(const Graphics::PipelineCreateInfo& pipelineCreateInfo, Graphics::UniquePtr&& oldPipeline) @@ -849,7 +976,7 @@ Graphics::UniquePtr TestGraphicsController::CreateSampler(con Graphics::UniquePtr TestGraphicsController::CreateRenderTarget(const Graphics::RenderTargetCreateInfo& renderTargetCreateInfo, Graphics::UniquePtr&& oldRenderTarget) { mCallStack.PushCall("CreateRenderTarget", ""); - return nullptr; + return Graphics::MakeUnique(mGl, renderTargetCreateInfo); } Graphics::UniquePtr TestGraphicsController::MapBufferRange(const Graphics::MapBufferInfo& mapInfo) diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.h index 803678e..f777053 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.h +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.h @@ -21,6 +21,7 @@ #include "test-gl-abstraction.h" #include "test-gl-context-helper-abstraction.h" #include "test-gl-sync-abstraction.h" +#include "test-graphics-command-buffer.h" #include "test-graphics-program.h" #include "test-graphics-reflection.h" @@ -36,6 +37,54 @@ std::ostream& operator<<(std::ostream& o, Graphics::SamplerFilter filterMode); std::ostream& operator<<(std::ostream& o, Graphics::SamplerMipmapMode mipmapMode); std::ostream& operator<<(std::ostream& o, const Graphics::SamplerCreateInfo& createInfo); +template +T* Uncast(const Graphics::CommandBuffer* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::Texture* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::Sampler* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::Buffer* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::Shader* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::Framebuffer* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::Pipeline* object) +{ + return const_cast(static_cast(object)); +} + +template +T* Uncast(const Graphics::RenderTarget* object) +{ + return const_cast(static_cast(object)); +} + class TestGraphicsController : public Dali::Graphics::Controller { public: @@ -331,9 +380,14 @@ public: // Test Functions */ bool GetProgramParameter(Graphics::Program& program, uint32_t parameterId, void* outData) override; + void ProcessCommandBuffer(TestGraphicsCommandBuffer& commandBuffer); + + void BindPipeline(TestGraphicsPipeline* pipeline); + public: mutable TraceCallStack mCallStack; mutable TraceCallStack mCommandBufferCallStack; + mutable TraceCallStack mFrameBufferCallStack; mutable std::vector mSubmitStack; TestGlAbstraction mGl; diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp new file mode 100644 index 0000000..74f1e29 --- /dev/null +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp @@ -0,0 +1,165 @@ +/* + * Copyright (c) 2021 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "test-graphics-framebuffer.h" +#include +#include "test-graphics-controller.h" +#include "test-graphics-texture.h" + +namespace +{ +const GLenum COLOR_ATTACHMENTS[] = + { + GL_COLOR_ATTACHMENT0, + GL_COLOR_ATTACHMENT1, + GL_COLOR_ATTACHMENT2, + GL_COLOR_ATTACHMENT3, + GL_COLOR_ATTACHMENT4, + GL_COLOR_ATTACHMENT5, + GL_COLOR_ATTACHMENT6, + GL_COLOR_ATTACHMENT7, +}; + +struct DEPTH_STENCIL_ATTACHMENT_TYPE +{ + constexpr explicit DEPTH_STENCIL_ATTACHMENT_TYPE(Graphics::Format textureFormat) + { + switch(textureFormat) + { + case Graphics::Format::D16_UNORM: + case Graphics::Format::D32_SFLOAT: + case Graphics::Format::X8_D24_UNORM_PACK32: + { + attachment = GL_DEPTH_ATTACHMENT; + break; + } + + case Graphics::Format::S8_UINT: + { + attachment = GL_STENCIL_ATTACHMENT; + break; + } + + case Graphics::Format::D16_UNORM_S8_UINT: + case Graphics::Format::D24_UNORM_S8_UINT: + case Graphics::Format::D32_SFLOAT_S8_UINT: + { + attachment = GL_DEPTH_STENCIL_ATTACHMENT; + break; + } + default: + { + attachment = GL_NONE; + break; + } + } + } + GLenum attachment{GL_NONE}; +}; + +} // namespace +//namespace + +namespace Dali +{ +TestGraphicsFramebuffer::TestGraphicsFramebuffer( + TraceCallStack& callStack, + TestGlAbstraction& glAbstraction, + const Graphics::FramebufferCreateInfo& createInfo) +: mGl(glAbstraction), + mCallStack(callStack) +{ + mCreateInfo.colorAttachments = std::move(createInfo.colorAttachments); + mCreateInfo.depthStencilAttachment = createInfo.depthStencilAttachment; + mCreateInfo.size = createInfo.size; +} + +TestGraphicsFramebuffer::~TestGraphicsFramebuffer() +{ + if(mId) + { + mGl.DeleteFramebuffers(1, &mId); + } +} + +void TestGraphicsFramebuffer::Initialize() +{ + mCallStack.PushCall("Initialize", ""); + + mGl.GenFramebuffers(1, &mId); + mGl.BindFramebuffer(GL_FRAMEBUFFER, mId); + + for(Graphics::ColorAttachment& attachment : mCreateInfo.colorAttachments) + { + AttachTexture(attachment.texture, COLOR_ATTACHMENTS[attachment.attachmentId], attachment.layerId, attachment.levelId); + } + mGl.DrawBuffers(mCreateInfo.colorAttachments.size(), COLOR_ATTACHMENTS); + + if(mCreateInfo.depthStencilAttachment.depthTexture) + { + // Create a depth or depth/stencil render target. + auto depthTexture = Uncast(mCreateInfo.depthStencilAttachment.depthTexture); + auto attachmentId = DEPTH_STENCIL_ATTACHMENT_TYPE(depthTexture->GetFormat()).attachment; + + mGl.GenRenderbuffers(1, &mDepthBuffer); + mGl.BindRenderbuffer(GL_RENDERBUFFER, mDepthBuffer); + mGl.RenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT16, mCreateInfo.size.width, mCreateInfo.size.height); + mGl.FramebufferRenderbuffer(GL_FRAMEBUFFER, attachmentId, GL_RENDERBUFFER, mDepthBuffer); + + AttachTexture(depthTexture, attachmentId, 0, mCreateInfo.depthStencilAttachment.depthLevel); + } + + if(mCreateInfo.depthStencilAttachment.stencilTexture) + { + auto stencilTexture = Uncast(mCreateInfo.depthStencilAttachment.stencilTexture); + auto attachmentId = DEPTH_STENCIL_ATTACHMENT_TYPE(stencilTexture->GetFormat()).attachment; + + // Create a stencil render target. + mGl.GenRenderbuffers(1, &mStencilBuffer); + mGl.BindRenderbuffer(GL_RENDERBUFFER, mStencilBuffer); + mGl.RenderbufferStorage(GL_RENDERBUFFER, GL_STENCIL_INDEX8, mCreateInfo.size.width, mCreateInfo.size.height); + mGl.FramebufferRenderbuffer(GL_FRAMEBUFFER, attachmentId, GL_RENDERBUFFER, mStencilBuffer); + + AttachTexture(stencilTexture, attachmentId, 0, mCreateInfo.depthStencilAttachment.stencilLevel); + } + mGl.BindFramebuffer(GL_FRAMEBUFFER, 0); +} + +void TestGraphicsFramebuffer::AttachTexture(Graphics::Texture* texture, uint32_t attachmentId, uint32_t layerId, uint32_t levelId) +{ + auto graphicsTexture = Uncast(texture); + if(graphicsTexture->GetType() == Graphics::TextureType::TEXTURE_2D) + { + mGl.FramebufferTexture2D(GL_FRAMEBUFFER, attachmentId, graphicsTexture->GetTarget(), graphicsTexture->mId, levelId); + } + else + { + mGl.FramebufferTexture2D(GL_FRAMEBUFFER, attachmentId, GL_TEXTURE_CUBE_MAP_POSITIVE_X + layerId, graphicsTexture->mId, levelId); + } +} + +void TestGraphicsFramebuffer::Bind() +{ + mCallStack.PushCall("Bind", ""); + + if(!mId) + { + Initialize(); + } + mGl.BindFramebuffer(GL_FRAMEBUFFER, mId); +} + +} // namespace Dali diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.h new file mode 100644 index 0000000..664c28b --- /dev/null +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.h @@ -0,0 +1,49 @@ +#ifndef TEST_GRAPHICS_FRAMEBUFFER_H +#define TEST_GRAPHICS_FRAMEBUFFER_H + +/* + * Copyright (c) 2021 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include +#include +#include "test-gl-abstraction.h" +#include "test-trace-call-stack.h" + +namespace Dali +{ +class TestGraphicsFramebuffer : public Graphics::Framebuffer +{ +public: + TestGraphicsFramebuffer(TraceCallStack& callStack, TestGlAbstraction& glAbstraction, const Graphics::FramebufferCreateInfo& createInfo); + ~TestGraphicsFramebuffer(); + + void Initialize(); + void AttachTexture(Graphics::Texture* texture, uint32_t attachmentId, uint32_t layerId, uint32_t levelId); + void Bind(); + + TestGlAbstraction& mGl; + Graphics::FramebufferCreateInfo mCreateInfo; + TraceCallStack& mCallStack; + + GLuint mId{0}; + GLuint mDepthBuffer; + GLuint mStencilBuffer; +}; + +} // namespace Dali + +#endif //TEST_GRAPHICS_FRAMEBUFFER_H diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp index d303d56..9e80f8f 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp @@ -21,7 +21,7 @@ namespace Dali TestGraphicsPipeline::TestGraphicsPipeline(TestGlAbstraction& gl, const Graphics::PipelineCreateInfo& createInfo) : mGl(gl) { - // Need to deep copy, otherwise pointed at memory will go out of scope. Probably should do something about this. + // Need to deep copy, otherwise pointed at memory will go out of scope. @todo Probably should do something about this. if(createInfo.colorBlendState) colorBlendState = *createInfo.colorBlendState; @@ -32,9 +32,6 @@ TestGraphicsPipeline::TestGraphicsPipeline(TestGlAbstraction& gl, const Graphics if(createInfo.viewportState) viewportState = *createInfo.viewportState; - if(createInfo.framebufferState) - framebufferState = *createInfo.framebufferState; - if(createInfo.depthStencilState) depthStencilState = *createInfo.depthStencilState; diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-pass.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-pass.h new file mode 100644 index 0000000..b52dd2d --- /dev/null +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-pass.h @@ -0,0 +1,41 @@ +#ifndef DALI_TEST_GRAPHICS_RENDER_PASS_H +#define DALI_TEST_GRAPHICS_RENDER_PASS_H + +/* + * Copyright (c) 2021 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include + +namespace Dali +{ +class TestGraphicsRenderPass : public Graphics::RenderPass +{ +public: + TestGraphicsRenderPass(TestGlAbstraction& gl, Graphics::RenderPassCreateInfo createInfo) + : mGl(gl) + { + attachments = *createInfo.attachments; // Deep copy the vector's contents... @todo FIXME! + } + ~TestGraphicsRenderPass() = default; + + TestGlAbstraction& mGl; + std::vector attachments; +}; + +} // namespace Dali + +#endif //DALI_TEST_GRAPHICS_RENDER_PASS_H diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-target.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-target.h new file mode 100644 index 0000000..1ad7a5a --- /dev/null +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-target.h @@ -0,0 +1,44 @@ +#ifndef DALI_TEST_GRAPHICS_RENDER_TARGET_H +#define DALI_TEST_GRAPHICS_RENDER_TARGET_H + +/* + * Copyright (c) 2021 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include + +namespace Dali +{ +class TestGraphicsRenderTarget : public Graphics::RenderTarget +{ +public: + TestGraphicsRenderTarget(TestGlAbstraction& gl, Graphics::RenderTargetCreateInfo createInfo) + : mGl(gl) + { + mCreateInfo.surface = createInfo.surface; + mCreateInfo.framebuffer = createInfo.framebuffer; + mCreateInfo.extent = createInfo.extent; + mCreateInfo.preTransform = createInfo.preTransform; + } + ~TestGraphicsRenderTarget() = default; + + TestGlAbstraction& mGl; + Graphics::RenderTargetCreateInfo mCreateInfo; +}; + +} // namespace Dali + +#endif //DALI_TEST_GRAPHICS_RENDER_TARGET_H diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.h index 3eb54d3..58f7738 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.h +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.h @@ -49,6 +49,22 @@ public: GLuint GetTarget(); /** + * Get the texture type + */ + Graphics::TextureType GetType() + { + return mCreateInfo.textureType; + } + + /** + * Get the texture format + */ + Graphics::Format GetFormat() + { + return mCreateInfo.format; + } + + /** * Bind this texture, ensure Native image is initialized if necessary. */ void Bind(uint32_t textureUnit); diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-scene-holder-impl.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-scene-holder-impl.h index 86b3bd9..0cfdcc0 100644 --- a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-scene-holder-impl.h +++ b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-scene-holder-impl.h @@ -2,7 +2,7 @@ #define DALI_TOOLKIT_SCENE_HOLDER_IMPL_H /* - * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * Copyright (c) 2021 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -51,7 +51,11 @@ public: bool PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) override { return false; }; - void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) override {}; + void PostRender() + { + } + + //void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) override {}; void StopRender() override {}; -- 2.7.4