From 3862e1d710a5de688ec87507bb3d4ba5fa6b1bb1 Mon Sep 17 00:00:00 2001 From: jmm Date: Mon, 10 Jun 2024 21:46:41 +0900 Subject: [PATCH] Add RenderEffectImpl::SynchronizeBackgroundCornerRadius() Change-Id: I3eedb39693907c128e67e480fb74f28ee622a461 --- .../src/dali-toolkit/utc-Dali-RenderEffect.cpp | 41 +++++++++++++- .../controls/render-effects/blur-effect-impl.cpp | 22 ++++++-- .../controls/render-effects/blur-effect-impl.h | 16 +++--- .../controls/render-effects/render-effect-impl.cpp | 15 +++--- .../internal/graphics/shaders/render-effect.frag | 62 ++++++++++++++++++++++ .../internal/graphics/shaders/render-effect.vert | 14 +++++ .../controls/render-effects/render-effect.cpp | 2 - 7 files changed, 150 insertions(+), 22 deletions(-) create mode 100644 dali-toolkit/internal/graphics/shaders/render-effect.frag create mode 100644 dali-toolkit/internal/graphics/shaders/render-effect.vert diff --git a/automated-tests/src/dali-toolkit/utc-Dali-RenderEffect.cpp b/automated-tests/src/dali-toolkit/utc-Dali-RenderEffect.cpp index 5f1933b..0f0f1db 100644 --- a/automated-tests/src/dali-toolkit/utc-Dali-RenderEffect.cpp +++ b/automated-tests/src/dali-toolkit/utc-Dali-RenderEffect.cpp @@ -16,6 +16,7 @@ */ #include +#include #include using namespace Dali; @@ -42,7 +43,7 @@ int UtcDaliRenderEffectNewN(void) try { - BackgroundBlurEffect blurEffect = BackgroundBlurEffect::New(-0.5f, 10.0f, 10.0f); + BackgroundBlurEffect blurEffect = BackgroundBlurEffect::New(-0.5f, 10.0f, 10.0f); BackgroundBlurEffect blurEffect2 = BackgroundBlurEffect::New(10.0f, 10.0f, 10.0f); DALI_TEST_CHECK(!blurEffect && !blurEffect2); } @@ -189,3 +190,41 @@ int UtcDaliRenderEffectRepeatActivateDeactivate(void) END_TEST; } + +int UtcDaliRenderEffectSynchronizeBackgroundCornerRadius(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliRenderEffectSynchronizeBackgroundCornerRadius"); + + Integration::Scene scene = application.GetScene(); + + Property::Map blackDimmerMap; + blackDimmerMap.Insert(Toolkit::Visual::Property::TYPE, Toolkit::Visual::COLOR); + blackDimmerMap.Insert(Toolkit::Visual::Property::MIX_COLOR, Color::BLACK); + blackDimmerMap.Insert(Toolkit::Visual::Property::OPACITY, 0.2f); + blackDimmerMap.Insert(Toolkit::DevelVisual::Property::CORNER_RADIUS, 30.0f); + + RenderEffect effect = BackgroundBlurEffect::New(0.4f, 40, 10.0f); + + Control control = Control::New(); + DALI_TEST_CHECK(control.GetRendererCount() == 0u); + control.SetProperty(Actor::Property::PARENT_ORIGIN, ParentOrigin::CENTER); + control.SetProperty(Actor::Property::SIZE, Vector2(1.0f, 1.0f)); + scene.Add(control); + + control.SetProperty(Toolkit::Control::Property::BACKGROUND, blackDimmerMap); + DALI_TEST_CHECK(control.GetRendererCount() == 1u); + control.SetRenderEffect(effect); + DALI_TEST_CHECK(control.GetRendererCount() == 2u); + + Renderer renderer = control.GetRendererAt(1u); + Vector4 radius = Vector4::ZERO; + renderer.GetProperty(renderer.GetPropertyIndex(std::string("uRadius"))).Get(radius); + + DALI_TEST_CHECK(radius.x == 30.0f); + DALI_TEST_CHECK(radius.y == 30.0f); + DALI_TEST_CHECK(radius.z == 30.0f); + DALI_TEST_CHECK(radius.w == 30.0f); + + END_TEST; +} diff --git a/dali-toolkit/internal/controls/render-effects/blur-effect-impl.cpp b/dali-toolkit/internal/controls/render-effects/blur-effect-impl.cpp index 3ff4a2f..fd1dbf8 100644 --- a/dali-toolkit/internal/controls/render-effects/blur-effect-impl.cpp +++ b/dali-toolkit/internal/controls/render-effects/blur-effect-impl.cpp @@ -28,6 +28,7 @@ //INTERNAL INCLUDES #include +#include #include #include @@ -56,7 +57,6 @@ namespace Internal BlurEffectImpl::BlurEffectImpl(bool isBackground) : RenderEffectImpl(), mInternalRoot(Actor::New()), - mPixelFormat(Pixel::Format::INVALID), mDownscaleFactor(BLUR_EFFECT_DOWNSCALE_FACTOR), mPixelRadius(BLUR_EFFECT_PIXEL_RADIUS), mBellCurveWidth(BLUR_EFFECT_BELL_CURVE_WIDTH), @@ -70,7 +70,6 @@ BlurEffectImpl::BlurEffectImpl(bool isBackground) BlurEffectImpl::BlurEffectImpl(float downscaleFactor, uint32_t blurRadius, float bellCurveWidth, bool isBackground) : RenderEffectImpl(), mInternalRoot(Actor::New()), - mPixelFormat(Pixel::Format::INVALID), mDownscaleFactor(downscaleFactor), mPixelRadius((blurRadius >> 2) + 1), mBellCurveWidth(std::max(bellCurveWidth, BLUR_EFFECT_DIVIDE_ZERO_EPSILON)), @@ -102,8 +101,6 @@ BlurEffectImplPtr BlurEffectImpl::New(float downscaleFactor, uint32_t blurRadius void BlurEffectImpl::Initialize() { - RegisterObject(); // of parent's parent class - mRenderFullSizeCamera = CameraActor::New(); mRenderFullSizeCamera.SetInvertYAxis(true); mRenderFullSizeCamera.SetProperty(Actor::Property::PARENT_ORIGIN, ParentOrigin::CENTER); @@ -318,6 +315,11 @@ void BlurEffectImpl::SetShaderConstants(float downsampledWidth, float downsample mVerticalBlurActor.RegisterProperty(GetSampleOffsetsPropertyName(i), Vector2(0.0f, uvOffsets[i] / downsampledHeight)); mVerticalBlurActor.RegisterProperty(GetSampleWeightsPropertyName(i), weights[i]); } + + if(mIsBackground) + { + SynchronizeBackgroundCornerRadius(); + } } std::string BlurEffectImpl::GetSampleOffsetsPropertyName(unsigned int index) const @@ -334,6 +336,18 @@ std::string BlurEffectImpl::GetSampleWeightsPropertyName(unsigned int index) con return oss.str(); } +void BlurEffectImpl::SynchronizeBackgroundCornerRadius() +{ + DALI_ASSERT_ALWAYS(GetOwnerControl() && "You should first SetRenderEffect(), then set its background property map"); + + Property::Map map = GetOwnerControl().GetProperty(Toolkit::Control::Property::BACKGROUND); + Vector4 radius = Vector4::ZERO; + map[Toolkit::DevelVisual::Property::CORNER_RADIUS].Get(radius); + + Renderer renderer = GetTargetRenderer(); + renderer.RegisterProperty("uRadius", radius); +} + } // namespace Internal } // namespace Toolkit } // namespace Dali diff --git a/dali-toolkit/internal/controls/render-effects/blur-effect-impl.h b/dali-toolkit/internal/controls/render-effects/blur-effect-impl.h index eb3fdc2..fe6b177 100644 --- a/dali-toolkit/internal/controls/render-effects/blur-effect-impl.h +++ b/dali-toolkit/internal/controls/render-effects/blur-effect-impl.h @@ -131,6 +131,11 @@ private: */ std::string GetSampleWeightsPropertyName(unsigned int index) const; + /** + * @brief Synchronize mOwnerControl's background corner radius to the blurred output. + */ + void SynchronizeBackgroundCornerRadius(); + BlurEffectImpl(const BlurEffectImpl&) = delete; BlurEffectImpl(BlurEffectImpl&&) = delete; BlurEffectImpl& operator=(BlurEffectImpl&&) = delete; // no move() @@ -155,12 +160,11 @@ private: RenderTask mSourceRenderTask; // Variables - Pixel::Format mPixelFormat; - float mDownscaleFactor; - uint32_t mPixelRadius; - float mBellCurveWidth; - float mMultiplierForFraction; - float mDenominator; + float mDownscaleFactor; + uint32_t mPixelRadius; + float mBellCurveWidth; + float mMultiplierForFraction; + float mDenominator; bool mIsActivated : 1; bool mIsBackground : 1; diff --git a/dali-toolkit/internal/controls/render-effects/render-effect-impl.cpp b/dali-toolkit/internal/controls/render-effects/render-effect-impl.cpp index ae3a36d..b265985 100644 --- a/dali-toolkit/internal/controls/render-effects/render-effect-impl.cpp +++ b/dali-toolkit/internal/controls/render-effects/render-effect-impl.cpp @@ -22,9 +22,6 @@ #include #include -#include -#include - namespace { static constexpr float SIZE_STEP_CONDITION = 3.0f; @@ -51,13 +48,18 @@ void RenderEffectImpl::SetOwnerControl(Dali::Toolkit::Control control) if(mOwnerControl) { mTargetSize = mOwnerControl.GetProperty(Actor::Property::SIZE); - mRenderer = CreateRenderer(BASIC_VERTEX_SOURCE, BASIC_FRAGMENT_SOURCE); + mRenderer = CreateRenderer(SHADER_RENDER_EFFECT_VERT, SHADER_RENDER_EFFECT_FRAG); mSizeNotification = control.AddPropertyNotification(Actor::Property::SIZE, StepCondition(SIZE_STEP_CONDITION)); mSizeNotification.NotifySignal().Connect(this, &RenderEffectImpl::OnSizeSet); } } +Toolkit::Control RenderEffectImpl::GetOwnerControl() const +{ + return mOwnerControl; +} + void RenderEffectImpl::OnSizeSet(PropertyNotification& source) { mTargetSize = mOwnerControl.GetProperty(Actor::Property::SIZE); @@ -70,11 +72,6 @@ Renderer RenderEffectImpl::GetTargetRenderer() const return mRenderer; } -Toolkit::Control RenderEffectImpl::GetOwnerControl() const -{ - return mOwnerControl; -} - Vector2 RenderEffectImpl::GetTargetSize() const { return mTargetSize; diff --git a/dali-toolkit/internal/graphics/shaders/render-effect.frag b/dali-toolkit/internal/graphics/shaders/render-effect.frag new file mode 100644 index 0000000..95ecb8c --- /dev/null +++ b/dali-toolkit/internal/graphics/shaders/render-effect.frag @@ -0,0 +1,62 @@ +precision highp float; +varying highp vec2 vFragCoord; +varying highp vec2 vTexCoord; +uniform highp vec3 uSize; +uniform sampler2D sTexture; +uniform highp vec4 uRadius; + +highp float nrand(const in vec2 uv) +{ + const highp float a = 12.9898, b = 78.233, c = 43758.5453, pi = 3.141592653589793; + highp float dt = dot(uv, vec2(a, b)), sn = mod(dt, pi); + return fract(sin(sn) * c); +} + +vec3 applyDithering( vec3 inColor ) +{ + float rnd = nrand(vTexCoord) - 0.5; + inColor.rgb += rnd / 255.0; + return inColor; +} + +// from https://iquilezles.org/articles/distfunctions +float roundedBoxSDF(vec2 PixelPositionFromCenter, vec2 RectangleEdgePositionFromCenter, float Radius) { + return length(max(abs(PixelPositionFromCenter) + - RectangleEdgePositionFromCenter + + Radius + ,0.0)) + - Radius; +} + +float getCurrentRadius() +{ + if(vTexCoord.x < 0.5 && vTexCoord.y < 0.5) + { + return uRadius.x; + } + else if(vTexCoord.x < 0.5 && vTexCoord.y > 0.5) + { + return uRadius.y; + } + else if(vTexCoord.x > 0.5 && vTexCoord.y > 0.5) + { + return uRadius.z; + } + else + { + return uRadius.w; + } +} + +void main() +{ + gl_FragColor = texture2D(sTexture, vTexCoord); + + float edgeSoftness = 1.0; + float distance = roundedBoxSDF(vFragCoord.xy - (uSize.xy/2.0), uSize.xy/2.0, getCurrentRadius()); + + float smoothedAlpha = 1.0 - smoothstep(0.0, edgeSoftness * 2.0, distance); + gl_FragColor.a *= smoothedAlpha; + + gl_FragColor.rgb = applyDithering(gl_FragColor.rgb); +} diff --git a/dali-toolkit/internal/graphics/shaders/render-effect.vert b/dali-toolkit/internal/graphics/shaders/render-effect.vert new file mode 100644 index 0000000..2de4f92 --- /dev/null +++ b/dali-toolkit/internal/graphics/shaders/render-effect.vert @@ -0,0 +1,14 @@ +precision highp float; +attribute highp vec2 aPosition; +varying highp vec2 vFragCoord; +varying highp vec2 vTexCoord; +uniform highp mat4 uMvpMatrix; +uniform highp vec3 uSize; + +void main() +{ + highp vec4 vertexPosition = vec4(aPosition * uSize.xy, 0.0, 1.0); + vFragCoord = vertexPosition.xy + uSize.xy/2.0; + vTexCoord = aPosition + vec2(0.5); + gl_Position = uMvpMatrix * vertexPosition; +} diff --git a/dali-toolkit/public-api/controls/render-effects/render-effect.cpp b/dali-toolkit/public-api/controls/render-effects/render-effect.cpp index 804c8e2..9964e13 100644 --- a/dali-toolkit/public-api/controls/render-effects/render-effect.cpp +++ b/dali-toolkit/public-api/controls/render-effects/render-effect.cpp @@ -25,7 +25,6 @@ namespace Dali { namespace Toolkit { - RenderEffect::RenderEffect(const RenderEffect& handle) : BaseHandle(handle) { @@ -37,6 +36,5 @@ RenderEffect::RenderEffect(Internal::RenderEffectImpl* renderEffectImpl) } RenderEffect::~RenderEffect() = default; - } // namespace Toolkit } // namespace Dali -- 2.7.4