From c5e1d2bfc9502a23cf781773d36d4aeffbc58a7b Mon Sep 17 00:00:00 2001 From: Richard Huang Date: Wed, 25 Oct 2017 17:57:34 +0100 Subject: [PATCH] Fix the text visual shaders to work with pre-multiplied alpha Change-Id: I5f82c3933ef61a1ebc3c8d02d171c5f9b0fe7503 --- dali-toolkit/internal/text/text-scroller.cpp | 15 +++++- dali-toolkit/internal/visuals/text/text-visual.cpp | 58 ++++++++++++++++++---- dali-toolkit/internal/visuals/visual-base-impl.cpp | 11 ++-- dali-toolkit/internal/visuals/visual-base-impl.h | 4 +- 4 files changed, 72 insertions(+), 16 deletions(-) diff --git a/dali-toolkit/internal/text/text-scroller.cpp b/dali-toolkit/internal/text/text-scroller.cpp index dbc16eb..466bfa6 100644 --- a/dali-toolkit/internal/text/text-scroller.cpp +++ b/dali-toolkit/internal/text/text-scroller.cpp @@ -81,12 +81,25 @@ const char* VERTEX_SHADER_SCROLL = DALI_COMPOSE_SHADER( const char* FRAGMENT_SHADER = DALI_COMPOSE_SHADER( varying highp vec2 vTexCoord;\n uniform sampler2D sTexture;\n + uniform lowp vec4 uColor;\n + uniform lowp vec3 mixColor;\n + uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n if ( vTexCoord.y > 1.0 )\n discard;\n - gl_FragColor = texture2D( sTexture, vTexCoord );\n + \n + mediump vec4 textTexture = texture2D( sTexture, vTexCoord );\n + textTexture.rgb *= mix( 1.0, textTexture.a, preMultipliedAlpha );\n + \n + gl_FragColor = textTexture * uColor * visualMixColor(); }\n ); diff --git a/dali-toolkit/internal/visuals/text/text-visual.cpp b/dali-toolkit/internal/visuals/text/text-visual.cpp index e979607..d70edce 100755 --- a/dali-toolkit/internal/visuals/text/text-visual.cpp +++ b/dali-toolkit/internal/visuals/text/text-visual.cpp @@ -106,6 +106,12 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT = DALI_COMPOSE_SHADER( uniform lowp vec4 uColor;\n uniform lowp vec3 mixColor;\n uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n @@ -113,7 +119,7 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT = DALI_COMPOSE_SHADER( mediump float textTexture = texture2D( sTexture, texCoord ).r;\n // Set the color of the text to what it is animated to. - gl_FragColor = uTextColorAnimatable * textTexture * uColor * vec4( mixColor, opacity ); + gl_FragColor = uTextColorAnimatable * textTexture * uColor * visualMixColor(); }\n ); @@ -124,13 +130,20 @@ const char* FRAGMENT_SHADER_MULTI_COLOR_TEXT = DALI_COMPOSE_SHADER( uniform lowp vec4 uColor;\n uniform lowp vec3 mixColor;\n uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n mediump vec2 texCoord = clamp( mix( uAtlasRect.xy, uAtlasRect.zw, vTexCoord ), uAtlasRect.xy, uAtlasRect.zw );\n mediump vec4 textTexture = texture2D( sTexture, texCoord );\n + textTexture.rgb *= mix( 1.0, textTexture.a, preMultipliedAlpha );\n - gl_FragColor = textTexture * uColor * vec4( mixColor, opacity ); + gl_FragColor = textTexture * uColor * visualMixColor(); }\n ); @@ -143,6 +156,12 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT_WITH_STYLE = DALI_COMPOSE_SHADER( uniform lowp vec4 uColor;\n uniform lowp vec3 mixColor;\n uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n @@ -151,7 +170,7 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT_WITH_STYLE = DALI_COMPOSE_SHADER( mediump vec4 styleTexture = texture2D( sStyle, texCoord );\n // Draw the text as overlay above the style - gl_FragColor = ( uTextColorAnimatable * textTexture + styleTexture * ( 1.0 - textTexture ) ) * uColor * vec4( mixColor, opacity );\n + gl_FragColor = ( uTextColorAnimatable * textTexture + styleTexture * ( 1.0 - textTexture ) ) * uColor * visualMixColor();\n }\n ); @@ -163,15 +182,22 @@ const char* FRAGMENT_SHADER_MULTI_COLOR_TEXT_WITH_STYLE = DALI_COMPOSE_SHADER( uniform lowp vec4 uColor;\n uniform lowp vec3 mixColor;\n uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n mediump vec2 texCoord = clamp( mix( uAtlasRect.xy, uAtlasRect.zw, vTexCoord ), uAtlasRect.xy, uAtlasRect.zw );\n mediump vec4 textTexture = texture2D( sTexture, texCoord );\n mediump vec4 styleTexture = texture2D( sStyle, texCoord );\n + textTexture.rgb *= mix( 1.0, textTexture.a, preMultipliedAlpha );\n // Draw the text as overlay above the style - gl_FragColor = ( textTexture + styleTexture * ( 1.0 - textTexture.a ) ) * uColor * vec4( mixColor, opacity );\n + gl_FragColor = ( textTexture + styleTexture * ( 1.0 - textTexture.a ) ) * uColor * visualMixColor();\n }\n ); @@ -184,6 +210,12 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT_WITH_EMOJI = DALI_COMPOSE_SHADER( uniform lowp vec4 uColor;\n uniform lowp vec3 mixColor;\n uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n @@ -195,10 +227,10 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT_WITH_EMOJI = DALI_COMPOSE_SHADER( // Markup text with multiple text colors are not animated (but can be supported later on if required). // Emoji color are not animated. mediump float vstep = step( 0.0001, textTexture.a );\n - textTexture.rgb = mix( textTexture.rgb, uTextColorAnimatable.rgb, vstep * maskTexture );\n + textTexture.rgb = mix( textTexture.rgb, uTextColorAnimatable.rgb, vstep * maskTexture ) * mix( 1.0, textTexture.a, preMultipliedAlpha );\n // Draw the text as overlay above the style - gl_FragColor = textTexture * uColor * vec4( mixColor, opacity );\n + gl_FragColor = textTexture * uColor * visualMixColor();\n }\n ); @@ -213,6 +245,12 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT_WITH_STYLE_AND_EMOJI = DALI_COMPOS uniform lowp vec4 uColor;\n uniform lowp vec3 mixColor;\n uniform lowp float opacity;\n + uniform lowp float preMultipliedAlpha;\n + \n + lowp vec4 visualMixColor()\n + {\n + return vec4( mixColor * mix( 1.0, opacity, preMultipliedAlpha ), opacity );\n + }\n \n void main()\n {\n @@ -225,10 +263,10 @@ const char* FRAGMENT_SHADER_SINGLE_COLOR_TEXT_WITH_STYLE_AND_EMOJI = DALI_COMPOS // Markup text with multiple text colors are not animated (but can be supported later on if required). // Emoji color are not animated. mediump float vstep = step( 0.0001, textTexture.a );\n - textTexture.rgb = mix( textTexture.rgb, uTextColorAnimatable.rgb, vstep * maskTexture * ( 1.0 - uHasMultipleTextColors ) );\n + textTexture.rgb = mix( textTexture.rgb, uTextColorAnimatable.rgb, vstep * maskTexture * ( 1.0 - uHasMultipleTextColors ) ) * mix( 1.0, textTexture.a, preMultipliedAlpha );\n // Draw the text as overlay above the style - gl_FragColor = ( textTexture + styleTexture * ( 1.0 - textTexture.a ) ) * uColor * vec4( mixColor, opacity );\n + gl_FragColor = ( textTexture + styleTexture * ( 1.0 - textTexture.a ) ) * uColor * visualMixColor();\n }\n ); @@ -428,6 +466,9 @@ void TextVisual::DoSetOnStage( Actor& actor ) mImpl->mRenderer = Renderer::New( geometry, shader ); mImpl->mRenderer.SetProperty( Dali::Renderer::Property::DEPTH_INDEX, Toolkit::DepthIndex::CONTENT ); + // Enable the pre-multiplied alpha to improve the text quality + EnablePreMultipliedAlpha(true); + const Vector4& defaultColor = mController->GetTextModel()->GetDefaultColor(); Dali::Property::Index shaderTextColorIndex = mImpl->mRenderer.RegisterProperty( "uTextColorAnimatable", defaultColor ); @@ -655,7 +696,6 @@ void TextVisual::UpdateRenderer() mImpl->mRenderer.RegisterProperty( "uHasMultipleTextColors", static_cast( hasMultipleTextColors ) ); mImpl->mRenderer.SetProperty( Renderer::Property::BLEND_MODE, BlendMode::ON); - mImpl->mRenderer.SetProperty( Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA, true ); //Register transform properties mImpl->mTransform.RegisterUniforms( mImpl->mRenderer, Direction::LEFT_TO_RIGHT ); diff --git a/dali-toolkit/internal/visuals/visual-base-impl.cpp b/dali-toolkit/internal/visuals/visual-base-impl.cpp index c829e8f..bd31fe7 100644 --- a/dali-toolkit/internal/visuals/visual-base-impl.cpp +++ b/dali-toolkit/internal/visuals/visual-base-impl.cpp @@ -35,6 +35,8 @@ namespace #if defined(DEBUG_ENABLED) Debug::Filter* gVisualBaseLogFilter = Debug::Filter::New( Debug::NoLogging, false, "LOG_VISUAL_BASE" ); #endif + +const char * const PRE_MULTIPLIED_ALPHA_PROPERTY( "preMultipliedAlpha" ); } namespace Dali @@ -301,9 +303,9 @@ void Visual::Base::CreateInstancePropertyMap( Property::Map& map ) const } -void Visual::Base::EnablePreMultipliedAlpha( bool preMultipled ) +void Visual::Base::EnablePreMultipliedAlpha( bool preMultiplied ) { - if( preMultipled ) + if( preMultiplied ) { mImpl->mFlags |= Impl::IS_PREMULTIPLIED_ALPHA; } @@ -314,7 +316,8 @@ void Visual::Base::EnablePreMultipliedAlpha( bool preMultipled ) if( mImpl->mRenderer ) { - mImpl->mRenderer.SetProperty(Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA, preMultipled); + mImpl->mRenderer.SetProperty(Renderer::Property::BLEND_PRE_MULTIPLIED_ALPHA, preMultiplied); + mImpl->mRenderer.RegisterProperty( PRE_MULTIPLIED_ALPHA_PROPERTY, static_cast( preMultiplied ) ); } } @@ -366,7 +369,7 @@ void Visual::Base::RegisterMixColor() { preMultipliedAlpha = 1.0f; } - mImpl->mRenderer.RegisterProperty( "preMultipliedAlpha", preMultipliedAlpha ); + mImpl->mRenderer.RegisterProperty( PRE_MULTIPLIED_ALPHA_PROPERTY, preMultipliedAlpha ); } void Visual::Base::SetMixColor( const Vector4& color ) diff --git a/dali-toolkit/internal/visuals/visual-base-impl.h b/dali-toolkit/internal/visuals/visual-base-impl.h index 1706b9c..c450d91 100644 --- a/dali-toolkit/internal/visuals/visual-base-impl.h +++ b/dali-toolkit/internal/visuals/visual-base-impl.h @@ -146,9 +146,9 @@ public: /** * @brief Set whether the Pre-multiplied Alpha Blending is required * - * @param[in] preMultipled whether alpha is pre-multiplied. + * @param[in] preMultiplied whether alpha is pre-multiplied. */ - void EnablePreMultipliedAlpha( bool preMultipled ); + void EnablePreMultipliedAlpha( bool preMultiplied ); /** * @brief Query whether alpha is pre-multiplied. -- 2.7.4