License conversion from Flora to Apache 2.0
[platform/core/uifw/dali-toolkit.git] / automated-tests / TET / dali-internal-test-suite / text-view / utc-Dali-TextView-Relayout-Utilities.cpp
1 /*
2  * Copyright (c) 2014 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 #include <iostream>
19
20 #include <stdlib.h>
21 #include <tet_api.h>
22
23 #include <dali/public-api/dali-core.h>
24 #include <dali-toolkit/dali-toolkit.h>
25
26 #include <dali-toolkit-test-suite-utils.h>
27
28 // Internal headers are allowed here
29 #include <dali-toolkit/internal/controls/text-view/relayout-utilities.h>
30 #include <dali-toolkit/internal/controls/text-view/text-view-processor.h>
31
32 using namespace Dali;
33 using namespace Dali::Toolkit;
34 using namespace Dali::Toolkit::Internal;
35
36 namespace
37 {
38
39 const Toolkit::Internal::TextView::LayoutParameters DEFAULT_LAYOUT_PARAMETERS;
40
41 // Data structures used to create an 'experiment' in TET cases
42
43
44 bool TestEqual( float x, float y )
45 {
46   return ( fabsf( x - y ) < Math::MACHINE_EPSILON_1000 );
47 }
48
49 //////////////////////////////////////////////////////////////////
50
51 struct CalculateSubLineLayoutTest
52 {
53   std::string description;
54   std::string inputLine;
55   float parentWidth;
56   std::size_t groupIndex;
57   std::size_t wordIndex;
58   std::size_t characterIndex;
59   TextViewRelayout::HorizontalWrapType splitPolicy;
60   float shrinkFactor;
61
62   float resultLineLength;
63   float resultMaxCharHeight;
64   float resultMaxAscender;
65 };
66
67 bool TestCalculateSubLineLayout( const CalculateSubLineLayoutTest& test,  const char* location )
68 {
69   tet_printf( "%s", test.description.c_str() );
70
71   // Create styled text.
72   MarkupProcessor::StyledTextArray inputStyledText;
73   MarkupProcessor::GetStyledTextArray( test.inputLine, inputStyledText, true );
74
75   // Create styled text layout info.
76   Toolkit::Internal::TextView::RelayoutData relayoutData;
77   TextViewProcessor::CreateTextInfo( inputStyledText,
78                                      DEFAULT_LAYOUT_PARAMETERS,
79                                      relayoutData );
80
81   // Prepare input parameters and the result structure and call the function to be tested.
82
83   // Creaqte indices.
84   TextViewProcessor::TextInfoIndices indices( 0, test.groupIndex, test.wordIndex, test.characterIndex );
85
86   // Get the input line.
87   TextViewProcessor::LineLayoutInfo inputLineLayout;
88
89   if( !relayoutData.mTextLayoutInfo.mLinesLayoutInfo.empty() )
90   {
91     inputLineLayout = *relayoutData.mTextLayoutInfo.mLinesLayoutInfo.begin();
92   }
93
94   // Result struct.
95   TextViewRelayout::SubLineLayoutInfo resultLayoutInfo;
96
97   CalculateSubLineLayout( test.parentWidth,
98                           indices,
99                           inputLineLayout,
100                           test.splitPolicy,
101                           test.shrinkFactor,
102                           resultLayoutInfo  );
103
104   // Check results.
105   if( !TestEqual( test.resultLineLength, resultLayoutInfo.mLineLength ) )
106   {
107     tet_printf( "Fail. different line length %f == %f. %s", test.resultLineLength, resultLayoutInfo.mLineLength, location );
108     return false;
109   }
110
111   if( !TestEqual( test.resultMaxCharHeight, resultLayoutInfo.mMaxCharHeight ) )
112   {
113     tet_printf( "Fail. different max character height %f == %f. %s", test.resultMaxCharHeight, resultLayoutInfo.mMaxCharHeight, location );
114     return false;
115   }
116
117   if( !TestEqual( test.resultMaxAscender, resultLayoutInfo.mMaxAscender ) )
118   {
119     tet_printf( "Fail. different max ascender %f == %f. %s", test.resultMaxAscender, resultLayoutInfo.mMaxAscender, location );
120     return false;
121   }
122
123   return true;
124 }
125
126 //////////////////////////////////////////////////////////////////
127
128 struct AlignmentOffsetTest
129 {
130   Toolkit::Alignment::Type alignment;
131   float parentSize;
132   float wholeTextSize;
133
134   float resultOffset;
135 };
136
137 bool TestAlignmentOffset( const AlignmentOffsetTest& test, const char* location )
138 {
139   float offset = 0.f;
140
141   switch( test.alignment )
142   {
143     case Toolkit::Alignment::HorizontalLeft:
144     case Toolkit::Alignment::HorizontalCenter:
145     case Toolkit::Alignment::HorizontalRight:
146     {
147       offset = TextViewRelayout::CalculateXoffset( test.alignment, test.parentSize, test.wholeTextSize );
148       break;
149     }
150     case Toolkit::Alignment::VerticalTop:
151     case Toolkit::Alignment::VerticalCenter:
152     case Toolkit::Alignment::VerticalBottom:
153     {
154       offset = TextViewRelayout::CalculateYoffset( test.alignment, test.parentSize, test.wholeTextSize );
155       break;
156     }
157   }
158
159   // Check results.
160   if( !TestEqual( test.resultOffset, offset ) )
161   {
162     tet_printf( "Fail. different offset %f == %f. %s", test.resultOffset, offset, location );
163     return false;
164   }
165
166   return true;
167 }
168
169 //////////////////////////////////////////////////////////////////
170
171 struct JustificationOffsetTest
172 {
173   Toolkit::TextView::LineJustification justification;
174   float wholeTextWidth;
175   float lineLength;
176
177   float resultOffset;
178 };
179
180 bool TestJustificationOffset( const JustificationOffsetTest& test, const char* location )
181 {
182   float offset = TextViewRelayout::CalculateJustificationOffset( test.justification, test.wholeTextWidth, test.lineLength );
183
184   // Check results.
185   if( !TestEqual( test.resultOffset, offset ) )
186   {
187     tet_printf( "Fail. different offset %f == %f. %s", test.resultOffset, offset, location );
188     return false;
189   }
190
191   return true;
192 }
193
194 //////////////////////////////////////////////////////////////////
195
196 struct CalculateVisibilityTest
197 {
198   Vector3 position;
199   Size size;
200   Size parentSize;
201   TextViewRelayout::VisibilityTestType type;
202
203   bool resultVisible;
204 };
205
206 bool TestCalculateVisibility( const CalculateVisibilityTest& test, const char* location )
207 {
208   if( test.resultVisible != TextViewRelayout::IsVisible( test.position, test.size, test.parentSize, test.type ) )
209   {
210     tet_printf( "Fail. different visibility. Type %d, %s", test.type, location );
211     return false;
212   }
213
214   return true;
215 }
216
217 //////////////////////////////////////////////////////////////////
218
219 } // namespace
220
221 static void Startup();
222 static void Cleanup();
223
224 extern "C" {
225   void (*tet_startup)() = Startup;
226   void (*tet_cleanup)() = Cleanup;
227 }
228
229 enum {
230   POSITIVE_TC_IDX = 0x01,
231   NEGATIVE_TC_IDX,
232 };
233
234 #define MAX_NUMBER_OF_TESTS 10000
235 extern "C" {
236   struct tet_testlist tet_testlist[MAX_NUMBER_OF_TESTS];
237 }
238
239 // Add test functionality for all APIs in the class (Positive and Negative)
240 TEST_FUNCTION( UtcDaliTextViewDefaultConstructorDestructor, POSITIVE_TC_IDX );  // Calls structs's default constructor and destructors and checks their default values.
241 TEST_FUNCTION( UtcDaliTextViewCalculateSubLineLayout, POSITIVE_TC_IDX );        // Checks the function which calculates the layout info of the portion of the line which fits on the text-view width.
242 TEST_FUNCTION( UtcDaliTextViewCalculateAlignmentOffsets, POSITIVE_TC_IDX );     // Checks the horizontal and vertical alignaments (for the whole text).
243 TEST_FUNCTION( UtcDaliTextViewCalculateJustificationOffsets, POSITIVE_TC_IDX ); // Checks the justification alignment (line per line).
244 TEST_FUNCTION( UtcDaliTextViewCalculateVisibility, POSITIVE_TC_IDX );           // Checks the text-actor visibility within the text-view with a rectangle intersection test.
245
246 TEST_FUNCTION( UtcDaliTextViewMiscelaneousAsserts, NEGATIVE_TC_IDX );           // Tests some strange asserts.
247
248 // Called only once before first test is run.
249 static void Startup()
250 {
251 }
252
253 // Called only once after last test is run
254 static void Cleanup()
255 {
256 }
257
258 static void UtcDaliTextViewDefaultConstructorDestructor()
259 {
260   ToolkitTestApplication application;
261
262   tet_infoline("UtcDaliTextViewDefaultConstructorDestructor : ");
263
264   // Test RelayoutParameters defaults.
265   TextViewRelayout::RelayoutParameters relayoutParameters;
266
267   DALI_TEST_EQUALS( relayoutParameters.mPositionOffset, Vector3::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
268   DALI_TEST_EQUALS( relayoutParameters.mLineSize, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
269   DALI_TEST_EQUALS( relayoutParameters.mWordSize, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
270   DALI_TEST_EQUALS( relayoutParameters.mCharacterSize, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
271   DALI_TEST_EQUALS( relayoutParameters.mIndices.mLineIndex, 0u, TEST_LOCATION );
272   DALI_TEST_EQUALS( relayoutParameters.mIndices.mGroupIndex, 0u, TEST_LOCATION );
273   DALI_TEST_EQUALS( relayoutParameters.mIndices.mWordIndex, 0u, TEST_LOCATION );
274   DALI_TEST_EQUALS( relayoutParameters.mIndices.mCharacterIndex, 0u, TEST_LOCATION );
275   DALI_TEST_EQUALS( relayoutParameters.mCharacterGlobalIndex, 0u, TEST_LOCATION );
276   DALI_TEST_CHECK( !relayoutParameters.mIsFirstCharacter );
277   DALI_TEST_CHECK( !relayoutParameters.mIsFirstCharacterOfWord );
278   DALI_TEST_CHECK( !relayoutParameters.mIsNewLine );
279   DALI_TEST_CHECK( !relayoutParameters.mIsNewLineCharacter );
280   DALI_TEST_CHECK( !relayoutParameters.mIsWhiteSpace );
281   DALI_TEST_CHECK( !relayoutParameters.mIsVisible );
282
283   // Test FadeParameter defaults
284   TextViewRelayout::FadeParameters fadeParameters;
285
286   DALI_TEST_EQUALS( fadeParameters.mRightFadeBoundary, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
287   DALI_TEST_EQUALS( fadeParameters.mRightFadeThreshold, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
288   DALI_TEST_EQUALS( fadeParameters.mRightFadeBoundaryOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
289   DALI_TEST_EQUALS( fadeParameters.mRightFadeThresholdOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
290   DALI_TEST_EQUALS( fadeParameters.mRightAlphaCoeficients, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
291   DALI_TEST_EQUALS( fadeParameters.mLeftFadeBoundary, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
292   DALI_TEST_EQUALS( fadeParameters.mLeftFadeThreshold, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
293   DALI_TEST_EQUALS( fadeParameters.mLeftFadeBoundaryOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
294   DALI_TEST_EQUALS( fadeParameters.mLeftFadeThresholdOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
295   DALI_TEST_EQUALS( fadeParameters.mLeftAlphaCoeficients, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
296   DALI_TEST_EQUALS( fadeParameters.mTopFadeBoundary, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
297   DALI_TEST_EQUALS( fadeParameters.mTopFadeThreshold, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
298   DALI_TEST_EQUALS( fadeParameters.mTopFadeBoundaryOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
299   DALI_TEST_EQUALS( fadeParameters.mTopFadeThresholdOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
300   DALI_TEST_EQUALS( fadeParameters.mTopAlphaCoeficients, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
301   DALI_TEST_EQUALS( fadeParameters.mBottomFadeBoundary, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
302   DALI_TEST_EQUALS( fadeParameters.mBottomFadeThreshold, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
303   DALI_TEST_EQUALS( fadeParameters.mBottomFadeBoundaryOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
304   DALI_TEST_EQUALS( fadeParameters.mBottomFadeThresholdOffset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
305   DALI_TEST_EQUALS( fadeParameters.mBottomAlphaCoeficients, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
306   DALI_TEST_CHECK( !fadeParameters.mIsPartiallyVisible );
307
308   // Test EllipsizeParameters defaults
309   TextViewRelayout::EllipsizeParameters ellipsizeParameters;
310
311   DALI_TEST_EQUALS( ellipsizeParameters.mPosition, Vector3::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
312   DALI_TEST_EQUALS( ellipsizeParameters.mLineDescender, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
313   DALI_TEST_EQUALS( ellipsizeParameters.mLineWidth, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
314   DALI_TEST_EQUALS( ellipsizeParameters.mEllipsizeBoundary, Vector2::ZERO, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
315   DALI_TEST_EQUALS( ellipsizeParameters.mFirstIndex, 0u, TEST_LOCATION );
316   DALI_TEST_EQUALS( ellipsizeParameters.mLastIndex, 0u, TEST_LOCATION );
317   DALI_TEST_CHECK( !ellipsizeParameters.mEllipsizeLine );
318   DALI_TEST_CHECK( !ellipsizeParameters.mIsLineWidthFullyVisible );
319   DALI_TEST_CHECK( !ellipsizeParameters.mIsLineHeightFullyVisible );
320   DALI_TEST_CHECK( !ellipsizeParameters.mIsNextLineFullyVisibleHeight );
321   DALI_TEST_CHECK( !ellipsizeParameters.mCreateEllipsizedTextActors );
322   DALI_TEST_CHECK( !ellipsizeParameters.mLineFits );
323   DALI_TEST_CHECK( !ellipsizeParameters.mWordFits );
324
325   // Test UnderlineInfo defaults
326   TextViewRelayout::UnderlineInfo underlineInfo;
327
328   DALI_TEST_EQUALS( underlineInfo.mMaxHeight, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
329   DALI_TEST_EQUALS( underlineInfo.mMaxThickness, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
330   DALI_TEST_EQUALS( underlineInfo.mPosition, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
331
332   // Test TextUnderlineStatus defaults
333   TextViewRelayout::TextUnderlineStatus textUnderlineStatus;
334
335   DALI_TEST_CHECK( textUnderlineStatus.mUnderlineInfo.empty() );
336   DALI_TEST_EQUALS( textUnderlineStatus.mCharacterGlobalIndex, 0u, TEST_LOCATION );
337   DALI_TEST_EQUALS( textUnderlineStatus.mLineGlobalIndex, 0u, TEST_LOCATION );
338   DALI_TEST_CHECK( !textUnderlineStatus.mCurrentUnderlineStatus );
339
340   // Test SubLineLayoutInfo defaults
341   TextViewRelayout::SubLineLayoutInfo subLineLayoutInfo;
342
343   DALI_TEST_EQUALS( subLineLayoutInfo.mLineLength, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
344   DALI_TEST_EQUALS( subLineLayoutInfo.mMaxCharHeight, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
345   DALI_TEST_EQUALS( subLineLayoutInfo.mMaxAscender, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
346 }
347
348 static void UtcDaliTextViewCalculateSubLineLayout()
349 {
350   ToolkitTestApplication application;
351
352   tet_infoline("UtcDaliTextViewCalculateSubLineLayout : ");
353
354   struct CalculateSubLineLayoutTest calculateSubLineLayoutTest[] =
355   {
356     //WrapByCharacter
357     {
358       "The line is wraped by character. All characters have the same size.",
359       "Hello world", // input line
360       100.f,         // parent width
361       0,
362       0,              // indices
363       0,
364       TextViewRelayout::WrapByCharacter, // split policy
365       1.f,
366       // results
367       91.041672f, // line length. (only fits 8 characters 8x11.38)
368       11.380209f, // max character height
369       10.242188f  // max ascender
370     },
371     {
372       "The line is wraped by character. There are characters with different sizes.",
373       "Hello <font size='14'>world</font>", // input line
374       100.f,         // parent width
375       0,
376       0,              // indices
377       0,
378       TextViewRelayout::WrapByCharacter, // split policy
379       1.f,
380       // results
381       94.835075f, // line length. (only fits 8 characters 6x11.38 + 2x13.27)
382       13.276911f, // max character height
383       11.949220f  // max ascender
384     },
385     {
386       "The line is wraped by character. There are characters with different sizes. It calculates the layout for the second line.",
387       "Hello <font size='14'>wo</font>rld hell<font size='14'>o world</font>", // input line
388       100.f,         // parent width
389       0,
390       2,              // indices. The third character of the third word starts in a new line.
391       2,
392       TextViewRelayout::WrapByCharacter, // split policy
393       1.f,
394       // results
395       91.041672f, // line length. (only fits 8 characters 8x11.38)
396       11.380209f, // max character height
397       10.242188f  // max ascender
398     },
399     {
400       "The line is wraped by character. There are characters with different sizes. It calculates the layout for the third line.",
401       "Hello <font size='14'>wo</font>rld hell<font size='14'>o world</font>", // input line
402       100.f,         // parent width
403       0,
404       4,              // indices. The fifth character of the fifth word starts in a new line.
405       4,
406       TextViewRelayout::WrapByCharacter, // split policy
407       1.f,
408       // results
409       92.938377f, // line length. (only fits 8 characters 8x11.38)
410       13.276911f, // max character height
411       11.949220f  // max ascender
412     },
413
414     //WrapByWord
415     {
416       "The line is wraped by word. All characters have the same size.",
417       "Hello world", // input line
418       100.f,         // parent width
419       0,
420       0,              // indices. It shouldn't use the index character so 9999999 shouldn't make it crash.
421       9999999,
422       TextViewRelayout::WrapByWord, // split policy
423       1.f,
424       // results
425       56.901047f, // line length. (only fits 5 characters 5x11.38, white space is not counted)
426       11.380209f, // max character height
427       10.242188f  // max ascender
428     },
429     {
430       "The line is wraped by word. There are characters with different sizes.",
431       "Hell<font size='14'>o</font> world", // input line
432       100.f,         // parent width
433       0,
434       0,              // indices.
435       0,
436       TextViewRelayout::WrapByWord, // split policy
437       1.f,
438       // results
439       58.797747f, // line length. (only fits 5 characters 4x11.38 + 13.276911, white space is not counted)
440       13.276911f, // max character height
441       11.949220f  // max ascender
442     },
443     {
444       "The line is wraped by word. There are characters with different sizes. It calculates the layout for the second line.",
445       "Hello <font size='14'>wo</font>rld <font size='16'>hello world</font>", // input line
446       100.f,         // parent width
447       0,
448       2,              // indices. The third word starts in a new line.
449       0,
450       TextViewRelayout::WrapByWord, // split policy
451       1.f,
452       // results
453       60.694449f, // line length. (only fits 5 characters 2x13.276911 + 3x11.38)
454       13.276911f, // max character height
455       11.949220f  // max ascender
456     },
457     {
458       "The line is wraped by word. The word doen't fit.",
459       "Hello world", // input line
460       40.f,          // parent width
461       0,
462       0,              // indices. The third word starts in a new line.
463       0,
464       TextViewRelayout::WrapByWord, // split policy
465       1.f,
466       // results
467       0.f,        // line length. (The word doesn't fit)
468       11.380209f, // max character height
469       10.242188f  // max ascender
470     },
471
472     //WrapByWordAndSplit
473     {
474       "The line is wraped by word and by character. All characters have the same size. There is not a long word.",
475       "Hello world hello world", // input line
476       100.f,         // parent width
477       0,
478       0,              // indices.
479       0,
480       TextViewRelayout::WrapByWordAndSplit, // split policy
481       1.f,
482       // results
483       56.901047f, // line length. (only fits 5 characters 5x11.38, white space is not counted)
484       11.380209f, // max character height
485       10.242188f  // max ascender
486     },
487     {
488       "The line is wraped by word and by character. All characters have the same size. There is a long word.",
489       "Helloooooooo world", // input line
490       100.f,         // parent width
491       0,
492       0,              // indices.
493       0,
494       TextViewRelayout::WrapByWordAndSplit, // split policy
495       1.f,
496       // results
497       91.041672f, // line length. (only fits 8 characters 8x11.38)
498       11.380209f, // max character height
499       10.242188f  // max ascender
500     },
501     {
502       "The line is wraped by word and by character. There are characters with different sizes. There is a long word. It calculates the layout for the second line.",
503       "Helloooooooo <font size='14'>world</font>", // input line
504       100.f,         // parent width
505       0,
506       0,              // indices.
507       8,
508       TextViewRelayout::WrapByWordAndSplit, // split policy
509       1.f,
510       // results
511       45.520836f, // line length. (only fits 8 characters 8x11.38)
512       11.380209f, // max character height
513       10.242188f  // max ascender
514     },
515     {
516       "The line is wraped by word and by character. There are characters with different sizes. There is a shrink factor.",
517       "Helloooooooo<font size='14'> world</font>", // input line
518       100.f,         // parent width
519       0,
520       0,              // indices.
521       8,
522       TextViewRelayout::WrapByWordAndSplit, // split policy
523       0.7f,
524       // results
525       95.593755f, // line length. (only fits 12 characters 8x11.38)
526       7.9661463f, // max character height
527       7.169531f  // max ascender
528     },
529
530     //WrapByLineAndSplit
531     {
532       "The line is wraped by end of line and by character. All characters have the same size.",
533       "Hello world", // input line
534       100.f,         // parent width
535       0,
536       0,              // indices
537       0,
538       TextViewRelayout::WrapByLineAndSplit, // split policy
539       1.f,
540       // results
541       91.041672f, // line length. (only fits 8 characters 8x11.38)
542       11.380209f, // max character height
543       10.242188f  // max ascender
544     },
545     {
546       "The line fits in the width.",
547       "Hello", // input line
548       100.f,         // parent width
549       0,
550       0,             // indices
551       0,
552       TextViewRelayout::WrapByLineAndSplit, // split policy
553       1.f,
554       // results
555       56.901047f, // line length. (only fits 5 characters 5x11.38)
556       11.380209f, // max character height
557       10.242188f  // max ascender
558     },
559     {
560       "The line is wraped by end of line and by character. All characters have the same size. It calculates the layout for the second line.",
561       "Hello world, hello world", // input line
562       100.f,         // parent width
563       0,
564       2,             // indices
565       2,
566       TextViewRelayout::WrapByLineAndSplit, // split policy
567       1.f,
568       // results
569       91.041672f, // line length. (only fits 8 characters 8x11.38)
570       11.380209f, // max character height
571       10.242188f  // max ascender
572     },
573   };
574   const std::size_t numberOfTests( 15 );
575
576   for( std::size_t index = 0; index < numberOfTests; ++index )
577   {
578     const CalculateSubLineLayoutTest& test = calculateSubLineLayoutTest[index];
579
580     if( !TestCalculateSubLineLayout( test, TEST_LOCATION ) )
581     {
582       tet_result( TET_FAIL );
583     }
584   }
585
586   tet_result( TET_PASS );
587 }
588
589 static void UtcDaliTextViewCalculateAlignmentOffsets()
590 {
591   ToolkitTestApplication application;
592
593   tet_infoline("UtcDaliTextViewCalculateAlignmentOffsets : ");
594
595   struct AlignmentOffsetTest alignmentOffsetTest[] =
596   {
597     {
598       Toolkit::Alignment::HorizontalLeft,
599       100.f,
600       75.f,
601       0.f
602     },
603     {
604       Toolkit::Alignment::HorizontalCenter,
605       100.f,
606       75.f,
607       12.5f
608     },
609     {
610       Toolkit::Alignment::HorizontalRight,
611       100.f,
612       75.f,
613       25.f
614     },
615     {
616       Toolkit::Alignment::VerticalTop,
617       100.f,
618       75.f,
619       0.f
620     },
621     {
622       Toolkit::Alignment::VerticalCenter,
623       100.f,
624       75.f,
625       12.5f
626     },
627     {
628       Toolkit::Alignment::VerticalBottom,
629       100.f,
630       75.f,
631       25.f
632     }
633   };
634   const std::size_t numberOfTests( 6 );
635
636   for( std::size_t index = 0; index < numberOfTests; ++index )
637   {
638     const AlignmentOffsetTest& test = alignmentOffsetTest[index];
639
640     if( !TestAlignmentOffset( test, TEST_LOCATION ) )
641     {
642       tet_result( TET_FAIL );
643     }
644   }
645
646   tet_result( TET_PASS );
647 }
648
649 static void UtcDaliTextViewCalculateJustificationOffsets()
650 {
651   ToolkitTestApplication application;
652
653   tet_infoline("UtcDaliTextViewCalculateJustificationOffsets : ");
654
655   struct JustificationOffsetTest justificationOffsetTest[] =
656   {
657     {
658       Toolkit::TextView::Left,
659       100.f,
660       75.f,
661       0.f
662     },
663     {
664       Toolkit::TextView::Justified,
665       100.f,
666       75.f,
667       0.f
668     },
669     {
670       Toolkit::TextView::Center,
671       100.f,
672       150.f,
673       -25.f
674     },
675     {
676       Toolkit::TextView::Right,
677       100.f,
678       75.f,
679       25.f
680     },
681   };
682   const std::size_t numberOfTests( 4 );
683
684   for( std::size_t index = 0; index < numberOfTests; ++index )
685   {
686     const JustificationOffsetTest& test = justificationOffsetTest[index];
687
688     if( !TestJustificationOffset( test, TEST_LOCATION ) )
689     {
690       tet_result( TET_FAIL );
691     }
692   }
693
694   tet_result( TET_PASS );
695 }
696
697
698 static void UtcDaliTextViewCalculateVisibility()
699 {
700   ToolkitTestApplication application;
701
702   tet_infoline("UtcDaliTextViewCalculateVisibility : ");
703
704   struct CalculateVisibilityTest calculateVisibilityTest[] =
705   {
706     {
707       Vector3( 0.f, 10.f, 0.f ),
708       Size( 10.f, 10.f ),
709       Size( 100.f, 100.f ),
710       TextViewRelayout::FULLY_VISIBLE,
711       true
712     },
713     {
714       Vector3( 10.f, 10.f, 0.f ),
715       Size( 10.f, 10.f ),
716       Size( 100.f, 100.f ),
717       TextViewRelayout::FULLY_VISIBLE,
718       true
719     },
720     {
721       Vector3( 0.f, 10.f, 0.f ),
722       Size( 150.f, 10.f ),
723       Size( 100.f, 100.f ),
724       TextViewRelayout::FULLY_VISIBLE,
725       false
726     },
727     {
728       Vector3( 0.f, 10.f, 0.f ),
729       Size( 10.f, 10.f ),
730       Size( 100.f, 100.f ),
731       TextViewRelayout::FULLY_VISIBLE_WIDTH,
732       true
733     },
734     {
735       Vector3( 95.f, 10.f, 0.f ),
736       Size( 10.f, 10.f ),
737       Size( 100.f, 100.f ),
738       TextViewRelayout::FULLY_VISIBLE_WIDTH,
739       false
740     },
741     {
742       Vector3( 0.f, 10.f, 0.f ),
743       Size( 10.f, 10.f ),
744       Size( 100.f, 100.f ),
745       TextViewRelayout::FULLY_VISIBLE_HEIGHT,
746       true
747     },
748     {
749       Vector3( 0.f, 0.f, 0.f ),
750       Size( 10.f, 10.f ),
751       Size( 100.f, 100.f ),
752       TextViewRelayout::FULLY_VISIBLE_HEIGHT,
753       false
754     },
755     {
756       Vector3( -10.f, 10.f, 0.f ),
757       Size( 150.f, 150.f ),
758       Size( 100.f, 100.f ),
759       TextViewRelayout::PARTIALLY_VISIBLE,
760       true
761     },
762     {
763       Vector3( -100.f, -100.f, 0.f ),
764       Size( 10.f, 10.f ),
765       Size( 100.f, 100.f ),
766       TextViewRelayout::PARTIALLY_VISIBLE,
767       false
768     },
769     {
770       Vector3( -10.f, 10.f, 0.f ),
771       Size( 50.f, 10.f ),
772       Size( 100.f, 100.f ),
773       TextViewRelayout::PARTIALLY_VISIBLE_WIDTH,
774       true
775     },
776     {
777       Vector3( 110.f, 10.f, 0.f ),
778       Size( 10.f, 10.f ),
779       Size( 100.f, 100.f ),
780       TextViewRelayout::PARTIALLY_VISIBLE_WIDTH,
781       false
782     },
783     {
784       Vector3( 0.f, 20.f, 0.f ),
785       Size( 10.f, 50.f ),
786       Size( 100.f, 100.f ),
787       TextViewRelayout::PARTIALLY_VISIBLE_HEIGHT,
788       true
789     },
790     {
791       Vector3( 0.f, -10.f, 0.f ),
792       Size( 10.f, 10.f ),
793       Size( 100.f, 100.f ),
794       TextViewRelayout::PARTIALLY_VISIBLE_HEIGHT,
795       false
796     },
797   };
798   const std::size_t numberOfTests( 13 );
799
800   for( std::size_t index = 0; index < numberOfTests; ++index )
801   {
802     const CalculateVisibilityTest& test = calculateVisibilityTest[index];
803
804     if( !TestCalculateVisibility( test, TEST_LOCATION ) )
805     {
806       tet_result( TET_FAIL );
807     }
808   }
809
810   tet_result( TET_PASS );
811 }
812
813 static void UtcDaliTextViewMiscelaneousAsserts()
814 {
815   ToolkitTestApplication application;
816
817   tet_infoline("UtcDaliTextViewMiscelaneousAsserts : ");
818
819   float offset = 0.f;
820
821   bool assert1 = false;
822   bool assert2 = false;
823   try
824   {
825     offset = Toolkit::Internal::TextViewRelayout::CalculateXoffset( Toolkit::Alignment::VerticalTop, 100.f, 50.f );
826   }
827   catch( Dali::DaliException& e )
828   {
829     tet_printf( "Assertion %s failed at %s\n", e.mCondition.c_str(), e.mLocation.c_str() );
830     DALI_TEST_EQUALS( e.mCondition, "!\"TextViewRelayout::CalculateXoffset: Wrong horizontal text alignment. Did you set a vertical one?\"", TEST_LOCATION );
831     assert1 = true;
832   }
833   catch( ... )
834   {
835     tet_result( TET_FAIL );
836   }
837   DALI_TEST_EQUALS( offset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
838
839   try
840   {
841     offset = Toolkit::Internal::TextViewRelayout::CalculateYoffset( Toolkit::Alignment::HorizontalRight, 100.f, 50.f );
842   }
843   catch( Dali::DaliException& e )
844   {
845     tet_printf( "Assertion %s failed at %s\n", e.mCondition.c_str(), e.mLocation.c_str() );
846     DALI_TEST_EQUALS( e.mCondition, "!\"TextViewRelayout::CalculateXoffset: Wrong vertical text alignment. Did you set an horizontal one?\"", TEST_LOCATION );
847     assert2 = true;
848   }
849   catch( ... )
850   {
851     tet_result( TET_FAIL );
852   }
853   DALI_TEST_EQUALS( offset, 0.f, Math::MACHINE_EPSILON_1000, TEST_LOCATION );
854
855   DALI_TEST_CHECK( assert1 && assert2 );
856
857 }