X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=dali-toolkit%2Finternal%2Ftext%2Fmarkup-processor.cpp;h=6ea6352859f243ea4e0bcfc1378f7e4f516f8f93;hb=99f2a4758a1830accbcd79f4bc6b5c0ca836e2fe;hp=84707adbfb2ba016b15653c915c94bd16c669936;hpb=69669144df0027a66725f167fd1b99e12b8860ad;p=platform%2Fcore%2Fuifw%2Fdali-toolkit.git diff --git a/dali-toolkit/internal/text/markup-processor.cpp b/dali-toolkit/internal/text/markup-processor.cpp index 84707ad..6ea6352 100644 --- a/dali-toolkit/internal/text/markup-processor.cpp +++ b/dali-toolkit/internal/text/markup-processor.cpp @@ -20,6 +20,8 @@ // INTERNAL INCLUDES #include +#include +#include #include namespace Dali @@ -45,18 +47,81 @@ const std::string XHTML_SHADOW_TAG("shadow"); const std::string XHTML_GLOW_TAG("glow"); const std::string XHTML_OUTLINE_TAG("outline"); -const char LESS_THAN = '<'; -const char GREATER_THAN = '>'; -const char EQUAL = '='; -const char QUOTATION_MARK = '\''; -const char LINE_SEPARATOR_CR = 0x0D; // Carriage return character CR -const char LINE_SEPARATOR_LF = 0x0A; // New line character LF -const char SLASH = '/'; -const char BACK_SLASH = '\\'; +const char LESS_THAN = '<'; +const char GREATER_THAN = '>'; +const char EQUAL = '='; +const char QUOTATION_MARK = '\''; +const char SLASH = '/'; +const char BACK_SLASH = '\\'; -const char WHITE_SPACE = 0x20; // ASCII value of the white space. +const char WHITE_SPACE = 0x20; // ASCII value of the white space. const unsigned int MAX_NUM_OF_ATTRIBUTES = 5u; ///< The font tag has the 'family', 'size' 'weight', 'width' and 'slant' attrubutes. +const unsigned int DEFAULT_VECTOR_SIZE = 16u; ///< Default size of run vectors. + +/** + * @brief Struct used to retrieve the style runs from the mark-up string. + */ +struct StyleStack +{ + typedef VectorBase::SizeType RunIndex; + + Vector stack; ///< Use a vector as a style stack. Stores the indices pointing where the run is stored inside the logical model. + unsigned int topIndex; ///< Points the top of the stack. + + StyleStack() + : stack(), + topIndex( 0u ) + { + stack.Resize( DEFAULT_VECTOR_SIZE ); + } + + void Push( RunIndex index ) + { + // Check if there is space inside the style stack. + const VectorBase::SizeType size = stack.Count(); + if( topIndex >= size ) + { + // Resize the style stack. + stack.Resize( 2u * size ); + } + + // Set the run index in the top of the stack. + *( stack.Begin() + topIndex ) = index; + + // Reposition the pointer to the top of the stack. + ++topIndex; + } + + RunIndex Pop() + { + // Pop the top of the stack. + --topIndex; + return *( stack.Begin() + topIndex ); + } +}; + +/** + * @brief Initializes a font run description to its defaults. + * + * @param[in,out] fontRun The font description run to initialize. + */ +void Initialize( FontDescriptionRun& fontRun ) +{ + fontRun.characterRun.characterIndex = 0u; + fontRun.characterRun.numberOfCharacters = 0u; + fontRun.familyName = NULL; + fontRun.familyLength = 0u; + fontRun.weight = TextAbstraction::FontWeight::NORMAL; + fontRun.width = TextAbstraction::FontWidth::NORMAL; + fontRun.slant = TextAbstraction::FontSlant::NORMAL; + fontRun.size = 0u; + fontRun.familyDefined = false; + fontRun.weightDefined = false; + fontRun.widthDefined = false; + fontRun.slantDefined = false; + fontRun.sizeDefined = false; +} /** * @brief Splits the tag string into the tag name and its attributes. @@ -297,6 +362,17 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma const Length markupStringSize = markupString.size(); markupProcessData.markupProcessedText.reserve( markupStringSize ); + // Stores a struct with the index to the first character of the run, the type of run and its parameters. + StyleStack styleStack; + + // Points the next free position in the vector of runs. + StyleStack::RunIndex colorRunIndex = 0u; + StyleStack::RunIndex fontRunIndex = 0u; + + // Give an initial default value to the model's vectors. + markupProcessData.colorRuns.Reserve( DEFAULT_VECTOR_SIZE ); + markupProcessData.fontRuns.Reserve( DEFAULT_VECTOR_SIZE ); + // Get the mark-up string buffer. const char* markupStringBuffer = markupString.c_str(); const char* const markupStringEndBuffer = markupStringBuffer + markupStringSize; @@ -314,10 +390,29 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma if( !tag.isEndTag ) { // Create a new color run. + ColorRun colorRun; + colorRun.characterRun.numberOfCharacters = 0u; + + // Set the start character index. + colorRun.characterRun.characterIndex = characterIndex; + + // Fill the run with the attributes. + ProcessColorTag( tag, colorRun ); + + // Push the color run in the logical model. + markupProcessData.colorRuns.PushBack( colorRun ); + + // Push the index of the run into the stack. + styleStack.Push( colorRunIndex ); + + // Point the next color run. + ++colorRunIndex; } else { // Pop the top of the stack and set the number of characters of the run. + ColorRun& colorRun = *( markupProcessData.colorRuns.Begin() + styleStack.Pop() ); + colorRun.characterRun.numberOfCharacters = characterIndex - colorRun.characterRun.characterIndex; } } // else if( TokenComparison( XHTML_I_TAG, tag.buffer, tag.length ) ) @@ -325,10 +420,28 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma if( !tag.isEndTag ) { // Create a new font run. + FontDescriptionRun fontRun; + Initialize( fontRun ); + + // Fill the run with the parameters. + fontRun.characterRun.characterIndex = characterIndex; + fontRun.slant = TextAbstraction::FontSlant::ITALIC; + fontRun.slantDefined = true; + + // Push the font run in the logical model. + markupProcessData.fontRuns.PushBack( fontRun ); + + // Push the index of the run into the stack. + styleStack.Push( fontRunIndex ); + + // Point the next free font run. + ++fontRunIndex; } else { // Pop the top of the stack and set the number of characters of the run. + FontDescriptionRun& fontRun = *( markupProcessData.fontRuns.Begin() + styleStack.Pop() ); + fontRun.characterRun.numberOfCharacters = characterIndex - fontRun.characterRun.characterIndex; } } // else if( TokenComparison( XHTML_U_TAG, tag.buffer, tag.length ) ) @@ -347,10 +460,28 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma if( !tag.isEndTag ) { // Create a new font run. + FontDescriptionRun fontRun; + Initialize( fontRun ); + + // Fill the run with the parameters. + fontRun.characterRun.characterIndex = characterIndex; + fontRun.weight = TextAbstraction::FontWeight::BOLD; + fontRun.weightDefined = true; + + // Push the font run in the logical model. + markupProcessData.fontRuns.PushBack( fontRun ); + + // Push the index of the run into the stack. + styleStack.Push( fontRunIndex ); + + // Point the next free font run. + ++fontRunIndex; } else { // Pop the top of the stack and set the number of characters of the run. + FontDescriptionRun& fontRun = *( markupProcessData.fontRuns.Begin() + styleStack.Pop() ); + fontRun.characterRun.numberOfCharacters = characterIndex - fontRun.characterRun.characterIndex; } } // else if( TokenComparison( XHTML_FONT_TAG, tag.buffer, tag.length ) ) @@ -358,10 +489,28 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma if( !tag.isEndTag ) { // Create a new font run. + FontDescriptionRun fontRun; + Initialize( fontRun ); + + // Fill the run with the parameters. + fontRun.characterRun.characterIndex = characterIndex; + + ProcessFontTag( tag, fontRun ); + + // Push the font run in the logical model. + markupProcessData.fontRuns.PushBack( fontRun ); + + // Push the index of the run into the stack. + styleStack.Push( fontRunIndex ); + + // Point the next free font run. + ++fontRunIndex; } else { // Pop the top of the stack and set the number of characters of the run. + FontDescriptionRun& fontRun = *( markupProcessData.fontRuns.Begin() + styleStack.Pop() ); + fontRun.characterRun.numberOfCharacters = characterIndex - fontRun.characterRun.characterIndex; } } // else if( TokenComparison( XHTML_SHADOW_TAG, tag.buffer, tag.length ) ) @@ -412,15 +561,6 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma ++markupStringBuffer; } } - else if( ( LINE_SEPARATOR_CR == character ) && ( markupStringBuffer + 1u < markupStringEndBuffer ) ) - { - // Replacing CR+LF end line by LF. - if( LINE_SEPARATOR_LF == *( markupStringBuffer + 1u ) ) - { - character = LINE_SEPARATOR_LF; - ++markupStringBuffer; - } - } const unsigned char numberOfBytes = GetUtf8Length( character ); @@ -437,6 +577,23 @@ void ProcessMarkupString( const std::string& markupString, MarkupProcessData& ma } // Resize the model's vectors. + if( 0u == fontRunIndex ) + { + markupProcessData.fontRuns.Clear(); + } + else + { + markupProcessData.fontRuns.Resize( fontRunIndex ); + } + + if( 0u == colorRunIndex ) + { + markupProcessData.colorRuns.Clear(); + } + else + { + markupProcessData.colorRuns.Resize( colorRunIndex ); + } } } // namespace Text