* Renders a page of static text.
* Doesn't have any style effect.
* Shadows, underline and text auto-scroll don't work.
Change-Id: Ia2ec4b45d2d368448a35083b2f66ec0b6844dd27
Signed-off-by: Victor Cebollada <v.cebollada@samsung.com>
#include <stdlib.h>
#include <limits>
-#include <unistd.h>
#include <dali-toolkit-test-suite-utils.h>
#include <dali-toolkit/dali-toolkit.h>
const Size CONTROL_SIZE( 300.f, 60.f );
-const std::string DEFAULT_FONT_DIR( "/resources/fonts" );
-
std::string gClipboardText;
void ContentSelectedCallback( ClipboardEventNotifier& notifier )
{
#include <stdlib.h>
#include <limits>
+#include <unistd.h>
#include <dali-toolkit-test-suite-utils.h>
#include <dali-toolkit/dali-toolkit.h>
+#include <toolkit-text-utils.h>
#include <dali-toolkit/internal/text/rendering/text-typesetter.h>
#include <dali-toolkit/internal/text/rendering/view-model.h>
#include <dali-toolkit/internal/text/text-controller.h>
using namespace Toolkit;
using namespace Text;
+namespace
+{
+const std::string DEFAULT_FONT_DIR( "/resources/fonts" );
+const PointSize26Dot6 EMOJI_FONT_SIZE = 62u * 64u;
+} // namespace
+
int UtcDaliTextTypesetter(void)
{
tet_infoline(" UtcDaliTextTypesetter");
tet_result(TET_PASS);
END_TEST;
}
+
+int UtcDaliTextRenderingControllerRender(void)
+{
+ tet_infoline(" UtcDaliTextRenderingControllerRender");
+ ToolkitTestApplication application;
+
+ // Load some fonts.
+ TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
+
+ char* pathNamePtr = get_current_dir_name();
+ const std::string pathName( pathNamePtr );
+ free( pathNamePtr );
+
+ fontClient.GetFontId( pathName + DEFAULT_FONT_DIR + "/tizen/TizenColorEmoji.ttf", EMOJI_FONT_SIZE );
+ fontClient.GetFontId( pathName + DEFAULT_FONT_DIR + "/tizen/TizenSansRegular.ttf" );
+
+ // Creates a text controller.
+ ControllerPtr controller = Controller::New();
+
+ // Configures the text controller similarly to the text-label.
+ ConfigureTextLabel( controller );
+
+ // Sets the text.
+ controller->SetMarkupProcessorEnabled( true );
+ controller->SetText( "<font family='TizenSansRegular'>Hello world </font><font family='TizenColorEmoji'>\xF0\x9F\x98\x81</font>" );
+
+ // Creates the text's model and relais-out the text.
+ const Size relayoutSize( 120.f, 60.f );
+ controller->Relayout( relayoutSize );
+
+ // Tests the rendering controller has been created.
+ TypesetterPtr renderingController = Typesetter::New( controller->GetTextModel() );
+ DALI_TEST_CHECK( renderingController );
+
+ // Renders the text and creates the final bitmap.
+ PixelData bitmap = renderingController->Render( relayoutSize );
+ DALI_TEST_CHECK( bitmap );
+
+ DALI_TEST_EQUALS( 120u, bitmap.GetWidth(), TEST_LOCATION );
+ DALI_TEST_EQUALS( 60u, bitmap.GetHeight(), TEST_LOCATION );
+ DALI_TEST_EQUALS( Pixel::RGBA8888, bitmap.GetPixelFormat(), TEST_LOCATION );
+
+ // Changes vertical alignment.
+ controller->SetVerticalAlignment( Layout::VERTICAL_ALIGN_CENTER );
+ controller->Relayout( relayoutSize );
+
+ // Renders the text and creates the final bitmap.
+ bitmap = renderingController->Render( relayoutSize );
+ DALI_TEST_CHECK( bitmap );
+
+ DALI_TEST_EQUALS( 120u, bitmap.GetWidth(), TEST_LOCATION );
+ DALI_TEST_EQUALS( 60u, bitmap.GetHeight(), TEST_LOCATION );
+ DALI_TEST_EQUALS( Pixel::RGBA8888, bitmap.GetPixelFormat(), TEST_LOCATION );
+
+ controller->SetVerticalAlignment( Layout::VERTICAL_ALIGN_BOTTOM );
+ controller->Relayout( relayoutSize );
+
+ // Renders the text and creates the final bitmap.
+ bitmap = renderingController->Render( relayoutSize );
+ DALI_TEST_CHECK( bitmap );
+
+ DALI_TEST_EQUALS( 120u, bitmap.GetWidth(), TEST_LOCATION );
+ DALI_TEST_EQUALS( 60u, bitmap.GetHeight(), TEST_LOCATION );
+ DALI_TEST_EQUALS( Pixel::RGBA8888, bitmap.GetPixelFormat(), TEST_LOCATION );
+
+ tet_result(TET_PASS);
+ END_TEST;
+}
#include <dali-toolkit-test-suite-utils.h>
#include <dali-toolkit/public-api/visuals/visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/text-visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/visual-properties-devel.h>
#include <dali-toolkit/internal/visuals/visual-factory-cache.h>
#include <dali-toolkit/internal/visuals/wireframe/wireframe-visual.h>
+#include <dali-toolkit/dali-toolkit.h>
using namespace Dali::Toolkit::Internal;
tet_result(TET_PASS);
END_TEST;
}
+
+int UtcDaliTextVisual(void)
+{
+ tet_infoline(" UtcDaliTextVisual");
+ ToolkitTestApplication application;
+
+ Stage stage = Stage::GetCurrent();
+
+ Dali::Toolkit::Control control = Dali::Toolkit::Control::New();
+ control.SetParentOrigin( ParentOrigin::CENTER );
+
+ Dali::Property::Map map;
+ map[ Dali::Toolkit::Visual::Property::TYPE ] = Dali::Toolkit::DevelVisual::TEXT;
+ map[ Dali::Toolkit::TextVisual::Property::ENABLE_MARKUP ] = true;
+ std::string markupText( "<color value='blue'><font size='50'>H</font></color>ello <color value='blue'><font size='50'>w</font></color>orld" );
+ map[ Dali::Toolkit::TextVisual::Property::TEXT ] = markupText;
+ map[ Dali::Toolkit::TextVisual::Property::TEXT_COLOR ] = Dali::Vector4( 0.25f, 0.25f, 0.5f, 1.f );
+ map[ Dali::Toolkit::TextVisual::Property::FONT_FAMILY ] = "TizenSansRegular";
+ map[ Dali::Toolkit::TextVisual::Property::POINT_SIZE ] = 30.f;
+ map[ Dali::Toolkit::TextVisual::Property::HORIZONTAL_ALIGNMENT ] = "CENTER";
+ map[ Dali::Toolkit::TextVisual::Property::VERTICAL_ALIGNMENT ] = "CENTER";
+
+ control.SetProperty( Dali::Toolkit::Control::Property::BACKGROUND, map );
+
+ stage.Add( control );
+
+ try
+ {
+ application.SendNotification();
+ application.Render();
+ }
+ catch( ... )
+ {
+ tet_result(TET_FAIL);
+ }
+
+ // The renderer should be removed.
+ control.SetResizePolicy( ResizePolicy::FIXED, Dimension::ALL_DIMENSIONS );
+ control.SetSize( 1.f, 0.f );
+
+ application.SendNotification();
+ application.Render();
+
+ DALI_TEST_EQUALS( 0u, control.GetRendererCount(), TEST_LOCATION );
+
+ tet_result(TET_PASS);
+ END_TEST;
+}
void GetFontMetrics( FontId fontId, FontMetrics& metrics ){}
GlyphIndex GetGlyphIndex( FontId fontId, Character charcode ){return 0;}
bool GetGlyphMetrics( GlyphInfo* array, uint32_t size, bool horizontal ){return true;}
+ void CreateBitmap( FontId fontId, GlyphIndex glyphIndex, Dali::TextAbstraction::FontClient::GlyphBufferData& data ){}
PixelData CreateBitmap( FontId fontId, GlyphIndex glyphIndex ){return PixelData();}
void CreateVectorBlob( FontId fontId, GlyphIndex glyphIndex, VectorBlob*& blob,
unsigned int& blobLength, unsigned int& nominalWidth, unsigned int& nominalHeight )
blobLength = 0;
}
const GlyphInfo& GetEllipsisGlyph( PointSize26Dot6 pointSize ){return mGlyphInfo;}
+ bool IsColorGlyph( FontId fontId, GlyphIndex glyphIndex ){return false;}
private:
unsigned int mDpiHorizontal;
unsigned int mDpiVertical;
{
}
+FontClient::GlyphBufferData::GlyphBufferData()
+{
+}
+
+FontClient::GlyphBufferData::~GlyphBufferData()
+{
+}
+
FontClient& FontClient::operator=( const FontClient& handle )
{
BaseHandle::operator=( handle );
return GetImplementation(*this).GetGlyphMetrics( array, size, horizontal );
}
+void FontClient::CreateBitmap( FontId fontId, GlyphIndex glyphIndex, Dali::TextAbstraction::FontClient::GlyphBufferData& data )
+{
+ GetImplementation(*this).CreateBitmap( fontId, glyphIndex, data );
+}
+
PixelData FontClient::CreateBitmap( FontId fontId, GlyphIndex glyphIndex )
{
return GetImplementation(*this).CreateBitmap( fontId, glyphIndex );
}
-
void FontClient::CreateVectorBlob( FontId fontId,
GlyphIndex glyphIndex,
VectorBlob*& blob,
return GetImplementation(*this).GetEllipsisGlyph( pointSize );
}
+bool FontClient::IsColorGlyph( FontId fontId, GlyphIndex glyphIndex )
+{
+ return GetImplementation(*this).IsColorGlyph( fontId, glyphIndex );
+}
+
FontClient::FontClient( Internal::FontClient* internal )
: BaseHandle( internal )
{
#include <iostream>
#include <stdlib.h>
+#include <unistd.h>
+
#include <dali-toolkit-test-suite-utils.h>
#include <dali-toolkit/dali-toolkit.h>
const char* const PROPERTY_NAME_OUTLINE = "outline";
const int DEFAULT_RENDERING_BACKEND = Dali::Toolkit::Text::DEFAULT_RENDERING_BACKEND;
+const std::string DEFAULT_FONT_DIR( "/resources/fonts" );
+const unsigned int EMOJI_FONT_SIZE = 3968u;
bool DaliTestCheckMaps( const Property::Map& fontStyleMapGet, const Property::Map& fontStyleMapSet )
{
application.SendNotification();
application.Render();
- END_TEST;
-}
+ TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
-int UtcDaliToolkitTextLabelVectorBasedP(void)
-{
- ToolkitTestApplication application;
- tet_infoline(" UtcDaliToolkitTextLabelVectorBasedP");
+ char* pathNamePtr = get_current_dir_name();
+ const std::string pathName( pathNamePtr );
+ free( pathNamePtr );
- TestGlAbstraction& glAbstraction = application.GetGlAbstraction();
- glAbstraction.EnableTextureCallTrace( true );
+ fontClient.GetFontId( pathName + DEFAULT_FONT_DIR + "/tizen/TizenColorEmoji.ttf", EMOJI_FONT_SIZE );
- TextLabel label = TextLabel::New();
- label.SetParentOrigin( ParentOrigin::CENTER );
- label.SetSize( Stage::GetCurrent().GetSize() );
- label.SetProperty( TextLabel::Property::TEXT, "Hello World" );
- label.SetProperty( TextLabel::Property::POINT_SIZE, 10.0f );
- label.SetProperty( TextLabel::Property::RENDERING_BACKEND, Toolkit::Text::RENDERING_VECTOR_BASED );
- Stage::GetCurrent().Add( label );
-
- application.SendNotification();
- application.Render();
-
- // Test that the vector data is uploaded to atlas
- DALI_TEST_CHECK( glAbstraction.GetTextureTrace().FindMethod("TexSubImage2D") );
- glAbstraction.GetTextureTrace().Reset();
-
- // Add another label with the same text in a different point-size
- TextLabel label2 = TextLabel::New();
- label2.SetProperty( TextLabel::Property::TEXT, "Hello World" );
- label2.SetProperty( TextLabel::Property::POINT_SIZE, 13.0f );
- label2.SetProperty( TextLabel::Property::RENDERING_BACKEND, Toolkit::Text::RENDERING_VECTOR_BASED );
- Stage::GetCurrent().Add( label2 );
+ const std::string emojis = "<font family='TizenColorEmoji'>\xF0\x9F\x98\x81 \xF0\x9F\x98\x82 \xF0\x9F\x98\x83 \xF0\x9F\x98\x84</font>";
+ label.SetProperty( TextLabel::Property::ENABLE_MARKUP, true );
+ label.SetProperty( TextLabel::Property::TEXT, emojis );
application.SendNotification();
application.Render();
- // Test that no additional vector data was uploaded to atlas
- // i.e. the same vector data can be used to render any point-size
- DALI_TEST_CHECK( ! glAbstraction.GetTextureTrace().FindMethod("TexSubImage2D") );
-
END_TEST;
}
#include <dali/public-api/rendering/shader.h>
#include <dali-toolkit/devel-api/visual-factory/visual-factory.h>
#include <dali-toolkit/devel-api/visual-factory/devel-visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/text-visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/visual-properties-devel.h>
#include <dali-toolkit/devel-api/align-enums.h>
#include <dali-toolkit/dali-toolkit.h>
#include "dummy-control.h"
fontClient.GetFontId( pathName + DEFAULT_FONT_DIR + "/tizen/TizenSansRegular.ttf" );
propertyMap.Clear();
- propertyMap.Insert( Visual::Property::TYPE, Visual::TEXT );
+ propertyMap.Insert( Visual::Property::TYPE, DevelVisual::TEXT );
propertyMap.Insert( TextVisual::Property::ENABLE_MARKUP, true );
propertyMap.Insert( TextVisual::Property::TEXT, "<font family='TizenSans' size='12'>Hello world</font>" );
propertyMap.Insert( TextVisual::Property::MULTI_LINE, true );
VisualFactory factory = VisualFactory::Get();
Property::Map propertyMap;
- propertyMap.Insert( Visual::Property::TYPE, Visual::TEXT );
+ propertyMap.Insert( Visual::Property::TYPE, DevelVisual::TEXT );
propertyMap.Insert( "renderingBackend", static_cast<int>( Toolkit::Text::DEFAULT_RENDERING_BACKEND ) );
propertyMap.Insert( "text", "Hello world" );
propertyMap.Insert( "fontFamily", "TizenSans" );
propertyMap.Insert( "verticalAlignment", "CENTER" );
propertyMap.Insert( "textColor", Color::RED );
propertyMap.Insert( "enableMarkup", false );
- propertyMap.Insert( "enableAutoScroll", false );
- propertyMap.Insert( "lineSpacing", 0.f );
- propertyMap.Insert( "batchingEnabled", false );
Visual::Base textVisual = factory.CreateVisual( propertyMap );
Property::Map resultMap;
//Check values in the result map are identical to the initial map's values.
Property::Value* value = resultMap.Find( Visual::Property::TYPE, Property::INTEGER );
DALI_TEST_CHECK( value );
- DALI_TEST_EQUALS( value->Get<int>(), (int)Visual::TEXT, TEST_LOCATION );
-
- value = resultMap.Find( TextVisual::Property::RENDERING_BACKEND, Property::INTEGER );
- DALI_TEST_CHECK( value );
- DALI_TEST_EQUALS( value->Get<int>(), Toolkit::Text::DEFAULT_RENDERING_BACKEND, TEST_LOCATION );
+ DALI_TEST_EQUALS( value->Get<int>(), (int)DevelVisual::TEXT, TEST_LOCATION );
value = resultMap.Find( TextVisual::Property::TEXT, Property::STRING );
DALI_TEST_CHECK( value );
DALI_TEST_CHECK( value );
DALI_TEST_CHECK( !value->Get<bool>() );
- value = resultMap.Find( TextVisual::Property::ENABLE_AUTO_SCROLL, Property::BOOLEAN );
- DALI_TEST_CHECK( !value );
-
- value = resultMap.Find( TextVisual::Property::LINE_SPACING, Property::FLOAT );
- DALI_TEST_CHECK( value );
- DALI_TEST_EQUALS( value->Get<float>(), 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
-
- value = resultMap.Find( TextVisual::Property::BATCHING_ENABLED, Property::BOOLEAN );
- DALI_TEST_CHECK( value );
- DALI_TEST_CHECK( !value->Get<bool>() );
-
END_TEST;
}
VisualFactory factory = VisualFactory::Get();
Property::Map propertyMap;
- propertyMap.Insert( Visual::Property::TYPE, Visual::TEXT );
+ propertyMap.Insert( Visual::Property::TYPE, DevelVisual::TEXT );
propertyMap.Insert( "renderingBackend", static_cast<int>( Toolkit::Text::DEFAULT_RENDERING_BACKEND ) );
propertyMap.Insert( "text", "Hello world" );
propertyMap.Insert( "fontFamily", "TizenSans" );
propertyMap.Insert( "verticalAlignment", "CENTER" );
propertyMap.Insert( "textColor", Color::RED );
propertyMap.Insert( "enableMarkup", false );
- propertyMap.Insert( "enableAutoScroll", false );
- propertyMap.Insert( "lineSpacing", 0.f );
- propertyMap.Insert( "batchingEnabled", false );
Visual::Base textVisual = factory.CreateVisual( propertyMap );
textVisual.SetDepthIndex( 1.f );
develapitoolbardir = $(develapicontrolsdir)/tool-bar
develapitextselectionpopupdir = $(develapicontrolsdir)/text-controls
develapivisualfactorydir = $(develapidir)/visual-factory
+develapivisualsdir = $(develapidir)/visuals
# devel headers
develapi_HEADERS = $(devel_api_header_files)
develapipopup_HEADERS = $(devel_api_popup_header_files)
develapiprogressbar_HEADERS = $(devel_api_progress_bar_header_files)
develapivisualfactory_HEADERS = $(devel_api_visual_factory_header_files)
+develapivisuals_HEADERS = $(devel_api_visuals_header_files)
develapiscripting_HEADERS = $(devel_api_scripting_header_files)
develapishadowview_HEADERS = $(devel_api_shadow_view_header_files)
develapishadereffects_HEADERS = $(devel_api_shader_effects_header_files)
#include <dali-toolkit/public-api/visuals/image-visual-properties.h>
#include <dali-toolkit/public-api/visuals/mesh-visual-properties.h>
#include <dali-toolkit/public-api/visuals/primitive-visual-properties.h>
-#include <dali-toolkit/public-api/visuals/text-visual-properties.h>
#include <dali-toolkit/public-api/visuals/visual-properties.h>
#include <dali-toolkit/public-api/dali-toolkit-version.h>
$(devel_api_src_dir)/visual-factory/visual-factory.h \
$(devel_api_src_dir)/visual-factory/visual-base.h
+devel_api_visuals_header_files = \
+ $(devel_api_src_dir)/visuals/text-visual-properties.h \
+ $(devel_api_src_dir)/visuals/visual-properties-devel.h
+
devel_api_shadow_view_header_files = \
$(devel_api_src_dir)/controls/shadow-view/shadow-view.h
--- /dev/null
+#ifndef DALI_TOOLKIT_TEXT_VISUAL_PROPERTIES_H
+#define DALI_TOOLKIT_TEXT_VISUAL_PROPERTIES_H
+
+/*
+ * Copyright (c) 2016 Samsung Electronics Co., Ltd.
+ *
+ * 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.
+ *
+ */
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/public-api/toolkit-property-index-ranges.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace TextVisual
+{
+
+namespace Property
+{
+
+enum
+{
+ /**
+ * @brief The text to display in UTF-8 format,
+ * @details name "text", type STRING
+ */
+ TEXT = VISUAL_PROPERTY_START_INDEX,
+
+ /**
+ * @brief The requested font family to use,
+ * @details name "fontFamily", type STRING
+ */
+ FONT_FAMILY,
+
+ /**
+ * @brief The requested font style to use,
+ * @details name "fontStyle", type MAP
+ */
+ FONT_STYLE,
+
+ /**
+ * @brief The size of font in points
+ * @details name "pointSize", type FLOAT
+ */
+ POINT_SIZE,
+
+ /**
+ * @brief The single-line or multi-line layout option
+ * @details name "multiLine", type BOOLEAN, default false
+ */
+ MULTI_LINE,
+
+ /**
+ * @brief The line horizontal alignment
+ * @details name "horizontalAlignment", type STRING, values "BEGIN", "CENTER", "END", default BEGIN
+ */
+ HORIZONTAL_ALIGNMENT,
+
+ /**
+ * @brief The line vertical alignment
+ * @details name "verticalAlignment", type STRING, values "TOP", "CENTER", "BOTTOM", default TOP
+ */
+ VERTICAL_ALIGNMENT,
+
+ /**
+ * @brief The color of the text
+ * @details name "textColor", type VECTOR4
+ */
+ TEXT_COLOR,
+
+ /**
+ * @brief Whether the mark-up processing is enabled
+ * @details name "enableMarkup", type BOOLEAN
+ */
+ ENABLE_MARKUP,
+};
+
+} // namespace Property
+
+} // namespace TextVisual
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // DALI_TOOLKIT_TEXT_VISUAL_PROPERTIES_H
--- /dev/null
+#ifndef DALI_TOOLKIT_VISUAL_PROPERTIES_DEVEL_H
+#define DALI_TOOLKIT_VISUAL_PROPERTIES_DEVEL_H
+
+/*
+ * Copyright (c) 2016 Samsung Electronics Co., Ltd.
+ *
+ * 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.
+ *
+ */
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/public-api/visuals/visual-properties.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace DevelVisual
+{
+
+/**
+ * @brief All the visual types.
+ */
+enum Type
+{
+ BORDER = Dali::Toolkit::Visual::BORDER,
+ COLOR = Dali::Toolkit::Visual::COLOR,
+ GRADIENT = Dali::Toolkit::Visual::GRADIENT,
+ IMAGE = Dali::Toolkit::Visual::IMAGE,
+ MESH = Dali::Toolkit::Visual::MESH,
+ PRIMITIVE = Dali::Toolkit::Visual::PRIMITIVE,
+ WIREFRAME = Dali::Toolkit::Visual::WIREFRAME,
+ TEXT = Dali::Toolkit::Visual::WIREFRAME + 1, ///< Renders text.
+};
+
+} // namespace DevelVisual
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // DALI_TOOLKIT_VISUAL_PROPERTIES_DEVEL_H
$(toolkit_src_dir)/text/text-io.cpp \
$(toolkit_src_dir)/text/text-model.cpp \
$(toolkit_src_dir)/text/text-scroller.cpp \
- $(toolkit_src_dir)/text/text-scroller-interface.cpp \
$(toolkit_src_dir)/text/text-view.cpp \
$(toolkit_src_dir)/text/text-view-interface.cpp \
$(toolkit_src_dir)/text/visual-model-impl.cpp \
if( isValidFont &&
isEmojiScript )
{
- const PixelData bitmap = fontClient.CreateBitmap( fontId, glyphIndex );
-
- // For color emojis, the font is valid if the bitmap is RGBA.
- isValidFont = bitmap && ( Pixel::BGRA8888 == bitmap.GetPixelFormat() );
+ // For color emojis, the font is valid if the glyph is a color glyph (the bitmap is RGBA).
+ isValidFont = fontClient.IsColorGlyph( fontId, glyphIndex );
}
// If there is a valid font, cache it.
// CLASS HEADER
#include <dali-toolkit/internal/text/rendering/text-typesetter.h>
+// EXTERNAL INCLUDES
+#include <dali/devel-api/text-abstraction/font-client.h>
+#include <memory.h>
+
// INTERNAL INCLUDES
#include <dali-toolkit/internal/text/rendering/view-model.h>
namespace Text
{
+namespace
+{
+
+/**
+ * @brief Data struct used to set the buffer of the glyph's bitmap into the final bitmap's buffer.
+ */
+struct GlyphData
+{
+ uint32_t* bitmapBuffer; ///< The buffer of the whole bitmap. The format is RGBA8888.
+ Vector2* position; ///< The position of the glyph.
+ TextAbstraction::FontClient::GlyphBufferData glyphBitmap; ///< The glyph's bitmap.
+ unsigned int width; ///< The bitmap's width.
+ unsigned int height; ///< The bitmap's height.
+ int horizontalOffset; ///< The horizontal offset to be added to the 'x' glyph's position.
+ int verticalOffset; ///< The vertical offset to be added to the 'y' glyph's position.
+};
+
+/**
+ * @brief Sets the glyph's buffer into the bitmap's buffer.
+ *
+ * @param[in] data Struct which contains the glyph's data and the bitmap's data.
+ * @param[in] position The position of the glyph.
+ * @param[in] color The color of the glyph.
+ */
+void TypesetGlyph( const GlyphData& data,
+ const Vector2* const position,
+ const Vector4* const color )
+{
+ if( ( 0u == data.glyphBitmap.width ) || ( 0u == data.glyphBitmap.height ) )
+ {
+ // Nothing to do if the width or height of the buffer is zero.
+ return;
+ }
+
+ const int widthMinusOne = static_cast<int>( data.width - 1u );
+ const int heightMinusOne = static_cast<int>( data.height - 1u );
+
+ // Whether the given glyph is a color one.
+ const bool isColorGlyph = Pixel::BGRA8888 == data.glyphBitmap.format;
+
+ // Pointer to the color glyph if there is one.
+ const uint32_t* const colorGlyphBuffer = isColorGlyph ? reinterpret_cast<uint32_t*>( data.glyphBitmap.buffer ) : NULL;
+
+ // Pack the given color into a 32bit buffer. The alpha channel will be updated later for each pixel.
+ // The format is RGBA8888.
+ uint32_t packedColor = 0u;
+ uint8_t* packedColorBuffer = reinterpret_cast<uint8_t*>( &packedColor );
+ *( packedColorBuffer + 2 ) = static_cast<uint8_t>( color->b * 255.f );
+ *( packedColorBuffer + 1 ) = static_cast<uint8_t>( color->g * 255.f );
+ *packedColorBuffer = static_cast<uint8_t>( color->r * 255.f );
+
+ // Initial vertical offset.
+ const int yOffset = data.verticalOffset + position->y;
+
+ // Traverse the pixels of the glyph line per line.
+ for( int lineIndex = 0, glyphHeight = static_cast<int>( data.glyphBitmap.height ); lineIndex < glyphHeight; ++lineIndex )
+ {
+ const int yOffsetIndex = yOffset + lineIndex;
+ if( ( 0 > yOffsetIndex ) || ( yOffsetIndex > heightMinusOne ) )
+ {
+ // Do not write out of bounds.
+ break;
+ }
+
+ const int verticalOffset = yOffsetIndex * data.width;
+ const int xOffset = data.horizontalOffset + position->x;
+ const int glyphBufferOffset = lineIndex * static_cast<int>( data.glyphBitmap.width );
+ for( int index = 0, glyphWidth = static_cast<int>( data.glyphBitmap.width ); index < glyphWidth; ++index )
+ {
+ const int xOffsetIndex = xOffset + index;
+ if( ( 0 > xOffsetIndex ) || ( xOffsetIndex > widthMinusOne ) )
+ {
+ // Don't write out of bounds.
+ break;
+ }
+
+ if( isColorGlyph )
+ {
+ // Retrieves the color from the glyph. The format is BGRA8888.
+ uint32_t packedColorGlyph = *( colorGlyphBuffer + glyphBufferOffset + index );
+
+ // Update the alpha channel.
+ uint8_t* packedColorGlyphBuffer = reinterpret_cast<uint8_t*>( &packedColorGlyph );
+ std::swap( *packedColorGlyphBuffer, *( packedColorGlyphBuffer + 2u ) ); // Swap B and R.
+ *( packedColorGlyphBuffer + 3u ) = static_cast<uint8_t>( color->a * static_cast<float>( *( packedColorGlyphBuffer + 3u ) ) );
+
+ // Set the color into the final pixel buffer.
+ *( data.bitmapBuffer + verticalOffset + xOffsetIndex ) = packedColorGlyph;
+ }
+ else
+ {
+ // Update the alpha channel.
+ const uint8_t alpha = *( data.glyphBitmap.buffer + glyphBufferOffset + index );
+ *( packedColorBuffer + 3u ) = static_cast<uint8_t>( color->a * static_cast<float>( alpha ) );
+
+ // Set the color into the final pixel buffer.
+ *( data.bitmapBuffer + verticalOffset + xOffsetIndex ) = packedColor;
+ }
+ }
+ }
+}
+
+} // namespace
+
TypesetterPtr Typesetter::New( const ModelInterface* const model )
{
return TypesetterPtr( new Typesetter( model ) );
return mModel;
}
+PixelData Typesetter::Render( const Vector2& size )
+{
+ // @todo. This initial implementation for a TextLabel has only one visible page.
+
+ // Elides the text if needed.
+ mModel->ElideGlyphs();
+
+ // Retrieves the layout size.
+ const Size& layoutSize = mModel->GetLayoutSize();
+
+ // Set the offset for the vertical alignment.
+ int penY = 0u;
+
+ switch( mModel->GetVerticalAlignment() )
+ {
+ case Layout::VERTICAL_ALIGN_TOP:
+ {
+ // No offset to add.
+ break;
+ }
+ case Layout::VERTICAL_ALIGN_CENTER:
+ {
+ penY = static_cast<int>( 0.5f * ( size.height - layoutSize.height ) );
+ break;
+ }
+ case Layout::VERTICAL_ALIGN_BOTTOM:
+ {
+ penY = static_cast<int>( size.height - layoutSize.height );
+ break;
+ }
+ }
+
+ // Retrieve lines, glyphs, positions and colors from the view model.
+ const Length modelNumberOfLines = mModel->GetNumberOfLines();
+ const LineRun* const modelLinesBuffer = mModel->GetLines();
+ const Length numberOfGlyphs = mModel->GetNumberOfGlyphs();
+ const GlyphInfo* const glyphsBuffer = mModel->GetGlyphs();
+ const Vector2* const positionBuffer = mModel->GetLayout();
+ const Vector4* const colorsBuffer = mModel->GetColors();
+ const ColorIndex* const colorIndexBuffer = mModel->GetColorIndices();
+
+ // Whether to use the default color.
+ const bool useDefaultColor = NULL == colorsBuffer;
+ const Vector4& defaultColor = mModel->GetDefaultColor();
+
+ // Create and initialize the pixel buffer.
+ GlyphData glyphData;
+ glyphData.verticalOffset = penY;
+
+ glyphData.width = static_cast<unsigned int>( size.width );
+ glyphData.height = static_cast<unsigned int>( size.height );
+ const unsigned int bufferSizeInt = glyphData.width * glyphData.height;
+ const unsigned int bufferSizeChar = 4u * bufferSizeInt;
+ glyphData.bitmapBuffer = new uint32_t[ bufferSizeInt ]; // This array will get deleted by PixelData because of the DELETE_ARRAY parameter.
+ memset( glyphData.bitmapBuffer, 0u, bufferSizeChar );
+
+ PixelData pixelData = PixelData::New( reinterpret_cast<uint8_t*>( glyphData.bitmapBuffer ),
+ bufferSizeChar,
+ glyphData.width,
+ glyphData.height,
+ Pixel::RGBA8888, // The format is RGBA8888 because is the format accepted by the image atlas manager.
+ PixelData::DELETE_ARRAY );
+
+ // Get a handle of the font client. Used to retrieve the bitmaps of the glyphs.
+ TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
+
+ // Traverses the lines of the text.
+ for( LineIndex lineIndex = 0u; lineIndex < modelNumberOfLines; ++lineIndex )
+ {
+ const LineRun& line = *( modelLinesBuffer + lineIndex );
+
+ // Sets the horizontal offset of the line.
+ glyphData.horizontalOffset = static_cast<int>( line.alignmentOffset );
+
+ // Increases the vertical offset with the line's ascender.
+ glyphData.verticalOffset += static_cast<int>( line.ascender );
+
+ // Traverses the glyphs of the line.
+ const GlyphIndex endGlyphIndex = std::min( numberOfGlyphs, line.glyphRun.glyphIndex + line.glyphRun.numberOfGlyphs );
+ for( GlyphIndex glyphIndex = line.glyphRun.glyphIndex; glyphIndex < endGlyphIndex; ++glyphIndex )
+ {
+ // Retrieve the glyph's info.
+ const GlyphInfo* const glyphInfo = glyphsBuffer + glyphIndex;
+
+ if( ( glyphInfo->width < Math::MACHINE_EPSILON_1000 ) ||
+ ( glyphInfo->height < Math::MACHINE_EPSILON_1000 ) )
+ {
+ // Nothing to do if the glyph's width or height is zero.
+ continue;
+ }
+
+ // Retrieves the glyph's position.
+ const Vector2* const position = positionBuffer + glyphIndex;
+
+ // Retrieves the glyph's color.
+ const ColorIndex colorIndex = *( colorIndexBuffer + glyphIndex );
+ const Vector4* const color = ( useDefaultColor || ( 0u == colorIndex ) ) ? &defaultColor : colorsBuffer + ( colorIndex - 1u );
+
+ // Retrieves the glyph's bitmap.
+ glyphData.glyphBitmap.buffer = NULL;
+ fontClient.CreateBitmap( glyphInfo->fontId,
+ glyphInfo->index,
+ glyphData.glyphBitmap );
+
+ // Sets the glyph's bitmap into the bitmap of the whole text.
+ if( NULL != glyphData.glyphBitmap.buffer )
+ {
+ TypesetGlyph( glyphData,
+ position,
+ color );
+ }
+ }
+
+ // Increases the vertical offset with the line's descender.
+ glyphData.verticalOffset += static_cast<int>( -line.descender );
+ }
+
+ return pixelData;
+}
+
Typesetter::Typesetter( const ModelInterface* const model )
: mModel( new ViewModel( model ) )
{
// EXTERNAL INCLUDES
#include <dali/public-api/common/intrusive-ptr.h>
#include <dali/public-api/object/ref-object.h>
+#include <dali/public-api/images/pixel-data.h>
namespace Dali
{
*/
ViewModel* GetViewModel();
+ /**
+ * @brief Renders the text.
+ *
+ * Does the following operations:
+ * - Finds the visible pages needed to be rendered.
+ * - Elide glyphs if needed.
+ * - Retrieves the data buffers from the text model.
+ * - Creates the pixel data used to generate the final image with the given size.
+ * - Traverse the visible glyphs, retrieve their bitmaps and compose the final pixel data.
+ *
+ * @param[in] size The renderer size.
+ *
+ * @return A pixel data with the text rendered.
+ */
+ PixelData Render( const Vector2& size );
+
private:
/**
* @brief Private constructor.
+++ /dev/null
-/*
- * Copyright (c) 2016 Samsung Electronics Co., Ltd.
- *
- * 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.
- *
- */
-
-// CLASS HEADER
-#include <dali-toolkit/internal/text/text-scroller-interface.h>
-
-namespace Dali
-{
-
-namespace Toolkit
-{
-
-namespace Text
-{
-
-ScrollerInterface::ScrollerInterface()
-{
-}
-
-ScrollerInterface::~ScrollerInterface()
-{
-}
-
-} // namespace Text
-
-} // namespace Toolkit
-
-} // namespace Dali
{
public:
- /**
- * @brief Constructor.
- */
- ScrollerInterface();
-
/**
* @brief Virtual destructor.
*/
- virtual ~ScrollerInterface();
+ virtual ~ScrollerInterface()
+ {}
/**
* @brief Called when the scrolling finishes
// CLASS HEADER
#include <dali-toolkit/internal/visuals/text/text-visual.h>
-// EXTERNAL HEADER
-#include <dali/devel-api/scripting/enum-helper.h>
-
// INTERNAL HEADER
-#include <dali-toolkit/public-api/text/rendering-backend.h>
-#include <dali-toolkit/public-api/visuals/text-visual-properties.h>
#include <dali-toolkit/devel-api/visual-factory/devel-visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/text-visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/visual-properties-devel.h>
#include <dali-toolkit/devel-api/controls/control-depth-index-ranges.h>
-#include <dali-toolkit/internal/text/layouts/layout-alignment.h>
-#include <dali-toolkit/internal/text/rendering/text-backend.h>
-#include <dali-toolkit/internal/text/text-effects-style.h>
-#include <dali-toolkit/internal/text/text-font-style.h>
-#include <dali-toolkit/internal/text/text-view.h>
+#include <dali-toolkit/internal/visuals/image-atlas-manager.h>
#include <dali-toolkit/internal/visuals/visual-base-impl.h>
#include <dali-toolkit/internal/visuals/visual-base-data-impl.h>
+#include <dali-toolkit/internal/visuals/visual-string-constants.h>
+#include <dali-toolkit/internal/text/text-font-style.h>
namespace Dali
{
{
// Property names.
-const char * const RENDERING_BACKEND_PROPERTY( "renderingBackend" );
const char * const TEXT_PROPERTY( "text" );
const char * const FONT_FAMILY_PROPERTY( "fontFamily" );
const char * const FONT_STYLE_PROPERTY( "fontStyle" );
const char * const VERTICAL_ALIGNMENT_PROPERTY( "verticalAlignment" );
const char * const TEXT_COLOR_PROPERTY( "textColor" );
const char * const ENABLE_MARKUP_PROPERTY( "enableMarkup" );
-const char * const ENABLE_AUTO_SCROLL_PROPERTY( "enableAutoScroll" );
-const char * const AUTO_SCROLL_SPEED_PROPERTY( "autoScrollSpeed" );
-const char * const AUTO_SCROLL_LOOP_COUNT_PROPERTY( "autoScrollLoopCount" );
-const char * const AUTO_SCROLL_GAP_PROPERTY( "autoScrollGap" );
-const char * const LINE_SPACING_PROPERTY( "lineSpacing" );
-const char * const UNDERLINE_PROPERTY( "underline" );
-const char * const SHADOW_PROPERTY( "shadow" );
-const char * const OUTLINE_PROPERTY( "outline" );
-const char * const BATCHING_ENABLED_PROPERTY( "batchingEnabled" );
+
+const std::string PIXEL_AREA_UNIFORM_NAME = "pixelArea";
const Scripting::StringEnum HORIZONTAL_ALIGNMENT_STRING_TABLE[] =
{
};
const unsigned int VERTICAL_ALIGNMENT_STRING_TABLE_COUNT = sizeof( VERTICAL_ALIGNMENT_STRING_TABLE ) / sizeof( VERTICAL_ALIGNMENT_STRING_TABLE[0] );
+const Vector4 FULL_TEXTURE_RECT( 0.f, 0.f, 1.f, 1.f );
+
std::string GetHorizontalAlignment( Toolkit::Text::Layout::HorizontalAlignment alignment )
{
const char* name = Scripting::GetEnumerationName<Toolkit::Text::Layout::HorizontalAlignment>( alignment,
uniform mediump vec4 pixelArea;
varying mediump vec2 vTexCoord;\n
\n
+
+ //Visual size and offset
+ uniform mediump vec2 offset;\n
+ uniform mediump vec2 size;\n
+ uniform mediump vec4 offsetSizeMode;\n
+ uniform mediump vec2 origin;\n
+ uniform mediump vec2 anchorPoint;\n
+
+ vec4 ComputeVertexPosition()\n
+ {\n
+ vec2 visualSize = mix(uSize.xy*size, size, offsetSizeMode.zw );\n
+ vec2 visualOffset = mix( offset, offset/uSize.xy, offsetSizeMode.xy);\n
+ return vec4( (aPosition + anchorPoint)*visualSize + (visualOffset + origin)*uSize.xy, 0.0, 1.0 );\n
+ }\n
+
void main()\n
{\n
- mediump vec4 vertexPosition = vec4(aPosition, 0.0, 1.0);\n
- vertexPosition.xyz *= uSize;\n
- vertexPosition = uMvpMatrix * vertexPosition;\n
- \n
+ mediump vec4 vertexPosition = uMvpMatrix *ComputeVertexPosition();\n
vTexCoord = pixelArea.xy+pixelArea.zw*(aPosition + vec2(0.5) );\n
gl_Position = vertexPosition;\n
}\n
}\n
);
-Geometry CreateGeometry( VisualFactoryCache& factoryCache, ImageDimensions gridSize )
-{
- Geometry geometry;
-
- if( gridSize == ImageDimensions( 1, 1 ) )
- {
- geometry = factoryCache.GetGeometry( VisualFactoryCache::QUAD_GEOMETRY );
- if( !geometry )
- {
- geometry = VisualFactoryCache::CreateQuadGeometry();
- factoryCache.SaveGeometry( VisualFactoryCache::QUAD_GEOMETRY, geometry );
- }
- }
- else
- {
- geometry = VisualFactoryCache::CreateGridGeometry( gridSize );
- }
-
- return geometry;
-}
-
} // unnamed namespace
TextVisualPtr TextVisual::New( VisualFactoryCache& factoryCache )
Property::Value value;
map.Clear();
- map.Insert( Toolkit::VisualProperty::TYPE, Toolkit::Visual::TEXT );
-
- map.Insert( Toolkit::TextVisual::Property::RENDERING_BACKEND, mRenderingBackend );
+ map.Insert( Toolkit::VisualProperty::TYPE, Toolkit::DevelVisual::TEXT );
std::string text;
mController->GetText( text );
map.Insert( Toolkit::TextVisual::Property::TEXT_COLOR, mController->GetDefaultColor() );
map.Insert( Toolkit::TextVisual::Property::ENABLE_MARKUP, mController->IsMarkupProcessorEnabled() );
-
- map.Insert( Toolkit::TextVisual::Property::LINE_SPACING, mController->GetDefaultLineSpacing() );
-
- GetUnderlineProperties( mController, value, Text::EffectStyle::DEFAULT );
- map.Insert( Toolkit::TextVisual::Property::UNDERLINE, value );
-
- GetShadowProperties( mController, value, Text::EffectStyle::DEFAULT );
- map.Insert( Toolkit::TextVisual::Property::SHADOW, value );
-
- GetOutlineProperties( mController, value, Text::EffectStyle::DEFAULT );
- map.Insert( Toolkit::TextVisual::Property::OUTLINE, value );
-
- map.Insert( Toolkit::TextVisual::Property::BATCHING_ENABLED, false ); // TODO
}
TextVisual::TextVisual( VisualFactoryCache& factoryCache )
: Visual::Base( factoryCache ),
mController( Text::Controller::New() ),
- mRenderingBackend( Toolkit::Text::DEFAULT_RENDERING_BACKEND ),
- mHasBeenStaged( false )
+ mTypesetter( Text::Typesetter::New( mController->GetTextModel() ) )
{
}
}
case Property::Key::STRING:
{
- if( keyValue.first.stringKey == RENDERING_BACKEND_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::RENDERING_BACKEND, keyValue.second );
- }
- else if( keyValue.first.stringKey == TEXT_PROPERTY )
+ if( keyValue.first.stringKey == TEXT_PROPERTY )
{
DoSetProperty( Toolkit::TextVisual::Property::TEXT, keyValue.second );
}
{
DoSetProperty( Toolkit::TextVisual::Property::ENABLE_MARKUP, keyValue.second );
}
- else if( keyValue.first.stringKey == ENABLE_AUTO_SCROLL_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::ENABLE_AUTO_SCROLL, keyValue.second );
- }
- else if( keyValue.first.stringKey == AUTO_SCROLL_SPEED_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::AUTO_SCROLL_SPEED, keyValue.second );
- }
- else if( keyValue.first.stringKey == AUTO_SCROLL_LOOP_COUNT_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::AUTO_SCROLL_LOOP_COUNT, keyValue.second );
- }
- else if( keyValue.first.stringKey == AUTO_SCROLL_GAP_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::AUTO_SCROLL_GAP, keyValue.second );
- }
- else if( keyValue.first.stringKey == LINE_SPACING_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::LINE_SPACING, keyValue.second );
- }
- else if( keyValue.first.stringKey == UNDERLINE_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::UNDERLINE, keyValue.second );
- }
- else if( keyValue.first.stringKey == SHADOW_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::SHADOW, keyValue.second );
- }
- else if( keyValue.first.stringKey == OUTLINE_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::OUTLINE, keyValue.second );
- }
- else if( keyValue.first.stringKey == BATCHING_ENABLED_PROPERTY )
- {
- DoSetProperty( Toolkit::TextVisual::Property::BATCHING_ENABLED, keyValue.second );
- }
break;
}
}
void TextVisual::DoSetOnStage( Actor& actor )
{
- // TODO Create the actual renderer(s) for the text!!!!
- // Will crash if no mImpl->mRenderer is set.
- Geometry geometry;
- Shader shader;
+ mControl = actor;
- geometry = CreateGeometry( mFactoryCache, ImageDimensions( 1, 1 ) );
+ CreateRenderer();
+}
- shader = mFactoryCache.GetShader( VisualFactoryCache::IMAGE_SHADER_ATLAS_DEFAULT_WRAP );
- if( !shader )
+void TextVisual::DoSetOffStage( Actor& actor )
+{
+ if( mImpl->mRenderer )
{
- shader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER_ATLAS_CLAMP );
- mFactoryCache.SaveShader( VisualFactoryCache::IMAGE_SHADER_ATLAS_DEFAULT_WRAP, shader );
- }
-
- mImpl->mRenderer = Renderer::New( geometry, shader );
+ // Removes the renderer from the actor.
+ actor.RemoveRenderer( mImpl->mRenderer );
- mSelf = actor;
-
- if( mHasBeenStaged )
- {
- RenderText();
+ DestroyRenderer();
}
- else
- {
- mHasBeenStaged = true;
- }
-}
-void TextVisual::DoSetOffStage( Actor& actor )
-{
- mSelf.Reset();
+ // Resets the control handle.
+ mControl.Reset();
}
void TextVisual::DoSetProperty( Dali::Property::Index index, const Dali::Property::Value& propertyValue )
{
switch( index )
{
- case Toolkit::TextVisual::Property::RENDERING_BACKEND:
- {
- int backend = propertyValue.Get<int>();
-
-#ifndef ENABLE_VECTOR_BASED_TEXT_RENDERING
- if( Text::RENDERING_VECTOR_BASED == backend )
- {
- backend = TextAbstraction::BITMAP_GLYPH; // Fallback to bitmap-based rendering
- }
-#endif
- if( mRenderingBackend != backend )
- {
- mRenderingBackend = backend;
- mRenderer.Reset();
-
- // When using the vector-based rendering, the size of the GLyphs are different
- TextAbstraction::GlyphType glyphType = ( Text::RENDERING_VECTOR_BASED == mRenderingBackend ) ? TextAbstraction::VECTOR_GLYPH : TextAbstraction::BITMAP_GLYPH;
- mController->SetGlyphType( glyphType );
- }
- break;
- }
case Toolkit::TextVisual::Property::TEXT:
{
mController->SetText( propertyValue.Get<std::string>() );
if( mController->GetDefaultColor() != textColor )
{
mController->SetDefaultColor( textColor );
- mRenderer.Reset();
}
break;
}
mController->SetMarkupProcessorEnabled( enableMarkup );
break;
}
- case Toolkit::TextVisual::Property::ENABLE_AUTO_SCROLL:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::AUTO_SCROLL_SPEED:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::AUTO_SCROLL_LOOP_COUNT:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::AUTO_SCROLL_GAP:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::LINE_SPACING:
- {
- const float lineSpacing = propertyValue.Get<float>();
- mController->SetDefaultLineSpacing( lineSpacing );
- mRenderer.Reset();
- break;
- }
- case Toolkit::TextVisual::Property::UNDERLINE:
- {
- // TODO : This switch can be removed when the deprecated SHADOW_OFFSET and SHADOW_COLOR properties are finally removed.
- // Only the code for the MAP case should be kept.
- switch( propertyValue.GetType() )
- {
- case Property::VECTOR4:
- {
- const Vector4& color = propertyValue.Get<Vector4>();
- if( mController->GetUnderlineColor() != color )
- {
- mController->SetUnderlineColor( color );
- mRenderer.Reset();
- }
- break;
- }
- case Property::FLOAT:
- {
- float height = propertyValue.Get<float>();
- if( fabsf( mController->GetUnderlineHeight() - height ) > Math::MACHINE_EPSILON_1000 )
- {
- mController->SetUnderlineHeight( height );
- mRenderer.Reset();
- }
- break;
- }
- case Property::BOOLEAN:
- {
- const bool enabled = propertyValue.Get<bool>();
- if( mController->IsUnderlineEnabled() != enabled )
- {
- mController->SetUnderlineEnabled( enabled );
- mRenderer.Reset();
- }
- break;
- }
- case Property::MAP:
- {
- const bool update = SetUnderlineProperties( mController, propertyValue, Text::EffectStyle::DEFAULT );
- if( update )
- {
- mRenderer.Reset();
- }
- break;
- }
- default:
- {
- // Nothing to do.
- break;
- }
- }
-
- break;
- }
- case Toolkit::TextVisual::Property::SHADOW:
- {
- // TODO : This switch can be removed when the deprecated SHADOW_OFFSET and SHADOW_COLOR properties are finally removed.
- // Only the code for the MAP case should be kept.
- switch( propertyValue.GetType() )
- {
- case Property::VECTOR2:
- {
- const Vector2& shadowOffset = propertyValue.Get<Vector2>();
- if( mController->GetShadowOffset() != shadowOffset )
- {
- mController->SetShadowOffset( shadowOffset );
- mRenderer.Reset();
- }
- break;
- }
- case Property::VECTOR4:
- {
- const Vector4& shadowColor = propertyValue.Get<Vector4>();
- if( mController->GetShadowColor() != shadowColor )
- {
- mController->SetShadowColor( shadowColor );
- mRenderer.Reset();
- }
- break;
- }
- case Property::MAP:
- {
- const bool update = SetShadowProperties( mController, propertyValue, Text::EffectStyle::DEFAULT );
- if( update )
- {
- mRenderer.Reset();
- }
- break;
- }
- default:
- {
- // Nothing to do.
- break;
- }
- }
- break;
- }
- case Toolkit::TextVisual::Property::EMBOSS:
- {
- const bool update = SetEmbossProperties( mController, propertyValue, Text::EffectStyle::DEFAULT );
- if( update )
- {
- mRenderer.Reset();
- }
- break;
- }
- case Toolkit::TextVisual::Property::OUTLINE:
- {
- const bool update = SetOutlineProperties( mController, propertyValue, Text::EffectStyle::DEFAULT );
- if( update )
- {
- mRenderer.Reset();
- }
- break;
- }
- case Toolkit::TextVisual::Property::BATCHING_ENABLED:
- {
- // TODO
- break;
- }
default:
{
// Should not arrive here.
switch( index )
{
- case Toolkit::TextVisual::Property::RENDERING_BACKEND:
- {
- value = mRenderingBackend;
- break;
- }
case Toolkit::TextVisual::Property::TEXT:
{
std::string text;
value = mController->IsMarkupProcessorEnabled();
break;
}
- case Toolkit::TextVisual::Property::ENABLE_AUTO_SCROLL:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::AUTO_SCROLL_SPEED:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::AUTO_SCROLL_LOOP_COUNT:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::AUTO_SCROLL_GAP:
- {
- // nothing to do.
- break;
- }
- case Toolkit::TextVisual::Property::LINE_SPACING:
- {
- value = mController->GetDefaultLineSpacing();
- break;
- }
- case Toolkit::TextVisual::Property::UNDERLINE:
- {
- GetUnderlineProperties( mController, value, Text::EffectStyle::DEFAULT );
- break;
- }
- case Toolkit::TextVisual::Property::SHADOW:
- {
- GetShadowProperties( mController, value, Text::EffectStyle::DEFAULT );
- break;
- }
- case Toolkit::TextVisual::Property::EMBOSS:
- {
- GetEmbossProperties( mController, value, Text::EffectStyle::DEFAULT );
- break;
- }
- case Toolkit::TextVisual::Property::OUTLINE:
- {
- GetOutlineProperties( mController, value, Text::EffectStyle::DEFAULT );
- break;
- }
- case Toolkit::TextVisual::Property::BATCHING_ENABLED:
- {
- // TODO
- break;
- }
default:
{
// Should not arrive here.
void TextVisual::OnSetTransform()
{
- Vector2 visualSize = mImpl->mTransform.GetVisualSize( mImpl->mControlSize );
+ CreateRenderer();
+}
- // Note, the direction should come from the layout of the parent control
- mImpl->mTransform.RegisterUniforms( mImpl->mRenderer, Direction::LEFT_TO_RIGHT );
+void TextVisual::CreateRenderer()
+{
+ Actor control = mControl.GetHandle();
+ if( !control )
+ {
+ // Nothing to do.
+ return;
+ }
- const Text::Controller::UpdateTextType updateTextType = mController->Relayout( visualSize );
+ // Calculates the size to be used to relayout.
+ Vector2 relayoutSize;
- if( ( Text::Controller::NONE_UPDATED != ( Text::Controller::MODEL_UPDATED & updateTextType ) ) ||
- !mRenderer )
+ const bool isWidthRelative = fabsf( mImpl->mTransform.mOffsetSizeMode.z ) < Math::MACHINE_EPSILON_1000;
+ const bool isHeightRelative = fabsf( mImpl->mTransform.mOffsetSizeMode.w ) < Math::MACHINE_EPSILON_1000;
+
+ // Round the size and offset to avoid pixel alignement issues.
+ relayoutSize.width = floorf( 0.5f + ( isWidthRelative ? mImpl->mControlSize.width * mImpl->mTransform.mSize.x : mImpl->mTransform.mSize.width ) );
+ relayoutSize.height = floorf( 0.5f + ( isHeightRelative ? mImpl->mControlSize.height * mImpl->mTransform.mSize.y : mImpl->mTransform.mSize.height ) );
+
+ if( ( fabsf( relayoutSize.width ) < Math::MACHINE_EPSILON_1000 ) || ( fabsf( relayoutSize.height ) < Math::MACHINE_EPSILON_1000 ) )
{
- if( !mRenderer )
+ // Remove any renderer previously set.
+ if( mImpl->mRenderer )
{
- mRenderer = Text::Backend::Get().NewRenderer( mRenderingBackend );
+ control.RemoveRenderer( mImpl->mRenderer );
+
+ DestroyRenderer();
}
- RenderText();
- }
-}
-void TextVisual::RenderText()
-{
- Actor self = mSelf.GetHandle();
- if( !self )
- {
- // Nothing to do if the handle is not initialized.
+ // Nothing else to do if the relayout size is zero.
return;
}
- Actor renderableActor;
+ const Text::Controller::UpdateTextType updateTextType = mController->Relayout( relayoutSize );
- if( mRenderer )
+ if( Text::Controller::NONE_UPDATED != ( Text::Controller::MODEL_UPDATED & updateTextType ) )
{
- renderableActor = mRenderer->Render( mController->GetView(), Toolkit::DepthIndex::TEXT );
- }
+ // Remove any renderer previously set.
+ if( mImpl->mRenderer )
+ {
+ control.RemoveRenderer( mImpl->mRenderer );
- if( renderableActor != mRenderableActor )
- {
- UnparentAndReset( mRenderableActor );
+ DestroyRenderer();
+ }
- if( renderableActor )
+ if( ( relayoutSize.width > Math::MACHINE_EPSILON_1000 ) &&
+ ( relayoutSize.height > Math::MACHINE_EPSILON_1000 ) )
{
- const Vector2& scrollOffset = mController->GetTextModel()->GetScrollPosition();
- renderableActor.SetPosition( scrollOffset.x, scrollOffset.y );
+ PixelData data = mTypesetter->Render( relayoutSize );
+
+ Geometry geometry;
+ Shader shader;
+ TextureSet textureSet;
+
+ Vector4 atlasRect;
+
+ textureSet = mFactoryCache.GetAtlasManager()->Add( atlasRect, data );
+ mImpl->mFlags |= Impl::IS_ATLASING_APPLIED;
+
+ // Filter mode needs to be set to nearest to avoid blurry text.
+ Sampler sampler = Sampler::New();
+ sampler.SetFilterMode( FilterMode::NEAREST, FilterMode::NEAREST );
+ textureSet.SetSampler( 0u, sampler );
+
+ geometry = mFactoryCache.GetGeometry( VisualFactoryCache::QUAD_GEOMETRY );
+ if( !geometry )
+ {
+ geometry = VisualFactoryCache::CreateQuadGeometry();
+ mFactoryCache.SaveGeometry( VisualFactoryCache::QUAD_GEOMETRY , geometry );
+ }
+
+ shader = mFactoryCache.GetShader( VisualFactoryCache::IMAGE_SHADER_ATLAS_DEFAULT_WRAP );
+ if( !shader )
+ {
+ shader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER_ATLAS_CLAMP );
+ mFactoryCache.SaveShader( VisualFactoryCache::IMAGE_SHADER_ATLAS_DEFAULT_WRAP, shader );
+ }
+ shader.RegisterProperty( PIXEL_AREA_UNIFORM_NAME, FULL_TEXTURE_RECT );
- self.Add( renderableActor );
+ mImpl->mRenderer = Renderer::New( geometry, shader );
+ mImpl->mRenderer.SetProperty( Dali::Renderer::Property::DEPTH_INDEX, Toolkit::DepthIndex::TEXT );
+ mImpl->mRenderer.RegisterProperty( ATLAS_RECT_UNIFORM_NAME, atlasRect );
+
+ mImpl->mRenderer.SetTextures( textureSet );
+
+ control.AddRenderer( mImpl->mRenderer );
+
+ //Register transform properties
+ mImpl->mTransform.RegisterUniforms( mImpl->mRenderer, Direction::LEFT_TO_RIGHT );
+
+ mImpl->mFlags |= Impl::IS_FROM_CACHE;
}
- mRenderableActor = renderableActor;
}
}
+void TextVisual::DestroyRenderer()
+{
+ // Removes the text's image from the texture atlas.
+ Vector4 atlasRect;
+
+ const Property::Index index = mImpl->mRenderer.GetPropertyIndex( ATLAS_RECT_UNIFORM_NAME );
+ if( index != Property::INVALID_INDEX )
+ {
+ const Property::Value& atlasRectValue = mImpl->mRenderer.GetProperty( index );
+ atlasRectValue.Get( atlasRect );
+
+ const TextureSet& textureSet = mImpl->mRenderer.GetTextures();
+ mFactoryCache.GetAtlasManager()->Remove( textureSet, atlasRect );
+ }
+
+ // Resets the renderer.
+ mImpl->mRenderer.Reset();
+}
+
} // namespace Internal
} // namespace Toolkit
*
*/
-// EXTERNAL INCLUDES
-#include <dali/devel-api/object/weak-handle.h>
-#include <dali/public-api/common/intrusive-ptr.h>
-
// INTERNAL INCLUDES
#include <dali-toolkit/internal/visuals/visual-base-impl.h>
-#include <dali-toolkit/internal/text/rendering/text-renderer.h>
+#include <dali-toolkit/internal/text/rendering/text-typesetter.h>
#include <dali-toolkit/internal/text/text-controller.h>
namespace Dali
private:
/**
- * @brief Render view, create and attach actor(s) to this TextView.
- * @todo In a next patch a new text render back-end won't add extra actors.
+ * @brief Creates the text's renderer.
*/
- void RenderText();
-
-private:
- Text::ControllerPtr mController; ///< The text's controller.
- WeakHandle<Actor> mSelf;
+ void CreateRenderer();
- Text::RendererPtr mRenderer;
- Actor mRenderableActor;
+ /**
+ * @brief Destroys the text's renderer.
+ */
+ void DestroyRenderer();
- int mRenderingBackend;
- bool mHasBeenStaged : 1;
+private:
+ Text::ControllerPtr mController; ///< The text's controller.
+ Text::TypesetterPtr mTypesetter; ///< The text's typesetter.
+ WeakHandle<Actor> mControl; ///< The control where the renderer is added.
};
} // namespace Internal
// INTERNAL INCLUDES
#include <dali-toolkit/public-api/visuals/image-visual-properties.h>
#include <dali-toolkit/devel-api/visual-factory/devel-visual-properties.h>
+#include <dali-toolkit/devel-api/visuals/visual-properties-devel.h>
#include <dali-toolkit/internal/visuals/border/border-visual.h>
#include <dali-toolkit/internal/visuals/color/color-visual.h>
#include <dali-toolkit/internal/visuals/gradient/gradient-visual.h>
else
{
Property::Value* typeValue = propertyMap.Find( Toolkit::VisualProperty::TYPE, VISUAL_TYPE );
- Toolkit::Visual::Type visualType = Toolkit::Visual::IMAGE; // Default to IMAGE type.
+ Toolkit::DevelVisual::Type visualType = Toolkit::DevelVisual::IMAGE; // Default to IMAGE type.
if( typeValue )
{
Scripting::GetEnumerationProperty( *typeValue, VISUAL_TYPE_TABLE, VISUAL_TYPE_TABLE_COUNT, visualType );
break;
}
- case Toolkit::Visual::TEXT:
+ case Toolkit::DevelVisual::TEXT:
{
visualPtr = TextVisual::New( *( mFactoryCache.Get() ) );
break;
$(public_api_src_dir)/visuals/image-visual-properties.h \
$(public_api_src_dir)/visuals/mesh-visual-properties.h \
$(public_api_src_dir)/visuals/primitive-visual-properties.h \
- $(public_api_src_dir)/visuals/text-visual-properties.h \
$(public_api_src_dir)/visuals/visual-properties.h
+++ /dev/null
-#ifndef DALI_TOOLKIT_TEXT_VISUAL_PROPERTIES_H
-#define DALI_TOOLKIT_TEXT_VISUAL_PROPERTIES_H
-
-/*
- * Copyright (c) 2016 Samsung Electronics Co., Ltd.
- *
- * 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.
- *
- */
-
-// INTERNAL INCLUDES
-#include <dali-toolkit/public-api/toolkit-property-index-ranges.h>
-
-namespace Dali
-{
-
-namespace Toolkit
-{
-
-namespace TextVisual
-{
-
-namespace Property
-{
-
-enum
-{
- /**
- * @brief The type of rendering e.g. bitmap-based
- * @details name "renderingBackend", type INTEGER, default RENDERING_SHARED_ATLAS
- * @SINCE_1_2.11
- */
- RENDERING_BACKEND = VISUAL_PROPERTY_START_INDEX,
-
- /**
- * @brief The text to display in UTF-8 format,
- * @details name "text", type STRING
- * @SINCE_1_2.11
- */
- TEXT,
-
- /**
- * @brief The requested font family to use,
- * @details name "fontFamily", type STRING
- * @SINCE_1_2.11
- */
- FONT_FAMILY,
-
- /**
- * @brief The requested font style to use,
- * @details name "fontStyle", type STRING or MAP
- * @SINCE_1_2.13
- */
- FONT_STYLE,
-
- /**
- * @brief The size of font in points
- * @details name "pointSize", type FLOAT
- * @SINCE_1_2.11
- */
- POINT_SIZE,
-
- /**
- * @brief The single-line or multi-line layout option
- * @details name "multiLine", type BOOLEAN, default false
- * @SINCE_1_2.11
- */
- MULTI_LINE,
-
- /**
- * @brief The line horizontal alignment
- * @details name "horizontalAlignment", type STRING, values "BEGIN", "CENTER", "END", default BEGIN
- * @SINCE_1_2.11
- */
- HORIZONTAL_ALIGNMENT,
-
- /**
- * @brief The line vertical alignment
- * @details name "verticalAlignment", type STRING, values "TOP", "CENTER", "BOTTOM", default TOP
- * @SINCE_1_2.11
- */
- VERTICAL_ALIGNMENT,
-
- /**
- * @brief The color of the text
- * @details name "textColor", type VECTOR4
- * @SINCE_1_2.11
- */
- TEXT_COLOR,
-
- /**
- * @brief Whether the mark-up processing is enabled
- * @details name "enableMarkup", type BOOLEAN
- * @SINCE_1_2.11
- */
- ENABLE_MARKUP,
-
- /**
- * @brief Start or stop auto scrolling,
- * @details name "enableAutoScroll", type BOOLEAN, default is false
- * @SINCE_1_2.11
- */
- ENABLE_AUTO_SCROLL,
-
- /**
- * @brief Sets the speed of scrolling in pixels per second,
- * @details name "autoScrollSpeed", type INTEGER, default in style sheet
- * @SINCE_1_2.11
- */
- AUTO_SCROLL_SPEED,
-
- /**
- * @brief Number of complete loops when scrolling enabled
- * @details name "autoScrollLoopCount", type INTEGER, default in style sheet
- * @SINCE_1_2.11
- */
- AUTO_SCROLL_LOOP_COUNT,
-
- /**
- * @brief Gap before before scrolling wraps
- * @details name "autoScrollGap", type INTEGER, default in style sheet but can be overridden to prevent same text being show at start and end.
- * @SINCE_1_2.11
- */
- AUTO_SCROLL_GAP,
-
- /**
- * @brief The default extra space between lines in points.
- * @details name "lineSpacing", type FLOAT.
- * @SINCE_1_2.11
- */
- LINE_SPACING,
-
- /**
- * @brief The default underline parameters.
- * @details name "underline", type STRING or MAP.
- * @SINCE_1_2.13
- */
- UNDERLINE,
-
- /**
- * @brief The default shadow parameters.
- * @details name "shadow", type STRING or MAP.
- * @SINCE_1_2.13
- */
- SHADOW,
-
- /**
- * @brief The default emboss parameters.
- * @details name "emboss", type STRING or MAP.
- * @SINCE_1_2.13
- */
- EMBOSS,
-
- /**
- * @brief The default outline parameters.
- * @details name "outline", type STRING or MAP.
- * @SINCE_1_2.13
- */
- OUTLINE,
-
- /**
- * @brief This enables Text visuals to automatically be converted to Batch-Text visuals.
- * @details Name "batchingEnabled", type Property::BOOLEAN.
- * @SINCE_1_2.11
- * @note Optional. If not specified, the default is false.
- */
- BATCHING_ENABLED,
-};
-
-} // namespace Property
-
-} // namespace TextVisual
-
-} // namespace Toolkit
-
-} // namespace Dali
-
-#endif // DALI_TOOLKIT_TEXT_VISUAL_PROPERTIES_H
IMAGE, ///< Renders an image into the control's quad. @SINCE_1_1.45
MESH, ///< Renders a mesh using an "obj" file, optionally with textures provided by an "mtl" file. @SINCE_1_1.45
PRIMITIVE, ///< Renders a simple 3D shape, such as a cube or sphere. @SINCE_1_1.45
- WIREFRAME, ///< Renders a simple wire-frame outlining a quad. @SINCE_1_2_2
- TEXT, ///< Renders text. @SINCE_1_2.11
+ WIREFRAME ///< Renders a simple wire-frame outlining a quad. @SINCE_1_2_2
};
namespace Property