TextView - Right to left implementation.
[platform/core/uifw/dali-toolkit.git] / base / dali-toolkit / internal / controls / text-view / relayout-utilities.cpp
index 84fd943..23c943c 100644 (file)
@@ -5,7 +5,7 @@
  * 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
+ * http://www.apache.org/license/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,
 #include <dali-toolkit/internal/controls/text-view/relayout-utilities.h>
 
 // INTERNAL INCLUDES
+#include <dali-toolkit/internal/controls/text-view/text-processor.h>
+#include <dali-toolkit/internal/controls/text-view/text-processor-bidirectional-info.h>
+#include <dali-toolkit/internal/controls/text-view/text-view-word-processor.h>
 #include <dali-toolkit/internal/controls/text-view/text-view-processor-helper-functions.h>
+#include <dali-toolkit/internal/controls/text-view/text-view-processor-dbg.h>
 
 // EXTERNAL INCLUDES
 #include <cmath>
@@ -40,7 +44,7 @@ const float MINIMUM_FADE_BOUNDARY = 0.05f; // When the fade boundary is the same
 
 RelayoutParameters::RelayoutParameters()
 : mPositionOffset(),
-  mLineSize(),
+  mParagraphSize(),
   mWordSize(),
   mCharacterSize(),
   mIndices(),
@@ -48,7 +52,7 @@ RelayoutParameters::RelayoutParameters()
   mIsFirstCharacter( false ),
   mIsFirstCharacterOfWord( false ),
   mIsNewLine( false ),
-  mIsNewLineCharacter( false ),
+  mIsNewParagraphCharacter( false ),
   mIsWhiteSpace( false ),
   mIsVisible( false )
 {
@@ -131,14 +135,14 @@ TextUnderlineStatus::~TextUnderlineStatus()
 {
 }
 
-SubLineLayoutInfo::SubLineLayoutInfo()
+LineLayoutInfo::LineLayoutInfo()
 : mLineLength( 0.f ),
   mMaxCharHeight( 0.f ),
   mMaxAscender( 0.f )
 {
 }
 
-SubLineLayoutInfo::~SubLineLayoutInfo()
+LineLayoutInfo::~LineLayoutInfo()
 {
 }
 
@@ -184,7 +188,7 @@ bool IsExceedingHeight( const Vector3& position, const Size& size, const Size& p
  * @param[out] lineLength The length of the portion of line which doesn't exceed the parant's width
  * @param[out] endWhiteSpaceLength The length of white spaces which are at the end of the line.
  */
-void CalculateLineLength( const bool isWhiteSpace, const float width, const float parentWidth, bool& found, float& lineLength, float& endWhiteSpaceLength )
+void CalculateLineLength( bool isWhiteSpace, float width, float parentWidth, bool& found, float& lineLength, float& endWhiteSpaceLength )
 {
   if( lineLength + width > parentWidth )
   {
@@ -213,9 +217,7 @@ struct CurrentTextActorInfo
   Vector3 position;
   Size size;
   Vector4 color;
-  Vector4 gradientColor;
-  Vector2 startPoint;
-  Vector2 endPoint;
+  TextViewProcessor::CharacterLayoutInfo* characterLayout;
 };
 
 void SetVisualParameters( CurrentTextActorInfo& currentTextActorInfo,
@@ -224,9 +226,13 @@ void SetVisualParameters( CurrentTextActorInfo& currentTextActorInfo,
                           const float lineHeight )
 {
   currentTextActorInfo.textActor.SetTextColor( currentTextActorInfo.color );
-  currentTextActorInfo.textActor.SetGradientColor( currentTextActorInfo.gradientColor );
-  currentTextActorInfo.textActor.SetGradientStartPoint( currentTextActorInfo.startPoint );
-  currentTextActorInfo.textActor.SetGradientEndPoint( currentTextActorInfo.endPoint );
+  if( ( NULL != currentTextActorInfo.characterLayout ) &&
+      ( NULL != currentTextActorInfo.characterLayout->mGradientInfo ) )
+  {
+    currentTextActorInfo.textActor.SetGradientColor( currentTextActorInfo.characterLayout->mGradientInfo->mGradientColor );
+    currentTextActorInfo.textActor.SetGradientStartPoint( currentTextActorInfo.characterLayout->mGradientInfo->mStartPoint );
+    currentTextActorInfo.textActor.SetGradientEndPoint( currentTextActorInfo.characterLayout->mGradientInfo->mEndPoint );
+  }
 
   // The italics offset is used in the offscreen rendering. When text is in italics, it may exceed the text-view's boundary
   // due to the trick used to implement it.
@@ -241,12 +247,12 @@ void SetVisualParameters( CurrentTextActorInfo& currentTextActorInfo,
   currentTextActorInfo.textActor.SetBlendMode( !visualParameters.mSnapshotModeEnabled ? BlendingMode::ON : BlendingMode::OFF );
 }
 
-void CalculateSubLineLayout( const float parentWidth,
-                             const TextViewProcessor::TextInfoIndices& indices,
-                             const TextViewProcessor::LineLayoutInfo& lineLayoutInfo,
-                             const HorizontalWrapType splitPolicy,
-                             const float shrinkFactor,
-                             SubLineLayoutInfo& subLineInfo )
+void CalculateLineLayout( float parentWidth,
+                          const TextViewProcessor::TextInfoIndices& indices,
+                          const TextViewProcessor::ParagraphLayoutInfo& paragraphLayoutInfo,
+                          HorizontalWrapType splitPolicy,
+                          float shrinkFactor,
+                          LineLayoutInfo& subLineInfo )
 {
   subLineInfo.mLineLength = 0.f;
   subLineInfo.mMaxCharHeight = 0.f;
@@ -258,8 +264,8 @@ void CalculateSubLineLayout( const float parentWidth,
   float lineOffset = 0.f;
   bool found = false;
   bool isFirstCharacter = true;
-  for( TextViewProcessor::WordLayoutInfoContainer::const_iterator wordIt = lineLayoutInfo.mWordsLayoutInfo.begin() + indices.mWordIndex,
-         wordEndIt = lineLayoutInfo.mWordsLayoutInfo.end();
+  for( TextViewProcessor::WordLayoutInfoContainer::const_iterator wordIt = paragraphLayoutInfo.mWordsLayoutInfo.begin() + indices.mWordIndex,
+         wordEndIt = paragraphLayoutInfo.mWordsLayoutInfo.end();
        ( wordIt != wordEndIt ) && !found;
        ++wordIt )
   {
@@ -278,7 +284,7 @@ void CalculateSubLineLayout( const float parentWidth,
         break;
       }
       case WrapByWord:
-      case WrapByLine: // Fall through
+      case WrapByParagraphCharacter: // Fall through
       {
         splitByCharacter = false;
         break;
@@ -288,7 +294,7 @@ void CalculateSubLineLayout( const float parentWidth,
         splitByCharacter = ( shrunkWordWidth > parentWidth );
         break;
       }
-      case WrapByLineAndSplit:
+      case WrapByParagraphCharacterAndSplit:
       {
         if( ( 0u != characterIndex ) ||
             ( ( 0u == characterIndex ) && ( lineOffset + shrunkWordWidth > parentWidth ) ) )
@@ -342,7 +348,279 @@ void CalculateSubLineLayout( const float parentWidth,
   subLineInfo.mMaxAscender *= shrinkFactor;
 }
 
-float CalculateXoffset( const Toolkit::Alignment::Type horizontalTextAlignment, const float parentWidth, const float wholeTextWidth )
+
+/**
+ * Sets a character of a line of a bidirectional paragraph in the new position.
+ *
+ * @param[in] wordsLayoutInfo Layout info of all the words of the paragraph.
+ * @param[in] index Index within the paragraph to the character to be set in the new position.
+ * @param[in,out] character Reference to the character in the new position.
+ */
+void SetCharacter( const TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo,
+                   std::size_t index,
+                   TextViewProcessor::CharacterLayoutInfo& character )
+{
+  // Traverse all the characters of the paragraph till the one pointed by index is found.
+  std::size_t traversedCharacters = 0u;
+  for( TextViewProcessor::WordLayoutInfoContainer::const_iterator wordIt = wordsLayoutInfo.begin(),
+         wordEndIt = wordsLayoutInfo.end();
+       wordIt != wordEndIt;
+       ++wordIt )
+  {
+    const TextViewProcessor::WordLayoutInfo& word( *wordIt );
+
+    const std::size_t numberOfCharacters = word.mCharactersLayoutInfo.size();
+    if( index < traversedCharacters + numberOfCharacters  )
+    {
+      character = *( word.mCharactersLayoutInfo.begin() + ( index - traversedCharacters ) );
+      return;
+    }
+    traversedCharacters += numberOfCharacters;
+  }
+}
+
+/**
+ * Reorders the layout info of each line of the paragraph.
+ *
+ * Uses the visual to logical conversion table to order the text, styles and character's layout (metrics).
+ *
+ * @param[in,out] rtlParagraph Layout info for the paragraph with rtl text.
+ */
+void ReorderLayout( TextViewProcessor::ParagraphLayoutInfo& paragraph )
+{
+  // Clear any previous right to left layout.
+  if( NULL != paragraph.mRightToLeftLayout )
+  {
+    paragraph.mRightToLeftLayout->Clear();
+    paragraph.mRightToLeftLayout->mPreviousLayoutCleared = true;
+  }
+  else
+  {
+    // Create a new right to left layout if there isn't any.
+    paragraph.mRightToLeftLayout = new TextViewProcessor::RightToLeftParagraphLayout();
+  }
+
+  // Reorder Text and Styles.
+
+  // Reserve space for the styles.
+  paragraph.mRightToLeftLayout->mTextStyles.Reserve( paragraph.mTextStyles.Count() );
+
+  // Traverses all the bidirectional info per line.
+  for( Vector<TextProcessor::BidirectionalLineInfo*>::ConstIterator it = paragraph.mBidirectionalLinesInfo.Begin(), endIt = paragraph.mBidirectionalLinesInfo.End(); it != endIt; ++it )
+  {
+    TextProcessor::BidirectionalLineInfo* info( *it );
+
+    const std::size_t characterParagraphIndex = info->mCharacterParagraphIndex;
+    const Vector<int>& visualToLogicalMap = info->mVisualToLogicalMap;
+
+    // The text can be appended as it's already reordered.
+    paragraph.mRightToLeftLayout->mText.Append( info->mText );
+
+    // The visual to logical map needs to be used to reorder the styles.
+    for( std::size_t index = 0u, size = visualToLogicalMap.Count(); index < size; ++index )
+    {
+      paragraph.mRightToLeftLayout->mTextStyles.PushBack( *( paragraph.mTextStyles.Begin() + ( characterParagraphIndex + *( visualToLogicalMap.Begin() + index ) ) ) );
+    }
+  }
+
+  // Reorder Layout Info.
+
+  // Reserve space for the new word layout.
+  paragraph.mRightToLeftLayout->mWordsLayoutInfo.reserve( paragraph.mWordsLayoutInfo.size() );
+
+  // Traverses all the bidirectional info per line.
+  for( Vector<TextProcessor::BidirectionalLineInfo*>::ConstIterator it = paragraph.mBidirectionalLinesInfo.Begin(), endIt = paragraph.mBidirectionalLinesInfo.End(); it != endIt; ++it )
+  {
+    TextProcessor::BidirectionalLineInfo* info( *it );
+
+    // Reserve space for all characters.
+    TextViewProcessor::CharacterLayoutInfoContainer characters;
+    characters.resize( info->mNumberOfCharacters );
+
+    // Uses the visual to logical map to set every character in its new position.
+    for( std::size_t index = 0u; index < info->mNumberOfCharacters; ++index )
+    {
+      SetCharacter( paragraph.mWordsLayoutInfo,
+                    info->mCharacterParagraphIndex + info->mVisualToLogicalMap[index],
+                    *( characters.begin() + index ) );
+    }
+
+    // Sets the new 'x' position for each character.
+    float xPosition = 0.f;
+    for( TextViewProcessor::CharacterLayoutInfoContainer::iterator it = characters.begin(), endIt = characters.end(); it != endIt; ++it )
+    {
+      TextViewProcessor::CharacterLayoutInfo& character( *it );
+
+      character.mPosition.x = xPosition;
+      xPosition += character.mSize.width;
+    }
+
+    // Split the reordered text in words.
+    std::size_t previousPosition = 0u;
+    Vector<std::size_t> positions;
+    TextProcessor::SplitInWords( info->mText, positions );
+
+    // Sets the characters into the words they belong to.
+    for( Vector<size_t>::ConstIterator it = positions.Begin(), endIt = positions.End(); it != endIt; ++it )
+    {
+      const std::size_t position = *it;
+
+      TextViewProcessor::WordLayoutInfo word;
+      word.mCharactersLayoutInfo.insert( word.mCharactersLayoutInfo.end(),
+                                         characters.begin() + previousPosition,
+                                         characters.begin() + position );
+
+      if( !word.mCharactersLayoutInfo.empty() )
+      {
+        // Updates the layout of the word.
+        TextViewProcessor::UpdateLayoutInfo( word );
+
+        paragraph.mRightToLeftLayout->mWordsLayoutInfo.push_back( word );
+      }
+
+      // white space or new paragraph.
+      TextViewProcessor::WordLayoutInfo space;
+      space.mCharactersLayoutInfo.insert( space.mCharactersLayoutInfo.end(),
+                                          characters.begin() + position,
+                                          characters.begin() + position + 1u );
+
+      TextViewProcessor::UpdateLayoutInfo( space );
+
+      paragraph.mRightToLeftLayout->mWordsLayoutInfo.push_back( space );
+
+      previousPosition = position + 1u;
+    }
+
+    // The last word.
+    if( previousPosition < paragraph.mRightToLeftLayout->mText.GetLength() )
+    {
+      TextViewProcessor::WordLayoutInfo word;
+      word.mCharactersLayoutInfo.insert( word.mCharactersLayoutInfo.end(),
+                                         characters.begin() + previousPosition,
+                                         characters.end() );
+
+      TextViewProcessor::UpdateLayoutInfo( word );
+
+      paragraph.mRightToLeftLayout->mWordsLayoutInfo.push_back( word );
+    }
+  }
+}
+
+/**
+ * Creates the bidirectional info needed to reorder each line of the paragraph.
+ *
+ * @param[in,out] relayoutData Natural size (metrics), layout, text-actor info.
+ * @param[in,out] paragraph Layout info for the paragraph.
+ * @param[in] characterGlobalIndex Index to the character within the whole text.
+ * @param[in] lineLayoutInfoIndex Index to the table of lines.
+ */
+void CreateBidirectionalInfoForLines( TextView::RelayoutData& relayoutData,
+                                      TextViewProcessor::ParagraphLayoutInfo& paragraph,
+                                      std::size_t& characterGlobalIndex,
+                                      std::size_t& lineLayoutInfoIndex )
+{
+  const std::size_t lineLayoutInfoSize = relayoutData.mLines.size(); // Number or laid out lines.
+  bool lineLayoutEnd = false;            // Whether lineLayoutInfoIndex points at the last laid out line.
+
+  // Clear previously created bidirectional info.
+  paragraph.ClearBidirectionalInfo();
+
+  std::size_t characterParagraphIndex = 0u;   // Index to the character (within the paragraph).
+  for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = paragraph.mWordsLayoutInfo.begin(), wordEndIt = paragraph.mWordsLayoutInfo.end();
+       wordIt != wordEndIt;
+       ++wordIt )
+  {
+    TextViewProcessor::WordLayoutInfo& word( *wordIt );
+
+    for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterIt = word.mCharactersLayoutInfo.begin(), characterEndIt = word.mCharactersLayoutInfo.end();
+         characterIt != characterEndIt;
+         ++characterIt )
+    {
+      TextProcessor::BidirectionalLineInfo* bidirectionalLineInfo = NULL;
+
+      // Check if there is a new line.
+      const bool newLine = !lineLayoutEnd && ( characterGlobalIndex == relayoutData.mLines[lineLayoutInfoIndex].mCharacterGlobalIndex );
+
+      if( newLine )
+      {
+        // Point to the next line.
+        ++lineLayoutInfoIndex;
+        if( lineLayoutInfoIndex >= lineLayoutInfoSize )
+        {
+          // Arrived at last line.
+          lineLayoutEnd = true; // Avoids access out of bounds in the relayoutData.mLines vector.
+        }
+
+        // Number of characters of the line.
+        const size_t numberOfCharacters = ( lineLayoutEnd ? relayoutData.mTextLayoutInfo.mNumberOfCharacters : relayoutData.mLines[lineLayoutInfoIndex].mCharacterGlobalIndex ) - characterGlobalIndex;
+
+        // There is right to left characters in this line. It needs to be reordered.
+        bidirectionalLineInfo = new TextProcessor::BidirectionalLineInfo();
+        bidirectionalLineInfo->mCharacterParagraphIndex = characterParagraphIndex;
+        bidirectionalLineInfo->mNumberOfCharacters = numberOfCharacters;
+
+        // Set all the Text's characters in the visual order and creates the mapping tables.
+        TextProcessor::ReorderLine( paragraph.mBidirectionalParagraphInfo,
+                                    bidirectionalLineInfo );
+
+        paragraph.mBidirectionalLinesInfo.PushBack( bidirectionalLineInfo );
+
+        for( std::size_t index = 0u; index < numberOfCharacters; ++index )
+        {
+          relayoutData.mCharacterLogicalToVisualMap.push_back( characterGlobalIndex + bidirectionalLineInfo->mLogicalToVisualMap[index] );
+          relayoutData.mCharacterVisualToLogicalMap.push_back( characterGlobalIndex + bidirectionalLineInfo->mVisualToLogicalMap[index] );
+        }
+      }
+
+      ++characterGlobalIndex;
+      ++characterParagraphIndex;
+    } // characters
+  } // words
+}
+
+void ReorderRightToLeftLayout( TextView::RelayoutData& relayoutData )
+{
+  // Reset conversion tables shared through public-api
+  relayoutData.mCharacterLogicalToVisualMap.clear();
+  relayoutData.mCharacterVisualToLogicalMap.clear();
+
+  std::size_t characterGlobalIndex = 0u; // Index to the global character (within the whole text).
+  std::size_t lineLayoutInfoIndex = 0u;  // Index to the line info.
+
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(), paragraphEndIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphIt != paragraphEndIt;
+       ++paragraphIt )
+  {
+    TextViewProcessor::ParagraphLayoutInfo& paragraph( *paragraphIt );
+
+    if( NULL != paragraph.mBidirectionalParagraphInfo )
+    {
+      // There is right to left text in this paragraph.
+
+      // Creates the bidirectional info needed to reorder each line of the paragraph.
+      CreateBidirectionalInfoForLines( relayoutData,
+                                       paragraph,
+                                       characterGlobalIndex,
+                                       lineLayoutInfoIndex );
+
+      // Reorder each line of the paragraph
+      ReorderLayout( paragraph );
+    }
+    else
+    {
+      // Identity in case the paragraph has no right to left text.
+      for( std::size_t index = 0u; index < paragraph.mNumberOfCharacters; ++index )
+      {
+        const std::size_t globalIndex = characterGlobalIndex + index;
+        relayoutData.mCharacterLogicalToVisualMap.push_back( globalIndex );
+        relayoutData.mCharacterVisualToLogicalMap.push_back( globalIndex );
+      }
+      characterGlobalIndex += paragraph.mNumberOfCharacters;
+    }
+  } // paragraphs
+}
+
+float CalculateXoffset( Toolkit::Alignment::Type horizontalTextAlignment, float parentWidth, float wholeTextWidth )
 {
   float xOffset( 0.f );
   switch( horizontalTextAlignment )
@@ -371,7 +649,7 @@ float CalculateXoffset( const Toolkit::Alignment::Type horizontalTextAlignment,
   return xOffset;
 }
 
-float CalculateYoffset( const Toolkit::Alignment::Type verticalTextAlignment, const float parentHeight, const float wholeTextHeight )
+float CalculateYoffset( Toolkit::Alignment::Type verticalTextAlignment, float parentHeight, float wholeTextHeight )
 {
   float yOffset( 0.f );
   switch( verticalTextAlignment )
@@ -400,7 +678,7 @@ float CalculateYoffset( const Toolkit::Alignment::Type verticalTextAlignment, co
   return yOffset;
 }
 
-float CalculateJustificationOffset( const Toolkit::TextView::LineJustification justification, const float wholeTextWidth, const float lineLength )
+float CalculateJustificationOffset( Toolkit::TextView::LineJustification justification, float wholeTextWidth, float lineLength )
 {
   float offset = 0.f;
   switch( justification )
@@ -430,7 +708,7 @@ float CalculateJustificationOffset( const Toolkit::TextView::LineJustification j
   return offset;
 }
 
-bool IsVisible( const Vector3& position, const Size& size, const Size& parentSize, const VisibilityTestType type )
+bool IsVisible( const Vector3& position, const Size& size, const Size& parentSize, VisibilityTestType type )
 {
   bool visible = false;
 
@@ -512,24 +790,33 @@ void UpdateAlignment( const TextView::LayoutParameters& layoutParameters,
   const float textHorizontalOffset = CalculateXoffset( layoutParameters.mHorizontalAlignment, relayoutData.mTextViewSize.width, relayoutData.mTextSizeForRelayoutOption.width );
   const float textVerticalOffset = CalculateYoffset( layoutParameters.mVerticalAlignment, relayoutData.mTextViewSize.height, relayoutData.mTextSizeForRelayoutOption.height );
 
-  std::size_t lineJustificationIndex = 0u; // Index to the first position of the vector which stores all line justification info.
-  std::size_t infoTableCharacterIndex = 0u;
+  // Index to the global character (within the whole text).
+  std::size_t characterGlobalIndex = 0u;
+
+  // Index to the line info.
+  std::size_t lineLayoutInfoIndex = 0u;
 
-  relayoutParameters.mIndices.mLineIndex = 0u;
+  relayoutParameters.mIndices.mParagraphIndex = 0u;
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(),
-         endLineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineLayoutIt != endLineLayoutIt;
-       ++lineLayoutIt, ++relayoutParameters.mIndices.mLineIndex )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(),
+         endParagraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphLayoutIt != endParagraphLayoutIt;
+       ++paragraphLayoutIt, ++relayoutParameters.mIndices.mParagraphIndex )
   {
-    TextViewProcessor::LineLayoutInfo& lineLayoutInfo( *lineLayoutIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraphLayoutInfo( *paragraphLayoutIt );
 
     float justificationOffset = 0.f;
 
+    const std::size_t lineLayoutInfoSize = relayoutData.mLines.size(); // Number of lines.
+    bool lineLayoutEnd = false;            // Whether lineLayoutInfoIndex points at the last line.
+
     relayoutParameters.mIndices.mWordIndex = 0u;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.begin(),
-           endWordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.end();
+    const bool isRightToLeftLayout = NULL != paragraphLayoutInfo.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraphLayoutInfo.mRightToLeftLayout->mWordsLayoutInfo : paragraphLayoutInfo.mWordsLayoutInfo;
+
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = wordsLayoutInfo.begin(),
+           endWordLayoutIt = wordsLayoutInfo.end();
          wordLayoutIt != endWordLayoutIt;
          ++wordLayoutIt, ++relayoutParameters.mIndices.mWordIndex )
     {
@@ -540,19 +827,24 @@ void UpdateAlignment( const TextView::LayoutParameters& layoutParameters,
       for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterLayoutIt = wordLayoutInfo.mCharactersLayoutInfo.begin(),
              endCharacterLayoutIt = wordLayoutInfo.mCharactersLayoutInfo.end();
            characterLayoutIt != endCharacterLayoutIt;
-           ++characterLayoutIt, ++relayoutParameters.mIndices.mCharacterIndex, ++infoTableCharacterIndex )
+           ++characterLayoutIt, ++relayoutParameters.mIndices.mCharacterIndex, ++characterGlobalIndex )
       {
         TextViewProcessor::CharacterLayoutInfo& characterLayoutInfo( *characterLayoutIt );
 
-        // Calculate line justification offset.
-        if( lineJustificationIndex < relayoutData.mLineJustificationInfo.size() )
+        // Check if there is a new line.
+        const bool newLine = !lineLayoutEnd && ( characterGlobalIndex == relayoutData.mLines[lineLayoutInfoIndex].mCharacterGlobalIndex );
+
+        if( newLine )
         {
-          const TextView::LineJustificationInfo lineJustificationInfo( *( relayoutData.mLineJustificationInfo.begin() + lineJustificationIndex ) );
+          // Calculate line justification offset.
+          justificationOffset = CalculateJustificationOffset( layoutParameters.mLineJustification, relayoutData.mTextSizeForRelayoutOption.width, relayoutData.mLines[lineLayoutInfoIndex].mSize.width );
 
-          if( relayoutParameters.mIndices == lineJustificationInfo.mIndices )
+          // Point to the next line.
+          ++lineLayoutInfoIndex;
+          if( lineLayoutInfoIndex >= lineLayoutInfoSize )
           {
-            justificationOffset = CalculateJustificationOffset( layoutParameters.mLineJustification, relayoutData.mTextSizeForRelayoutOption.width, lineJustificationInfo.mLineLength );
-            ++lineJustificationIndex; // increase the index to point the next position in the vector.
+            // Arrived at last line.
+            lineLayoutEnd = true; // Avoids access out of bounds in the relayoutData.mLines vector.
           }
         }
 
@@ -564,16 +856,16 @@ void UpdateAlignment( const TextView::LayoutParameters& layoutParameters,
         // Updates the size and position table for text-input with the alignment offset.
         Vector3 positionOffset( characterLayoutInfo.mPosition );
 
-        std::vector<Toolkit::TextView::CharacterLayoutInfo>::iterator infoTableIt = relayoutData.mCharacterLayoutInfoTable.begin() + infoTableCharacterIndex;
+        std::vector<Toolkit::TextView::CharacterLayoutInfo>::iterator infoTableIt = relayoutData.mCharacterLayoutInfoTable.begin() + characterGlobalIndex;
         Toolkit::TextView::CharacterLayoutInfo& characterTableInfo( *infoTableIt );
 
         characterTableInfo.mPosition.x = positionOffset.x + characterLayoutInfo.mOffset.x;
         characterTableInfo.mPosition.y = positionOffset.y + characterLayoutInfo.mOffset.y;
 
-        positionOffset.x += characterLayoutInfo.mAdvance * relayoutData.mShrinkFactor;
+        positionOffset.x += characterLayoutInfo.mSize.width * relayoutData.mShrinkFactor;
       } // end characters
     } // end words
-  } // end lines
+  } // end paragraphs
 }
 
 void CalculateBearing( TextViewProcessor::CharacterLayoutInfo& characterLayoutInfo,
@@ -641,21 +933,22 @@ void UpdateLayoutInfoTable( Vector4& minMaxXY,
 
   const float descender = characterLayoutInfo.mSize.height - characterLayoutInfo.mAscender;
 
-  const Toolkit::TextView::CharacterLayoutInfo characterLayoutTableInfo( Size( characterLayoutInfo.mAdvance * relayoutData.mShrinkFactor,
-                                                                               characterLayoutInfo.mHeight * relayoutData.mShrinkFactor ),
+  const Toolkit::TextView::CharacterLayoutInfo characterLayoutTableInfo( Size( characterLayoutInfo.mSize.width * relayoutData.mShrinkFactor,
+                                                                               characterLayoutInfo.mSize.height * relayoutData.mShrinkFactor ),
                                                                          positionOffset,
-                                                                         ( TextViewProcessor::LineSeparator == wordLayoutInfo.mType ),
-                                                                         false, // VCC set the correct direction if needed.
-                                                                         true,
+                                                                         ( TextViewProcessor::ParagraphSeparator == wordLayoutInfo.mType ),
+                                                                         characterLayoutInfo.mIsRightToLeft, // whether the character is right to left.
+                                                                         true,  // whether the character is visible.
                                                                          descender );
 
   relayoutData.mCharacterLayoutInfoTable.push_back( characterLayoutTableInfo );
 
-  positionOffset.x += characterLayoutInfo.mAdvance * relayoutData.mShrinkFactor;
+  positionOffset.x += characterLayoutInfo.mSize.width * relayoutData.mShrinkFactor;
 }
 
 void CalculateVisibilityForFade( const Internal::TextView::LayoutParameters& layoutParameters,
                                  TextViewProcessor::CharacterLayoutInfo& characterLayoutInfo,
+                                 const TextStyle& style,
                                  RelayoutParameters& relayoutParameters,
                                  FadeParameters& fadeParameters,
                                  TextView::RelayoutData& relayoutData )
@@ -817,25 +1110,35 @@ void CalculateVisibilityForFade( const Internal::TextView::LayoutParameters& lay
       // Current implementation can't set gradient parameters for a text-actor exceeding at the same time the left and the right boundaries.
       if( rightFadeOut )
       {
-        gradientColor = characterLayoutInfo.mStyledText.mStyle.GetTextColor();
+        gradientColor = style.GetTextColor();
 
         // Calculates gradient coeficients.
         characterLayoutInfo.mColorAlpha = gradientColor.a * std::min( 1.f, fadeParameters.mRightAlphaCoeficients.x * position.x + fadeParameters.mRightAlphaCoeficients.y );
         gradientColor.a *= std::max( 0.f, fadeParameters.mRightAlphaCoeficients.x * characterPositionPlusWidth + fadeParameters.mRightAlphaCoeficients.y );
 
-        startPoint = Vector2( std::max( 0.f, ( fadeParameters.mRightFadeThresholdOffset - position.x ) / size.width ), 0.5f );
-        endPoint = Vector2( std::min( 1.f, ( relayoutData.mTextViewSize.width - position.x ) / size.width ), 0.5f );
+        startPoint = Vector2( std::max( 0.f, std::min( 1.f, ( fadeParameters.mRightFadeThresholdOffset - position.x ) / size.width ) ), 0.5f );
+        endPoint = Vector2( std::min( 1.f, std::max( 0.f, ( relayoutData.mTextViewSize.width - position.x ) / size.width ) ), 0.5f );
+
+        if( NULL == characterLayoutInfo.mGradientInfo )
+        {
+          characterLayoutInfo.mGradientInfo = new TextViewProcessor::GradientInfo();
+        }
       }
       else if( leftFadeOut )
       {
-        gradientColor = characterLayoutInfo.mStyledText.mStyle.GetTextColor();
+        gradientColor = style.GetTextColor();
 
         // Calculates gradient coeficients.
         characterLayoutInfo.mColorAlpha = std::min( 1.f, fadeParameters.mLeftAlphaCoeficients.x * characterPositionPlusWidth + fadeParameters.mLeftAlphaCoeficients.y );
         gradientColor.a *= gradientColor.a * std::max( 0.f, fadeParameters.mLeftAlphaCoeficients.x * position.x + fadeParameters.mLeftAlphaCoeficients.y );
 
-        startPoint = Vector2( std::max( 0.f, ( fadeParameters.mLeftFadeThresholdOffset - position.x ) / size.width ), 0.5f );
-        endPoint = Vector2( std::min( 1.f, -position.x / size.width ), 0.5f );
+        startPoint = Vector2( std::max( 0.f, std::min( 1.f, ( fadeParameters.mLeftFadeThresholdOffset - position.x ) / size.width ) ), 0.5f );
+        endPoint = Vector2( std::min( 1.f, std::max( 0.f, -position.x / size.width ) ), 0.5f );
+
+        if( NULL == characterLayoutInfo.mGradientInfo )
+        {
+          characterLayoutInfo.mGradientInfo = new TextViewProcessor::GradientInfo();
+        }
       }
     }
 
@@ -844,31 +1147,44 @@ void CalculateVisibilityForFade( const Internal::TextView::LayoutParameters& lay
       // Current implementation can't set gradient parameters for a text-actor exceeding at the same time the top and the bottom boundaries.
       if( bottomFadeOut )
       {
-        gradientColor = characterLayoutInfo.mStyledText.mStyle.GetTextColor();
+        gradientColor = style.GetTextColor();
 
         // Calculates gradient coeficients.
         characterLayoutInfo.mColorAlpha = gradientColor.a * std::min( 1.f, fadeParameters.mBottomAlphaCoeficients.x * characterPositionMinusHeight + fadeParameters.mBottomAlphaCoeficients.y );
         gradientColor.a *= std::max( 0.f, fadeParameters.mBottomAlphaCoeficients.x * position.y + fadeParameters.mBottomAlphaCoeficients.y );
 
-        startPoint = Vector2( 0.5f, std::max( 0.f, ( fadeParameters.mBottomFadeThresholdOffset - characterPositionMinusHeight ) / size.height ) );
-        endPoint = Vector2( 0.5f, std::min( 1.f, ( relayoutData.mTextViewSize.height - characterPositionMinusHeight ) / size.height ) );
+        startPoint = Vector2( 0.5f, std::max( 0.f, std::min( 1.f, ( fadeParameters.mBottomFadeThresholdOffset - characterPositionMinusHeight ) / size.height ) ) );
+        endPoint = Vector2( 0.5f, std::min( 1.f, std::max( 0.f, ( relayoutData.mTextViewSize.height - characterPositionMinusHeight ) / size.height ) ) );
+
+        if( NULL == characterLayoutInfo.mGradientInfo )
+        {
+          characterLayoutInfo.mGradientInfo = new TextViewProcessor::GradientInfo();
+        }
       }
       else if( topFadeOut )
       {
-        gradientColor = characterLayoutInfo.mStyledText.mStyle.GetTextColor();
+        gradientColor = style.GetTextColor();
 
         // Calculates gradient coeficients.
         characterLayoutInfo.mColorAlpha *= gradientColor.a * std::min( 1.f, fadeParameters.mTopAlphaCoeficients.x * position.y + fadeParameters.mTopAlphaCoeficients.y );
         gradientColor.a *= std::max( 0.f, fadeParameters.mTopAlphaCoeficients.x * characterPositionMinusHeight + fadeParameters.mTopAlphaCoeficients.y );
 
-        startPoint = Vector2( 0.5f, std::max( 0.f, ( fadeParameters.mTopFadeThresholdOffset - characterPositionMinusHeight ) / size.height ) );
-        endPoint = Vector2( 0.5f, std::min( 1.f,  -characterPositionMinusHeight / size.height ) );
+        startPoint = Vector2( 0.5f, std::max( 0.f, std::min( 1.f, ( fadeParameters.mTopFadeThresholdOffset - characterPositionMinusHeight ) / size.height ) ) );
+        endPoint = Vector2( 0.5f, std::min( 1.f,  std::max( 0.f, -characterPositionMinusHeight / size.height ) ) );
+
+        if( NULL == characterLayoutInfo.mGradientInfo )
+        {
+          characterLayoutInfo.mGradientInfo = new TextViewProcessor::GradientInfo();
+        }
       }
     }
 
-    characterLayoutInfo.mGradientColor = gradientColor;
-    characterLayoutInfo.mStartPoint = startPoint;
-    characterLayoutInfo.mEndPoint = endPoint;
+    if( NULL != characterLayoutInfo.mGradientInfo )
+    {
+      characterLayoutInfo.mGradientInfo->mGradientColor = gradientColor;
+      characterLayoutInfo.mGradientInfo->mStartPoint = startPoint;
+      characterLayoutInfo.mGradientInfo->mEndPoint = endPoint;
+    }
   }
   else
   {
@@ -1028,16 +1344,18 @@ void CreateEllipsizeTextActor( const EllipsizeParameters& ellipsizeParameters,
   float bearingOffset = 0.f;
 
   // Create ellipsize text-actor.
+  std::size_t characterIndex = 0u;
   for( TextViewProcessor::CharacterLayoutInfoContainer::const_iterator ellipsizeCharacterLayoutIt = relayoutData.mTextLayoutInfo.mEllipsizeLayoutInfo.mCharactersLayoutInfo.begin(),
          endEllipsizeCharacterLayoutIt = relayoutData.mTextLayoutInfo.mEllipsizeLayoutInfo.mCharactersLayoutInfo.end();
        ellipsizeCharacterLayoutIt != endEllipsizeCharacterLayoutIt;
-       ++ellipsizeCharacterLayoutIt )
+       ++ellipsizeCharacterLayoutIt, ++characterIndex )
   {
     const TextViewProcessor::CharacterLayoutInfo& ellipsizeCharacterLayoutInfo( *ellipsizeCharacterLayoutIt );
+    const TextStyle& style = *( *( relayoutData.mTextLayoutInfo.mEllipsisTextStyles.Begin() + characterIndex ) );
 
     if( isColorGlyph ||
         ( isColorGlyph != ellipsizeCharacterLayoutInfo.mIsColorGlyph ) ||
-        ( ellipsizeStyle != ellipsizeCharacterLayoutInfo.mStyledText.mStyle ) )
+        ( ellipsizeStyle != style ) )
     {
       // The style is different, so a new text-actor is needed.
       if( !ellipsizeText.IsEmpty() )
@@ -1055,8 +1373,8 @@ void CreateEllipsizeTextActor( const EllipsizeParameters& ellipsizeParameters,
       }
 
       // Resets the current ellipsize info.
-      ellipsizeText = ellipsizeCharacterLayoutInfo.mStyledText.mText;
-      ellipsizeStyle = ellipsizeCharacterLayoutInfo.mStyledText.mStyle;
+      ellipsizeText = Text( relayoutData.mTextLayoutInfo.mEllipsisText[characterIndex] );
+      ellipsizeStyle = style;
       ellipsizeSize = ellipsizeCharacterLayoutInfo.mSize;
       isColorGlyph = ellipsizeCharacterLayoutInfo.mIsColorGlyph;
 
@@ -1065,7 +1383,7 @@ void CreateEllipsizeTextActor( const EllipsizeParameters& ellipsizeParameters,
     else
     {
       // Updates text and size with the new character.
-      ellipsizeText.Append( ellipsizeCharacterLayoutInfo.mStyledText.mText );
+      ellipsizeText.Append( relayoutData.mTextLayoutInfo.mEllipsisText[characterIndex] );
       TextViewProcessor::UpdateSize( ellipsizeSize, ellipsizeCharacterLayoutInfo.mSize );
     }
   }
@@ -1086,16 +1404,16 @@ void EllipsizeLine( const TextView::LayoutParameters& layoutParameters,
                     EllipsizeParameters& ellipsizeParameters,
                     TextView::RelayoutData& relayoutData )
 {
-  // Traverses the text layout info from the first character of the laid out line
+  // Traverses the text layout info from the first character of the line
   // to the last one setting to each character its visibility. If needed, it adds the ellipsize text (...).
 
-  // Indices to the first character of the laid out line.
+  // Indices to the first character of the line.
   TextViewProcessor::TextInfoIndices firstIndices;
   TextViewProcessor::GetIndicesFromGlobalCharacterIndex( ellipsizeParameters.mFirstIndex,
                                                          relayoutData.mTextLayoutInfo,
                                                          firstIndices );
 
-  // Indices to the last character of the laid out line.
+  // Indices to the last character of the line.
   TextViewProcessor::TextInfoIndices lastIndices;
   TextViewProcessor::GetIndicesFromGlobalCharacterIndex( ellipsizeParameters.mLastIndex,
                                                          relayoutData.mTextLayoutInfo,
@@ -1106,12 +1424,12 @@ void EllipsizeLine( const TextView::LayoutParameters& layoutParameters,
   ellipsizeParameters.mEllipsizeBoundary = relayoutData.mTextViewSize;
   ellipsizeParameters.mEllipsizeBoundary.width -= relayoutData.mTextLayoutInfo.mEllipsizeLayoutInfo.mSize.width;
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin() + firstIndices.mLineIndex,
-         endLineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin() + lastIndices.mLineIndex + 1u;
-       lineLayoutIt != endLineLayoutIt;
-       ++lineLayoutIt )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin() + firstIndices.mParagraphIndex,
+         endParagraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin() + lastIndices.mParagraphIndex + 1u;
+       paragraphLayoutIt != endParagraphLayoutIt;
+       ++paragraphLayoutIt )
   {
-    TextViewProcessor::LineLayoutInfo& lineLayoutInfo( *lineLayoutIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraphLayoutInfo( *paragraphLayoutIt );
 
     ellipsizeParameters.mLineFits = ellipsizeParameters.mIsLineWidthFullyVisible && ellipsizeParameters.mIsLineHeightFullyVisible && ellipsizeParameters.mIsNextLineFullyVisibleHeight;
 
@@ -1125,8 +1443,11 @@ void EllipsizeLine( const TextView::LayoutParameters& layoutParameters,
 
     std::size_t wordCount = 0u;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.begin() + firstIndices.mWordIndex,
-           endWordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.begin() + lastIndices.mWordIndex + 1u;
+    const bool isRightToLeftLayout = NULL != paragraphLayoutInfo.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraphLayoutInfo.mRightToLeftLayout->mWordsLayoutInfo : paragraphLayoutInfo.mWordsLayoutInfo;
+
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = wordsLayoutInfo.begin() + firstIndices.mWordIndex,
+           endWordLayoutIt = wordsLayoutInfo.begin() + lastIndices.mWordIndex + 1u;
          wordLayoutIt != endWordLayoutIt;
          ++wordLayoutIt, ++wordCount )
     {
@@ -1176,20 +1497,24 @@ void EllipsizeLine( const TextView::LayoutParameters& layoutParameters,
       } // end characters
       firstWord = false;
     } // end words
-  } // end lines
+  } // end paragraphs
 }
 
 void SetTextVisible( TextView::RelayoutData& relayoutData )
 {
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(),
-         endLineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineLayoutIt != endLineLayoutIt;
-       ++lineLayoutIt )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(),
+         endParagraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphLayoutIt != endParagraphLayoutIt;
+       ++paragraphLayoutIt )
   {
-    TextViewProcessor::LineLayoutInfo& lineLayoutInfo( *lineLayoutIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraphLayoutInfo( *paragraphLayoutIt );
+    std::size_t characterIndex = 0u;
+
+    const bool isRightToLeftLayout = NULL != paragraphLayoutInfo.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraphLayoutInfo.mRightToLeftLayout->mWordsLayoutInfo : paragraphLayoutInfo.mWordsLayoutInfo;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.begin(),
-           endWordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.end();
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = wordsLayoutInfo.begin(),
+           endWordLayoutIt = wordsLayoutInfo.end();
          wordLayoutIt != endWordLayoutIt;
          ++wordLayoutIt )
     {
@@ -1198,18 +1523,17 @@ void SetTextVisible( TextView::RelayoutData& relayoutData )
       for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterLayoutIt = wordLayoutInfo.mCharactersLayoutInfo.begin(),
              endCharacterLayoutIt = wordLayoutInfo.mCharactersLayoutInfo.end();
            characterLayoutIt != endCharacterLayoutIt;
-           ++characterLayoutIt )
+           ++characterLayoutIt, ++characterIndex )
       {
         TextViewProcessor::CharacterLayoutInfo& characterLayoutInfo( *characterLayoutIt );
 
         characterLayoutInfo.mIsVisible = true;
-        characterLayoutInfo.mGradientColor = Vector4::ZERO;
-        characterLayoutInfo.mStartPoint = Vector2::ZERO;
-        characterLayoutInfo.mEndPoint = Vector2::ZERO;
-        characterLayoutInfo.mColorAlpha = characterLayoutInfo.mStyledText.mStyle.GetTextColor().a;
+        delete characterLayoutInfo.mGradientInfo;
+        characterLayoutInfo.mGradientInfo = NULL;
+        characterLayoutInfo.mColorAlpha = ( *( paragraphLayoutInfo.mTextStyles.Begin() + characterIndex ) )->GetTextColor().a;
       } // end characters
     } // end words
-  } // end lines
+  } // end paragraphs
 
   // Updates the visibility for text-input..
   for( std::vector<Toolkit::TextView::CharacterLayoutInfo>::iterator it = relayoutData.mCharacterLayoutInfoTable.begin(),
@@ -1258,19 +1582,23 @@ void UpdateVisibilityForFade( const TextView::LayoutParameters& layoutParameters
 
   std::size_t infoTableCharacterIndex = 0u;
 
-  relayoutParameters.mIndices.mLineIndex = 0u;
+  relayoutParameters.mIndices.mParagraphIndex = 0u;
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(),
-         endLineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineLayoutIt != endLineLayoutIt;
-       ++lineLayoutIt, ++relayoutParameters.mIndices.mLineIndex )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(),
+         endParagraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphLayoutIt != endParagraphLayoutIt;
+       ++paragraphLayoutIt, ++relayoutParameters.mIndices.mParagraphIndex )
   {
-    TextViewProcessor::LineLayoutInfo& lineLayoutInfo( *lineLayoutIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraphLayoutInfo( *paragraphLayoutIt );
 
+    std::size_t characterIndex = 0u;
     relayoutParameters.mIndices.mWordIndex = 0u;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.begin(),
-           endWordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.end();
+    const bool isRightToLeftLayout = NULL != paragraphLayoutInfo.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraphLayoutInfo.mRightToLeftLayout->mWordsLayoutInfo : paragraphLayoutInfo.mWordsLayoutInfo;
+
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = wordsLayoutInfo.begin(),
+           endWordLayoutIt = wordsLayoutInfo.end();
          wordLayoutIt != endWordLayoutIt;
          ++wordLayoutIt, ++relayoutParameters.mIndices.mWordIndex )
     {
@@ -1283,7 +1611,7 @@ void UpdateVisibilityForFade( const TextView::LayoutParameters& layoutParameters
       for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterLayoutIt = wordLayoutInfo.mCharactersLayoutInfo.begin(),
              endCharacterLayoutIt = wordLayoutInfo.mCharactersLayoutInfo.end();
            characterLayoutIt != endCharacterLayoutIt;
-           ++characterLayoutIt, ++relayoutParameters.mIndices.mCharacterIndex, ++infoTableCharacterIndex )
+           ++characterLayoutIt, ++relayoutParameters.mIndices.mCharacterIndex, ++infoTableCharacterIndex, ++characterIndex )
       {
         TextViewProcessor::CharacterLayoutInfo& characterLayoutInfo( *characterLayoutIt );
 
@@ -1293,6 +1621,7 @@ void UpdateVisibilityForFade( const TextView::LayoutParameters& layoutParameters
         // Calculates the visibility for the current character.
         CalculateVisibilityForFade( layoutParameters,
                                     characterLayoutInfo,
+                                    *( *( paragraphLayoutInfo.mTextStyles.Begin() + characterIndex ) ),
                                     relayoutParameters,
                                     fadeParameters,
                                     relayoutData );
@@ -1307,23 +1636,23 @@ void UpdateVisibilityForFade( const TextView::LayoutParameters& layoutParameters
         relayoutParameters.mIsFirstCharacterOfWord = false;
       } // end character
     } // end words
-  } // end lines
+  } // end paragraphs
 }
 
 void UpdateVisibilityForEllipsize( const TextView::LayoutParameters& layoutParameters,
                                    const TextView::VisualParameters& visualParameters,
                                    TextView::RelayoutData& relayoutData )
 {
-  // Traverses the laid-out lines and checks which ones doesn't fit in the text-view's boundary.
+  // Traverses the lines and checks which ones doesn't fit in the text-view's boundary.
   for( Toolkit::TextView::LineLayoutInfoContainer::const_iterator lineInfoIt = relayoutData.mLines.begin(), endLineInfoIt = relayoutData.mLines.end();
        lineInfoIt != endLineInfoIt;
        ++lineInfoIt )
   {
     const Toolkit::TextView::LineLayoutInfo& lineInfo( *lineInfoIt );
 
-    // To check if a laid-out line fits in the text-view's boundary,
+    // To check if a line fits in the text-view's boundary,
     // get the position of the first character is needed and do the test
-    // with the laid-out line size.
+    // with the line size.
 
     // An bearing offset may have been applied to the first character so it's needed to
     // get the start position of the line.
@@ -1500,7 +1829,7 @@ void CreateEmoticon( const TextView::VisualParameters& visualParameters,
  *
  * @param[in] visualParameters Some visual parameters (fade, sort modifier and blending).
  * @param[in,out] relayoutData Natural size (metrics), layout, text-actor info.
- * @param[in,out] line Layout info for the line.
+ * @param[in,out] paragraph Layout info for the paragraph.
  * @param[in,out] characterLayout Layout info for the character.
  * @param[in] character The character.
  * @param[in] style The character's style.
@@ -1509,7 +1838,7 @@ void CreateEmoticon( const TextView::VisualParameters& visualParameters,
  */
 void CreateTextActor( const TextView::VisualParameters& visualParameters,
                       TextView::RelayoutData& relayoutData,
-                      const TextViewProcessor::LineLayoutInfo& line,
+                      const TextViewProcessor::ParagraphLayoutInfo& paragraph,
                       TextViewProcessor::CharacterLayoutInfo& characterLayout,
                       const Character& character,
                       const TextStyle& style,
@@ -1519,18 +1848,33 @@ void CreateTextActor( const TextView::VisualParameters& visualParameters,
   // Set the text-actor for the current traversed text.
   if( currentTextActorInfo.textActor )
   {
-    currentTextActorInfo.textActor.SetText( currentTextActorInfo.text );
+    if( ( NULL != currentTextActorInfo.characterLayout ) &&
+        currentTextActorInfo.characterLayout->mSetText )
+    {
+      currentTextActorInfo.textActor.SetText( currentTextActorInfo.text );
+      currentTextActorInfo.characterLayout->mSetText = false;
+    }
     currentTextActorInfo.textActor.SetPosition( currentTextActorInfo.position );
     currentTextActorInfo.textActor.SetSize( currentTextActorInfo.size );
 
     SetVisualParameters( currentTextActorInfo,
                          visualParameters,
                          relayoutData,
-                         line.mSize.height );
+                         paragraph.mSize.height );
+  }
+
+  float rightToLeftOffset = 0.f;
+  if( character.IsWhiteSpace() )
+  {
+    // In left to right text, a word never starts with a white space but
+    // it may happen in right to left text as the text is reversed.
+    // The text alignment and justification offset is calculated without this white space.
+    // It causes a missalignment which can be corrected by removing the size of the white space.
+    rightToLeftOffset = characterLayout.mSize.width * relayoutData.mShrinkFactor;
   }
 
   currentTextActorInfo.text = Text( character );
-  currentTextActorInfo.position = Vector3( characterLayout.mPosition.x + characterLayout.mOffset.x,
+  currentTextActorInfo.position = Vector3( characterLayout.mPosition.x + characterLayout.mOffset.x - rightToLeftOffset,
                                            characterLayout.mPosition.y + characterLayout.mOffset.y,
                                            characterLayout.mPosition.z );
   currentTextActorInfo.size = characterLayout.mSize * relayoutData.mShrinkFactor;
@@ -1538,10 +1882,6 @@ void CreateTextActor( const TextView::VisualParameters& visualParameters,
   currentTextActorInfo.color = style.GetTextColor();
   currentTextActorInfo.color.a = characterLayout.mColorAlpha;
 
-  currentTextActorInfo.gradientColor = characterLayout.mGradientColor;
-  currentTextActorInfo.startPoint = characterLayout.mStartPoint;
-  currentTextActorInfo.endPoint = characterLayout.mEndPoint;
-
   TextActor textActor = TextActor::DownCast( characterLayout.mGlyphActor );
 
   if( createGlyphActors )
@@ -1567,6 +1907,9 @@ void CreateTextActor( const TextView::VisualParameters& visualParameters,
         textActor.SetTextStyle( style );
       }
     }
+    characterLayout.mSetText = true;
+    currentTextActorInfo.characterLayout = &characterLayout;
+
     characterLayout.mGlyphActor = textActor;
   }
 
@@ -1575,46 +1918,57 @@ void CreateTextActor( const TextView::VisualParameters& visualParameters,
 }
 
 /**
- * Traverses the whole line initializating renderable-actor handles and updating them with the new size and position.
+ * Traverses the whole paragraph initializating renderable-actor handles and updating them with the new size and position.
  *
  * @param[in] visualParameters Some visual parameters (fade, sort modifier and blending).
  * @param[in,out] relayoutData Natural size (metrics), layout, text-actor info.
- * @param[in,out] line Layout info for the line.
+ * @param[in,out] paragraph Layout info for the paragraph.
  * @param[in,out] characterGlobalIndex Index to the character within the whole text.
- * @param[in,out] lineLayoutInfoIndex Index to the table of laid out lines.
+ * @param[in,out] lineLayoutInfoIndex Index to the table of lines.
  * @param[in,out] createGlyphActors Whether to initialize renderable-actor handles.
  */
-void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParameters,
-                                 TextView::RelayoutData& relayoutData,
-                                 TextViewProcessor::LineLayoutInfo& line,
-                                 std::size_t& characterGlobalIndex,
-                                 std::size_t& lineLayoutInfoIndex,
-                                 bool createGlyphActors )
+void UpdateTextActorInfoForParagraph( const TextView::VisualParameters& visualParameters,
+                                      TextView::RelayoutData& relayoutData,
+                                      TextViewProcessor::ParagraphLayoutInfo& paragraphLayout,
+                                      std::size_t& characterGlobalIndex,
+                                      std::size_t& lineLayoutInfoIndex,
+                                      bool createGlyphActors )
 {
   CurrentTextActorInfo currentTextActorInfo;
+  currentTextActorInfo.characterLayout = NULL;
 
-  const std::size_t lineLayoutInfoSize = relayoutData.mLines.size(); // Number of laid out lines.
-  bool lineLayoutEnd = false;            // Whether lineLayoutInfoIndex points at the last laid out line.
+  const std::size_t lineLayoutInfoSize = relayoutData.mLines.size(); // Number of lines.
+  bool lineLayoutEnd = false;            // Whether lineLayoutInfoIndex points at the last line.
   bool glyphActorCreatedForLine = false; // Whether a renderable actor has been created for this line.
 
   TextStyle currentStyle;                // style for the current text-actor.
 
-  Vector4 currentGradientColor;          // gradient color for the current text-actor.
-  Vector2 currentStartPoint;             // start point for the current text-actor.
-  Vector2 currentEndPoint;               // end point for the current text-actor.
+  TextViewProcessor::GradientInfo* currentGradientInfo = NULL; // gradient color for the current text-actor.
+                                                               // start point for the current text-actor.
+                                                               // end point for the current text-actor.
 
   bool currentIsColorGlyph = false;      // Whether current glyph is an emoticon.
 
   std::vector<TextActor> textActorsToRemove; // Keep a vector of text-actors to be included into the cache.
 
-  std::size_t characterLineIndex = 0u;   // Index to the character (within the line).
-  for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = line.mWordsLayoutInfo.begin(), wordEndIt = line.mWordsLayoutInfo.end();
+  // Retrieve the layout info to traverse. If there is right to left text it retrieves the right to left layout.
+  const bool isRightToLeftLayout = NULL != paragraphLayout.mRightToLeftLayout;
+
+  TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraphLayout.mRightToLeftLayout->mWordsLayoutInfo : paragraphLayout.mWordsLayoutInfo;
+  Text& text = isRightToLeftLayout ? paragraphLayout.mRightToLeftLayout->mText : paragraphLayout.mText;
+  Vector<TextStyle*>& textStyles = isRightToLeftLayout ? paragraphLayout.mRightToLeftLayout->mTextStyles : paragraphLayout.mTextStyles;
+
+  // In case the previous right to left layout has been cleared, all text-actors have been removed as well. If this bool is set to true, text-actors will be created again.
+  const bool previousRightToLeftLayoutCleared = isRightToLeftLayout ? paragraphLayout.mRightToLeftLayout->mPreviousLayoutCleared : false;
+
+  std::size_t characterParagraphIndex = 0u;   // Index to the character (within the paragraph).
+  for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = wordsLayoutInfo.begin(), wordEndIt = wordsLayoutInfo.end();
        wordIt != wordEndIt;
        ++wordIt )
   {
-    TextViewProcessor::WordLayoutInfo& word( *wordIt );
+    TextViewProcessor::WordLayoutInfo& wordLayout( *wordIt );
 
-    for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterIt = word.mCharactersLayoutInfo.begin(), characterEndIt = word.mCharactersLayoutInfo.end();
+    for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterIt = wordLayout.mCharactersLayoutInfo.begin(), characterEndIt = wordLayout.mCharactersLayoutInfo.end();
          characterIt != characterEndIt;
          ++characterIt )
     {
@@ -1636,33 +1990,40 @@ void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParamet
       }
 
       // Do not create a glyph-actor if there is no text.
-      const Character character = characterLayout.mStyledText.mText[0u]; // there are only one character per character layout.
-      const TextStyle& style = characterLayout.mStyledText.mStyle;
+      const Character character = text[characterParagraphIndex];
+      const TextStyle& style = *( *( textStyles.Begin() + characterParagraphIndex ) );
 
       bool appendCharacter = false;
 
       if( characterLayout.mIsColorGlyph ||
-          !character.IsWhiteSpace() || // A new line character is also a white space.
-          ( character.IsWhiteSpace() && style.IsUnderlineEnabled() ) )
+          ( TextViewProcessor::NoSeparator == wordLayout.mType ) ||
+          ( ( TextViewProcessor::WordSeparator == wordLayout.mType ) && style.IsUnderlineEnabled() ) )
       {
-        // Do not create a glyph-actor if it's a white space (without underline) or a new line character.
+        // Do not create a glyph-actor if it's a white space (without underline) or a new paragraph character.
 
-        // Creates one glyph-actor for each counsecutive group of characters, with the same style, per line, or if it's an emoticon.
+        // Check if the character has the same gradient info than the current one.
+        bool differentGradientInfo = false;
+        if( characterLayout.mGradientInfo && currentGradientInfo )
+        {
+          differentGradientInfo = ( characterLayout.mGradientInfo->mGradientColor != currentGradientInfo->mGradientColor ) ||
+            ( characterLayout.mGradientInfo->mStartPoint != currentGradientInfo->mStartPoint ) ||
+            ( characterLayout.mGradientInfo->mEndPoint != currentGradientInfo->mEndPoint );
+        }
+        else if( ( NULL != currentGradientInfo ) || ( NULL != characterLayout.mGradientInfo ) )
+        {
+          differentGradientInfo = true;
+        }
 
+        // Creates one glyph-actor for each counsecutive group of characters, with the same style, per line, or if it's an emoticon.
         if( !glyphActorCreatedForLine ||
             characterLayout.mIsColorGlyph ||
+            differentGradientInfo ||
             ( characterLayout.mIsColorGlyph != currentIsColorGlyph ) ||
-            ( style != currentStyle ) ||
-            ( characterLayout.mGradientColor != currentGradientColor ) ||
-            ( characterLayout.mStartPoint != currentStartPoint ) ||
-            ( characterLayout.mEndPoint != currentEndPoint ) )
+            ( style != currentStyle ) )
         {
           characterLayout.mSetText = false;
           characterLayout.mSetStyle = false;
 
-          // There is a new style or a new line.
-          glyphActorCreatedForLine = true;
-
           if( characterLayout.mIsColorGlyph )
           {
             CreateEmoticon( visualParameters,
@@ -1673,19 +2034,20 @@ void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParamet
           {
             CreateTextActor( visualParameters,
                              relayoutData,
-                             line,
+                             paragraphLayout,
                              characterLayout,
                              character,
                              style,
                              currentTextActorInfo,
-                             createGlyphActors );
+                             createGlyphActors || previousRightToLeftLayoutCleared );
           }
 
+          // There is a new style or a new line.
+          glyphActorCreatedForLine = true;
+
           // Update style to be checked with next characters.
           currentStyle = style;
-          currentGradientColor = characterLayout.mGradientColor;
-          currentStartPoint = characterLayout.mStartPoint;
-          currentEndPoint = characterLayout.mEndPoint;
+          currentGradientInfo = characterLayout.mGradientInfo;
           currentIsColorGlyph = characterLayout.mIsColorGlyph;
 
           characterLayout.mGlyphActor.SetParentOrigin( ParentOrigin::TOP_LEFT );
@@ -1714,7 +2076,7 @@ void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParamet
             characterLayout.mGlyphActor.Reset();
           }
         }
-      } // no white space / new line char
+      } // no white space / new paragraph char
       else
       {
         appendCharacter = true;
@@ -1723,7 +2085,7 @@ void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParamet
       if( appendCharacter )
       {
         // Add the character to the current text-actor and update the size.
-        if( characterLayout.mIsVisible && ( TextViewProcessor::LineSeparator != word.mType ) )
+        if( characterLayout.mIsVisible && ( TextViewProcessor::ParagraphSeparator != wordLayout.mType ) )
         {
           currentTextActorInfo.text.Append( character );
 
@@ -1734,7 +2096,7 @@ void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParamet
       }
 
       ++characterGlobalIndex;
-      ++characterLineIndex;
+      ++characterParagraphIndex;
     } // characters
   } // words
 
@@ -1742,14 +2104,19 @@ void UpdateTextActorInfoForLine( const TextView::VisualParameters& visualParamet
   {
     if( currentTextActorInfo.textActor )
     {
-      currentTextActorInfo.textActor.SetText( currentTextActorInfo.text );
+      if( ( NULL != currentTextActorInfo.characterLayout ) &&
+          currentTextActorInfo.characterLayout->mSetText )
+      {
+        currentTextActorInfo.textActor.SetText( currentTextActorInfo.text );
+        currentTextActorInfo.characterLayout->mSetText = false;
+      }
       currentTextActorInfo.textActor.SetPosition( currentTextActorInfo.position );
       currentTextActorInfo.textActor.SetSize( currentTextActorInfo.size );
 
       SetVisualParameters( currentTextActorInfo,
                            visualParameters,
                            relayoutData,
-                           line.mSize.height );
+                           paragraphLayout.mSize.height );
     }
   }
 
@@ -1761,29 +2128,30 @@ void UpdateTextActorInfo( const TextView::VisualParameters& visualParameters,
                           TextView::RelayoutData& relayoutData,
                           bool createGlyphActors )
 {
-  if( relayoutData.mTextLayoutInfo.mLinesLayoutInfo.empty() )
+  if( relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.empty() )
   {
-    // nothing to do if there is no lines.
+    // nothing to do if there is no paragraphs.
     return;
   }
 
   std::size_t characterGlobalIndex = 0u; // Index to the global character (within the whole text).
-  std::size_t lineLayoutInfoIndex = 0u;  // Index to the laid out line info.
+  std::size_t lineLayoutInfoIndex = 0u;  // Index to the line info.
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(), lineEndIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineIt != lineEndIt;
-       ++lineIt )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(), paragraphEndIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphIt != paragraphEndIt;
+       ++paragraphIt )
   {
-    TextViewProcessor::LineLayoutInfo& line( *lineIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraph( *paragraphIt );
 
-    UpdateTextActorInfoForLine( visualParameters,
-                                relayoutData,
-                                line,
-                                characterGlobalIndex,
-                                lineLayoutInfoIndex,
-                                createGlyphActors );
-  } // lines
+    UpdateTextActorInfoForParagraph( visualParameters,
+                                     relayoutData,
+                                     paragraph,
+                                     characterGlobalIndex,
+                                     lineLayoutInfoIndex,
+                                     createGlyphActors );
+  } // paragraphs
 
+  // Set visual parameters for ellipsis renderable actors.
   for( std::vector<RenderableActor>::iterator it = relayoutData.mEllipsizedGlyphActors.begin(),
          endIt = relayoutData.mEllipsizedGlyphActors.end();
        it != endIt;
@@ -1804,18 +2172,23 @@ void UpdateTextActorInfo( const TextView::VisualParameters& visualParameters,
 
 void CalculateUnderlineInfo( TextView::RelayoutData& relayoutData, TextViewRelayout::TextUnderlineStatus& textUnderlineStatus )
 {
-  // Traverse the whole text to find all groups of consecutive underlined characters in the same laid-out line.
+  // Traverse the whole text to find all groups of consecutive underlined characters in the same line.
   //
-  // Note that relayoutData.mTextLayoutInfo contains layout info per line but these lines are the result of split the whole text every time a '\n' is found.
-  // According with the layout option, one of this lines could be laid-out in more than one.
+  // Note that relayoutData.mTextLayoutInfo contains layout info per paragraph but these paragraphs are the result of split the whole text every time a '\n' is found.
+  // According with the layout option, one of this paragraphs could be laid-out in more than one line.
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(), lineEndIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineIt != lineEndIt;
-       ++lineIt )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(), paragraphEndIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphIt != paragraphEndIt;
+       ++paragraphIt )
   {
-    TextViewProcessor::LineLayoutInfo& line( *lineIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraph( *paragraphIt );
+
+    std::size_t characterIndex = 0u;
+
+    const bool isRightToLeftLayout = NULL != paragraph.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraph.mRightToLeftLayout->mWordsLayoutInfo : paragraph.mWordsLayoutInfo;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = line.mWordsLayoutInfo.begin(), wordEndIt = line.mWordsLayoutInfo.end();
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = wordsLayoutInfo.begin(), wordEndIt = wordsLayoutInfo.end();
          wordIt != wordEndIt;
          ++wordIt )
     {
@@ -1823,11 +2196,12 @@ void CalculateUnderlineInfo( TextView::RelayoutData& relayoutData, TextViewRelay
 
       for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterIt = word.mCharactersLayoutInfo.begin(), characterEndIt = word.mCharactersLayoutInfo.end();
            characterIt != characterEndIt;
-           ++characterIt )
+           ++characterIt, ++characterIndex )
       {
         TextViewProcessor::CharacterLayoutInfo& character( *characterIt );
+        const TextStyle& style = *( *( paragraph.mTextStyles.Begin() + characterIndex ) );
 
-        // Check if current character is the first of a new laid-out line
+        // Check if current character is the first of a new line
         const bool isNewLine = ( textUnderlineStatus.mLineGlobalIndex < relayoutData.mLines.size() ) &&
           ( textUnderlineStatus.mCharacterGlobalIndex == ( *( relayoutData.mLines.begin() + textUnderlineStatus.mLineGlobalIndex ) ).mCharacterGlobalIndex );
         if( isNewLine )
@@ -1835,10 +2209,10 @@ void CalculateUnderlineInfo( TextView::RelayoutData& relayoutData, TextViewRelay
           ++textUnderlineStatus.mLineGlobalIndex; // If it's a new line, point to the next one.
         }
 
-        if( character.mStyledText.mStyle.IsUnderlineEnabled() )
+        if( style.IsUnderlineEnabled() )
         {
           if( !textUnderlineStatus.mCurrentUnderlineStatus || // Current character is underlined but previous one it wasn't.
-              isNewLine )                                     // Current character is underlined and is the first of current laid-out line.
+              isNewLine )                                     // Current character is underlined and is the first of current line.
           {
             // Create a new underline info for the current underlined characters.
             UnderlineInfo underlineInfo;
@@ -1872,15 +2246,15 @@ void CalculateUnderlineInfo( TextView::RelayoutData& relayoutData, TextViewRelay
         ++textUnderlineStatus.mCharacterGlobalIndex;
       } // end characters.
     } // end words.
-  } // end lines.
+  } // end paragraphs.
 }
 
 void SetUnderlineInfo( TextView::RelayoutData& relayoutData )
 {
-  // Stores for each group of consecutive underlined characters in each laid-out line its maximum thicknes, its position of that thickness and the maximum character's height.
+  // Stores for each group of consecutive underlined characters in each line its maximum thicknes, its position of that thickness and the maximum character's height.
   TextViewRelayout::TextUnderlineStatus textUnderlineStatus;
 
-  // Traverse the whole text to find all groups of consecutive underlined characters in the same laid-out line.
+  // Traverse the whole text to find all groups of consecutive underlined characters in the same line.
   CalculateUnderlineInfo( relayoutData, textUnderlineStatus );
 
   if( textUnderlineStatus.mUnderlineInfo.empty() )
@@ -1910,13 +2284,17 @@ void SetUnderlineInfo( TextView::RelayoutData& relayoutData )
   float currentLineHeight = 0.f;
   float currentLineAscender = 0.f;
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(), lineEndIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineIt != lineEndIt;
-       ++lineIt )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(), paragraphEndIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphIt != paragraphEndIt;
+       ++paragraphIt )
   {
-    TextViewProcessor::LineLayoutInfo& line( *lineIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraph( *paragraphIt );
+    std::size_t characterIndex = 0u;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = line.mWordsLayoutInfo.begin(), wordEndIt = line.mWordsLayoutInfo.end();
+    const bool isRightToLeftLayout = NULL != paragraph.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraph.mRightToLeftLayout->mWordsLayoutInfo : paragraph.mWordsLayoutInfo;
+
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordIt = wordsLayoutInfo.begin(), wordEndIt = wordsLayoutInfo.end();
          wordIt != wordEndIt;
          ++wordIt )
     {
@@ -1924,11 +2302,12 @@ void SetUnderlineInfo( TextView::RelayoutData& relayoutData )
 
       for( TextViewProcessor::CharacterLayoutInfoContainer::iterator characterIt = word.mCharactersLayoutInfo.begin(), characterEndIt = word.mCharactersLayoutInfo.end();
            characterIt != characterEndIt;
-           ++characterIt )
+           ++characterIt, ++characterIndex )
       {
         TextViewProcessor::CharacterLayoutInfo& character( *characterIt );
+        TextStyle& style = *( *( paragraph.mTextStyles.Begin() + characterIndex ) );
 
-        // Check if current character is the first of a new laid-out line
+        // Check if current character is the first of a new line
 
         bool isNewLine = false;
 
@@ -1945,7 +2324,7 @@ void SetUnderlineInfo( TextView::RelayoutData& relayoutData )
           }
         }
 
-        if( character.mStyledText.mStyle.IsUnderlineEnabled() )
+        if( style.IsUnderlineEnabled() )
         {
           if( textUnderlineStatus.mCurrentUnderlineStatus )
           {
@@ -1970,7 +2349,7 @@ void SetUnderlineInfo( TextView::RelayoutData& relayoutData )
           const float positionOffset = ( underlineInfo.mMaxHeight - character.mSize.height ) - bearingOffset;
 
           // Sets the underline's parameters.
-          character.mStyledText.mStyle.SetUnderline( true, underlineInfo.mMaxThickness, underlineInfo.mPosition - positionOffset );
+          style.SetUnderline( true, underlineInfo.mMaxThickness, underlineInfo.mPosition - positionOffset );
 
           // Mark the character to be set the new style into the text-actor.
           character.mSetStyle = true;
@@ -1996,7 +2375,7 @@ void SetUnderlineInfo( TextView::RelayoutData& relayoutData )
         ++textUnderlineStatus.mCharacterGlobalIndex;
       } // end of characters.
     } // end of word.
-  } // end of lines.
+  } // end of paragraphs.
 }
 
 void RemoveGlyphActors( Actor textView,
@@ -2019,15 +2398,19 @@ void InsertToTextView( Actor textView,
 {
   // Add text-actors to the text-view.
 
-  for( TextViewProcessor::LineLayoutInfoContainer::iterator lineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin(),
-         endLineLayoutIt = relayoutData.mTextLayoutInfo.mLinesLayoutInfo.end();
-       lineLayoutIt != endLineLayoutIt;
-       ++lineLayoutIt )
+  for( TextViewProcessor::ParagraphLayoutInfoContainer::iterator paragraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.begin(),
+         endParagraphLayoutIt = relayoutData.mTextLayoutInfo.mParagraphsLayoutInfo.end();
+       paragraphLayoutIt != endParagraphLayoutIt;
+       ++paragraphLayoutIt )
   {
-    TextViewProcessor::LineLayoutInfo& lineLayoutInfo( *lineLayoutIt );
+    TextViewProcessor::ParagraphLayoutInfo& paragraphLayoutInfo( *paragraphLayoutIt );
+
+    // Retrieve the layout info to traverse. If there is right to left text it retrieves the right to left layout.
+    const bool isRightToLeftLayout = NULL != paragraphLayoutInfo.mRightToLeftLayout;
+    TextViewProcessor::WordLayoutInfoContainer& wordsLayoutInfo = isRightToLeftLayout ? paragraphLayoutInfo.mRightToLeftLayout->mWordsLayoutInfo : paragraphLayoutInfo.mWordsLayoutInfo;
 
-    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.begin(),
-           endWordLayoutIt = lineLayoutInfo.mWordsLayoutInfo.end();
+    for( TextViewProcessor::WordLayoutInfoContainer::iterator wordLayoutIt = wordsLayoutInfo.begin(),
+           endWordLayoutIt = wordsLayoutInfo.end();
          wordLayoutIt != endWordLayoutIt;
          ++wordLayoutIt )
     {
@@ -2048,7 +2431,7 @@ void InsertToTextView( Actor textView,
         }
       } // end character
     } // end words
-  } // end lines
+  } // end paragraphs
 
   for( std::vector<RenderableActor>::iterator it = relayoutData.mEllipsizedGlyphActors.begin(),
          endIt = relayoutData.mEllipsizedGlyphActors.end();