diff --git a/.gitignore b/.gitignore index e5a2d6eb..29175734 100644 --- a/.gitignore +++ b/.gitignore @@ -9,4 +9,5 @@ testPathCopy testBlending testUpdate testDirectUpdate +testScene testTransform diff --git a/inc/tizenvg.h b/inc/tizenvg.h index e9a501ad..63da89fc 100644 --- a/inc/tizenvg.h +++ b/inc/tizenvg.h @@ -56,6 +56,7 @@ namespace tvg enum class TIZENVG_EXPORT PathCommand { Close, MoveTo, LineTo, CubicTo }; class RenderMethod; +class Scene; struct Point { @@ -107,6 +108,7 @@ public: virtual int draw(bool async = true) noexcept; virtual int sync() = 0; + _TIZENVG_DECLARE_ACCESSOR(Scene); _TIZENVG_DECLARE_PRIVATE(Canvas); }; @@ -149,8 +151,9 @@ public: static std::unique_ptr gen() noexcept; - _TIZENVG_DECLARE_PRIVATE(Shape); + _TIZENVG_DECLARE_ACCESSOR(Scene); _TIZENVG_DECLARE_ACCESSOR(Canvas); + _TIZENVG_DECLARE_PRIVATE(Shape); }; @@ -167,7 +170,8 @@ class TIZENVG_EXPORT Scene final : public Paint public: ~Scene(); - int push(std::unique_ptr shape) noexcept; + int push(std::unique_ptr shape) noexcept; + int reserve(size_t size) noexcept; int rotate(float degree) noexcept override; int scale(float factor) noexcept override; @@ -179,6 +183,7 @@ public: static std::unique_ptr gen() noexcept; _TIZENVG_DECLARE_PRIVATE(Scene); + _TIZENVG_DECLARE_ACCESSOR(Canvas); }; diff --git a/src/lib/meson.build b/src/lib/meson.build index a2ef7433..0a56f0dd 100644 --- a/src/lib/meson.build +++ b/src/lib/meson.build @@ -7,6 +7,7 @@ source_file = [ 'tvgShapePath.h', 'tvgShapeImpl.h', 'tvgCanvasImpl.h', + 'tvgSceneImpl.h', 'tvgEngine.cpp', 'tvgCanvas.cpp', 'tvgSwCanvas.cpp', diff --git a/src/lib/tvgCanvasImpl.h b/src/lib/tvgCanvasImpl.h index f70753a4..20a5efd0 100644 --- a/src/lib/tvgCanvasImpl.h +++ b/src/lib/tvgCanvasImpl.h @@ -18,7 +18,6 @@ #define _TVG_CANVAS_IMPL_H_ #include "tvgCommon.h" -#include "tvgShapeImpl.h" /************************************************************************/ /* Internal Class Implementation */ @@ -55,9 +54,9 @@ struct Canvas::Impl for (auto paint : paints) { if (auto scene = dynamic_cast(paint)) { - cout << "TODO: " << scene << endl; + if (!SCENE_IMPL->clear(*renderer)) return -1; } else if (auto shape = dynamic_cast(paint)) { - if (!shape->pImpl.get()->dispose(*shape, *renderer)) return -1; + if (!SHAPE_IMPL->dispose(*shape, *renderer)) return -1; } delete(paint); } @@ -72,9 +71,9 @@ struct Canvas::Impl for(auto paint: paints) { if (auto scene = dynamic_cast(paint)) { - cout << "TODO: " << scene << endl; + if (!SCENE_IMPL->update(*renderer)) return -1; } else if (auto shape = dynamic_cast(paint)) { - if (!shape->pImpl.get()->update(*shape, *renderer)) return -1; + if (!SHAPE_IMPL->update(*shape, *renderer)) return -1; } } return 0; @@ -85,9 +84,9 @@ struct Canvas::Impl assert(renderer); if (auto scene = dynamic_cast(paint)) { - cout << "TODO: " << scene << endl; + if (!SCENE_IMPL->update(*renderer)) return -1; } else if (auto shape = dynamic_cast(paint)) { - if (!shape->pImpl.get()->update(*shape, *renderer)) return -1; + if (!SHAPE_IMPL->update(*shape, *renderer)) return -1; } return 0; } @@ -101,9 +100,9 @@ struct Canvas::Impl for(auto paint: paints) { if (auto scene = dynamic_cast(paint)) { - cout << "TODO: " << scene << endl; + if(!SCENE_IMPL->render(*renderer)) return -1; } else if (auto shape = dynamic_cast(paint)) { - if(!shape->pImpl.get()->render(*shape, *renderer)) return -1; + if(!SHAPE_IMPL->render(*shape, *renderer)) return -1; } } return 0; diff --git a/src/lib/tvgCommon.h b/src/lib/tvgCommon.h index c3f0c568..c404f1fa 100644 --- a/src/lib/tvgCommon.h +++ b/src/lib/tvgCommon.h @@ -24,9 +24,16 @@ #include #include #include "tizenvg.h" -#include "tvgRenderCommon.h" using namespace std; using namespace tvg; +#define SCENE_IMPL scene->pImpl.get() +#define SHAPE_IMPL shape->pImpl.get() + +#include "tvgRenderCommon.h" +#include "tvgShapePath.h" +#include "tvgShapeImpl.h" +#include "tvgSceneImpl.h" + #endif //_TVG_COMMON_H_ diff --git a/src/lib/tvgScene.cpp b/src/lib/tvgScene.cpp index bc26a99b..9b9844bd 100644 --- a/src/lib/tvgScene.cpp +++ b/src/lib/tvgScene.cpp @@ -19,17 +19,6 @@ #include "tvgCommon.h" -/************************************************************************/ -/* Internal Class Implementation */ -/************************************************************************/ - -struct Scene::Impl -{ - -}; - - - /************************************************************************/ /* External Class Implementation */ /************************************************************************/ @@ -42,7 +31,6 @@ Scene::Scene() : pImpl(make_unique()) Scene::~Scene() { - cout << "Scene(" << this << ") destroyed!" << endl; } @@ -52,8 +40,26 @@ unique_ptr Scene::gen() noexcept } -int Scene::push(unique_ptr shape) noexcept +int Scene::push(unique_ptr paint) noexcept { + auto impl = pImpl.get(); + assert(impl); + + auto p = paint.release(); + assert(p); + impl->paints.push_back(p); + + return 0; +} + + +int Scene::reserve(size_t size) noexcept +{ + auto impl = pImpl.get(); + assert(impl); + + impl->paints.reserve(size); + return 0; } diff --git a/src/lib/tvgSceneImpl.h b/src/lib/tvgSceneImpl.h new file mode 100644 index 00000000..31a36147 --- /dev/null +++ b/src/lib/tvgSceneImpl.h @@ -0,0 +1,76 @@ +/* + * Copyright (c) 2020 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ +#ifndef _TVG_SCENE_IMPL_H_ +#define _TVG_SCENE_IMPL_H_ + +#include "tvgCommon.h" + +/************************************************************************/ +/* Internal Class Implementation */ +/************************************************************************/ + +struct Scene::Impl +{ + vector paints; + + ~Impl() + { + //Are you sure clear() prior to this? + assert(paints.empty()); + } + + bool clear(RenderMethod& renderer) + { + for (auto paint : paints) { + if (auto scene = dynamic_cast(paint)) { + if (!SCENE_IMPL->clear(renderer)) return false; + } else if (auto shape = dynamic_cast(paint)) { + if (!SHAPE_IMPL->dispose(*shape, renderer)) return false; + } + delete(paint); + } + paints.clear(); + + return true; + } + + bool update(RenderMethod &renderer) + { + for(auto paint: paints) { + if (auto scene = dynamic_cast(paint)) { + if (!SCENE_IMPL->update(renderer)) return false; + } else if (auto shape = dynamic_cast(paint)) { + if (!SHAPE_IMPL->update(*shape, renderer)) return false; + } + } + return true; + } + + bool render(RenderMethod &renderer) + { + for(auto paint: paints) { + if (auto scene = dynamic_cast(paint)) { + if(!SCENE_IMPL->render(renderer)) return false; + } else if (auto shape = dynamic_cast(paint)) { + if(!SHAPE_IMPL->render(*shape, renderer)) return false; + } + } + return true; + } +}; + +#endif //_TVG_SCENE_IMPL_H_ \ No newline at end of file diff --git a/src/lib/tvgShapeImpl.h b/src/lib/tvgShapeImpl.h index f1bb1ebc..63b74773 100644 --- a/src/lib/tvgShapeImpl.h +++ b/src/lib/tvgShapeImpl.h @@ -18,7 +18,6 @@ #define _TVG_SHAPE_IMPL_H_ #include "tvgCommon.h" -#include "tvgShapePath.h" /************************************************************************/ /* Internal Class Implementation */ diff --git a/test/makefile b/test/makefile index 4c780680..e437084c 100644 --- a/test/makefile +++ b/test/makefile @@ -7,4 +7,5 @@ all: gcc -o testBlending testBlending.cpp -g -lstdc++ `pkg-config --cflags --libs elementary tizenvg` gcc -o testUpdate testUpdate.cpp -g -lstdc++ `pkg-config --cflags --libs elementary tizenvg` gcc -o testDirectUpdate testDirectUpdate.cpp -g -lstdc++ `pkg-config --cflags --libs elementary tizenvg` + gcc -o testScene testScene.cpp -g -lstdc++ `pkg-config --cflags --libs elementary tizenvg` gcc -o testTransform testTransform.cpp -g -lstdc++ `pkg-config --cflags --libs elementary tizenvg` diff --git a/test/testScene.cpp b/test/testScene.cpp index 3232b659..f7c9ea5b 100644 --- a/test/testScene.cpp +++ b/test/testScene.cpp @@ -1,4 +1,5 @@ #include +#include using namespace std; @@ -7,39 +8,79 @@ using namespace std; static uint32_t buffer[WIDTH * HEIGHT]; -int main(int argc, char **argv) +void tvgtest() { //Initialize TizenVG Engine tvg::Engine::init(); //Create a Canvas - auto canvas = tvg::SwCanvas::gen(buffer, WIDTH, HEIGHT); + 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) - //Shape1 + //Prepare Round Rectangle auto shape1 = tvg::Shape::gen(); - shape1->rect(0, 0, 400, 400, 0.1); - shape1->fill(255, 0, 0, 255); - shape1->rotate(0, 0, 45); //axis x, y, z + shape1->appendRect(0, 0, 400, 400, 50); //x, y, w, h, cornerRadius + shape1->fill(0, 255, 0, 255); //r, g, b, a scene->push(move(shape1)); - //Shape2 + //Prepare Circle auto shape2 = tvg::Shape::gen(); - shape2->rect(0, 0, 400, 400, 0.1); - shape2->fill(0, 255, 0, 255); - shape2->transform(matrix); //by matrix (var matrix[4 * 4];) + shape2->appendCircle(400, 400, 200, 200); //cx, cy, radiusW, radiusH + shape2->fill(255, 255, 0, 255); //r, g, b, a scene->push(move(shape2)); - //Shape3 + //Prepare Ellipse auto shape3 = tvg::Shape::gen(); - shape3->rect(0, 0, 400, 400, 0.1); - shape3->fill(0, 0, 255, 255); - shape3->origin(100, 100); //offset + shape3->appendCircle(600, 600, 150, 100); //cx, cy, radiusW, radiusH + shape3->fill(0, 255, 255, 255); //r, g, b, a scene->push(move(shape3)); + //Create another Scene + auto scene2 = tvg::Scene::gen(); + scene2->reserve(2); //reserve 2 shape nodes (optional) + + //Star + auto shape4 = tvg::Shape::gen(); + + //Appends Paths + shape4->moveTo(199, 34); + shape4->lineTo(253, 143); + shape4->lineTo(374, 160); + shape4->lineTo(287, 244); + shape4->lineTo(307, 365); + shape4->lineTo(199, 309); + shape4->lineTo(97, 365); + shape4->lineTo(112, 245); + shape4->lineTo(26, 161); + shape4->lineTo(146, 143); + shape4->close(); + shape4->fill(0, 0, 255, 255); + scene2->push(move(shape4)); + + //Circle + auto shape5 = tvg::Shape::gen(); + + auto cx = 550.0f; + auto cy = 550.0f; + auto radius = 125.0f; + auto halfRadius = radius * 0.552284f; + + //Append Paths + shape5->moveTo(cx, cy - radius); + shape5->cubicTo(cx + halfRadius, cy - radius, cx + radius, cy - halfRadius, cx + radius, cy); + shape5->cubicTo(cx + radius, cy + halfRadius, cx + halfRadius, cy + radius, cx, cy+ radius); + shape5->cubicTo(cx - halfRadius, cy + radius, cx - radius, cy + halfRadius, cx - radius, cy); + shape5->cubicTo(cx - radius, cy - halfRadius, cx - halfRadius, cy - radius, cx, cy - radius); + shape5->fill(255, 0, 0, 255); + scene2->push(move(shape5)); + + //Push scene2 onto the scene + scene->push(move(scene2)); + //Draw the Scene onto the Canvas canvas->push(move(scene)); canvas->draw(); @@ -48,3 +89,34 @@ int main(int argc, char **argv) //Terminate TizenVG Engine tvg::Engine::term(); } + +void +win_del(void *data, Evas_Object *o, void *ev) +{ + elm_exit(); +} + + +int main(int argc, char **argv) +{ + tvgtest(); + + //Show the result using EFL... + elm_init(argc, argv); + + Eo* win = elm_win_util_standard_add(NULL, "TizenVG Test"); + evas_object_smart_callback_add(win, "delete,request", win_del, 0); + + 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_win_resize_object_add(win, img); + evas_object_geometry_set(win, 0, 0, WIDTH, HEIGHT); + evas_object_show(win); + + elm_run(); + elm_shutdown(); +}