2 // Open Service Platform
3 // Copyright (c) 2012-2013 Samsung Electronics Co., Ltd.
5 // Licensed under the Flora License, Version 1.0 (the License);
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
9 // http://floralicense.org/license/
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an AS IS BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
19 * @file FGrp_TextTextComposite.cpp
20 * @brief This is the implementation file for TextComposite class.
25 #include <FBaseSysLog.h>
26 #include <FApp_AppInfo.h>
27 #include "FGrp_TextCommon.h"
28 #include "FGrp_TextTextElement.h"
29 #include "FGrp_TextTextSimple.h"
30 #include "FGrp_TextTextCutLink.h"
31 #include "FGrp_TextTextLine.h"
32 #include "FGrp_TextTextColumn.h"
33 #include "FGrp_TextTextCutLinkListInfo.h"
34 #include "FGrp_TextTextComposite.h"
35 #include "FGrp_TextTextUtility.h"
36 #include "FGrp_CanvasImpl.h"
37 #include "FGrp_TextTextWidthManager.h"
38 #include "../FGrp_Canvas.h"
40 using namespace Tizen::Base;
41 using namespace Tizen::Base::Utility;
42 using namespace Tizen::Base::Collection;
51 namespace Tizen { namespace Graphics
57 struct NoneWrapComposeInfo
66 TextComposite::TextComposite(TextElement* pTextElement)
68 __pTextElementList = new (std::nothrow) LinkedList;
71 , , E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
73 __wrap = TEXT_OBJECT_WRAP_TYPE_WORD;
78 __displayBlock = false;
79 __defaultBlockColor = Color(183, 212, 247);
82 __ignoreRearBlank = true;
83 __ignoreFrontBlank = false;
85 __rearSpaceHideMode = TEXT_OBJECT_SPACE_HIDE_TYPE_ONE;
86 __frontSpaceHideMode = TEXT_OBJECT_SPACE_HIDE_TYPE_ONE;
89 __elementVertialAlignment = TEXT_OBJECT_ALIGNMENT_BOTTOM;
90 __pCurrentTextColumn = null;
91 __pCutLinkListInfo = new (std::nothrow)TextCutLinkListInfo;
94 wchar_t abbrevText[2];
95 abbrevText[0] = TEXT_ABBREV_CHARACTER;
98 __pAbbrevTextElement = new (std::nothrow)TextSimple(abbrevText, 1, TEXT_ELEMENT_SOURCE_TYPE_INTERNAL, null,
99 Color::GetColor(COLOR_ID_BLACK), Color::GetColor(COLOR_ID_WHITE), Color::GetColor(COLOR_ID_WHITE));
102 if (pTextElement != null)
104 AppendElement(*pTextElement);
106 __drawAbbrevText = false;
107 __drawTextEllipsis = false;
108 __TextObjectEllipsisType = TEXT_OBJECT_ELLIPSIS_TYPE_TAIL;
110 __partialComposingModeEnabled = false;
111 __lineIndexCompositeDone = 0;
112 __totalComposedHeight = 0;
113 __composePartialLimitHeight = 0;
115 __headEllipsisTextLength = 0;
116 __headEllipsisWidth = 0;
117 __middleEllipsisHeadWidth = 0;
118 __middleEllipsisTextLengthInHead = 0;
119 __middleEllipsisTextLengthInTail = 0;
120 __middleEllipsisWidth = 0;
122 __pTextWidthManager = null;
123 __widthManagerEnabled = false;
128 TextComposite::~TextComposite(void)
130 if (__pCutLinkListInfo)
132 delete __pCutLinkListInfo;
133 __pCutLinkListInfo = null;
136 if (__pTextElementList)
138 RemoveAllElements(true);
139 delete __pTextElementList;
140 __pTextElementList = null;
143 if (__pAbbrevTextElement)
145 delete __pAbbrevTextElement;
146 __pAbbrevTextElement = null;
151 TextComposite::ForwardAnalyze(int startTextIndex, int textLength, int maxWidth, TextObjectWrapType wrap, int& actualLength,
152 int& width, int& height)
155 , 0 <= startTextIndex && startTextIndex < __length
156 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid. startTextIndex(%d)", startTextIndex);
159 , textLength <= __length
160 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid. textLength(%d)", textLength);
162 result r = E_SUCCESS;
165 int elementTextOffset = 0;
166 int elementIndex = 0;
167 int textIndexFromElementOffset = 0;
168 int remainingWidth = 0;
169 int remainingLength = 0;
171 int currentLength = 0;
172 int ret = TEXT_RETBY_NORMAL;
174 IEnumerator* pEnum = null;
175 TextElement* pTextElement = null;
177 bool isFirstWord = true;
178 Dimension tempTextSize;
179 int tempTextCount = 0;
184 pTextElement = GetElementAtTextIndex(startTextIndex, elementTextOffset, elementIndex, currentLength,
185 textIndexFromElementOffset);
188 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
191 remainingWidth = maxWidth;
192 remainingLength = textLength;
193 currentLength = Math::Min(remainingLength, currentLength);
195 pEnum = __pTextElementList->GetEnumeratorN();
196 for (int i = 0; i <= elementIndex; i++)
198 r = pEnum->MoveNext();
201 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
204 while ((remainingWidth != 0) && (remainingLength != 0))
206 ret = pTextElement->ForwardAnalyze(textIndexFromElementOffset, currentLength, remainingWidth,
207 __wrap, textCount, textSize.width, textSize.height);
209 textSize.height += __lineSpacing;
211 remainingWidth -= textSize.width;
212 remainingLength -= textCount;
213 currentLength -= textCount;
217 actualLength += textCount;
218 width += textSize.width;
219 height = Math::Max(textSize.height, height);
222 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD && ret != TEXT_RETBY_LIMITWIDTH)
224 tempTextCount = actualLength;
225 tempTextSize.width = width;
226 tempTextSize.height = height;
229 if (ret == TEXT_RETBY_OVERWIDTH || ret == TEXT_RETBY_LINEFEED)
234 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD)
236 if (ret == TEXT_RETBY_LIMITWIDTH)
238 if (isFirstWord == false)
240 actualLength = tempTextCount;
241 width = tempTextSize.width;
242 height = tempTextSize.height;
244 ret = TEXT_RETBY_NORMAL;
251 if (0 < currentLength)
253 textIndexFromElementOffset += textCount;
259 if (ret == TEXT_RETBY_LIMITWIDTH)
265 if (pEnum->MoveNext() != E_SUCCESS)
270 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
271 if (pTextElement == null)
277 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
278 currentLength = Math::Min(pTextElement->GetTextLength(), remainingLength);
281 if (ret == TEXT_RETBY_LIMITLENGTH)
283 ret = TEXT_RETBY_NORMAL;
286 SetLastResult(E_SUCCESS);
296 TextComposite::ForwardAnalyzeWithBaseline(int startTextIndex, int textLength, int maxWidth, TextObjectWrapType wrap, int& actualLength,
297 int& width, int& height, int& baseline)
300 , 0 <= startTextIndex && startTextIndex < __length
301 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid. startTextIndex(%d)", startTextIndex);
304 , textLength <= __length
305 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid. textLength(%d)", textLength);
307 result r = E_SUCCESS;
310 int elementTextOffset = 0;
311 int elementIndex = 0;
312 int textIndexFromElementOffset = 0;
313 int remainingWidth = 0;
314 int remainingLength = 0;
316 int currentLength = 0;
317 int ret = TEXT_RETBY_NORMAL;
318 bool isMaxHeightImage = false;
320 IEnumerator* pEnum = null;
321 TextElement* pTextElement = null;
323 bool isFirstWord = true;
324 Dimension tempTextSize;
325 int tempTextCount = 0;
330 pTextElement = GetElementAtTextIndex(startTextIndex, elementTextOffset, elementIndex, currentLength,
331 textIndexFromElementOffset);
334 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
337 remainingWidth = maxWidth;
338 remainingLength = textLength;
339 currentLength = Math::Min(remainingLength, currentLength);
340 baseline = pTextElement->GetBaseline();
342 pEnum = __pTextElementList->GetEnumeratorN();
343 for (int i = 0; i <= elementIndex; i++)
345 r = pEnum->MoveNext();
348 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
351 while (remainingLength != 0)
353 ret = pTextElement->ForwardAnalyze(textIndexFromElementOffset, currentLength, remainingWidth,
354 __wrap, textCount, textSize.width, textSize.height);
356 textSize.height += __lineSpacing;
357 remainingWidth -= textSize.width;
358 remainingLength -= textCount;
359 currentLength -= textCount;
363 actualLength += textCount;
364 width += textSize.width;
365 baseline = Math::Max(pTextElement->GetBaseline(), baseline);
367 // height = Math::Max(textSize.height, height);
368 if (height < textSize.height)
370 height = textSize.height;
372 (pTextElement->GetType() == TEXT_ELEMENT_TYPE_IMAGE) ? isMaxHeightImage = true : isMaxHeightImage = false;
376 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD && ret != TEXT_RETBY_LIMITWIDTH)
378 tempTextCount = actualLength;
379 tempTextSize.width = width;
380 tempTextSize.height = height;
383 if (ret == TEXT_RETBY_OVERWIDTH || ret == TEXT_RETBY_LINEFEED)
388 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD)
390 if (ret == TEXT_RETBY_LIMITWIDTH)
392 if (isFirstWord == false)
394 actualLength = tempTextCount;
395 width = tempTextSize.width;
396 height = tempTextSize.height;
398 ret = TEXT_RETBY_NORMAL;
405 if (0 < currentLength)
407 textIndexFromElementOffset += textCount;
413 if (ret == TEXT_RETBY_LIMITWIDTH)
419 if (pEnum->MoveNext() != E_SUCCESS)
424 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
425 if (pTextElement == null)
431 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
432 currentLength = Math::Min(pTextElement->GetTextLength(), remainingLength);
435 if (ret == TEXT_RETBY_LIMITLENGTH)
437 ret = TEXT_RETBY_NORMAL;
440 if (isMaxHeightImage)
445 SetLastResult(E_SUCCESS);
455 TextComposite::GetRegion(int textIndex, int textLength, int& width, int& height) const
458 , 0 <= textIndex && textIndex < __length
459 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid. textIndex(%d) __length(%d)"
460 , textIndex, __length);
463 , textLength <= __length
464 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid. textIndex(%d) __length(%d)"
465 , textIndex, __length);
467 result r = E_SUCCESS;
468 IEnumerator* pEnum = null;
469 TextElement* pTextElement = null;
471 int currentLength = 0;
472 int elementTextOffset = 0;
473 int elementIndex = 0;
474 int textIndexFromElementOffset = 0;
479 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
480 textIndexFromElementOffset);
483 , r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
485 pEnum = __pTextElementList->GetEnumeratorN();
486 for (int i = 0; i <= elementIndex; i++)
488 r = pEnum->MoveNext();
491 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
494 currentLength = Math::Min(currentLength, textLength);
496 while (textLength != 0)
498 pTextElement->GetRegion(textIndexFromElementOffset, currentLength, textSize.width, textSize.height);
500 width += textSize.width;
501 height = Math::Max(height, textSize.height);
502 textLength -= currentLength;
504 if (pEnum->MoveNext() != E_SUCCESS)
509 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
510 if (pTextElement == null)
515 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
516 currentLength = Math::Min(textLength, pTextElement->GetTextLength());
531 TextComposite::GetHeight(int textIndex) const
539 , 0 <= textIndex && textIndex < __length
540 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
542 TextElement* pTextElement = null;
543 int currentLength = 0;
544 int elementTextOffset = 0;
545 int elementIndex = 0;
546 int textIndexFromElementOffset = 0;
548 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
549 textIndexFromElementOffset);
552 , , E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
554 return pTextElement->GetHeight();
561 TextComposite::Draw(_CanvasImpl& canvasImpl, Rectangle& displayRect, int startTextIndex, int textLength, const TextObjectAlignment alignment,
562 const TextObjectActionType action)
570 , 0 <= startTextIndex && startTextIndex < __length
571 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
574 , textLength <= __length
575 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
577 result r = E_SUCCESS;
578 IEnumerator* pEnum = null;
579 TextElement* pTextElement = null;
582 Dimension spaceCharDim;
583 Dimension abbrevTextDim;
584 Rectangle adjustedRect = displayRect;
585 int currentLength = 0;
586 int elementTextOffset = 0;
587 int elementIndex = 0;
588 int textIndexFromElementOffset = 0;
589 int blockStartTextIndex = 0;
590 int blockEndTextIndex = 0;
591 bool drawAbbrevText = false;
592 bool isAlternateLookEnabled = false;
594 _Canvas* pCanvas = _Canvas::GetInstance(canvasImpl);
597 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get native canvas instance.");
599 pTextElement = GetElementAtTextIndex(startTextIndex + textLength - 1, elementTextOffset, elementIndex, currentLength,
600 textIndexFromElementOffset);
602 if (pTextElement && __ignoreRearBlank && __rearSpaceHideMode == TEXT_OBJECT_SPACE_HIDE_TYPE_ONE)
604 const TextSimple* pSimpleText = dynamic_cast <const TextSimple*>(pTextElement);
605 if (pSimpleText != null)
607 int length = startTextIndex + textLength - elementTextOffset - 1;
608 const wchar_t* pText = pSimpleText->GetText();
611 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text.");
614 , length >= 0 && length < pSimpleText->GetTextLength()
615 , E_OUT_OF_RANGE, E_OUT_OF_RANGE
616 , "[E_OUT_OF_RANGE] text index(%d) must greater than 0 and must be less than total string length(%d)",length, pSimpleText->GetTextLength());
618 if (pText[length] == (wchar_t)L' ')
620 GetRegion(length + elementTextOffset, 1, spaceCharDim.width, spaceCharDim.height);
626 pTextElement = GetElementAtTextIndex(startTextIndex, elementTextOffset, elementIndex, currentLength,
627 textIndexFromElementOffset);
630 , r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get element.");
632 if (__ignoreFrontBlank && __frontSpaceHideMode == TEXT_OBJECT_SPACE_HIDE_TYPE_ONE)
634 const TextSimple* pSimpleText = dynamic_cast <const TextSimple*>(pTextElement);
635 if (pSimpleText != null)
637 int index = startTextIndex - elementTextOffset;
638 const wchar_t* pText = pSimpleText->GetText();
641 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text.");
644 , index >= 0 && index < pSimpleText->GetTextLength()
645 , E_OUT_OF_RANGE, E_OUT_OF_RANGE
646 , "[E_OUT_OF_RANGE] text index(%d) must greater than 0 and must be less than total string length(%d)",index, pSimpleText->GetTextLength());
648 if (pText[index] == (wchar_t)L' ')
650 GetRegion(textIndexFromElementOffset, 1, spaceCharDim.width, spaceCharDim.height);
654 textIndexFromElementOffset++;
659 switch (alignment & TEXT_ALIGNMASK_HORIZ)
661 case TEXT_OBJECT_ALIGNMENT_LEFT:
666 case TEXT_OBJECT_ALIGNMENT_CENTER:
667 GetRegion(startTextIndex, textLength, textSize.width, textSize.height);
668 if (textSize.width < adjustedRect.width)
670 adjustedRect.x += (adjustedRect.width - textSize.width) / 2;
674 case TEXT_OBJECT_ALIGNMENT_RIGHT:
675 GetRegion(startTextIndex, textLength, textSize.width, textSize.height);
676 if (textSize.width < adjustedRect.width)
678 adjustedRect.x += adjustedRect.width - textSize.width;
683 pEnum = __pTextElementList->GetEnumeratorN();
684 for (int i = 0; i <= elementIndex; i++)
686 r = pEnum->MoveNext();
689 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
692 currentLength = Math::Min(textLength, currentLength);
694 while (textLength > 0)
696 textLength -= currentLength;
698 pTextElement->GetRegion(textIndexFromElementOffset, currentLength, textSize.width, textSize.height);
700 if (action == TEXT_OBJECT_ACTION_TYPE_ABBREV && (pTextElement->GetType() == TEXT_ELEMENT_TYPE_TEXT))
702 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
705 , r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to cast text element.");
707 SetAbbrevObjectFontInfo(pSimpleText);
710 __pAbbrevTextElement->GetRegion(0, 1, abbrevTextDim.width, abbrevTextDim.height);
712 if (adjustedRect.width < textSize.width + abbrevTextDim.width || textLength <= 0)
714 int endType = TEXT_RETBY_NORMAL;
716 if (adjustedRect.width > abbrevTextDim.width)
718 int remainingLength = pSimpleText->GetTextLength() - textIndexFromElementOffset;
719 endType = pSimpleText->ForwardAnalyze(textIndexFromElementOffset, remainingLength, adjustedRect.width - abbrevTextDim.width,
720 TEXT_OBJECT_WRAP_TYPE_NONE, textCount, textSize.width, textSize.height);
722 if (endType == TEXT_RETBY_OVERWIDTH)
733 textSize.height = pSimpleText->GetHeight();
736 currentLength = textCount;
737 drawAbbrevText = true;
739 switch (alignment & TEXT_ALIGNMASK_HORIZ)
741 case TEXT_OBJECT_ALIGNMENT_CENTER:
742 if (textSize.width + abbrevTextDim.width < adjustedRect.width)
744 adjustedRect.x = displayRect.x + (adjustedRect.width - (textSize.width + abbrevTextDim.width)) / 2;
748 case TEXT_OBJECT_ALIGNMENT_RIGHT:
749 if (textSize.width + abbrevTextDim.width < adjustedRect.width)
751 adjustedRect.x = displayRect.x + adjustedRect.width - (textSize.width + abbrevTextDim.width);
755 case TEXT_OBJECT_ALIGNMENT_LEFT:
763 switch (alignment & TEXT_ALIGNMASK_VERT)
765 case TEXT_OBJECT_ALIGNMENT_TOP:
768 adjustedRect.y = displayRect.y;
771 case TEXT_OBJECT_ALIGNMENT_MIDDLE:
772 adjustedRect.y = displayRect.y + (displayRect.height - textSize.height) / 2;
775 case TEXT_OBJECT_ALIGNMENT_BOTTOM:
776 adjustedRect.y = displayRect.y + (displayRect.height - textSize.height);
780 if (pTextElement->IsBackGroundDrawingModeEnable())
783 r = pTextElement->GetRegion(textIndexFromElementOffset, currentLength, blockSize.width, blockSize.height);
786 , r, r, "[%s] Propagating.", GetErrorMessage(r));
788 r = pCanvas->FillRectangle(pTextElement->GetBackgroundColor(), Rectangle(adjustedRect.x, displayRect.y, blockSize.width, displayRect.height));
791 , r, r, "[%s] Propagating.", GetErrorMessage(r));
794 isAlternateLookEnabled = (bool)pTextElement->GetValue(SET_ALTERNATE_LOOK);
795 if (__displayBlock && isAlternateLookEnabled == false)
797 Dimension tempTextSize;
800 blockStartTextIndex = Math::Max(__workStart, startTextIndex);
801 blockEndTextIndex = Math::Min(__workStart + __workLength, startTextIndex + currentLength);
803 if (blockStartTextIndex < blockEndTextIndex)
805 blockStartTextIndex = textIndexFromElementOffset + (blockStartTextIndex - startTextIndex);
806 blockEndTextIndex = textIndexFromElementOffset + (blockEndTextIndex - startTextIndex);
807 adjustedX = adjustedRect.x;
809 if (textIndexFromElementOffset < blockStartTextIndex)
811 //[TODO] yunji19.park : to change api -> _Font::GetPosition()
812 pTextElement->GetRegion(textIndexFromElementOffset, blockStartTextIndex - textIndexFromElementOffset, tempTextSize.width, tempTextSize.height);
813 adjustedX += tempTextSize.width;
816 Rectangle blockRect = adjustedRect;
817 blockRect.x = adjustedX;
820 int blockLength = blockEndTextIndex - blockStartTextIndex;
821 r = pTextElement->GetBlockRegion(blockStartTextIndex, blockLength, blockSize.width, blockSize.height);
824 , r, r, "[%s] Propagating.", GetErrorMessage(r));
826 r = pCanvas->FillRectangle(__defaultBlockColor, Rectangle(blockRect.x, displayRect.y, blockSize.width, displayRect.height));
829 , r, r, "[%s] Propagating.", GetErrorMessage(r));
833 pTextElement->Draw(canvasImpl, adjustedRect, textIndexFromElementOffset, currentLength, alignment, action);
835 adjustedRect.x += textSize.width;
836 adjustedRect.width -= textSize.width;
840 if (pTextElement->IsBackGroundDrawingModeEnable())
842 r = pCanvas->FillRectangle(pTextElement->GetBackgroundColor(), Rectangle(adjustedRect.x, displayRect.y, abbrevTextDim.width, displayRect.height));
845 , r, r, "[%s] Propagating.", GetErrorMessage(r));
848 __pAbbrevTextElement->Draw(canvasImpl, adjustedRect, 0, 1, (TextObjectAlignment)(TEXT_OBJECT_ALIGNMENT_TOP | TEXT_OBJECT_ALIGNMENT_LEFT), action);
850 adjustedRect.x += abbrevTextDim.width;
851 adjustedRect.width -= abbrevTextDim.width;
856 if (!textLength || adjustedRect.width <= 0)
861 startTextIndex += currentLength;
863 if (pEnum->MoveNext() != E_SUCCESS)
868 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
869 if (pTextElement == null)
874 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
875 currentLength = Math::Min(textLength, pTextElement->GetTextLength());
877 if (currentLength == 0)
892 TextComposite::DrawWithBaseline(_CanvasImpl& canvasImpl, Rectangle& displayRect, int startTextIndex, int textLength, const TextObjectAlignment alignment,
893 const TextObjectActionType action, int baseline)
901 , 0 <= startTextIndex && startTextIndex < __length
902 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
905 , textLength <= __length
906 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
908 result r = E_SUCCESS;
909 IEnumerator* pEnum = null;
910 TextElement* pTextElement = null;
913 Dimension spaceCharDim;
914 Dimension abbrevTextDim;
915 Rectangle adjustedRect = displayRect;
916 int currentLength = 0;
917 int elementTextOffset = 0;
918 int elementIndex = 0;
919 int textIndexFromElementOffset = 0;
920 int blockStartTextIndex = 0;
921 int blockEndTextIndex = 0;
922 bool drawAbbrevText = false;
923 bool isAlternateLookEnabled = false;
925 _Canvas* pCanvas = _Canvas::GetInstance(canvasImpl);
928 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get native canvas instance.");
930 pTextElement = GetElementAtTextIndex(startTextIndex + textLength - 1, elementTextOffset, elementIndex, currentLength,
931 textIndexFromElementOffset);
933 if (pTextElement && __ignoreRearBlank && __rearSpaceHideMode == TEXT_OBJECT_SPACE_HIDE_TYPE_ONE)
935 const TextSimple* pSimpleText = dynamic_cast <const TextSimple*>(pTextElement);
936 if (pSimpleText != null)
938 int length = startTextIndex + textLength - elementTextOffset - 1;
939 const wchar_t* pText = pSimpleText->GetText();
942 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text.");
945 , length >= 0 && length < pSimpleText->GetTextLength()
946 , E_OUT_OF_RANGE, E_OUT_OF_RANGE, "[E_OUT_OF_RANGE] text index(%d) must greater than 0 and must be less than total string length(%d)",length, pSimpleText->GetTextLength());
948 if (pText[length] == (wchar_t)L' ')
950 GetRegion(length + elementTextOffset, 1, spaceCharDim.width, spaceCharDim.height);
956 pTextElement = GetElementAtTextIndex(startTextIndex, elementTextOffset, elementIndex, currentLength,
957 textIndexFromElementOffset);
960 , r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get element.");
962 if (__ignoreFrontBlank && __frontSpaceHideMode == TEXT_OBJECT_SPACE_HIDE_TYPE_ONE)
964 const TextSimple* pSimpleText = dynamic_cast <const TextSimple*>(pTextElement);
965 if (pSimpleText != null)
967 int index = startTextIndex - elementTextOffset;
968 const wchar_t* pText = pSimpleText->GetText();
971 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text.");
974 , index >= 0 && index < pSimpleText->GetTextLength()
975 , E_OUT_OF_RANGE, E_OUT_OF_RANGE, "[E_OUT_OF_RANGE] text index(%d) must greater than 0 and must be less than total string length(%d)",index, pSimpleText->GetTextLength());
977 if (pText[index] == (wchar_t)L' ')
979 GetRegion(textIndexFromElementOffset, 1, spaceCharDim.width, spaceCharDim.height);
982 textIndexFromElementOffset++;
987 switch (alignment & TEXT_ALIGNMASK_HORIZ)
989 case TEXT_OBJECT_ALIGNMENT_LEFT:
994 case TEXT_OBJECT_ALIGNMENT_CENTER:
995 GetRegion(startTextIndex, textLength, textSize.width, textSize.height);
996 if (textSize.width < adjustedRect.width)
998 adjustedRect.x += (adjustedRect.width - textSize.width) / 2;
1002 case TEXT_OBJECT_ALIGNMENT_RIGHT:
1003 GetRegion(startTextIndex, textLength, textSize.width, textSize.height);
1004 if (textSize.width < adjustedRect.width)
1006 adjustedRect.x += adjustedRect.width - textSize.width;
1011 pEnum = __pTextElementList->GetEnumeratorN();
1012 for (int i = 0; i <= elementIndex; i++)
1014 r = pEnum->MoveNext();
1017 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
1020 adjustedRect.y = displayRect.y + displayRect.height - baseline;
1021 canvasImpl.SetTextOrigin(TEXT_ORIGIN_BASELINE);
1023 currentLength = Math::Min(textLength, currentLength);
1025 while (textLength > 0)
1027 textLength -= currentLength;
1029 pTextElement->GetRegion(textIndexFromElementOffset, currentLength, textSize.width, textSize.height);
1031 if (action == TEXT_OBJECT_ACTION_TYPE_ABBREV && (pTextElement->GetType() == TEXT_ELEMENT_TYPE_TEXT))
1033 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
1036 , r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to cast text element.");
1038 SetAbbrevObjectFontInfo(pSimpleText);
1041 __pAbbrevTextElement->GetRegion(0, 1, abbrevTextDim.width, abbrevTextDim.height);
1043 if (adjustedRect.width < textSize.width + abbrevTextDim.width || textLength <= 0)
1045 int endType = TEXT_RETBY_NORMAL;
1047 if (adjustedRect.width > abbrevTextDim.width)
1049 int remainingLength = pSimpleText->GetTextLength() - textIndexFromElementOffset;
1050 endType = pSimpleText->ForwardAnalyze(textIndexFromElementOffset, remainingLength, adjustedRect.width - abbrevTextDim.width,
1051 TEXT_OBJECT_WRAP_TYPE_NONE, textCount, textSize.width, textSize.height);
1053 if (endType == TEXT_RETBY_OVERWIDTH)
1056 textSize.height = 0;
1064 textSize.height = pSimpleText->GetHeight();
1067 currentLength = textCount;
1068 drawAbbrevText = true;
1070 switch (alignment & TEXT_ALIGNMASK_HORIZ)
1072 case TEXT_OBJECT_ALIGNMENT_CENTER:
1073 if (textSize.width + abbrevTextDim.width < adjustedRect.width)
1075 adjustedRect.x = displayRect.x + (adjustedRect.width - (textSize.width + abbrevTextDim.width)) / 2;
1079 case TEXT_OBJECT_ALIGNMENT_RIGHT:
1080 if (textSize.width + abbrevTextDim.width < adjustedRect.width)
1082 adjustedRect.x = displayRect.x + adjustedRect.width - (textSize.width + abbrevTextDim.width);
1086 case TEXT_OBJECT_ALIGNMENT_LEFT:
1094 if (pTextElement->IsBackGroundDrawingModeEnable())
1096 Dimension blockSize;
1097 r = pTextElement->GetRegion(textIndexFromElementOffset, currentLength, blockSize.width, blockSize.height);
1098 SysTryReturn(NID_GRP
1100 , r, r, "[%s] Propagating.", GetErrorMessage(r));
1102 r = pCanvas->FillRectangle(pTextElement->GetBackgroundColor(), Rectangle(adjustedRect.x, displayRect.y, blockSize.width, displayRect.height));
1103 SysTryReturn(NID_GRP
1105 , r, r, "[%s] Propagating.", GetErrorMessage(r));
1108 isAlternateLookEnabled = (bool)pTextElement->GetValue(SET_ALTERNATE_LOOK);
1109 if (__displayBlock && isAlternateLookEnabled == false)
1111 Dimension tempTextSize;
1114 blockStartTextIndex = Math::Max(__workStart, startTextIndex);
1115 blockEndTextIndex = Math::Min(__workStart + __workLength, startTextIndex + currentLength);
1116 if (blockStartTextIndex < blockEndTextIndex)
1118 blockStartTextIndex = textIndexFromElementOffset + (blockStartTextIndex - startTextIndex);
1119 blockEndTextIndex = textIndexFromElementOffset + (blockEndTextIndex - startTextIndex);
1120 adjustedX = adjustedRect.x;
1122 if (textIndexFromElementOffset < blockStartTextIndex)
1124 pTextElement->GetRegion(textIndexFromElementOffset, blockStartTextIndex - textIndexFromElementOffset, tempTextSize.width, tempTextSize.height);
1125 adjustedX += tempTextSize.width;
1128 Rectangle block_rect = adjustedRect;
1129 block_rect.x = adjustedX;
1133 Rectangle imageRect = adjustedRect;
1134 imageRect.y -= textSize.height;
1135 TextElementType objectType = pTextElement->GetType();
1136 if (objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT)
1138 pTextElement->Draw(canvasImpl, adjustedRect, textIndexFromElementOffset, currentLength, alignment, action);
1142 pTextElement->Draw(canvasImpl, imageRect, textIndexFromElementOffset, currentLength, alignment, action);
1145 adjustedRect.x += textSize.width;
1146 adjustedRect.width -= textSize.width;
1150 if (pTextElement->IsBackGroundDrawingModeEnable())
1152 r = pCanvas->FillRectangle(pTextElement->GetBackgroundColor(), Rectangle(adjustedRect.x, displayRect.y, abbrevTextDim.width, displayRect.height));
1153 SysTryReturn(NID_GRP
1155 , r, r, "[%s] Propagating.", GetErrorMessage(r));
1158 __pAbbrevTextElement->Draw(canvasImpl, adjustedRect, 0, 1, (TextObjectAlignment)(TEXT_OBJECT_ALIGNMENT_TOP | TEXT_OBJECT_ALIGNMENT_LEFT), action);
1160 adjustedRect.x += abbrevTextDim.width;
1161 adjustedRect.width -= abbrevTextDim.width;
1166 if (!textLength || adjustedRect.width <= 0)
1171 startTextIndex += currentLength;
1173 if (pEnum->MoveNext() != E_SUCCESS)
1178 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1179 if (pTextElement == null)
1184 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
1185 currentLength = Math::Min(textLength, pTextElement->GetTextLength());
1187 if (currentLength == 0)
1193 canvasImpl.SetTextOrigin(TEXT_ORIGIN_LEFT_TOP);
1199 canvasImpl.SetTextOrigin(TEXT_ORIGIN_LEFT_TOP);
1206 TextComposite::DrawLine(_CanvasImpl& canvasImpl, TextLine* pTextLine, const Rectangle& displayRect,
1207 const TextObjectAlignment align, const TextObjectActionType action)
1209 SysTryReturn(NID_GRP
1211 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1216 Rectangle adjustedRect;
1217 Rectangle lineBounds;
1218 Dimension lineTextSize;
1220 lineLength = pTextLine->GetTextLength();
1221 lineOffset = pTextLine->GetTextOffset();
1223 lineBounds = pTextLine->GetBounds();
1224 pTextLine->GetRegion(0, lineLength, lineTextSize.width, lineTextSize.height);
1226 adjustedRect = displayRect;
1227 adjustedRect.width = lineBounds.width;
1228 adjustedRect.height = lineBounds.height;
1230 if (__elementVertialAlignment & TEXT_OBJECT_ALIGNMENT_BASELINE)
1232 return DrawWithBaseline(canvasImpl, adjustedRect, lineOffset, lineLength, (TextObjectAlignment)((TEXT_ALIGNMASK_HORIZ & align) | TEXT_OBJECT_ALIGNMENT_BASELINE), action, pTextLine->GetBaseline());
1236 return Draw(canvasImpl, adjustedRect, lineOffset, lineLength, (TextObjectAlignment)((TEXT_ALIGNMASK_HORIZ & align) | __elementVertialAlignment), action);
1241 TextComposite::GetValue(TextElement* pTextElement, TextComponentInfoValueType type, unsigned int* value) const
1243 SysTryReturn(NID_GRP
1245 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1247 TextElementType objectType = TextUtility::GetObjectTypeFromValueType(type);
1249 SysTryReturn(NID_GRP
1250 , pTextElement->GetType() == objectType
1251 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get type.");
1253 *value = pTextElement->GetValue(type);
1259 TextComposite::InsertElementAt(TextElement& textElement, int textIndex)
1261 SysTryReturn(NID_GRP
1262 , 0 <= textIndex && textIndex <= __length
1263 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1265 result r = E_SUCCESS;
1267 TextElement* pCurrentTextElement = null;
1268 TextElement* pNewTextElement = null;
1270 int currentLength = 0;
1271 int elementTextOffset = 0;
1272 int elementIndex = 0;
1273 int textIndexFromElementOffset = 0;
1275 pCurrentTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex,
1276 currentLength, textIndexFromElementOffset);
1278 if (pCurrentTextElement != null)
1280 if (textIndex == elementTextOffset)
1282 r = __pTextElementList->InsertAt(textElement, elementIndex);
1283 SysTryReturn(NID_GRP
1285 , r, r, "[%s] Fail to insert element.", GetErrorMessage(r));
1289 pCurrentTextElement->SetTextLength(pCurrentTextElement->GetTextLength() - currentLength);
1291 r = __pTextElementList->InsertAt(textElement, ++elementIndex);
1292 SysTryReturn(NID_GRP
1294 , r, r, "[%s] Fail to insert element.", GetErrorMessage(r));
1296 pNewTextElement = pCurrentTextElement->CloneN(SET_ALLVALUE_CLONE, 0);
1297 SysTryReturn(NID_GRP
1299 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to clone text element.");
1301 pNewTextElement->SetTextLength(currentLength);
1303 if (textIndexFromElementOffset != 0)
1305 pNewTextElement->SetValue(SET_TEXT_OFFSET, textIndexFromElementOffset);
1308 r = __pTextElementList->InsertAt(*pNewTextElement, ++elementIndex);
1309 SysTryReturn(NID_GRP
1311 , r, r, "[%s] Fail to insert element.", GetErrorMessage(r));
1316 if (textIndex == __length)
1318 r = __pTextElementList->Add(textElement);
1319 SysTryReturn(NID_GRP
1321 , r, r, "[%s] Fail to add element.", GetErrorMessage(r));
1329 int elementTextLength = textElement.GetTextLength();
1331 __workStart = textIndex;
1332 __workLength = elementTextLength;
1333 __length += elementTextLength;
1336 TextElementType objectType = textElement.GetType();
1337 if (objectType == TEXT_ELEMENT_TYPE_CUTLINK)
1339 TextCutLink* pLinkElement = dynamic_cast < TextCutLink* >(&textElement);
1340 __pCutLinkListInfo->InsertCutLinkElementInfo(textIndex, *pLinkElement, elementTextLength);
1344 __pCutLinkListInfo->InsertText(textIndex, elementTextLength);
1347 if (objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT)
1349 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(&textElement);
1350 if (pSimpleText != null)
1352 pSimpleText->SetUserWrap(__wrap);
1360 TextComposite::AppendElement(TextElement& textElement)
1362 result r = E_SUCCESS;
1363 int elementTextLength = textElement.GetTextLength();
1365 r = __pTextElementList->Add(textElement);
1366 SysTryReturn(NID_GRP
1368 , r, r, "[%s] Fail to add element.", GetErrorMessage(r));
1370 __workStart = __length;
1371 __workLength = elementTextLength;
1372 __length += elementTextLength;
1375 TextElementType objectType = textElement.GetType();
1376 if (objectType == TEXT_ELEMENT_TYPE_CUTLINK)
1378 TextCutLink* pLinkElement = dynamic_cast < TextCutLink* >(&textElement);
1379 __pCutLinkListInfo->InsertCutLinkElementInfo(__workStart, *pLinkElement, elementTextLength);
1383 __pCutLinkListInfo->InsertText(__workStart, elementTextLength);
1386 if (objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT)
1388 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(&textElement);
1389 if (pSimpleText != null)
1391 pSimpleText->SetUserWrap(__wrap);
1399 TextComposite::RemoveElementAt(int elementIndex, bool deallocate)
1401 SysTryReturn(NID_GRP
1402 , elementIndex >= 0 && elementIndex < __pTextElementList->GetCount()
1403 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1405 result r = E_SUCCESS;
1406 TextElement* pTextElement = null;
1408 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(elementIndex));
1409 if (pTextElement != null)
1411 int elementTextLength = pTextElement->GetTextLength();
1412 int elementTextOffset = GetFirstTextIndexAt(elementIndex);
1414 r = __pTextElementList->RemoveAt(elementIndex);
1415 SysTryReturn(NID_GRP
1417 , r, r, "[%s] Fail to remove element.", GetErrorMessage(r));
1419 if (pTextElement->GetType() == TEXT_ELEMENT_TYPE_CUTLINK)
1421 __pCutLinkListInfo->RemoveCutLinkElementInfo(dynamic_cast < TextCutLink* >(pTextElement));
1425 __pCutLinkListInfo->RemoveText(elementTextOffset, elementTextLength);
1428 __length -= elementTextLength;
1432 delete pTextElement;
1433 pTextElement = null;
1441 TextComposite::RemoveAllElements(bool deallocate)
1443 result r = E_SUCCESS;
1445 if (__pCutLinkListInfo)
1447 __pCutLinkListInfo->RemoveAllCutLinkElementInfos();
1450 __pTextElementList->RemoveAll(deallocate);
1453 , __pTextElementList->GetCount() == 0
1454 , r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to remove all elements.");
1459 __displayBlock = false;
1460 __ignoreRearBlank = false;
1461 __ignoreFrontBlank = false;
1463 __rearSpaceHideMode = TEXT_OBJECT_SPACE_HIDE_TYPE_NONE;
1464 __frontSpaceHideMode = TEXT_OBJECT_SPACE_HIDE_TYPE_NONE;
1478 TextComposite::SearchTextElement(TextElementType type, int textIndex, int& elementTextOffset) const
1480 SysTryReturn(NID_GRP
1481 , 0 <= textIndex && textIndex < __length
1482 , null, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1484 result r = E_SUCCESS;
1485 IEnumerator* pEnum = null;
1486 TextElement* pTextElement = null;
1488 int elementIndex = 0;
1489 int currentLength = 0;
1490 int textIndexFromElementOffset = 0;
1492 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
1493 textIndexFromElementOffset);
1494 SysTryReturn(NID_GRP
1496 , null, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
1498 if (pTextElement->GetType() == type)
1500 return pTextElement;
1503 elementTextOffset += pTextElement->GetTextLength();
1505 pEnum = __pTextElementList->GetEnumeratorN();
1506 for (int i = 0; i < elementIndex; i++)
1508 r = pEnum->MoveNext();
1511 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
1514 while (pEnum->MoveNext() == E_SUCCESS)
1516 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1517 if (pTextElement == null)
1522 if (pTextElement->GetType() == type)
1525 SetLastResult(E_SUCCESS);
1526 return pTextElement;
1529 elementTextOffset += pTextElement->GetTextLength();
1533 SetLastResult(E_SUCCESS);
1542 TextComposite::GetText(TextComposite* pTargetCompsiteText, int textIndex, int textLength)
1544 SysTryReturn(NID_GRP
1545 , pTargetCompsiteText
1546 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1548 SysTryReturn(NID_GRP
1550 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1552 result r = E_SUCCESS;
1553 IEnumerator* pEnum = null;
1554 TextElement* pTextElement = null;
1555 TextElement* pNewTextElement = null;
1557 int currentLength = 0;
1558 int elementTextOffset = 0;
1559 int elementIndex = 0;
1560 int textIndexFromElementOffset = 0;
1562 if (textIndex == -1 || textIndex < 0)
1567 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
1568 textIndexFromElementOffset);
1569 SysTryReturn(NID_GRP
1571 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get element.");
1573 textIndexFromElementOffset = textIndex - elementTextOffset;
1575 pEnum = __pTextElementList->GetEnumeratorN();
1576 for (int i = 0; i < elementIndex; i++)
1578 r = pEnum->MoveNext();
1581 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
1584 while (pEnum->MoveNext() == E_SUCCESS)
1586 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1587 if (pTextElement == null)
1592 textIndexFromElementOffset = 0;
1593 currentLength = Math::Min(pTextElement->GetTextLength(), textLength);
1595 pNewTextElement = pTextElement->CopyN(textIndexFromElementOffset, currentLength);
1596 if (pNewTextElement != null)
1598 pTargetCompsiteText->AppendElement(*pNewTextElement);
1601 textLength -= currentLength;
1613 TextComposite::Compose(Rectangle& rect, TextColumn* pTextColumn)
1615 SysTryReturn(NID_GRP
1617 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1619 __pCurrentTextColumn = pTextColumn;
1623 if (__pTextElementList->GetCount() == 0 || __length == 0)
1625 pTextColumn->RemoveAllLines();
1632 case TEXT_OBJECT_WRAP_TYPE_NONE:
1634 if (__drawAbbrevText)
1636 __pCurrentTextColumn->PrepareCompose();
1638 __drawTextEllipsis = false;
1639 if (__TextObjectEllipsisType == TEXT_OBJECT_ELLIPSIS_TYPE_TAIL)
1641 lineCount = ComposeInNoneWrap(rect);
1643 else if (__TextObjectEllipsisType == TEXT_OBJECT_ELLIPSIS_TYPE_MIDDLE)
1645 lineCount = ComposeInNoneWrapMiddleEllipsis(rect);
1649 lineCount = ComposeInNoneWrapHeadEllipsis(rect);
1654 bool setNoneWrapComposeInfo = false;
1655 NoneWrapComposeInfo noneWrapComposeInfo;
1657 TextLine* pTextLine = __pCurrentTextColumn->GetTextLine(0);
1658 if (pTextLine != null)
1661 noneWrapComposeInfo.prevTextOffset = pTextLine->GetTextOffset();
1662 noneWrapComposeInfo.prevTextLength = pTextLine->GetTextLength();
1663 pTextLine->GetRegion(0, noneWrapComposeInfo.prevTextLength,
1664 noneWrapComposeInfo.prevWidth, noneWrapComposeInfo.prevHeight);
1665 noneWrapComposeInfo.prevEndType = pTextLine->GetEndType();
1666 setNoneWrapComposeInfo = true;
1669 __pCurrentTextColumn->PrepareCompose();
1670 __drawTextEllipsis = false;
1671 if (setNoneWrapComposeInfo)
1673 lineCount = ComposeInNoneWrap(rect, &noneWrapComposeInfo);
1677 lineCount = ComposeInNoneWrap(rect);
1681 __pCurrentTextColumn->FinishCompose();
1685 case TEXT_OBJECT_WRAP_TYPE_CHARACTER:
1687 __pCurrentTextColumn->PrepareCompose();
1688 lineCount = ComposeInNormalWrap(rect);
1689 __pCurrentTextColumn->FinishCompose();
1693 case TEXT_OBJECT_WRAP_TYPE_WORD:
1695 if (IsPartialComposingModeEnabled())
1697 if (__pCurrentTextColumn->GetTotalLineCount() == 0)
1699 __pCurrentTextColumn->PrepareCompose();
1701 lineCount = ComposeInPartialMode(rect);
1705 __pCurrentTextColumn->PrepareCompose();
1706 lineCount = ComposeInWordWrap(rect);
1707 __pCurrentTextColumn->CompareDeletedLine();
1708 __pCurrentTextColumn->FinishCompose();
1719 TextComposite::SetRange(int textStartIndex, int textLength)
1721 SysTryReturn(NID_GRP
1722 , 0 <= textStartIndex && textStartIndex <= __length
1723 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1725 __workStart = textStartIndex;
1726 __workLength = textLength;
1732 TextComposite::GetRange(int& startTextIndex, int& textLength) const
1734 startTextIndex = __workStart;
1735 textLength = __workLength;
1739 TextComposite::SetFont(Font* pFont)
1741 return SetValueToAllTextElements(SET_FONT, (unsigned int)pFont);
1745 TextComposite::GetFont(int textIndex) const
1747 unsigned int value = 0;
1749 GetValue(textIndex, SET_FONT, &value);
1750 Font* pFont = static_cast < Font* >((void*)value);
1752 SetLastResult(E_SUCCESS);
1758 TextComposite::SetForegroundColor(const Color& color)
1760 return SetValueToAllTextElements(SET_FONT_FGCOLOR, (unsigned int)color.GetRGB32());
1764 TextComposite::GetForegroundColor(int textIndex) const
1766 result r = E_SUCCESS;
1767 unsigned int value = 0;
1769 r = GetValue(textIndex, SET_FONT_FGCOLOR, &value);
1770 SysTryReturn(NID_GRP
1772 , Color::GetColor(COLOR_ID_BLACK), r, "[%s] Propagating.", GetErrorMessage(r));
1774 return Color(value);
1778 TextComposite::SetBackgroundColor(const Color& color)
1780 return SetValueToAllTextElements(SET_FONT_BGCOLOR, (unsigned int)color.GetRGB32());
1784 TextComposite::GetBackgroundColor(int textIndex) const
1786 result r = E_SUCCESS;
1787 unsigned int value = 0;
1789 r = GetValue(textIndex, SET_FONT_BGCOLOR, &value);
1790 SysTryReturn(NID_GRP
1792 , Color::GetColor(COLOR_ID_BLACK), r, "[%s] Propagating.", GetErrorMessage(r));
1794 return Color(value);
1798 TextComposite::SetOutlineColor(const Color& color)
1800 return SetValueToAllTextElements(SET_FONT_OUTLINECOLOR, (unsigned int)color.GetRGB32());
1804 TextComposite::GetOutlineColor(int textIndex) const
1806 result r = E_SUCCESS;
1807 unsigned int value = 0;
1809 r = GetValue(textIndex, SET_FONT_OUTLINECOLOR, &value);
1810 SysTryReturn(NID_GRP
1812 , Color::GetColor(COLOR_ID_BLACK), r, "[%s] Propagating.", GetErrorMessage(r));
1814 return Color(value);
1818 TextComposite::GetAlternativeForegroundColor(int textIndex) const
1820 SysTryReturn(NID_GRP
1821 , 0 <= textIndex && textIndex < __length
1822 , Color::GetColor(COLOR_ID_BLACK), E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
1824 result r = E_SUCCESS;
1825 unsigned int value = 0;
1827 r = GetValue(textIndex, SET_ALTERNATIVE_FGCOLOR, &value);
1828 SysTryReturn(NID_GRP
1830 , Color::GetColor(COLOR_ID_BLACK), r, "[%s] Propagating.", GetErrorMessage(r));
1832 return Color(value);
1836 TextComposite::SetAlternateLookEnabled(bool enable)
1838 return SetValueToAllTextElements(SET_ALTERNATE_LOOK, (unsigned int)enable);
1842 TextComposite::GetMaxLineHeight(void) const
1844 IEnumerator* pEnum = null;
1845 TextElement* pTextElement = null;
1849 pEnum = __pTextElementList->GetEnumeratorN();
1850 while (pEnum->MoveNext() == E_SUCCESS)
1852 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1853 if (pTextElement == null)
1858 height = pTextElement->GetHeight();
1859 maxHeight = Math::Max(maxHeight, height);
1867 TextComposite::GetElementAtTextIndex(int textIndex, int& elementTextOffset, int& elementIndex, int& elementTextLength,
1868 int& textIndexFromElementOffset) const
1870 result r = E_SUCCESS;
1871 IEnumerator* pEnum = null;
1872 TextElement* pTextElement = null;
1874 int currentElementLength = 0;
1876 elementTextOffset = 0;
1878 elementTextLength = 0;
1879 textIndexFromElementOffset = 0;
1881 if (__pTextElementList->GetCount() == 0)
1886 pEnum = __pTextElementList->GetEnumeratorN();
1887 r = pEnum->MoveNext();
1888 SysTryReturn(NID_GRP
1890 , null, r, "[%s] Fail to move next element. Now Elements count is (%d)", GetErrorMessage(r), __pTextElementList->GetCount());
1892 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1893 SysTryReturn(NID_GRP
1895 , null, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
1899 currentElementLength = pTextElement->GetTextLength();
1900 if (textIndex < elementTextOffset + currentElementLength)
1902 offset = pTextElement->GetValue(SET_TEXT_OFFSET);
1903 textIndexFromElementOffset = offset + (textIndex - elementTextOffset);
1908 if (currentElementLength == 0 && textIndex == elementTextOffset)
1910 offset = pTextElement->GetValue(SET_TEXT_OFFSET);
1911 textIndexFromElementOffset = offset + (textIndex - elementTextOffset);
1916 pTextElement = null;
1917 if (pEnum->MoveNext() != E_SUCCESS)
1922 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1923 if (pTextElement == null)
1928 elementTextOffset += currentElementLength;
1932 if (pTextElement != null)
1934 elementTextLength = elementTextOffset + currentElementLength - textIndex;
1938 return pTextElement;
1942 TextComposite::GetElementAtTextIndex(int textIndex) const
1944 result r = E_SUCCESS;
1945 IEnumerator* pEnum = null;
1946 TextElement* pTextElement = null;
1947 int currentElementLength = 0;
1948 int elementTextOffset = 0;
1950 if (__pTextElementList->GetCount() == 0)
1955 pEnum = __pTextElementList->GetEnumeratorN();
1956 r = pEnum->MoveNext();
1957 SysTryReturn(NID_GRP
1959 , null, r, "[%s] Fail to move next element. Now Elements count is (%d)", GetErrorMessage(r), __pTextElementList->GetCount());
1961 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1962 SysTryReturn(NID_GRP
1964 , null, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
1968 currentElementLength = pTextElement->GetTextLength();
1969 if (textIndex < elementTextOffset + currentElementLength)
1975 if (currentElementLength == 0 && textIndex == elementTextOffset)
1981 pTextElement = null;
1982 if (pEnum->MoveNext() != E_SUCCESS)
1987 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
1988 if (pTextElement == null)
1993 elementTextOffset += currentElementLength;
1997 return pTextElement;
2001 TextComposite::SetWrap(TextObjectWrapType wrap)
2010 IEnumerator* pEnum = null;
2011 TextElement* pTextElement = null;
2013 pEnum = __pTextElementList->GetEnumeratorN();
2014 while (pEnum->MoveNext() == E_SUCCESS)
2016 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
2017 if (pTextElement == null)
2022 TextElementType objectType = pTextElement->GetType();
2023 if (objectType == TEXT_ELEMENT_TYPE_TEXT || objectType == TEXT_ELEMENT_TYPE_CUTLINK)
2025 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
2026 if (pSimpleText != null)
2028 pSimpleText->SetUserWrap(__wrap);
2038 TextComposite::Optimize(int startElementIndex, int endElementIndex)
2040 int elementCount = 0;
2043 TextElement* pStartTextElement = null;
2044 TextElement* pEndTextElement = null;
2045 TextElement* pCurrentTextElement = null;
2046 TextElement* pNextTextElement = null;
2048 elementCount = __pTextElementList->GetCount();
2049 if (elementCount == 0)
2054 if (startElementIndex == -1 || startElementIndex < 0)
2056 startElementIndex = 0;
2059 if (endElementIndex == -1 || endElementIndex < 0 || endElementIndex > elementCount - 1)
2061 endElementIndex = elementCount - 1;
2064 if (0 < startElementIndex)
2066 startElementIndex--;
2069 if (endElementIndex < elementCount - 1)
2074 if (endElementIndex - startElementIndex < 1)
2079 pStartTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(startElementIndex));
2080 SysTryReturn(NID_GRP
2082 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
2084 pEndTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(endElementIndex));
2085 SysTryReturn(NID_GRP
2087 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
2091 pCurrentTextElement = pStartTextElement;
2093 nodeIndex = startElementIndex + 1;
2095 pNextTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(nodeIndex));
2096 if (pNextTextElement == null)
2101 if (TextUtility::CanMerge(pCurrentTextElement, pNextTextElement))
2103 pCurrentTextElement->SetTextLength(pCurrentTextElement->GetTextLength() + pNextTextElement->GetTextLength());
2104 __pTextElementList->Remove(*pNextTextElement, true);
2108 pStartTextElement = pNextTextElement;
2111 startElementIndex++;
2112 pStartTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(startElementIndex));
2114 while (startElementIndex != endElementIndex);
2120 TextComposite::ChangeTextOffset(wchar_t* pText, int elementIndex, int gap)
2122 SysTryReturn(NID_GRP
2124 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
2126 SysTryReturn(NID_GRP
2128 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
2130 result r = E_SUCCESS;
2131 IEnumerator* pEnum = null;
2132 TextElement* pTextElement = null;
2134 pEnum = __pTextElementList->GetEnumeratorN();
2135 for (int i = 0; i < elementIndex; i++)
2137 r = pEnum->MoveNext();
2140 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
2143 while (pEnum->MoveNext() == E_SUCCESS)
2145 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
2146 if (pTextElement == null)
2151 TextElementType objectType = pTextElement->GetType();
2152 if (objectType == TEXT_ELEMENT_TYPE_TEXT || objectType == TEXT_ELEMENT_TYPE_CUTLINK)
2154 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
2155 if (pSimpleText != null)
2157 pSimpleText->ChangeTextOffset(pText, gap);
2171 TextComposite::NotifyTextChanged(wchar_t* pText, int startTextIndex, int textLength, int gap, Font* pFont,
2172 const Color& fgColor, const Color& bgColor, const Color& outlineColor)
2179 result r = E_SUCCESS;
2180 TextElement* pTextElement = null;
2181 TextElement* pNextTextElement = null;
2183 int currentLength = 0;
2184 int elementTextOffset = 0;
2185 int elementIndex = 0;
2186 int textIndexFromElementOffset = 0;
2187 bool isOptimized = false;
2189 SetWorkWidth(pFont, pText, __workStart, textLength);
2193 bool checkNextElement = false;
2195 if (__workStart == startTextIndex)
2197 pTextElement = GetElementAtTextIndex(__workStart, elementTextOffset, elementIndex, currentLength,
2198 textIndexFromElementOffset);
2202 pTextElement = GetElementAtTextIndex(__workStart - 1, elementTextOffset, elementIndex, currentLength,
2203 textIndexFromElementOffset);
2204 checkNextElement = true;
2207 if (pTextElement == null)
2209 TextSimple* pSimpleText = null;
2210 pSimpleText = new (std::nothrow)TextSimple(pText, gap, TEXT_ELEMENT_SOURCE_TYPE_EXTERNAL, pFont, fgColor, bgColor,
2212 SysTryReturn(NID_GRP
2214 , E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
2216 pSimpleText->SetTextOffset(__workStart - startTextIndex);
2217 InsertElementAt(*pSimpleText, __workStart);
2223 TextSimple* pSimpleText = null;
2224 bool canMerge = false;
2226 TextElementType objectType = pTextElement->GetType();
2227 if (objectType == TEXT_ELEMENT_TYPE_TEXT || objectType == TEXT_ELEMENT_TYPE_CUTLINK)
2229 pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
2230 if (pSimpleText != null)
2232 if (pSimpleText->IsSame(pText, pFont, fgColor, bgColor, outlineColor))
2238 pTextElement = null;
2244 pTextElement = null;
2247 if (!canMerge && checkNextElement)
2249 pTextElement = null;
2251 if (currentLength == 1)
2253 pNextTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(elementIndex+1));
2254 if (pNextTextElement != null)
2256 objectType = pNextTextElement->GetType();
2257 if (objectType == TEXT_ELEMENT_TYPE_TEXT || objectType == TEXT_ELEMENT_TYPE_CUTLINK)
2259 pSimpleText = dynamic_cast < TextSimple* >(pNextTextElement);
2260 if (pSimpleText != null)
2262 if (pSimpleText->IsSame(pText, pFont, fgColor, bgColor, outlineColor))
2265 pTextElement = pNextTextElement;
2269 pTextElement = null;
2275 pTextElement = null;
2280 pTextElement = null;
2285 if (pTextElement == null)
2287 TextSimple* pSimpleText = null;
2288 pSimpleText = new (std::nothrow)TextSimple(pText, gap, TEXT_ELEMENT_SOURCE_TYPE_EXTERNAL, pFont, fgColor, bgColor,
2290 SysTryReturn(NID_GRP
2292 , E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
2294 pSimpleText->SetTextOffset(__workStart - startTextIndex);
2295 InsertElementAt(*pSimpleText, __workStart);
2298 r = __pTextElementList->IndexOf(*pSimpleText, elementIndex);
2299 SysTryReturn(NID_GRP
2301 , r, r, "[%s] Fail to get element index.", GetErrorMessage(r));
2305 __pCutLinkListInfo->InsertText(startTextIndex, gap);
2307 pTextElement->SetTextLength(pTextElement->GetTextLength() + gap);
2313 int remainingGap = -gap;
2316 int currentelementIndex = 0;
2318 textIndex = __workStart + remainingGap;
2319 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
2320 textIndexFromElementOffset);
2321 if (pTextElement == null || elementTextOffset == textIndex)
2323 pTextElement = GetElementAtTextIndex(textIndex - 1, elementTextOffset, elementIndex, currentLength,
2324 textIndexFromElementOffset);
2327 SysTryReturn(NID_GRP
2329 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
2331 currentelementIndex = elementIndex;
2332 currentGap = Math::Min(remainingGap, textIndex - elementTextOffset);
2333 if (currentGap == pTextElement->GetTextLength())
2335 RemoveElementAt(currentelementIndex);
2341 pTextElement->SetTextLength(pTextElement->GetTextLength() - currentGap);
2342 __length -= currentGap;
2343 if (currentGap < remainingGap)
2345 TextSimple* pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
2346 if (pSimpleText != null)
2348 int offset = pSimpleText->GetTextOffset();
2349 offset -= (remainingGap - currentGap);
2350 pSimpleText->SetTextOffset(offset);
2355 remainingGap -= currentGap;
2356 while (remainingGap > 0)
2358 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(--currentelementIndex));
2359 SysTryReturn(NID_GRP
2361 , r, r, "[%s] Fail to get element.", GetErrorMessage(r));
2363 int elementTextLength = pTextElement->GetTextLength();
2364 currentGap = Math::Min(elementTextLength, remainingGap);
2366 if (currentGap == elementTextLength)
2368 RemoveElementAt(currentelementIndex);
2374 __pCutLinkListInfo->RemoveText(__workStart, currentGap);
2375 pTextElement->SetTextLength(elementTextLength - currentGap);
2376 __length -= currentGap;
2379 remainingGap -= currentGap;
2383 ChangeTextOffset(pText, elementIndex + 1, gap);
2387 Optimize(elementIndex, elementIndex);
2394 TextComposite::ForwardAnalyzeWithFocusedObjectType(int textIndex, int textLength, int maxWidth,
2395 int& cursorIndex, TextElementType& type)
2397 result r = E_SUCCESS;
2399 int currentLength = 0;
2400 int elementTextOffset = 0;
2401 int elementIndex = 0;
2402 int textIndexFromElementOffset = 0;
2404 int remainingWidth = 0;
2405 int remainingLength = 0;
2406 int ret = TEXT_RETBY_NORMAL;
2408 IEnumerator* pEnum = null;
2409 TextElement* pTextElement = null;
2411 bool isFirstWord = true;
2415 type = TEXT_ELEMENT_TYPE_MAX;
2417 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
2418 textIndexFromElementOffset);
2419 SysTryReturn(NID_GRP
2421 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
2423 remainingWidth = maxWidth;
2424 remainingLength = textLength;
2426 pEnum = __pTextElementList->GetEnumeratorN();
2427 for (int i = 0; i <= elementIndex; i++)
2429 r = pEnum->MoveNext();
2432 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
2435 currentLength = Math::Min(remainingLength, currentLength);
2437 while (remainingWidth > 0 || remainingLength > 0)
2439 ret = pTextElement->ForwardAnalyze(textIndexFromElementOffset, currentLength, remainingWidth, __wrap, textCount , textSize.width, textSize.height);
2440 TextElementType objectType = pTextElement->GetType();
2442 if ((objectType == TEXT_ELEMENT_TYPE_TEXT || objectType == TEXT_ELEMENT_TYPE_CUTLINK) && (ret == TEXT_RETBY_LIMITWIDTH))
2444 Dimension tempTextSize;
2445 r = pTextElement->GetRegion(textIndexFromElementOffset, textCount + 1, tempTextSize.width, tempTextSize.height);
2446 SysTryReturn(NID_GRP
2448 , r, r, "[%s] Propagating.", GetErrorMessage(r));
2450 if ((remainingWidth - textSize.width) > (tempTextSize.width - remainingWidth))
2452 textSize.width = tempTextSize.width;
2457 remainingWidth -= textSize.width;
2458 if (remainingWidth < 0)
2463 remainingLength -= textCount;
2464 currentLength -= textCount ;
2465 cursorIndex += textCount ;
2467 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD && ret != TEXT_RETBY_LIMITWIDTH)
2469 index = cursorIndex;
2472 if (remainingLength <= currentLength)
2477 if (ret == TEXT_RETBY_OVERWIDTH || ret == TEXT_RETBY_LINEFEED)
2482 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD)
2484 if (ret == TEXT_RETBY_LIMITWIDTH)
2486 if (isFirstWord == false)
2488 cursorIndex = index;
2489 ret = TEXT_RETBY_NORMAL;
2494 isFirstWord = false;
2496 if (currentLength > 0)
2498 textIndexFromElementOffset += textCount ;
2504 if (ret == TEXT_RETBY_LIMITWIDTH)
2510 if (pEnum->MoveNext() != E_SUCCESS)
2515 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
2516 if (pTextElement == null)
2521 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
2522 currentLength = Math::Min(pTextElement->GetTextLength(), remainingLength);
2525 if (ret == TEXT_RETBY_LIMITLENGTH)
2527 ret = TEXT_RETBY_NORMAL;
2530 SetLastResult(E_SUCCESS);
2540 TextComposite::HideFrontSpace(TextObjectSpaceHideType mode)
2542 __ignoreFrontBlank = true;
2543 __frontSpaceHideMode = mode;
2547 TextComposite::HideRearSpace(TextObjectSpaceHideType mode)
2549 __ignoreRearBlank = true;
2550 __rearSpaceHideMode = mode;
2554 TextComposite::ForwardAnalyzeInNoneCursorMode(int startTextIndex, int textLength, int maxWidth, int& textIndex)
2556 result r = E_SUCCESS;
2558 int currentLength = 0;
2559 int elementTextOffset = 0;
2560 int elementIndex = 0;
2561 int textIndexFromElementOffset = 0;
2563 int remainingWidth = 0;
2564 int remainingLength = 0;
2565 int ret = TEXT_RETBY_NORMAL;
2567 IEnumerator* pEnum = null;
2568 TextElement* pTextElement = null;
2570 bool isFirstWord = true;
2574 pTextElement = GetElementAtTextIndex(startTextIndex, elementTextOffset, elementIndex, currentLength,
2575 textIndexFromElementOffset);
2576 SysTryReturn(NID_GRP
2578 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
2581 remainingWidth = maxWidth;
2582 remainingLength = textLength;
2584 pEnum = __pTextElementList->GetEnumeratorN();
2585 for (int i = 0; i <= elementIndex; i++)
2587 r = pEnum->MoveNext();
2590 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
2593 currentLength = Math::Min(remainingLength, currentLength);
2595 while (remainingWidth > 0 || remainingLength > 0)
2597 ret = pTextElement->ForwardAnalyze(textIndexFromElementOffset, currentLength, remainingWidth,
2598 __wrap, textCount, textSize.width, textSize.width);
2600 TextElementType objectType = pTextElement->GetType();
2602 if ((objectType == TEXT_ELEMENT_TYPE_TEXT || objectType == TEXT_ELEMENT_TYPE_CUTLINK) && (ret == TEXT_RETBY_LIMITWIDTH))
2604 Dimension tempTextSize;
2605 r = pTextElement->GetRegion(textIndexFromElementOffset, textCount + 1, tempTextSize.width, tempTextSize.height);
2606 SysTryReturn(NID_GRP
2608 , r, r, "[%s] Propagating.", GetErrorMessage(r));
2610 textSize.width = tempTextSize.width;
2614 remainingWidth -= textSize.width;
2615 if (remainingWidth < 0)
2620 remainingLength -= textCount;
2621 currentLength -= textCount;
2622 textIndex += textCount;
2624 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD && ret != TEXT_RETBY_LIMITWIDTH)
2629 if (remainingLength <= currentLength)
2634 if (ret == TEXT_RETBY_OVERWIDTH || ret == TEXT_RETBY_LINEFEED)
2639 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD)
2641 if (ret == TEXT_RETBY_LIMITWIDTH)
2643 if (isFirstWord == false)
2646 ret = TEXT_RETBY_NORMAL;
2651 isFirstWord = false;
2653 if (currentLength > 0)
2655 textIndexFromElementOffset += textCount;
2661 if (ret == TEXT_RETBY_LIMITWIDTH)
2667 if (pEnum->MoveNext() != E_SUCCESS)
2672 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
2673 if (pTextElement == null)
2678 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
2679 currentLength = Math::Min(pTextElement->GetTextLength(), remainingLength);
2682 if (ret == TEXT_RETBY_LIMITLENGTH)
2684 ret = TEXT_RETBY_NORMAL;
2687 SetLastResult(E_SUCCESS);
2697 TextComposite::GetCutLinkElementCount(void) const
2699 return __pCutLinkListInfo->GetCutLinkElementCount();
2703 TextComposite::GetCutLinkElementIndexAt(int textIndex) const
2705 return __pCutLinkListInfo->GetCutLinkElementIndexAt(textIndex);
2709 TextComposite::GetCutLinkElementAtCutLinkElementIndex(int index) const
2711 return __pCutLinkListInfo->GetCutLinkElementAtCutLinkElementIndex(index);
2715 TextComposite::ResetAllCutLinkElementsState(void)
2717 return __pCutLinkListInfo->ResetAllCutLinkElementsState();
2721 TextComposite::ChangeCutLinkState(int linkIndex, bool select)
2723 return __pCutLinkListInfo->ChangeCutLinkState(linkIndex, select);
2727 TextComposite::SetValueToAllTextElements(TextComponentInfoValueType type, unsigned int value)
2729 result r = E_SUCCESS;
2730 IEnumerator* pEnum = null;
2731 TextElement* pTextElement = null;
2732 TextElement* pNewTextElement = null;
2734 int startelementIndex = -1;
2735 int endelementIndex = -1;
2738 int elementTextOffset = 0;
2739 int elementIndex = 0;
2740 int currentLength = 0;
2741 int textIndexFromElementOffset = 0;
2744 textIndex = __workStart;
2745 textLength = __workLength;
2747 if (textLength == 0)
2752 while (0 < textLength)
2754 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
2755 textIndexFromElementOffset);
2756 SysTryReturn(NID_GRP
2758 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
2760 SysTryReturn(NID_GRP
2762 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element node.");
2764 TextElementType objectType = pTextElement->GetType();
2765 TextElementType objectTypeFromValueType = TextUtility::GetObjectTypeFromValueType(type);
2767 unsigned int objectValue = pTextElement->GetValue(type);
2768 if ((objectType == objectTypeFromValueType) && (value != objectValue))
2771 startelementIndex = elementIndex;
2774 else if ((COMMONOBJECT_VALUE_START <= type && type < MAX_COMMONOBJECT_VALUE) && (value != objectValue))
2777 startelementIndex = elementIndex;
2780 textIndex += currentLength;
2781 textLength -= currentLength;
2789 if (elementTextOffset == textIndex && textLength == currentLength)
2791 pTextElement->SetValue(type, value);
2794 else if ((elementTextOffset < textIndex) && (textLength < currentLength))
2796 pTextElement->SetTextLength(pTextElement->GetTextLength() - currentLength);
2798 pNewTextElement = pTextElement->CloneN(type, value);
2799 SysTryReturn(NID_GRP
2801 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to clone text element.");
2803 pNewTextElement->SetTextLength(textLength);
2804 pNewTextElement->SetValue(SET_TEXT_OFFSET, textIndexFromElementOffset);
2806 r = __pTextElementList->InsertAt(*pNewTextElement, ++elementIndex);
2809 , , r, "[%s] Fail to insert element.", GetErrorMessage(r));
2811 pNewTextElement = pTextElement->CloneN(SET_ALLVALUE_CLONE, 0);
2812 SysTryReturn(NID_GRP
2814 , r, r, "[E_SYSTEM] Fail to clone text element.");
2816 pNewTextElement->SetTextLength(currentLength - textLength);
2817 pNewTextElement->SetValue(SET_TEXT_OFFSET, textIndexFromElementOffset + textLength);
2819 r = __pTextElementList->InsertAt(*pNewTextElement, ++elementIndex);
2822 , , r, "[%s] Fail to insert element.", GetErrorMessage(r));
2824 endelementIndex = elementIndex;
2827 else if (elementTextOffset < textIndex)
2829 pTextElement->SetTextLength(pTextElement->GetTextLength() - currentLength);
2831 pNewTextElement = pTextElement->CloneN(type, value);
2832 SysTryReturn(NID_GRP
2834 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to clone text element.");
2836 pNewTextElement->SetValue(SET_TEXT_OFFSET, textIndexFromElementOffset);
2837 pNewTextElement->SetTextLength(currentLength);
2839 r = __pTextElementList->InsertAt(*pNewTextElement, ++elementIndex);
2842 , , r, "[%s] Fail to insert element.", GetErrorMessage(r));
2844 textIndex += currentLength;
2845 textLength -= currentLength;
2848 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, elementIndex, currentLength,
2849 textIndexFromElementOffset);
2850 if (pTextElement == null)
2857 endelementIndex = elementIndex;
2862 pEnum = __pTextElementList->GetEnumeratorN();
2863 for (int i = 0; i <= elementIndex; i++)
2865 r = pEnum->MoveNext();
2868 , , r, "[%s] Fail to move next element.", GetErrorMessage(r));
2871 while (textLength > 0)
2873 TextElementType objectType = pTextElement->GetType();
2874 TextElementType objectTypeFromValueType = TextUtility::GetObjectTypeFromValueType(type);
2876 if (objectType == objectTypeFromValueType)
2878 if (value != objectTypeFromValueType)
2880 if (textLength < currentLength)
2882 pNewTextElement = pTextElement->CloneN(SET_ALLVALUE_CLONE, 0);
2883 SysTryReturn(NID_GRP
2885 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to clone text element.");
2887 pNewTextElement->SetTextLength(currentLength - textLength);
2888 pNewTextElement->SetValue(SET_TEXT_OFFSET, textIndexFromElementOffset + textLength);
2890 pTextElement->SetValue(type, value);
2891 pTextElement->SetTextLength(textLength);
2893 r = __pTextElementList->InsertAt(*pNewTextElement, ++elementIndex);
2896 , , r, "[%s] Fail to insert element.", GetErrorMessage(r));
2902 pTextElement->SetValue(type, value);
2905 endelementIndex = elementIndex;
2909 elementTextOffset += currentLength;
2910 textLength -= currentLength;
2913 if (pEnum->MoveNext() != E_SUCCESS)
2918 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
2919 if (pTextElement == null)
2924 currentLength = pTextElement->GetTextLength();
2925 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
2929 Optimize(startelementIndex, endelementIndex);
2934 if (pNewTextElement != null)
2936 delete pNewTextElement;
2937 pNewTextElement = null;
2945 TextComposite::SetAbbrevObjectFontInfo(TextSimple* pSimpleText)
2947 SysTryReturn(NID_GRP
2948 , __pAbbrevTextElement
2949 , false, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
2951 __pAbbrevTextElement->SetFont(pSimpleText->GetFont());
2952 __pAbbrevTextElement->SetForegroundColor(pSimpleText->GetForegroundColor());
2953 __pAbbrevTextElement->SetBackgroundColor(pSimpleText->GetBackgroundColor());
2954 __pAbbrevTextElement->SetOutlineColor(pSimpleText->GetOutlineColor());
2955 __pAbbrevTextElement->SetAlternativeForegroundColor(pSimpleText->GetAlternativeForegroundColor());
2956 __pAbbrevTextElement->SetAlternateLookEnabled(pSimpleText->IsAlternateLookEnabled());
2962 TextComposite::ComposeInNoneWrap(Rectangle& rect, NoneWrapComposeInfo* pNoneWrapComposeInfo)
2964 SysTryReturn(NID_GRP
2965 , __pCurrentTextColumn
2966 , -1, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
2968 TextLine* pTextLine = null;
2969 Rectangle lineBounds;
2973 int endType = TEXT_RETBY_NORMAL;
2974 bool isChanged = false;
2975 bool forwardSearch = true;
2976 int textIndex = __workStart;
2984 if (textIndex > __length)
2986 textIndex = __length;
2989 if (textIndex == __length)
2991 forwardSearch = false;
2994 if (__pCurrentTextColumn->GetTotalLineCount() > 0)
2996 pTextLine = __pCurrentTextColumn->GetTextLine(0);
2997 SysTryReturn(NID_GRP
2999 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text line.");
3001 lineBounds = pTextLine->GetBounds();
3002 endType = pTextLine->GetEndType();
3004 if (lineBounds.width != rect.width)
3009 lineOffset = pTextLine->GetTextOffset();
3010 lineLength = pTextLine->GetTextLength();
3012 if (lineOffset <= textIndex && textIndex < lineOffset + lineLength)
3019 pTextLine = new (std::nothrow)TextLine(this);
3020 SysTryReturn(NID_GRP
3022 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3026 if (pNoneWrapComposeInfo != null)
3028 lineOffset = pNoneWrapComposeInfo->prevTextOffset;
3037 lineOffset = __length - 1;
3041 lineBounds.width = rect.width;
3044 lineBounds.height = 0;
3046 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3053 lineBounds.width = rect.width;
3059 // endType = ForwardAnalyze(lineOffset, __length - lineOffset, lineBounds.width, __wrap,
3060 // lineLength, textSize.width, textSize.height);
3061 endType = ForwardAnalyzeWithBaseline(lineOffset, __length - lineOffset, lineBounds.width, __wrap,
3062 lineLength, textSize.width, textSize.height, baseline);
3064 lineBounds.height = textSize.height;
3065 pTextLine->SetBounds(lineBounds);
3066 pTextLine->SetTextOffset(lineOffset);
3067 pTextLine->SetTextLength(lineLength);
3068 pTextLine->SetRegion(textSize.width, textSize.height);
3069 pTextLine->SetEndType(endType);
3070 pTextLine->SetBaseline(baseline);
3076 BackwardAnalyze(lineOffset, lineBounds.width, &textCount, &textSize.width, &textSize.height);
3078 lineBounds.height = textSize.height;
3079 lineOffset -= (textCount - 1);
3080 lineLength = textCount;
3081 if (lineOffset == 0)
3083 endType = TEXT_RETBY_NORMAL;
3087 endType = TEXT_RETBY_LIMITWIDTH;
3090 pTextLine->SetBounds(lineBounds);
3091 pTextLine->SetTextOffset(lineOffset);
3092 pTextLine->SetTextLength(lineLength);
3093 pTextLine->SetRegion(textSize.width, textSize.height);
3094 pTextLine->SetEndType(endType);
3095 pTextLine->SetBaseline(baseline);
3101 pTextLine->SetEndType(TEXT_RETBY_NORMAL);
3105 rect.height = lineBounds.height;
3107 if (textIndex < lineOffset)
3109 lineOffset = textIndex;
3110 endType = ForwardAnalyze(lineOffset, __length - lineOffset, lineBounds.width, __wrap,
3111 lineLength, textSize.width, textSize.height);
3113 lineBounds.height = textSize.height;
3115 else if (forwardSearch && textIndex >= lineOffset + lineLength)
3118 GetRegion(lineOffset + lineLength, textIndex - (lineOffset + lineLength) + 1,
3119 needDim.width, needDim.height);
3122 int remainingWidth = needDim.width - (lineBounds.width - textSize.width);
3125 textSize.width += needDim.width;
3126 lineLength += textIndex - (lineOffset + lineLength) + 1;
3130 GetRegion(lineOffset, 1, charDim.width, charDim.height);
3133 remainingWidth -= charDim.width;
3134 textSize.width -= charDim.width;
3136 if (remainingWidth <= 0)
3142 lineLength -= index;
3144 else if (endType != TEXT_RETBY_LIMITWIDTH && lineLength != __length)
3148 Dimension lineTextSize;
3150 int remainingWidth = 0;
3152 pTextLine->GetRegion(0, lineLength, lineTextSize.width, lineTextSize.height);
3153 remainingWidth = lineBounds.width - lineTextSize.width;
3154 BackwardAnalyze(lineOffset - 1, remainingWidth, &textCount, &textSize.width, &textSize.height);
3156 if (textSize.width > 0)
3158 lineOffset -= textCount;
3159 lineLength += textCount;
3160 textSize.width += lineTextSize.width;
3161 lineBounds.height = textSize.height;
3162 endType = TEXT_RETBY_LIMITLENGTH;
3179 pTextLine->SetBounds(lineBounds);
3180 pTextLine->SetRegion(textSize.width, textSize.height);
3181 pTextLine->SetTextLength(lineLength);
3182 pTextLine->SetTextOffset(lineOffset);
3183 pTextLine->SetEndType(endType);
3184 pTextLine->SetBaseline(baseline);
3190 TextComposite::ComposeInWrap(Rectangle& rect)
3192 SysTryReturn(NID_GRP
3193 , __pCurrentTextColumn
3194 , -1, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
3199 int remainingLength = 0;
3200 int remainingWidth = 0;
3201 int remainingHeight = 0;
3203 bool hasPrevLine = false;
3205 TextLine* pTextLine = null;
3207 int endType = TEXT_RETBY_NORMAL;
3208 Rectangle lineBounds;
3209 Dimension lineTextSize;
3212 int displayLineCount = 0;
3213 int displayHeight = 0;
3215 int lineBaseline = 0;
3217 pTextLine = __pCurrentTextColumn->GetPrevLineChangedStartLine();
3218 if (pTextLine != null)
3220 endType = pTextLine->GetEndType();
3221 lineOffset = pTextLine->GetTextOffset();
3222 lineLength = pTextLine->GetTextLength();
3223 lineBounds = pTextLine->GetBounds();
3224 lineBaseline = pTextLine->GetBaseline();
3225 pTextLine->GetRegion(0, pTextLine->GetTextLength(), lineTextSize.width, lineTextSize.height);
3227 if (endType != TEXT_RETBY_LINEFEED)
3229 textIndex = lineOffset + lineLength;
3230 remainingLength = __length - textIndex;
3231 remainingWidth = lineBounds.width - lineTextSize.width;
3234 if (remainingLength == 0)
3241 textIndex = lineOffset + lineLength;
3242 remainingLength = __length - textIndex;
3243 remainingWidth = rect.width;
3244 offsetY = lineBounds.y + lineBounds.height;
3246 if (remainingLength == 0)
3248 int nextY = offsetY;
3249 lineTextSize.height = lineBounds.height;
3251 pTextLine = new (std::nothrow)TextLine(this);
3252 SysTryReturn(NID_GRP
3254 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3256 lineBounds.y = nextY;
3258 pTextLine->SetBounds(lineBounds);
3259 pTextLine->SetRegion(0, lineTextSize.height);
3260 pTextLine->SetTextLength(0);
3261 pTextLine->SetTextOffset(textIndex);
3262 pTextLine->SetEndType(TEXT_RETBY_LINEFEED);
3263 pTextLine->SetBaseline(0);
3265 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3267 if (lineBounds.y + lineBounds.height <= rect.height)
3269 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3270 displayHeight += lineBounds.height;
3271 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3281 remainingLength = __length;
3282 remainingWidth = rect.width;
3284 __pCurrentTextColumn->SetChangedStartLineIndex(0);
3289 pTextLine = new (std::nothrow)TextLine(this);
3290 SysTryReturn(NID_GRP
3292 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3294 lineBounds.x = rect.x;
3295 lineBounds.width = rect.width;
3296 lineBounds.y = offsetY;
3297 lineTextSize.height = 0;
3299 if (remainingLength == 0)
3301 lineTextSize.height = GetHeight(0);
3302 lineBounds.height = lineTextSize.height;
3304 pTextLine->SetBounds(lineBounds);
3305 pTextLine->SetRegion(0, lineTextSize.height);
3306 pTextLine->SetTextLength(0);
3307 pTextLine->SetTextOffset(textIndex);
3308 pTextLine->SetEndType(TEXT_RETBY_NORMAL);
3309 pTextLine->SetBaseline(0);
3311 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3313 if (lineBounds.y + lineBounds.height <= rect.height)
3315 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3316 displayHeight += lineBounds.height;
3317 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3324 remainingHeight = rect.height;
3326 while (remainingLength != 0)
3328 ret = ForwardAnalyzeWithBaseline(textIndex, remainingLength, remainingWidth, __wrap, textCount, textSize.width, textSize.height, baseline);
3344 lineOffset = textIndex;
3345 lineLength = textCount;
3346 lineTextSize.width = textSize.width;
3347 lineTextSize.height = textSize.height;
3348 lineBounds.height = textSize.height;
3351 pTextLine->SetBounds(lineBounds);
3352 pTextLine->SetRegion(lineTextSize.width, lineTextSize.height);
3353 pTextLine->SetTextLength(lineLength);
3354 pTextLine->SetTextOffset(lineOffset);
3355 pTextLine->SetEndType(ret);
3356 pTextLine->SetBaseline(baseline);
3358 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3361 if (lineBounds.y + lineBounds.height <= rect.height)
3363 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3364 displayHeight += lineBounds.height;
3365 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3370 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD)
3372 if (ret != TEXT_RETBY_LIMITWIDTH)
3374 lineLength += textCount;
3375 lineTextSize.width += textSize.width;
3376 lineBounds.height = Math::Max(lineBounds.height, textSize.height);
3377 lineTextSize.height = lineBounds.height;
3379 baseline = Math::Min(lineBaseline, baseline);
3381 pTextLine->SetBounds(lineBounds);
3382 pTextLine->SetRegion(lineTextSize.width, lineTextSize.height);
3383 pTextLine->SetTextLength(lineLength);
3384 pTextLine->SetEndType(endType);
3385 pTextLine->SetBaseline(baseline);
3394 lineLength += textCount;
3395 lineTextSize.width += textSize.width;
3396 lineBounds.height = Math::Max(lineBounds.height, textSize.height);
3397 lineTextSize.height = lineBounds.height;
3399 baseline = Math::Min(lineBaseline, baseline);
3401 pTextLine->SetBounds(lineBounds);
3402 pTextLine->SetRegion(lineTextSize.width, lineTextSize.height);
3403 pTextLine->SetTextLength(lineLength);
3404 pTextLine->SetEndType(endType);
3405 pTextLine->SetBaseline(baseline);
3410 __pCurrentTextColumn->SetChangedStartLineIndex(pTextLine->GetIndex());
3413 hasPrevLine = false;
3416 if (__pCurrentTextColumn->IsComposeDone())
3421 textIndex += textCount;
3422 remainingLength -= textCount;
3424 remainingHeight -= lineTextSize.height;
3426 if (remainingLength > 0)
3428 int nextY = lineBounds.y + lineBounds.height;
3430 pTextLine = new (std::nothrow)TextLine(this);
3431 SysTryReturn(NID_GRP
3433 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3435 lineBounds.x = rect.x;
3436 lineBounds.y = nextY;
3437 lineBounds.width = rect.width;
3438 lineTextSize.height = 0;
3440 remainingWidth = rect.width;
3444 if (endType == TEXT_RETBY_LINEFEED)
3446 int nextY = lineBounds.y + lineBounds.height;
3447 lineTextSize.height = lineBounds.height;
3449 pTextLine = new (std::nothrow)TextLine(this);
3450 SysTryReturn(NID_GRP
3452 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3454 lineBounds.x = rect.x;
3455 lineBounds.y = nextY;
3456 lineBounds.width = rect.width;
3457 lineBounds.height = lineTextSize.height;
3459 pTextLine->SetBounds(lineBounds);
3460 pTextLine->SetRegion(0, lineTextSize.height);
3461 pTextLine->SetTextLength(0);
3462 pTextLine->SetTextOffset(textIndex);
3463 pTextLine->SetEndType(TEXT_RETBY_LINEFEED);
3464 pTextLine->SetBaseline(0);
3466 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3469 if (lineBounds.y + lineBounds.height <= rect.height)
3471 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3472 displayHeight += lineBounds.height;
3473 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3482 Dimension columnTextSize;
3483 __pCurrentTextColumn->GetRegion(0, __length, columnTextSize.width, columnTextSize.height);
3484 rect.height = columnTextSize.height;
3488 __pCurrentTextColumn->SetChangedLastLineIndex(pTextLine->GetIndex());
3491 if (Tizen::App::_AppInfo::IsOspCompat())
3493 __pCurrentTextColumn->SetDisplayLineCount(0);
3494 __pCurrentTextColumn->SetDisplayHeight(0);
3501 TextComposite::ComposeInPartialMode(Rectangle& rect)
3503 SysTryReturn(NID_GRP
3504 , __pCurrentTextColumn
3505 , -1, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
3510 int remainingLength = 0;
3511 int remainingWidth = 0;
3512 int remainingHeight = 0;
3518 Dimension lineTextSize;
3519 Rectangle lineBounds;
3520 bool hasPrevLine = false;
3521 int displayLineCount = 0;
3522 int displayHeight = 0;
3524 int lineBaseline = 0;
3526 TextLine* pTextLine = null;
3527 int endType = TEXT_RETBY_NORMAL;
3529 if (__lineIndexCompositeDone != 0)
3531 pTextLine = __pCurrentTextColumn->GetTextLine(__lineIndexCompositeDone - 1);
3532 lineCount = __lineIndexCompositeDone;
3535 if (pTextLine != null)
3537 endType = pTextLine->GetEndType();
3538 lineOffset = pTextLine->GetTextOffset();
3539 lineLength = pTextLine->GetTextLength();
3540 lineBounds = pTextLine->GetBounds();
3541 lineBaseline = pTextLine->GetBaseline();
3542 pTextLine->GetRegion(0, pTextLine->GetTextLength(), lineTextSize.width, lineTextSize.height);
3544 if (endType != TEXT_RETBY_LINEFEED)
3546 textIndex = lineOffset + lineLength;
3547 remainingLength = __length - textIndex;
3548 remainingWidth = lineBounds.width - lineTextSize.width;
3551 if (remainingLength == 0)
3558 textIndex = lineOffset + lineLength;
3559 remainingLength = __length - textIndex;
3560 remainingWidth = rect.width;
3561 offsetY = lineBounds.y + lineBounds.height;
3563 if (remainingLength == 0)
3565 int nextY = offsetY;
3566 lineTextSize.height = lineBounds.height;
3568 pTextLine = new (std::nothrow)TextLine(this);
3569 SysTryReturn(NID_GRP
3571 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3573 lineBounds.y = nextY;
3575 pTextLine->SetBounds(lineBounds);
3576 pTextLine->SetRegion(0, lineTextSize.height);
3577 pTextLine->SetTextLength(0);
3578 pTextLine->SetTextOffset(textIndex);
3579 pTextLine->SetEndType(TEXT_RETBY_LINEFEED);
3580 pTextLine->SetBaseline(0);
3582 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3584 if (lineBounds.y + lineBounds.height <= rect.height)
3586 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3587 displayHeight += lineBounds.height;
3588 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3598 remainingLength = __length;
3599 remainingWidth = rect.width;
3601 __pCurrentTextColumn->SetChangedStartLineIndex(0);
3606 pTextLine = new (std::nothrow)TextLine(this);
3607 SysTryReturn(NID_GRP
3609 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3611 lineBounds.x = rect.x;
3612 lineBounds.width = rect.width;
3613 lineBounds.y = offsetY;
3614 lineTextSize.height = 0;
3616 if (remainingLength == 0)
3618 lineTextSize.height = GetHeight(0);
3619 lineBounds.height = lineTextSize.height;
3621 pTextLine->SetBounds(lineBounds);
3622 pTextLine->SetRegion(0, lineTextSize.height);
3623 pTextLine->SetTextLength(0);
3624 pTextLine->SetTextOffset(textIndex);
3625 pTextLine->SetEndType(TEXT_RETBY_NORMAL);
3626 pTextLine->SetBaseline(0);
3628 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3630 if (lineBounds.y + lineBounds.height <= rect.height)
3632 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3633 displayHeight += lineBounds.height;
3634 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3641 remainingHeight = GetComposePartialLimitHeight();
3642 if (remainingHeight == 0)
3644 remainingHeight = rect.height;
3646 if (remainingHeight < lineBounds.height && remainingLength > 0)
3648 remainingHeight = lineBounds.height;
3651 while (remainingLength != 0)
3653 //ret = ForwardAnalyze(textIndex, remainingLength, remainingWidth, __wrap, textCount, textSize.width, textSize.height);
3654 ret = ForwardAnalyzeWithBaseline(textIndex, remainingLength, remainingWidth, __wrap, textCount, textSize.width, textSize.height, baseline);
3670 lineOffset = textIndex;
3671 lineLength = textCount;
3672 lineTextSize.width = textSize.width;
3673 lineTextSize.height = textSize.height;
3674 lineBounds.height = textSize.height;
3677 pTextLine->SetBounds(lineBounds);
3678 pTextLine->SetRegion(lineTextSize.width, lineTextSize.height);
3679 pTextLine->SetTextLength(lineLength);
3680 pTextLine->SetTextOffset(lineOffset);
3681 pTextLine->SetEndType(endType);
3682 pTextLine->SetBaseline(baseline);
3684 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3686 if (lineBounds.y + lineBounds.height <= rect.height)
3688 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3689 displayHeight += lineBounds.height;
3690 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3694 __lineIndexCompositeDone++;
3695 __totalComposedHeight += lineTextSize.height;
3699 if (__wrap == TEXT_OBJECT_WRAP_TYPE_WORD)
3701 if (ret != TEXT_RETBY_LIMITWIDTH)
3703 lineLength += textCount;
3704 lineTextSize.width += textSize.width;
3705 lineBounds.height = Math::Max(lineBounds.height, textSize.height);
3706 lineTextSize.height = lineBounds.height;
3708 baseline = Math::Min(lineBaseline, baseline);
3710 pTextLine->SetBounds(lineBounds);
3711 pTextLine->SetRegion(lineTextSize.width, lineTextSize.height);
3712 pTextLine->SetTextLength(lineLength);
3713 pTextLine->SetEndType(endType);
3714 pTextLine->SetBaseline(baseline);
3723 lineLength += textCount;
3724 lineTextSize.width += textSize.width;
3725 lineBounds.height = Math::Max(lineBounds.height, textSize.height);
3726 lineTextSize.height = lineBounds.height;
3728 baseline = Math::Min(lineBaseline, baseline);
3730 pTextLine->SetBounds(lineBounds);
3731 pTextLine->SetRegion(lineTextSize.width, lineTextSize.height);
3732 pTextLine->SetTextLength(lineLength);
3733 pTextLine->SetEndType(endType);
3734 pTextLine->SetBaseline(baseline);
3739 __pCurrentTextColumn->SetChangedStartLineIndex(pTextLine->GetIndex());
3742 hasPrevLine = false;
3745 if (__pCurrentTextColumn->IsComposeDone())
3750 textIndex += textCount;
3751 remainingLength -= textCount;
3752 remainingHeight -= lineTextSize.height;
3754 if (remainingHeight < 0)
3759 if (remainingLength > 0)
3761 int nextY = lineBounds.y + lineBounds.height;
3763 pTextLine = new (std::nothrow)TextLine(this);
3764 SysTryReturn(NID_GRP
3766 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3768 lineBounds.x = rect.x;
3769 lineBounds.y = nextY;
3770 lineBounds.width = rect.width;
3771 lineTextSize.height = 0;
3773 remainingWidth = rect.width;
3777 if (endType == TEXT_RETBY_LINEFEED)
3779 int nextY = lineBounds.y + lineBounds.height;
3780 lineTextSize.height = lineBounds.height;
3782 pTextLine = new (std::nothrow)TextLine(this);
3783 SysTryReturn(NID_GRP
3785 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3787 lineBounds.x = rect.x;
3788 lineBounds.y = nextY;
3789 lineBounds.width = rect.width;
3790 lineBounds.height = lineTextSize.height;
3792 pTextLine->SetBounds(lineBounds);
3793 pTextLine->SetRegion(0, lineTextSize.height);
3794 pTextLine->SetTextLength(0);
3795 pTextLine->SetTextOffset(textIndex);
3796 pTextLine->SetEndType(TEXT_RETBY_LINEFEED);
3797 pTextLine->SetBaseline(0);
3799 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3803 if (lineBounds.y + lineBounds.height <= rect.height)
3805 __pCurrentTextColumn->SetDisplayLineCount(++displayLineCount);
3806 displayHeight += lineBounds.height;
3807 __pCurrentTextColumn->SetDisplayHeight(displayHeight);
3810 __lineIndexCompositeDone++;
3811 __totalComposedHeight += lineTextSize.height;
3812 __pCurrentTextColumn->FinishCompose();
3819 __pCurrentTextColumn->FinishCompose();
3824 rect.height = __totalComposedHeight;
3828 __pCurrentTextColumn->SetChangedLastLineIndex(pTextLine->GetIndex());
3831 if (Tizen::App::_AppInfo::IsOspCompat())
3833 __pCurrentTextColumn->SetDisplayLineCount(0);
3834 __pCurrentTextColumn->SetDisplayHeight(0);
3841 TextComposite::ComposeInNormalWrap(Rectangle& rect)
3843 return ComposeInWrap(rect);
3847 TextComposite::ComposeInWordWrap(Rectangle& rect)
3849 if (IsWidthManagerEnabled())
3851 return ComposeInWrapByTextWidth(rect);
3855 return ComposeInWrap(rect);
3860 TextComposite::ComposeInNoneWrapMiddleEllipsis(Rectangle& rect)
3862 int endType = TEXT_RETBY_NORMAL;
3863 Rectangle lineBounds;
3864 Dimension abbrevTextDim;
3870 lineBounds.width = rect.width;
3873 lineBounds.height = rect.height;
3874 endType = ForwardAnalyzeWithBaseline(0, __length, lineBounds.width, __wrap, length, textSize.width, textSize.height, baseline);
3876 if (endType != TEXT_RETBY_LIMITWIDTH)
3878 __drawTextEllipsis = false;
3879 return ComposeInNoneWrap(rect);
3882 __drawTextEllipsis = true;
3884 TextElement* pTextElement = null;
3885 TextSimple* pSimpleText = null;
3887 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(0));
3888 SysTryReturn(NID_GRP
3890 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
3892 TextElementType objectType = pTextElement->GetType();
3893 SysTryReturn(NID_GRP
3894 , objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT
3895 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
3897 pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
3898 if (pSimpleText != null)
3900 SetAbbrevObjectFontInfo(pSimpleText);
3903 __pAbbrevTextElement->GetRegion(0, 1, abbrevTextDim.width, abbrevTextDim.height);
3904 __middleEllipsisWidth = abbrevTextDim.width;
3906 ForwardAnalyze(0, __length, ((lineBounds.width - __middleEllipsisWidth + 10) >> 1), __wrap, length, textSize.width, textSize.height);
3907 __middleEllipsisTextLengthInHead = length;
3908 __middleEllipsisHeadWidth = textSize.width;
3910 maxHeight = textSize.height;
3912 ForwardAnalyze(__middleEllipsisTextLengthInHead, __length - __middleEllipsisTextLengthInHead, lineBounds.width - __middleEllipsisWidth -
3913 __middleEllipsisHeadWidth, __wrap, length, textSize.width, textSize.height);
3914 __middleEllipsisTextLengthInTail = length;
3916 if (maxHeight < textSize.height)
3918 maxHeight = textSize.height;
3921 TextLine* pTextLine = new (std::nothrow)TextLine(this);
3922 SysTryReturn(NID_GRP
3924 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3926 pTextLine->SetBounds(lineBounds);
3927 pTextLine->SetRegion(lineBounds.width, maxHeight);
3928 pTextLine->SetTextLength(__length);
3929 pTextLine->SetTextOffset(0);
3930 pTextLine->SetEndType(TEXT_RETBY_NORMAL);
3931 pTextLine->SetBaseline(baseline);
3933 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
3935 lineBounds.height = maxHeight;
3941 TextComposite::ComposeInNoneWrapHeadEllipsis(Rectangle& rect)
3943 SysTryReturn(NID_GRP
3944 , __pCurrentTextColumn
3945 , -1, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
3947 int endType = TEXT_RETBY_NORMAL;
3948 Rectangle lineBounds;
3949 Dimension abbrevTextDim;
3955 lineBounds.width = rect.width;
3958 lineBounds.height = rect.height;
3959 endType = ForwardAnalyzeWithBaseline(0, __length, lineBounds.width, __wrap, length, textSize.width, textSize.height, baseline);
3961 if (endType != TEXT_RETBY_LIMITWIDTH)
3963 __drawTextEllipsis = false;
3964 return ComposeInNoneWrap(rect);
3967 __drawTextEllipsis = true;
3968 TextElement* pTextElement = null;
3969 TextSimple* pSimpleText = null;
3971 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(0));
3972 SysTryReturn(NID_GRP
3974 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
3976 TextElementType objectType = pTextElement->GetType();
3977 SysTryReturn(NID_GRP
3978 , objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT
3979 , -1, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
3981 pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
3982 if (pSimpleText != null)
3984 SetAbbrevObjectFontInfo(pSimpleText);
3987 __pAbbrevTextElement->GetRegion(0, 1, abbrevTextDim.width, abbrevTextDim.height);
3988 __headEllipsisWidth = abbrevTextDim.width;
3990 BackwardAnalyze(__length - 1, lineBounds.width - abbrevTextDim.width, &__headEllipsisTextLength, &textSize.width, &textSize.height);
3991 maxHeight = textSize.height;
3993 TextLine* pTextLine = new (std::nothrow)TextLine(this);
3994 SysTryReturn(NID_GRP
3996 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
3998 pTextLine->SetBounds(lineBounds);
3999 pTextLine->SetRegion(lineBounds.width, maxHeight);
4000 pTextLine->SetTextLength(__length);
4001 pTextLine->SetTextOffset(0);
4002 pTextLine->SetEndType(TEXT_RETBY_NORMAL);
4003 pTextLine->SetBaseline(baseline);
4005 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
4007 lineBounds.height = maxHeight;
4013 TextComposite::DrawAbbrev(_CanvasImpl& canvasImpl, const Rectangle& displayRect, const TextObjectAlignment align)
4015 if (__TextObjectEllipsisType == TEXT_OBJECT_ELLIPSIS_TYPE_MIDDLE)
4017 return DrawAbbrevInMiddleEllipsis(canvasImpl, displayRect, align);
4019 else if (__TextObjectEllipsisType == TEXT_OBJECT_ELLIPSIS_TYPE_HEAD)
4021 return DrawAbbrevInHeadEllipsis(canvasImpl, displayRect, align);
4028 TextComposite::GetValue(int textIndex, TextComponentInfoValueType type, unsigned int* value) const
4030 IEnumerator* pEnum = null;
4031 TextElement* pTextElement = null;
4033 int elementTextLength = 0;
4035 pEnum = __pTextElementList->GetEnumeratorN();
4036 while (pEnum->MoveNext() == E_SUCCESS)
4038 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
4039 if (pTextElement == null)
4044 elementTextLength = pTextElement->GetTextLength();
4046 if (textIndex < offset + elementTextLength)
4048 TextElementType objectType = pTextElement->GetType();
4050 if (objectType != TextUtility::GetObjectTypeFromValueType(type) && objectType != TEXT_ELEMENT_TYPE_CUTLINK)
4053 return E_INVALID_ARG;
4056 *value = pTextElement->GetValue(type);
4061 offset += elementTextLength;
4065 return E_INVALID_ARG;
4069 TextComposite::BackwardAnalyze(int startTextIndex, int maxWidth, int* actualLength, int* width, int* height)
4071 int remainingWidth = 0;
4079 remainingWidth = maxWidth;
4082 while (startTextIndex >= 0 && textSize.width < remainingWidth)
4084 GetRegion(startTextIndex, length, textSize.width, textSize.height);
4086 if (textSize.width <= remainingWidth)
4088 *actualLength = length;
4089 *width = textSize.width;
4090 *height = textSize.height;
4101 TextComposite::GetFirstTextIndexAt(int elementIndex) const
4103 SysTryReturn(NID_GRP
4104 , elementIndex >= 0 && elementIndex < __pTextElementList->GetCount()
4105 , -1, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
4107 IEnumerator* pEnum = null;
4108 TextElement* pTextElement = null;
4111 int elementTextOffset = 0;
4113 if (elementIndex == 0)
4118 pEnum = __pTextElementList->GetEnumeratorN();
4119 while (pEnum->MoveNext() == E_SUCCESS)
4121 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
4122 if (pTextElement == null)
4127 if (index == elementIndex)
4132 elementTextOffset += pTextElement->GetTextLength();
4134 pTextElement = null;
4140 if (pTextElement != null)
4142 return elementTextOffset;
4149 TextComposite::DrawAbbrevInMiddleEllipsis(_CanvasImpl& canvasImpl, const Rectangle& displayRect, const TextObjectAlignment alignment)
4151 TextLine* pTextLine = __pCurrentTextColumn->GetTextLine(0);
4152 SysTryReturn(NID_GRP
4154 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text line.");
4157 Rectangle adjustedRect;
4159 pTextLine->GetRegion(0, __length, textSize.width, textSize.height);
4160 adjustedRect.x = displayRect.x;
4161 adjustedRect.width = displayRect.width;
4163 switch (alignment & TEXT_ALIGNMASK_VERT)
4165 case TEXT_OBJECT_ALIGNMENT_TOP:
4168 adjustedRect.y = displayRect.y;
4171 case TEXT_OBJECT_ALIGNMENT_MIDDLE:
4172 adjustedRect.y = displayRect.y + (displayRect.height - textSize.height) / 2;
4175 case TEXT_OBJECT_ALIGNMENT_BOTTOM:
4176 adjustedRect.y = displayRect.y + (displayRect.height - textSize.height);
4179 adjustedRect.height = displayRect.height - (displayRect.y - adjustedRect.y);
4181 TextElement* pTextElement = null;
4182 TextSimple* pSimpleText = null;
4184 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(0));
4185 SysTryReturn(NID_GRP
4187 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
4189 TextElementType objectType = pTextElement->GetType();
4190 SysTryReturn(NID_GRP
4191 , objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT
4192 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to draw to symbol object.");
4194 pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
4195 if (pSimpleText != null)
4197 SetAbbrevObjectFontInfo(pSimpleText);
4200 DrawPartial(canvasImpl, adjustedRect, 0, __middleEllipsisTextLengthInHead);
4202 adjustedRect.x += __middleEllipsisHeadWidth;
4203 __pAbbrevTextElement->Draw(canvasImpl, adjustedRect, 0, 1, (TextObjectAlignment)(TEXT_OBJECT_ALIGNMENT_TOP | TEXT_OBJECT_ALIGNMENT_LEFT), TEXT_OBJECT_ACTION_TYPE_NONE);
4205 adjustedRect.x += __middleEllipsisWidth;
4206 DrawPartial(canvasImpl, adjustedRect, __length - __middleEllipsisTextLengthInTail, __middleEllipsisTextLengthInTail);
4212 TextComposite::DrawAbbrevInHeadEllipsis(_CanvasImpl& canvasImpl, const Rectangle& displayRect, const TextObjectAlignment alignment)
4214 TextLine* pTextLine = __pCurrentTextColumn->GetTextLine(0);
4215 SysTryReturn(NID_GRP
4217 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text line.");
4219 result r = E_SUCCESS;
4221 Rectangle adjustedRect;
4223 pTextLine->GetRegion(0, __length, textSize.width, textSize.height);
4224 adjustedRect.x = displayRect.x;
4225 adjustedRect.width = displayRect.width;
4227 switch (alignment & TEXT_ALIGNMASK_VERT)
4229 case TEXT_OBJECT_ALIGNMENT_TOP:
4232 adjustedRect.y = displayRect.y;
4235 case TEXT_OBJECT_ALIGNMENT_MIDDLE:
4236 adjustedRect.y = displayRect.y + (displayRect.height - textSize.height) / 2;
4239 case TEXT_OBJECT_ALIGNMENT_BOTTOM:
4240 adjustedRect.y = displayRect.y + (displayRect.height - textSize.height);
4243 adjustedRect.height = displayRect.height - (displayRect.y - adjustedRect.y);
4245 TextElement* pTextElement = null;
4246 TextSimple* pSimpleText = null;
4248 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(0));
4249 r = GetLastResult();
4250 SysTryReturn(NID_GRP
4252 , r, r, "[%s] Fail to get element.", GetErrorMessage(r));
4254 TextElementType objectType = pTextElement->GetType();
4255 SysTryReturn(NID_GRP
4256 , objectType == TEXT_ELEMENT_TYPE_CUTLINK || objectType == TEXT_ELEMENT_TYPE_TEXT
4257 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to draw to symbol object.");
4259 pSimpleText = dynamic_cast < TextSimple* >(pTextElement);
4260 if (pSimpleText != null)
4262 SetAbbrevObjectFontInfo(pSimpleText);
4265 __pAbbrevTextElement->Draw(canvasImpl, adjustedRect, 0, 1, (TextObjectAlignment)(TEXT_OBJECT_ALIGNMENT_TOP | TEXT_OBJECT_ALIGNMENT_LEFT), TEXT_OBJECT_ACTION_TYPE_NONE);
4267 adjustedRect.x += __headEllipsisWidth;
4268 DrawPartial(canvasImpl, adjustedRect, __length - __headEllipsisTextLength, __headEllipsisTextLength);
4274 TextComposite::DrawPartial(_CanvasImpl& canvasImpl, Rectangle& displayRect, int startTextIndex, int textLength)
4276 SysTryReturn(NID_GRP
4277 , 0 <= startTextIndex && startTextIndex < __length
4278 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
4280 SysTryReturn(NID_GRP
4281 , textLength <= __length
4282 , E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The argument is invalid.");
4284 result r = E_SUCCESS;
4285 IEnumerator* pEnum = null;
4286 TextElement* pTextElement = null;
4289 int currentLength = 0;
4290 int textIndexFromElementOffset = 0;
4292 int elementTextOffset = 0;
4293 Rectangle adjustedRect = displayRect;
4294 int blockStartTextIndex = 0;
4295 int blockEndTextIndex = 0;
4296 bool isAlternateLookEnabled = false;
4297 int textIndex = startTextIndex;
4299 _Canvas* pCanvas = _Canvas::GetInstance(canvasImpl);
4300 SysTryReturn(NID_GRP
4302 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get native canvas instance.");
4304 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset, nodeIndex, currentLength,
4305 textIndexFromElementOffset);
4306 SysTryReturn(NID_GRP
4308 , E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Fail to get text element.");
4310 currentLength = Math::Min(textLength, currentLength);
4312 pEnum = __pTextElementList->GetEnumeratorN();
4313 while (textLength > 0)
4315 textLength -= currentLength;
4317 pTextElement->GetRegion(textIndexFromElementOffset, currentLength, textSize.width, textSize.height);
4319 if (pTextElement->IsBackGroundDrawingModeEnable())
4321 r = pCanvas->FillRectangle(pTextElement->GetBackgroundColor(), Rectangle(adjustedRect.x, displayRect.y, textSize.width, displayRect.height));
4322 SysTryReturn(NID_GRP
4324 , r, r, "[%s] Propagating.", GetErrorMessage(r));
4327 isAlternateLookEnabled = pTextElement->GetValue(SET_ALTERNATE_LOOK);
4328 if ((__displayBlock) && (isAlternateLookEnabled == false))
4330 Dimension tempTextSize;
4333 blockStartTextIndex = Math::Max(__workStart, textIndex);
4334 blockEndTextIndex = Math::Min(__workStart + __workLength, textIndex + currentLength);
4335 if (blockStartTextIndex < blockEndTextIndex)
4337 blockStartTextIndex = textIndexFromElementOffset + (blockStartTextIndex - textIndex);
4338 blockEndTextIndex = textIndexFromElementOffset + (blockEndTextIndex - textIndex);
4339 adjustedX = adjustedRect.x;
4341 if (textIndexFromElementOffset < blockStartTextIndex)
4343 pTextElement->GetRegion(textIndexFromElementOffset, blockStartTextIndex - textIndexFromElementOffset,
4344 tempTextSize.width, tempTextSize.height);
4345 adjustedX += tempTextSize.width;
4348 Rectangle blockRect = adjustedRect;
4349 blockRect.x = adjustedX;
4353 pTextElement->Draw(canvasImpl, adjustedRect, textIndexFromElementOffset, currentLength, (TextObjectAlignment)(TEXT_OBJECT_ALIGNMENT_TOP | TEXT_OBJECT_ALIGNMENT_LEFT),
4354 TEXT_OBJECT_ACTION_TYPE_NONE);
4356 adjustedRect.x += textSize.width;
4357 adjustedRect.width -= textSize.width;
4359 if (!textLength || adjustedRect.width <= 0)
4364 textIndex += currentLength;
4366 if (pEnum->MoveNext() != E_SUCCESS)
4371 pTextElement = static_cast < TextElement* >(pEnum->GetCurrent());
4373 textIndexFromElementOffset = pTextElement->GetValue(SET_TEXT_OFFSET);
4374 currentLength = Math::Min(textLength, pTextElement->GetTextLength());
4376 if (currentLength == 0)
4387 TextComposite::SetPartialComposingModeEnabled(bool enable)
4389 __partialComposingModeEnabled = enable;
4393 TextComposite::IsPartialComposingModeEnabled(void) const
4395 return __partialComposingModeEnabled;
4399 TextComposite::InitPartialComposeMode(void)
4401 __lineIndexCompositeDone = 0;
4402 __totalComposedHeight = 0;
4403 __composePartialLimitHeight = 0;
4405 SysTryReturn(NID_GRP
4406 , __pCurrentTextColumn
4407 , false, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
4409 __pCurrentTextColumn->SetFirstDisplayLineIndex(0);
4410 __pCurrentTextColumn->SetFirstDisplayPositionY(0);
4411 __pCurrentTextColumn->PrepareCompose();
4417 TextComposite::IsComposeDone() const
4419 SysTryReturn(NID_GRP
4420 , __pCurrentTextColumn
4421 , false, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
4423 return __pCurrentTextColumn->IsComposeDone();
4427 TextComposite::ComposeInWrapByTextWidth(Rectangle& rect)
4429 SysTryReturn(NID_GRP
4430 , __pCurrentTextColumn
4431 , false, E_INVALID_STATE, "[E_INVALID_STATE] This instance is not constructed yet.");
4433 Rectangle lineBounds;
4436 int remainingLength = 0;
4437 int remainingWidth = 0;
4438 int remainingHeight = 0;
4440 bool hasPrevLine = false;
4441 int endType = TEXT_RETBY_NORMAL;
4442 Dimension lineTextSize;
4445 TextLine* pTextLine = null;
4447 pTextLine = __pCurrentTextColumn->GetPrevLineChangedStartLine();
4448 if (pTextLine != null)
4450 endType = pTextLine->GetEndType();
4451 lineOffset = pTextLine->GetTextOffset();
4452 lineLength = pTextLine->GetTextLength();
4453 lineBounds = pTextLine->GetBounds();
4454 pTextLine->GetRegion(0, pTextLine->GetTextLength(), lineTextSize.width, lineTextSize.height);
4456 if (endType != TEXT_RETBY_LINEFEED)
4458 textIndex = lineOffset;
4459 remainingLength = __length - textIndex;
4460 remainingWidth = rect.width;
4463 if (remainingLength == 0)
4470 textIndex = lineOffset + lineLength;
4471 remainingLength = __length - textIndex;
4472 remainingWidth = rect.width;
4473 offsetY = lineBounds.y + lineBounds.height;
4474 lineBounds.y = offsetY;
4476 if (remainingLength == 0)
4478 lineTextSize.height = lineBounds.height;
4480 pTextLine = new (std::nothrow)TextLine(this);
4481 SysTryReturn(NID_GRP
4483 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
4485 pTextLine->SetBounds(lineBounds);
4486 pTextLine->SetRegion(0, lineTextSize.height);
4487 pTextLine->SetTextLength(0);
4488 pTextLine->SetTextOffset(textIndex);
4489 pTextLine->SetEndType(TEXT_RETBY_LINEFEED);
4491 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
4500 remainingLength = __length;
4501 remainingWidth = rect.width;
4502 lineBounds.x = rect.x;
4504 lineBounds.width = rect.width;
4507 remainingHeight = rect.height;
4509 __pTextWidthManager->StartCompose(textIndex);
4511 TextLineComposeInfo composeInfo;
4512 composeInfo.height = 0;
4513 composeInfo.width = 0;
4514 composeInfo.length = 0;
4515 composeInfo.endType = TEXT_RETBY_NORMAL;
4517 while (remainingLength != 0)
4519 __pTextWidthManager->GetCurrentLineInfo(remainingWidth, composeInfo);
4520 composeInfo.height += __lineSpacing;
4524 lineBounds.height = composeInfo.height;
4525 pTextLine->SetBounds(lineBounds);
4526 pTextLine->SetRegion(composeInfo.width, composeInfo.height);
4527 pTextLine->SetTextLength(composeInfo.length);
4528 pTextLine->SetEndType(composeInfo.endType);
4529 hasPrevLine = false;
4533 if (composeInfo.length == 0)
4535 composeInfo.length = 1;
4538 pTextLine = new (std::nothrow)TextLine(this);
4539 SysTryReturn(NID_GRP
4541 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
4543 lineBounds.height = composeInfo.height;
4545 pTextLine->SetBounds(lineBounds);
4546 pTextLine->SetTextOffset(textIndex);
4547 pTextLine->SetRegion(composeInfo.width, composeInfo.height);
4548 pTextLine->SetTextLength(composeInfo.length);
4549 pTextLine->SetEndType(composeInfo.endType);
4551 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
4555 if (__pCurrentTextColumn->IsComposeDone())
4560 textIndex += composeInfo.length;
4561 remainingLength -= composeInfo.length;
4562 remainingHeight -= composeInfo.height;
4564 if (remainingLength > 0)
4566 int nextY = lineBounds.y + lineBounds.height;
4568 lineBounds.x = rect.x;
4569 lineBounds.y = nextY;
4570 lineBounds.width = rect.width;
4571 lineTextSize.height = 0;
4572 remainingWidth = rect.width;
4576 if (composeInfo.endType == TEXT_RETBY_LINEFEED)
4578 int nextY = lineBounds.y + lineBounds.height;
4579 lineTextSize.height = lineBounds.height;
4581 pTextLine = new (std::nothrow)TextLine(this);
4582 SysTryReturn(NID_GRP
4584 , -1, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
4586 lineBounds.x = rect.x;
4587 lineBounds.y = nextY;
4588 lineBounds.width = rect.width;
4589 lineBounds.height = lineTextSize.height;
4591 pTextLine->SetBounds(lineBounds);
4592 pTextLine->SetRegion(0, lineTextSize.height);
4593 pTextLine->SetTextLength(0);
4594 pTextLine->SetTextOffset(textIndex);
4595 pTextLine->SetEndType(TEXT_RETBY_LINEFEED);
4596 __pCurrentTextColumn->AddLineDuringCompose(pTextLine);
4610 __pTextWidthManager->EndCompose();
4612 Dimension columnSize;
4613 __pCurrentTextColumn->GetRegion(0, __length, columnSize.width, columnSize.height);
4614 rect.height = columnSize.height;
4620 TextComposite::GetCutLinkObjectInfo(int cutLinkIndex, int& textStartIndex, int& textLength) const
4622 return __pCutLinkListInfo->GetCutLinkObjectInfo(cutLinkIndex, textStartIndex, textLength);
4626 TextComposite::GetTotalComposedHeight(void) const
4628 return __totalComposedHeight;
4632 TextComposite::GetAnalysedTotalHeight(void) const
4634 TextLine* pTextLine = null;
4635 pTextLine = __pCurrentTextColumn->GetTextLine(__lineIndexCompositeDone - 1);
4642 int lineOffset = pTextLine->GetTextOffset();
4643 int lineLength = pTextLine->GetTextLength();
4645 int composedLength = lineOffset + lineLength;
4646 if (composedLength == 0)
4651 return (int)(GetTotalComposedHeight() * __length / composedLength);
4655 TextComposite::SetComposePartialLimitHeight(int limitHeight)
4657 __composePartialLimitHeight = limitHeight;
4661 TextComposite::GetComposePartialLimitHeight(void) const
4663 return __composePartialLimitHeight;
4668 TextComposite::GetObjectType(int textIndex) const
4670 TextElement* pTextElement = null;
4672 int currentLength = 0;
4673 int elementIndex = 0;
4674 int textIndexFromElementOffset = 0;
4675 int elementTextOffset = 0;
4677 pTextElement = GetElementAtTextIndex(textIndex, elementTextOffset
4678 , elementIndex, currentLength, textIndexFromElementOffset);
4679 if (pTextElement == null)
4681 return TEXT_ELEMENT_TYPE_NONE;
4685 return pTextElement->GetType();
4690 TextComposite::GetElementIndexOf(TextElement& textElement) const
4694 result r = E_SUCCESS;
4696 r = __pTextElementList->IndexOf(textElement, index);
4697 SysTryReturn(NID_GRP
4699 , false, r, "[%s] Fail to add element.", GetErrorMessage(r));
4705 TextComposite::GetElementAtElementIndex(int nodeIndex) const
4707 result r = E_SUCCESS;
4709 TextElement* pTextElement = null;
4710 pTextElement = static_cast < TextElement* >(__pTextElementList->GetAt(nodeIndex));
4711 SysTryReturn(NID_GRP
4713 , null, r, "[%s] Fail to add element.", GetErrorMessage(r));
4715 return pTextElement;
4719 TextComposite::GetTextLength(void) const
4725 TextComposite::GetElementCount(void) const
4727 return __pTextElementList->GetCount();
4731 TextComposite::SetBlock(bool enable)
4733 __displayBlock = enable;
4737 TextComposite::SetImageAlign(TextObjectAlignment align)
4739 return SetValueToAllTextElements(SET_IMAGE_ALIGN, (unsigned int)align);
4743 TextComposite::GetWrap(void) const
4749 TextComposite::SetLineSpace(int gap)
4751 __lineSpacing = gap;
4755 TextComposite::GetLineSpace(void) const
4757 return __lineSpacing;
4761 TextComposite::SetElementVerticalAlignment(TextObjectAlignment alignment)
4763 __elementVertialAlignment = alignment;
4767 TextComposite::GetElementVerticalAlignment(void) const
4769 return __elementVertialAlignment;
4773 TextComposite::SetCursorIndex(int cursorIndex)
4775 __cursorIndex = cursorIndex;
4779 TextComposite::GetCursorIndex(void) const
4781 return __cursorIndex;
4785 TextComposite::SetTextObjectEllipsisType(TextObjectEllipsisType type)
4787 __TextObjectEllipsisType = type;
4790 TextObjectEllipsisType
4791 TextComposite::GetTextObjectEllipsisType(void) const
4793 return __TextObjectEllipsisType;
4797 TextComposite::SetTextAbbreviationEnabled(bool enable)
4799 __drawAbbrevText = enable;
4803 TextComposite::IsTextAbbreviationEnabled(void) const
4805 if (__drawAbbrevText && __drawTextEllipsis)
4814 TextComposite::GetBlock(void) const
4816 return __displayBlock;
4820 TextComposite::GetWorkStart(void) const
4826 TextComposite::GetWorkLength(void) const
4828 return __workLength;
4832 TextComposite::GetImageAlign(int textIndex) const
4834 result r = E_SUCCESS;
4835 unsigned int value = 0;
4837 r = GetValue(textIndex, SET_IMAGE_ALIGN, &value);
4838 SysTryReturn(NID_GRP
4840 , TEXT_OBJECT_ALIGNMENT_INVALID, r, "[%s] Propagating.", GetErrorMessage(r));
4842 return (TextObjectAlignment)value;
4846 TextComposite::IsChanged(void) const
4852 TextComposite::SetBlockColor(const Color& color)
4854 __defaultBlockColor = color;
4858 TextComposite::GetBlockColor(void) const
4860 return __defaultBlockColor;
4864 TextComposite::SetTextWidthManager(TextWidthManager* pTextWidthManager)
4866 __pTextWidthManager = pTextWidthManager;
4870 TextComposite::SetWidthManagerEnabled(bool widthManagerEnable)
4872 __widthManagerEnabled = widthManagerEnable;
4876 TextComposite::IsWidthManagerEnabled(void) const
4878 return __widthManagerEnabled;
4882 TextComposite::SetWorkWidth(Font* pFont, wchar_t* pText, int workStart, int textLength)
4884 result r = E_SUCCESS;
4888 const wchar_t* pSrc = &pText[workStart];
4890 workLength = Math::Abs(textLength);
4892 r = TextUtility::GetTextExtent(pFont, pSrc, workLength, false, width, height);
4893 SysTryReturn(NID_GRP
4895 , r, r, "[%s] Propagating.", GetErrorMessage(r));
4899 __workWidth = -width;
4903 __workWidth = width;
4910 TextComposite::GetWorkWidth(void)
4916 TextComposite::SetTextSweepInfo(TextObjectSweepInfo* pTextSweepInfo)
4918 __pSweepInfo = pTextSweepInfo;
4922 TextComposite::GetTextSweepInfo(TextObjectSweepInfo& textSweepInfo)
4924 textSweepInfo.isValid = __pSweepInfo->isValid;
4925 textSweepInfo.sweepType = __pSweepInfo->sweepType;
4926 textSweepInfo.sweepEventType = __pSweepInfo->sweepEventType;
4927 textSweepInfo.anchorTextIndex = __pSweepInfo->anchorTextIndex;
4928 textSweepInfo.anchorLineIndex = __pSweepInfo->anchorLineIndex;
4929 textSweepInfo.sweepRegionStartLineIndex = __pSweepInfo->sweepRegionStartLineIndex;
4930 textSweepInfo.sweepRegionLineCount = __pSweepInfo->sweepRegionLineCount;
4931 textSweepInfo.insertedLineCount = __pSweepInfo->insertedLineCount;
4932 textSweepInfo.deletedLineCount = __pSweepInfo->deletedLineCount;
4933 textSweepInfo.widthChanged = __pSweepInfo->widthChanged;
4937 TextComposite::UpdateTextSweepInfo(TextObjectSweepInfo* pTextSweepInfo)
4939 __pSweepInfo->isValid = pTextSweepInfo->isValid;
4940 __pSweepInfo->sweepType = pTextSweepInfo->sweepType;
4941 __pSweepInfo->sweepEventType = pTextSweepInfo->sweepEventType;
4942 __pSweepInfo->anchorTextIndex = pTextSweepInfo->anchorTextIndex;
4943 __pSweepInfo->anchorLineIndex = pTextSweepInfo->anchorLineIndex;
4944 __pSweepInfo->sweepRegionStartLineIndex = pTextSweepInfo->sweepRegionStartLineIndex;
4945 __pSweepInfo->sweepRegionLineCount = pTextSweepInfo->sweepRegionLineCount;
4946 __pSweepInfo->insertedLineCount = pTextSweepInfo->insertedLineCount;
4947 __pSweepInfo->deletedLineCount = pTextSweepInfo->deletedLineCount;
4948 __pSweepInfo->widthChanged = pTextSweepInfo->widthChanged;
4951 }}} // Tizen::Graphics::_Text