test: unify test code for supporting gl engine from all test cases. 42/237342/7
authorHermet Park <chuneon.park@samsung.com>
Mon, 29 Jun 2020 08:35:04 +0000 (17:35 +0900)
committerHermet Park <chuneon.park@samsung.com>
Mon, 29 Jun 2020 12:00:26 +0000 (21:00 +0900)
now you can launch tests with gl engine by "gl" option

ex)
$ testTransform gl
$ testScene gl

Change-Id: Idb720ed369a2fbfb908c977fdaebd7289986fb6f

22 files changed:
test/testAsync.cpp
test/testBlending.cpp
test/testBoundary.cpp
test/testCommon.h [new file with mode: 0644]
test/testComposition.cpp [deleted file]
test/testCustomTransform.cpp
test/testDirectUpdate.cpp
test/testGradient.cpp [deleted file]
test/testGradientTransform.cpp
test/testLinearGradient.cpp
test/testMultiShapes.cpp
test/testPath.cpp
test/testPathCopy.cpp
test/testRadialGradient.cpp
test/testScene.cpp
test/testSceneTransform.cpp
test/testShape.cpp
test/testStroke.cpp
test/testStrokeLine.cpp
test/testSvg.cpp
test/testTransform.cpp
test/testUpdate.cpp

index 7172dd9..a8ac2b0 100644 (file)
@@ -1,25 +1,14 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 1920
-#define HEIGHT 1080
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 #define COUNT 50
 
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
 static double t1, t2, t3, t4;
 static unsigned cnt = 0;
 
-void tvgtest()
-{
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-}
-
-Eina_Bool anim_cb(void *data)
+bool tvgUpdateCmds(tvg::Canvas* canvas)
 {
     auto t = ecore_time_get();
 
@@ -27,7 +16,7 @@ Eina_Bool anim_cb(void *data)
     if (canvas->clear() != tvg::Result::Success)
       {
          //Logically wrong! Probably, you missed to call sync() before.
-         return ECORE_CALLBACK_RENEW;
+         return false;
       }
 
     t1 = t;
@@ -38,8 +27,8 @@ Eina_Bool anim_cb(void *data)
 
         float x = rand() % (WIDTH/2);
         float y = rand() % (HEIGHT/2);
-        float w = 1 + rand() % 1200;
-        float h = 1 + rand() %  800;
+        float w = 1 + rand() % (int)(WIDTH * 1.3 / 2);
+        float h = 1 + rand() %  (int)(HEIGHT * 1.3 / 2);
 
         shape->appendRect(x, y, w, h, rand() % 400);
 
@@ -61,8 +50,29 @@ Eina_Bool anim_cb(void *data)
 
     t3 = ecore_time_get();
 
+    return true;
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+}
+
+Eina_Bool animSwCb(void* data)
+{
+    if (!tvgUpdateCmds(swCanvas.get())) return ECORE_CALLBACK_RENEW;
+
     //Drawing task can be performed asynchronously.
-    canvas->draw();
+    swCanvas->draw();
 
     //Update Efl Canvas
     Eo* img = (Eo*) data;
@@ -72,50 +82,96 @@ Eina_Bool anim_cb(void *data)
     return ECORE_CALLBACK_RENEW;
 }
 
-void render_cb(void* data, Eo* obj)
+void drawSwView(void* data, Eo* obj)
 {
     //Make it guarantee finishing drawing task.
-    canvas->sync();
+    swCanvas->sync();
 
     t4 = ecore_time_get();
 
     printf("[%5d]: total[%fms] = clear[%fms], update[%fms], render[%fms]\n", ++cnt, t4 - t1, t2 - t1, t3 - t2, t4 - t3);
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+}
+
+void drawGLview(Evas_Object *obj)
 {
-    elm_exit();
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->sync();
 }
 
+Eina_Bool animGlCb(void* data)
+{
+    if (!tvgUpdateCmds(glCanvas.get())) return ECORE_CALLBACK_RENEW;
+
+    //Drawing task can be performed asynchronously.
+    glCanvas->draw();
+
+    return ECORE_CALLBACK_RENEW;
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    tvgtest();
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_image_pixels_get_callback_set(img, render_cb, nullptr);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_init(argc, argv);
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    elm_config_accel_preference_set("gl");
 
-    ecore_animator_add(anim_cb, img);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        evas_object_image_pixels_get_callback_set(view, drawSwView, nullptr);
+        ecore_animator_add(animSwCb, view);
+    } else {
+        auto view = createGlView();
+        ecore_animator_add(animGlCb, view);
+    }
 
     elm_run();
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 82aa32d..7794689 100644 (file)
@@ -1,21 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
     canvas->reserve(5);
 
     //Prepare Round Rectangle
@@ -57,40 +47,108 @@ void tvgtest()
     shape5->appendCircle(600, 650, 200, 150);
     shape5->fill(0, 0, 255, 255);
     canvas->push(move(shape5));
+}
 
-    //Draw the Shapes onto the Canvas
-    canvas->draw();
-    canvas->sync();
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawSwView(void* data, Eo* obj)
 {
-   elm_exit();
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index d7cb8fa..e74ac5e 100644 (file)
@@ -1,21 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
     canvas->reserve(5);             //reserve 5 shape nodes (optional)
 
     //Prepare Shape1
@@ -47,40 +37,107 @@ void tvgtest()
     shape5->appendCircle(200, 650, 250, 200);
     shape5->fill(0, 0, 0, 255);
     canvas->push(move(shape5));
+}
 
-    //Draw the Shapes onto the Canvas
-    canvas->draw();
-    canvas->sync();
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawGLview(Evas_Object *obj)
 {
-   elm_exit();
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
diff --git a/test/testCommon.h b/test/testCommon.h
new file mode 100644 (file)
index 0000000..c47723a
--- /dev/null
@@ -0,0 +1,70 @@
+#include <iostream>
+#include <Elementary.h>
+#include <thorvg.h>
+
+using namespace std;
+
+#define WIDTH 800
+#define HEIGHT 800
+
+/************************************************************************/
+/* Common Infrastructure Code                                           */
+/************************************************************************/
+
+void tvgSwTest(uint32_t* buffer);
+
+void win_del(void *data, Evas_Object *o, void *ev)
+{
+   elm_exit();
+}
+
+void drawSwView(void* data, Eo* obj);
+
+static Eo* createSwView()
+{
+    static uint32_t buffer[WIDTH * HEIGHT];
+
+    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
+    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+
+    Eo* view = evas_object_image_filled_add(evas_object_evas_get(win));
+    evas_object_image_size_set(view, WIDTH, HEIGHT);
+    evas_object_image_data_set(view, buffer);
+    evas_object_image_pixels_get_callback_set(view, drawSwView, nullptr);
+    evas_object_image_pixels_dirty_set(view, EINA_TRUE);
+    evas_object_image_data_update_add(view, 0, 0, WIDTH, HEIGHT);
+    evas_object_size_hint_weight_set(view, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
+    evas_object_show(view);
+
+    elm_win_resize_object_add(win, view);
+    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
+    evas_object_show(win);
+
+    tvgSwTest(buffer);
+
+    return view;
+}
+
+void initGLview(Evas_Object *obj);
+void drawGLview(Evas_Object *obj);
+
+static Eo* createGlView()
+{
+    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
+    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+
+    Eo* view = elm_glview_add(win);
+    evas_object_size_hint_weight_set(view, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
+    elm_glview_mode_set(view, ELM_GLVIEW_ALPHA);
+    elm_glview_resize_policy_set(view, ELM_GLVIEW_RESIZE_POLICY_RECREATE);
+    elm_glview_render_policy_set(view, ELM_GLVIEW_RENDER_POLICY_ON_DEMAND);
+    elm_glview_init_func_set(view, initGLview);
+    elm_glview_render_func_set(view, drawGLview);
+    evas_object_show(view);
+
+    elm_win_resize_object_add(win, view);
+    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
+    evas_object_show(win);
+
+    return view;
+}
diff --git a/test/testComposition.cpp b/test/testComposition.cpp
deleted file mode 100644 (file)
index 6230dc0..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#include <thorvg.h>
-
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-int main(int argc, char **argv)
-{
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Composition Source Canvas
-    auto canvas1 = tvg::SwCanvas::gen(buffer, WIDTH, HEIGHT);
-
-    //Draw something onto the Canvas and leaving sync to the target.
-    canvas1->draw();
-
-    //Create a Main Canvas
-    auto canvas2 = tvg::SwCanvas::gen(buffer, WIDTH, HEIGHT);
-
-    //Create a Shape
-    auto shape = tvg::Shape::gen();
-    shape->composite(canvas, tvg::CompMaskAdd);
-
-    //Draw the Scene onto the Canvas
-    canvas2->push(move(shape));
-    canvas2->draw();
-    canvas2->sync();
-
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
index c57d4d4..1109a21 100644 (file)
@@ -1,21 +1,12 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 tvg::Shape* pShape = nullptr;
 
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Shape1
     auto shape = tvg::Shape::gen();
 
@@ -36,13 +27,9 @@ void tvgtest()
     shape->close();
     shape->fill(0, 0, 255, 255);
     canvas->push(move(shape));
-
-    //Draw first frame
-    canvas->draw();
-    canvas->sync();
 }
 
-void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+void tvgUpdateCmds(tvg::Canvas* canvas, float progress)
 {
     /* Update shape directly.
        You can update only necessary properties of this shape,
@@ -86,46 +73,124 @@ void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progres
 
     //Update shape for drawing (this may work asynchronously)
     canvas->update(pShape);
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
 
-    //Draw Next frames
-    canvas->draw();
-    canvas->sync();
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void transitSwCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+{
+    tvgUpdateCmds(swCanvas.get(), progress);
 
     //Update Efl Canvas
     Eo* img = (Eo*) effect;
     evas_object_image_data_update_add(img, 0, 0, WIDTH, HEIGHT);
+    evas_object_image_pixels_dirty_set(img, EINA_TRUE);
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void transitGlCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
 {
-    elm_exit();
+    tvgUpdateCmds(glCanvas.get(), progress);
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
+
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
     //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    tvgtest();
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    //Show the result using EFL...
     elm_init(argc, argv);
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    elm_config_accel_preference_set("gl");
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    Elm_Transit *transit = elm_transit_add();
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        elm_transit_effect_add(transit, transitSwCb, view, nullptr);
+    } else {
+        auto view = createGlView();
+        elm_transit_effect_add(transit, transitGlCb, view, nullptr);
+    }
 
-    Elm_Transit *transit = elm_transit_add();
-    elm_transit_effect_add(transit, transit_cb, img, nullptr);
     elm_transit_duration_set(transit, 2);
     elm_transit_repeat_times_set(transit, -1);
     elm_transit_auto_reverse_set(transit, EINA_TRUE);
@@ -135,5 +200,5 @@ int main(int argc, char **argv)
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 4dbc26b..93b2dfb 100644 (file)
@@ -1,21 +1,12 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 tvg::Shape* pShape = nullptr;
 
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Shape
     auto shape = tvg::Shape::gen();
 
@@ -31,13 +22,9 @@ void tvgtest()
     shape->stroke(1);
 
     canvas->push(move(shape));
-
-    //Draw first frame
-    canvas->draw();
-    canvas->sync();
 }
 
-void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+void tvgUpdateCmds(tvg::Canvas* canvas, float progress)
 {
     /* Update shape directly.
        You can update only necessary properties of this shape,
@@ -50,47 +37,124 @@ void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progres
 
     //Update shape for drawing (this may work asynchronously)
     canvas->update(pShape);
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
 
-    //Draw Next frames
-    canvas->draw();
-    canvas->sync();
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void transitSwCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+{
+    tvgUpdateCmds(swCanvas.get(), progress);
 
     //Update Efl Canvas
     Eo* img = (Eo*) effect;
     evas_object_image_data_update_add(img, 0, 0, WIDTH, HEIGHT);
+    evas_object_image_pixels_dirty_set(img, EINA_TRUE);
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
-void
-win_del(void *data, Evas_Object *o, void *ev)
+void transitGlCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
 {
-    elm_exit();
+    tvgUpdateCmds(glCanvas.get(), progress);
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
+
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
     //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    tvgtest();
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    //Show the result using EFL...
     elm_init(argc, argv);
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    elm_config_accel_preference_set("gl");
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    Elm_Transit *transit = elm_transit_add();
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        elm_transit_effect_add(transit, transitSwCb, view, nullptr);
+    } else {
+        auto view = createGlView();
+        elm_transit_effect_add(transit, transitGlCb, view, nullptr);
+    }
 
-    Elm_Transit *transit = elm_transit_add();
-    elm_transit_effect_add(transit, transit_cb, img, nullptr);
     elm_transit_duration_set(transit, 2);
     elm_transit_repeat_times_set(transit, -1);
     elm_transit_auto_reverse_set(transit, EINA_TRUE);
@@ -100,5 +164,5 @@ int main(int argc, char **argv)
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
diff --git a/test/testGradient.cpp b/test/testGradient.cpp
deleted file mode 100644 (file)
index d20cce9..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-#include <thorvg.h>
-
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-int main(int argc, char **argv)
-{
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen(buffer, WIDTH, HEIGHT);
-
-    //Prepare a Shape
-    auto shape1 = tvg::Shape::gen();
-    shape1->rect(0, 0, 400, 400, 0.1);        //x, y, w, h, corner_radius
-
-    //Linear Gradient Fill
-    auto fill1 = tvg::LinearFill::gen();
-    fill1->range(fill1, 0, 0, 400, 400);      //from(x, y), to(x, y)
-    fill1->color(0, 255, 0, 0, 255);          //color Stop 0: Red
-    fill1->color(0.5, 0, 255, 0, 255);        //color Stop 1: Green
-    fill1->color(1, 0, 0, 255, 255);          //color Stop 2: Blue
-    shape1.fill(fill1);
-
-    canvas->push(move(shape1));
-
-    //Prepare Circle
-    auto shape2 = tvg::Shape::gen();
-    shape2->circle(400, 400, 200);            //cx, cy, radius
-
-    //Radial Gradient Fill
-    auto fill2 = tvg::RadialFill::gen();
-    fill2->range(400, 400, 200);              //center(x, y), radius
-    fill2->color(0, 255, 0, 0, 255);          //color Stop 0: Red
-    fill2->color(0.5, 0, 255, 0, 255);        //color Stop 1: Green
-    fill2->color(1, 0, 0, 255, 255);          //color Stop 2: Blue
-    shape2.fill(fill2);
-
-    canvas->push(move(shape2));
-
-    //Draw the Shapes onto the Canvas
-    canvas->draw();
-    canvas->sync();
-
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
index 1b5137b..b77062b 100644 (file)
@@ -1,23 +1,14 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 tvg::Shape* pShape = nullptr;
 tvg::Shape* pShape2 = nullptr;
 tvg::Shape* pShape3 = nullptr;
 
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Shape1
     auto shape = tvg::Shape::gen();
 
@@ -88,13 +79,9 @@ void tvgtest()
     shape3->fill(move(fill3));
     shape3->translate(400, 400);
     canvas->push(move(shape3));
-
-    //Draw first frame
-    canvas->draw();
-    canvas->sync();
 }
 
-void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+void tvgUpdateCmds(tvg::Canvas* canvas, float progress)
 {
     /* Update shape directly.
        You can update only necessary properties of this shape,
@@ -116,46 +103,124 @@ void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progres
     pShape3->rotate(-360 * progress);
     pShape3->scale(0.5 + progress);
     canvas->update(pShape3);
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
 
-    //Draw Next frames
-    canvas->draw();
-    canvas->sync();
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void transitSwCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+{
+    tvgUpdateCmds(swCanvas.get(), progress);
 
     //Update Efl Canvas
     Eo* img = (Eo*) effect;
     evas_object_image_data_update_add(img, 0, 0, WIDTH, HEIGHT);
+    evas_object_image_pixels_dirty_set(img, EINA_TRUE);
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void transitGlCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
 {
-    elm_exit();
+    tvgUpdateCmds(glCanvas.get(), progress);
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
+
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
     //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    tvgtest();
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    //Show the result using EFL...
     elm_init(argc, argv);
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    elm_config_accel_preference_set("gl");
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    Elm_Transit *transit = elm_transit_add();
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        elm_transit_effect_add(transit, transitSwCb, view, nullptr);
+    } else {
+        auto view = createGlView();
+        elm_transit_effect_add(transit, transitGlCb, view, nullptr);
+    }
 
-    Elm_Transit *transit = elm_transit_add();
-    elm_transit_effect_add(transit, transit_cb, img, nullptr);
     elm_transit_duration_set(transit, 2);
     elm_transit_repeat_times_set(transit, -1);
     elm_transit_auto_reverse_set(transit, EINA_TRUE);
@@ -165,5 +230,5 @@ int main(int argc, char **argv)
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index ed0d31d..36251f5 100644 (file)
@@ -1,21 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
     canvas->reserve(3);                          //reserve 3 shape nodes (optional)
 
     //Prepare Round Rectangle
@@ -75,40 +65,108 @@ void tvgtest()
 
     shape3->fill(move(fill3));
     canvas->push(move(shape3));
+}
 
-    //Draw the Shapes onto the Canvas
-    canvas->draw();
-    canvas->sync();
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawSwView(void* data, Eo* obj)
 {
-   elm_exit();
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 02101ed..195547d 100644 (file)
@@ -1,21 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
     canvas->reserve(3);                          //reserve 3 shape nodes (optional)
 
     //Prepare Round Rectangle
@@ -35,40 +25,108 @@ void tvgtest()
     shape3->appendCircle(600, 600, 150, 100);    //cx, cy, radiusW, radiusH
     shape3->fill(0, 255, 255, 255);              //r, g, b, a
     canvas->push(move(shape3));
+}
 
-    //Draw the Shapes onto the Canvas
-    canvas->draw();
-    canvas->sync();
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawSwView(void* data, Eo* obj)
 {
-   elm_exit();
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index a5bdc9e..49bd738 100644 (file)
@@ -1,22 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Star
     auto shape1 = tvg::Shape::gen();
 
@@ -51,39 +40,107 @@ void tvgtest()
     shape2->cubicTo(cx - radius, cy - halfRadius, cx - halfRadius, cy - radius, cx, cy - radius);
     shape2->fill(255, 0, 0, 255);
     canvas->push(move(shape2));
+}
 
-    canvas->draw();
-    canvas->sync();
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawSwView(void* data, Eo* obj)
 {
-   elm_exit();
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index fc3395e..b619f78 100644 (file)
@@ -1,22 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     /* Star */
 
     //Prepare Path Commands
@@ -91,39 +80,107 @@ void tvgtest()
     shape2->appendPath(cmds2, 6, pts2, 13);     //copy path data
     shape2->fill(255, 255, 0, 255);
     canvas->push(move(shape2));
+}
 
-    canvas->draw();
-    canvas->sync();
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawSwView(void* data, Eo* obj)
 {
-   elm_exit();
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 841c6e1..f12777c 100644 (file)
@@ -1,21 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
     canvas->reserve(3);                          //reserve 3 shape nodes (optional)
 
     //Prepare Round Rectangle
@@ -75,40 +65,108 @@ void tvgtest()
 
     shape3->fill(move(fill3));
     canvas->push(move(shape3));
+}
 
-    //Draw the Shapes onto the Canvas
-    canvas->draw();
-    canvas->sync();
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawSwView(void* data, Eo* obj)
 {
-   elm_exit();
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
+
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index c5672c7..e16772a 100644 (file)
@@ -1,22 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Create a Scene
     auto scene = tvg::Scene::gen();
     scene->reserve(3);   //reserve 3 shape nodes (optional)
@@ -83,39 +72,108 @@ void tvgtest()
 
     //Draw the Scene onto the Canvas
     canvas->push(move(scene));
-    canvas->draw();
-    canvas->sync();
+}
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawGLview(Evas_Object *obj)
 {
-   elm_exit();
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
 
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 07879c1..7bd8b41 100644 (file)
@@ -1,22 +1,13 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 tvg::Scene* pScene1 = nullptr;
 tvg::Scene* pScene2 = nullptr;
 
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Create a Scene1
     auto scene = tvg::Scene::gen();
     pScene1 = scene.get();
@@ -94,12 +85,9 @@ void tvgtest()
 
     //Draw the Scene onto the Canvas
     canvas->push(move(scene));
-
-    canvas->draw();
-    canvas->sync();
 }
 
-void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+void tvgUpdateCmds(tvg::Canvas* canvas, float progress)
 {
     /* Update scene directly.
        You can update only necessary properties of this scene,
@@ -110,53 +98,132 @@ void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progres
 
     //Update shape for drawing (this may work asynchronously)
     canvas->update(pScene1);
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
 
-    //Draw Next frames
-    canvas->draw();
-    canvas->sync();
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void transitSwCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+{
+    tvgUpdateCmds(swCanvas.get(), progress);
 
     //Update Efl Canvas
     Eo* img = (Eo*) effect;
     evas_object_image_data_update_add(img, 0, 0, WIDTH, HEIGHT);
+    evas_object_image_pixels_dirty_set(img, EINA_TRUE);
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void transitGlCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
 {
-    elm_exit();
+    tvgUpdateCmds(glCanvas.get(), progress);
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
+
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
     //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    tvgtest();
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    //Show the result using EFL...
     elm_init(argc, argv);
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    elm_config_accel_preference_set("gl");
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    Elm_Transit *transit = elm_transit_add();
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        elm_transit_effect_add(transit, transitSwCb, view, nullptr);
+    } else {
+        auto view = createGlView();
+        elm_transit_effect_add(transit, transitGlCb, view, nullptr);
+    }
 
-    Elm_Transit *transit = elm_transit_add();
-    elm_transit_effect_add(transit, transit_cb, img, nullptr);
     elm_transit_duration_set(transit, 2);
     elm_transit_repeat_times_set(transit, -1);
+    elm_transit_auto_reverse_set(transit, EINA_TRUE);
     elm_transit_go(transit);
 
     elm_run();
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index cd1bab1..9aa284d 100644 (file)
@@ -1,13 +1,10 @@
-#include <thorvg.h>
-#include <iostream>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-unique_ptr<tvg::Paint> tvgDrawCmds()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
     //Prepare a Shape (Rectangle + Rectangle + Circle + Circle)
     auto shape1 = tvg::Shape::gen();
@@ -17,62 +14,55 @@ unique_ptr<tvg::Paint> tvgDrawCmds()
     shape1->appendCircle(400, 500, 170, 100);       //cx, cy, radiusW, radiusH
     shape1->fill(255, 255, 0, 255);                 //r, g, b, a
 
-    return move(shape1);
+    canvas->push(move(shape1));
 }
 
+
 /************************************************************************/
 /* Sw Engine Test Code                                                  */
 /************************************************************************/
 
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
 void tvgSwTest(uint32_t* buffer)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
     //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
 
     /* Push the shape into the Canvas drawing list
        When this shape is into the canvas list, the shape could update & prepare
        internal data asynchronously for coming rendering.
        Canvas keeps this shape node unless user call canvas->clear() */
-    canvas->push(tvgDrawCmds());
-    canvas->draw();
-    canvas->sync();
+    tvgDrawCmds(swCanvas.get());
+}
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
 }
 
+
 /************************************************************************/
 /* GL Engine Test Code                                                  */
 /************************************************************************/
 
-static unique_ptr<tvg::GlCanvas> canvas;
+static unique_ptr<tvg::GlCanvas> glCanvas;
 
 void initGLview(Evas_Object *obj)
 {
     static constexpr auto BPP = 4;
 
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Gl);
-
     //Create a Canvas
-    canvas = tvg::GlCanvas::gen();
-    canvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
 
     /* Push the shape into the Canvas drawing list
        When this shape is into the canvas list, the shape could update & prepare
        internal data asynchronously for coming rendering.
        Canvas keeps this shape node unless user call canvas->clear() */
-    canvas->push(tvgDrawCmds());
-}
-
-void delGLview(Evas_Object *obj)
-{
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Gl);
+    tvgDrawCmds(glCanvas.get());
 }
 
 void drawGLview(Evas_Object *obj)
@@ -87,65 +77,46 @@ void drawGLview(Evas_Object *obj)
     gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
     gl->glEnable(GL_BLEND);
 
-    canvas->draw();
-    canvas->sync();
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
+
 /************************************************************************/
-/* Common Infrastructure Code                                           */
+/* Main Code                                                            */
 /************************************************************************/
 
-void win_del(void *data, Evas_Object *o, void *ev)
-{
-   elm_exit();
-}
-
 int main(int argc, char **argv)
 {
-    bool swEngine = true;
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
     if (argc > 1) {
-        if (!strcmp(argv[1], "gl")) swEngine = false;
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
     }
 
-    if (swEngine) cout << "engine: software" << endl;
-    else cout << "engine: opengl" << endl;
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
     elm_init(argc, argv);
 
-    //Show the result using EFL...
     elm_config_accel_preference_set("gl");
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
-
-    Eo* viewer;
-
-    if (swEngine) {
-        static uint32_t buffer[WIDTH * HEIGHT];
-        viewer = evas_object_image_filled_add(evas_object_evas_get(win));
-        evas_object_image_size_set(viewer, WIDTH, HEIGHT);
-        evas_object_image_data_set(viewer, buffer);
-        evas_object_size_hint_weight_set(viewer, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-        evas_object_show(viewer);
-        tvgSwTest(buffer);
-    //GlEngine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
     } else {
-        viewer = elm_glview_add(win);
-        evas_object_size_hint_weight_set(viewer, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-        elm_glview_mode_set(viewer, ELM_GLVIEW_ALPHA);
-        elm_glview_resize_policy_set(viewer, ELM_GLVIEW_RESIZE_POLICY_RECREATE);
-        elm_glview_render_policy_set(viewer, ELM_GLVIEW_RENDER_POLICY_ON_DEMAND);
-        elm_glview_init_func_set(viewer, initGLview);
-        elm_glview_del_func_set(viewer, delGLview);
-        elm_glview_render_func_set(viewer, drawGLview);
-        evas_object_show(viewer);
+        createGlView();
     }
 
-    elm_win_resize_object_add(win, viewer);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
-
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index bc50dca..493bbde 100644 (file)
@@ -1,23 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Shape 1
     auto shape1 = tvg::Shape::gen();
     shape1->appendRect(50, 50, 200, 200, 0);
@@ -74,40 +62,108 @@ void tvgtest()
     shape6->stroke(4);
 
     canvas->push(move(shape6));
+}
 
 
-    canvas->draw();
-    canvas->sync();
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawGLview(Evas_Object *obj)
 {
-   elm_exit();
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 559479d..d57bf1f 100644 (file)
@@ -1,22 +1,11 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
-
-    //Create a Canvas
-    auto canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Test for Stroke Width
     for (int i = 0; i < 10; ++i) {
         auto shape = tvg::Shape::gen();
@@ -28,7 +17,6 @@ void tvgtest()
         canvas->push(move(shape));
     }
 
-
     //Test for StrokeJoin & StrokeCap
     auto shape1 = tvg::Shape::gen();
     shape1->moveTo(20, 350);
@@ -111,39 +99,108 @@ void tvgtest()
     float dashPattern3[2] = {10, 10};
     shape6->stroke(dashPattern3, 2);
     canvas->push(move(shape6));
+}
 
-    canvas->draw();
-    canvas->sync();
 
-    //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void drawGLview(Evas_Object *obj)
 {
-   elm_exit();
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
-    tvgtest();
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    elm_init(argc, argv);
+
+    elm_config_accel_preference_set("gl");
+
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
-}
+
+    //Terminate ThorVG Engine
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 1ae4fe0..938d37a 100644 (file)
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
+#define NUM_PER_LINE 3
 
-static uint32_t buffer[WIDTH * HEIGHT];
-
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
+int x = 30;
+int y = 30;
 int count = 0;
-static const int numberPerLine = 3;
-
-static int x = 30;
-static int y = 30;
-
 
 void svgDirCallback(const char* name, const char* path, void* data)
 {
+    tvg::Canvas* canvas = static_cast<tvg::Canvas*>(data);
+
     auto scene = tvg::Scene::gen();
+
     char buf[255];
     sprintf(buf,"%s/%s", path, name);
+
     scene->load(buf);
-    printf("SVG Load : %s\n", buf);
-    scene->translate(((WIDTH - (x * 2)) / numberPerLine) * (count % numberPerLine) + x, ((HEIGHT - (y * 2))/ numberPerLine) * (int)((float)count / (float)numberPerLine) + y);
+    scene->translate(((WIDTH - (x * 2)) / NUM_PER_LINE) * (count % NUM_PER_LINE) + x, ((HEIGHT - (y * 2))/ NUM_PER_LINE) * (int)((float)count / (float)NUM_PER_LINE) + y);    
     canvas->push(move(scene));
+
     count++;
+
+    cout << "SVG: " << buf << endl;
 }
 
+void tvgDrawCmds(tvg::Canvas* canvas)
+{
+    auto shape1 = tvg::Shape::gen();
+    shape1->appendRect(0, 0, WIDTH, HEIGHT, 0);       //x, y, w, h, cornerRadius
+    shape1->fill(255, 255, 255, 255);                 //r, g, b, a
 
-void win_del(void* data, Evas_Object* o, void* ev)
+    canvas->push(move(shape1));
+
+    eina_file_dir_list("./svgs", EINA_TRUE, svgDirCallback, canvas);
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
+
+void tvgSwTest(uint32_t* buffer)
 {
-   elm_exit();
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
 }
 
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
 
-int main(int argc, char** argv)
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
 {
-    //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    static constexpr auto BPP = 4;
 
     //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
 
-    //Draw white background
-    auto scene = tvg::Scene::gen();
-    auto shape1 = tvg::Shape::gen();
-    shape1->appendRect(0, 0, WIDTH, HEIGHT, 0);
-    shape1->fill(255, 255, 255, 255);
-    scene->push(move(shape1));
-    canvas->push(move(scene));
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
+}
 
-    eina_file_dir_list("./svgs", EINA_TRUE, svgDirCallback, NULL);
 
-    canvas->draw();
-    canvas->sync();
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
 
-    //Show the result using EFL...
-    elm_init(argc, argv);
+int main(int argc, char **argv)
+{
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
+    //Initialize ThorVG Engine
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
+
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
+
+    elm_init(argc, argv);
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    elm_config_accel_preference_set("gl");
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        createSwView();
+    } else {
+        createGlView();
+    }
 
     elm_run();
     elm_shutdown();
index dd3423a..c017f24 100644 (file)
@@ -1,23 +1,14 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
-
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 tvg::Shape* pShape = nullptr;
 tvg::Shape* pShape2 = nullptr;
 tvg::Shape* pShape3 = nullptr;
 
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Shape1
     auto shape = tvg::Shape::gen();
 
@@ -51,13 +42,9 @@ void tvgtest()
     shape3->fill(255, 0, 255, 255);
     shape3->translate(400, 400);
     canvas->push(move(shape3));
-
-    //Draw first frame
-    canvas->draw();
-    canvas->sync();
 }
 
-void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+void tvgUpdateCmds(tvg::Canvas* canvas, float progress)
 {
     /* Update shape directly.
        You can update only necessary properties of this shape,
@@ -79,46 +66,124 @@ void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progres
     pShape3->rotate(-360 * progress);
     pShape3->scale(0.5 + progress);
     canvas->update(pShape3);
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
 
-    //Draw Next frames
-    canvas->draw();
-    canvas->sync();
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void transitSwCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+{
+    tvgUpdateCmds(swCanvas.get(), progress);
 
     //Update Efl Canvas
     Eo* img = (Eo*) effect;
     evas_object_image_data_update_add(img, 0, 0, WIDTH, HEIGHT);
+    evas_object_image_pixels_dirty_set(img, EINA_TRUE);
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void transitGlCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
 {
-    elm_exit();
+    tvgUpdateCmds(glCanvas.get(), progress);
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
+
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
     //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    tvgtest();
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    //Show the result using EFL...
     elm_init(argc, argv);
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    elm_config_accel_preference_set("gl");
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    Elm_Transit *transit = elm_transit_add();
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        elm_transit_effect_add(transit, transitSwCb, view, nullptr);
+    } else {
+        auto view = createGlView();
+        elm_transit_effect_add(transit, transitGlCb, view, nullptr);
+    }
 
-    Elm_Transit *transit = elm_transit_add();
-    elm_transit_effect_add(transit, transit_cb, img, nullptr);
     elm_transit_duration_set(transit, 2);
     elm_transit_repeat_times_set(transit, -1);
     elm_transit_auto_reverse_set(transit, EINA_TRUE);
@@ -128,5 +193,5 @@ int main(int argc, char **argv)
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file
index 3a39913..d28207a 100644 (file)
@@ -1,32 +1,19 @@
-#include <thorvg.h>
-#include <Elementary.h>
+#include "testCommon.h"
 
-using namespace std;
+/************************************************************************/
+/* Drawing Commands                                                     */
+/************************************************************************/
 
-#define WIDTH 800
-#define HEIGHT 800
-
-static uint32_t buffer[WIDTH * HEIGHT];
-unique_ptr<tvg::SwCanvas> canvas = nullptr;
-
-void tvgtest()
+void tvgDrawCmds(tvg::Canvas* canvas)
 {
-    //Create a Canvas
-    canvas = tvg::SwCanvas::gen();
-    canvas->target(buffer, WIDTH, WIDTH, HEIGHT);
-
     //Shape
     auto shape = tvg::Shape::gen();
     shape->appendRect(-100, -100, 200, 200, 0);
     shape->fill(255, 255, 255, 255);
     canvas->push(move(shape));
-
-    //Draw first frame
-    canvas->draw();
-    canvas->sync();
 }
 
-void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+void tvgUpdateCmds(tvg::Canvas* canvas, float progress)
 {
     //Explicitly clear all retained paint nodes.
     canvas->clear();
@@ -40,46 +27,124 @@ void transit_cb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progres
     shape->rotate(360 * progress);
 
     canvas->push(move(shape));
+}
+
+
+/************************************************************************/
+/* Sw Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::SwCanvas> swCanvas;
 
-    //Draw Next frames
-    canvas->draw();
-    canvas->sync();
+void tvgSwTest(uint32_t* buffer)
+{
+    //Create a Canvas
+    swCanvas = tvg::SwCanvas::gen();
+    swCanvas->target(buffer, WIDTH, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(swCanvas.get());
+}
+
+void transitSwCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
+{
+    tvgUpdateCmds(swCanvas.get(), progress);
 
     //Update Efl Canvas
     Eo* img = (Eo*) effect;
     evas_object_image_data_update_add(img, 0, 0, WIDTH, HEIGHT);
+    evas_object_image_pixels_dirty_set(img, EINA_TRUE);
+}
+
+void drawSwView(void* data, Eo* obj)
+{
+    swCanvas->draw();
+    swCanvas->sync();
+}
+
+
+/************************************************************************/
+/* GL Engine Test Code                                                  */
+/************************************************************************/
+
+static unique_ptr<tvg::GlCanvas> glCanvas;
+
+void initGLview(Evas_Object *obj)
+{
+    static constexpr auto BPP = 4;
+
+    //Create a Canvas
+    glCanvas = tvg::GlCanvas::gen();
+    glCanvas->target(nullptr, WIDTH * BPP, WIDTH, HEIGHT);
+
+    /* Push the shape into the Canvas drawing list
+       When this shape is into the canvas list, the shape could update & prepare
+       internal data asynchronously for coming rendering.
+       Canvas keeps this shape node unless user call canvas->clear() */
+    tvgDrawCmds(glCanvas.get());
+}
+
+void drawGLview(Evas_Object *obj)
+{
+    auto gl = elm_glview_gl_api_get(obj);
+    int w, h;
+    elm_glview_size_get(obj, &w, &h);
+    gl->glViewport(0, 0, w, h);
+    gl->glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
+    gl->glClear(GL_COLOR_BUFFER_BIT);
+    gl->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+    gl->glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE);
+    gl->glEnable(GL_BLEND);
+
+    glCanvas->draw();
+    glCanvas->sync();
 }
 
-void win_del(void *data, Evas_Object *o, void *ev)
+void transitGlCb(Elm_Transit_Effect *effect, Elm_Transit* transit, double progress)
 {
-    elm_exit();
+    tvgUpdateCmds(glCanvas.get(), progress);
 }
 
+
+/************************************************************************/
+/* Main Code                                                            */
+/************************************************************************/
+
 int main(int argc, char **argv)
 {
+    tvg::CanvasEngine tvgEngine = tvg::CanvasEngine::Sw;
+
+    if (argc > 1) {
+        if (!strcmp(argv[1], "gl")) tvgEngine = tvg::CanvasEngine::Gl;
+    }
+
     //Initialize ThorVG Engine
-    tvg::Initializer::init(tvg::CanvasEngine::Sw);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        cout << "tvg engine: software" << endl;
+    } else {
+        cout << "tvg engine: opengl" << endl;
+    }
 
-    tvgtest();
+    //Initialize ThorVG Engine
+    tvg::Initializer::init(tvgEngine);
 
-    //Show the result using EFL...
     elm_init(argc, argv);
 
-    Eo* win = elm_win_util_standard_add(NULL, "ThorVG Test");
-    evas_object_smart_callback_add(win, "delete,request", win_del, 0);
+    elm_config_accel_preference_set("gl");
 
-    Eo* img = evas_object_image_filled_add(evas_object_evas_get(win));
-    evas_object_image_size_set(img, WIDTH, HEIGHT);
-    evas_object_image_data_set(img, buffer);
-    evas_object_size_hint_weight_set(img, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
-    evas_object_show(img);
+    Elm_Transit *transit = elm_transit_add();
 
-    elm_win_resize_object_add(win, img);
-    evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT);
-    evas_object_show(win);
+    if (tvgEngine == tvg::CanvasEngine::Sw) {
+        auto view = createSwView();
+        elm_transit_effect_add(transit, transitSwCb, view, nullptr);
+    } else {
+        auto view = createGlView();
+        elm_transit_effect_add(transit, transitGlCb, view, nullptr);
+    }
 
-    Elm_Transit *transit = elm_transit_add();
-    elm_transit_effect_add(transit, transit_cb, img, nullptr);
     elm_transit_duration_set(transit, 2);
     elm_transit_repeat_times_set(transit, -1);
     elm_transit_auto_reverse_set(transit, EINA_TRUE);
@@ -89,5 +154,5 @@ int main(int argc, char **argv)
     elm_shutdown();
 
     //Terminate ThorVG Engine
-    tvg::Initializer::term(tvg::CanvasEngine::Sw);
-}
+    tvg::Initializer::term(tvgEngine);
+}
\ No newline at end of file