Merge "Merge branch 'devel/master' into devel/graphics" into devel/master
authorDavid Steele <david.steele@samsung.com>
Wed, 26 May 2021 12:27:08 +0000 (12:27 +0000)
committerGerrit Code Review <gerrit@review>
Wed, 26 May 2021 12:27:08 +0000 (12:27 +0000)
36 files changed:
automated-tests/resources/papermill_E_diffuse-64.ktx [new file with mode: 0644]
automated-tests/src/dali-scene-loader-internal/CMakeLists.txt
automated-tests/src/dali-scene-loader/CMakeLists.txt
automated-tests/src/dali-scene-loader/utc-Dali-KtxLoader.cpp
automated-tests/src/dali-shader-generator/CMakeLists.txt
automated-tests/src/dali-toolkit-internal/CMakeLists.txt
automated-tests/src/dali-toolkit-styling/CMakeLists.txt
automated-tests/src/dali-toolkit-third-party/CMakeLists.txt
automated-tests/src/dali-toolkit/CMakeLists.txt
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-application.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-application.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-buffer.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-buffer.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-command-buffer.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-controller.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.cpp [new file with mode: 0644]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-framebuffer.h [new file with mode: 0644]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-pipeline.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-pass.h [new file with mode: 0644]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-render-target.h [new file with mode: 0644]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-impl.cpp [moved from automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-sync-abstraction.cpp with 66% similarity]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-impl.h [moved from automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-gl-sync-abstraction.h with 64% similarity]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.cpp [new file with mode: 0644]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.h [new file with mode: 0644]
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-texture.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-scene-holder-impl.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-test-application.cpp
dali-scene-loader/public-api/ktx-loader.cpp
dali-toolkit/devel-api/utility/npatch-utilities.cpp

diff --git a/automated-tests/resources/papermill_E_diffuse-64.ktx b/automated-tests/resources/papermill_E_diffuse-64.ktx
new file mode 100644 (file)
index 0000000..c000b61
Binary files /dev/null and b/automated-tests/resources/papermill_E_diffuse-64.ktx differ
index 16f96f0..0270d3d 100755 (executable)
@@ -42,10 +42,12 @@ SET(TEST_HARNESS_SOURCES
   ${TEST_HARNESS_DIR}/test-harness.cpp
   ${TEST_HARNESS_DIR}/test-gesture-generator.cpp
   ${TEST_HARNESS_DIR}/test-gl-abstraction.cpp
-  ${TEST_HARNESS_DIR}/test-gl-sync-abstraction.cpp
+  ${TEST_HARNESS_DIR}/test-graphics-sync-impl.cpp
+  ${TEST_HARNESS_DIR}/test-graphics-sync-object.cpp
   ${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
index 693db47..60c1b22 100755 (executable)
@@ -57,9 +57,11 @@ SET(TEST_HARNESS_SOURCES
   ${TEST_HARNESS_DIR}/test-harness.cpp
   ${TEST_HARNESS_DIR}/test-gesture-generator.cpp
   ${TEST_HARNESS_DIR}/test-gl-abstraction.cpp
-  ${TEST_HARNESS_DIR}/test-gl-sync-abstraction.cpp
+  ${TEST_HARNESS_DIR}/test-graphics-sync-impl.cpp
+  ${TEST_HARNESS_DIR}/test-graphics-sync-object.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
index 15d6b58..783745d 100644 (file)
@@ -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.
@@ -146,3 +146,20 @@ int UtcDaliKtxLoaderCubeDataCreateTexture2(void)
 
   END_TEST;
 }
+
+int UtcDaliKtxLoaderCubeDataCreateTexture3(void)
+{
+  CubeData cubeData;
+  auto path = TEST_RESOURCE_DIR "/papermill_E_diffuse-64.ktx";
+  DALI_TEST_CHECK(LoadCubeMapData(path, cubeData));
+
+  TestApplication app;
+  auto texture = cubeData.CreateTexture();
+
+  DALI_TEST_CHECK(texture);
+  DALI_TEST_EQUAL(64u, texture.GetWidth());
+  DALI_TEST_EQUAL(64u, texture.GetHeight());
+
+  END_TEST;
+
+}
index 9a30ca7..517b7d3 100644 (file)
@@ -44,10 +44,12 @@ SET(TEST_HARNESS_SOURCES
   ${TEST_HARNESS_DIR}/test-harness.cpp
   ${TEST_HARNESS_DIR}/test-gesture-generator.cpp
   ${TEST_HARNESS_DIR}/test-gl-abstraction.cpp
-  ${TEST_HARNESS_DIR}/test-gl-sync-abstraction.cpp
+  ${TEST_HARNESS_DIR}/test-graphics-sync-impl.cpp
+  ${TEST_HARNESS_DIR}/test-graphics-sync-object.cpp
   ${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-program.cpp
@@ -129,4 +131,3 @@ ADD_CUSTOM_TARGET(
   ALL
   COMMAND ${SHADER_GENERATOR} ${SHADER_FOLDER} ${GENERATED_FOLDER} | grep "SHADER_SHADER_DEFINE_DEF" | grep "shader-define-def.h" > /dev/null 2>&1 && echo "test_def_correct Succeeded"
   VERBATIM)
-
index f20e494..0a65397 100755 (executable)
@@ -81,10 +81,12 @@ SET(TEST_HARNESS_SOURCES
    ../dali-toolkit/dali-toolkit-test-utils/test-button.cpp
    ../dali-toolkit/dali-toolkit-test-utils/test-harness.cpp
    ../dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp
-   ../dali-toolkit/dali-toolkit-test-utils/test-gl-sync-abstraction.cpp
+   ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-impl.cpp
+   ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.cpp
    ../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
index cc1488e..4c211d1 100644 (file)
@@ -45,10 +45,12 @@ SET(TEST_HARNESS_SOURCES
    ../dali-toolkit/dali-toolkit-test-utils/test-application.cpp
    ../dali-toolkit/dali-toolkit-test-utils/test-platform-abstraction.cpp
    ../dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp
-   ../dali-toolkit/dali-toolkit-test-utils/test-gl-sync-abstraction.cpp
+   ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-impl.cpp
+   ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.cpp
    ../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
index 820a4a5..e30acba 100644 (file)
@@ -31,10 +31,12 @@ SET(TEST_HARNESS_SOURCES
    ../dali-toolkit/dali-toolkit-test-utils/test-button.cpp
    ../dali-toolkit/dali-toolkit-test-utils/test-harness.cpp
    ../dali-toolkit/dali-toolkit-test-utils/test-gl-abstraction.cpp
-   ../dali-toolkit/dali-toolkit-test-utils/test-gl-sync-abstraction.cpp
+   ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-impl.cpp
+   ../dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.cpp
    ../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
index c3ab255..2983fd7 100755 (executable)
@@ -112,10 +112,12 @@ SET(TEST_HARNESS_SOURCES
   dali-toolkit-test-utils/test-harness.cpp
   dali-toolkit-test-utils/test-gesture-generator.cpp
   dali-toolkit-test-utils/test-gl-abstraction.cpp
-  dali-toolkit-test-utils/test-gl-sync-abstraction.cpp
+  dali-toolkit-test-utils/test-graphics-sync-impl.cpp
+  dali-toolkit-test-utils/test-graphics-sync-object.cpp
   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
index 2db4dbc..bf62bb8 100644 (file)
@@ -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,44 @@ Actor CreateRenderableActor(Texture texture, const std::string& vertexShader, co
   return actor;
 }
 
+Actor CreateRenderableActor2(TextureSet textures, const std::string& vertexShader, const std::string& fragmentShader)
+{
+  // Create the geometry
+  Geometry geometry = CreateQuadGeometry();
+
+  // Create Shader
+  Shader shader = Shader::New(vertexShader, fragmentShader);
+
+  // Create renderer from geometry and material
+  Renderer renderer = Renderer::New(geometry, shader);
+
+  // Create actor and set renderer
+  Actor actor = Actor::New();
+  actor.AddRenderer(renderer);
+
+  // If we a texture, then create a texture-set and add to renderer
+  if(textures)
+  {
+    renderer.SetTextures(textures);
+
+    auto texture = textures.GetTexture(0);
+
+    // Set actor to the size of the texture if set
+    actor.SetProperty(Actor::Property::SIZE, Vector2(texture.GetWidth(), texture.GetHeight()));
+  }
+
+  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<uint8_t*>(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
index be085bf..0dbe07e 100644 (file)
@@ -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,8 @@
  */
 
 // EXTERNAL INCLUDES
+#include <dali/public-api/rendering/texture-set.h>
+#include <dali/public-api/rendering/texture.h>
 #include <string>
 
 namespace Dali
@@ -49,6 +51,17 @@ Actor CreateRenderableActor(Texture texture);
  */
 Actor CreateRenderableActor(Texture texture, const std::string& vertexShader, const std::string& fragmentShader);
 
+/**
+ * @brief Creates a renderable-actor with a texture and custom shaders.
+ * @param[in] textures TextureSet to set.
+ * @param[in] vertexShader The vertex-shader.
+ * @param[in] fragmentShader The fragment-shader.
+ * @return An actor with a renderer.
+ */
+Actor CreateRenderableActor2(TextureSet textures, 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
index a2a1848..5e69c95 100644 (file)
@@ -76,6 +76,12 @@ void TestApplication::CreateScene()
 {
   mScene = Dali::Integration::Scene::New(Size(static_cast<float>(mSurfaceWidth), static_cast<float>(mSurfaceHeight)));
   mScene.SetDpi(Vector2(static_cast<float>(mDpi.x), static_cast<float>(mDpi.y)));
+
+  // Create render target for the scene
+  Graphics::RenderTargetCreateInfo rtInfo{};
+  rtInfo.SetExtent({mSurfaceWidth, mSurfaceHeight});
+  mRenderTarget = mGraphicsController.CreateRenderTarget(rtInfo, nullptr);
+  mScene.SetSurfaceRenderTarget(mRenderTarget.get());
 }
 
 void TestApplication::InitializeCore()
@@ -149,14 +155,14 @@ TestGlAbstraction& TestApplication::GetGlAbstraction()
   return static_cast<TestGlAbstraction&>(mGraphicsController.GetGlAbstraction());
 }
 
-TestGlSyncAbstraction& TestApplication::GetGlSyncAbstraction()
+TestGlContextHelperAbstraction& TestApplication::GetGlContextHelperAbstraction()
 {
-  return static_cast<TestGlSyncAbstraction&>(mGraphicsController.GetGlSyncAbstraction());
+  return static_cast<TestGlContextHelperAbstraction&>(mGraphicsController.GetGlContextHelperAbstraction());
 }
 
-TestGlContextHelperAbstraction& TestApplication::GetGlContextHelperAbstraction()
+TestGraphicsSyncImplementation& TestApplication::GetGraphicsSyncImpl()
 {
-  return static_cast<TestGlContextHelperAbstraction&>(mGraphicsController.GetGlContextHelperAbstraction());
+  return static_cast<TestGraphicsSyncImplementation&>(mGraphicsController.GetGraphicsSyncImpl());
 }
 
 void TestApplication::ProcessEvent(const Integration::Event& event)
index e7d8c76..4f32cd8 100644 (file)
@@ -65,8 +65,8 @@ public:
   TestGraphicsController&  GetGraphicsController();
 
   TestGlAbstraction&              GetGlAbstraction();
-  TestGlSyncAbstraction&          GetGlSyncAbstraction();
   TestGlContextHelperAbstraction& GetGlContextHelperAbstraction();
+  TestGraphicsSyncImplementation& GetGraphicsSyncImpl();
 
   void        ProcessEvent(const Integration::Event& event);
   void        SendNotification();
@@ -108,6 +108,8 @@ protected:
   uint32_t mSurfaceHeight;
   uint32_t mFrame;
 
+  Graphics::UniquePtr<Graphics::RenderTarget> mRenderTarget;
+
   struct
   {
     uint32_t x;
index f2086d6..b85cf4d 100644 (file)
 #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();
 }
@@ -46,7 +49,6 @@ void TestGlAbstraction::Initialize()
   mCurrentProgram                  = 0;
   mCompileStatus                   = GL_TRUE;
   mLinkStatus                      = GL_TRUE;
-  mNumberOfActiveUniforms          = 0;
   mGetErrorResult                  = 0;
   mGetStringResult                 = NULL;
   mIsBufferResult                  = 0;
@@ -112,6 +114,31 @@ void TestGlAbstraction::Initialize()
   {
     mVertexAttribArrayState[i] = false;
   }
+
+  mActiveUniforms = std::vector<ActiveUniform>{
+    {"uRendererColor", GL_FLOAT, 1},
+    {"uCustom", GL_FLOAT_VEC3, 1},
+    {"uCustom3", GL_FLOAT_VEC3, 1},
+    {"uFadeColor", GL_FLOAT_VEC4, 1},
+    {"uUniform1", GL_FLOAT_VEC4, 1},
+    {"uUniform2", GL_FLOAT_VEC4, 1},
+    {"uUniform3", GL_FLOAT_VEC4, 1},
+    {"uFadeProgress", GL_FLOAT, 1},
+    {"uANormalMatrix", GL_FLOAT_MAT3, 1},
+    {"sEffect", GL_SAMPLER_2D, 1},
+    {"sTexture", GL_SAMPLER_2D, 1},
+    {"sTextureRect", GL_SAMPLER_2D, 1},
+    {"sGloss", GL_SAMPLER_2D, 1},
+    {"uColor", GL_FLOAT_VEC4, 1},
+    {"uModelMatrix", GL_FLOAT_MAT4, 1},
+    {"uModelView", GL_FLOAT_MAT4, 1},
+    {"uMvpMatrix", GL_FLOAT_MAT4, 1},
+    {"uNormalMatrix", GL_FLOAT_MAT4, 1},
+    {"uProjection", GL_FLOAT_MAT4, 1},
+    {"uSize", GL_FLOAT_VEC3, 1},
+    {"uViewMatrix", GL_FLOAT_MAT4, 1},
+    {"uLightCameraProjectionMatrix", GL_FLOAT_MAT4, 1},
+    {"uLightCameraViewMatrix", GL_FLOAT_MAT4, 1}};
 }
 
 void TestGlAbstraction::PreRender()
index 9357803..aec9f5d 100644 (file)
@@ -49,6 +49,13 @@ struct UniformData
   }
 };
 
+struct ActiveUniform
+{
+  std::string name;
+  GLenum      type;
+  GLint       size;
+};
+
 class DALI_CORE_API TestGlAbstraction : public Dali::Integration::GlAbstraction
 {
 public:
@@ -621,6 +628,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
@@ -749,27 +761,18 @@ public:
   {
   }
 
+  inline void SetActiveUniforms(const std::vector<ActiveUniform>& uniforms)
+  {
+    mActiveUniforms = uniforms;
+  }
+
   inline void GetActiveUniform(GLuint program, GLuint index, GLsizei bufsize, GLsizei* length, GLint* size, GLenum* type, char* name) override
   {
-    switch(index)
+    if(index < mActiveUniforms.size())
     {
-      case 0:
-        *length = snprintf(name, bufsize, "sTexture");
-        *type   = GL_SAMPLER_2D;
-        *size   = 1;
-        break;
-      case 1:
-        *length = snprintf(name, bufsize, "sEffect");
-        *type   = GL_SAMPLER_2D;
-        *size   = 1;
-        break;
-      case 2:
-        *length = snprintf(name, bufsize, "sGloss");
-        *type   = GL_SAMPLER_2D;
-        *size   = 1;
-        break;
-      default:
-        break;
+      *length = snprintf(name, bufsize, "%s", mActiveUniforms[index].name.c_str());
+      *type   = mActiveUniforms[index].type;
+      *size   = mActiveUniforms[index].size;
     }
   }
 
@@ -837,7 +840,7 @@ public:
         *params = mProgramBinaryLength;
         break;
       case GL_ACTIVE_UNIFORMS:
-        *params = mNumberOfActiveUniforms;
+        *params = mActiveUniforms.size();
         break;
       case GL_ACTIVE_UNIFORM_MAX_LENGTH:
         *params = 100;
@@ -981,31 +984,10 @@ public:
     namedParams["program"] << program;
     mShaderTrace.PushCall("LinkProgram", out.str(), namedParams);
 
-    mNumberOfActiveUniforms = 3;
-
-    GetUniformLocation(program, "uRendererColor");
-    GetUniformLocation(program, "uCustom");
-    GetUniformLocation(program, "uCustom3");
-    GetUniformLocation(program, "uFadeColor");
-    GetUniformLocation(program, "uUniform1");
-    GetUniformLocation(program, "uUniform2");
-    GetUniformLocation(program, "uUniform3");
-    GetUniformLocation(program, "uFadeProgress");
-    GetUniformLocation(program, "uANormalMatrix");
-    GetUniformLocation(program, "sEffect");
-    GetUniformLocation(program, "sTexture");
-    GetUniformLocation(program, "sTextureRect");
-    GetUniformLocation(program, "sGloss");
-    GetUniformLocation(program, "uColor");
-    GetUniformLocation(program, "uModelMatrix");
-    GetUniformLocation(program, "uModelView");
-    GetUniformLocation(program, "uMvpMatrix");
-    GetUniformLocation(program, "uNormalMatrix");
-    GetUniformLocation(program, "uProjection");
-    GetUniformLocation(program, "uSize");
-    GetUniformLocation(program, "uViewMatrix");
-    GetUniformLocation(program, "uLightCameraProjectionMatrix");
-    GetUniformLocation(program, "uLightCameraViewMatrix");
+    for(const auto& uniform : mActiveUniforms)
+    {
+      GetUniformLocation(program, uniform.name.c_str());
+    }
 
     for(const auto& uniform : mCustomUniformData)
     {
@@ -2465,14 +2447,13 @@ public: // TEST FUNCTIONS
     mBufferSubDataCalls.clear();
   }
 
-private:
+public:
   GLuint                                mCurrentProgram;
   GLuint                                mCompileStatus;
   BufferDataCalls                       mBufferDataCalls;
   BufferSubDataCalls                    mBufferSubDataCalls;
   GLvoid*                               mMappedBuffer{nullptr};
   GLuint                                mLinkStatus;
-  GLint                                 mNumberOfActiveUniforms;
   GLenum                                mGetErrorResult;
   GLubyte*                              mGetStringResult;
   GLboolean                             mIsBufferResult;
@@ -2547,8 +2528,8 @@ private:
   typedef std::map<std::string, GLint>   UniformIDMap;
   typedef std::map<GLuint, UniformIDMap> ProgramUniformMap;
   ProgramUniformMap                      mUniforms;
-
-  std::vector<UniformData> mCustomUniformData{};
+  std::vector<ActiveUniform>             mActiveUniforms;
+  std::vector<UniformData>               mCustomUniformData{};
 
   template<typename T>
   struct ProgramUniformValue : public std::map<GLuint, std::map<GLint, T> >
index d8a1b1a..21eecf4 100644 (file)
@@ -80,14 +80,15 @@ GLenum TestGraphicsBuffer::GetTarget()
   return target;
 }
 
-void TestGraphicsBuffer::BindAsUniformBuffer(const TestGraphicsProgram* program) const
+void TestGraphicsBuffer::BindAsUniformBuffer(const TestGraphicsProgram* program, const Dali::UniformBufferBindingDescriptor& uboBinding) const
 {
   auto* reflection = static_cast<const TestGraphicsReflection*>(&program->GetReflection());
 
   Graphics::UniformBlockInfo uboInfo{};
   reflection->GetUniformBlock(0, uboInfo);
 
-  auto* data = memory.data();
+  auto  offset = uboBinding.offset;
+  auto* data   = memory.data() + offset;
 
   for(const auto& member : uboInfo.members)
   {
index 87c9f87..1dc2715 100644 (file)
@@ -26,6 +26,7 @@
 namespace Dali
 {
 class TestGraphicsProgram;
+class UniformBufferBindingDescriptor;
 class TestGraphicsBuffer : public Graphics::Buffer
 {
 public:
@@ -40,7 +41,7 @@ public:
     return true;
   }
 
-  void BindAsUniformBuffer(const TestGraphicsProgram* program) const;
+  void BindAsUniformBuffer(const TestGraphicsProgram* program, const Dali::UniformBufferBindingDescriptor& uboBinding) const;
 
   TraceCallStack&            mCallStack;
   TestGlAbstraction&         mGl;
index ed63416..9f86b99 100644 (file)
 
 namespace Dali
 {
+std::ostream& operator<<(std::ostream& os, Graphics::StencilOp op)
+{
+  switch(op)
+  {
+    case Graphics::StencilOp::KEEP:
+      os << "KEEP";
+      return os;
+    case Graphics::StencilOp::ZERO:
+      os << "ZERO";
+      return os;
+    case Graphics::StencilOp::REPLACE:
+      os << "REPLACE";
+      return os;
+    case Graphics::StencilOp::INCREMENT_AND_CLAMP:
+      os << "INCREMENT_AND_CLAMP";
+      return os;
+    case Graphics::StencilOp::DECREMENT_AND_CLAMP:
+      os << "DECREMENT_AND_CLAMP";
+      return os;
+    case Graphics::StencilOp::INVERT:
+      os << "INVERT";
+      return os;
+    case Graphics::StencilOp::INCREMENT_AND_WRAP:
+      os << "INCREMENT_AND_WRAP";
+      return os;
+    case Graphics::StencilOp::DECREMENT_AND_WRAP:
+      os << "DECREMENT_AND_WRAP";
+      return os;
+  }
+  return os;
+};
+
+std::ostream& operator<<(std::ostream& os, Graphics::CompareOp op)
+{
+  switch(op)
+  {
+    case Graphics::CompareOp::NEVER:
+      os << "NEVER";
+      return os;
+    case Graphics::CompareOp::LESS:
+      os << "LESS";
+      return os;
+    case Graphics::CompareOp::EQUAL:
+      os << "EQUAL";
+      return os;
+    case Graphics::CompareOp::LESS_OR_EQUAL:
+      os << "LESS_OR_EQUAL";
+      return os;
+    case Graphics::CompareOp::GREATER:
+      os << "GREATER";
+      return os;
+    case Graphics::CompareOp::NOT_EQUAL:
+      os << "NOT_EQUAL";
+      return os;
+    case Graphics::CompareOp::GREATER_OR_EQUAL:
+      os << "GREATER_OR_EQUAL";
+      return os;
+    case Graphics::CompareOp::ALWAYS:
+      os << "ALWAYS";
+      return os;
+  }
+  return os;
+};
+
 TestGraphicsCommandBuffer::TestGraphicsCommandBuffer(TraceCallStack& callstack, TestGlAbstraction& glAbstraction)
 : mCallStack(callstack),
   mGlAbstraction(glAbstraction)
@@ -60,9 +124,9 @@ void TestGraphicsCommandBuffer::GetStateForDrawCall(int drawCallIndex)
   }
 }
 
-std::vector<Command*> TestGraphicsCommandBuffer::GetCommandsByType(CommandTypeMask mask)
+std::vector<const Command*> TestGraphicsCommandBuffer::GetCommandsByType(CommandTypeMask mask) const
 {
-  std::vector<Command*> mCommandStack{};
+  std::vector<const Command*> mCommandStack{};
   for(auto& cmd : mCommands)
   {
     if(uint32_t(cmd.type) == (mask & uint32_t(cmd.type)))
@@ -73,4 +137,27 @@ std::vector<Command*> TestGraphicsCommandBuffer::GetCommandsByType(CommandTypeMa
   return mCommandStack;
 }
 
+std::vector<const Command*> TestGraphicsCommandBuffer::GetChildCommandsByType(CommandTypeMask mask) const
+{
+  std::vector<const Command*> 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
index c10c3f1..3df3219 100644 (file)
@@ -32,27 +32,45 @@ 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,
+  SET_COLOR_MASK          = 1 << 17,
+  CLEAR_STENCIL_BUFFER    = 1 << 18,
+  CLEAR_DEPTH_BUFFER      = 1 << 19,
+  SET_STENCIL_TEST_ENABLE = 1 << 20,
+  SET_STENCIL_WRITE_MASK  = 1 << 21,
+  SET_STENCIL_OP          = 1 << 22,
+  SET_STENCIL_FUNC        = 1 << 23,
+  SET_DEPTH_COMPARE_OP    = 1 << 24,
+  SET_DEPTH_TEST_ENABLE   = 1 << 25,
+  SET_DEPTH_WRITE_ENABLE  = 1 << 26,
 };
 
+std::ostream& operator<<(std::ostream& os, Graphics::StencilOp op);
+
+std::ostream& operator<<(std::ostream& os, Graphics::CompareOp op);
+
 using CommandTypeMask = uint32_t;
 template<typename T>
 inline CommandTypeMask operator|(T flags, CommandType bit)
@@ -160,8 +178,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 +219,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;
@@ -245,6 +308,59 @@ struct Command
         data.viewportTest.enable = rhs.data.viewportTest.enable;
         break;
       }
+      case CommandType::SET_COLOR_MASK:
+      {
+        data.colorMask.enabled = rhs.data.colorMask.enabled;
+        break;
+      }
+      case CommandType::CLEAR_STENCIL_BUFFER:
+      {
+        break;
+      }
+      case CommandType::CLEAR_DEPTH_BUFFER:
+      {
+        break;
+      }
+      case CommandType::SET_STENCIL_TEST_ENABLE:
+      {
+        data.stencilTest.enabled = rhs.data.stencilTest.enabled;
+        break;
+      }
+      case CommandType::SET_STENCIL_FUNC:
+      {
+        data.stencilFunc.compareMask = rhs.data.stencilFunc.compareMask;
+        data.stencilFunc.compareOp   = rhs.data.stencilFunc.compareOp;
+        data.stencilFunc.reference   = rhs.data.stencilFunc.reference;
+        break;
+      }
+      case CommandType::SET_STENCIL_WRITE_MASK:
+      {
+        data.stencilWriteMask.mask = rhs.data.stencilWriteMask.mask;
+        break;
+      }
+      case CommandType::SET_STENCIL_OP:
+      {
+        data.stencilOp.failOp      = rhs.data.stencilOp.failOp;
+        data.stencilOp.depthFailOp = rhs.data.stencilOp.depthFailOp;
+        data.stencilOp.passOp      = rhs.data.stencilOp.passOp;
+        break;
+      }
+
+      case CommandType::SET_DEPTH_COMPARE_OP:
+      {
+        data.depth.compareOp = rhs.data.depth.compareOp;
+        break;
+      }
+      case CommandType::SET_DEPTH_TEST_ENABLE:
+      {
+        data.depth.testEnabled = rhs.data.depth.testEnabled;
+        break;
+      }
+      case CommandType::SET_DEPTH_WRITE_ENABLE:
+      {
+        data.depth.writeEnabled = rhs.data.depth.writeEnabled;
+        break;
+      }
     }
     type = rhs.type;
   }
@@ -257,6 +373,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);
@@ -330,6 +461,59 @@ struct Command
         data.viewportTest.enable = rhs.data.viewportTest.enable;
         break;
       }
+
+      case CommandType::SET_COLOR_MASK:
+      {
+        data.colorMask.enabled = rhs.data.colorMask.enabled;
+        break;
+      }
+      case CommandType::CLEAR_STENCIL_BUFFER:
+      {
+        break;
+      }
+      case CommandType::CLEAR_DEPTH_BUFFER:
+      {
+        break;
+      }
+      case CommandType::SET_STENCIL_TEST_ENABLE:
+      {
+        data.stencilTest.enabled = rhs.data.stencilTest.enabled;
+        break;
+      }
+      case CommandType::SET_STENCIL_WRITE_MASK:
+      {
+        data.stencilWriteMask.mask = rhs.data.stencilWriteMask.mask;
+        break;
+      }
+      case CommandType::SET_STENCIL_OP:
+      {
+        data.stencilOp.failOp      = rhs.data.stencilOp.failOp;
+        data.stencilOp.depthFailOp = rhs.data.stencilOp.depthFailOp;
+        data.stencilOp.passOp      = rhs.data.stencilOp.passOp;
+        break;
+      }
+      case CommandType::SET_STENCIL_FUNC:
+      {
+        data.stencilFunc.compareMask = rhs.data.stencilFunc.compareMask;
+        data.stencilFunc.compareOp   = rhs.data.stencilFunc.compareOp;
+        data.stencilFunc.reference   = rhs.data.stencilFunc.reference;
+        break;
+      }
+      case CommandType::SET_DEPTH_COMPARE_OP:
+      {
+        data.depth.compareOp = rhs.data.depth.compareOp;
+        break;
+      }
+      case CommandType::SET_DEPTH_TEST_ENABLE:
+      {
+        data.depth.testEnabled = rhs.data.depth.testEnabled;
+        break;
+      }
+      case CommandType::SET_DEPTH_WRITE_ENABLE:
+      {
+        data.depth.writeEnabled = rhs.data.depth.writeEnabled;
+        break;
+      }
     }
     type = rhs.type;
   }
@@ -398,6 +582,60 @@ struct Command
     {
       bool enable;
     } viewportTest;
+
+    struct BeginRenderPassDescriptor
+    {
+      Graphics::RenderPass*             renderPass;
+      Graphics::RenderTarget*           renderTarget;
+      Graphics::Rect2D                  renderArea;
+      std::vector<Graphics::ClearValue> clearValues;
+    } beginRenderPass;
+
+    struct
+    {
+      Graphics::SyncObject* syncObject;
+    } endRenderPass;
+
+    struct
+    {
+      std::vector<const TestGraphicsCommandBuffer*> buffers;
+    } executeCommandBuffers;
+
+    struct
+    {
+      Graphics::CompareOp compareOp;
+      bool                testEnabled;
+      bool                writeEnabled;
+    } depth;
+
+    struct
+    {
+      Graphics::StencilOp failOp;
+      Graphics::StencilOp passOp;
+      Graphics::StencilOp depthFailOp;
+    } stencilOp;
+
+    struct
+    {
+      uint32_t mask;
+    } stencilWriteMask;
+
+    struct
+    {
+      uint32_t            compareMask;
+      Graphics::CompareOp compareOp;
+      uint32_t            reference;
+    } stencilFunc;
+
+    struct
+    {
+      bool enabled;
+    } stencilTest;
+
+    struct
+    {
+      bool enabled;
+    } colorMask;
   } data;
 };
 
@@ -509,12 +747,23 @@ public:
   }
 
   void BeginRenderPass(
-    Graphics::RenderPass&             renderPass,
-    Graphics::RenderTarget&           renderTarget,
-    Graphics::Extent2D                renderArea,
+    Graphics::RenderPass*             renderPass,
+    Graphics::RenderTarget*           renderTarget,
+    Graphics::Rect2D                  renderArea,
     std::vector<Graphics::ClearValue> 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);
   }
 
   /**
@@ -526,9 +775,29 @@ public:
    * dependencies (for example, to know when target texture is ready
    * before passing it to another render pass).
    */
-  void EndRenderPass() override
+  void EndRenderPass(Graphics::SyncObject* syncObject) override
   {
-    mCallStack.PushCall("EndRenderPass", "");
+    mCommands.emplace_back(CommandType::END_RENDER_PASS);
+    auto& cmd = mCommands.back();
+
+    cmd.data.endRenderPass.syncObject = syncObject;
+
+    TraceCallStack::NamedParams namedParams;
+    namedParams["syncObject"] << std::hex << syncObject;
+    mCallStack.PushCall("EndRenderPass", namedParams.str(), namedParams);
+  }
+
+  void ExecuteCommandBuffers(std::vector<const CommandBuffer*>&& 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<const TestGraphicsCommandBuffer*>(item));
+    }
+    mCallStack.PushCall("ExecuteCommandBuffers", "");
   }
 
   void Draw(
@@ -642,6 +911,112 @@ public:
     mCommands.back().data.viewportTest.enable = value;
   }
 
+  void SetColorMask(bool enabled) override
+  {
+    TraceCallStack::NamedParams params;
+    params["enabled"] << (enabled ? "T" : "F");
+    mCallStack.PushCall("SetColorMask", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                   = CommandType::SET_COLOR_MASK;
+    mCommands.back().data.colorMask.enabled = enabled;
+  }
+
+  void ClearStencilBuffer() override
+  {
+    mCallStack.PushCall("SetStencilMask", "");
+    mCommands.emplace_back();
+    mCommands.back().type = CommandType::CLEAR_STENCIL_BUFFER;
+  }
+
+  void SetStencilTestEnable(bool stencilEnable) override
+  {
+    TraceCallStack::NamedParams params;
+    params["enabled"] << (stencilEnable ? "T" : "F");
+    mCallStack.PushCall("SetStencilTestEnable", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                     = CommandType::SET_STENCIL_TEST_ENABLE;
+    mCommands.back().data.stencilTest.enabled = stencilEnable;
+  }
+
+  void SetStencilWriteMask(uint32_t writeMask) override
+  {
+    TraceCallStack::NamedParams params;
+    params["writeMask"] << std::hex << writeMask;
+    mCallStack.PushCall("SetStencilWriteMask", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                       = CommandType::SET_STENCIL_WRITE_MASK;
+    mCommands.back().data.stencilWriteMask.mask = writeMask;
+  }
+
+  void SetStencilOp(Graphics::StencilOp failOp,
+                    Graphics::StencilOp passOp,
+                    Graphics::StencilOp depthFailOp) override
+  {
+    TraceCallStack::NamedParams params;
+    params["failOp"] << failOp;
+    params["passOp"] << passOp;
+    params["depthFailOp"] << depthFailOp;
+    mCallStack.PushCall("SetStencilOp", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                       = CommandType::SET_STENCIL_OP;
+    mCommands.back().data.stencilOp.failOp      = failOp;
+    mCommands.back().data.stencilOp.passOp      = passOp;
+    mCommands.back().data.stencilOp.depthFailOp = depthFailOp;
+  }
+
+  void SetStencilFunc(Graphics::CompareOp compareOp,
+                      uint32_t            reference,
+                      uint32_t            compareMask) override
+  {
+    TraceCallStack::NamedParams params;
+    params["compareOp"] << compareOp;
+    params["compareMask"] << std::hex << compareMask;
+    params["reference"] << std::hex << reference;
+    mCallStack.PushCall("SetStencilFunc", params.str(), params);
+
+    mCommands.emplace_back();
+    mCommands.back().type = CommandType::SET_STENCIL_FUNC;
+
+    mCommands.back().data.stencilFunc.compareOp   = compareOp;
+    mCommands.back().data.stencilFunc.compareMask = compareMask;
+    mCommands.back().data.stencilFunc.reference   = reference;
+  }
+
+  void SetDepthCompareOp(Graphics::CompareOp compareOp) override
+  {
+    TraceCallStack::NamedParams params;
+    params["compareOp"] << compareOp;
+    mCallStack.PushCall("SetDepthCompareOp", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                 = CommandType::SET_DEPTH_COMPARE_OP;
+    mCommands.back().data.depth.compareOp = compareOp;
+  }
+
+  void SetDepthTestEnable(bool depthTestEnable) override
+  {
+    TraceCallStack::NamedParams params;
+    params["enabled"] << (depthTestEnable ? "T" : "F");
+    mCallStack.PushCall("SetDepthTestEnable", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                   = CommandType::SET_DEPTH_TEST_ENABLE;
+    mCommands.back().data.depth.testEnabled = depthTestEnable;
+  }
+  void SetDepthWriteEnable(bool depthWriteEnable) override
+  {
+    TraceCallStack::NamedParams params;
+    params["enabled"] << (depthWriteEnable ? "T" : "F");
+    mCallStack.PushCall("SetDepthWriteEnable", params.str(), params);
+    mCommands.emplace_back();
+    mCommands.back().type                    = CommandType::SET_DEPTH_WRITE_ENABLE;
+    mCommands.back().data.depth.writeEnabled = depthWriteEnable;
+  }
+  void ClearDepthBuffer() override
+  {
+    mCallStack.PushCall("ClearDepthBuffer", "");
+    mCommands.emplace_back();
+    mCommands.back().type = CommandType::CLEAR_DEPTH_BUFFER;
+  }
+
   [[nodiscard]] const std::vector<Command>& GetCommands() const
   {
     return mCommands;
@@ -662,7 +1037,9 @@ public:
   /**
    * Retrieves commands of specified type
    */
-  std::vector<Command*> GetCommandsByType(CommandTypeMask mask);
+  std::vector<const Command*> GetCommandsByType(CommandTypeMask mask) const;
+
+  std::vector<const Command*> GetChildCommandsByType(CommandTypeMask mask) const;
 
 private:
   TraceCallStack&    mCallStack;
index 51f0721..cbdd5dd 100644 (file)
 
 #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-sync-object.h"
 #include "test-graphics-texture.h"
 
 #include <dali/integration-api/gl-defines.h>
 
 namespace Dali
 {
-template<typename T>
-T* Uncast(const Graphics::CommandBuffer* object)
-{
-  return const_cast<T*>(static_cast<const T*>(object));
-}
-
-template<typename T>
-T* Uncast(const Graphics::Texture* object)
-{
-  return const_cast<T*>(static_cast<const T*>(object));
-}
-
-template<typename T>
-T* Uncast(const Graphics::Sampler* object)
-{
-  return const_cast<T*>(static_cast<const T*>(object));
-}
-
-template<typename T>
-T* Uncast(const Graphics::Buffer* object)
-{
-  return const_cast<T*>(static_cast<const T*>(object));
-}
-
-template<typename T>
-T* Uncast(const Graphics::Shader* object)
-{
-  return const_cast<T*>(static_cast<const T*>(object));
-}
-
 std::ostream& operator<<(std::ostream& o, const Graphics::BufferCreateInfo& bufferCreateInfo)
 {
   return o << "usage:" << std::hex << bufferCreateInfo.usage << ", size:" << std::dec << bufferCreateInfo.size;
@@ -173,70 +147,34 @@ 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)
@@ -447,6 +385,143 @@ GLenum GetBlendOp(Graphics::BlendOp blendOp)
   return op;
 }
 
+struct GLCompareOp
+{
+  constexpr explicit GLCompareOp(Graphics::CompareOp compareOp)
+  {
+    switch(compareOp)
+    {
+      case Graphics::CompareOp::NEVER:
+        op = GL_NEVER;
+        break;
+      case Graphics::CompareOp::LESS:
+        op = GL_LESS;
+        break;
+      case Graphics::CompareOp::EQUAL:
+        op = GL_EQUAL;
+        break;
+      case Graphics::CompareOp::LESS_OR_EQUAL:
+        op = GL_LEQUAL;
+        break;
+      case Graphics::CompareOp::GREATER:
+        op = GL_GREATER;
+        break;
+      case Graphics::CompareOp::NOT_EQUAL:
+        op = GL_NOTEQUAL;
+        break;
+      case Graphics::CompareOp::GREATER_OR_EQUAL:
+        op = GL_GEQUAL;
+        break;
+      case Graphics::CompareOp::ALWAYS:
+        op = GL_ALWAYS;
+        break;
+    }
+  }
+  GLenum op{GL_LESS};
+};
+
+struct GLStencilOp
+{
+  constexpr explicit GLStencilOp(Graphics::StencilOp stencilOp)
+  {
+    switch(stencilOp)
+    {
+      case Graphics::StencilOp::KEEP:
+        op = GL_KEEP;
+        break;
+      case Graphics::StencilOp::ZERO:
+        op = GL_ZERO;
+        break;
+      case Graphics::StencilOp::REPLACE:
+        op = GL_REPLACE;
+        break;
+      case Graphics::StencilOp::INCREMENT_AND_CLAMP:
+        op = GL_INCR;
+        break;
+      case Graphics::StencilOp::DECREMENT_AND_CLAMP:
+        op = GL_DECR;
+        break;
+      case Graphics::StencilOp::INVERT:
+        op = GL_INVERT;
+        break;
+      case Graphics::StencilOp::INCREMENT_AND_WRAP:
+        op = GL_INCR_WRAP;
+        break;
+      case Graphics::StencilOp::DECREMENT_AND_WRAP:
+        op = GL_DECR_WRAP;
+        break;
+    }
+  }
+  GLenum op{GL_KEEP};
+};
+
+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 +535,407 @@ void TestGraphicsController::SubmitCommandBuffers(const Graphics::SubmitInfo& su
   for(auto& graphicsCommandBuffer : submitInfo.cmdBuffer)
   {
     auto commandBuffer = Uncast<TestGraphicsCommandBuffer>(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<TestGraphicsTexture>(binding.texture);
-
-          texture->Bind(binding.binding);
-
-          if(binding.sampler)
+          if(binding.texture)
           {
-            auto sampler = Uncast<TestGraphicsSampler>(binding.sampler);
-            if(sampler)
+            auto texture = Uncast<TestGraphicsTexture>(binding.texture);
+            texture->Bind(binding.binding);
+
+            if(binding.sampler)
             {
-              sampler->Apply(texture->GetTarget());
+              auto sampler = Uncast<TestGraphicsSampler>(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<TestGraphicsBuffer>(indexBufferBinding.buffer);
-        buffer->Bind();
+        for(auto& binding : cmd.data.bindVertexBuffers.vertexBufferBindings)
+        {
+          auto graphicsBuffer = binding.buffer;
+          auto vertexBuffer   = Uncast<TestGraphicsBuffer>(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<TestGraphicsBuffer>(graphicsBuffer);
-        vertexBuffer->Bind();
+        auto& indexBufferBinding = cmd.data.bindIndexBuffer;
+        if(indexBufferBinding.buffer)
+        {
+          auto buffer = Uncast<TestGraphicsBuffer>(indexBufferBinding.buffer);
+          buffer->Bind();
+        }
+        break;
       }
-    }
-
-    bool scissorEnabled = false;
+      case CommandType::BIND_UNIFORM_BUFFER:
+      {
+        auto& bindings = cmd.data.bindUniformBuffers;
+        auto  buffer   = bindings.standaloneUniformsBufferBinding;
 
-    auto scissorTestList = commandBuffer->GetCommandsByType(0 | CommandType::SET_SCISSOR_TEST);
-    if(!scissorTestList.empty())
-    {
-      if(scissorTestList[0]->data.scissorTest.enable)
+        // based on reflection, issue gl calls
+        buffer.buffer->BindAsUniformBuffer(static_cast<const TestGraphicsProgram*>(currentPipeline->programState.program), bindings.standaloneUniformsBufferBinding);
+        break;
+      }
+      case CommandType::BIND_SAMPLERS:
       {
-        mGl.Enable(GL_SCISSOR_TEST);
-        scissorEnabled = true;
+        break;
       }
-      else
+      case CommandType::BIND_PIPELINE:
       {
-        mGl.Disable(GL_SCISSOR_TEST);
+        currentPipeline = Uncast<TestGraphicsPipeline>(cmd.data.bindPipeline.pipeline);
+        BindPipeline(currentPipeline);
+        break;
+      }
+      case CommandType::DRAW:
+      {
+        mGl.DrawArrays(GetTopology(currentPipeline->inputAssemblyState.topology),
+                       0,
+                       cmd.data.draw.draw.vertexCount);
+        break;
+      }
+      case CommandType::DRAW_INDEXED:
+      {
+        mGl.DrawElements(GetTopology(currentPipeline->inputAssemblyState.topology),
+                         static_cast<GLsizei>(cmd.data.draw.drawIndexed.indexCount),
+                         GL_UNSIGNED_SHORT,
+                         reinterpret_cast<void*>(cmd.data.draw.drawIndexed.firstIndex));
+        break;
+      }
+      case CommandType::DRAW_INDEXED_INDIRECT:
+      {
+        mGl.DrawElements(GetTopology(currentPipeline->inputAssemblyState.topology),
+                         static_cast<GLsizei>(cmd.data.draw.drawIndexed.indexCount),
+                         GL_UNSIGNED_SHORT,
+                         reinterpret_cast<void*>(cmd.data.draw.drawIndexed.firstIndex));
+        break;
+      }
+      case CommandType::SET_SCISSOR:
+      {
+        if(scissorEnabled)
+        {
+          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.Disable(GL_SCISSOR_TEST);
+          scissorEnabled = false;
+        }
+        break;
+      }
+      case CommandType::SET_VIEWPORT_TEST:
+      {
+        break;
+      }
+      case CommandType::SET_VIEWPORT: // @todo Consider correcting for orientation here?
+      {
+        auto& rect = cmd.data.viewport.region;
+        mGl.Viewport(rect.x, rect.y, rect.width, rect.height);
+        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);
-    }
+      case CommandType::SET_COLOR_MASK:
+      {
+        // Set all channels to the same mask
+        const bool mask = cmd.data.colorMask.enabled;
+        mGl.ColorMask(mask, mask, mask, mask);
+        break;
+      }
+      case CommandType::CLEAR_STENCIL_BUFFER:
+      {
+        mGl.Clear(GL_STENCIL_BUFFER_BIT);
+        break;
+      }
+      case CommandType::CLEAR_DEPTH_BUFFER:
+      {
+        mGl.Clear(GL_DEPTH_BUFFER_BIT);
+        break;
+      }
 
-    // ignore viewport enable
+      case CommandType::SET_STENCIL_TEST_ENABLE:
+      {
+        if(cmd.data.stencilTest.enabled)
+        {
+          mGl.Enable(GL_STENCIL_TEST);
+        }
+        else
+        {
+          mGl.Disable(GL_STENCIL_TEST);
+        }
+        break;
+      }
 
-    // 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)
+      case CommandType::SET_STENCIL_FUNC:
       {
-        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<void*>(attributeOffset));
+        mGl.StencilFunc(GLCompareOp(cmd.data.stencilFunc.compareOp).op,
+                        cmd.data.stencilFunc.reference,
+                        cmd.data.stencilFunc.compareMask);
+        break;
       }
 
-      // Cull face setup
-      auto& rasterizationState = pipeline->rasterizationState;
-      if(rasterizationState.cullMode == Graphics::CullMode::NONE)
+      case CommandType::SET_STENCIL_WRITE_MASK:
       {
-        mGl.Disable(GL_CULL_FACE);
+        mGl.StencilMask(cmd.data.stencilWriteMask.mask);
+        break;
       }
-      else
+      case CommandType::SET_STENCIL_OP:
       {
-        mGl.Enable(GL_CULL_FACE);
-        mGl.CullFace(GetCullFace(rasterizationState.cullMode));
+        mGl.StencilOp(GLStencilOp(cmd.data.stencilOp.failOp).op,
+                      GLStencilOp(cmd.data.stencilOp.depthFailOp).op,
+                      GLStencilOp(cmd.data.stencilOp.passOp).op);
+        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_DEPTH_COMPARE_OP:
       {
-        mGl.Enable(GL_BLEND);
-
-        mGl.BlendFuncSeparate(GetBlendFactor(colorBlendState.srcColorBlendFactor),
-                              GetBlendFactor(colorBlendState.dstColorBlendFactor),
-                              GetBlendFactor(colorBlendState.srcAlphaBlendFactor),
-                              GetBlendFactor(colorBlendState.dstAlphaBlendFactor));
-        if(colorBlendState.colorBlendOp != colorBlendState.alphaBlendOp)
+        mGl.DepthFunc(GLCompareOp(cmd.data.depth.compareOp).op);
+        break;
+      }
+      case CommandType::SET_DEPTH_TEST_ENABLE:
+      {
+        if(cmd.data.depth.testEnabled)
         {
-          mGl.BlendEquationSeparate(GetBlendOp(colorBlendState.colorBlendOp), GetBlendOp(colorBlendState.alphaBlendOp));
+          mGl.Enable(GL_DEPTH_TEST);
         }
         else
         {
-          mGl.BlendEquation(GetBlendOp(colorBlendState.colorBlendOp));
+          mGl.Disable(GL_DEPTH_TEST);
         }
-        mGl.BlendColor(colorBlendState.blendConstants[0],
-                       colorBlendState.blendConstants[1],
-                       colorBlendState.blendConstants[2],
-                       colorBlendState.blendConstants[3]);
+        break;
       }
-      else
+      case CommandType::SET_DEPTH_WRITE_ENABLE:
       {
-        mGl.Disable(GL_BLEND);
+        mGl.DepthMask(cmd.data.depth.writeEnabled);
+        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::EXECUTE_COMMAND_BUFFERS:
       {
-        auto buffer = bindUniformBuffersCmds[0]->data.bindUniformBuffers.standaloneUniformsBufferBinding;
-
-        // based on reflection, issue gl calls
-        buffer.buffer->BindAsUniformBuffer(static_cast<const TestGraphicsProgram*>(pipeline->programState.program));
+        // Process secondary command buffers
+        for(auto& buf : cmd.data.executeCommandBuffers.buffers)
+        {
+          ProcessCommandBuffer(*Uncast<TestGraphicsCommandBuffer>(buf));
+        }
+        break;
       }
-
-      auto drawCmds = commandBuffer->GetCommandsByType(0 |
-                                                       CommandType::DRAW |
-                                                       CommandType::DRAW_INDEXED_INDIRECT |
-                                                       CommandType::DRAW_INDEXED);
-
-      if(!drawCmds.empty())
+      case CommandType::BEGIN_RENDER_PASS:
       {
-        if(drawCmds[0]->data.draw.type == DrawCallDescriptor::Type::DRAW_INDEXED)
+        auto renderTarget = Uncast<TestGraphicsRenderTarget>(cmd.data.beginRenderPass.renderTarget);
+
+        if(renderTarget)
         {
-          mGl.DrawElements(GetTopology(topology),
-                           static_cast<GLsizei>(drawCmds[0]->data.draw.drawIndexed.indexCount),
-                           GL_UNSIGNED_SHORT,
-                           reinterpret_cast<void*>(drawCmds[0]->data.draw.drawIndexed.firstIndex));
+          auto fb = renderTarget->mCreateInfo.framebuffer;
+          if(fb)
+          {
+            if(currentFramebuffer != fb)
+            {
+              currentFramebuffer = Uncast<TestGraphicsFramebuffer>(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<TestGraphicsRenderPass*>(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)
+              {
+                mGl.DepthMask(true);
+                uint32_t depthClearColor = 0u;
+                if(clearValues.size() == renderPass->attachments.size())
+                {
+                  depthClearColor = clearValues.back().depthStencil.depth;
+                }
+                mGl.ClearDepthf(depthClearColor);
+                mask |= GL_DEPTH_BUFFER_BIT;
+              }
+              if(depthStencil.stencilLoadOp == Graphics::AttachmentLoadOp::CLEAR)
+              {
+                uint32_t stencilClearColor = 0u;
+                if(clearValues.size() == renderPass->attachments.size())
+                {
+                  stencilClearColor = clearValues.back().depthStencil.stencil;
+                }
+                mGl.ClearStencil(stencilClearColor);
+                mGl.StencilMask(0xFF); // Clear all the bitplanes (assume 8)
+                mask |= GL_STENCIL_BUFFER_BIT;
+              }
+            }
+
+            if(mask != 0)
+            {
+              // Test scissor area and RT size
+              const auto& area = cmd.data.beginRenderPass.renderArea;
+              if(area.x == 0 &&
+                 area.y == 0 &&
+                 area.width == renderTarget->mCreateInfo.extent.width &&
+                 area.height == renderTarget->mCreateInfo.extent.height)
+              {
+                mGl.Disable(GL_SCISSOR_TEST);
+                mGl.Clear(mask);
+              }
+              else
+              {
+                mGl.Enable(GL_SCISSOR_TEST);
+                mGl.Scissor(cmd.data.beginRenderPass.renderArea.x, cmd.data.beginRenderPass.renderArea.y, cmd.data.beginRenderPass.renderArea.width, cmd.data.beginRenderPass.renderArea.height);
+                mGl.Clear(mask);
+                mGl.Disable(GL_SCISSOR_TEST);
+              }
+            }
+          }
+          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);
+        if(cmd.data.endRenderPass.syncObject != nullptr)
+        {
+          auto syncObject = Uncast<TestGraphicsSyncObject>(cmd.data.endRenderPass.syncObject);
+          syncObject->InitializeResource(); // create the sync object.
+        }
+        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<void*>(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);
+  }
+
+  auto* program = static_cast<const TestGraphicsProgram*>(pipeline->programState.program);
+  mGl.UseProgram(program->mImpl->mId);
+}
+
 /**
  * @brief Presents render target
  * @param renderTarget render target to present
@@ -713,6 +1002,15 @@ void TestGraphicsController::UpdateTextures(const std::vector<Graphics::TextureU
   }
 }
 
+void TestGraphicsController::GenerateTextureMipmaps(const Graphics::Texture& texture)
+{
+  mCallStack.PushCall("GenerateTextureMipmaps", "");
+
+  auto gfxTexture = Uncast<TestGraphicsTexture>(&texture);
+  mGl.BindTexture(gfxTexture->GetTarget(), 0);
+  mGl.GenerateMipmap(gfxTexture->GetTarget());
+}
+
 bool TestGraphicsController::EnableDepthStencilBuffer(bool enableDepth, bool enableStencil)
 {
   TraceCallStack::NamedParams namedParams;
@@ -770,7 +1068,7 @@ Graphics::UniquePtr<Graphics::CommandBuffer> TestGraphicsController::CreateComma
 Graphics::UniquePtr<Graphics::RenderPass> TestGraphicsController::CreateRenderPass(const Graphics::RenderPassCreateInfo& renderPassCreateInfo, Graphics::UniquePtr<Graphics::RenderPass>&& oldRenderPass)
 {
   mCallStack.PushCall("CreateRenderPass", "");
-  return nullptr;
+  return Graphics::MakeUnique<TestGraphicsRenderPass>(mGl, renderPassCreateInfo);
 }
 
 Graphics::UniquePtr<Graphics::Texture> TestGraphicsController::CreateTexture(const Graphics::TextureCreateInfo& textureCreateInfo, Graphics::UniquePtr<Graphics::Texture>&& oldTexture)
@@ -782,10 +1080,15 @@ Graphics::UniquePtr<Graphics::Texture> TestGraphicsController::CreateTexture(con
   return Graphics::MakeUnique<TestGraphicsTexture>(mGl, textureCreateInfo);
 }
 
-Graphics::UniquePtr<Graphics::Framebuffer> TestGraphicsController::CreateFramebuffer(const Graphics::FramebufferCreateInfo& framebufferCreateInfo, Graphics::UniquePtr<Graphics::Framebuffer>&& oldFramebuffer)
+Graphics::UniquePtr<Graphics::Framebuffer> TestGraphicsController::CreateFramebuffer(
+  const Graphics::FramebufferCreateInfo&       createInfo,
+  Graphics::UniquePtr<Graphics::Framebuffer>&& oldFramebuffer)
 {
-  mCallStack.PushCall("CreateFramebuffer", "");
-  return nullptr;
+  TraceCallStack::NamedParams namedParams;
+  namedParams["framebufferCreateInfo"] << createInfo;
+  mCallStack.PushCall("Controller::CreateFramebuffer", namedParams.str(), namedParams);
+
+  return Graphics::MakeUnique<TestGraphicsFramebuffer>(mFrameBufferCallStack, mGl, createInfo);
 }
 
 Graphics::UniquePtr<Graphics::Pipeline> TestGraphicsController::CreatePipeline(const Graphics::PipelineCreateInfo& pipelineCreateInfo, Graphics::UniquePtr<Graphics::Pipeline>&& oldPipeline)
@@ -849,7 +1152,15 @@ Graphics::UniquePtr<Graphics::Sampler> TestGraphicsController::CreateSampler(con
 Graphics::UniquePtr<Graphics::RenderTarget> TestGraphicsController::CreateRenderTarget(const Graphics::RenderTargetCreateInfo& renderTargetCreateInfo, Graphics::UniquePtr<Graphics::RenderTarget>&& oldRenderTarget)
 {
   mCallStack.PushCall("CreateRenderTarget", "");
-  return nullptr;
+  return Graphics::MakeUnique<TestGraphicsRenderTarget>(mGl, renderTargetCreateInfo);
+}
+
+Graphics::UniquePtr<Graphics::SyncObject> TestGraphicsController::CreateSyncObject(
+  const Graphics::SyncObjectCreateInfo&       syncObjectCreateInfo,
+  Graphics::UniquePtr<Graphics::SyncObject>&& oldSyncObject)
+{
+  mCallStack.PushCall("CreateSyncObject", "");
+  return Graphics::MakeUnique<TestGraphicsSyncObject>(mGraphicsSyncImpl, syncObjectCreateInfo);
 }
 
 Graphics::UniquePtr<Graphics::Memory> TestGraphicsController::MapBufferRange(const Graphics::MapBufferInfo& mapInfo)
index 803678e..cabc414 100644 (file)
 #include <dali/graphics-api/graphics-controller.h>
 #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"
+#include "test-graphics-sync-impl.h"
 
 namespace Dali
 {
@@ -36,6 +37,60 @@ 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<typename T>
+T* Uncast(const Graphics::CommandBuffer* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::Texture* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::Sampler* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::Buffer* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::Shader* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::Framebuffer* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::Pipeline* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::RenderTarget* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
+template<typename T>
+T* Uncast(const Graphics::SyncObject* object)
+{
+  return const_cast<T*>(static_cast<const T*>(object));
+}
+
 class TestGraphicsController : public Dali::Graphics::Controller
 {
 public:
@@ -53,14 +108,14 @@ public:
     return mGl;
   }
 
-  Integration::GlSyncAbstraction& GetGlSyncAbstraction() override
+  Integration::GlContextHelperAbstraction& GetGlContextHelperAbstraction() override
   {
-    return mGlSyncAbstraction;
+    return mGlContextHelperAbstraction;
   }
 
-  Integration::GlContextHelperAbstraction& GetGlContextHelperAbstraction() override
+  TestGraphicsSyncImplementation& GetGraphicsSyncImpl()
   {
-    return mGlContextHelperAbstraction;
+    return mGraphicsSyncImpl;
   }
 
   void SubmitCommandBuffers(const Graphics::SubmitInfo& submitInfo) override;
@@ -113,6 +168,12 @@ public:
                       const std::vector<Graphics::TextureUpdateSourceInfo>& sourceList) override;
 
   /**
+   * Auto generates mipmaps for the texture
+   * @param[in] texture The texture
+   */
+  void GenerateTextureMipmaps(const Graphics::Texture& texture) override;
+
+  /**
    * TBD: do we need those functions in the new implementation?
    */
   bool EnableDepthStencilBuffer(bool enableDepth, bool enableStencil) override;
@@ -219,11 +280,20 @@ public:
   Graphics::UniquePtr<Graphics::RenderTarget> CreateRenderTarget(const Graphics::RenderTargetCreateInfo& renderTargetCreateInfo, Graphics::UniquePtr<Graphics::RenderTarget>&& oldRenderTarget) override;
 
   /**
+   * @brief Creates new sync object
+   * Could add timeout etc to createinfo... but nah.
+   *
+   * @return pointer to the SyncObject
+   */
+  Graphics::UniquePtr<Graphics::SyncObject> CreateSyncObject(const Graphics::SyncObjectCreateInfo&       syncObjectCreateInfo,
+                                                             Graphics::UniquePtr<Graphics::SyncObject>&& oldSyncObject) override;
+
+  /**
    * @brief Maps memory associated with Buffer object
    *
    * @param[in] mapInfo Filled details of mapped resource
    *
-   * @return Returns pointer to Memory object or Graphicsnullptr on error
+   * @return Returns pointer to Memory object or nullptr on error
    */
   Graphics::UniquePtr<Graphics::Memory> MapBufferRange(const Graphics::MapBufferInfo& mapInfo) override;
 
@@ -331,13 +401,18 @@ 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<Graphics::SubmitInfo> mSubmitStack;
 
   TestGlAbstraction              mGl;
-  TestGlSyncAbstraction          mGlSyncAbstraction;
+  TestGraphicsSyncImplementation mGraphicsSyncImpl;
   TestGlContextHelperAbstraction mGlContextHelperAbstraction;
 
   bool isDiscardQueueEmptyResult{true};
@@ -352,6 +427,10 @@ public:
   };
   std::vector<ProgramCache> mProgramCache;
 
+  struct PipelineCache
+  {
+  };
+
   std::vector<UniformData> mCustomUniforms;
 };
 
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 (file)
index 0000000..74f1e29
--- /dev/null
@@ -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 <dali/integration-api/gl-defines.h>
+#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<TestGraphicsTexture>(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<TestGraphicsTexture>(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<TestGraphicsTexture>(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 (file)
index 0000000..664c28b
--- /dev/null
@@ -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 <dali/graphics-api/graphics-framebuffer-create-info.h>
+#include <dali/graphics-api/graphics-framebuffer.h>
+#include <dali/graphics-api/graphics-types.h>
+#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
index d303d56..9e80f8f 100644 (file)
@@ -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 (file)
index 0000000..b52dd2d
--- /dev/null
@@ -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 <dali/graphics-api/graphics-render-pass-create-info.h>
+#include <dali/graphics-api/graphics-render-pass.h>
+
+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<Graphics::AttachmentDescription> 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 (file)
index 0000000..1ad7a5a
--- /dev/null
@@ -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 <dali/graphics-api/graphics-render-target-create-info.h>
+#include <dali/graphics-api/graphics-render-target.h>
+
+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
  *
  */
 
-#include "test-gl-sync-abstraction.h"
+#include "test-graphics-sync-impl.h"
 
 namespace Dali
 {
-TestSyncObject::TestSyncObject(TraceCallStack& trace)
+TestSyncObject::TestSyncObject(Dali::TraceCallStack& trace)
+
 : synced(false),
   mTrace(trace)
 {
+  mTrace.PushCall("TestSyncObject cons", ""); // Trace the method
 }
 
 TestSyncObject::~TestSyncObject()
 {
+  mTrace.PushCall("TestSyncObject dstr", ""); // Trace the method
 }
 
 bool TestSyncObject::IsSynced()
@@ -35,7 +38,7 @@ bool TestSyncObject::IsSynced()
   return synced;
 }
 
-TestGlSyncAbstraction::TestGlSyncAbstraction()
+TestGraphicsSyncImplementation::TestGraphicsSyncImplementation()
 {
   Initialize();
 }
@@ -43,7 +46,7 @@ TestGlSyncAbstraction::TestGlSyncAbstraction()
 /**
  * Destructor
  */
-TestGlSyncAbstraction::~TestGlSyncAbstraction()
+TestGraphicsSyncImplementation::~TestGraphicsSyncImplementation()
 {
   for(SyncIter iter = mSyncObjects.begin(), end = mSyncObjects.end(); iter != end; ++iter)
   {
@@ -52,18 +55,14 @@ TestGlSyncAbstraction::~TestGlSyncAbstraction()
 }
 
 /**
- * Initialize the sync objects - clear down the map
+ * Initialize the sync objects
  */
-void TestGlSyncAbstraction::Initialize()
+void TestGraphicsSyncImplementation::Initialize()
 {
   mSyncObjects.clear();
 }
 
-/**
- * Create a sync object
- * @return the sync object
- */
-Integration::GlSyncAbstraction::SyncObject* TestGlSyncAbstraction::CreateSyncObject()
+Integration::GraphicsSyncAbstraction::SyncObject* TestGraphicsSyncImplementation::CreateSyncObject()
 {
   mTrace.PushCall("CreateSyncObject", ""); // Trace the method
 
@@ -76,7 +75,7 @@ Integration::GlSyncAbstraction::SyncObject* TestGlSyncAbstraction::CreateSyncObj
  * Destroy a sync object
  * @param[in] syncObject The object to destroy
  */
-void TestGlSyncAbstraction::DestroySyncObject(Integration::GlSyncAbstraction::SyncObject* syncObject)
+void TestGraphicsSyncImplementation::DestroySyncObject(Integration::GraphicsSyncAbstraction::SyncObject* syncObject)
 {
   std::stringstream out;
   out << syncObject;
@@ -93,7 +92,7 @@ void TestGlSyncAbstraction::DestroySyncObject(Integration::GlSyncAbstraction::Sy
   }
 }
 
-Integration::GlSyncAbstraction::SyncObject* TestGlSyncAbstraction::GetLastSyncObject()
+Integration::GraphicsSyncAbstraction::SyncObject* TestGraphicsSyncImplementation::GetLastSyncObject()
 {
   if(!mSyncObjects.empty())
   {
@@ -107,7 +106,7 @@ Integration::GlSyncAbstraction::SyncObject* TestGlSyncAbstraction::GetLastSyncOb
  * @param[in]
  * @param[in] sync The sync value to set
  */
-void TestGlSyncAbstraction::SetObjectSynced(Integration::GlSyncAbstraction::SyncObject* syncObject, bool sync)
+void TestGraphicsSyncImplementation::SetObjectSynced(Integration::GraphicsSyncAbstraction::SyncObject* syncObject, bool sync)
 {
   TestSyncObject* testSyncObject = static_cast<TestSyncObject*>(syncObject);
   testSyncObject->synced         = sync;
@@ -116,7 +115,7 @@ void TestGlSyncAbstraction::SetObjectSynced(Integration::GlSyncAbstraction::Sync
 /**
  * Turn trace on
  */
-void TestGlSyncAbstraction::EnableTrace(bool enable)
+void TestGraphicsSyncImplementation::EnableTrace(bool enable)
 {
   mTrace.Enable(enable);
 }
@@ -124,7 +123,7 @@ void TestGlSyncAbstraction::EnableTrace(bool enable)
 /**
  * Reset the trace callstack
  */
-void TestGlSyncAbstraction::ResetTrace()
+void TestGraphicsSyncImplementation::ResetTrace()
 {
   mTrace.Reset();
 }
@@ -132,12 +131,12 @@ void TestGlSyncAbstraction::ResetTrace()
 /**
  * Get the trace object (allows test case to find methods on it)
  */
-TraceCallStack& TestGlSyncAbstraction::GetTrace()
+TraceCallStack& TestGraphicsSyncImplementation::GetTrace()
 {
   return mTrace;
 }
 
-int32_t TestGlSyncAbstraction::GetNumberOfSyncObjects()
+int32_t TestGraphicsSyncImplementation::GetNumberOfSyncObjects()
 {
   return static_cast<int32_t>(mSyncObjects.size());
 }
@@ -1,5 +1,5 @@
-#ifndef TEST_GL_SYNC_ABSTRACTION_H
-#define TEST_GL_SYNC_ABSTRACTION_H
+#ifndef TEST_SYNC_IMPLEMENTATION_H
+#define TEST_SYNC_IMPLEMENTATION_H
 
 /*
  * Copyright (c) 2021 Samsung Electronics Co., Ltd.
 #include <string>
 
 // INTERNAL INCLUDES
+#include <dali/graphics-api/graphics-sync-object-create-info.h>
+#include <dali/graphics-api/graphics-sync-object.h>
 #include <dali/integration-api/core.h>
-#include <dali/integration-api/gl-sync-abstraction.h>
+#include <dali/integration-api/graphics-sync-abstraction.h>
 
 #include "test-trace-call-stack.h"
 
 namespace Dali
 {
-class DALI_CORE_API TestSyncObject : public Integration::GlSyncAbstraction::SyncObject
+class TestGraphicsSyncImplementation;
+
+class TestSyncObject : public Integration::GraphicsSyncAbstraction::SyncObject
 {
 public:
   TestSyncObject(TraceCallStack& trace);
@@ -42,47 +46,45 @@ public:
 };
 
 /**
- * Class to emulate the GL sync functions with tracing
+ * Class to emulate the gpu sync functions with tracing
  */
-class DALI_CORE_API TestGlSyncAbstraction : public Integration::GlSyncAbstraction
+class TestGraphicsSyncImplementation : public Integration::GraphicsSyncAbstraction
 {
 public:
   /**
    * Constructor
    */
-  TestGlSyncAbstraction();
+  TestGraphicsSyncImplementation();
 
   /**
    * Destructor
    */
-  ~TestGlSyncAbstraction() override;
+  virtual ~TestGraphicsSyncImplementation();
 
   /**
-   * Initialize the sync objects - clear down the map
+   * Initialize the sync objects
    */
   void Initialize();
 
   /**
-   * Create a sync object
-   * @return the sync object
+   * Create a sync object that can be polled
    */
-  Integration::GlSyncAbstraction::SyncObject* CreateSyncObject() override;
+  GraphicsSyncAbstraction::SyncObject* CreateSyncObject() override;
 
   /**
    * Destroy a sync object
-   * @param[in] syncObject The object to destroy
    */
-  void DestroySyncObject(Integration::GlSyncAbstraction::SyncObject* syncObject) override;
+  void DestroySyncObject(GraphicsSyncAbstraction::SyncObject* syncObject) override;
 
 public: // TEST FUNCTIONS
-  Integration::GlSyncAbstraction::SyncObject* GetLastSyncObject();
+  GraphicsSyncAbstraction::SyncObject* GetLastSyncObject();
 
   /**
    * Test method to trigger the object sync behaviour.
    * @param[in]
    * @param[in] sync The sync value to set
    */
-  void SetObjectSynced(Integration::GlSyncAbstraction::SyncObject* syncObject, bool sync);
+  void SetObjectSynced(GraphicsSyncAbstraction::SyncObject* syncObject, bool sync);
 
   /**
    * Turn trace on
@@ -106,10 +108,10 @@ public: // TEST FUNCTIONS
    */
   int32_t GetNumberOfSyncObjects();
 
-private:
-  TestGlSyncAbstraction(const TestGlSyncAbstraction&);            ///< Undefined
-  TestGlSyncAbstraction& operator=(const TestGlSyncAbstraction&); ///< Undefined
+  TestGraphicsSyncImplementation(const TestGraphicsSyncImplementation&) = delete;
+  TestGraphicsSyncImplementation& operator=(const TestGraphicsSyncImplementation&) = delete;
 
+private:
   typedef std::vector<TestSyncObject*> SyncContainer;
   typedef SyncContainer::iterator      SyncIter;
   SyncContainer                        mSyncObjects;       ///< The sync objects
diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.cpp b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.cpp
new file mode 100644 (file)
index 0000000..cf9b3c9
--- /dev/null
@@ -0,0 +1,48 @@
+/*
+ * 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-sync-object.h"
+
+namespace Dali
+{
+TestGraphicsSyncObject::TestGraphicsSyncObject(TestGraphicsSyncImplementation& syncImpl, const Graphics::SyncObjectCreateInfo& createInfo)
+: mSyncImplementation(syncImpl),
+  mSyncObject(nullptr),
+  mCreateInfo(createInfo)
+{
+}
+
+TestGraphicsSyncObject::~TestGraphicsSyncObject()
+{
+  mSyncImplementation.DestroySyncObject(mSyncObject);
+}
+
+void TestGraphicsSyncObject::InitializeResource()
+{
+  mSyncObject = static_cast<TestSyncObject*>(mSyncImplementation.CreateSyncObject());
+}
+
+bool TestGraphicsSyncObject::IsSynced()
+{
+  bool synced = false;
+  if(mSyncObject)
+  {
+    synced = mSyncObject->IsSynced();
+  }
+  return synced;
+}
+
+} // namespace Dali
diff --git a/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.h b/automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-graphics-sync-object.h
new file mode 100644 (file)
index 0000000..c33de6c
--- /dev/null
@@ -0,0 +1,43 @@
+#ifndef DALI_TEST_GRAPHICS_SYNC_OBJECT_H_
+#define DALI_TEST_GRAPHICS_SYNC_OBJECT_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 <dali/graphics-api/graphics-sync-object-create-info.h>
+#include <dali/graphics-api/graphics-sync-object.h>
+
+#include <test-graphics-sync-impl.h>
+
+namespace Dali
+{
+class TestGraphicsSyncObject : public Graphics::SyncObject
+{
+public:
+  TestGraphicsSyncObject(TestGraphicsSyncImplementation& syncImpl, const Graphics::SyncObjectCreateInfo& createInfo);
+  ~TestGraphicsSyncObject() override;
+  void InitializeResource();
+  bool IsSynced() override;
+
+public:
+  TestGraphicsSyncImplementation& mSyncImplementation;
+  TestSyncObject*                 mSyncObject;
+  Graphics::SyncObjectCreateInfo  mCreateInfo;
+};
+
+} // namespace Dali
+
+#endif //DALI_TEST_GRAPHICS_SYNC_OBJECT_H
index adeeeca..9e1ad3e 100644 (file)
@@ -183,6 +183,7 @@ bool IsCompressedFormat(Graphics::Format pixelFormat)
     case Graphics::Format::R64G64B64A64_SINT:
     case Graphics::Format::R64G64B64A64_SFLOAT:
     case Graphics::Format::B10G11R11_UFLOAT_PACK32:
+    case Graphics::Format::R11G11B10_UFLOAT_PACK32:
     case Graphics::Format::E5B9G9R9_UFLOAT_PACK32:
     case Graphics::Format::D16_UNORM:
     case Graphics::Format::X8_D24_UNORM_PACK32:
@@ -618,6 +619,12 @@ void PixelFormatToGl(Graphics::Format pixelFormat, GLenum& glFormat, GLint& glIn
       glFormat = 0;
       break;
     }
+    case Graphics::Format::R11G11B10_UFLOAT_PACK32:
+    {
+      glFormat      = GL_RGB;
+      pixelDataType = GL_FLOAT;
+      break;
+    }
 
     case Graphics::Format::R4G4_UNORM_PACK8:
     case Graphics::Format::A1R5G5B5_UNORM_PACK16:
@@ -768,6 +775,7 @@ void PixelFormatToGl(Graphics::Format pixelFormat, GLenum& glFormat, GLint& glIn
   {
     case Graphics::Format::R16G16B16A16_SFLOAT:
     case Graphics::Format::R32G32B32A32_SFLOAT:
+    case Graphics::Format::R11G11B10_UFLOAT_PACK32:
     {
       glInternalFormat = GL_R11F_G11F_B10F;
       break;
index 3eb54d3..58f7738 100644 (file)
@@ -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);
index 86b3bd9..0cfdcc0 100644 (file)
@@ -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<Rect<int>>& damagedRects, Rect<int>& clippingRect  ) override { return false; };
 
-  void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector<Rect<int>>& damagedRects ) override {};
+  void PostRender()
+  {
+  }
+
+  //void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector<Rect<int>>& damagedRects ) override {};
 
   void StopRender() override {};
 
index 48173fd..e309bfe 100644 (file)
@@ -45,6 +45,12 @@ ToolkitTestApplication::ToolkitTestApplication( size_t surfaceWidth, size_t surf
   mScene = AdaptorImpl::GetScene( *mMainWindow );
   mScene.SetDpi( Vector2( horizontalDpi, verticalDpi ) );
 
+  // Create render target for the scene
+  Graphics::RenderTargetCreateInfo rtInfo{};
+  rtInfo.SetExtent( {mSurfaceWidth, mSurfaceHeight });
+  mRenderTarget = mGraphicsController.CreateRenderTarget( rtInfo, nullptr );
+  mScene.SetSurfaceRenderTarget( mRenderTarget.get() );
+
   // Core needs to be initialized next before we start the adaptor
   InitializeCore();
   Accessibility::Accessible::SetObjectRegistry(mCore->GetObjectRegistry());
index 147b3fd..857163d 100644 (file)
@@ -161,7 +161,7 @@ bool ConvertPixelFormat(const uint32_t ktxPixelFormat, Pixel::Format& format)
     }
     case 0x8C3A: // GL_R11F_G11F_B10F
     {
-      format = Pixel::RGB32F;
+      format = Pixel::R11G11B10F;
       break;
     }
     case 0x8D7C: // GL_RGBA8UI
index 7f462f6..78a6268 100644 (file)
@@ -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.
@@ -175,6 +175,7 @@ void GetRedOffsetAndMask(Dali::Pixel::Format pixelFormat, int32_t& byteOffset, i
     case Dali::Pixel::DEPTH_UNSIGNED_INT:
     case Dali::Pixel::DEPTH_FLOAT:
     case Dali::Pixel::DEPTH_STENCIL:
+    case Dali::Pixel::R11G11B10F:
     {
       DALI_LOG_ERROR("Pixel format not compatible.\n");
       byteOffset = 0;