TextModel - Create the text segmentation info for a given range of characters inside...
[platform/core/uifw/dali-toolkit.git] / dali-toolkit / internal / text / text-style-run-container.h
1 #ifndef __DALI_TOOLKIT_TEXT_STYLE_RUN_CONTAINER_H__
2 #define __DALI_TOOLKIT_TEXT_STYLE_RUN_CONTAINER_H__
3
4 /*
5  * Copyright (c) 2015 Samsung Electronics Co., Ltd.
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  */
20
21 // INTERNAL INCLUDES
22 #include <dali-toolkit/internal/text/character-run.h>
23
24 namespace Dali
25 {
26
27 namespace Toolkit
28 {
29
30 namespace Text
31 {
32
33 /**
34  * @brief Updates the number of characters and the character index of the text's style runs.
35  *
36  * If the @p numberOfCharacters is a negative value, it means the number of characters that are removed starting from the @p index.
37  *
38  * It deletes runs if all their characters are removed.
39  *
40  * @param[in] index Index to the first character updated.
41  * @param[in] numberOfCharacters The number of characters to be updated.
42  * @param[in] totalNumberOfCharacters Total number of characters of the text.
43  * @param[in,out] runs The text's style runs.
44  * @param[out] removedRuns The text's style removed runs.
45  */
46 template< typename T >
47 void UpdateCharacterRuns( CharacterIndex index,
48                           int numberOfCharacters,
49                           Length totalNumberOfCharacters,
50                           Vector<T>& runs,
51                           Vector<T>& removedRuns )
52 {
53   if( 0 > numberOfCharacters )
54   {
55     // Remove characters.
56     const Length numberOfRemovedCharacters = -numberOfCharacters;
57
58     if( ( 0u == index ) && ( numberOfRemovedCharacters == totalNumberOfCharacters ) )
59     {
60       // Set the removed runs.
61       removedRuns = runs;
62
63       // All characters are removed.
64       runs.Clear();
65
66       // Nothing else to do.
67       return;
68     }
69
70     const VectorBase::SizeType size = runs.Count();
71     // Temporary vector used to remove runs.
72     Vector<T> tempRuns;
73     // Reserve some space for the temporary vector.
74     tempRuns.Reserve( size );
75     removedRuns.Reserve( size );
76
77     // Whether any run has to be removed.
78     bool runsRemoved = false;
79
80     // Index to the last character added/removed.
81     const CharacterIndex lastIndex = index + numberOfRemovedCharacters - 1u;
82
83     // Update the style runs
84     for( typename Vector<T>::Iterator it = runs.Begin(),
85            endIt = runs.End();
86          it != endIt;
87          ++it )
88     {
89       T& run = *it;
90
91       const CharacterIndex lastRunIndex = run.characterRun.characterIndex + run.characterRun.numberOfCharacters - 1u;
92
93       if( lastRunIndex < index )
94       {
95         // The style run is not affected by the removed text.
96         tempRuns.PushBack( run );
97         continue;
98       }
99
100       if( ( index <= run.characterRun.characterIndex ) &&
101           ( lastIndex >= lastRunIndex ) )
102       {
103         // Add the removed run into the vector.
104         removedRuns.PushBack( run );
105
106         // All the characters are removed.
107         runsRemoved = true;
108       }
109       else
110       {
111         if( lastIndex < run.characterRun.characterIndex )
112         {
113           // Just move the character index.
114           run.characterRun.characterIndex -= numberOfRemovedCharacters;
115         }
116         else
117         {
118           if( run.characterRun.characterIndex < index )
119           {
120             // Remove characters starting from a character within the run.
121             run.characterRun.numberOfCharacters -= std::min( numberOfRemovedCharacters, 1u + lastRunIndex - index );
122           }
123           else
124           {
125             // Remove characters starting from a character located before the first index of the run.
126             run.characterRun.numberOfCharacters -= 1u + lastIndex - run.characterRun.characterIndex;
127             run.characterRun.characterIndex = index;
128           }
129         }
130
131         tempRuns.PushBack( run );
132       }
133     }
134
135     // Copy the temporary vector if there are runs removed.
136     if( runsRemoved )
137     {
138       runs = tempRuns;
139     }
140   }
141   else
142   {
143     // Add characters.
144
145     // Update the style runs
146     for( typename Vector<T>::Iterator it = runs.Begin(),
147            endIt = runs.End();
148          it != endIt;
149          ++it )
150     {
151       T& run = *it;
152
153       // Update the number of characters of the style run.
154
155       if( ( 0u == index ) && ( 0u == run.characterRun.characterIndex ) )
156       {
157         run.characterRun.numberOfCharacters += numberOfCharacters;
158       }
159       else if( index <= run.characterRun.characterIndex )
160       {
161         run.characterRun.characterIndex += numberOfCharacters;
162       }
163       else if( index <= run.characterRun.characterIndex + run.characterRun.numberOfCharacters )
164       {
165         run.characterRun.numberOfCharacters += numberOfCharacters;
166       }
167     }
168   }
169 }
170
171 } // namespace Text
172
173 } // namespace Toolkit
174
175 } // namespace Dali
176
177 #endif // __DALI_TOOLKIT_TEXT_STYLE_RUN_CONTAINER_H__