From bdccfb2449512ef52c0cc05b47a7ccbc99854bab Mon Sep 17 00:00:00 2001 From: Jinny You Date: Wed, 23 Jul 2025 17:14:28 +0900 Subject: [PATCH] renderer: support duplicate effects implement effect duplication functionality to enable proper Scene duplication with effects. issue: https://github.com/thorvg/thorvg/issues/3631 Co-Authored-By: Hermet Park --- examples/Duplicate.cpp | 4 ++-- src/renderer/tvgScene.h | 35 ++++++++++++++++++++++++++++++++++- 2 files changed, 36 insertions(+), 3 deletions(-) diff --git a/examples/Duplicate.cpp b/examples/Duplicate.cpp index 77860757..702f575f 100644 --- a/examples/Duplicate.cpp +++ b/examples/Duplicate.cpp @@ -103,9 +103,9 @@ struct UserExample : tvgexam::Example //Duplicate Picture - svg { auto picture1 = tvg::Picture::gen(); - if (!tvgexam::verify(picture1->load(EXAMPLE_DIR"/svg/tiger.svg"))) return false; + if (!tvgexam::verify(picture1->load(EXAMPLE_DIR"/svg/2684.svg"))) return false; picture1->translate(350, 200); - picture1->scale(0.25); + picture1->scale(4); auto picture2 = picture1->duplicate(); picture2->translate(550, 250); diff --git a/src/renderer/tvgScene.h b/src/renderer/tvgScene.h index 8368ce2e..a9fc1ea3 100644 --- a/src/renderer/tvgScene.h +++ b/src/renderer/tvgScene.h @@ -272,7 +272,40 @@ struct SceneImpl : Scene dup->paints.push_back(cdup); } - if (effects) TVGERR("RENDERER", "TODO: Duplicate Effects?"); + if (effects) { + dup->effects = new Array; + ARRAY_FOREACH(p, *effects) { + RenderEffect* ret = nullptr; + switch ((*p)->type) { + case SceneEffect::GaussianBlur: { + ret = new RenderEffectGaussianBlur(*(RenderEffectGaussianBlur*)(*p)); + break; + } + case SceneEffect::DropShadow: { + ret = new RenderEffectDropShadow(*(RenderEffectDropShadow*)(*p)); + break; + } + case SceneEffect::Fill: { + ret = new RenderEffectFill(*(RenderEffectFill*)(*p)); + break; + } + case SceneEffect::Tint: { + ret = new RenderEffectTint(*(RenderEffectTint*)(*p)); + break; + } + case SceneEffect::Tritone: { + ret = new RenderEffectTritone(*(RenderEffectTritone*)(*p)); + break; + } + default: break; + } + if (ret) { + ret->rd = nullptr; + ret->valid = false; + dup->effects->push(ret); + } + } + } return scene; }