[dali_1.1.2] Merge branch 'devel/master' 66/47966/1
authorRichard Huang <r.huang@samsung.com>
Thu, 10 Sep 2015 10:06:04 +0000 (11:06 +0100)
committerRichard Huang <r.huang@samsung.com>
Thu, 10 Sep 2015 10:06:04 +0000 (11:06 +0100)
Change-Id: Id118d13609c287eb5eff8c9d92777784043daf8d

80 files changed:
automated-tests/src/dali-toolkit/utc-Dali-ScrollView.cpp
build/tizen/configure.ac
build/tizen/dali-toolkit/Makefile.am
build/tizen/docs/dali.doxy.in
dali-toolkit/devel-api/styling/style-manager.cpp
dali-toolkit/devel-api/styling/style-manager.h
dali-toolkit/internal/atlas-manager/atlas-manager-impl.cpp
dali-toolkit/internal/builder/builder-impl.cpp
dali-toolkit/internal/builder/builder-set-property.cpp
dali-toolkit/internal/controls/bubble-effect/bubble-actor.cpp
dali-toolkit/internal/controls/bubble-effect/bubble-actor.h
dali-toolkit/internal/controls/bubble-effect/bubble-emitter-impl.cpp
dali-toolkit/internal/controls/bubble-effect/bubble-emitter-impl.h
dali-toolkit/internal/controls/scroll-bar/scroll-bar-impl.cpp
dali-toolkit/internal/controls/scrollable/item-view/depth-layout.h
dali-toolkit/internal/controls/scrollable/item-view/grid-layout.h
dali-toolkit/internal/controls/scrollable/item-view/spiral-layout.h
dali-toolkit/internal/controls/scrollable/scroll-view/scroll-overshoot-indicator-impl.cpp
dali-toolkit/internal/controls/scrollable/scroll-view/scroll-overshoot-indicator-impl.h
dali-toolkit/internal/controls/scrollable/scroll-view/scroll-view-impl.cpp
dali-toolkit/internal/controls/scrollable/scroll-view/scroll-view-page-path-effect-impl.cpp
dali-toolkit/internal/controls/text-controls/text-field-impl.cpp
dali-toolkit/internal/controls/text-controls/text-font-style.cpp [new file with mode: 0644]
dali-toolkit/internal/controls/text-controls/text-font-style.h [new file with mode: 0644]
dali-toolkit/internal/controls/text-controls/text-label-impl.cpp
dali-toolkit/internal/controls/text-controls/text-selection-popup-impl.cpp
dali-toolkit/internal/file.list
dali-toolkit/internal/styling/style-manager-impl.cpp
dali-toolkit/internal/styling/style-manager-impl.h
dali-toolkit/internal/text/decorator/text-decorator.cpp
dali-toolkit/internal/text/decorator/text-decorator.h
dali-toolkit/internal/text/layouts/layout-engine.cpp
dali-toolkit/internal/text/layouts/layout-engine.h
dali-toolkit/internal/text/metrics.h [new file with mode: 0644]
dali-toolkit/internal/text/multi-language-support-impl.cpp
dali-toolkit/internal/text/rendering/atlas/text-atlas-renderer.cpp
dali-toolkit/internal/text/text-controller-impl.cpp
dali-toolkit/internal/text/text-controller-impl.h
dali-toolkit/internal/text/text-controller.cpp
dali-toolkit/internal/text/text-controller.h
dali-toolkit/internal/text/text-definitions.h
dali-toolkit/internal/text/text-io.cpp
dali-toolkit/public-api/accessibility-manager/accessibility-manager.h
dali-toolkit/public-api/controls/alignment/alignment.h
dali-toolkit/public-api/controls/buttons/button.h
dali-toolkit/public-api/controls/buttons/check-box-button.h
dali-toolkit/public-api/controls/buttons/push-button.h
dali-toolkit/public-api/controls/buttons/radio-button.h
dali-toolkit/public-api/controls/control-depth-index-ranges.h
dali-toolkit/public-api/controls/control-impl.h
dali-toolkit/public-api/controls/control.h
dali-toolkit/public-api/controls/default-controls/solid-color-actor.h
dali-toolkit/public-api/controls/gaussian-blur-view/gaussian-blur-view.h
dali-toolkit/public-api/controls/image-view/image-view.h
dali-toolkit/public-api/controls/scroll-bar/scroll-bar.h
dali-toolkit/public-api/controls/scrollable/item-view/default-item-layout.h
dali-toolkit/public-api/controls/scrollable/item-view/item-factory.h
dali-toolkit/public-api/controls/scrollable/item-view/item-layout.h
dali-toolkit/public-api/controls/scrollable/item-view/item-view-declarations.h
dali-toolkit/public-api/controls/scrollable/item-view/item-view.h
dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view-constraints.h
dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view-effect.h
dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view-page-path-effect.h
dali-toolkit/public-api/controls/scrollable/scroll-view/scroll-view.h
dali-toolkit/public-api/controls/scrollable/scrollable.h
dali-toolkit/public-api/controls/table-view/table-view.h
dali-toolkit/public-api/controls/text-controls/text-field.h
dali-toolkit/public-api/controls/text-controls/text-label.h
dali-toolkit/public-api/dali-toolkit-version.cpp
dali-toolkit/public-api/enums.h
dali-toolkit/public-api/focus-manager/keyboard-focus-manager.h
dali-toolkit/styles/480x800/dali-toolkit-default-theme.json
dali-toolkit/styles/720x1280/dali-toolkit-default-theme.json
doc/dali-toolkit-doc.h [new file with mode: 0644]
doc/file.list [new file with mode: 0644]
docs/content/shared-javascript-and-cpp-documentation/font-selection.md [new file with mode: 0644]
docs/content/shared-javascript-and-cpp-documentation/text-field.md
docs/content/shared-javascript-and-cpp-documentation/text-label.md
node-addon/dali-addon.cpp
packaging/dali-toolkit.spec

index d5baabb..cf3e163 100644 (file)
@@ -1324,8 +1324,11 @@ int UtcDaliToolkitScrollViewSetMaxOvershootP(void)
   currentPos = PerformGestureDiagonalSwipe(application, OVERSHOOT_START_SCROLL_POSITION, Vector2(1.0f, 1.0f), 105, false);
   overshootXValue = scrollView.GetProperty<float>(ScrollView::Property::OVERSHOOT_X);
   overshootYValue = scrollView.GetProperty<float>(ScrollView::Property::OVERSHOOT_Y);
-  DALI_TEST_CHECK(overshootXValue > 0.49f && overshootXValue < 0.51f);
-  DALI_TEST_CHECK(overshootYValue > 0.49f && overshootYValue < 0.51f);
+  // The overshoot value is a 0.0f - 1.0f ranged value of the amount overshot related to the maximum overshoot.
+  // EG. If we move 105, max overshoot is 50, then we overshot 50 / 105.
+  float correctOvershootValue = 50.0f / 105.f;
+  DALI_TEST_EQUALS( overshootXValue, correctOvershootValue, 0.001f, TEST_LOCATION );
+  DALI_TEST_EQUALS( overshootYValue, correctOvershootValue, 0.001f, TEST_LOCATION );
 
   // Scroll page further in NW (-30,-30 pixels), then check that overshoot should be now 1.0. (don't release touch)
   currentPos = PerformGestureDiagonalSwipe(application, OVERSHOOT_START_SCROLL_POSITION, Vector2(1.0f, 1.0f), 30, false);
@@ -1373,7 +1376,8 @@ int UtcDaliToolkitScrollViewSetScrollingDirectionP(void)
   Wait(application);
   // Try a vertical swipe.
   PerformGestureDiagonalSwipe(application, START_POSITION, Vector2(0.0f, 1.0f), 60, true);
-  DALI_TEST_EQUALS( scrollView.GetCurrentScrollPosition(), Vector2(10.0f, -50.0f), TEST_LOCATION );
+  // Take into account resampling done when prediction is off.
+  DALI_TEST_EQUALS( scrollView.GetCurrentScrollPosition() - Vector2(0.0f, 0.5f), Vector2(10.0f, -50.0f), 0.25f, TEST_LOCATION );
 
   scrollView.SetScrollingDirection(Dali::PanGestureDetector::DIRECTION_VERTICAL);
 
@@ -1389,7 +1393,7 @@ int UtcDaliToolkitScrollViewSetScrollingDirectionP(void)
   Wait(application);
   // Try a vertical swipe.
   PerformGestureDiagonalSwipe(application, START_POSITION, Vector2(0.0f, 1.0f), 60, true);
-  DALI_TEST_EQUALS( scrollView.GetCurrentScrollPosition(), Vector2(10.0f, -50.0f), TEST_LOCATION );
+  DALI_TEST_EQUALS( scrollView.GetCurrentScrollPosition() - Vector2(0.0f, 0.5f), Vector2(10.0f, -50.0f), 0.25f, TEST_LOCATION );
 
   END_TEST;
 }
@@ -1423,7 +1427,8 @@ int UtcDaliToolkitScrollViewRemoveScrollingDirectionP(void)
   Wait(application);
   // Try a vertical swipe.
   PerformGestureDiagonalSwipe(application, START_POSITION, Vector2(0.0f, 1.0f), 60, true);
-  DALI_TEST_EQUALS( scrollView.GetCurrentScrollPosition(), Vector2(10.0f, -50.0f), TEST_LOCATION );
+  // Take into account resampling done when prediction is off.
+  DALI_TEST_EQUALS( scrollView.GetCurrentScrollPosition() - Vector2(0.0f, 0.5f), Vector2(10.0f, -50.0f), 0.25f, TEST_LOCATION );
 
   END_TEST;
 }
index 9378eed..77c33f0 100644 (file)
@@ -179,6 +179,7 @@ Configuration
   Profile:                          $dali_profile
   Data Dir (Read/Write):            $dataReadWriteDir
   Data Dir (Read Only):             $dataReadOnlyDir
-  Style Dir                         $STYLE_DIR
-  Style                             $dali_style
+  Style Dir:                        $STYLE_DIR
+  Style:                            $dali_style
+  i18n:                             $enable_i18n
 "
index b5ba49a..bd24d22 100644 (file)
@@ -38,6 +38,9 @@ daliimage_DATA = ${dali_toolkit_image_files}
 dalisounddir = ${dataReadOnlyDir}/toolkit/sounds/
 dalisound_DATA = ${dali_toolkit_sound_files}
 
+package_doxy_dir = ../../../doc
+include ../../../doc/file.list
+
 # The library
 lib_LTLIBRARIES = libdali-toolkit.la
 
@@ -155,3 +158,6 @@ publicapitextcontrols_HEADERS =        $(public_api_text_controls_header_files)
 publicapifocusmanager_HEADERS =        $(public_api_focus_manager_header_files)
 publicapirenderingbackend_HEADERS =    $(public_api_rendering_backend_header_files)
 
+# package doxygen file (contains doxygen grouping information)
+packagedoxydir = $(topleveldir)/doc
+packagedoxy_HEADERS = $(package_doxy_files)
index 438d79d..3fa2e57 100644 (file)
@@ -758,9 +758,12 @@ WARN_LOGFILE           =
 # Note: If this tag is empty the current directory is searched.
 
 INPUT                  = @DOXYGEN_DOCS_DIR@/content \
+                         @prefix@/include/dali/doc/dali-core-doc.h \
+                         @prefix@/include/dali/doc/dali-adaptor-doc.h \
+                         ../../../../dali-toolkit/doc/dali-toolkit-doc.h \
+                         @prefix@/include/dali \
                          ../../../../dali-toolkit/dali-toolkit/public-api \
-                         ../../../automated-tests/README.md \
-                         @prefix@/include/dali
+                         ../../../automated-tests/README.md
 
 # This tag can be used to specify the character encoding of the source files
 # that doxygen parses. Internally doxygen uses the UTF-8 encoding. Doxygen uses
index b3a0028..19e2f1f 100644 (file)
@@ -58,6 +58,11 @@ void StyleManager::SetOrientation( Orientation orientation )
   GetImpl(*this).SetOrientation( orientation );
 }
 
+std::string StyleManager::GetDefaultFontFamily() const
+{
+  return GetImpl(*this).GetDefaultFontFamily();
+}
+
 Orientation StyleManager::GetOrientation()
 {
   return GetImpl(*this).GetOrientation();
index a568bba..a1596e1 100644 (file)
@@ -115,6 +115,12 @@ public:
   Orientation GetOrientation();
 
   /**
+   * @brief Retrieves the default font family.
+   * @return The default font family.
+   */
+  std::string GetDefaultFontFamily() const;
+
+  /**
    * @brief Make a request to set the theme JSON file to one that exists in the Toolkit package.
    *
    * Multiple requests per event processing cycle can be made, but only the final one will be acted
index 9a2289a..832e5d9 100644 (file)
@@ -132,11 +132,31 @@ Toolkit::AtlasManager::AtlasId AtlasManager::CreateAtlas( const Toolkit::AtlasMa
   atlasDescriptor.mHorizontalStrip = BufferImage::New( blockWidth, SINGLE_PIXEL_PADDING, pixelformat );
   atlasDescriptor.mVerticalStrip = BufferImage::New( SINGLE_PIXEL_PADDING, blockHeight - DOUBLE_PIXEL_PADDING, pixelformat );
 
-  memset( atlasDescriptor.mHorizontalStrip.GetBuffer(), 0, atlasDescriptor.mHorizontalStrip.GetBufferSize() );
-  memset( atlasDescriptor.mVerticalStrip.GetBuffer(), 0, atlasDescriptor.mVerticalStrip.GetBufferSize() );
+  PixelBuffer* buffer = atlasDescriptor.mHorizontalStrip.GetBuffer();
+  if( buffer == NULL )
+  {
+    DALI_LOG_ERROR("atlasDescriptor.mHorizontalStrip.GetBuffer() returns NULL\n");
+    return 0;
+  }
+  memset( buffer, 0, atlasDescriptor.mHorizontalStrip.GetBufferSize() );
+
+  buffer = atlasDescriptor.mVerticalStrip.GetBuffer();
+  if( buffer == NULL )
+  {
+    DALI_LOG_ERROR("atlasDescriptor.mVerticalStrip.GetBuffer() returns NULL\n");
+    return 0;
+  }
+  memset( buffer, 0, atlasDescriptor.mVerticalStrip.GetBufferSize() );
 
   BufferImage filledPixelImage = BufferImage::New( 1u, 1u, pixelformat );
-  memset( filledPixelImage.GetBuffer(), 0xFF, filledPixelImage.GetBufferSize() );
+  buffer = filledPixelImage.GetBuffer();
+  if( buffer == NULL)
+  {
+    DALI_LOG_ERROR("filledPixelImage.GetBuffer() returns NULL\n");
+    return 0;
+  }
+
+  memset( buffer, 0xFF, filledPixelImage.GetBufferSize() );
   atlas.Upload( filledPixelImage, 0, 0 );
 
   Sampler sampler = Sampler::New( atlas, "sTexture" );
index 07ca895..4ea4aee 100644 (file)
@@ -717,9 +717,13 @@ FrameBufferImage Builder::GetFrameBufferImage( const std::string &name, const Re
         if( SetPropertyFromNode( *image, Property::MAP, property, constant ) )
         {
           Property::Map* map = property.GetMap();
-          (*map)[ KEYNAME_TYPE ] = Property::Value(std::string("FrameBufferImage") );
-          ret = FrameBufferImage::DownCast( Dali::Scripting::NewImage( property ) );
-          mFrameBufferImageLut[ name ] = ret;
+
+          if( map )
+          {
+            (*map)[ KEYNAME_TYPE ] = Property::Value(std::string("FrameBufferImage") );
+            ret = FrameBufferImage::DownCast( Dali::Scripting::NewImage( property ) );
+            mFrameBufferImageLut[ name ] = ret;
+          }
         }
       }
     }
index 12f602c..c78e19c 100644 (file)
@@ -343,24 +343,29 @@ bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::V
       {
         value = Property::Value(Property::ARRAY);
         Property::Array* array = value.GetArray();
+
         unsigned int i = 0;
         TreeNode::ConstIterator iter(node.CBegin());
-        for( ; i < node.Size(); ++i, ++iter)
+
+        if( array )
         {
-          Property::Value childValue;
-          if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+          for( ; i < node.Size(); ++i, ++iter)
           {
-            array->PushBack( childValue );
+            Property::Value childValue;
+            if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+            {
+              array->PushBack( childValue );
+            }
           }
-        }
 
-        if( array->Count() == node.Size() )
-        {
-          done = true;
-        }
-        else
-        {
-          done = false;
+          if( array->Count() == node.Size() )
+          {
+            done = true;
+          }
+          else
+          {
+            done = false;
+          }
         }
       }
       break;
@@ -375,24 +380,29 @@ bool SetPropertyFromNode( const TreeNode& node, Property::Type type, Property::V
       {
         value = Property::Value(Property::MAP);
         Property::Map* map = value.GetMap();
+
         unsigned int i = 0;
         TreeNode::ConstIterator iter(node.CBegin());
-        for( ; i < node.Size(); ++i, ++iter)
+
+        if( map )
         {
-          Property::Value childValue;
-          if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+          for( ; i < node.Size(); ++i, ++iter)
           {
-            map->Insert( (*iter).first, childValue );
+            Property::Value childValue;
+            if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+            {
+              map->Insert( (*iter).first, childValue );
+            }
           }
-        }
 
-        if( map->Count() == node.Size() )
-        {
-          done = true;
-        }
-        else
-        {
-          done = false;
+          if( map->Count() == node.Size() )
+          {
+            done = true;
+          }
+          else
+          {
+            done = false;
+          }
         }
       }
       break;
@@ -483,13 +493,16 @@ bool SetPropertyFromNode( const TreeNode& node, Property::Value& value,
           value = Property::Value(Property::ARRAY);
           Property::Array* array = value.GetArray();
 
-          for(TreeConstIter iter = node.CBegin(); iter != node.CEnd(); ++iter)
+          if( array )
           {
-            Property::Value childValue;
-            if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+            for(TreeConstIter iter = node.CBegin(); iter != node.CEnd(); ++iter)
             {
-              array->PushBack( childValue );
-              done = true;
+              Property::Value childValue;
+              if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+              {
+                array->PushBack( childValue );
+                done = true;
+              }
             }
           }
         }
@@ -507,13 +520,17 @@ bool SetPropertyFromNode( const TreeNode& node, Property::Value& value,
         {
           value = Property::Value(Property::ARRAY);
           Property::Array* array = value.GetArray();
-          for(unsigned int i = 0; i < node.Size(); ++i, ++iter)
+
+          if( array )
           {
-            Property::Value childValue;
-            if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+            for(unsigned int i = 0; i < node.Size(); ++i, ++iter)
             {
-              array->PushBack( childValue );
-              done = true;
+              Property::Value childValue;
+              if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+              {
+                array->PushBack( childValue );
+                done = true;
+              }
             }
           }
         }
@@ -521,13 +538,17 @@ bool SetPropertyFromNode( const TreeNode& node, Property::Value& value,
         {
           value = Property::Value(Property::MAP);
           Property::Map* map = value.GetMap();
-          for(unsigned int i = 0; i < node.Size(); ++i, ++iter)
+
+          if( map )
           {
-            Property::Value childValue;
-            if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+            for(unsigned int i = 0; i < node.Size(); ++i, ++iter)
             {
-              map->Insert( (*iter).first, childValue );
-              done = true;
+              Property::Value childValue;
+              if( SetPropertyFromNode( (*iter).second, childValue, replacer ) )
+              {
+                map->Insert( (*iter).first, childValue );
+                done = true;
+              }
             }
           }
         }
index 50df6af..0b3a186 100644 (file)
@@ -36,7 +36,8 @@ namespace Internal
 BubbleActor::BubbleActor( unsigned int numberOfBubble,
                           const Vector2& movementArea)
 : mMovementArea( movementArea ),
-  mNumBubble( numberOfBubble )
+  mNumBubble( numberOfBubble ),
+  mRandomSeed( 0 )
 {
   mActor = Actor::New();
 }
@@ -61,18 +62,20 @@ void BubbleActor::MakeRenderable( Geometry geometry, Material material  )
 
   mIndexInvertedMovementArea = mActor.RegisterProperty( "uInvertedMovementArea", Vector2(1.f,1.f) / mMovementArea );
 
-  srand(time(NULL));
   mIndicesOffset.resize(9);
   int offset = mMovementArea.Length() / 10.f;
-  mIndicesOffset[0] = mActor.RegisterProperty( "uOffset[0]", Vector2(0.f,0.f));
-  mIndicesOffset[1] = mActor.RegisterProperty( "uOffset[1]", Vector2(rand()%offset,rand()%offset) );
-  mIndicesOffset[2] = mActor.RegisterProperty( "uOffset[2]", Vector2(rand()%offset,-rand()%offset) );
-  mIndicesOffset[3] = mActor.RegisterProperty( "uOffset[3]", Vector2(-rand()%offset,rand()%offset) );
-  mIndicesOffset[4] = mActor.RegisterProperty( "uOffset[4]", Vector2(-rand()%offset,-rand()%offset) );
-  mIndicesOffset[5] = mActor.RegisterProperty( "uOffset[5]", Vector2(rand()%offset,0.f));
-  mIndicesOffset[6] = mActor.RegisterProperty( "uOffset[6]", Vector2(-rand()%offset,0.f));
-  mIndicesOffset[7] = mActor.RegisterProperty( "uOffset[7]", Vector2(0.f,rand()%offset));
-  mIndicesOffset[8] = mActor.RegisterProperty( "uOffset[8]", Vector2(0.f,-rand()%offset));
+
+  mRandomSeed = time( NULL );
+
+  mIndicesOffset[0] = mActor.RegisterProperty( "uOffset[0]", Vector2( 0.f,0.f ) );
+  mIndicesOffset[1] = mActor.RegisterProperty( "uOffset[1]", Vector2( rand_r( &mRandomSeed ) % offset,  rand_r( &mRandomSeed ) % offset ) );
+  mIndicesOffset[2] = mActor.RegisterProperty( "uOffset[2]", Vector2( rand_r( &mRandomSeed ) % offset, -rand_r( &mRandomSeed ) % offset ) );
+  mIndicesOffset[3] = mActor.RegisterProperty( "uOffset[3]", Vector2(-rand_r( &mRandomSeed ) % offset,  rand_r( &mRandomSeed ) % offset ) );
+  mIndicesOffset[4] = mActor.RegisterProperty( "uOffset[4]", Vector2(-rand_r( &mRandomSeed ) % offset, -rand_r( &mRandomSeed ) % offset ) );
+  mIndicesOffset[5] = mActor.RegisterProperty( "uOffset[5]", Vector2( rand_r( &mRandomSeed ) % offset, 0.f ) );
+  mIndicesOffset[6] = mActor.RegisterProperty( "uOffset[6]", Vector2(-rand_r( &mRandomSeed ) % offset, 0.f ) );
+  mIndicesOffset[7] = mActor.RegisterProperty( "uOffset[7]", Vector2( 0.f,  rand_r( &mRandomSeed ) % offset ) );
+  mIndicesOffset[8] = mActor.RegisterProperty( "uOffset[8]", Vector2( 0.f, -rand_r( &mRandomSeed ) % offset ) );
 
   Vector4 zeroVector;
   mIndiceStartEndPos.resize( mNumBubble );
@@ -111,14 +114,15 @@ void BubbleActor::SetMovementArea( const Vector2& movementArea )
   mActor.SetProperty( mIndexInvertedMovementArea, Vector2(1.f,1.f) / mMovementArea );
 
   int offset = mMovementArea.Length() / 10.f;
-  mActor.SetProperty( mIndicesOffset[1], Vector2(rand()%offset,rand()%offset) );
-  mActor.SetProperty( mIndicesOffset[2], Vector2(rand()%offset,-rand()%offset) );
-  mActor.SetProperty( mIndicesOffset[3], Vector2(-rand()%offset,rand()%offset) );
-  mActor.SetProperty( mIndicesOffset[4], Vector2(-rand()%offset,-rand()%offset) );
-  mActor.SetProperty( mIndicesOffset[5], Vector2(rand()%offset,0.f));
-  mActor.SetProperty( mIndicesOffset[6], Vector2(-rand()%offset,0.f));
-  mActor.SetProperty( mIndicesOffset[7], Vector2(0.f,rand()%offset));
-  mActor.SetProperty( mIndicesOffset[8], Vector2(0.f,-rand()%offset));
+
+  mActor.SetProperty( mIndicesOffset[1], Vector2( rand_r( &mRandomSeed ) % offset,  rand_r( &mRandomSeed ) % offset ) );
+  mActor.SetProperty( mIndicesOffset[2], Vector2( rand_r( &mRandomSeed ) % offset, -rand_r( &mRandomSeed ) % offset ) );
+  mActor.SetProperty( mIndicesOffset[3], Vector2(-rand_r( &mRandomSeed ) % offset,  rand_r( &mRandomSeed ) % offset ) );
+  mActor.SetProperty( mIndicesOffset[4], Vector2(-rand_r( &mRandomSeed ) % offset, -rand_r( &mRandomSeed ) % offset ) );
+  mActor.SetProperty( mIndicesOffset[5], Vector2( rand_r( &mRandomSeed ) % offset, 0.f ) );
+  mActor.SetProperty( mIndicesOffset[6], Vector2(-rand_r( &mRandomSeed ) % offset, 0.f ) );
+  mActor.SetProperty( mIndicesOffset[7], Vector2( 0.f,  rand_r( &mRandomSeed ) % offset ) );
+  mActor.SetProperty( mIndicesOffset[8], Vector2( 0.f, -rand_r( &mRandomSeed ) % offset ) );
 }
 
 void BubbleActor::SetStartAndEndPosition( unsigned int index, const Vector4& startAndEndPosition )
index a0938f0..357cddf 100644 (file)
@@ -139,6 +139,7 @@ private:
   Property::Index              mIndexInvertedMovementArea; ///< Index of the property mapping to uniform 'uInvertedMovementArea'
 
   unsigned int mNumBubble;  ///< How many groups of uniforms are used to control the bubble movement.
+  unsigned int mRandomSeed; ///< Seed to generate random number.
 };
 
 } // namespace Internal
index a9b9aa9..9fed7cc 100644 (file)
@@ -48,11 +48,12 @@ struct Vertex
  * Return a random value between the given interval.
  * @param[in] f0 The low bound
  * @param[in] f1 The up bound
+ * @param[in] seed The seed to genergate random number
  * @return A random value between the given interval
  */
-float RandomRange(float f0, float f1)
+float RandomRange(float f0, float f1, unsigned int& seed)
 {
-  return f0 + (rand() & 0xfff) * (f1-f0) * (1.0f/4095.0f);
+  return f0 + (rand_r( &seed ) & 0xfff) * (f1-f0) * (1.0f/4095.0f);
 }
 
 }
@@ -76,6 +77,7 @@ BubbleEmitter::BubbleEmitter( const Vector2& movementArea,
   mDensity( 5 ),
   mTotalNumOfBubble( maximumNumberOfBubble ),
   mCurrentBubble( 0 ),
+  mRandomSeed( 0 ),
   mRenderTaskRunning(false)
 {
   // Calculate how many shaders are required
@@ -95,6 +97,8 @@ BubbleEmitter::BubbleEmitter( const Vector2& movementArea,
     mNumBubblePerActor = mTotalNumOfBubble;
     mNumActor = 1;
   }
+
+  mRandomSeed = time( NULL );
 }
 
 BubbleEmitter::~BubbleEmitter()
@@ -297,7 +301,7 @@ Geometry BubbleEmitter::CreateGeometry( unsigned int numOfPatch )
 
   for(unsigned int i = 0; i < numOfPatch; i++)
   {
-    float curSize = RandomRange(mBubbleSizeRange.x, mBubbleSizeRange.y);
+    float curSize = RandomRange(mBubbleSizeRange.x, mBubbleSizeRange.y, mRandomSeed);
 
     float index = static_cast<float>( i );
     vertexData.push_back( Vertex( index, Vector2(0.f,0.f),         Vector2(0.f,0.f) ) );
@@ -340,7 +344,7 @@ void BubbleEmitter::SetBubbleParameter( BubbleActorPtr bubbleActor, unsigned int
 
   int halfRange = displacement.x / 2;
   // for the y coordinate, always negative, so bubbles always go upwards
-  Vector2 randomVec(rand()%static_cast<int>(displacement.x) - halfRange, -rand()%static_cast<int>(displacement.y));
+  Vector2 randomVec( rand_r( &mRandomSeed ) % static_cast<int>(displacement.x) - halfRange, -rand_r( &mRandomSeed ) % static_cast<int>(displacement.y) );
   dir.Normalize();
   randomVec.x -= dir.x*halfRange;
   randomVec.y *= 1.0f - fabsf(dir.x)*0.33f;
index 91158b2..40b4b74 100644 (file)
@@ -178,6 +178,7 @@ private:
   unsigned int                mDensity;             ///< How many bubbles will emit at each time, they are controlled by same uniforms in the shader.
   unsigned int                mTotalNumOfBubble;    ///< mNumBubblePerShader*mNumShader.
   unsigned int                mCurrentBubble;       ///< Keep track of the index for the newly emitted bubble
+  unsigned int                mRandomSeed;          ///< Seed to generate random number.
 
   bool                        mRenderTaskRunning;   ///< If the background render task is currently running
 
index 74450ae..d2b699b 100755 (executable)
@@ -664,11 +664,15 @@ Property::Value ScrollBar::GetProperty( BaseObject* object, Property::Index inde
       {
         Property::Value value( Property::ARRAY );
         Property::Array* array = value.GetArray();
-        Dali::Vector<float> positions = scrollBarImpl.GetScrollPositionIntervals();
-        size_t positionCount( array->Count() );
-        for( size_t i( 0 ); i != positionCount; ++i )
+
+        if( array )
         {
-          array->PushBack( positions[i] );
+          Dali::Vector<float> positions = scrollBarImpl.GetScrollPositionIntervals();
+          size_t positionCount( array->Count() );
+          for( size_t i( 0 ); i != positionCount; ++i )
+          {
+            array->PushBack( positions[i] );
+          }
         }
         break;
       }
index 82ce8fc..6ce8c73 100644 (file)
@@ -214,6 +214,14 @@ protected:
 
 private:
 
+  // Undefined
+  DepthLayout( const DepthLayout& depthLayout );
+
+  // Undefined
+  DepthLayout& operator=( const DepthLayout& depthLayout );
+
+private:
+
   struct Impl;
   Impl* mImpl;
 };
index 8cbdd33..7476822 100644 (file)
@@ -257,6 +257,14 @@ protected:
 
 private:
 
+  // Undefined
+  GridLayout( const GridLayout& itemLayout );
+
+  // Undefined
+  GridLayout& operator=( const GridLayout& rhs );
+
+private:
+
   struct Impl;
   Impl* mImpl;
 };
index 00f550a..1a3e30c 100644 (file)
@@ -187,6 +187,14 @@ protected:
 
 private:
 
+  // Undefined
+  SpiralLayout( const SpiralLayout& spiralLayout );
+
+  // Undefined
+  SpiralLayout& operator=( const SpiralLayout& spiralLayout );
+
+private:
+
   struct Impl;
   Impl* mImpl;
 };
index 592fefc..0420830 100644 (file)
@@ -112,18 +112,6 @@ void ScrollOvershootIndicator::SetOvershootEffectColor( const Vector4& color )
   }
 }
 
-void ScrollOvershootIndicator::ClearOvershoot()
-{
-  if(mEffectX)
-  {
-    mEffectX->SetOvershoot(0.0f);
-  }
-  if(mEffectY)
-  {
-    mEffectY->SetOvershoot(0.0f);
-  }
-}
-
 ScrollOvershootEffect::ScrollOvershootEffect( bool vertical ) :
     mVertical(vertical)
 {
index f19e39c..7eebe4b 100644 (file)
@@ -76,11 +76,6 @@ public:
   void Reset();
 
   /**
-   * Clears the overshoot
-   */
-  void ClearOvershoot();
-
-  /**
    * Create an initialized ScrollOvershootIndicator
    *
    * @return A pointer to the created ScrollOvershootIndicator.
index 86e9173..a8bd61e 100644 (file)
@@ -2439,11 +2439,6 @@ void ScrollView::OnPan( const PanGesture& gesture )
         {
           mScrollMainInternalPrePositionConstraint.Remove();
         }
-
-        if( mOvershootIndicator )
-        {
-          mOvershootIndicator->ClearOvershoot();
-        }
       }
       else
       {
index f12b873..89268b3 100644 (file)
@@ -51,9 +51,13 @@ ScrollViewPagePathEffect::ScrollViewPagePathEffect(Path path, const Vector3& for
   //Create linear constrainer
   pointsProperty = Property::Value(Property::ARRAY);
   Property::Array* array = pointsProperty.GetArray();
-  array->PushBack(0.0f);
-  array->PushBack(1.0f);
-  array->PushBack(0.0f);
+
+  if( array )
+  {
+    array->PushBack(0.0f);
+    array->PushBack(1.0f);
+    array->PushBack(0.0f);
+  }
   mLinearConstrainer = Dali::LinearConstrainer::New();
   mLinearConstrainer.SetProperty( LinearConstrainer::Property::VALUE, pointsProperty );
 }
index d633e9b..9c3d4c8 100644 (file)
 #include <dali-toolkit/internal/controls/text-controls/text-field-impl.h>
 
 // EXTERNAL INCLUDES
-#include <string>
-#include <iostream>
 #include <cstring>
 #include <dali/public-api/adaptor-framework/key.h>
 #include <dali/public-api/common/stage.h>
 #include <dali/public-api/images/resource-image.h>
-#include <dali/public-api/object/type-registry.h>
-#include <dali/devel-api/object/type-registry-helper.h>
-#include <dali/devel-api/scripting/scripting.h>
 #include <dali/devel-api/adaptor-framework/virtual-keyboard.h>
+#include <dali/devel-api/object/type-registry-helper.h>
 #include <dali/integration-api/debug.h>
 
 // INTERNAL INCLUDES
 #include <dali-toolkit/public-api/text/rendering-backend.h>
-#include <dali-toolkit/internal/text/layouts/layout-engine.h>
+#include <dali-toolkit/internal/controls/text-controls/text-font-style.h>
 #include <dali-toolkit/internal/text/rendering/text-backend.h>
 #include <dali-toolkit/internal/text/text-view.h>
 #include <dali-toolkit/internal/styling/style-manager-impl.h>
@@ -57,7 +53,6 @@ namespace // unnamed namespace
 #endif
 
   const unsigned int DEFAULT_RENDERING_BACKEND = Dali::Toolkit::Text::DEFAULT_RENDERING_BACKEND;
-
 } // unnamed namespace
 
 namespace
@@ -149,6 +144,9 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
 {
   Toolkit::TextField textField = Toolkit::TextField::DownCast( Dali::BaseHandle( object ) );
 
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextField SetProperty\n");
+
+
   if( textField )
   {
     TextField& impl( GetImpl( textField ) );
@@ -210,23 +208,14 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
 
           if( impl.mController->GetDefaultFontFamily() != fontFamily )
           {
-            impl.mController->SetDefaultFontFamily( fontFamily );
+            impl.mController->SetDefaultFontFamily( fontFamily, true ); // "true" as SetProperty means user defined font so don't change when system font changes.
           }
         }
         break;
       }
       case Toolkit::TextField::Property::FONT_STYLE:
       {
-        if( impl.mController )
-        {
-          const std::string fontStyle = value.Get< std::string >();
-          DALI_LOG_INFO( gLogFilter, Debug::General, "TextField %p FONT_STYLE %s\n", impl.mController.Get(), fontStyle.c_str() );
-
-          if( impl.mController->GetDefaultFontStyle() != fontStyle )
-          {
-            impl.mController->SetDefaultFontStyle( fontStyle );
-          }
-        }
+        SetFontStyleProperty( impl.mController, value );
         break;
       }
       case Toolkit::TextField::Property::POINT_SIZE:
@@ -234,7 +223,7 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
         if( impl.mController )
         {
           const float pointSize = value.Get< float >();
-          DALI_LOG_INFO( gLogFilter, Debug::General, "TextField %p FONT_STYLE %f\n", impl.mController.Get(), pointSize );
+          DALI_LOG_INFO( gLogFilter, Debug::General, "TextField %p POINT_SIZE %f\n", impl.mController.Get(), pointSize );
 
           if( !Equals( impl.mController->GetDefaultPointSize(), pointSize ) )
           {
@@ -475,7 +464,7 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
       {
         const Image image = Scripting::NewImage( value );
 
-        if( impl.mDecorator )
+        if( impl.mDecorator && image )
         {
           impl.mDecorator->SetHandleImage( LEFT_SELECTION_HANDLE, HANDLE_IMAGE_RELEASED, image );
           impl.RequestTextRelayout();
@@ -486,7 +475,7 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
       {
         const Image image = Scripting::NewImage( value );
 
-        if( impl.mDecorator )
+        if( impl.mDecorator && image )
         {
           impl.mDecorator->SetHandleImage( RIGHT_SELECTION_HANDLE, HANDLE_IMAGE_RELEASED, image );
           impl.RequestTextRelayout();
@@ -497,7 +486,7 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
       {
         const Image image = Scripting::NewImage( value );
 
-        if( impl.mDecorator )
+        if( impl.mDecorator && image )
         {
           impl.mDecorator->SetHandleImage( LEFT_SELECTION_HANDLE, HANDLE_IMAGE_PRESSED, image );
           impl.RequestTextRelayout();
@@ -508,7 +497,7 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
       {
         const Image image = Scripting::NewImage( value );
 
-        if( impl.mDecorator )
+        if( impl.mDecorator && image )
         {
           impl.mDecorator->SetHandleImage( RIGHT_SELECTION_HANDLE, HANDLE_IMAGE_PRESSED, image );
           impl.RequestTextRelayout();
@@ -518,7 +507,8 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
       case Toolkit::TextField::Property::SELECTION_HANDLE_MARKER_IMAGE_LEFT:
       {
         const Image image = Scripting::NewImage( value );
-        if( impl.mDecorator )
+
+        if( impl.mDecorator && image )
         {
           impl.mDecorator->SetHandleImage( LEFT_SELECTION_HANDLE_MARKER, HANDLE_IMAGE_RELEASED, image );
           impl.RequestTextRelayout();
@@ -528,7 +518,8 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
       case Toolkit::TextField::Property::SELECTION_HANDLE_MARKER_IMAGE_RIGHT:
       {
         const Image image = Scripting::NewImage( value );
-        if( impl.mDecorator )
+
+        if( impl.mDecorator && image )
         {
           impl.mDecorator->SetHandleImage( RIGHT_SELECTION_HANDLE_MARKER, HANDLE_IMAGE_RELEASED, image );
           impl.RequestTextRelayout();
@@ -627,10 +618,7 @@ Property::Value TextField::GetProperty( BaseObject* object, Property::Index inde
       }
       case Toolkit::TextField::Property::FONT_STYLE:
       {
-        if( impl.mController )
-        {
-          value = impl.mController->GetDefaultFontStyle();
-        }
+        GetFontStyleProperty( impl.mController, value );
         break;
       }
       case Toolkit::TextField::Property::POINT_SIZE:
@@ -841,7 +829,9 @@ Property::Value TextField::GetProperty( BaseObject* object, Property::Index inde
       {
         if( impl.mDecorator )
         {
-          value = impl.mDecorator->GetBoundingBox();
+          Rect<int> boundingBox;
+          impl.mDecorator->GetBoundingBox( boundingBox );
+          value = boundingBox;
         }
         break;
       }
@@ -909,7 +899,10 @@ void TextField::OnInitialize()
   self.TouchedSignal().Connect( this, &TextField::OnTouched );
 
   // Set BoundingBox to stage size if not already set.
-  if ( mDecorator->GetBoundingBox().IsEmpty() )
+  Rect<int> boundingBox;
+  mDecorator->GetBoundingBox( boundingBox );
+
+  if( boundingBox.IsEmpty() )
   {
     Vector2 stageSize = Dali::Stage::GetCurrent().GetSize();
     mDecorator->SetBoundingBox( Rect<int>( 0.0f, 0.0f, stageSize.width, stageSize.height ) );
@@ -929,12 +922,10 @@ void TextField::OnStyleChange( Toolkit::StyleManager styleManager, StyleChange::
    {
      case StyleChange::DEFAULT_FONT_CHANGE:
      {
-       DALI_LOG_INFO( gLogFilter, Debug::General, "TextField::OnStyleChange StyleChange::DEFAULT_FONT_CHANGE\n");
-       if ( mController->GetDefaultFontFamily() == "" )
-       {
-         // Property system did not set the font so should update it.
-         // todo instruct text-controller to update model
-       }
+       DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextField::OnStyleChange DEFAULT_FONT_CHANGE\n");
+       std::string newFont = styleManager.GetDefaultFontFamily();
+       // Property system did not set the font so should update it.
+       mController->UpdateAfterFontChange( newFont );
        break;
      }
 
@@ -969,6 +960,8 @@ float TextField::GetHeightForWidth( float width )
 
 void TextField::OnRelayout( const Vector2& size, RelayoutContainer& container )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextField OnRelayout\n");
+
   if( mController->Relayout( size ) ||
       !mRenderer )
   {
@@ -1130,7 +1123,15 @@ void TextField::OnPan( const PanGesture& gesture )
 
 void TextField::OnLongPress( const LongPressGesture& gesture )
 {
+  // Show the keyboard if it was hidden.
+  if (!VirtualKeyboard::IsVisible())
+  {
+    VirtualKeyboard::Show();
+  }
+
   mController->LongPressEvent( gesture.state, gesture.localPoint.x, gesture.localPoint.y );
+
+  SetKeyInputFocus();
 }
 
 bool TextField::OnKeyEvent( const KeyEvent& event )
diff --git a/dali-toolkit/internal/controls/text-controls/text-font-style.cpp b/dali-toolkit/internal/controls/text-controls/text-font-style.cpp
new file mode 100644 (file)
index 0000000..2c29f68
--- /dev/null
@@ -0,0 +1,202 @@
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+// FILE HEADER
+#include <dali-toolkit/internal/controls/text-controls/text-font-style.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/devel-api/builder/json-parser.h>
+#include <dali-toolkit/devel-api/builder/tree-node.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+namespace
+{
+const std::string STYLE_KEY( "style" );
+const std::string WIDTH_KEY( "width" );
+const std::string WEIGHT_KEY( "weight" );
+const std::string SLANT_KEY( "slant" );
+const std::string EMPTY_STRING( "" );
+
+} // namespace
+
+/**
+ * @brief Creates a map with pairs 'key,value' with the font's style parameters.
+ *
+ * @param[in] node Data structure with the font's style parameters.
+ * @param[out] map A map with the font's style parameters.
+ *
+ */
+void CreateFontStyleMap( const TreeNode* const node, Property::Map& map )
+{
+  switch( node->GetType() )
+  {
+    case TreeNode::IS_NULL:
+    case TreeNode::OBJECT:
+    case TreeNode::ARRAY: // FALL THROUGH
+    {
+      break;
+    }
+    case TreeNode::STRING:
+    {
+      map.Insert( node->GetName(), Property::Value( node->GetString() ) );
+      break;
+    }
+    case TreeNode::INTEGER:
+    case TreeNode::FLOAT:
+    case TreeNode::BOOLEAN: // FALL THROUGH
+    {
+      break;
+    }
+  }
+
+  for( TreeNode::ConstIterator it = node->CBegin(), endIt = node->CEnd(); it != endIt; ++it )
+  {
+    const TreeNode::KeyNodePair& pair = *it;
+    CreateFontStyleMap( &pair.second, map );
+  }
+}
+
+/**
+ * @brief Parses the font's style string.
+ *
+ * @param[in] style The font's style string.
+ * @param[out] map A map with the font's style parameters.
+ *
+ */
+void ParseFontStyleString( const std::string& style, Property::Map& map )
+{
+  Toolkit::JsonParser parser = Toolkit::JsonParser::New();
+
+  if( parser.Parse( style ) )
+  {
+    const TreeNode* const node = parser.GetRoot();
+
+    CreateFontStyleMap( node, map );
+  }
+}
+
+void SetFontStyleProperty( ControllerPtr controller, const Property::Value& value )
+{
+  if( controller )
+  {
+    const std::string style = value.Get< std::string >();
+
+    // Stores the string to be recovered by the GetFontStyleProperty() function.
+    controller->SetDefaultFontStyle( style );
+
+    // Parses and applies the style.
+    Property::Map map;
+    ParseFontStyleString( style, map );
+
+    if( !map.Empty() )
+    {
+      /// Width key
+      Property::Value* widthValue = map.Find( WIDTH_KEY );
+
+      if( widthValue )
+      {
+        const std::string widthStr = widthValue->Get<std::string>();
+
+        FontWidth width = TextAbstraction::FontWidth::NORMAL;
+        if( Scripting::GetEnumeration< FontWidth >( widthStr.c_str(),
+                                                    FONT_WIDTH_STRING_TABLE,
+                                                    FONT_WIDTH_STRING_TABLE_COUNT,
+                                                    width ) )
+        {
+          if( controller->GetDefaultFontWidth() != width )
+          {
+            controller->SetDefaultFontWidth( width );
+          }
+        }
+      }
+      else
+      {
+        controller->SetDefaultFontWidth( TextAbstraction::FontWidth::NORMAL );
+      }
+
+      /// Weight key
+      Property::Value* weightValue = map.Find( WEIGHT_KEY );
+
+      if( weightValue )
+      {
+        const std::string weightStr = weightValue->Get<std::string>();
+
+        FontWeight weight = TextAbstraction::FontWeight::NORMAL;
+        if( Scripting::GetEnumeration< FontWeight >( weightStr.c_str(),
+                                                     FONT_WEIGHT_STRING_TABLE,
+                                                     FONT_WEIGHT_STRING_TABLE_COUNT,
+                                                     weight ) )
+        {
+          if( controller->GetDefaultFontWeight() != weight )
+          {
+            controller->SetDefaultFontWeight( weight );
+          }
+        }
+      }
+      else
+      {
+        controller->SetDefaultFontWeight( TextAbstraction::FontWeight::NORMAL );
+      }
+
+      /// Slant key
+      Property::Value* slantValue = map.Find( SLANT_KEY );
+
+      if( slantValue )
+      {
+        const std::string slantStr = slantValue->Get<std::string>();
+
+        FontSlant slant = TextAbstraction::FontSlant::NORMAL;
+        if( Scripting::GetEnumeration< FontSlant >( slantStr.c_str(),
+                                                    FONT_SLANT_STRING_TABLE,
+                                                    FONT_SLANT_STRING_TABLE_COUNT,
+                                                    slant ) )
+        {
+          if( controller->GetDefaultFontSlant() != slant )
+          {
+            controller->SetDefaultFontSlant( slant );
+          }
+        }
+      }
+      else
+      {
+        controller->SetDefaultFontSlant( TextAbstraction::FontSlant::NORMAL );
+      }
+    }
+  }
+}
+
+void GetFontStyleProperty( ControllerPtr controller, Property::Value& value )
+{
+  if( controller )
+  {
+    value = controller->GetDefaultFontStyle();
+  }
+}
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
diff --git a/dali-toolkit/internal/controls/text-controls/text-font-style.h b/dali-toolkit/internal/controls/text-controls/text-font-style.h
new file mode 100644 (file)
index 0000000..35696af
--- /dev/null
@@ -0,0 +1,106 @@
+#ifndef __DALI_TOOLKIT_INTERNAL_TEXT_FONT_STYLE_H__
+#define __DALI_TOOLKIT_INTERNAL_TEXT_FONT_STYLE_H__
+
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+// EXTERNAL INCLUDES
+#include <dali/devel-api/scripting/scripting.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/text-controller.h>
+#include <dali-toolkit/internal/text/text-definitions.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+const Scripting::StringEnum FONT_WIDTH_STRING_TABLE[] =
+{
+  { "ultra-condensed", TextAbstraction::FontWidth::ULTRA_CONDENSED },
+  { "extra-condensed", TextAbstraction::FontWidth::EXTRA_CONDENSED },
+  { "condensed", TextAbstraction::FontWidth::CONDENSED },
+  { "semi-condensed", TextAbstraction::FontWidth::SEMI_CONDENSED },
+  { "normal", TextAbstraction::FontWidth::NORMAL },
+  { "semi-expanded", TextAbstraction::FontWidth::SEMI_EXPANDED },
+  { "expanded", TextAbstraction::FontWidth::EXPANDED },
+  { "extra-expanded", TextAbstraction::FontWidth::EXTRA_EXPANDED },
+  { "ultra-expanded", TextAbstraction::FontWidth::ULTRA_EXPANDED },
+};
+const unsigned int FONT_WIDTH_STRING_TABLE_COUNT = sizeof( FONT_WIDTH_STRING_TABLE ) / sizeof( FONT_WIDTH_STRING_TABLE[0] );
+
+const Scripting::StringEnum FONT_WEIGHT_STRING_TABLE[] =
+{
+  { "thin", TextAbstraction::FontWeight::THIN },
+  { "ultra-light", TextAbstraction::FontWeight::ULTRA_LIGHT },
+  { "extra-light", TextAbstraction::FontWeight::EXTRA_LIGHT },
+  { "light", TextAbstraction::FontWeight::LIGHT },
+  { "demi-light", TextAbstraction::FontWeight::DEMI_LIGHT },
+  { "semi-light", TextAbstraction::FontWeight::SEMI_LIGHT },
+  { "book", TextAbstraction::FontWeight::BOOK },
+  { "normal", TextAbstraction::FontWeight::NORMAL },
+  { "regular", TextAbstraction::FontWeight::REGULAR },
+  { "medium", TextAbstraction::FontWeight::MEDIUM },
+  { "demi-bold", TextAbstraction::FontWeight::DEMI_BOLD },
+  { "semi-bold", TextAbstraction::FontWeight::SEMI_BOLD },
+  { "bold", TextAbstraction::FontWeight::BOLD },
+  { "ultra-bold", TextAbstraction::FontWeight::ULTRA_BOLD },
+  { "extra-bold", TextAbstraction::FontWeight::EXTRA_BOLD },
+  { "black", TextAbstraction::FontWeight::BLACK },
+  { "heavy", TextAbstraction::FontWeight::HEAVY },
+  { "extra-black", TextAbstraction::FontWeight::EXTRA_BLACK }
+};
+const unsigned int FONT_WEIGHT_STRING_TABLE_COUNT = sizeof( FONT_WEIGHT_STRING_TABLE ) / sizeof( FONT_WEIGHT_STRING_TABLE[0] );
+
+const Scripting::StringEnum FONT_SLANT_STRING_TABLE[] =
+{
+  { "normal", TextAbstraction::FontSlant::NORMAL },
+  { "roman", TextAbstraction::FontSlant::ROMAN },
+  { "italic", TextAbstraction::FontSlant::ITALIC },
+  { "oblique", TextAbstraction::FontSlant::OBLIQUE }
+};
+const unsigned int FONT_SLANT_STRING_TABLE_COUNT = sizeof( FONT_SLANT_STRING_TABLE ) / sizeof( FONT_SLANT_STRING_TABLE[0] );
+
+/**
+ * @brief Sets the font's style property.
+ *
+ * @param[in] controller The text's controller.
+ * @param[in] value The value of the font's style.
+ *
+ */
+void SetFontStyleProperty( ControllerPtr controller, const Property::Value& value );
+
+/**
+ * @brief Retrieves the font's style property.
+ *
+ * @param[in] controller The text's controller.
+ * @param[out] value The value of the font's style.
+ */
+void GetFontStyleProperty( ControllerPtr controller, Property::Value& value );
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_INTERNAL_TEXT_FONT_STYLE_H__
index 81a5c97..1c31449 100644 (file)
 #include <dali-toolkit/internal/controls/text-controls/text-label-impl.h>
 
 // EXTERNAL INCLUDES
-#include <dali/public-api/object/type-registry.h>
 #include <dali/devel-api/object/type-registry-helper.h>
-#include <dali/devel-api/scripting/scripting.h>
 #include <dali/integration-api/debug.h>
 
 // INTERNAL INCLUDES
 #include <dali-toolkit/public-api/text/rendering-backend.h>
-#include <dali-toolkit/internal/text/layouts/layout-engine.h>
+#include <dali-toolkit/internal/controls/text-controls/text-font-style.h>
 #include <dali-toolkit/internal/text/rendering/text-backend.h>
 #include <dali-toolkit/internal/text/text-view.h>
 #include <dali-toolkit/internal/styling/style-manager-impl.h>
@@ -149,24 +147,17 @@ void TextLabel::SetProperty( BaseObject* object, Property::Index index, const Pr
         {
           const std::string fontFamily = value.Get< std::string >();
 
+          DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::SetProperty Property::FONT_FAMILY newFont(%s)\n", fontFamily.c_str() );
           if( impl.mController->GetDefaultFontFamily() != fontFamily )
           {
-            impl.mController->SetDefaultFontFamily( fontFamily );
+            impl.mController->SetDefaultFontFamily( fontFamily, true );
           }
         }
         break;
       }
       case Toolkit::TextLabel::Property::FONT_STYLE:
       {
-        if( impl.mController )
-        {
-          const std::string fontStyle = value.Get< std::string >();
-
-          if( impl.mController->GetDefaultFontStyle() != fontStyle )
-          {
-            impl.mController->SetDefaultFontStyle( fontStyle );
-          }
-        }
+        SetFontStyleProperty( impl.mController, value );
         break;
       }
       case Toolkit::TextLabel::Property::POINT_SIZE:
@@ -341,10 +332,7 @@ Property::Value TextLabel::GetProperty( BaseObject* object, Property::Index inde
       }
       case Toolkit::TextLabel::Property::FONT_STYLE:
       {
-        if( impl.mController )
-        {
-          value = impl.mController->GetDefaultFontStyle();
-        }
+        GetFontStyleProperty( impl.mController, value );
         break;
       }
       case Toolkit::TextLabel::Property::POINT_SIZE:
@@ -470,12 +458,10 @@ void TextLabel::OnStyleChange( Toolkit::StyleManager styleManager, StyleChange::
   {
     case StyleChange::DEFAULT_FONT_CHANGE:
     {
-      DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::OnStyleChange StyleChange::DEFAULT_FONT_CHANGE\n");
-      if ( mController->GetDefaultFontFamily() == "" )
-      {
-        // Property system did not set the font so should update it.
-        // todo instruct text-controller to update model
-      }
+      // Property system did not set the font so should update it.
+      std::string newFont = styleManager.GetDefaultFontFamily();
+      DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::OnStyleChange StyleChange::DEFAULT_FONT_CHANGE newFont(%s)\n", newFont.c_str() );
+      mController->UpdateAfterFontChange( newFont );
       break;
     }
 
index 68a30c5..3a42d6a 100644 (file)
@@ -32,6 +32,7 @@
 #include <dali/public-api/math/vector4.h>
 #include <dali/public-api/object/property-map.h>
 #include <dali/devel-api/object/type-registry-helper.h>
+#include <dali/integration-api/debug.h>
 
 #include <libintl.h>
 #include <cfloat>
@@ -48,11 +49,15 @@ namespace Internal
 namespace
 {
 // todo Move this to adaptor??
-#define GET_LOCALE_TEXT(string) dgettext("elementary", string)
+#define GET_LOCALE_TEXT(string) dgettext("sys_string", string)
 
 const std::string TEXT_SELECTION_POPUP_BUTTON_STYLE_NAME( "textselectionpopupbutton" );
 const Dali::Vector4 DEFAULT_OPTION_PRESSED_COLOR( Dali::Vector4( 0.24f, 0.72f, 0.8f, 1.0f ) );
 
+#if defined(DEBUG_ENABLED)
+  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, true, "LOG_TEXT_CONTROLS");
+#endif
+
 #ifdef DGETTEXT_ENABLED
 
 #define POPUP_CUT_STRING GET_LOCALE_TEXT("IDS_COM_BODY_CUT")
@@ -114,6 +119,8 @@ DALI_TYPE_REGISTRATION_END()
 
 Dali::Toolkit::TextSelectionPopup TextSelectionPopup::New( TextSelectionPopupCallbackInterface* callbackInterface )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextSelectionPopup::New\n" );
+
    // Create the implementation, temporarily owned by this handle on stack
   IntrusivePtr< TextSelectionPopup > impl = new TextSelectionPopup( callbackInterface );
 
@@ -376,6 +383,7 @@ void TextSelectionPopup::HidePopup()
 
 void TextSelectionPopup::OnInitialize()
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "TextSelectionPopup::OnInitialize\n" );
   Actor self = Self();
   self.SetResizePolicy( ResizePolicy::FIT_TO_CHILDREN, Dimension::ALL_DIMENSIONS );
   self.SetProperty( Actor::Property::COLOR_ALPHA, 0.0f );
@@ -383,6 +391,7 @@ void TextSelectionPopup::OnInitialize()
 
 void TextSelectionPopup::OnStageConnection( int depth )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "TextSelectionPopup::OnStageConnection\n" );
   // Call the Control::OnStageConnection() to set the depth of the background.
   Control::OnStageConnection( depth );
 
@@ -394,7 +403,8 @@ void TextSelectionPopup::HideAnimationFinished( Animation& animation )
   Actor self = Self();
   if ( !mPopupShowing ) // During the Hide/Fade animation there could be a call to Show the Popup again, mPopupShowing will be true in this case.
   {
-    UnparentAndReset( self );  // Popup needs to be shown so do not unparent
+    DALI_LOG_INFO( gLogFilter, Debug::General, "TextSelectionPopup::HideAnimationFinished\n" );
+    UnparentAndReset( mToolbar );
   }
 }
 
@@ -642,6 +652,8 @@ std::string TextSelectionPopup::GetPressedImage() const
  void TextSelectionPopup::AddOption( const ButtonRequirement& button, bool showDivider, bool showIcons, bool showCaption  )
  {
    // 1. Create a option.
+   DALI_LOG_INFO( gLogFilter, Debug::General, "TextSelectionPopup::AddOption\n" );
+
    Toolkit::PushButton option = Toolkit::PushButton::New();
    option.SetName( button.name );
    option.SetAnimationTime( 0.0f );
@@ -753,6 +765,8 @@ std::string TextSelectionPopup::GetPressedImage() const
 
  void TextSelectionPopup::AddPopupOptionsToToolbar( bool showIcons, bool showCaptions )
  {
+   DALI_LOG_INFO( gLogFilter, Debug::General, "TextSelectionPopup::AddPopupOptionsToToolbar\n" );
+
    CreateOrderedListOfPopupOptions();
 
    mButtonsChanged = false;
index 0b71ff8..0b0517c 100644 (file)
@@ -49,6 +49,7 @@ toolkit_src_files = \
    $(toolkit_src_dir)/controls/super-blur-view/super-blur-view-impl.cpp \
    $(toolkit_src_dir)/controls/table-view/table-view-impl.cpp \
    $(toolkit_src_dir)/controls/text-controls/text-field-impl.cpp \
+   $(toolkit_src_dir)/controls/text-controls/text-font-style.cpp \
    $(toolkit_src_dir)/controls/text-controls/text-label-impl.cpp \
    $(toolkit_src_dir)/controls/text-controls/text-selection-popup-impl.cpp \
    $(toolkit_src_dir)/controls/text-controls/text-selection-toolbar-impl.cpp \
index 08d61fd..41f20e3 100644 (file)
@@ -100,6 +100,7 @@ Toolkit::StyleManager StyleManager::Get()
 StyleManager::StyleManager()
 : mOrientationDegrees( 0 ),  // Portrait
   mDefaultFontSize( -1 ),
+  mDefaultFontFamily(""),
   mThemeFile( DEFAULT_THEME ),
   mFeedbackStyle( NULL )
 {
@@ -155,6 +156,11 @@ void StyleManager::SetOrientation( Orientation orientation )
   }
 }
 
+std::string StyleManager::GetDefaultFontFamily() const
+{
+  return mDefaultFontFamily;
+}
+
 Orientation StyleManager::GetOrientation()
 {
   return mOrientation;
@@ -417,6 +423,7 @@ void StyleManager::StyleMonitorChange( StyleMonitor styleMonitor, StyleChange::T
   {
     case StyleChange::DEFAULT_FONT_CHANGE:
     {
+      mDefaultFontFamily = styleMonitor.GetDefaultFontFamily();
       break;
     }
 
index 86c6d4c..ab5e24d 100644 (file)
@@ -81,6 +81,11 @@ public:
   Orientation GetOrientation();
 
   /**
+   * @copydoc Toolkit::StyleManager::GetDefaultFontFamily
+   */
+  std::string GetDefaultFontFamily() const;
+
+  /**
    * @copydoc Toolkit::StyleManager::SetStyleConstant
    */
   void SetStyleConstant( const std::string& key, const Property::Value& value );
@@ -254,6 +259,8 @@ private:
 
   int mDefaultFontSize;               ///< Logical size, not a point-size
 
+  std::string mDefaultFontFamily;
+
   std::string mThemeFile;             ///< The full path of the current theme file
 
   Property::Map mThemeBuilderConstants;   ///< Contants to give the theme builder
index 9ec055e..441d179 100644 (file)
@@ -159,6 +159,16 @@ void LocalToWorldCoordinatesBoundingBox( const Dali::Rect<int>& boundingRectangl
                                originY + boundingRectangle.height );
 }
 
+void WorldToLocalCoordinatesBoundingBox( const Dali::Vector4& boundingBox, Dali::Rect<int>& boundingRectangle )
+{
+  // Convert to local coordinates and store as a Dali::Rect.
+  Dali::Vector2 stageSize = Dali::Stage::GetCurrent().GetSize();
+
+  boundingRectangle.x = boundingBox.x + 0.5f * stageSize.width;
+  boundingRectangle.y = boundingBox.y + 0.5f * stageSize.height;
+  boundingRectangle.width = boundingBox.z - boundingBox.x;
+  boundingRectangle.height = boundingBox.w - boundingBox.y;
+}
 
 } // end of namespace
 
@@ -202,13 +212,15 @@ struct Decorator::Impl : public ConnectionTracker
   {
     HandleImpl()
     : position(),
+      size(),
       lineHeight( 0.0f ),
       grabDisplacementX( 0.f ),
       grabDisplacementY( 0.f ),
       active( false ),
       visible( false ),
       pressed( false ),
-      flipped( false )
+      horizontallyFlipped( false ),
+      verticallyFlipped( false )
     {
     }
 
@@ -217,13 +229,15 @@ struct Decorator::Impl : public ConnectionTracker
     ImageActor markerActor;
 
     Vector2 position;
-    float lineHeight; ///< Not the handle height
-    float grabDisplacementX;
-    float grabDisplacementY;
-    bool active  : 1;
-    bool visible : 1;
-    bool pressed : 1;
-    bool flipped : 1;
+    Size    size;
+    float   lineHeight;              ///< Not the handle height
+    float   grabDisplacementX;
+    float   grabDisplacementY;
+    bool    active  : 1;
+    bool    visible : 1;
+    bool    pressed : 1;
+    bool    horizontallyFlipped : 1; ///< Whether the handle has been horizontally flipped.
+    bool    verticallyFlipped   : 1; ///< Whether the handle has been vertically flipped.
   };
 
   struct PopupImpl
@@ -245,7 +259,7 @@ struct Decorator::Impl : public ConnectionTracker
     mEnabledPopupButtons( TextSelectionPopup::NONE ),
     mTextSelectionPopupCallbackInterface( callbackInterface ),
     mHandleColor( HANDLE_COLOR ),
-    mBoundingBox( Rect<int>() ),
+    mBoundingBox(),
     mHighlightColor( LIGHT_BLUE ),
     mHighlightPosition( Vector2::ZERO ),
     mActiveCursor( ACTIVE_CURSOR_NONE ),
@@ -263,12 +277,19 @@ struct Decorator::Impl : public ConnectionTracker
     mDelayCursorBlink( false ),
     mPrimaryCursorVisible( false ),
     mSecondaryCursorVisible( false ),
-    mSwapSelectionHandles( false ),
+    mFlipSelectionHandlesOnCross( false ),
+    mFlipLeftSelectionHandleDirection( false ),
+    mFlipRightSelectionHandleDirection( false ),
+    mHandlePanning( false ),
+    mHandleCurrentCrossed( false ),
+    mHandlePreviousCrossed( false ),
     mNotifyEndOfScroll( false )
   {
     mQuadVertexFormat[ "aPosition" ] = Property::VECTOR2;
     mQuadIndexFormat[ "indices" ] = Property::INTEGER;
     mHighlightMaterial = Material::New( Shader::New( VERTEX_SHADER, FRAGMENT_SHADER ) );
+
+    SetupTouchEvents();
   }
 
   /**
@@ -289,7 +310,7 @@ struct Decorator::Impl : public ConnectionTracker
       mPrimaryCursorVisible = ( cursor.position.x <= size.width ) && ( cursor.position.x >= 0.f );
       if( mPrimaryCursorVisible )
       {
-        Vector2 position = cursor.position;
+        const Vector2& position = cursor.position;
 
         mPrimaryCursor.SetPosition( position.x,
                                     position.y );
@@ -314,18 +335,19 @@ struct Decorator::Impl : public ConnectionTracker
     HandleImpl& grabHandle = mHandle[GRAB_HANDLE];
     if( grabHandle.active )
     {
-      Vector2 position = grabHandle.position;
+      const Vector2& position = grabHandle.position;
 
       const bool isVisible = ( position.x <= size.width ) && ( position.x >= 0.f );
 
       if( isVisible )
       {
-        SetupTouchEvents();
-
         CreateGrabHandle();
 
-        grabHandle.actor.SetPosition( position.x - floor( 0.5f * mCursorWidth ),
-                                      position.y + grabHandle.lineHeight ); // TODO : Fix for multiline.
+        // Sets the grab handle position and calculate if it needs to be vertically flipped if it exceeds the boundary box.
+        SetGrabHandlePosition();
+
+        // Sets the grab handle image according if it's pressed, flipped, etc.
+        SetHandleImage( GRAB_HANDLE );
       }
       grabHandle.actor.SetVisible( isVisible );
     }
@@ -339,30 +361,32 @@ struct Decorator::Impl : public ConnectionTracker
     HandleImpl& secondary = mHandle[ RIGHT_SELECTION_HANDLE ];
     if( primary.active || secondary.active )
     {
-      Vector2 primaryPosition = primary.position;
-      Vector2 secondaryPosition = secondary.position;
+      const Vector2& primaryPosition = primary.position;
+      const Vector2& secondaryPosition = secondary.position;
 
       const bool isPrimaryVisible = ( primaryPosition.x <= size.width ) && ( primaryPosition.x >= 0.f );
       const bool isSecondaryVisible = ( secondaryPosition.x <= size.width ) && ( secondaryPosition.x >= 0.f );
 
       if( isPrimaryVisible || isSecondaryVisible )
       {
-        SetupTouchEvents();
-
         CreateSelectionHandles();
 
         if( isPrimaryVisible )
         {
-          primary.actor.SetPosition( primaryPosition.x,
-                                     primaryPosition.y + primary.lineHeight ); // TODO : Fix for multiline.
+          SetSelectionHandlePosition( LEFT_SELECTION_HANDLE );
+
+          // Sets the primary handle image according if it's pressed, flipped, etc.
+          SetHandleImage( LEFT_SELECTION_HANDLE );
 
           SetSelectionHandleMarkerSize( primary );
         }
 
         if( isSecondaryVisible )
         {
-          secondary.actor.SetPosition( secondaryPosition.x,
-                                       secondaryPosition.y + secondary.lineHeight ); // TODO : Fix for multiline.
+          SetSelectionHandlePosition( RIGHT_SELECTION_HANDLE );
+
+          // Sets the secondary handle image according if it's pressed, flipped, etc.
+          SetHandleImage( RIGHT_SELECTION_HANDLE );
 
           SetSelectionHandleMarkerSize( secondary );
         }
@@ -410,7 +434,6 @@ struct Decorator::Impl : public ConnectionTracker
     mHandle[ LEFT_SELECTION_HANDLE ].position += scrollOffset;
     mHandle[ RIGHT_SELECTION_HANDLE ].position += scrollOffset;
     mHighlightPosition += scrollOffset;
-    DeterminePositionPopup();
   }
 
   void ShowPopup()
@@ -561,17 +584,11 @@ struct Decorator::Impl : public ConnectionTracker
 
   void SetupTouchEvents()
   {
-    if ( !mTapDetector )
-    {
-      mTapDetector = TapGestureDetector::New();
-      mTapDetector.DetectedSignal().Connect( this, &Decorator::Impl::OnTap );
-    }
+    mTapDetector = TapGestureDetector::New();
+    mTapDetector.DetectedSignal().Connect( this, &Decorator::Impl::OnTap );
 
-    if ( !mPanGestureDetector )
-    {
-      mPanGestureDetector = PanGestureDetector::New();
-      mPanGestureDetector.DetectedSignal().Connect( this, &Decorator::Impl::OnPan );
-    }
+    mPanGestureDetector = PanGestureDetector::New();
+    mPanGestureDetector.DetectedSignal().Connect( this, &Decorator::Impl::OnPan );
   }
 
   void CreateActiveLayer()
@@ -598,7 +615,6 @@ struct Decorator::Impl : public ConnectionTracker
   {
     if ( handle.markerActor )
     {
-      handle.markerActor.SetResizePolicy ( ResizePolicy::FIXED, Dimension::HEIGHT );
       handle.markerActor.SetSize( 0, handle.lineHeight );
     }
   }
@@ -610,7 +626,7 @@ struct Decorator::Impl : public ConnectionTracker
     {
       if( !mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED] )
       {
-        mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED] = ResourceImage::New( DEFAULT_GRAB_HANDLE_IMAGE_RELEASED );
+        SetHandleImage( GRAB_HANDLE, HANDLE_IMAGE_RELEASED, ResourceImage::New( DEFAULT_GRAB_HANDLE_IMAGE_RELEASED ) );
       }
 
       grabHandle.actor = ImageActor::New( mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED] );
@@ -655,12 +671,14 @@ struct Decorator::Impl : public ConnectionTracker
 
   void CreateHandleMarker( HandleImpl& handle, Image& image, HandleType handleType )
   {
-    if ( image)
+    if ( image )
     {
       handle.markerActor = ImageActor::New( image );
       handle.markerActor.SetColor( mHandleColor );
       handle.actor.Add( handle.markerActor );
 
+      handle.markerActor.SetResizePolicy ( ResizePolicy::FIXED, Dimension::HEIGHT );
+
       if ( LEFT_SELECTION_HANDLE == handleType )
       {
         handle.markerActor.SetAnchorPoint( AnchorPoint::BOTTOM_RIGHT );
@@ -685,7 +703,6 @@ struct Decorator::Impl : public ConnectionTracker
 #endif
       primary.actor.SetAnchorPoint( AnchorPoint::TOP_RIGHT ); // Change to BOTTOM_RIGHT if Look'n'Feel requires handle above text.
       primary.actor.SetSortModifier( DECORATION_DEPTH_INDEX );
-      primary.flipped = false;
       primary.actor.SetColor( mHandleColor );
 
       primary.grabArea = Actor::New(); // Area that Grab handle responds to, larger than actual handle so easier to move
@@ -720,7 +737,6 @@ struct Decorator::Impl : public ConnectionTracker
 #endif
       secondary.actor.SetAnchorPoint( AnchorPoint::TOP_LEFT ); // Change to BOTTOM_LEFT if Look'n'Feel requires handle above text.
       secondary.actor.SetSortModifier( DECORATION_DEPTH_INDEX );
-      secondary.flipped = false;
       secondary.actor.SetColor( mHandleColor );
 
       secondary.grabArea = Actor::New(); // Area that Grab handle responds to, larger than actual handle so easier to move
@@ -747,6 +763,141 @@ struct Decorator::Impl : public ConnectionTracker
     }
   }
 
+  void CalculateHandleWorldCoordinates( HandleImpl& handle, Vector2& position )
+  {
+    // Get the world position of the active layer
+    const Vector3 parentWorldPosition = mActiveLayer.GetCurrentWorldPosition();
+
+    // Get the size of the UI control.
+    Vector2 targetSize;
+    mController.GetTargetSize( targetSize );
+
+    // The grab handle position in world coords.
+    position.x = parentWorldPosition.x - 0.5f * targetSize.width + handle.position.x;
+    position.y = parentWorldPosition.y - 0.5f * targetSize.height + handle.position.y + handle.lineHeight;
+  }
+
+  void SetGrabHandlePosition()
+  {
+    // Reference to the grab handle.
+    HandleImpl& grabHandle = mHandle[GRAB_HANDLE];
+
+    // The grab handle position in world coords.
+    Vector2 grabHandleWorldPosition;
+    CalculateHandleWorldCoordinates( grabHandle, grabHandleWorldPosition );
+
+    // Check if the grab handle exceeds the boundaries of the decoration box.
+    // At the moment only the height is checked for the grab handle.
+    grabHandle.verticallyFlipped = ( grabHandleWorldPosition.y + grabHandle.size.height > mBoundingBox.w );
+
+    // The grab handle 'y' position in local coords.
+    // If the grab handle exceeds the bottom of the decoration box,
+    // set the 'y' position to the top of the line.
+    // The SetGrabHandleImage() method will change the orientation.
+    const float yLocalPosition = grabHandle.verticallyFlipped ? grabHandle.position.y : grabHandle.position.y + grabHandle.lineHeight;
+
+    grabHandle.actor.SetPosition( grabHandle.position.x - floor( 0.5f * mCursorWidth ),
+                                  yLocalPosition ); // TODO : Fix for multiline.
+  }
+
+  void SetSelectionHandlePosition( HandleType type )
+  {
+    const bool isPrimaryHandle = LEFT_SELECTION_HANDLE == type;
+
+    // Reference to the selection handle.
+    HandleImpl& handle = mHandle[type];
+
+    // Get the world coordinates of the handle position.
+    Vector2 handleWorldPosition;
+    CalculateHandleWorldCoordinates( handle, handleWorldPosition );
+
+    // Whether to flip the handle.
+    bool flipHandle = isPrimaryHandle ? mFlipLeftSelectionHandleDirection : mFlipRightSelectionHandleDirection;
+
+    // Whether to flip the handles if they are crossed.
+    bool crossFlip = false;
+    if( mFlipSelectionHandlesOnCross || !mHandlePanning )
+    {
+      crossFlip = mHandleCurrentCrossed;
+    }
+
+    // Does not flip if both conditions are true (double flip)
+    flipHandle = flipHandle != ( crossFlip || mHandlePreviousCrossed );
+
+    // Check if the selection handle exceeds the boundaries of the decoration box.
+    const bool exceedsLeftEdge = ( isPrimaryHandle ? !flipHandle : flipHandle ) && ( handleWorldPosition.x - handle.size.width < mBoundingBox.x );
+
+    const bool exceedsRightEdge = ( isPrimaryHandle ? flipHandle : !flipHandle ) && ( handleWorldPosition.x + handle.size.width > mBoundingBox.z );
+
+    // Does not flip if both conditions are true (double flip)
+    flipHandle = flipHandle != ( exceedsLeftEdge || exceedsRightEdge );
+
+    if( flipHandle )
+    {
+      if( !handle.horizontallyFlipped )
+      {
+        // Change the anchor point to flip the image.
+        handle.actor.SetAnchorPoint( isPrimaryHandle ? AnchorPoint::TOP_LEFT : AnchorPoint::TOP_RIGHT );
+
+        handle.horizontallyFlipped = true;
+      }
+    }
+    else
+    {
+      if( handle.horizontallyFlipped )
+      {
+        // Reset the anchor point.
+        handle.actor.SetAnchorPoint( isPrimaryHandle ? AnchorPoint::TOP_RIGHT : AnchorPoint::TOP_LEFT );
+
+        handle.horizontallyFlipped = false;
+      }
+    }
+
+    // Whether to flip the handle vertically.
+    handle.verticallyFlipped = ( handleWorldPosition.y + handle.size.height > mBoundingBox.w );
+
+    // The primary selection handle 'y' position in local coords.
+    // If the handle exceeds the bottom of the decoration box,
+    // set the 'y' position to the top of the line.
+    // The SetHandleImage() method will change the orientation.
+    const float yLocalPosition = handle.verticallyFlipped ? handle.position.y : handle.position.y + handle.lineHeight;
+
+    handle.actor.SetPosition( handle.position.x,
+                              yLocalPosition ); // TODO : Fix for multiline.
+  }
+
+  void SetHandleImage( HandleType type )
+  {
+    HandleImpl& handle = mHandle[type];
+
+    HandleType markerType = HANDLE_TYPE_COUNT;
+    // If the selection handle is flipped it chooses the image of the other selection handle. Does nothing for the grab handle.
+    if( LEFT_SELECTION_HANDLE == type )
+    {
+      type = handle.horizontallyFlipped ? RIGHT_SELECTION_HANDLE : LEFT_SELECTION_HANDLE;
+      markerType = handle.horizontallyFlipped ? RIGHT_SELECTION_HANDLE_MARKER : LEFT_SELECTION_HANDLE_MARKER;
+    }
+    else if( RIGHT_SELECTION_HANDLE == type )
+    {
+      type = handle.horizontallyFlipped ? LEFT_SELECTION_HANDLE : RIGHT_SELECTION_HANDLE;
+      markerType = handle.horizontallyFlipped ? LEFT_SELECTION_HANDLE_MARKER : RIGHT_SELECTION_HANDLE_MARKER;
+    }
+
+    // Chooses between the released or pressed image. It checks whether the pressed image exists.
+    const HandleImageType imageType = ( handle.pressed ? ( mHandleImages[type][HANDLE_IMAGE_PRESSED] ? HANDLE_IMAGE_PRESSED : HANDLE_IMAGE_RELEASED ) : HANDLE_IMAGE_RELEASED );
+
+    handle.actor.SetImage( mHandleImages[type][imageType] );
+
+    if( HANDLE_TYPE_COUNT != markerType )
+    {
+      const HandleImageType markerImageType = ( handle.pressed ? ( mHandleImages[markerType][HANDLE_IMAGE_PRESSED] ? HANDLE_IMAGE_PRESSED : HANDLE_IMAGE_RELEASED ) : HANDLE_IMAGE_RELEASED );
+      handle.markerActor.SetImage( mHandleImages[markerType][markerImageType] );
+    }
+
+    // Whether to flip the handle vertically.
+    handle.actor.SetOrientation( handle.verticallyFlipped ? ANGLE_180 : ANGLE_0, Vector3::XAXIS );
+  }
+
   void CreateHighlight()
   {
     if( !mHighlightActor )
@@ -906,6 +1057,8 @@ struct Decorator::Impl : public ConnectionTracker
         StopScrollTimer();
         mController.DecorationEvent( type, HANDLE_PRESSED, x, y );
       }
+
+      mHandlePanning = true;
     }
     else if( Gesture::Finished  == gesture.state ||
              Gesture::Cancelled == gesture.state )
@@ -923,22 +1076,10 @@ struct Decorator::Impl : public ConnectionTracker
         mController.DecorationEvent( type, HANDLE_RELEASED, x, y );
       }
 
-      if( GRAB_HANDLE == type )
-      {
-        handle.actor.SetImage( mHandleImages[type][HANDLE_IMAGE_RELEASED] );
-      }
-      else
-      {
-        HandleType selectionHandleType = type;
-
-        if( mSwapSelectionHandles != handle.flipped )
-        {
-          selectionHandleType = ( LEFT_SELECTION_HANDLE == type ) ? RIGHT_SELECTION_HANDLE : LEFT_SELECTION_HANDLE;
-        }
-
-        handle.actor.SetImage( mHandleImages[selectionHandleType][HANDLE_IMAGE_RELEASED] );
-      }
+      handle.actor.SetImage( mHandleImages[type][HANDLE_IMAGE_RELEASED] );
       handle.pressed = false;
+
+      mHandlePanning = false;
     }
   }
 
@@ -973,22 +1114,14 @@ struct Decorator::Impl : public ConnectionTracker
       if( TouchPoint::Down == point.state )
       {
         mHandle[GRAB_HANDLE].pressed = true;
-        Image imagePressed = mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_PRESSED];
-        if( imagePressed )
-        {
-          mHandle[GRAB_HANDLE].actor.SetImage( imagePressed );
-        }
       }
       else if( ( TouchPoint::Up == point.state ) ||
                ( TouchPoint::Interrupted == point.state ) )
       {
         mHandle[GRAB_HANDLE].pressed = false;
-        Image imageReleased = mHandleImages[GRAB_HANDLE][HANDLE_IMAGE_RELEASED];
-        if( imageReleased )
-        {
-          mHandle[GRAB_HANDLE].actor.SetImage( imageReleased );
-        }
       }
+
+      SetHandleImage( GRAB_HANDLE );
     }
 
     // Consume to avoid pop-ups accidentally closing, when handle is outside of pop-up area
@@ -1003,26 +1136,19 @@ struct Decorator::Impl : public ConnectionTracker
     {
       const TouchPoint& point = event.GetPoint(0);
 
-      const bool flip = mSwapSelectionHandles != mHandle[LEFT_SELECTION_HANDLE].flipped;
       if( TouchPoint::Down == point.state )
       {
         mHandle[LEFT_SELECTION_HANDLE].pressed = true;
-        Image imagePressed = mHandleImages[flip ? RIGHT_SELECTION_HANDLE : LEFT_SELECTION_HANDLE][HANDLE_IMAGE_PRESSED];
-        if( imagePressed )
-        {
-          mHandle[LEFT_SELECTION_HANDLE].actor.SetImage( imagePressed );
-        }
       }
       else if( ( TouchPoint::Up == point.state ) ||
                ( TouchPoint::Interrupted == point.state ) )
       {
         mHandle[LEFT_SELECTION_HANDLE].pressed = false;
-        Image imageReleased = mHandleImages[flip ? RIGHT_SELECTION_HANDLE : LEFT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED];
-        if( imageReleased )
-        {
-          mHandle[LEFT_SELECTION_HANDLE].actor.SetImage( imageReleased );
-        }
+        mHandlePreviousCrossed = mHandleCurrentCrossed;
+        mHandlePanning = false;
       }
+
+      SetHandleImage( LEFT_SELECTION_HANDLE );
     }
 
     // Consume to avoid pop-ups accidentally closing, when handle is outside of pop-up area
@@ -1037,26 +1163,19 @@ struct Decorator::Impl : public ConnectionTracker
     {
       const TouchPoint& point = event.GetPoint(0);
 
-      const bool flip = mSwapSelectionHandles != mHandle[RIGHT_SELECTION_HANDLE].flipped;
       if( TouchPoint::Down == point.state )
       {
-        Image imagePressed = mHandleImages[flip ? LEFT_SELECTION_HANDLE : RIGHT_SELECTION_HANDLE][HANDLE_IMAGE_PRESSED];
         mHandle[RIGHT_SELECTION_HANDLE].pressed = true;
-        if( imagePressed )
-        {
-          mHandle[RIGHT_SELECTION_HANDLE].actor.SetImage( imagePressed );
-        }
       }
       else if( ( TouchPoint::Up == point.state ) ||
                ( TouchPoint::Interrupted == point.state ) )
       {
-        Image imageReleased = mHandleImages[flip ? LEFT_SELECTION_HANDLE : RIGHT_SELECTION_HANDLE][HANDLE_IMAGE_RELEASED];
         mHandle[RIGHT_SELECTION_HANDLE].pressed = false;
-        if( imageReleased )
-        {
-          mHandle[RIGHT_SELECTION_HANDLE].actor.SetImage( imageReleased );
-        }
+        mHandlePreviousCrossed = mHandleCurrentCrossed;
+        mHandlePanning = false;
       }
+
+      SetHandleImage( RIGHT_SELECTION_HANDLE );
     }
 
     // Consume to avoid pop-ups accidentally closing, when handle is outside of pop-up area
@@ -1109,19 +1228,16 @@ struct Decorator::Impl : public ConnectionTracker
 
     // Exceeding vertical boundary
 
-    Vector4 worldCoordinatesBoundingBox;
-    LocalToWorldCoordinatesBoundingBox( mBoundingBox, worldCoordinatesBoundingBox );
-
     float popupHeight = mCopyPastePopup.actor.GetRelayoutSize( Dimension::HEIGHT);
 
     PropertyNotification verticalExceedNotification = mCopyPastePopup.actor.AddPropertyNotification( Actor::Property::WORLD_POSITION_Y,
-                                                      OutsideCondition( worldCoordinatesBoundingBox.y + popupHeight * 0.5f,
-                                                                        worldCoordinatesBoundingBox.w - popupHeight * 0.5f ) );
+                                                      OutsideCondition( mBoundingBox.y + popupHeight * 0.5f,
+                                                                        mBoundingBox.w - popupHeight * 0.5f ) );
 
     verticalExceedNotification.NotifySignal().Connect( this, &Decorator::Impl::PopUpLeavesVerticalBoundary );
   }
 
-  void GetConstrainedPopupPosition( Vector3& requiredPopupPosition, Vector3& popupSize, Vector3 anchorPoint, Actor& parent, Rect<int>& boundingBox )
+  void GetConstrainedPopupPosition( Vector3& requiredPopupPosition, Vector3& popupSize, Vector3 anchorPoint, Actor& parent, const Vector4& boundingRectangleWorld )
   {
     DALI_ASSERT_DEBUG ( "Popup parent not on stage" && parent.OnStage() )
 
@@ -1131,10 +1247,6 @@ struct Decorator::Impl : public ConnectionTracker
     Vector3 popupWorldPosition = parentWorldPositionLeftAnchor + requiredPopupPosition;  // Parent World position plus popup local position gives World Position
     Vector3 popupDistanceFromAnchorPoint = popupSize*anchorPoint;
 
-    // Bounding rectangle is supplied as screen coordinates, bounding will be done in world coordinates.
-    Vector4 boundingRectangleWorld;
-    LocalToWorldCoordinatesBoundingBox( boundingBox, boundingRectangleWorld );
-
     // Calculate distance to move popup (in local space) so fits within the boundary
     float xOffSetToKeepWithinBounds = 0.0f;
     if( popupWorldPosition.x - popupDistanceFromAnchorPoint.x < boundingRectangleWorld.x )
@@ -1157,41 +1269,14 @@ struct Decorator::Impl : public ConnectionTracker
     // Prevent pixel mis-alignment by rounding down.
     requiredPopupPosition.x = static_cast<int>( requiredPopupPosition.x );
     requiredPopupPosition.y = static_cast<int>( requiredPopupPosition.y );
-
   }
 
-  void FlipSelectionHandleImages()
+  void SetHandleImage( HandleType handleType, HandleImageType handleImageType, Dali::Image image )
   {
-    SetupTouchEvents();
-
-    CreateSelectionHandles();
-
-    HandleImpl& leftHandle = mHandle[LEFT_SELECTION_HANDLE];
-    HandleImpl& rightHandle = mHandle[RIGHT_SELECTION_HANDLE];
-
-    // If handle pressed and pressed image exists then use pressed image else stick with released image
-    const HandleImageType leftImageType = ( leftHandle.pressed && mHandleImages[LEFT_SELECTION_HANDLE][HANDLE_IMAGE_PRESSED] ) ? HANDLE_IMAGE_PRESSED : HANDLE_IMAGE_RELEASED;
-    const HandleImageType rightImageType = ( rightHandle.pressed && mHandleImages[RIGHT_SELECTION_HANDLE][HANDLE_IMAGE_PRESSED] ) ? HANDLE_IMAGE_PRESSED : HANDLE_IMAGE_RELEASED;
+    HandleImpl& handle = mHandle[handleType];
+    handle.size = Size( image.GetWidth(), image.GetHeight() );
 
-    const bool leftFlipped = mSwapSelectionHandles != leftHandle.flipped;
-    const bool rightFlipped = mSwapSelectionHandles != rightHandle.flipped;
-
-    leftHandle.actor.SetImage( leftFlipped ? mHandleImages[RIGHT_SELECTION_HANDLE][leftImageType] : mHandleImages[LEFT_SELECTION_HANDLE][leftImageType] );
-
-    leftHandle.actor.SetAnchorPoint( leftFlipped ? AnchorPoint::TOP_LEFT : AnchorPoint::TOP_RIGHT );
-
-    rightHandle.actor.SetImage( rightFlipped ? mHandleImages[LEFT_SELECTION_HANDLE][rightImageType] : mHandleImages[RIGHT_SELECTION_HANDLE][rightImageType] );
-
-    rightHandle.actor.SetAnchorPoint( rightFlipped ? AnchorPoint::TOP_RIGHT : AnchorPoint::TOP_LEFT );
-
-    if ( leftHandle.markerActor )
-    {
-      leftHandle.markerActor.SetImage( leftFlipped ? mHandleImages[RIGHT_SELECTION_HANDLE_MARKER][leftImageType] : mHandleImages[LEFT_SELECTION_HANDLE_MARKER][leftImageType] );
-    }
-    if ( rightHandle.markerActor )
-    {
-      rightHandle.markerActor.SetImage( rightFlipped ? mHandleImages[LEFT_SELECTION_HANDLE_MARKER][rightImageType] : mHandleImages[RIGHT_SELECTION_HANDLE_MARKER][rightImageType] );
-    }
+    mHandleImages[handleType][handleImageType] = image;
   }
 
   void SetScrollThreshold( float threshold )
@@ -1304,7 +1389,7 @@ struct Decorator::Impl : public ConnectionTracker
   Geometry            mQuadGeometry;
   QuadContainer       mHighlightQuadList;         ///< Sub-selections that combine to create the complete selection highlight
 
-  Rect<int>           mBoundingBox;
+  Vector4             mBoundingBox;               ///< The bounding box in world coords.
   Vector4             mHighlightColor;            ///< Color of the highlight
   Vector2             mHighlightPosition;         ///< The position of the highlight actor.
 
@@ -1319,13 +1404,18 @@ struct Decorator::Impl : public ConnectionTracker
   float               mScrollDistance;          ///< Distance the text scrolls during a scroll interval.
   int                 mTextDepth;               ///< The depth used to render the text.
 
-  bool                mActiveCopyPastePopup   : 1;
-  bool                mCursorBlinkStatus      : 1; ///< Flag to switch between blink on and blink off.
-  bool                mDelayCursorBlink       : 1; ///< Used to avoid cursor blinking when entering text.
-  bool                mPrimaryCursorVisible   : 1; ///< Whether the primary cursor is visible.
-  bool                mSecondaryCursorVisible : 1; ///< Whether the secondary cursor is visible.
-  bool                mSwapSelectionHandles   : 1; ///< Whether to swap the selection handle images.
-  bool                mNotifyEndOfScroll      : 1; ///< Whether to notify the end of the scroll.
+  bool                mActiveCopyPastePopup              : 1;
+  bool                mCursorBlinkStatus                 : 1; ///< Flag to switch between blink on and blink off.
+  bool                mDelayCursorBlink                  : 1; ///< Used to avoid cursor blinking when entering text.
+  bool                mPrimaryCursorVisible              : 1; ///< Whether the primary cursor is visible.
+  bool                mSecondaryCursorVisible            : 1; ///< Whether the secondary cursor is visible.
+  bool                mFlipSelectionHandlesOnCross       : 1; ///< Whether to flip the selection handles as soon as they cross.
+  bool                mFlipLeftSelectionHandleDirection  : 1; ///< Whether to flip the left selection handle image because of the character's direction.
+  bool                mFlipRightSelectionHandleDirection : 1; ///< Whether to flip the right selection handle image because of the character's direction.
+  bool                mHandlePanning                     : 1; ///< Whether any of the handles is moving.
+  bool                mHandleCurrentCrossed              : 1; ///< Whether the handles are crossed.
+  bool                mHandlePreviousCrossed             : 1; ///< Whether the handles where crossed at the last handle touch up.
+  bool                mNotifyEndOfScroll                 : 1; ///< Whether to notify the end of the scroll.
 };
 
 DecoratorPtr Decorator::New( ControllerInterface& controller,
@@ -1337,12 +1427,12 @@ DecoratorPtr Decorator::New( ControllerInterface& controller,
 
 void Decorator::SetBoundingBox( const Rect<int>& boundingBox )
 {
-  mImpl->mBoundingBox = boundingBox;
+  LocalToWorldCoordinatesBoundingBox( boundingBox, mImpl->mBoundingBox );
 }
 
-const Rect<int>& Decorator::GetBoundingBox() const
+void Decorator::GetBoundingBox( Rect<int>& boundingBox ) const
 {
-  return mImpl->mBoundingBox;
+  WorldToLocalCoordinatesBoundingBox( mImpl->mBoundingBox, boundingBox );
 }
 
 void Decorator::Relayout( const Vector2& size )
@@ -1466,6 +1556,11 @@ void Decorator::SetHandleActive( HandleType handleType, bool active )
 
   if( !active )
   {
+    if( ( LEFT_SELECTION_HANDLE == handleType ) || ( RIGHT_SELECTION_HANDLE == handleType ) )
+    {
+      mImpl->mHandlePreviousCrossed = false;
+    }
+
     // TODO: this is a work-around.
     // The problem is the handle actor does not receive the touch event with the Interrupt
     // state when the power button is pressed and the application goes to background.
@@ -1477,6 +1572,7 @@ void Decorator::SetHandleActive( HandleType handleType, bool active )
        imageActor.SetImage( imageReleased );
     }
   }
+
 }
 
 bool Decorator::IsHandleActive( HandleType handleType ) const
@@ -1486,7 +1582,7 @@ bool Decorator::IsHandleActive( HandleType handleType ) const
 
 void Decorator::SetHandleImage( HandleType handleType, HandleImageType handleImageType, Dali::Image image )
 {
-  mImpl->mHandleImages[handleType][handleImageType] = image;
+  mImpl->SetHandleImage( handleType, handleImageType, image );
 }
 
 Dali::Image Decorator::GetHandleImage( HandleType handleType, HandleImageType handleImageType ) const
@@ -1531,11 +1627,16 @@ const Vector2& Decorator::GetPosition( HandleType handleType ) const
   return mImpl->mHandle[handleType].position;
 }
 
-void Decorator::SwapSelectionHandlesEnabled( bool enable )
+void Decorator::FlipSelectionHandlesOnCrossEnabled( bool enable )
 {
-  mImpl->mSwapSelectionHandles = enable;
+  mImpl->mFlipSelectionHandlesOnCross = enable;
+}
 
-  mImpl->FlipSelectionHandleImages();
+void Decorator::SetSelectionHandleFlipState( bool indicesSwapped, bool left, bool right )
+{
+  mImpl->mHandleCurrentCrossed = indicesSwapped;
+  mImpl->mFlipLeftSelectionHandleDirection = left;
+  mImpl->mFlipRightSelectionHandleDirection = right;
 }
 
 void Decorator::AddHighlight( float x1, float y1, float x2, float y2 )
index 1587703..4e36fa7 100644 (file)
@@ -179,9 +179,9 @@ public:
    * @brief Retrieve the bounding box origin and dimensions.
    *
    * default is set once control is added to stage, before this the return vector will be Vector4:ZERO
-   * @return Rect<int> the bounding box origin, width and height
+   * @param[out] boundingBox The bounding box origin, width and height.
    */
-  const Rect<int>& GetBoundingBox() const;
+  void GetBoundingBox( Rect<int>& boundingBox ) const;
 
   /**
    * @brief The decorator waits until a relayout before creating actors etc.
@@ -397,12 +397,25 @@ public:
   const Vector2& GetPosition( HandleType handleType ) const;
 
   /**
-   * @brief Swaps the selection handle's images.
+   * @brief Whether to flip the selection handles as soon as they are crossed.
    *
-   * This method is called by the text controller to swap the handles
-   * when the start index is bigger than the end one.
+   * By default they flip when the handle is released.
+   *
+   * @param[in] enable If @e true the selection handles will flip as soon as they are crossed.
+   */
+  void FlipSelectionHandlesOnCrossEnabled( bool enable );
+
+  /**
+   * @brief Sets info to calculate the handle flip state.
+   *
+   * Sets the character's direction where the handles are pointing.
+   * It resets the decorator internal flip state when there is a new selection.
+   *
+   * @param[in] indicesSwapped Whether the selection handle indices are swapped (start > end).
+   * @param[in] left The direction of the character pointed by the primary selection handle.
+   * @param[in] right The direction of the character pointed by the secondary selection handle.
    */
-  void SwapSelectionHandlesEnabled( bool enable );
+  void SetSelectionHandleFlipState( bool indicesSwapped, bool left, bool right );
 
   /**
    * @brief Adds a quad to the existing selection highlights.
index 5ee4992..9062b07 100644 (file)
@@ -105,7 +105,6 @@ struct LayoutEngine::Impl
     mCursorWidth( CURSOR_WIDTH ),
     mEllipsisEnabled( false )
   {
-    mFontClient = TextAbstraction::FontClient::Get();
   }
 
   /**
@@ -117,7 +116,7 @@ struct LayoutEngine::Impl
   void UpdateLineHeight( FontId fontId, LineLayout& lineLayout )
   {
     Text::FontMetrics fontMetrics;
-    mFontClient.GetFontMetrics( fontId, fontMetrics );
+    mMetrics->GetFontMetrics( fontId, fontMetrics );
 
     // Sets the maximum ascender.
     if( fontMetrics.ascender > lineLayout.ascender )
@@ -634,7 +633,7 @@ struct LayoutEngine::Impl
           const GlyphInfo& glyphInfo = *( layoutParameters.glyphsBuffer + layoutParameters.totalNumberOfGlyphs - 1u );
 
           Text::FontMetrics fontMetrics;
-          mFontClient.GetFontMetrics( glyphInfo.fontId, fontMetrics );
+          mMetrics->GetFontMetrics( glyphInfo.fontId, fontMetrics );
 
           LineRun lineRun;
           lineRun.glyphRun.glyphIndex = 0u;
@@ -821,7 +820,7 @@ struct LayoutEngine::Impl
   LayoutEngine::VerticalAlignment mVerticalAlignment;
   float mCursorWidth;
 
-  TextAbstraction::FontClient mFontClient;
+  IntrusivePtr<Metrics> mMetrics;
 
   bool mEllipsisEnabled:1;
 };
@@ -837,6 +836,11 @@ LayoutEngine::~LayoutEngine()
   delete mImpl;
 }
 
+void LayoutEngine::SetMetrics( MetricsPtr& metrics )
+{
+  mImpl->mMetrics = metrics;
+}
+
 void LayoutEngine::SetLayout( Layout layout )
 {
   mImpl->mLayout = layout;
index d0f1ab6..f866f3e 100644 (file)
@@ -24,6 +24,7 @@
 
 // INTERNAL INCLUDE
 #include <dali-toolkit/internal/text/line-run.h>
+#include <dali-toolkit/internal/text/metrics.h>
 
 namespace Dali
 {
@@ -74,6 +75,13 @@ public:
   ~LayoutEngine();
 
   /**
+   * @brief Provide the wrapper around FontClient used to get metrics
+   *
+   * @param[in] metrics Used to get metrics
+   */
+  void SetMetrics( MetricsPtr& metrics );
+
+  /**
    * @brief Choose the required layout.
    *
    * @param[in] layout The required layout.
diff --git a/dali-toolkit/internal/text/metrics.h b/dali-toolkit/internal/text/metrics.h
new file mode 100644 (file)
index 0000000..147ae79
--- /dev/null
@@ -0,0 +1,134 @@
+#ifndef __DALI_TOOLKIT_TEXT_METRICS_H__
+#define __DALI_TOOLKIT_TEXT_METRICS_H__
+
+/*
+ * Copyright (c) 2015 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+// EXTERNAL INCLUDES
+#include <dali/public-api/common/intrusive-ptr.h>
+#include <dali/devel-api/text-abstraction/font-client.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+class Metrics;
+typedef IntrusivePtr<Metrics> MetricsPtr;
+
+/**
+ * @brief A wrapper around FontClient used to get metrics & potentially down-scaled Emoji metrics.
+ */
+class Metrics : public RefObject
+{
+public:
+
+  /**
+   * Create a new Metrics object
+   */
+  static Metrics* New( TextAbstraction::FontClient& fontClient )
+  {
+    return new Metrics( fontClient );
+  }
+
+  /**
+   * @brief Set the maximum Emoji size.
+   *
+   * @param[in] emojiSize Emoticons will be scaled to fit this size in pixels.
+   */
+  void SetMaxEmojiSize( int emojiSize )
+  {
+    mEmojiSize = emojiSize;
+  }
+
+  /**
+   * @brief Get the maximum Emoji size.
+   *
+   * @return The maximum Emoji size.
+   */
+  int GetMaxEmojiSize() const
+  {
+    return mEmojiSize;
+  }
+
+  /**
+   * @brief Query the metrics for a font.
+   *
+   * @param[in] fontId The ID of the font for the required glyph.
+   * @param[out] metrics The font metrics.
+   */
+  void GetFontMetrics( FontId fontId, FontMetrics& metrics )
+  {
+    mFontClient.GetFontMetrics( fontId, metrics, mEmojiSize ); // inline for performance
+  }
+
+  /**
+   * @brief Retrieve the metrics for a series of glyphs.
+   *
+   * @param[in,out] array An array of glyph-info structures with initialized FontId & GlyphIndex values.
+   * It may contain the advance and an offset set into the bearing from the shaping tool.
+   * On return, the glyph's size value will be initialized. The bearing value will be updated by adding the font's glyph bearing to the one set by the shaping tool.
+   * @param[in] size The size of the array.
+   * @return True if all of the requested metrics were found.
+   */
+  bool GetGlyphMetrics( GlyphInfo* array, uint32_t size )
+  {
+    return mFontClient.GetGlyphMetrics( array, size, true, mEmojiSize ); // inline for performance
+  }
+
+protected:
+
+  /**
+   * A reference counted object may only be deleted by calling Unreference()
+   */
+  virtual ~Metrics() {}
+
+private:
+
+  /**
+   * Constructor.
+   */
+  Metrics( TextAbstraction::FontClient& fontClient )
+  : mFontClient( fontClient ),
+    mEmojiSize( 0 )
+  {
+  }
+
+  // Undefined
+  Metrics(const Metrics&);
+
+  // Undefined
+  Metrics& operator=(const Metrics& rhs);
+
+private:
+
+  TextAbstraction::FontClient mFontClient;
+
+  int mEmojiSize;
+};
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_TEXT_METRICS_H__
index d730c9e..8e55537 100644 (file)
@@ -32,7 +32,7 @@ namespace Toolkit
 namespace
 {
 #if defined(DEBUG_ENABLED)
-Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Concise, true, "LOG_MULTI_LANGUAGE_SUPPORT");
+Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, true, "LOG_MULTI_LANGUAGE_SUPPORT");
 #endif
 
 const Dali::Toolkit::Text::Character UTF32_A = 0x0041;
@@ -351,19 +351,19 @@ void MultilanguageSupport::ValidateFonts( const Vector<Character>& text,
                                           const Vector<ScriptRun>& scripts,
                                           Vector<FontRun>& fonts )
 {
-  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "-->MultilanguageSupport::ValidateFonts\n" );
+  DALI_LOG_INFO( gLogFilter, Debug::General, "-->MultilanguageSupport::ValidateFonts\n" );
   const Length numberOfCharacters = text.Count();
 
   if( 0u == numberOfCharacters )
   {
-    DALI_LOG_INFO( gLogFilter, Debug::Verbose, "<--MultilanguageSupport::ValidateFonts\n" );
+    DALI_LOG_INFO( gLogFilter, Debug::General, "<--MultilanguageSupport::ValidateFonts\n" );
     // Nothing to do if there are no characters.
     return;
   }
 
   // Copy the fonts set by application developers.
   const Length numberOfFontRuns = fonts.Count();
-  const Vector<FontRun> definedFonts = fonts;
+  const Vector<FontRun> userSetFonts = fonts;
   fonts.Clear();
 
   // Traverse the characters and validate/set the fonts.
@@ -386,8 +386,8 @@ void MultilanguageSupport::ValidateFonts( const Vector<Character>& text,
   TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
 
   // Iterators of the font and script runs.
-  Vector<FontRun>::ConstIterator fontRunIt = definedFonts.Begin();
-  Vector<FontRun>::ConstIterator fontRunEndIt = definedFonts.End();
+  Vector<FontRun>::ConstIterator fontRunIt = userSetFonts.Begin();
+  Vector<FontRun>::ConstIterator fontRunEndIt = userSetFonts.End();
   Vector<ScriptRun>::ConstIterator scriptRunIt = scripts.Begin();
   Vector<ScriptRun>::ConstIterator scriptRunEndIt = scripts.End();
 
@@ -585,7 +585,7 @@ void MultilanguageSupport::ValidateFonts( const Vector<Character>& text,
     // Store the last run.
     fonts.PushBack( currentFontRun );
   }
-  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "<--MultilanguageSupport::ValidateFonts\n" );
+  DALI_LOG_INFO( gLogFilter, Debug::General, "<--MultilanguageSupport::ValidateFonts\n" );
 }
 
 } // namespace Internal
index a4fc1d8..5af46ef 100644 (file)
@@ -331,6 +331,16 @@ struct AtlasRenderer::Impl : public ConnectionTracker
         textCacheEntry.mIndex = glyph.index;
         newTextCache.PushBack( textCacheEntry );
 
+        // Adjust the vertices if the fixed-size font should be down-scaled
+        if( glyph.scaleFactor > 0 )
+        {
+          for( unsigned int i=0; i<newMesh.mVertices.Count(); ++i )
+          {
+            newMesh.mVertices[i].mPosition.x = position.x + ( ( newMesh.mVertices[i].mPosition.x - position.x ) * glyph.scaleFactor );
+            newMesh.mVertices[i].mPosition.y = position.y + ( ( newMesh.mVertices[i].mPosition.y - position.y ) * glyph.scaleFactor );
+          }
+        }
+
         // Find an existing mesh data object to attach to ( or create a new one, if we can't find one using the same atlas)
         StitchTextMesh( meshContainer,
                         newMesh,
@@ -713,8 +723,8 @@ struct AtlasRenderer::Impl : public ConnectionTracker
 
     Dali::Renderer renderer = Dali::Renderer::New( quadGeometry, material );
 
-    // Ensure shadow is behind the text...
-    renderer.SetDepthIndex( CONTENT_DEPTH_INDEX + mDepth );
+    // Set depth index to -1.0 to make sure shadow is rendered first in 3D layers
+    renderer.SetDepthIndex( -1.0f );
     Actor actor = Actor::New();
     actor.AddRenderer( renderer );
     actor.SetParentOrigin( ParentOrigin::CENTER ); // Keep all of the origins aligned
index 5e64f87..e533a3f 100644 (file)
@@ -33,7 +33,7 @@ namespace
 {
 
 #if defined(DEBUG_ENABLED)
-  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Concise, true, "LOG_TEXT_CONTROLS");
+  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, true, "LOG_TEXT_CONTROLS");
 #endif
 
 /**
@@ -58,8 +58,6 @@ struct GlyphMetrics
   float xBearing;   ///< The x bearing of the first glyph.
 };
 
-const std::string EMPTY_STRING("");
-
 } // namespace
 
 namespace Dali
@@ -78,20 +76,20 @@ namespace Text
  * @param[in] numberOfGlyphs The number of glyphs.
  * @param[out] glyphMetrics Some glyph metrics (font height, advance, ascender and x bearing).
  * @param[in] visualModel The visual model.
- * @param[in] fontClient The font client.
+ * @param[in] metrics Used to access metrics from FontClient.
  */
 void GetGlyphsMetrics( GlyphIndex glyphIndex,
                        Length numberOfGlyphs,
                        GlyphMetrics& glyphMetrics,
-                       VisualModelPtr visualModel,
-                       TextAbstraction::FontClient& fontClient )
+                       VisualModelPtr& visualModel,
+                       MetricsPtr& metrics )
 {
   const GlyphInfo* glyphsBuffer = visualModel->mGlyphs.Begin();
 
   const GlyphInfo& firstGlyph = *( glyphsBuffer + glyphIndex );
 
   Text::FontMetrics fontMetrics;
-  fontClient.GetFontMetrics( firstGlyph.fontId, fontMetrics );
+  metrics->GetFontMetrics( firstGlyph.fontId, fontMetrics );
 
   glyphMetrics.fontHeight = fontMetrics.height;
   glyphMetrics.advance = firstGlyph.advance;
@@ -279,6 +277,8 @@ bool Controller::Impl::ProcessInputEvents()
 
 void Controller::Impl::UpdateModel( OperationsMask operationsRequired )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::UpdateModel\n" );
+
   // Calculate the operations to be done.
   const OperationsMask operations = static_cast<OperationsMask>( mOperationsPending & operationsRequired );
 
@@ -423,7 +423,7 @@ void Controller::Impl::UpdateModel( OperationsMask operationsRequired )
   if( GET_GLYPH_METRICS & operations )
   {
     GlyphInfo* glyphsBuffer = glyphs.Begin();
-    mFontClient.GetGlyphMetrics( glyphsBuffer, numberOfGlyphs );
+    mMetrics->GetGlyphMetrics( glyphsBuffer, numberOfGlyphs );
 
     // Update the width and advance of all new paragraph characters.
     for( Vector<GlyphIndex>::ConstIterator it = newParagraphGlyphs.Begin(), endIt = newParagraphGlyphs.End(); it != endIt; ++it )
@@ -463,6 +463,7 @@ void Controller::Impl::GetDefaultFonts( Vector<FontRun>& fonts, Length numberOfC
 {
   if( mFontDefaults )
   {
+    DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::GetDefaultFonts font family(%s)\n", mFontDefaults->mFontDescription.family.c_str() );
     FontRun fontRun;
     fontRun.characterRun.characterIndex = 0;
     fontRun.characterRun.numberOfCharacters = numberOfCharacters;
@@ -478,8 +479,8 @@ float Controller::Impl::GetDefaultFontLineHeight()
   FontId defaultFontId = 0u;
   if( NULL == mFontDefaults )
   {
-    defaultFontId = mFontClient.GetFontId( EMPTY_STRING,
-                                           EMPTY_STRING );
+    TextAbstraction::FontDescription fontDescription;
+    defaultFontId = mFontClient.GetFontId( fontDescription );
   }
   else
   {
@@ -487,7 +488,7 @@ float Controller::Impl::GetDefaultFontLineHeight()
   }
 
   Text::FontMetrics fontMetrics;
-  mFontClient.GetFontMetrics( defaultFontId, fontMetrics );
+  mMetrics->GetFontMetrics( defaultFontId, fontMetrics );
 
   return( fontMetrics.ascender - fontMetrics.descender );
 }
@@ -876,12 +877,14 @@ void Controller::Impl::RetrieveSelection( std::string& selectedText, bool delete
     return;
   }
 
+  const bool handlesCrossed = mEventData->mLeftSelectionPosition > mEventData->mRightSelectionPosition;
+
   //Get start and end position of selection
-  uint32_t startOfSelectedText = mEventData->mLeftSelectionPosition;
-  uint32_t lengthOfSelectedText =  mEventData->mRightSelectionPosition - startOfSelectedText;
+  uint32_t startOfSelectedText = handlesCrossed ? mEventData->mRightSelectionPosition : mEventData->mLeftSelectionPosition;
+  uint32_t lengthOfSelectedText =  ( handlesCrossed ? mEventData->mLeftSelectionPosition : mEventData->mRightSelectionPosition ) - startOfSelectedText;
 
   // Validate the start and end selection points
-  if( ( startOfSelectedText >= 0 ) && (  ( startOfSelectedText + lengthOfSelectedText ) <=  mLogicalModel->mText.Count() ) )
+  if(  ( startOfSelectedText + lengthOfSelectedText ) <=  mLogicalModel->mText.Count() )
   {
     //Get text as a UTF8 string
     Vector<Character>& utf32Characters = mLogicalModel->mText;
@@ -897,7 +900,7 @@ void Controller::Impl::RetrieveSelection( std::string& selectedText, bool delete
       Vector<Character>::Iterator last  = first + lengthOfSelectedText;
       currentText.Erase( first, last );
     }
-    mEventData->mPrimaryCursorPosition = mEventData->mLeftSelectionPosition;
+    mEventData->mPrimaryCursorPosition = handlesCrossed ? mEventData->mRightSelectionPosition : mEventData->mLeftSelectionPosition;
     mEventData->mScrollAfterDelete = true;
     mEventData->mDecoratorUpdated = true;
   }
@@ -970,8 +973,16 @@ void Controller::Impl::RepositionSelectionHandles( CharacterIndex selectionStart
   const LineRun& firstLine = *lines.Begin();
   const float height = firstLine.ascender + -firstLine.descender;
 
+  const bool isLastCharacter = selectionEnd >= mLogicalModel->mText.Count();
+  const bool startDirection = ( ( NULL == modelCharacterDirectionsBuffer ) ? false : *( modelCharacterDirectionsBuffer + selectionStart ) );
+  const bool endDirection = ( ( NULL == modelCharacterDirectionsBuffer ) ? false : *( modelCharacterDirectionsBuffer + ( selectionEnd - ( isLastCharacter ? 1u : 0u ) ) ) );
+
   // Swap the indices if the start is greater than the end.
-  const bool indicesSwapped = ( selectionStart > selectionEnd );
+  const bool indicesSwapped = selectionStart > selectionEnd;
+
+  // Tell the decorator to flip the selection handles if needed.
+  mEventData->mDecorator->SetSelectionHandleFlipState( indicesSwapped, startDirection, endDirection );
+
   if( indicesSwapped )
   {
     std::swap( selectionStart, selectionEnd );
@@ -991,9 +1002,6 @@ void Controller::Impl::RepositionSelectionHandles( CharacterIndex selectionStart
   const Length numberOfCharactersEnd = *( charactersPerGlyphBuffer + glyphEnd );
   bool splitEndGlyph = ( glyphStart != glyphEnd ) && ( numberOfCharactersEnd > 1u ) && HasLigatureMustBreak( mLogicalModel->GetScript( selectionEndMinusOne ) );
 
-  // Tell the decorator to swap the selection handles if needed.
-  mEventData->mDecorator->SwapSelectionHandlesEnabled( firstLine.direction != indicesSwapped );
-
   const Vector2 offset = mEventData->mScrollPosition + mAlignmentOffset;
 
   // Traverse the glyphs.
@@ -1078,7 +1086,7 @@ void Controller::Impl::RepositionSelectionHandles( CharacterIndex selectionStart
   mEventData->mDecorator->SetPosition( RIGHT_SELECTION_HANDLE, secondaryPosition.x, secondaryPosition.y, secondaryCursorInfo.lineHeight );
 
   // Cursor to be positioned at end of selection so if selection interrupted and edit mode restarted the cursor will be at end of selection
-  mEventData->mPrimaryCursorPosition = (indicesSwapped)?mEventData->mLeftSelectionPosition:mEventData->mRightSelectionPosition;
+  mEventData->mPrimaryCursorPosition = ( indicesSwapped ) ? mEventData->mLeftSelectionPosition : mEventData->mRightSelectionPosition;
 
   // Set the flag to update the decorator.
   mEventData->mDecoratorUpdated = true;
@@ -1462,7 +1470,7 @@ CharacterIndex Controller::Impl::GetClosestCursorIndex( float visualX,
                       numberOfGlyphs,
                       glyphMetrics,
                       mVisualModel,
-                      mFontClient );
+                      mMetrics );
 
     const Vector2& position = *( positionsBuffer + glyphLogicalOrderIndex );
 
@@ -1601,7 +1609,7 @@ void Controller::Impl::GetCursorPosition( CharacterIndex logical,
                     primaryNumberOfGlyphs,
                     glyphMetrics,
                     mVisualModel,
-                    mFontClient );
+                    mMetrics );
 
   // Whether to add the glyph's advance to the cursor position.
   // i.e if the paragraph is left to right and the logical cursor is zero, the position is the position of the first glyph and the advance is not added,
@@ -1691,7 +1699,7 @@ void Controller::Impl::GetCursorPosition( CharacterIndex logical,
                       secondaryNumberOfGlyphs,
                       glyphMetrics,
                       mVisualModel,
-                      mFontClient );
+                      mMetrics );
 
     // Set the secondary cursor's position.
     cursorInfo.secondaryPosition.x = -glyphMetrics.xBearing + secondaryPosition.x + ( isCurrentRightToLeft ? 0.f : glyphMetrics.advance );
@@ -1768,8 +1776,8 @@ void Controller::Impl::UpdateCursorPosition()
     FontId defaultFontId = 0u;
     if( NULL == mFontDefaults )
     {
-      defaultFontId = mFontClient.GetFontId( EMPTY_STRING,
-                                             EMPTY_STRING );
+      TextAbstraction::FontDescription fontDescription;
+      defaultFontId = mFontClient.GetFontId( fontDescription );
     }
     else
     {
@@ -1777,7 +1785,7 @@ void Controller::Impl::UpdateCursorPosition()
     }
 
     Text::FontMetrics fontMetrics;
-    mFontClient.GetFontMetrics( defaultFontId, fontMetrics );
+    mMetrics->GetFontMetrics( defaultFontId, fontMetrics );
 
     lineHeight = fontMetrics.ascender - fontMetrics.descender;
 
index 3073611..2936d4d 100644 (file)
@@ -174,9 +174,14 @@ struct ModifyEvent
 struct FontDefaults
 {
   FontDefaults()
-  : mDefaultPointSize(0.0f),
+  : mFontDescription(),
+    mFontStyle(),
+    mDefaultPointSize(0.0f),
     mFontId(0u)
   {
+    // Initially use the default platform font
+    TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
+    fontClient.GetDefaultPlatformFontDescription( mFontDescription );
   }
 
   FontId GetFontId( TextAbstraction::FontClient& fontClient )
@@ -184,14 +189,14 @@ struct FontDefaults
     if( !mFontId )
     {
       Dali::TextAbstraction::PointSize26Dot6 pointSize = mDefaultPointSize*64;
-      mFontId = fontClient.GetFontId( mDefaultFontFamily, mDefaultFontStyle, pointSize );
+      mFontId = fontClient.GetFontId( mFontDescription, pointSize );
     }
 
     return mFontId;
   }
 
-  std::string mDefaultFontFamily;
-  std::string mDefaultFontStyle;
+  TextAbstraction::FontDescription mFontDescription;
+  std::string mFontStyle;
   float mDefaultPointSize;
   FontId mFontId;
 };
@@ -207,13 +212,15 @@ struct Controller::Impl
     mFontClient(),
     mClipboard(),
     mView(),
+    mMetrics(),
     mLayoutEngine(),
     mModifyEvents(),
     mTextColor( Color::BLACK ),
     mAlignmentOffset(),
     mOperationsPending( NO_OPERATION ),
     mMaximumNumberOfCharacters( 50 ),
-    mRecalculateNaturalSize( true )
+    mRecalculateNaturalSize( true ),
+    mUserDefinedFontFamily( false )
   {
     mLogicalModel = LogicalModel::New();
     mVisualModel  = VisualModel::New();
@@ -223,6 +230,10 @@ struct Controller::Impl
 
     mView.SetVisualModel( mVisualModel );
 
+    // Use this to access FontClient i.e. to get down-scaled Emoji metrics.
+    mMetrics = Metrics::New( mFontClient );
+    mLayoutEngine.SetMetrics( mMetrics );
+
     // Set the text properties to default
     mVisualModel->SetUnderlineEnabled( false );
     mVisualModel->SetUnderlineHeight( 0.0f );
@@ -311,14 +322,17 @@ struct Controller::Impl
 
   void ResetImfManager()
   {
-    // Reset incase we are in a pre-edit state.
-    ImfManager imfManager = ImfManager::Get();
-    if ( imfManager )
+    if( mEventData )
     {
-      imfManager.Reset(); // Will trigger a commit message
+      // Reset incase we are in a pre-edit state.
+      ImfManager imfManager = ImfManager::Get();
+      if ( imfManager )
+      {
+        imfManager.Reset(); // Will trigger a commit message
+      }
+
+      ClearPreEditFlag();
     }
-
-    ClearPreEditFlag();
   }
 
   bool IsClipboardEmpty()
@@ -468,15 +482,18 @@ struct Controller::Impl
   FontDefaults* mFontDefaults;             ///< Avoid allocating this when the user does not specify a font.
   EventData* mEventData;                   ///< Avoid allocating everything for text input until EnableTextInput().
   TextAbstraction::FontClient mFontClient; ///< Handle to the font client.
-  Clipboard mClipboard;                   ///< Handle to the system clipboard
+  Clipboard mClipboard;                    ///< Handle to the system clipboard
   View mView;                              ///< The view interface to the rendering back-end.
+  MetricsPtr mMetrics;                     ///< A wrapper around FontClient used to get metrics & potentially down-scaled Emoji metrics.
   LayoutEngine mLayoutEngine;              ///< The layout engine.
   std::vector<ModifyEvent> mModifyEvents;  ///< Temporary stores the text set until the next relayout.
   Vector4 mTextColor;                      ///< The regular text color
   Vector2 mAlignmentOffset;                ///< Vertical and horizontal offset of the whole text inside the control due to alignment.
   OperationsMask mOperationsPending;       ///< Operations pending to be done to layout the text.
   Length mMaximumNumberOfCharacters;       ///< Maximum number of characters that can be inserted.
+
   bool mRecalculateNaturalSize:1;          ///< Whether the natural size needs to be recalculated.
+  bool mUserDefinedFontFamily:1;           ///< Whether the Font family was set by the user instead of being left as sytem default.
 };
 
 } // namespace Text
index e3b29bd..ef10a3f 100644 (file)
@@ -38,8 +38,10 @@ namespace
 #endif
 
 const float MAX_FLOAT = std::numeric_limits<float>::max();
+const unsigned int POINTS_PER_INCH = 72;
 
 const std::string EMPTY_STRING("");
+const unsigned int ZERO = 0u;
 
 float ConvertToEven( float value )
 {
@@ -73,6 +75,11 @@ void Controller::EnableTextInput( DecoratorPtr decorator )
 
 void Controller::SetText( const std::string& text )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Controller::SetText\n" );
+
+  // Reset keyboard as text changed
+  mImpl->ResetImfManager();
+
   // Remove the previously set text
   ResetText();
 
@@ -138,8 +145,8 @@ void Controller::SetText( const std::string& text )
     mImpl->mEventData->mEventQueue.clear();
   }
 
-  // Reset keyboard as text changed
-  mImpl->ResetImfManager();
+  // Notify IMF as text changed
+  NotifyImfManager();
 
   // Do this last since it provides callbacks into application code
   mImpl->mControlInterface.TextChanged();
@@ -222,14 +229,16 @@ int Controller::GetMaximumNumberOfCharacters()
   return mImpl->mMaximumNumberOfCharacters;
 }
 
-void Controller::SetDefaultFontFamily( const std::string& defaultFontFamily )
+void Controller::SetDefaultFontFamily( const std::string& defaultFontFamily, bool userDefined )
 {
   if( !mImpl->mFontDefaults )
   {
     mImpl->mFontDefaults = new FontDefaults();
   }
 
-  mImpl->mFontDefaults->mDefaultFontFamily = defaultFontFamily;
+  mImpl->mFontDefaults->mFontDescription.family = defaultFontFamily;
+  DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetDefaultFontFamily %s userDefined: %s\n", defaultFontFamily.c_str(), userDefined ? "true":"false" );
+  mImpl->mUserDefinedFontFamily = userDefined;
 
   // Clear the font-specific data
   ClearFontData();
@@ -244,20 +253,40 @@ const std::string& Controller::GetDefaultFontFamily() const
 {
   if( mImpl->mFontDefaults )
   {
-    return mImpl->mFontDefaults->mDefaultFontFamily;
+    return mImpl->mFontDefaults->mFontDescription.family;
   }
 
   return EMPTY_STRING;
 }
 
-void Controller::SetDefaultFontStyle( const std::string& defaultFontStyle )
+void Controller::SetDefaultFontStyle( const std::string& style )
 {
   if( !mImpl->mFontDefaults )
   {
     mImpl->mFontDefaults = new FontDefaults();
   }
 
-  mImpl->mFontDefaults->mDefaultFontStyle = defaultFontStyle;
+  mImpl->mFontDefaults->mFontStyle = style;
+}
+
+const std::string& Controller::GetDefaultFontStyle() const
+{
+  if( mImpl->mFontDefaults )
+  {
+    return mImpl->mFontDefaults->mFontStyle;
+  }
+
+  return EMPTY_STRING;
+}
+
+void Controller::SetDefaultFontWidth( FontWidth width )
+{
+  if( !mImpl->mFontDefaults )
+  {
+    mImpl->mFontDefaults = new FontDefaults();
+  }
+
+  mImpl->mFontDefaults->mFontDescription.width = width;
 
   // Clear the font-specific data
   ClearFontData();
@@ -268,14 +297,70 @@ void Controller::SetDefaultFontStyle( const std::string& defaultFontStyle )
   mImpl->RequestRelayout();
 }
 
-const std::string& Controller::GetDefaultFontStyle() const
+FontWidth Controller::GetDefaultFontWidth() const
 {
   if( mImpl->mFontDefaults )
   {
-    return mImpl->mFontDefaults->mDefaultFontStyle;
+    return mImpl->mFontDefaults->mFontDescription.width;
   }
 
-  return EMPTY_STRING;
+  return TextAbstraction::FontWidth::NORMAL;
+}
+
+void Controller::SetDefaultFontWeight( FontWeight weight )
+{
+  if( !mImpl->mFontDefaults )
+  {
+    mImpl->mFontDefaults = new FontDefaults();
+  }
+
+  mImpl->mFontDefaults->mFontDescription.weight = weight;
+
+  // Clear the font-specific data
+  ClearFontData();
+
+  mImpl->mOperationsPending = ALL_OPERATIONS;
+  mImpl->mRecalculateNaturalSize = true;
+
+  mImpl->RequestRelayout();
+}
+
+FontWeight Controller::GetDefaultFontWeight() const
+{
+  if( mImpl->mFontDefaults )
+  {
+    return mImpl->mFontDefaults->mFontDescription.weight;
+  }
+
+  return TextAbstraction::FontWeight::NORMAL;
+}
+
+void Controller::SetDefaultFontSlant( FontSlant slant )
+{
+  if( !mImpl->mFontDefaults )
+  {
+    mImpl->mFontDefaults = new FontDefaults();
+  }
+
+  mImpl->mFontDefaults->mFontDescription.slant = slant;
+
+  // Clear the font-specific data
+  ClearFontData();
+
+  mImpl->mOperationsPending = ALL_OPERATIONS;
+  mImpl->mRecalculateNaturalSize = true;
+
+  mImpl->RequestRelayout();
+}
+
+FontSlant Controller::GetDefaultFontSlant() const
+{
+  if( mImpl->mFontDefaults )
+  {
+    return mImpl->mFontDefaults->mFontDescription.slant;
+  }
+
+  return TextAbstraction::FontSlant::NORMAL;
 }
 
 void Controller::SetDefaultPointSize( float pointSize )
@@ -287,6 +372,15 @@ void Controller::SetDefaultPointSize( float pointSize )
 
   mImpl->mFontDefaults->mDefaultPointSize = pointSize;
 
+  unsigned int horizontalDpi( 0u );
+  unsigned int verticalDpi( 0u );
+  mImpl->mFontClient.GetDpi( horizontalDpi, verticalDpi );
+
+  // Adjust the metrics if the fixed-size font should be down-scaled
+  int maxEmojiSize( pointSize/POINTS_PER_INCH * verticalDpi );
+  DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetDefaultPointSize %p setting MaxEmojiSize %d\n", this, maxEmojiSize );
+  mImpl->mMetrics->SetMaxEmojiSize( maxEmojiSize );
+
   // Clear the font-specific data
   ClearFontData();
 
@@ -306,6 +400,23 @@ float Controller::GetDefaultPointSize() const
   return 0.0f;
 }
 
+void Controller::UpdateAfterFontChange( std::string& newDefaultFont )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::UpdateAfterFontChange");
+
+  ClearFontData();
+
+  if ( !mImpl->mUserDefinedFontFamily ) // If user defined font then should not update when system font changes
+  {
+    DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::UpdateAfterFontChange newDefaultFont(%s)\n", newDefaultFont.c_str() );
+    mImpl->mFontDefaults->mFontDescription.family = newDefaultFont;
+    mImpl->UpdateModel( ALL_OPERATIONS );
+    mImpl->QueueModifyEvent( ModifyEvent::TEXT_REPLACED );
+    mImpl->mRecalculateNaturalSize = true;
+    mImpl->RequestRelayout();
+  }
+}
+
 void Controller::SetTextColor( const Vector4& textColor )
 {
   mImpl->mTextColor = textColor;
@@ -641,11 +752,24 @@ bool Controller::Relayout( const Size& size )
   // Do not re-do any operation until something changes.
   mImpl->mOperationsPending = NO_OPERATION;
 
+  // Keep the current offset and alignment as it will be used to update the decorator's positions.
+  Vector2 offset;
+  if( mImpl->mEventData )
+  {
+    offset = mImpl->mAlignmentOffset + mImpl->mEventData->mScrollPosition;
+  }
+
   // After doing the text layout, the alignment offset to place the actor in the desired position can be calculated.
   CalculateTextAlignment( size );
 
   if( mImpl->mEventData )
   {
+    // If there is a nex size, the scroll position needs to be clamped.
+    mImpl->ClampHorizontalScroll( layoutSize );
+
+    // Update the decorator's positions.
+    mImpl->mEventData->mDecorator->UpdatePositions( mImpl->mAlignmentOffset + mImpl->mEventData->mScrollPosition - offset );
+
     // Move the cursor, grab handle etc.
     updated = mImpl->ProcessInputEvents() || updated;
   }
@@ -1453,21 +1577,38 @@ void Controller::PanEvent( Gesture::State state, const Vector2& displacement )
 
 void Controller::LongPressEvent( Gesture::State state, float x, float y  )
 {
-  DALI_ASSERT_DEBUG( mImpl->mEventData && "Unexpected PanEvent" );
+  DALI_ASSERT_DEBUG( mImpl->mEventData && "Unexpected LongPressEvent" );
 
-  if  ( mImpl->IsShowingPlaceholderText() || mImpl->mLogicalModel->mText.Count() == 0u )
+  if( state == Gesture::Started &&
+      mImpl->mEventData )
   {
-    if ( mImpl->mEventData )
+    if( ! mImpl->IsShowingRealText() )
     {
       Event event( Event::LONG_PRESS_EVENT );
       event.p1.mInt = state;
       mImpl->mEventData->mEventQueue.push_back( event );
       mImpl->RequestRelayout();
     }
-  }
-  else if( mImpl->mEventData )
-  {
-    SelectEvent( x, y, false );
+    else
+    {
+      // The 1st long-press on inactive text-field is treated as tap
+      if( EventData::INACTIVE == mImpl->mEventData->mState )
+      {
+        mImpl->ChangeState( EventData::EDITING );
+
+        Event event( Event::TAP_EVENT );
+        event.p1.mUint = 1;
+        event.p2.mFloat = x;
+        event.p3.mFloat = y;
+        mImpl->mEventData->mEventQueue.push_back( event );
+
+        mImpl->RequestRelayout();
+      }
+      else
+      {
+        SelectEvent( x, y, false );
+      }
+    }
   }
 }
 
@@ -1592,6 +1733,13 @@ void Controller::TextPopupButtonTouched( Dali::Toolkit::TextSelectionPopup::Butt
     {
       mImpl->SendSelectionToClipboard( true ); // Synchronous call to modify text
       mImpl->mOperationsPending = ALL_OPERATIONS;
+
+      // This is to reset the virtual keyboard to Upper-case
+      if( 0u == mImpl->mLogicalModel->mText.Count() )
+      {
+        NotifyImfManager();
+      }
+
       if( 0u != mImpl->mLogicalModel->mText.Count() ||
           !mImpl->IsPlaceholderAvailable() )
       {
@@ -1755,6 +1903,12 @@ bool Controller::BackspaceKeyEvent()
 
   if( removed )
   {
+    // This is to reset the virtual keyboard to Upper-case
+    if( 0u == mImpl->mLogicalModel->mText.Count() )
+    {
+      NotifyImfManager();
+    }
+
     if( 0u != mImpl->mLogicalModel->mText.Count() ||
         !mImpl->IsPlaceholderAvailable() )
     {
@@ -1770,6 +1924,25 @@ bool Controller::BackspaceKeyEvent()
   return removed;
 }
 
+void Controller::NotifyImfManager()
+{
+  if( mImpl->mEventData )
+  {
+    ImfManager imfManager = ImfManager::Get();
+
+    if( imfManager )
+    {
+      // Notifying IMF of a cursor change triggers a surrounding text request so updating it now.
+      std::string text;
+      GetText( text );
+      imfManager.SetSurroundingText( text );
+
+      imfManager.SetCursorPosition( GetLogicalCursorPosition() );
+      imfManager.NotifyCursorPosition();
+    }
+  }
+}
+
 void Controller::ShowPlaceholderText()
 {
   if( mImpl->IsPlaceholderAvailable() )
index 99c2ab0..3c6125d 100644 (file)
@@ -178,8 +178,9 @@ public:
    * @brief Set the default font family.
    *
    * @param[in] defaultFontFamily The default font family.
+   * @param[in] userDefined If set by the user
    */
-  void SetDefaultFontFamily( const std::string& defaultFontFamily );
+  void SetDefaultFontFamily( const std::string& defaultFontFamily, bool userDefined );
 
   /**
    * @brief Retrieve the default font family.
@@ -189,23 +190,67 @@ public:
   const std::string& GetDefaultFontFamily() const;
 
   /**
-   * @brief Set the default font style.
+   * @brief Sets the font's style string.
    *
-   * @param[in] defaultFontStyle The default font style.
+   * @note The style set may be changed by the underlying font system. The string is stored to be recovered.
+   *
+   * @param[in] style The font's style string.
    */
-  void SetDefaultFontStyle( const std::string& defaultFontStyle );
+  void SetDefaultFontStyle( const std::string& style );
 
   /**
-   * @brief Retrieve the default font style.
+   * @brief Retrieves the font's style.
    *
-   * @return The default font style.
+   * @return The font's style.
    */
   const std::string& GetDefaultFontStyle() const;
 
   /**
+   * @brief Sets the default font width.
+   *
+   * @param[in] width The font width.
+   */
+  void SetDefaultFontWidth( FontWidth width );
+
+  /**
+   * @brief Retrieves the default font width.
+   *
+   * @return The default font width.
+   */
+  FontWidth GetDefaultFontWidth() const;
+
+  /**
+   * @brief Sets the default font weight.
+   *
+   * @param[in] weight The font weight.
+   */
+  void SetDefaultFontWeight( FontWeight weight );
+
+  /**
+   * @brief Retrieves the default font weight.
+   *
+   * @return The default font weight.
+   */
+  FontWeight GetDefaultFontWeight() const;
+
+  /**
+   * @brief Sets the default font slant.
+   *
+   * @param[in] slant The font slant.
+   */
+  void SetDefaultFontSlant( FontSlant slant );
+
+  /**
+   * @brief Retrieves the default font slant.
+   *
+   * @return The default font slant.
+   */
+  FontSlant GetDefaultFontSlant() const;
+
+  /**
    * @brief Set the default point size.
    *
-   * @param[in] defaultFontStyle The default point size.
+   * @param[in] pointSize The default point size.
    */
   void SetDefaultPointSize( float pointSize );
 
@@ -217,6 +262,12 @@ public:
   float GetDefaultPointSize() const;
 
   /**
+   * @ brief Update the text after a font change
+   * @param[in] newDefaultFont The new font to change to
+   */
+  void UpdateAfterFontChange( std::string& newDefaultFont );
+
+  /**
    * @brief Set the text color
    *
    * @param textColor The text color
@@ -592,6 +643,11 @@ private:
   bool BackspaceKeyEvent();
 
   /**
+   * @brief Helper to notify IMF manager with surrounding text & cursor changes.
+   */
+  void NotifyImfManager();
+
+  /**
    * @brief Helper to clear font-specific data.
    */
   void ShowPlaceholderText();
index 85888b0..dbb29cd 100644 (file)
@@ -20,6 +20,7 @@
 
 // EXTERNAL INCLUDES
 #include <dali/devel-api/text-abstraction/text-abstraction-definitions.h>
+#include <dali/devel-api/text-abstraction/font-list.h>
 #include <dali/devel-api/text-abstraction/font-metrics.h>
 #include <dali/devel-api/text-abstraction/glyph-info.h>
 #include <dali/devel-api/text-abstraction/script.h>
@@ -34,6 +35,9 @@ namespace Text
 {
 
 typedef TextAbstraction::FontId             FontId;             ///< The unique identifier for a font face (generated by FontClient).
+typedef TextAbstraction::FontWidth::Type    FontWidth;          ///< The font's width.
+typedef TextAbstraction::FontWeight::Type   FontWeight;         ///< The font's weight.
+typedef TextAbstraction::FontSlant::Type    FontSlant;          ///< The font's slant.
 typedef TextAbstraction::FontMetrics        FontMetrics;        ///< The metrics for a Font expressed in 26.6 fractional pixel format.
 typedef TextAbstraction::PointSize26Dot6    PointSize26Dot6;    ///< The point size in 26.6 fractional points.
 typedef TextAbstraction::FaceIndex          FaceIndex;          ///< Used with fonts which allow several font faces.
index 99f8a8c..279e1aa 100644 (file)
@@ -77,7 +77,7 @@ std::ostream& operator<< (std::ostream& o, const Vector<FontRun>& fontRun)
     FontId id = fontRun[i].fontId;
     TextAbstraction::FontDescription fontDescription;
     fontClient.GetDescription( id, fontDescription );
-    o << "ID:" << id << ", " << fontDescription.family << " style:" << fontDescription.style << " size:" << (fontClient.GetPointSize(id) / 64);
+    o << "ID:" << id << ", " << fontDescription.family << " width: " << fontDescription.width << " weight: " << fontDescription.weight << " slant: " << fontDescription.slant <<  " size:" << (fontClient.GetPointSize(id) / 64);
 
     if( i+1 < fontRun.Count() )
     {
index 9f807ac..08ce8ce 100644 (file)
@@ -32,6 +32,10 @@ namespace Internal DALI_INTERNAL
 {
 class AccessibilityManager;
 }
+/**
+ * @addtogroup dali-toolkit-accessibility-manager
+ * @{
+ */
 
 /**
  * @brief Manages registration of actors in a accessibility focus chain and changing the
@@ -750,6 +754,9 @@ public:
 
 }; // class AccessibilityManager
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 1f34eb5..5a9d56c 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class Alignment;
 }
+/**
+ * @addtogroup dali-toolkit-controls-alignment
+ * @{
+ */
 
 /**
  * @brief Alignment is a container which provides an easy way to align other actors inside its boundary.
@@ -229,6 +233,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL Alignment( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 9c0eba0..f5c2701 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class Button;
 }
+/**
+ * @addtogroup dali-toolkit-controls-buttons
+ * @{
+ */
 
 /**
  * @brief Button is a base class for different kind of buttons.
@@ -420,6 +424,9 @@ public: // Not intended for application developers
   DALI_INTERNAL Button( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 5798ef3..357c3e1 100644 (file)
@@ -33,6 +33,10 @@ namespace Internal DALI_INTERNAL
 {
 class CheckBoxButton;
 }
+/**
+ * @addtogroup dali-toolkit-controls-buttons
+ * @{
+ */
 
 /**
  * CheckBoxButton provides a check box button which user can check or uncheck.
@@ -106,6 +110,9 @@ public: // Not intended for application developers
   DALI_INTERNAL CheckBoxButton( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 0e53a9c..8ebbf58 100644 (file)
@@ -35,6 +35,10 @@ namespace Internal DALI_INTERNAL
 
 class PushButton;
 }
+/**
+ * @addtogroup dali-toolkit-controls-buttons
+ * @{
+ */
 
 /**
  * @brief A PushButton changes its appearance when is pressed and returns to its original when is released.
@@ -193,6 +197,9 @@ public: // Not intended for application developers
   DALI_INTERNAL PushButton( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 20ec386..7c04b42 100644 (file)
@@ -35,6 +35,10 @@ namespace Internal DALI_INTERNAL
 
 class RadioButton;
 }
+/**
+ * @addtogroup dali-toolkit-controls-buttons
+ * @{
+ */
 
 /**
  * @brief A RadioButton provides a radio button which two states \e selected or \e unselected.
@@ -124,6 +128,9 @@ class DALI_IMPORT_API RadioButton: public Button
   DALI_INTERNAL RadioButton( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 1a55cf2..ff5732c 100644 (file)
@@ -23,6 +23,11 @@ namespace Dali
 {
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls
+ * @{
+ */
+
 enum ControlDepthIndexRanges
 {
     BACKGROUND_DEPTH_INDEX    = static_cast<int>( -Dali::Layer::TREE_DEPTH_MULTIPLIER * 0.1f ),
@@ -30,6 +35,9 @@ enum ControlDepthIndexRanges
     DECORATION_DEPTH_INDEX    = static_cast<int>( Dali::Layer::TREE_DEPTH_MULTIPLIER * 0.1f )
 };
 
+/**
+ * @}
+ */
 }
 
 }
index 1ce94b7..b8ae6bb 100644 (file)
@@ -35,11 +35,15 @@ namespace Dali
 
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls
+ * @{
+ */
+
 class StyleManager;
 
 namespace Internal
 {
-
 /**
  * @brief This is the internal base class for all controls.
  *
@@ -629,6 +633,9 @@ DALI_IMPORT_API const Internal::Control& GetImplementation( const Dali::Toolkit:
 
 } // namespace Internal
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 1e4d74d..35587f9 100644 (file)
@@ -40,6 +40,10 @@ namespace Internal
 {
 class Control;
 }
+/**
+ * @addtogroup dali-toolkit-controls
+ * @{
+ */
 
 /**
  * @brief Control is the base class for all controls.
@@ -403,6 +407,9 @@ public: // Templates for Deriving Classes
 
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 23b00e2..6c88108 100644 (file)
@@ -27,7 +27,6 @@ namespace Dali
 
 namespace Toolkit
 {
-
 /**
  * @brief Creates a Dali::ImageActor with a solid color, optionally it creates a border.
  *
@@ -40,7 +39,6 @@ namespace Toolkit
  * @return a handle to the new ImageActor
  */
 DALI_IMPORT_API ImageActor CreateSolidColorActor( const Vector4& color, bool border = false, const Vector4& borderColor = Color::WHITE, const unsigned int borderSize = 1 );
-
 } // namespace Toolkit
 
 } // namespace Dali
index e6a32b8..a2c5ea6 100644 (file)
@@ -49,6 +49,10 @@ class GaussianBlurView;
 class BloomView;
 
 } // namespace Internal
+/**
+ * @addtogroup dali-toolkit-controls-gaussian-blur-view
+ * @{
+ */
 
 /**
  *
@@ -274,6 +278,9 @@ public:
 
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 821a981..fe6d7b1 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class ImageView;
 }
+/**
+ * @addtogroup dali-toolkit-controls-image-view
+ * @{
+ */
 
 /**
  *
@@ -157,6 +161,9 @@ public: // Not intended for application developers
 
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 5da66a5..3f1ad10 100755 (executable)
@@ -33,6 +33,10 @@ namespace Internal DALI_INTERNAL
 
 class ScrollBar;
 }
+/**
+ * @addtogroup dali-toolkit-controls-scroll-bar
+ * @{
+ */
 
 /**
  * ScrollBar is a UI component that can be linked to the scrollable objects
@@ -323,11 +327,11 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL ScrollBar( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
 
-/**
- * @}
- */
 #endif // __DALI_TOOLKIT_SCROLL_BAR_H__
index 6f4eb00..8299d84 100644 (file)
@@ -26,6 +26,10 @@ namespace Dali
 
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls-item-view
+ * @{
+ */
 
 namespace DefaultItemLayout
 {
@@ -49,6 +53,9 @@ DALI_IMPORT_API ItemLayoutPtr New( Type type );
 
 } // namespace DefaultItemLayout
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index d018716..84ef7b7 100644 (file)
@@ -26,6 +26,10 @@ namespace Dali
 
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls-item-view
+ * @{
+ */
 
 /**
  * @brief ItemFactory is for providing actors to ItemView.
@@ -77,6 +81,9 @@ public:
   }
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index cc1a2ae..9302e8a 100644 (file)
@@ -30,6 +30,10 @@ namespace Dali
 
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls-item-view
+ * @{
+ */
 
 class ItemLayout;
 
@@ -346,12 +350,27 @@ protected:
    */
   DALI_IMPORT_API ItemLayout();
 
+private:
+
+  /**
+   * Don't allow copy constructor
+   */
+  ItemLayout( const ItemLayout& handle );
+
+  /**
+   * Don't allow copy operator
+   */
+  ItemLayout& operator=( const ItemLayout& handle );
+
 protected:
 
   struct Impl;
   Impl* mImpl;
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 7772d45..7388bfa 100644 (file)
@@ -28,6 +28,10 @@ namespace Dali
 
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls-item-view
+ * @{
+ */
 
 typedef unsigned int ItemId; ///< Unique identity for each item in the view.
 
@@ -44,6 +48,9 @@ typedef ItemContainer::const_iterator ConstItemIter;
 class ItemView;
 class ItemLayout;
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index cb0859d..2790194 100644 (file)
@@ -34,6 +34,10 @@ namespace Internal DALI_INTERNAL
 {
 class ItemView;
 }
+/**
+ * @addtogroup dali-toolkit-controls-item-view
+ * @{
+ */
 
 class ItemFactory;
 class ItemLayout;
@@ -462,6 +466,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL ItemView( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 40a1f45..15a29d6 100644 (file)
@@ -31,6 +31,10 @@ class PropertyInput;
 
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls-scroll-view
+ * @{
+ */
 
 // Constraints ////////////////////////////////////////////////////////////////////////////////////
 
@@ -52,6 +56,9 @@ DALI_IMPORT_API void MoveActorConstraint( Vector3& current, const PropertyInputC
  */
 DALI_IMPORT_API void WrapActorConstraint( Vector3& position, const PropertyInputContainer& inputs );
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 1295861..4af0442 100644 (file)
@@ -37,6 +37,10 @@ namespace Internal DALI_INTERNAL
 class ScrollViewEffect;
 class ScrollViewWobbleEffect;
 }
+/**
+ * @addtogroup dali-toolkit-controls-scroll-view
+ * @{
+ */
 
 class ScrollView;
 class ScrollViewEffect;
@@ -73,6 +77,9 @@ public: // Not intended for application developers
 
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index de7c649..af59f83 100644 (file)
@@ -34,6 +34,10 @@ namespace Internal DALI_INTERNAL
 {
 class ScrollViewPagePathEffect;
 }
+/**
+ * @addtogroup dali-toolkit-controls-scroll-view
+ * @{
+ */
 
 /**
  * ScrollView Page Path Effect.
@@ -103,6 +107,9 @@ protected:
 
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index fb9d5cb..508b3d2 100644 (file)
@@ -34,6 +34,10 @@ namespace Internal DALI_INTERNAL
 {
 class ScrollView;
 }
+/**
+ * @addtogroup dali-toolkit-controls-scroll-view
+ * @{
+ */
 
 /**
  * @brief How axes/rotation or scale are clamped
@@ -1136,6 +1140,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL ScrollView( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index b262212..d43a29a 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class Scrollable;
 }
+/**
+ * @addtogroup dali-toolkit-controls-scrollable
+ * @{
+ */
 
 /**
  * @brief Base class for derived Scrollables that contains actors that can be scrolled manually
@@ -229,6 +233,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL Scrollable( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index c3f0545..eb03b9e 100644 (file)
@@ -35,6 +35,10 @@ namespace Internal DALI_INTERNAL
 {
 class TableView;
 }
+/**
+ * @addtogroup dali-toolkit-controls-table-view
+ * @{
+ */
 
 /**
  * @brief TableView is a layout container for aligning child actors in a grid like layout.
@@ -441,6 +445,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL TableView( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index eacee82..7b9d11b 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class TextField;
 }
+/**
+ * @addtogroup dali-toolkit-controls-text-controls
+ * @{
+ */
 
 /**
  * @brief A control which provides a single-line editable text field.
@@ -67,7 +71,7 @@ public:
       PLACEHOLDER_TEXT,                         ///< name "placeholder-text",                    The text to display when the TextField is empty and inactive,             type STRING
       PLACEHOLDER_TEXT_FOCUSED,                 ///< name "placeholder-text-focused",            The text to display when the TextField is empty with key-input focus,     type STRING
       FONT_FAMILY,                              ///< name "font-family",                         The requested font family,                                                type STRING
-      FONT_STYLE,                               ///< name "font-style",                          The requested font style e.g. Regular/Italic,                             type STRING
+      FONT_STYLE,                               ///< name "font-style",                          The requested font style,                                                 type STRING
       POINT_SIZE,                               ///< name "point-size",                          The size of font in points,                                               type FLOAT
       MAX_LENGTH,                               ///< name "max-length"                           The maximum number of characters that can be inserted,                    type INTEGER
       EXCEED_POLICY,                            ///< name "exceed-policy"                        Specifies how the text is truncated when it does not fit,                 type INTEGER
@@ -201,6 +205,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL TextField( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index b11bd13..7669b05 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class TextLabel;
 }
+/**
+ * @addtogroup dali-toolkit-controls-text-controls
+ * @{
+ */
 
 /**
  * @brief A control which renders a short text string.
@@ -60,7 +64,7 @@ public:
       RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "rendering-backend",    The type or rendering e.g. bitmap-based,          type INT
       TEXT,                                     ///< name "text",                 The text to display in UTF-8 format,              type STRING
       FONT_FAMILY,                              ///< name "font-family",          The requested font family,                        type STRING
-      FONT_STYLE,                               ///< name "font-style",           The requested font style e.g. Regular/Italic,     type STRING
+      FONT_STYLE,                               ///< name "font-style",           The requested font style,                         type STRING
       POINT_SIZE,                               ///< name "point-size",           The size of font in points,                       type FLOAT
       MULTI_LINE,                               ///< name "multi-line",           The single-line or multi-line layout option,      type BOOLEAN
       HORIZONTAL_ALIGNMENT,                     ///< name "horizontal-alignment", The line horizontal alignment,                    type STRING,  values "BEGIN", "CENTER", "END"
@@ -144,6 +148,9 @@ public: // Not intended for application developers
   explicit DALI_INTERNAL TextLabel( Dali::Internal::CustomActor* internal );
 };
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index a0b3e1e..56709e4 100644 (file)
@@ -31,7 +31,7 @@ namespace Toolkit
 
 const unsigned int TOOLKIT_MAJOR_VERSION = 1;
 const unsigned int TOOLKIT_MINOR_VERSION = 1;
-const unsigned int TOOLKIT_MICRO_VERSION = 1;
+const unsigned int TOOLKIT_MICRO_VERSION = 2;
 const char * const TOOLKIT_BUILD_DATE    = __DATE__ " " __TIME__;
 
 #ifdef DEBUG_ENABLED
index 5582ba3..ff678a9 100644 (file)
 
 namespace Dali
 {
-
 /**
  * @brief DALi Toolkit namespace.
  */
 namespace Toolkit
 {
+/**
+ * @addtogroup dali-toolkit-controls
+ * @{
+ */
 
 /**
  * @brief Control Orientation namespace.
@@ -65,6 +68,9 @@ DALI_IMPORT_API bool IsVertical(ControlOrientation::Type orientation);
  */
 DALI_IMPORT_API bool IsHorizontal(ControlOrientation::Type orientation);
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 3383a47..3b6b33f 100644 (file)
@@ -31,6 +31,10 @@ namespace Internal DALI_INTERNAL
 {
 class KeyboardFocusManager;
 }
+/**
+ * @addtogroup dali-toolkit-focus-manager
+ * @{
+ */
 
 /**
  * @brief Provides the functionality of handling keyboard navigation
@@ -273,6 +277,9 @@ public: // Signals
 
 }; // class KeyboardFocusManager
 
+/**
+ * @}
+ */
 } // namespace Toolkit
 
 } // namespace Dali
index 660a392..35531e4 100644 (file)
@@ -110,7 +110,7 @@ distributing this software or its derivatives.
       "label":
       {
         "point-size":8,
-        "font-style":"Light"
+        "font-style":"{\"weight\":\"light\"}"
       }
     },
     "scrollview":
index 7b4def1..935744f 100644 (file)
@@ -110,7 +110,7 @@ distributing this software or its derivatives.
       "label":
       {
         "point-size":8,
-        "font-style":"Light"
+        "font-style":"{\"weight\":\"light\"}"
       }
     },
     "scrollview":
diff --git a/doc/dali-toolkit-doc.h b/doc/dali-toolkit-doc.h
new file mode 100644 (file)
index 0000000..2cb0f1a
--- /dev/null
@@ -0,0 +1,75 @@
+#ifndef __DALI_TOOLKIT_DOC_H__
+#define __DALI_TOOLKIT_DOC_H__
+
+/**
+ * @defgroup dali DALi
+ * @ingroup CAPI_UI_FRAMEWORK
+ *
+ * @brief DALi is a cross-platform 3D UI Toolkit for embedded systems.
+ *
+ * @section dali-overview Overview
+ * DALi's 3D user interface engine enables you to create rich and high-performance
+ * UI applications. DALi is based on OpenGL ES 2.0, but provides a clean
+ * cross-platform C++ framework.
+ * This means that you can use high-level DALi APIs instead of accessing
+ * low-level OpenGL APIs directly.
+ * <ul>
+ * <li>DALi Core: This module provides scene graph-based rendering, animation, and event handling.</li>
+ * <li>DALi Adaptor: This module is a platform adaptation layer.</li>
+ * <li>DALi Toolkit: This module provides UI components and various effects on top of the dali-core.</li>
+ * </ul>
+ *
+ * @defgroup dali-toolkit DALi Toolkit
+ * @ingroup dali
+ *
+ * @brief This module provides UI components and various effects on top of the dali-core.
+ *
+ * @{
+ *   @defgroup dali-toolkit-accessibility-manager Accessibility Manager
+ *   @brief AccessibilityManager manages a accessibility focus chain.
+
+ *   @defgroup dali-toolkit-controls Controls
+ *   @brief Controls are interactive components for layouting the user interface.
+
+ *   @{
+ *     @defgroup dali-toolkit-controls-alignment Alignment
+ *     @brief Alignment is a container which provides an easy way to align other actors inside its boundary.
+
+ *     @defgroup dali-toolkit-controls-buttons Buttons
+ *     @brief Button is a small object on UI that you can press.
+
+ *     @defgroup dali-toolkit-controls-gaussian-blur-view Gaussian Blur View
+ *     @brief GaussianBlurView provides a render process that blurs an image.
+
+ *     @defgroup dali-toolkit-controls-image-view Image View
+ *     @brief ImageView is a control displying an image.
+
+ *     @defgroup dali-toolkit-controls-scroll-bar Scroll Bar
+ *     @brief ScrollBar control.
+
+ *     @defgroup dali-toolkit-controls-scrollable Scrollable
+ *     @brief Scrollable container controls.
+
+ *     @{
+ *       @defgroup dali-toolkit-controls-item-view Item View
+ *       @brief ItemView class is a scrollable container that can contain many items.
+
+ *       @defgroup dali-toolkit-controls-scroll-view Scroll View
+ *       @brief ScrollView class provides scrollable view which contains actors and can be scrolled automatically or manually by panning. 
+
+ *     @}
+ *     @defgroup dali-toolkit-controls-table-view Table View
+ *     @brief TableView class is a layout container for aligning child actors in a grid like layout.
+
+ *     @defgroup dali-toolkit-controls-text-controls Text Controls
+ *     @brief Controls for displaying text or text input.
+
+ *   @}
+ *   @defgroup dali-toolkit-focus-manager Focus Manager
+ *   @brief Classes for handling keyboard navigation and maintaining the two dimensional keyboard focus chain.
+
+ * @}
+ */
+
+
+#endif  /* __DALI_TOOLKIT_DOC_H__ */
diff --git a/doc/file.list b/doc/file.list
new file mode 100644 (file)
index 0000000..f9681c1
--- /dev/null
@@ -0,0 +1,3 @@
+package_doxy_files = \
+  $(package_doxy_dir)/dali-toolkit-doc.h
+
diff --git a/docs/content/shared-javascript-and-cpp-documentation/font-selection.md b/docs/content/shared-javascript-and-cpp-documentation/font-selection.md
new file mode 100644 (file)
index 0000000..348bf1b
--- /dev/null
@@ -0,0 +1,133 @@
+<!--
+/**-->
+
+# Font Selection {#font-selection}
+
+By default TextLabel or TextField will automatically select a suitable font from the platform.
+Typically fonts do not support all scripts, for example Latin fonts often do not provide Arabic glyphs.
+Therefore you should expect the text control to select different fonts for each script.
+
+Alternatively a font may be requested using either or all of FONT_FAMILY, FONT_STYLE, and POINT_SIZE properties:
+
+- FONT_FAMILY
+  Is a string with the font's family name. i.e. *FreeSerif*
+- FONT_STYLE
+  Is a json formatted string with the font's style. Possible *key, value* pairs are:
+  + *width* Modifies the space between glyphs. Possible values are:
+    - *ultra-condensed*
+    - *extra-condensed*
+    - *condensed*
+    - *semi-condensed*
+    - *normal*
+    - *semi-expanded*
+    - *expanded*
+    - *extra-expanded*
+    - *ultra-expanded*
+  + *weight* Modifies the thickness or darkness of the glyphs. Possible values are:
+    - *thin*
+    - *ultra-light*
+    - *extra-light*
+    - *light*
+    - *demi-light*
+    - *semi-light*
+    - *book*
+    - *normal*
+    - *regular*
+    - *medium*
+    - *demi-bold*
+    - *semi-bold*
+    - *bold*
+    - *ultra-bold*
+    - *extra-bold*
+    - *black*
+    - *heavy*
+    - *extra-black*
+  + *slant* Whether to use italics. Usually *italic* is a different font whilst the *oblique* has been generated by slanting the *normal* one. Possible values are:
+    - *normal*
+    - *roman* Same as *normal*
+    - *italic*
+    - *oblique*
+- POINT_SIZE
+  Is a float with the font's size in points. To get the point size from pixels, could use the formula: <em>point_size = 72 * pixels / vertical_dpi</em> where <em>vertical_dpi</em> is the device's vertical resolution in dots per inch.
+
+~~~{.cpp}
+// C++
+
+label.SetProperty( TextLabel::Property::FONT_FAMILY, "FreeSerif" );
+label.SetProperty( TextLabel::Property::FONT_STYLE,  "{\"weight\":\"bold\",\"slant\":\"italic\"}" );
+label.SetProperty( TextLabel::Property::POINT_SIZE,  12.0f );
+~~~
+
+~~~{.js}
+// JavaScript
+
+label.fontFamily = "FreeSerif";
+label.fontStyle = "{\"weight\":\"bold\",\"slant\":\"italic\"}";
+label.pointSize = 12;
+~~~
+
+However the text control will fall-back to using the default font, if the requested font does not support the required scripts.
+
+### Font Styles
+
+Setting a font size programmatically is not ideal for applications which support multiple screen resolutions etc.
+A more flexible approach is to prepare various JSON stylesheets, and request a different style for each platform:
+
+~~~{.cpp}
+// C++
+StyleManager styleManager = StyleManager::Get();
+styleManager.RequestThemeChange( "example-path/example.json" );
+~~~
+
+To change the font for standard text controls, this JSON syntax can be used:
+
+~~~{.json}
+{
+  "styles":
+  {
+    "textlabel":
+    {
+      "font-family":"FreeSerif",
+      "font-style":"{\"weight\":\"bold\",\"slant\":\"italic\"}",
+      "point-size":8
+    }
+  }
+}
+~~~
+
+However the same point-size is unlikely to be suitable for all text controls in an application.
+To set custom sizes simply set a "style name" for each case, and then provide a style override in JSON:
+
+~~~{.cpp}
+  // C++
+
+  label.SetProperty( Control::Property::STYLE_NAME, "custom" );
+~~~
+~~~{.js}
+  // JavaScript
+
+  label.styleName = "custom"';
+~~~
+
+~~~{.json}
+{
+  "styles":
+  {
+    "textlabel":
+    {
+      "font-family":"FreeSerif",
+      "font-style":"{\"weight\":\"bold\",\"slant\":\"italic\"}",
+      "point-size":8
+    },
+
+    "custom":
+    {
+      "point-size":10
+    }
+  }
+}
+~~~
+
+In the example above, standard text labels will have point-size 8, and "custom" labels will have point-size 10.
+
+*/
index 79e20ed..05bf048 100644 (file)
@@ -51,22 +51,7 @@ console.log( field.text );
 
 ### Font Selection
 
-TextField will automatically select a suitable fonts, in the same was as TextLabel.
-The preferred font can also be selected from a JSON stylesheet:
-
-~~~{.json}
-{
-  "styles":
-  {
-    "textfield":
-    {
-      "font-family":"Arial",
-      "font-style":"Regular",
-      "point-size":8
-    }
-  }
-}
-~~~
+By default TextField will automatically select a suitable font from the platform. However, a different font could be selected. See the [Font Selection](@ref font-selection) section for more details.
 
 ### Text Alignment
 
index c08af6d..1b63a42 100644 (file)
@@ -41,91 +41,7 @@ The position of the label on-screen is dependent on the parent-origin and anchor
 
 ### Font Selection
 
-By default TextLabel will automatically select a suitable font from the platform.  
-Typically fonts do not support all scripts, for example Latin fonts often do not provide Arabic glyphs.  
-Therefore you should expect TextLabel to select different fonts for each script.
-
-Alternatively a font may be requested using either or all of FONT_FAMILY, FONT_STYLE, and POINT_SIZE properties:
-
-~~~{.cpp}
-// C++
-
-label.SetProperty( TextLabel::Property::FONT_FAMILY, "HelveticaNue" );
-label.SetProperty( TextLabel::Property::FONT_STYLE,  "Regular" );
-label.SetProperty( TextLabel::Property::POINT_SIZE,  12.0f );
-~~~
-
-~~~{.js}
-// JavaScript
-
-label.fontFamily = "HelveticaNue";
-label.fontStyle = "Regular";
-label.pointSize = 12;
-~~~
-
-However the TextLabel will fall-back to using the default font, if the requested font does not support the required scripts.
-
-### Font Styles
-
-Setting a font size programmatically is not ideal for applications which support multiple screen resolutions etc.  
-A more flexible approach is to prepare various JSON stylesheets, and request a different style for each platform:  
-
-~~~{.cpp}
-// C++
-StyleManager styleManager = StyleManager::Get();
-styleManager.RequestThemeChange( "example-path/example.json" );
-~~~
-
-To change the font for standard text labels, this JSON syntax can be used:
-
-~~~{.json}
-{
-  "styles":
-  {
-    "textlabel":
-    {
-      "font-family":"Arial",
-      "font-style":"Regular",
-      "point-size":8
-    }
-  }
-}
-~~~
-
-However the same point-size is unlikely to be suitable for all labels in an application.  
-To set custom sizes simply set a "style name" for each case, and then provide a style override in JSON:
-
-~~~{.cpp}
-  // C++
-
-  label.SetProperty( Control::Property::STYLE_NAME, "custom" );
-~~~
-~~~{.js}
-  // JavaScript
-
-  label.styleName = "custom"';
-~~~
-
-~~~{.json}
-{
-  "styles":
-  {
-    "textlabel":
-    {
-      "font-family":"Arial",
-      "font-style":"Regular",
-      "point-size":8
-    },
-
-    "custom":
-    {
-      "point-size":10
-    }
-  }
-}
-~~~
-
-In the example above, standard text labels will have point-size 8, and "custom" labels will have point-size 10.  
+By default TextLabel will automatically select a suitable font from the platform. However, a different font could be selected. See the [Font Selection](@ref font-selection) section for more details.
 
 ### Text Alignment
 
index 8c28eec..8f750dd 100644 (file)
@@ -82,7 +82,7 @@ public:
       }
 
       // fire the scene create signal
-      adaptor->SceneCreated();
+      adaptor->NotifySceneCreated();
 
       mInitialized = true;
     }
index 634d8e4..5ae4f93 100644 (file)
@@ -1,6 +1,6 @@
 Name:       dali-toolkit
 Summary:    The OpenGLES Canvas Core Library Toolkit
-Version:    1.1.1
+Version:    1.1.2
 Release:    1
 Group:      System/Libraries
 License:    Apache-2.0, BSD-2.0, MIT
@@ -73,7 +73,7 @@ cd %{_builddir}/dali-toolkit-%{version}/build/tizen
 autoreconf --install
 DALI_DATA_RW_DIR="%{dali_data_rw_dir}" ; export DALI_DATA_RW_DIR
 DALI_DATA_RO_DIR="%{dali_data_ro_dir}" ; export DALI_DATA_RO_DIR
-%configure --enable-profile=%{dali_toolkit_profile} --with-style=%{dali_style_folder}
+%configure --enable-profile=%{dali_toolkit_profile} --with-style=%{dali_style_folder} --enable-i18n=yes
 make %{?jobs:-j%jobs}
 
 ##############################