[dali_1.1.35] Merge branch 'devel/master' 56/70756/1
authorNick Holland <nick.holland@partner.samsung.com>
Fri, 20 May 2016 10:18:09 +0000 (11:18 +0100)
committerNick Holland <nick.holland@partner.samsung.com>
Fri, 20 May 2016 10:18:09 +0000 (11:18 +0100)
Change-Id: I7971d40e610154e3cce808e3a409023db32edc10

60 files changed:
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/mesh-builder.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/mesh-builder.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-actor-utils.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/toolkit-style-monitor.cpp
automated-tests/src/dali-toolkit/utc-Dali-FlexContainer.cpp
automated-tests/src/dali-toolkit/utc-Dali-TextLabel.cpp
build/tizen/dali-toolkit/Makefile.am
dali-toolkit/dali-toolkit.h
dali-toolkit/devel-api/file.list
dali-toolkit/internal/accessibility-manager/accessibility-manager-impl.cpp
dali-toolkit/internal/builder/builder-impl.h
dali-toolkit/internal/controls/bubble-effect/bubble-actor.h
dali-toolkit/internal/controls/flex-container/flex-container-impl.cpp
dali-toolkit/internal/controls/flex-container/flex-container-impl.h
dali-toolkit/internal/controls/renderers/color/color-renderer.cpp
dali-toolkit/internal/controls/renderers/gradient/gradient-renderer.cpp
dali-toolkit/internal/controls/renderers/image/image-renderer.cpp
dali-toolkit/internal/controls/renderers/renderer-factory-cache.cpp
dali-toolkit/internal/controls/renderers/renderer-factory-cache.h
dali-toolkit/internal/controls/renderers/svg/nanosvg/nanosvg.cc
dali-toolkit/internal/controls/renderers/svg/nanosvg/nanosvg.h
dali-toolkit/internal/controls/renderers/svg/nanosvg/nanosvgrast.cc
dali-toolkit/internal/controls/renderers/svg/svg-renderer.cpp
dali-toolkit/internal/controls/text-controls/text-label-impl.cpp
dali-toolkit/internal/controls/text-controls/text-label-impl.h
dali-toolkit/internal/feedback/feedback-style.cpp
dali-toolkit/internal/file.list
dali-toolkit/internal/focus-manager/keyinput-focus-manager-impl.cpp
dali-toolkit/internal/text/layouts/layout-engine.cpp
dali-toolkit/internal/text/rendering/atlas/text-atlas-renderer.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-scroller-interface.cpp [new file with mode: 0644]
dali-toolkit/internal/text/text-scroller-interface.h [new file with mode: 0644]
dali-toolkit/internal/text/text-scroller.cpp [new file with mode: 0644]
dali-toolkit/internal/text/text-scroller.h [new file with mode: 0644]
dali-toolkit/internal/text/text-view-interface.h
dali-toolkit/internal/text/visual-model-impl.h
dali-toolkit/internal/transition-effects/cube-transition-cross-effect-impl.cpp
dali-toolkit/internal/transition-effects/cube-transition-effect-impl.cpp
dali-toolkit/internal/transition-effects/cube-transition-wave-effect-impl.cpp
dali-toolkit/public-api/controls/flex-container/flex-container.cpp [moved from dali-toolkit/devel-api/controls/flex-container/flex-container.cpp with 95% similarity]
dali-toolkit/public-api/controls/flex-container/flex-container.h [moved from dali-toolkit/devel-api/controls/flex-container/flex-container.h with 68% similarity]
dali-toolkit/public-api/controls/text-controls/text-label.h
dali-toolkit/public-api/dali-toolkit-version.cpp
dali-toolkit/public-api/file.list
dali-toolkit/styles/480x800/dali-toolkit-default-theme.json
dali-toolkit/styles/720x1280/dali-toolkit-default-theme.json
docs/content/images/text-controls/AutoScroll.gif [new file with mode: 0644]
docs/content/shared-javascript-and-cpp-documentation/flex-container.md
docs/content/shared-javascript-and-cpp-documentation/text-auto-scrolling.md [new file with mode: 0644]
docs/content/shared-javascript-and-cpp-documentation/text-label.md
packaging/dali-toolkit.spec
plugins/dali-script-v8/src/module-loader/module-loader.cpp
plugins/dali-script-v8/src/object/handle-wrapper.cpp
plugins/dali-script-v8/src/object/property-value-wrapper.cpp
plugins/dali-script-v8/src/object/property-value-wrapper.h
plugins/dali-script-v8/src/utils/v8-utils.cpp
plugins/dali-script-v8/src/utils/v8-utils.h

index 5b127c7..4cc72bd 100644 (file)
@@ -28,6 +28,7 @@ TextureSet CreateTextureSet()
 {
   return TextureSet::New();
 }
+
 TextureSet CreateTextureSet( Image image )
 {
   TextureSet textureSet = TextureSet::New();
@@ -45,32 +46,4 @@ PropertyBuffer CreatePropertyBuffer()
   return vertexData;
 }
 
-Geometry CreateQuadGeometry(void)
-{
-  PropertyBuffer vertexData = CreatePropertyBuffer();
-  return CreateQuadGeometryFromBuffer( vertexData );
-}
-
-Geometry CreateQuadGeometryFromBuffer( PropertyBuffer vertexData )
-{
-  const float halfQuadSize = .5f;
-  struct TexturedQuadVertex { Vector2 position; Vector2 textureCoordinates; };
-  TexturedQuadVertex texturedQuadVertexData[4] = {
-    { Vector2(-halfQuadSize, -halfQuadSize), Vector2(0.f, 0.f) },
-    { Vector2( halfQuadSize, -halfQuadSize), Vector2(1.f, 0.f) },
-    { Vector2(-halfQuadSize,  halfQuadSize), Vector2(0.f, 1.f) },
-    { Vector2( halfQuadSize,  halfQuadSize), Vector2(1.f, 1.f) } };
-  vertexData.SetData(texturedQuadVertexData, 4);
-
-  unsigned short indexData[6] = { 0, 3, 1, 0, 2, 3 };
-
-  Geometry geometry = Geometry::New();
-  geometry.AddVertexBuffer( vertexData );
-  geometry.SetIndexBuffer( indexData, sizeof(indexData)/sizeof(indexData[0]) );
-
-  return geometry;
-}
-
-
-
 } // namespace Dali
index bf5f6a6..391bcc4 100644 (file)
@@ -30,8 +30,6 @@ namespace Dali
 Shader CreateShader();
 TextureSet CreateTextureSet();
 TextureSet CreateTextureSet( Image image );
-Geometry CreateQuadGeometry();
-Geometry CreateQuadGeometryFromBuffer( PropertyBuffer vertexData );
 PropertyBuffer CreatePropertyBuffer();
 
 }
index 2f833c6..fb50bf5 100644 (file)
@@ -67,7 +67,7 @@ Actor CreateRenderableActor( Image texture )
 Actor CreateRenderableActor( Image texture, const std::string& vertexShader, const std::string& fragmentShader )
 {
   // Create the geometry
-  Geometry geometry = CreateQuadGeometry();
+  Geometry geometry = Geometry::QUAD();
 
   // Create Shader
   Shader shader = Shader::New( vertexShader, fragmentShader );
index 3d85457..a7e0b46 100644 (file)
  *
  */
 
+// HEADER
 #include "toolkit-style-monitor.h"
 
+// EXTERNAL INCLUDES
 #include <dali/public-api/common/dali-common.h>
+#include <dali/public-api/common/vector-wrapper.h>
 #include <dali/public-api/object/base-object.h>
 #include <dali/public-api/signals/dali-signal.h>
 
index a2009d0..b92e8e7 100644 (file)
@@ -19,7 +19,6 @@
 #include <stdlib.h>
 #include <dali-toolkit-test-suite-utils.h>
 #include <dali-toolkit/dali-toolkit.h>
-#include <dali-toolkit/devel-api/controls/flex-container/flex-container.h>
 
 using namespace Dali;
 using namespace Toolkit;
@@ -43,6 +42,9 @@ const char* const PROPERTY_NAME_FLEX_WRAP = "flexWrap";
 const char* const PROPERTY_NAME_JUSTIFY_CONTENT = "justifyContent";
 const char* const PROPERTY_NAME_ALIGN_ITEMS = "alignItems";
 const char* const PROPERTY_NAME_ALIGN_CONTENT =  "alignContent";
+const char* const CHILD_PROPERTY_NAME_FLEX = "flex";
+const char* const CHILD_PROPERTY_NAME_ALIGN_SELF = "alignSelf";
+const char* const CHILD_PROPERTY_NAME_FLEX_MARGIN =  "flexMargin";
 
 } // namespace
 
@@ -145,6 +147,18 @@ int UtcDaliToolkitFlexContainerSetPropertyP(void)
   FlexContainer flexContainer = FlexContainer::New();
   DALI_TEST_CHECK( flexContainer );
 
+  // Add flex container to the stage
+  Stage::GetCurrent().Add( flexContainer );
+
+  // Create two actors and add them to the container
+  Actor actor1 = Actor::New();
+  Actor actor2 = Actor::New();
+  DALI_TEST_CHECK( actor1 );
+  DALI_TEST_CHECK( actor2 );
+
+  flexContainer.Add(actor1);
+  flexContainer.Add(actor2);
+
   // Check content direction property.
   flexContainer.SetProperty( FlexContainer::Property::CONTENT_DIRECTION, FlexContainer::RTL );
   DALI_TEST_EQUALS( (FlexContainer::ContentDirection)flexContainer.GetProperty<int>( FlexContainer::Property::CONTENT_DIRECTION ), FlexContainer::RTL, TEST_LOCATION );
@@ -172,3 +186,37 @@ int UtcDaliToolkitFlexContainerSetPropertyP(void)
   END_TEST;
 }
 
+int UtcDaliToolkitFlexContainerSetChildPropertyP(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline(" UtcDaliToolkitFlexContainerSetChildPropertyP");
+  FlexContainer flexContainer = FlexContainer::New();
+  DALI_TEST_CHECK( flexContainer );
+
+  // Add flex container to the stage
+  Stage::GetCurrent().Add( flexContainer );
+
+  // Create an actor and add it to the container
+  Actor actor = Actor::New();
+  DALI_TEST_CHECK( actor );
+
+  flexContainer.Add(actor);
+
+  // Check flex child property.
+  actor.SetProperty( FlexContainer::ChildProperty::FLEX, 2.0f );
+  DALI_TEST_EQUALS( actor.GetProperty<float>( FlexContainer::ChildProperty::FLEX ), 2.0f, TEST_LOCATION );
+  DALI_TEST_CHECK( actor.GetPropertyIndex( CHILD_PROPERTY_NAME_FLEX ) == FlexContainer::ChildProperty::FLEX );
+
+  // Check align self child property.
+  actor.SetProperty( FlexContainer::ChildProperty::ALIGN_SELF, FlexContainer::ALIGN_FLEX_END );
+  DALI_TEST_EQUALS( (FlexContainer::Alignment)actor.GetProperty<int>( FlexContainer::ChildProperty::ALIGN_SELF ), FlexContainer::ALIGN_FLEX_END, TEST_LOCATION );
+  DALI_TEST_CHECK( actor.GetPropertyIndex( CHILD_PROPERTY_NAME_ALIGN_SELF ) == FlexContainer::ChildProperty::ALIGN_SELF );
+
+  // Check flex margin child property.
+  actor.SetProperty( FlexContainer::ChildProperty::FLEX_MARGIN, Vector4( 10.0f, 10.0f, 10.0f, 10.0f ) );
+  DALI_TEST_EQUALS( actor.GetProperty<Vector4>( FlexContainer::ChildProperty::FLEX_MARGIN ), Vector4( 10.0f, 10.0f, 10.0f, 10.0f ), TEST_LOCATION );
+  DALI_TEST_CHECK( actor.GetPropertyIndex( CHILD_PROPERTY_NAME_FLEX_MARGIN ) == FlexContainer::ChildProperty::FLEX_MARGIN );
+
+  END_TEST;
+}
+
index 9378648..08f085d 100644 (file)
@@ -51,6 +51,10 @@ const char* const PROPERTY_NAME_UNDERLINE_ENABLED = "underlineEnabled";
 const char* const PROPERTY_NAME_UNDERLINE_COLOR = "underlineColor";
 const char* const PROPERTY_NAME_UNDERLINE_HEIGHT = "underlineHeight";
 const char* const PROPERTY_NAME_ENABLE_MARKUP = "enableMarkup";
+const char* const PROPERTY_NAME_ENABLE_AUTO_SCROLL = "enableAutoScroll";
+const char* const PROPERTY_NAME_ENABLE_AUTO_SCROLL_SPEED = "autoScrollSpeed";
+const char* const PROPERTY_NAME_ENABLE_AUTO_SCROLL_LOOPS = "autoScrollLoopCount";
+const char* const PROPERTY_NAME_ENABLE_AUTO_SCROLL_GAP = "autoScrollGap";
 
 const int DEFAULT_RENDERING_BACKEND = Dali::Toolkit::Text::DEFAULT_RENDERING_BACKEND;
 
@@ -152,6 +156,10 @@ int UtcDaliToolkitTextLabelGetPropertyP(void)
   DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_UNDERLINE_COLOR ) == TextLabel::Property::UNDERLINE_COLOR );
   DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_UNDERLINE_HEIGHT) == TextLabel::Property::UNDERLINE_HEIGHT );
   DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_ENABLE_MARKUP) == TextLabel::Property::ENABLE_MARKUP );
+  DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_ENABLE_AUTO_SCROLL ) == TextLabel::Property::ENABLE_AUTO_SCROLL );
+  DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_ENABLE_AUTO_SCROLL_SPEED ) == TextLabel::Property::AUTO_SCROLL_SPEED );
+  DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_ENABLE_AUTO_SCROLL_LOOPS ) == TextLabel::Property::AUTO_SCROLL_LOOP_COUNT );
+  DALI_TEST_CHECK( label.GetPropertyIndex( PROPERTY_NAME_ENABLE_AUTO_SCROLL_GAP ) == TextLabel::Property::AUTO_SCROLL_GAP );
 
   END_TEST;
 }
@@ -218,6 +226,20 @@ int UtcDaliToolkitTextLabelSetPropertyP(void)
   label.SetProperty( TextLabel::Property::ENABLE_MARKUP, true );
   DALI_TEST_CHECK( label.GetProperty<bool>( TextLabel::Property::ENABLE_MARKUP ) );
 
+  // Check autoscroll properties
+  const int SCROLL_SPEED = 80;
+  const int SCROLL_LOOPS = 4;
+  const float SCROLL_GAP = 50.0f;
+  label.SetProperty( TextLabel::Property::MULTI_LINE, false ); // Autoscroll only supported in single line
+  DALI_TEST_CHECK( !label.GetProperty<bool>( TextLabel::Property::ENABLE_AUTO_SCROLL ) );
+  label.SetProperty( TextLabel::Property::ENABLE_AUTO_SCROLL, true );
+  DALI_TEST_CHECK( label.GetProperty<bool>( TextLabel::Property::ENABLE_AUTO_SCROLL ) );
+  label.SetProperty( TextLabel::Property::AUTO_SCROLL_SPEED, SCROLL_SPEED );
+  DALI_TEST_EQUALS( SCROLL_SPEED, label.GetProperty<int>( TextLabel::Property::AUTO_SCROLL_SPEED ), TEST_LOCATION );
+  label.SetProperty( TextLabel::Property::AUTO_SCROLL_LOOP_COUNT, SCROLL_LOOPS );
+  DALI_TEST_EQUALS( SCROLL_LOOPS, label.GetProperty<int>( TextLabel::Property::AUTO_SCROLL_LOOP_COUNT ), TEST_LOCATION );
+  label.SetProperty( TextLabel::Property::AUTO_SCROLL_GAP, SCROLL_GAP );
+  DALI_TEST_EQUALS( SCROLL_GAP, label.GetProperty<float>( TextLabel::Property::AUTO_SCROLL_GAP ), TEST_LOCATION );
   END_TEST;
 }
 
@@ -321,3 +343,32 @@ int UtcDaliToolkitTextLabelVectorBasedP(void)
   END_TEST;
 }
 
+int UtcDaliToolkitTextlabelScrollingP(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline(" UtcDaliToolkitTextLabelScrollingP");
+  TextLabel label = TextLabel::New("Some text to scroll");
+  DALI_TEST_CHECK( label );
+  // Avoid a crash when core load gl resources.
+  application.GetGlAbstraction().SetCheckFramebufferStatusResult( GL_FRAMEBUFFER_COMPLETE );
+  Stage::GetCurrent().Add( label );
+  // Turn on all the effects
+  label.SetProperty( TextLabel::Property::MULTI_LINE, false );
+  label.SetProperty(  TextLabel::Property::AUTO_SCROLL_GAP, 50.0f );
+  label.SetProperty(  TextLabel::Property::AUTO_SCROLL_LOOP_COUNT, 3 );
+  label.SetProperty(  TextLabel::Property::AUTO_SCROLL_SPEED, 80.0f);
+
+  try
+  {
+    // Render some text with the shared atlas backend
+    label.SetProperty(  TextLabel::Property::ENABLE_AUTO_SCROLL, true );
+    application.SendNotification();
+    application.Render();
+  }
+  catch( ... )
+  {
+    tet_result(TET_FAIL);
+  }
+
+  END_TEST;
+}
index f967eb5..75aa867 100644 (file)
@@ -98,7 +98,6 @@ develapicontrolsdir =           $(develapidir)/controls
 develapibloomviewdir =          $(develapicontrolsdir)/bloom-view
 develapibubbleemitterdir =      $(develapicontrolsdir)/bubble-effect
 develapieffectsviewdir =        $(develapicontrolsdir)/effects-view
-develapiflexcontainerdir =      $(develapicontrolsdir)/flex-container
 develapimagnifierdir =          $(develapicontrolsdir)/magnifier
 develapirendererfactorydir =    $(develapicontrolsdir)/renderer-factory
 develapipopupdir =              $(develapicontrolsdir)/popup
@@ -119,7 +118,6 @@ develapibloomview_HEADERS =         $(devel_api_bloom_view_header_files)
 develapibubbleemitter_HEADERS =     $(devel_api_bubble_emitter_header_files)
 develapibuilder_HEADERS =           $(devel_api_builder_header_files)
 develapieffectsview_HEADERS =       $(devel_api_effects_view_header_files)
-develapiflexcontainer_HEADERS =     $(devel_api_flex_container_header_files)
 develapifocusmanager_HEADERS =      $(devel_api_focus_manager_header_files)
 develapiimageatlas_HEADERS =        $(devel_api_image_atlas_header_files)
 develapimagnifier_HEADERS =         $(devel_api_magnifier_header_files)
@@ -141,6 +139,7 @@ publicapiaccessibilitymanagerdir = $(publicapidir)/accessibility-manager
 publicapialignmentdir =            $(publicapicontrolsdir)/alignment
 publicapibuttonsdir =              $(publicapicontrolsdir)/buttons
 publicapidefaultcontrolsdir =      $(publicapicontrolsdir)/default-controls
+publicapiflexcontainerdir =        $(publicapicontrolsdir)/flex-container
 publicapigaussianblurviewdir =     $(publicapicontrolsdir)/gaussian-blur-view
 publicapiimageviewdir =            $(publicapicontrolsdir)/image-view
 publicapimodel3dviewdir =          $(publicapicontrolsdir)/model3d-view
@@ -162,6 +161,7 @@ publicapiaccessibilitymanager_HEADERS = $(public_api_accessibility_manager_heade
 publicapialignment_HEADERS =            $(public_api_alignment_header_files)
 publicapibuttons_HEADERS =              $(public_api_buttons_header_files)
 publicapidefaultcontrols_HEADERS =      $(public_api_default_controls_header_files)
+publicapiflexcontainer_HEADERS =        $(public_api_flex_container_header_files)
 publicapigaussianblurview_HEADERS =     $(public_api_gaussian_blur_view_header_files)
 publicapiimageview_HEADERS =            $(public_api_image_view_header_files)
 publicapiitemview_HEADERS =             $(public_api_item_view_header_files)
index 36484f1..637d534 100644 (file)
@@ -29,6 +29,7 @@
 #include <dali-toolkit/public-api/controls/control-impl.h>
 #include <dali-toolkit/public-api/controls/control.h>
 #include <dali-toolkit/public-api/controls/default-controls/solid-color-actor.h>
+#include <dali-toolkit/public-api/controls/flex-container/flex-container.h>
 #include <dali-toolkit/public-api/controls/gaussian-blur-view/gaussian-blur-view.h>
 #include <dali-toolkit/public-api/controls/image-view/image-view.h>
 #include <dali-toolkit/public-api/controls/model3d-view/model3d-view.h>
index f28fa71..e6b7576 100755 (executable)
@@ -7,7 +7,6 @@ devel_api_src_files = \
   $(devel_api_src_dir)/controls/bloom-view/bloom-view.cpp \
   $(devel_api_src_dir)/controls/bubble-effect/bubble-emitter.cpp \
   $(devel_api_src_dir)/controls/effects-view/effects-view.cpp \
-  $(devel_api_src_dir)/controls/flex-container/flex-container.cpp \
   $(devel_api_src_dir)/controls/magnifier/magnifier.cpp \
   $(devel_api_src_dir)/controls/popup/confirmation-popup.cpp \
   $(devel_api_src_dir)/controls/popup/popup.cpp \
@@ -47,9 +46,6 @@ devel_api_builder_header_files = \
 devel_api_effects_view_header_files = \
   $(devel_api_src_dir)/controls/effects-view/effects-view.h
 
-devel_api_flex_container_header_files = \
-  $(devel_api_src_dir)/controls/flex-container/flex-container.h
-
 devel_api_magnifier_header_files = \
   $(devel_api_src_dir)/controls/magnifier/magnifier.h
 
index a3eac2c..0212161 100644 (file)
@@ -1392,27 +1392,28 @@ Toolkit::AccessibilityManager::FocusedActorActivatedSignalType& AccessibilityMan
 
 bool AccessibilityManager::DoConnectSignal( BaseObject* object, ConnectionTrackerInterface* tracker, const std::string& signalName, FunctorDelegate* functor )
 {
-  Dali::BaseHandle handle( object );
-
   bool connected( true );
   AccessibilityManager* manager = dynamic_cast<AccessibilityManager*>( object );
 
-  if( 0 == strcmp( signalName.c_str(), SIGNAL_FOCUS_CHANGED ) )
-  {
-    manager->FocusChangedSignal().Connect( tracker, functor );
-  }
-  else if( 0 == strcmp( signalName.c_str(), SIGNAL_FOCUS_OVERSHOT ) )
-  {
-    manager->FocusOvershotSignal().Connect( tracker, functor );
-  }
-  else if( 0 == strcmp( signalName.c_str(), SIGNAL_FOCUSED_ACTOR_ACTIVATED ) )
+  if( manager )
   {
-    manager->FocusedActorActivatedSignal().Connect( tracker, functor );
-  }
-  else
-  {
-    // signalName does not match any signal
-    connected = false;
+    if( 0 == strcmp( signalName.c_str(), SIGNAL_FOCUS_CHANGED ) )
+    {
+      manager->FocusChangedSignal().Connect( tracker, functor );
+    }
+    else if( 0 == strcmp( signalName.c_str(), SIGNAL_FOCUS_OVERSHOT ) )
+    {
+      manager->FocusOvershotSignal().Connect( tracker, functor );
+    }
+    else if( 0 == strcmp( signalName.c_str(), SIGNAL_FOCUSED_ACTOR_ACTIVATED ) )
+    {
+      manager->FocusedActorActivatedSignal().Connect( tracker, functor );
+    }
+    else
+    {
+      // signalName does not match any signal
+      connected = false;
+    }
   }
 
   return connected;
index dc0ab41..4c018aa 100644 (file)
@@ -23,6 +23,7 @@
 #include <list>
 #include <map>
 #include <dali/public-api/common/stage.h>
+#include <dali/public-api/common/vector-wrapper.h>
 #include <dali/public-api/actors/actor.h>
 #include <dali/public-api/object/base-object.h>
 #include <dali/public-api/object/property-map.h>
index 6d5ef93..69d0026 100644 (file)
@@ -18,6 +18,8 @@
  *
  */
 
+// EXTERNAL INCLUDES
+#include <dali/public-api/common/vector-wrapper.h>
 #include <dali/public-api/actors/actor.h>
 #include <dali/public-api/object/property-map.h>
 #include <dali/devel-api/rendering/renderer.h>
index 00e1271..88724e0 100644 (file)
@@ -31,18 +31,6 @@ using namespace Dali;
 
 namespace
 {
-/*
- * Custom properties for how to lay out the actor.
- *
- * When an actor is add to the flex container, the following custom properties of the actor
- * are checked to decide how to lay out the actor inside the flex container.
- *
- * These non-animatable properties should be registered to the child which would be added
- * to the flex container, and once added their values can not be changed.
- */
-const char * const FLEX_PROPERTY_NAME("flex");
-const char * const ALIGN_SELF_PROPERTY_NAME("alignSelf");
-const char * const FLEX_MARGIN_PROPERTY_NAME("flexMargin");
 
 #if defined(DEBUG_ENABLED)
 // debugging support, very useful when new features are added or bugs are hunted down
@@ -93,12 +81,15 @@ BaseHandle Create()
 // Setup properties, signals and actions using the type-registry.
 DALI_TYPE_REGISTRATION_BEGIN( Toolkit::FlexContainer, Toolkit::Control, Create );
 
-DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer, "contentDirection",   INTEGER, CONTENT_DIRECTION )
-DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer, "flexDirection",      INTEGER, FLEX_DIRECTION    )
-DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer, "flexWrap",           INTEGER, FLEX_WRAP         )
-DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer, "justifyContent",     INTEGER, JUSTIFY_CONTENT   )
-DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer, "alignItems",         INTEGER, ALIGN_ITEMS       )
-DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer, "alignContent",       INTEGER, ALIGN_CONTENT     )
+DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer,        "contentDirection",  INTEGER,  CONTENT_DIRECTION )
+DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer,        "flexDirection",     INTEGER,  FLEX_DIRECTION    )
+DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer,        "flexWrap",          INTEGER,  FLEX_WRAP         )
+DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer,        "justifyContent",    INTEGER,  JUSTIFY_CONTENT   )
+DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer,        "alignItems",        INTEGER,  ALIGN_ITEMS       )
+DALI_PROPERTY_REGISTRATION( Toolkit, FlexContainer,        "alignContent",      INTEGER,  ALIGN_CONTENT     )
+DALI_CHILD_PROPERTY_REGISTRATION( Toolkit, FlexContainer,  "flex",              FLOAT,    FLEX              )
+DALI_CHILD_PROPERTY_REGISTRATION( Toolkit, FlexContainer,  "alignSelf",         INTEGER,  ALIGN_SELF        )
+DALI_CHILD_PROPERTY_REGISTRATION( Toolkit, FlexContainer,  "flexMargin",        VECTOR4,  FLEX_MARGIN       )
 
 DALI_TYPE_REGISTRATION_END()
 
@@ -605,41 +596,33 @@ void FlexContainer::ComputeLayout()
       childNode->style.maxDimensions[CSS_WIDTH] = childActor.GetMaximumSize().x;
       childNode->style.maxDimensions[CSS_HEIGHT] = childActor.GetMaximumSize().y;
 
-      // Test custom properties on the child
-      if( childActor.GetPropertyIndex( FLEX_PROPERTY_NAME ) != Property::INVALID_INDEX )
-      {
-        childNode->style.flex = childActor.GetProperty( childActor.GetPropertyIndex(FLEX_PROPERTY_NAME) ).Get<float>();
-      }
+      // Check child properties on the child for how to layout it.
+      // These properties should be dynamically registered to the child which
+      // would be added to FlexContainer.
 
-      Property::Index alignSelfPropertyIndex = childActor.GetPropertyIndex( ALIGN_SELF_PROPERTY_NAME );
-      if( alignSelfPropertyIndex != Property::INVALID_INDEX )
-      {
-        Property::Value alignSelfPropertyValue = childActor.GetProperty( alignSelfPropertyIndex );
+      childNode->style.flex = childActor.GetProperty( Toolkit::FlexContainer::ChildProperty::FLEX ).Get<float>();
 
-        Toolkit::FlexContainer::Alignment alignSelf( Toolkit::FlexContainer::ALIGN_AUTO );
-        if( alignSelfPropertyValue.GetType() == Property::INTEGER )
-        {
-          alignSelf = static_cast<Toolkit::FlexContainer::Alignment>( alignSelfPropertyValue.Get< int >() );
-        }
-        else if( alignSelfPropertyValue.GetType() == Property::STRING )
-        {
-          std::string value = alignSelfPropertyValue.Get<std::string>();
-          Scripting::GetEnumeration< Toolkit::FlexContainer::Alignment >( value.c_str(),
-                                                                          ALIGN_SELF_STRING_TABLE,
-                                                                          ALIGN_SELF_STRING_TABLE_COUNT,
-                                                                          alignSelf );
-        }
-        childNode->style.align_self = static_cast<css_align_t>(alignSelf);
+      Toolkit::FlexContainer::Alignment alignSelf( Toolkit::FlexContainer::ALIGN_AUTO );
+      Property::Value alignSelfPropertyValue = childActor.GetProperty( Toolkit::FlexContainer::ChildProperty::ALIGN_SELF );
+      if( alignSelfPropertyValue.GetType() == Property::INTEGER )
+      {
+        alignSelf = static_cast<Toolkit::FlexContainer::Alignment>( alignSelfPropertyValue.Get< int >() );
       }
-
-      if( childActor.GetPropertyIndex( FLEX_MARGIN_PROPERTY_NAME ) != Property::INVALID_INDEX )
+      else if( alignSelfPropertyValue.GetType() == Property::STRING )
       {
-        Vector4 flexMargin = childActor.GetProperty( childActor.GetPropertyIndex(FLEX_MARGIN_PROPERTY_NAME) ).Get<Vector4>();
-        childNode->style.margin[CSS_LEFT] = flexMargin.x;
-        childNode->style.margin[CSS_TOP] = flexMargin.y;
-        childNode->style.margin[CSS_RIGHT] = flexMargin.z;
-        childNode->style.margin[CSS_BOTTOM] = flexMargin.w;
+        std::string value = alignSelfPropertyValue.Get<std::string>();
+        Scripting::GetEnumeration< Toolkit::FlexContainer::Alignment >( value.c_str(),
+                                                                        ALIGN_SELF_STRING_TABLE,
+                                                                        ALIGN_SELF_STRING_TABLE_COUNT,
+                                                                        alignSelf );
       }
+      childNode->style.align_self = static_cast<css_align_t>(alignSelf);
+
+      Vector4 flexMargin = childActor.GetProperty( Toolkit::FlexContainer::ChildProperty::FLEX_MARGIN ).Get<Vector4>();
+      childNode->style.margin[CSS_LEFT] = flexMargin.x;
+      childNode->style.margin[CSS_TOP] = flexMargin.y;
+      childNode->style.margin[CSS_RIGHT] = flexMargin.z;
+      childNode->style.margin[CSS_BOTTOM] = flexMargin.w;
     }
 
     // Calculate the layout
index 17ea2b6..2005f9c 100644 (file)
@@ -23,7 +23,7 @@
 
 // INTERNAL INCLUDES
 #include <dali-toolkit/public-api/controls/control-impl.h>
-#include <dali-toolkit/devel-api/controls/flex-container/flex-container.h>
+#include <dali-toolkit/public-api/controls/flex-container/flex-container.h>
 extern "C"
 {
 #include "layout.h"
index c09f86f..3fd6a74 100644 (file)
@@ -119,7 +119,7 @@ void ColorRenderer::InitializeRenderer()
   Geometry geometry = mFactoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
   if( !geometry )
   {
-    geometry =  RendererFactoryCache::CreateQuadGeometry();
+    geometry =  Geometry::QUAD();
     mFactoryCache.SaveGeometry( RendererFactoryCache::QUAD_GEOMETRY, geometry );
   }
 
index 6b35829..c150497 100644 (file)
@@ -311,7 +311,7 @@ void GradientRenderer::InitializeRenderer()
   Geometry geometry = mFactoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
   if( !geometry )
   {
-    geometry =  RendererFactoryCache::CreateQuadGeometry();
+    geometry =  Geometry::QUAD();
     mFactoryCache.SaveGeometry( RendererFactoryCache::QUAD_GEOMETRY, geometry );
   }
 
index d0c6c91..90dd616 100644 (file)
@@ -113,7 +113,7 @@ Geometry CreateGeometry( RendererFactoryCache& factoryCache, ImageDimensions gri
     geometry = factoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
     if( !geometry )
     {
-      geometry =  RendererFactoryCache::CreateQuadGeometry();
+      geometry =  Geometry::QUAD();
       factoryCache.SaveGeometry( RendererFactoryCache::QUAD_GEOMETRY, geometry );
     }
   }
index 4fd7424..3db2282 100644 (file)
@@ -153,32 +153,6 @@ Renderer RendererFactoryCache::GetDebugRenderer()
   return mDebugRenderer;
 }
 
-Geometry RendererFactoryCache::CreateQuadGeometry()
-{
-  const float halfWidth = 0.5f;
-  const float halfHeight = 0.5f;
-  struct QuadVertex { Vector2 position;};
-  QuadVertex quadVertexData[4] =
-  {
-      { Vector2(-halfWidth, -halfHeight) },
-      { Vector2(-halfWidth, halfHeight)  },
-      { Vector2( halfWidth, -halfHeight) },
-      { Vector2( halfWidth, halfHeight)  }
-  };
-
-  Property::Map quadVertexFormat;
-  quadVertexFormat["aPosition"] = Property::VECTOR2;
-  PropertyBuffer quadVertices = PropertyBuffer::New( quadVertexFormat );
-  quadVertices.SetData( quadVertexData, 4 );
-
-  // Create the geometry object
-  Geometry geometry = Geometry::New();
-  geometry.AddVertexBuffer( quadVertices );
-  geometry.SetGeometryType( Geometry::TRIANGLE_STRIP );
-
-  return geometry;
-}
-
 SvgRasterizeThread* RendererFactoryCache::GetSVGRasterizationThread()
 {
   if( !mSvgRasterizeThread )
index f6fd573..8bffd15 100644 (file)
@@ -109,12 +109,6 @@ public:
    */
   void SaveShader( ShaderType type, Shader shader );
 
-  /*
-   * Greate the quad geometry.
-   * Quad geometry is shared by multiple kind of Renderer, so implement it in the factory-cache.
-   */
-  static Geometry CreateQuadGeometry();
-
   /**
    * Create the grid geometry.
    * @param[in] gridSize The size of the grid.
index e52cb15..9643567 100644 (file)
@@ -230,13 +230,25 @@ typedef struct NSVGgradientData
 {
     char id[64];
     char ref[64];
-    char type;
+
+    /**
+     * In the original file, using char type (without signed or unsigned) can be interpreted
+     * as 'unsigned char' in some build environments, like ARM architecture.
+     * To prevent the unexpected behavior, we replace 'char type' with 'signed char type' here.
+     */
+    signed char type;
     union {
         NSVGlinearData linear;
         NSVGradialData radial;
     };
     char spread;
-    char units;
+
+    /**
+     * In the original file, using char type (without signed or unsigned) can be interpreted
+     * as 'unsigned char' in some build environments, like ARM architecture.
+     * To prevent the unexpected behavior, we replace 'char units' with 'signed char units' here.
+     */
+    signed char units;
     float xform[6];
     int nstops;
     NSVGgradientStop* stops;
@@ -643,7 +655,12 @@ static NSVGgradientData* nsvg__findGradientData(NSVGparser* p, const char* id)
     return NULL;
 }
 
-static NSVGgradient* nsvg__createGradient(NSVGparser* p, const char* id, const float* localBounds, char* paintType)
+/**
+ * In the original file, using char type (without signed or unsigned) can be interpreted
+ * as 'unsigned char' in some build environments, like ARM architecture.
+ * To prevent the unexpected behavior, we replace 'char paintType' with 'signed char paintType' here.
+ */
+static NSVGgradient* nsvg__createGradient(NSVGparser* p, const char* id, const float* localBounds, signed char* paintType)
 {
     NSVGattrib* attr = nsvg__getAttr(p);
     NSVGgradientData* data = NULL;
index 608bcd6..2634297 100644 (file)
@@ -113,7 +113,12 @@ typedef struct NSVGgradient {
 } NSVGgradient;
 
 typedef struct NSVGpaint {
-       char type;
+       /**
+        * In the original file, using char type (without signed or unsigned) can be interpreted
+        * as 'unsigned char' in some build environments, like ARM architecture.
+        * To prevent the unexpected behavior, we replace 'char type' with 'signed char type' here.
+        */
+       signed char type;
        union {
                unsigned int color;
                NSVGgradient* gradient;
index 73bfd2c..a3f3bdb 100644 (file)
@@ -68,7 +68,12 @@ typedef struct NSVGmemPage {
 } NSVGmemPage;
 
 typedef struct NSVGcachedPaint {
-    char type;
+    /**
+     * In the original file, using char type (without signed or unsigned) can be interpreted
+     * as 'unsigned char' in some build environments, like ARM architecture.
+     * To prevent the unexpected behavior, we replace 'char type' with 'signed char type' here.
+     */
+    signed char type;
     char spread;
     float xform[6];
     unsigned int colors[256];
@@ -873,7 +878,13 @@ static void nsvg__fillScanline(unsigned char* scanline, int len, int x0, int x1,
 // note: this routine clips fills that extend off the edges... ideally this
 // wouldn't happen, but it could happen if the truetype glyph bounding boxes
 // are wrong, or if the user supplies a too-small bitmap
-static void nsvg__fillActiveEdges(unsigned char* scanline, int len, NSVGactiveEdge* e, int maxWeight, int* xmin, int* xmax, char fillRule)
+
+ /**
+  * In the original file, using char type (without signed or unsigned) can be interpreted
+  * as 'unsigned char' in some build environments, like ARM architecture.
+  * To prevent the unexpected behavior, we replace 'char fillRule' with 'signed char fillRule' here.
+  */
+static void nsvg__fillActiveEdges(unsigned char* scanline, int len, NSVGactiveEdge* e, int maxWeight, int* xmin, int* xmax, signed char fillRule)
 {
     // non-zero winding fill
     int x0 = 0, w = 0;
index d6619d3..f48a5ad 100644 (file)
@@ -96,7 +96,7 @@ void SvgRenderer::DoSetOnStage( Actor& actor )
   Geometry geometry = mFactoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
   if( !geometry )
   {
-    geometry =  mFactoryCache.CreateQuadGeometry();
+    geometry =  Geometry::QUAD();
     mFactoryCache.SaveGeometry( RendererFactoryCache::QUAD_GEOMETRY, geometry );
   }
   TextureSet textureSet = TextureSet::New();
index e7bac78..32afaf0 100644 (file)
@@ -28,6 +28,7 @@
 #include <dali-toolkit/internal/text/rendering/text-backend.h>
 #include <dali-toolkit/internal/text/text-font-style.h>
 #include <dali-toolkit/internal/text/text-view.h>
+#include <dali-toolkit/internal/text/text-definitions.h>
 #include <dali-toolkit/internal/styling/style-manager-impl.h>
 
 using Dali::Toolkit::Text::LayoutEngine;
@@ -50,8 +51,8 @@ namespace
 namespace
 {
 
-#if defined(DEBUG_ENABLED)
-  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Concise, true, "LOG_TEXT_CONTROLS");
+#if defined ( DEBUG_ENABLED )
+  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, true, "LOG_TEXT_CONTROLS");
 #endif
 
 const Scripting::StringEnum HORIZONTAL_ALIGNMENT_STRING_TABLE[] =
@@ -79,24 +80,30 @@ BaseHandle Create()
 // Setup properties, signals and actions using the type-registry.
 DALI_TYPE_REGISTRATION_BEGIN( Toolkit::TextLabel, Toolkit::Control, Create );
 
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "renderingBackend",     INTEGER, RENDERING_BACKEND    )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "text",                 STRING,  TEXT                 )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "fontFamily",           STRING,  FONT_FAMILY          )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "fontStyle",            STRING,  FONT_STYLE           )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "pointSize",            FLOAT,   POINT_SIZE           )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "multiLine",            BOOLEAN, MULTI_LINE           )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "horizontalAlignment",  STRING,  HORIZONTAL_ALIGNMENT )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "verticalAlignment",    STRING,  VERTICAL_ALIGNMENT   )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "textColor",            VECTOR4, TEXT_COLOR           )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "shadowOffset",         VECTOR2, SHADOW_OFFSET        )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "shadowColor",          VECTOR4, SHADOW_COLOR         )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "underlineEnabled",     BOOLEAN, UNDERLINE_ENABLED    )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "underlineColor",       VECTOR4, UNDERLINE_COLOR      )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "underlineHeight",      FLOAT,   UNDERLINE_HEIGHT     )
-DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "enableMarkup",         BOOLEAN, ENABLE_MARKUP        )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "renderingBackend",     INTEGER, RENDERING_BACKEND      )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "text",                 STRING,  TEXT                   )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "fontFamily",           STRING,  FONT_FAMILY            )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "fontStyle",            STRING,  FONT_STYLE             )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "pointSize",            FLOAT,   POINT_SIZE             )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "multiLine",            BOOLEAN, MULTI_LINE             )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "horizontalAlignment",  STRING,  HORIZONTAL_ALIGNMENT   )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "verticalAlignment",    STRING,  VERTICAL_ALIGNMENT     )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "textColor",            VECTOR4, TEXT_COLOR             )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "shadowOffset",         VECTOR2, SHADOW_OFFSET          )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "shadowColor",          VECTOR4, SHADOW_COLOR           )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "underlineEnabled",     BOOLEAN, UNDERLINE_ENABLED      )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "underlineColor",       VECTOR4, UNDERLINE_COLOR        )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "underlineHeight",      FLOAT,   UNDERLINE_HEIGHT       )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "enableMarkup",         BOOLEAN, ENABLE_MARKUP          )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "enableAutoScroll",     BOOLEAN, ENABLE_AUTO_SCROLL     )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "autoScrollSpeed",      INTEGER, AUTO_SCROLL_SPEED      )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "autoScrollLoopCount",  INTEGER, AUTO_SCROLL_LOOP_COUNT )
+DALI_PROPERTY_REGISTRATION( Toolkit, TextLabel, "autoScrollGap",        FLOAT,   AUTO_SCROLL_GAP        )
 
 DALI_TYPE_REGISTRATION_END()
 
+
+
 } // namespace
 
 Toolkit::TextLabel TextLabel::New()
@@ -161,7 +168,7 @@ 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() );
+          DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextLabel::SetProperty Property::FONT_FAMILY newFont(%s)\n", fontFamily.c_str() );
           impl.mController->SetDefaultFontFamily( fontFamily );
         }
         break;
@@ -312,6 +319,59 @@ void TextLabel::SetProperty( BaseObject* object, Property::Index index, const Pr
         }
         break;
       }
+      case Toolkit::TextLabel::Property::ENABLE_AUTO_SCROLL:
+      {
+        if( impl.mController )
+        {
+          const bool enableAutoScroll = value.Get<bool>();
+          // If request to auto scroll is the same as current state then do nothing.
+          if ( enableAutoScroll != impl.mController->IsAutoScrollEnabled() )
+          {
+             // If request is disable (false) and auto scrolling is enabled then need to stop it
+             if ( enableAutoScroll == false )
+             {
+               if( impl.mTextScroller )
+               {
+                 impl.mTextScroller->SetLoopCount( 0 ); // Causes the current animation to finish playing (0)
+               }
+             }
+             // If request is enable (true) then start autoscroll as not already running
+             else
+             {
+               impl.mController->GetLayoutEngine().SetTextEllipsisEnabled( false );
+               impl.mController->SetAutoScrollEnabled( enableAutoScroll );
+             }
+          }
+        }
+        break;
+      }
+      case Toolkit::TextLabel::Property::AUTO_SCROLL_SPEED:
+      {
+        if( !impl.mTextScroller )
+        {
+          impl.mTextScroller = Text::TextScroller::New( impl );
+        }
+        impl.mTextScroller->SetSpeed( value.Get<int>() );
+        break;
+      }
+      case Toolkit::TextLabel::Property::AUTO_SCROLL_LOOP_COUNT:
+      {
+        if( !impl.mTextScroller )
+        {
+          impl.mTextScroller = Text::TextScroller::New( impl );
+        }
+        impl.mTextScroller->SetLoopCount( value.Get<int>() );
+        break;
+      }
+      case Toolkit::TextLabel::Property::AUTO_SCROLL_GAP:
+      {
+        if( !impl.mTextScroller )
+        {
+          impl.mTextScroller = Text::TextScroller::New( impl );
+        }
+        impl.mTextScroller->SetGap( value.Get<float>() );
+        break;
+      }
     }
   }
 }
@@ -455,6 +515,44 @@ Property::Value TextLabel::GetProperty( BaseObject* object, Property::Index inde
         }
         break;
       }
+      case Toolkit::TextLabel::Property::ENABLE_AUTO_SCROLL:
+      {
+        if( impl.mController )
+        {
+          value = impl.mController->IsAutoScrollEnabled();
+        }
+        break;
+      }
+      case Toolkit::TextLabel::Property::AUTO_SCROLL_SPEED:
+      {
+        TextLabel& impl( GetImpl( label ) );
+        if ( impl.mTextScroller )
+        {
+          value = impl.mTextScroller->GetSpeed();
+        }
+        break;
+      }
+      case Toolkit::TextLabel::Property::AUTO_SCROLL_LOOP_COUNT:
+      {
+        if( impl.mController )
+        {
+          TextLabel& impl( GetImpl( label ) );
+          if ( impl.mTextScroller )
+          {
+            value = impl.mTextScroller->GetLoopCount();
+          }
+        }
+        break;
+      }
+      case Toolkit::TextLabel::Property::AUTO_SCROLL_GAP:
+      {
+        TextLabel& impl( GetImpl( label ) );
+        if ( impl.mTextScroller )
+        {
+          value = impl.mTextScroller->GetGap();
+        }
+        break;
+      }
     }
   }
 
@@ -478,7 +576,7 @@ void TextLabel::OnInitialize()
   // Enable the text ellipsis.
   LayoutEngine& engine = mController->GetLayoutEngine();
 
-  engine.SetTextEllipsisEnabled( true );
+  engine.SetTextEllipsisEnabled( true );   // If false then text larger than control will overflow
   engine.SetCursorWidth( 0u ); // Do not layout space for the cursor.
 
   self.OnStageSignal().Connect( this, &TextLabel::OnStageConnect );
@@ -530,6 +628,8 @@ float TextLabel::GetHeightForWidth( float width )
 
 void TextLabel::OnRelayout( const Vector2& size, RelayoutContainer& container )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::OnRelayout\n" );
+
   if( mController->Relayout( size ) ||
       !mRenderer )
   {
@@ -548,8 +648,11 @@ void TextLabel::RequestTextRelayout()
 
 void TextLabel::RenderText()
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::RenderText IsAutoScrollEnabled[%s] [%p]\n", ( mController->IsAutoScrollEnabled())?"true":"false", this );
+
   Actor self = Self();
   Actor renderableActor;
+
   if( mRenderer )
   {
     renderableActor = mRenderer->Render( mController->GetView(), DepthIndex::TEXT );
@@ -568,9 +671,38 @@ void TextLabel::RenderText()
       self.Add( renderableActor );
     }
     mRenderableActor = renderableActor;
+
+    if ( mController->IsAutoScrollEnabled() )
+    {
+      SetUpAutoScrolling();
+    }
   }
 }
 
+void TextLabel::SetUpAutoScrolling()
+{
+  const Size& controlSize = mController->GetView().GetControlSize();
+  const Size offScreenSize = GetNaturalSize().GetVectorXY(); // As relayout of text may not be done at this point natural size is used to get size. Single line scrolling only.
+  const Vector2& alignmentOffset = mController->GetAlignmentOffset();
+  const Text::CharacterDirection direction = mController->GetAutoScrollDirection();
+
+  DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::SetUpAutoScrolling alignmentOffset[%f,%f] offScreenSize[%f,%f] controlSize[%f,%f]\n",
+                 alignmentOffset.x, alignmentOffset.y, offScreenSize.x,offScreenSize.y , controlSize.x,controlSize.y);
+
+  if ( !mTextScroller )
+  {
+    DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::SetUpAutoScrolling Creating default TextScoller\n");
+
+    // If speed, loopCount or gap not set via property system then will need to create a TextScroller with defaults
+    mTextScroller = Text::TextScroller::New( *this );
+  }
+  mTextScroller->SetParameters( mRenderableActor, controlSize, offScreenSize, direction, alignmentOffset );
+
+  Actor self = Self();
+  self.Add( mTextScroller->GetScrollingText() );
+  self.Add( mTextScroller->GetSourceCamera() );
+}
+
 void TextLabel::OnStageConnect( Dali::Actor actor )
 {
   if ( mHasBeenStaged )
@@ -606,6 +738,15 @@ void TextLabel::MaxLengthReached()
   // Pure Virtual from TextController Interface, only needed when inputting text
 }
 
+void TextLabel::ScrollingFinished()
+{
+  // Pure Virtual from TextScroller Interface
+  DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::ScrollingFinished\n");
+  mController->SetAutoScrollEnabled( false );
+  mController->GetLayoutEngine().SetTextEllipsisEnabled( true );
+  RequestTextRelayout();
+}
+
 TextLabel::TextLabel()
 : Control( ControlBehaviour( REQUIRES_STYLE_CHANGE_SIGNALS ) ),
   mRenderingBackend( DEFAULT_RENDERING_BACKEND ),
index ae88beb..c2dd485 100644 (file)
@@ -22,7 +22,9 @@
 #include <dali-toolkit/public-api/controls/control-impl.h>
 #include <dali-toolkit/public-api/controls/text-controls/text-label.h>
 #include <dali-toolkit/internal/text/text-controller.h>
+#include <dali-toolkit/internal/text/text-scroller-interface.h>
 #include <dali-toolkit/internal/text/rendering/text-renderer.h>
+#include <dali-toolkit/internal/text/text-scroller.h>
 
 namespace Dali
 {
@@ -36,7 +38,7 @@ namespace Internal
 /**
  * @brief A control which renders a short text string.
  */
-class TextLabel : public Control, public Text::ControlInterface
+class TextLabel : public Control, public Text::ControlInterface, public Text::ScrollerInterface
 {
 public:
 
@@ -117,6 +119,13 @@ private: // From Control
    */
   virtual void MaxLengthReached();
 
+private: // from TextScroller
+
+  /**
+   * @copydoc Text::ScrollerInterface::ScrollingFinished()
+   */
+  virtual void ScrollingFinished();
+
 private: // Implementation
 
   /**
@@ -143,10 +152,16 @@ private:
    */
   void RenderText();
 
+  /**
+   * @brief Set up Autoscrolling
+   */
+  void SetUpAutoScrolling();
+
 private: // Data
 
   Text::ControllerPtr mController;
   Text::RendererPtr mRenderer;
+  Text::TextScrollerPtr mTextScroller;
   Actor mRenderableActor;
   int mRenderingBackend;
   bool mHasBeenStaged:1;
index e02dbc1..184f37a 100644 (file)
@@ -19,6 +19,7 @@
 #include <dali-toolkit/internal/feedback/feedback-style.h>
 
 // EXTERNAL INCLUDES
+#include <dali/public-api/common/vector-wrapper.h>
 #include <dali/integration-api/debug.h>
 #include <dali/public-api/common/stage.h>
 #include <dali/public-api/object/object-registry.h>
index cd24d24..d043b79 100644 (file)
@@ -106,6 +106,8 @@ toolkit_src_files = \
    $(toolkit_src_dir)/text/text-controller-impl.cpp \
    $(toolkit_src_dir)/text/text-font-style.cpp \
    $(toolkit_src_dir)/text/text-io.cpp \
+   $(toolkit_src_dir)/text/text-scroller.cpp \
+   $(toolkit_src_dir)/text/text-scroller-interface.cpp \
    $(toolkit_src_dir)/text/text-view.cpp \
    $(toolkit_src_dir)/text/text-view-interface.cpp \
    $(toolkit_src_dir)/text/visual-model-impl.cpp \
index 9f5d27a..cdcc8e2 100644 (file)
@@ -228,23 +228,24 @@ void KeyInputFocusManager::OnObjectDestroyed( const Dali::RefObject* object )
 
 bool KeyInputFocusManager::DoConnectSignal( BaseObject* object, ConnectionTrackerInterface* tracker, const std::string& signalName, FunctorDelegate* functor )
 {
-  Dali::BaseHandle handle( object );
-
   bool connected( true );
   KeyInputFocusManager* manager = dynamic_cast<KeyInputFocusManager*>( object );
 
-  if( 0 == strcmp( signalName.c_str(), SIGNAL_KEY_INPUT_FOCUS_CHANGED ) )
-  {
-    manager->KeyInputFocusChangedSignal().Connect( tracker, functor );
-  }
-  else if( 0 == strcmp( signalName.c_str(), SIGNAL_UNHANDLED_KEY_EVENT ) )
-  {
-    manager->UnhandledKeyEventSignal().Connect( tracker, functor );
-  }
-  else
+  if( manager )
   {
-    // signalName does not match any signal
-    connected = false;
+    if( 0 == strcmp( signalName.c_str(), SIGNAL_KEY_INPUT_FOCUS_CHANGED ) )
+    {
+      manager->KeyInputFocusChangedSignal().Connect( tracker, functor );
+    }
+    else if( 0 == strcmp( signalName.c_str(), SIGNAL_UNHANDLED_KEY_EVENT ) )
+    {
+      manager->UnhandledKeyEventSignal().Connect( tracker, functor );
+    }
+    else
+    {
+      // signalName does not match any signal
+      connected = false;
+    }
   }
 
   return connected;
index a5da5a4..ac9110e 100644 (file)
@@ -1242,11 +1242,13 @@ void LayoutEngine::SetLayout( Layout layout )
 
 LayoutEngine::Layout LayoutEngine::GetLayout() const
 {
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "GetLayout[%d]\n", mImpl->mLayout);
   return mImpl->mLayout;
 }
 
 void LayoutEngine::SetTextEllipsisEnabled( bool enabled )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "-->LayoutEngine::SetTextEllipsisEnabled[%s]\n", (enabled)?"true":"false" );
   mImpl->mEllipsisEnabled = enabled;
 }
 
index 2db0faa..32ab39b 100644 (file)
@@ -38,7 +38,7 @@ using namespace Dali::Toolkit::Text;
 namespace
 {
 #if defined(DEBUG_ENABLED)
-  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::Concise, true, "LOG_TEXT_RENDERING");
+  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, true, "LOG_TEXT_RENDERING");
 #endif
 
 const float ZERO( 0.0f );
@@ -433,6 +433,9 @@ struct AtlasRenderer::Impl
             renderer.SetProperty( Dali::Renderer::Property::DEPTH_INDEX, depthIndex - 1 );
             containerActor.Add( shadowActor );
             containerActor.Add( actor );
+#if defined(DEBUG_ENABLED)
+            containerActor.SetName("TextContainer");
+#endif
             actor = containerActor;
           }
         }
@@ -504,7 +507,6 @@ struct AtlasRenderer::Impl
     // Keep all of the origins aligned
     actor.SetParentOrigin( ParentOrigin::TOP_LEFT );
     actor.SetAnchorPoint( AnchorPoint::TOP_LEFT );
-
     actor.SetSize( actorSize );
     actor.RegisterProperty("uOffset", Vector2::ZERO );
     return actor;
@@ -738,6 +740,8 @@ Text::RendererPtr AtlasRenderer::New()
 
 Actor AtlasRenderer::Render( Text::ViewInterface& view, int depth )
 {
+  DALI_LOG_INFO( gLogFilter, Debug::General, "Text::AtlasRenderer::Render()\n" );
+
   UnparentAndReset( mImpl->mActor );
 
   Length numberOfGlyphs = view.GetNumberOfGlyphs();
index ce8a291..5c1ed0c 100644 (file)
@@ -301,7 +301,9 @@ struct Controller::Impl
     mMaximumNumberOfCharacters( 50u ),
     mRecalculateNaturalSize( true ),
     mMarkupProcessorEnabled( false ),
-    mClipboardHideEnabled( true )
+    mClipboardHideEnabled( true ),
+    mAutoScrollEnabled( false ),
+    mAutoScrollDirectionRTL( false )
   {
     mLogicalModel = LogicalModel::New();
     mVisualModel  = VisualModel::New();
@@ -658,7 +660,10 @@ public:
 
   bool mRecalculateNaturalSize:1;          ///< Whether the natural size needs to be recalculated.
   bool mMarkupProcessorEnabled:1;          ///< Whether the mark-up procesor is enabled.
-  bool mClipboardHideEnabled:1;           ///< Whether the ClipboardHide function work or not
+  bool mClipboardHideEnabled:1;            ///< Whether the ClipboardHide function work or not
+  bool mAutoScrollEnabled:1;               ///< Whether auto text scrolling is enabled.
+  CharacterDirection mAutoScrollDirectionRTL:1;  ///< Direction of auto scrolling, true if rtl
+
 };
 
 } // namespace Text
index 3a211e1..268519b 100644 (file)
@@ -132,6 +132,55 @@ bool Controller::IsMarkupProcessorEnabled() const
   return mImpl->mMarkupProcessorEnabled;
 }
 
+void Controller::SetAutoScrollEnabled( bool enable )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetAutoScrollEnabled[%s] SingleBox[%s]-> [%p]\n", (enable)?"true":"false", ( mImpl->mLayoutEngine.GetLayout() == LayoutEngine::SINGLE_LINE_BOX)?"true":"false", this );
+
+  if ( mImpl->mLayoutEngine.GetLayout() == LayoutEngine::SINGLE_LINE_BOX )
+  {
+    if ( enable )
+    {
+      DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetAutoScrollEnabled for SINGLE_LINE_BOX\n" );
+      mImpl->mOperationsPending = static_cast<OperationsMask>( mImpl->mOperationsPending |
+                                                               LAYOUT                    |
+                                                               ALIGN                     |
+                                                               UPDATE_ACTUAL_SIZE        |
+                                                               UPDATE_DIRECTION          |
+                                                               REORDER );
+
+    }
+    else
+    {
+      DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetAutoScrollEnabled Disabling autoscroll\n");
+      mImpl->mOperationsPending = static_cast<OperationsMask>( mImpl->mOperationsPending |
+                                                               LAYOUT                    |
+                                                               ALIGN                     |
+                                                               UPDATE_ACTUAL_SIZE        |
+                                                               REORDER );
+    }
+
+    mImpl->mAutoScrollEnabled = enable;
+    mImpl->RequestRelayout();
+  }
+  else
+  {
+    DALI_LOG_WARNING( "Attempted AutoScrolling on a non SINGLE_LINE_BOX, request ignored" );
+    mImpl->mAutoScrollEnabled = false;
+  }
+}
+
+bool Controller::IsAutoScrollEnabled() const
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Controller::IsAutoScrollEnabled[%s]\n", (mImpl->mAutoScrollEnabled)?"true":"false" );
+
+  return mImpl->mAutoScrollEnabled;
+}
+
+CharacterDirection Controller::GetAutoScrollDirection() const
+{
+  return mImpl->mAutoScrollDirectionRTL;
+}
+
 void Controller::SetText( const std::string& text )
 {
   DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Controller::SetText\n" );
@@ -473,7 +522,7 @@ float Controller::GetDefaultPointSize() const
 
 void Controller::UpdateAfterFontChange( const std::string& newDefaultFont )
 {
-  DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::UpdateAfterFontChange");
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Controller::UpdateAfterFontChange");
 
   if( !mImpl->mFontDefaults->familyDefined ) // If user defined font then should not update when system font changes
   {
@@ -1063,8 +1112,8 @@ Vector3 Controller::GetNaturalSize()
     mImpl->mTextUpdateInfo.mParagraphCharacterIndex = 0u;
     mImpl->mTextUpdateInfo.mRequestedNumberOfCharacters = mImpl->mLogicalModel->mText.Count();
 
-    // Store the actual control's width.
-    const float actualControlWidth = mImpl->mVisualModel->mControlSize.width;
+    // Store the actual control's size to restore later.
+    const Size actualControlSize = mImpl->mVisualModel->mControlSize;
 
     DoRelayout( Size( MAX_FLOAT, MAX_FLOAT ),
                 static_cast<OperationsMask>( onlyOnceOperations |
@@ -1089,8 +1138,8 @@ Vector3 Controller::GetNaturalSize()
     // Clear the update info. This info will be set the next time the text is updated.
     mImpl->mTextUpdateInfo.Clear();
 
-    // Restore the actual control's width.
-    mImpl->mVisualModel->mControlSize.width = actualControlWidth;
+    // Restore the actual control's size.
+    mImpl->mVisualModel->mControlSize = actualControlSize;
 
     DALI_LOG_INFO( gLogFilter, Debug::Verbose, "<--Controller::GetNaturalSize calculated %f,%f,%f\n", naturalSize.x, naturalSize.y, naturalSize.z );
   }
@@ -1173,7 +1222,7 @@ float Controller::GetHeightForWidth( float width )
 
 bool Controller::Relayout( const Size& size )
 {
-  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "-->Controller::Relayout %p size %f,%f\n", this, size.width, size.height );
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "-->Controller::Relayout %p size %f,%f, autoScroll[%s]\n", this, size.width, size.height, (mImpl->mAutoScrollEnabled)?"true":"false"  );
 
   if( ( size.width < Math::MACHINE_EPSILON_1000 ) || ( size.height < Math::MACHINE_EPSILON_1000 ) )
   {
@@ -1432,6 +1481,8 @@ bool Controller::DoRelayout( const Size& size,
 
   if( NO_OPERATION != ( LAYOUT & operations ) )
   {
+    DALI_LOG_INFO( gLogFilter, Debug::Verbose, "-->Controller::DoRelayout LAYOUT & operations\n");
+
     // Some vectors with data needed to layout and reorder may be void
     // after the first time the text has been laid out.
     // Fill the vectors again.
@@ -1500,8 +1551,14 @@ bool Controller::DoRelayout( const Size& size,
                                                    mImpl->mVisualModel->mLines,
                                                    layoutSize );
 
+
     if( viewUpdated )
     {
+      if ( NO_OPERATION != ( UPDATE_DIRECTION & operations ) )
+      {
+        mImpl->mAutoScrollDirectionRTL = false;
+      }
+
       // Reorder the lines
       if( NO_OPERATION != ( REORDER & operations ) )
       {
@@ -1532,6 +1589,14 @@ bool Controller::DoRelayout( const Size& size,
                                                          requestedNumberOfCharacters,
                                                          glyphPositions );
 
+          if ( ( NO_OPERATION != ( UPDATE_DIRECTION & operations ) ) && ( numberOfLines > 0 ) )
+          {
+            const LineRun* const firstline = mImpl->mVisualModel->mLines.Begin();
+            if ( firstline )
+            {
+              mImpl->mAutoScrollDirectionRTL = firstline->direction;
+            }
+          }
         }
       } // REORDER
 
@@ -1562,7 +1627,11 @@ bool Controller::DoRelayout( const Size& size,
 
     viewUpdated = true;
   }
-
+#if defined(DEBUG_ENABLED)
+  std::string currentText;
+  GetText( currentText );
+  DALI_LOG_INFO( gLogFilter, Debug::Concise, "Controller::DoRelayout [%p] mImpl->mAutoScrollDirectionRTL[%s] [%s]\n", this, (mImpl->mAutoScrollDirectionRTL)?"true":"false",  currentText.c_str() );
+#endif
   DALI_LOG_INFO( gLogFilter, Debug::Verbose, "<--Controller::DoRelayout, view updated %s\n", ( viewUpdated ? "true" : "false" ) );
   return viewUpdated;
 }
index 6a83374..5a96349 100644 (file)
@@ -86,6 +86,7 @@ public:
     REORDER            = 0x0400,
     ALIGN              = 0x0800,
     COLOR              = 0x1000,
+    UPDATE_DIRECTION   = 0x2000,
     ALL_OPERATIONS     = 0xFFFF
   };
 
@@ -149,6 +150,30 @@ public:
   bool IsMarkupProcessorEnabled() const;
 
   /**
+   * @brief Enables/disables the auto text scrolling
+   *
+   * By default is disabled.
+   *
+   * @param[in] enable Whether to enable the auto scrolling
+   */
+  void SetAutoScrollEnabled( bool enable );
+
+  /**
+   * @brief Retrieves whether auto text scrolling is enabled.
+   *
+   * By default is disabled.
+   *
+   * @return @e true if auto scrolling is enabled, otherwise returns @e false.
+   */
+  bool IsAutoScrollEnabled() const;
+
+  /**
+   * @brief Get direction of the text from the first line of text,
+   * @return bool rtl (right to left) is true
+   */
+  CharacterDirection GetAutoScrollDirection() const;
+
+  /**
    * @brief Replaces any text previously set.
    *
    * @note This will be converted into UTF-32 when stored in the text model.
diff --git a/dali-toolkit/internal/text/text-scroller-interface.cpp b/dali-toolkit/internal/text/text-scroller-interface.cpp
new file mode 100644 (file)
index 0000000..ee85ef9
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+// CLASS HEADER
+#include <dali-toolkit/internal/text/text-scroller-interface.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+ScrollerInterface::ScrollerInterface()
+{
+}
+
+ScrollerInterface::~ScrollerInterface()
+{
+}
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
diff --git a/dali-toolkit/internal/text/text-scroller-interface.h b/dali-toolkit/internal/text/text-scroller-interface.h
new file mode 100644 (file)
index 0000000..31a0819
--- /dev/null
@@ -0,0 +1,61 @@
+#ifndef __DALI_TOOLKIT_TEXT_SCROLLER_INTERFACE_H__
+#define __DALI_TOOLKIT_TEXT_SCROLLER_INTERFACE_H__
+
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+namespace Dali
+{
+
+class Actor;
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+/**
+ * @brief An interface used by the text-controls which implement auto-scrolling
+ */
+class ScrollerInterface
+{
+public:
+
+  /**
+   * @brief Constructor.
+   */
+  ScrollerInterface();
+
+  /**
+   * @brief Virtual destructor.
+   */
+  virtual ~ScrollerInterface();
+
+  /**
+   * @brief Called when the scrolling finishes
+   */
+  virtual void ScrollingFinished() = 0;
+};
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_TEXT_SCROLLER_INTERFACE_H__
diff --git a/dali-toolkit/internal/text/text-scroller.cpp b/dali-toolkit/internal/text/text-scroller.cpp
new file mode 100644 (file)
index 0000000..a8180fc
--- /dev/null
@@ -0,0 +1,345 @@
+/*
+ * Copyright (c) 2016 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.
+ *
+ */
+
+// CLASS HEADER
+#include <dali-toolkit/internal/text/text-scroller.h>
+
+// EXTERNAL INCLUDES
+#include <dali/devel-api/rendering/geometry.h>
+#include <dali/devel-api/rendering/renderer.h>
+#include <dali/devel-api/rendering/sampler.h>
+#include <dali/devel-api/rendering/shader.h>
+#include <dali/integration-api/debug.h>
+#include <dali/public-api/common/stage.h>
+#include <dali/public-api/images/frame-buffer-image.h>
+#include <dali/public-api/render-tasks/render-task-list.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/text-scroller-interface.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace
+{
+
+#if defined ( DEBUG_ENABLED )
+  Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, true, "LOG_TEXT_SCROLLING");
+#endif
+
+const int MINIMUM_SCROLL_SPEED = 1; // Speed should be set by Property system.
+
+const char* VERTEX_SHADER_SCROLL = DALI_COMPOSE_SHADER(
+  attribute mediump vec2 aPosition;\n
+  varying highp vec2 vTexCoord;\n
+  varying highp float vRatio;\n
+  uniform mediump mat4 uMvpMatrix;\n
+  uniform mediump vec3 uSize;\n
+  uniform mediump float uDelta;\n
+  uniform mediump vec2 uTextureSize;
+  uniform mediump float uGap;\n
+  uniform mediump float uRtl;\n
+  \n
+  void main()\n
+  {\n
+    {\n
+      mediump vec4 vertexPosition = vec4(aPosition*uSize.xy, 0.0, 1.0);\n
+      float smallTextPadding = max(uSize.x - uTextureSize.x, 0. );\n
+      float gap = max( uGap, smallTextPadding );\n
+      vTexCoord.x = ( uDelta + ( uRtl * ( uTextureSize.x - uSize.x ) )  + ( aPosition.x * uSize.x ) )/ ( uTextureSize.x+gap );\n
+      vTexCoord.y = aPosition.y;\n
+      vRatio = uTextureSize.x / ( uTextureSize.x + gap );\n
+      gl_Position = uMvpMatrix * vertexPosition;\n
+    }\n
+  }\n
+);
+
+const char* FRAGMENT_SHADER = DALI_COMPOSE_SHADER(
+  varying mediump vec2 vTexCoord;\n
+  varying highp float vRatio;\n
+  uniform sampler2D sTexture;\n
+  \n
+  void main()\n
+  {\n
+    mediump vec2 texCoord;\n
+    texCoord.y = vTexCoord.y;\n
+    texCoord.x = fract( vTexCoord.x ) / vRatio;\n
+    if ( texCoord.x > 1.0 )\n
+      discard;\n
+    \n
+    gl_FragColor = texture2D( sTexture, texCoord );\n
+  }\n
+);
+
+/**
+ * @brief Create and set up a camera for the render task to use
+ *
+ * @param[in] sizeOfTarget size of the source camera to look at
+ * @param[out] offscreenCamera custom camera
+ */
+void CreateCameraActor( const Size& sizeOfTarget, CameraActor& offscreenCamera )
+{
+  offscreenCamera = CameraActor::New();
+  offscreenCamera.SetOrthographicProjection( sizeOfTarget );
+  offscreenCamera.SetInvertYAxis( true );
+}
+
+/**
+ * @brief Create a render task
+ *
+ * @param[in] sourceActor actor to be used as source
+ * @param[in] cameraActor camera looking at source
+ * @param[in] offscreenTarget resulting image from render task
+ * @param[out] renderTask render task that has been setup
+ */
+void CreateRenderTask( Actor sourceActor, CameraActor cameraActor , FrameBufferImage offscreenTarget, RenderTask& renderTask )
+{
+  Stage stage = Stage::GetCurrent();
+  RenderTaskList taskList = stage.GetRenderTaskList();
+  renderTask = taskList.CreateTask();
+  renderTask.SetSourceActor( sourceActor );
+  renderTask.SetExclusive( true );
+  renderTask.SetInputEnabled( false );
+  renderTask.SetClearEnabled( true );
+  renderTask.SetCameraActor( cameraActor );
+  renderTask.SetTargetFrameBuffer( offscreenTarget );
+  renderTask.SetClearColor( Color::TRANSPARENT );
+  renderTask.SetCullMode( false );
+}
+
+/**
+ * @brief Create quad geometry for the mesh
+ *
+ * @param[out] geometry quad geometry that can be used for a mesh
+ */
+void CreateGeometry( Geometry& geometry )
+{
+  struct QuadVertex { Vector2 position;  };
+
+  QuadVertex quadVertexData[4] =
+  {
+      { Vector2( 0.0f, 0.0f) },
+      { Vector2( 1.0f, 0.0f) },
+      { Vector2( 0.0f, 1.0f) },
+      { Vector2( 1.0f, 1.0f) },
+  };
+
+  const unsigned short indices[6] =
+  {
+     3,1,0,0,2,3
+  };
+
+  Property::Map quadVertexFormat;
+  quadVertexFormat["aPosition"] = Property::VECTOR2;
+  PropertyBuffer quadVertices = PropertyBuffer::New( quadVertexFormat );
+  quadVertices.SetData(quadVertexData, 4 );
+
+  geometry = Geometry::New();
+  geometry.AddVertexBuffer( quadVertices );
+  geometry.SetIndexBuffer( indices, sizeof(indices)/sizeof(indices[0]) );
+}
+
+
+/**
+ * @brief Create a renderer
+ *
+ * @param[in] frameBufferImage texture to be used
+ * @param[out] renderer mesh renderer using the supplied texture
+ */
+void CreateRenderer( FrameBufferImage frameBufferImage, Dali::Renderer& renderer )
+{
+  Shader shader = Shader::New( VERTEX_SHADER_SCROLL , FRAGMENT_SHADER, Shader::HINT_NONE );
+
+  Sampler sampler = Sampler::New();
+  sampler.SetFilterMode(FilterMode::NEAREST, FilterMode::NEAREST );
+
+  TextureSet textureSet = TextureSet::New();
+  textureSet.SetImage( 0u, frameBufferImage );
+  textureSet.SetSampler( 0u, sampler );
+
+  Geometry meshGeometry;
+  CreateGeometry( meshGeometry );
+
+  renderer = Renderer::New( meshGeometry, shader );
+  renderer.SetTextures( textureSet );
+}
+
+} // namespace
+
+namespace Text
+{
+
+TextScrollerPtr TextScroller::New( ScrollerInterface& scrollerInterface )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::New\n" );
+
+  TextScrollerPtr textScroller( new TextScroller( scrollerInterface) );
+  return textScroller;
+}
+
+void TextScroller::SetGap( int gap )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::SetGap gap[%d]\n", gap );
+  mWrapGap = gap;
+}
+
+int TextScroller::GetGap() const
+{
+  return mWrapGap;
+}
+
+void TextScroller::SetSpeed( int scrollSpeed )
+{
+  mScrollSpeed = std::max( MINIMUM_SCROLL_SPEED, scrollSpeed );
+}
+
+int TextScroller::GetSpeed() const
+{
+  return mScrollSpeed;
+}
+
+void TextScroller::SetLoopCount( int loopCount )
+{
+  if ( loopCount > 0 )
+  {
+    mLoopCount = loopCount;
+  }
+
+  if (  mScrollAnimation && mScrollAnimation.GetState() == Animation::PLAYING )
+  {
+    if ( loopCount == 0 ) // Request to stop looping
+    {
+      DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::SetLoopCount Single loop forced\n" );
+      mScrollAnimation.SetLoopCount( 1 ); // As animation already playing this allows the current animation to finish instead of trying to stop mid-way
+    }
+  }
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::SetLoopCount [%d] Status[%s]\n", mLoopCount, (loopCount)?"looping":"stop" );
+}
+
+int TextScroller::GetLoopCount() const
+{
+  return mLoopCount;
+}
+
+Actor TextScroller::GetSourceCamera() const
+{
+  return mOffscreenCameraActor;
+}
+
+Actor TextScroller::GetScrollingText() const
+{
+  return mScrollingTextActor;
+}
+
+TextScroller::TextScroller( ScrollerInterface& scrollerInterface ) : mScrollerInterface( scrollerInterface ),
+                            mScrollDeltaIndex( Property::INVALID_INDEX ),
+                            mScrollSpeed( MINIMUM_SCROLL_SPEED ),
+                            mLoopCount( 1 ),
+                            mWrapGap( 0 )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller Default Constructor\n" );
+}
+
+TextScroller::~TextScroller()
+{
+  CleanUp();
+}
+
+void TextScroller::SetParameters( Actor sourceActor, const Size& controlSize, const Size& offScreenSize, CharacterDirection direction, const Vector2 alignmentOffset )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::SetParameters controlSize[%f,%f] offscreenSize[%f,%f] direction[%d] alignmentOffset[%f,%f]\n",
+                 controlSize.x, controlSize.y, offScreenSize.x, offScreenSize.y, direction, alignmentOffset.x, alignmentOffset.y );
+
+  FrameBufferImage offscreenRenderTargetForText = FrameBufferImage::New( offScreenSize.width, offScreenSize.height, Pixel::RGBA8888, Dali::Image::UNUSED );
+  Renderer renderer;
+
+  CreateCameraActor( offScreenSize, mOffscreenCameraActor );
+  CreateRenderer( offscreenRenderTargetForText, renderer );
+  CreateRenderTask( sourceActor, mOffscreenCameraActor, offscreenRenderTargetForText, mRenderTask );
+
+  // Reposition camera to match alignment of target, RTL text has direction=true
+  if ( direction )
+  {
+    mOffscreenCameraActor.SetX( alignmentOffset.x + offScreenSize.width*0.5f );
+  }
+  else
+  {
+    mOffscreenCameraActor.SetX( offScreenSize.width * 0.5f );
+  }
+
+  mOffscreenCameraActor.SetY( offScreenSize.height * 0.5f );
+
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::SetParameters mWrapGap[%d]\n", mWrapGap )
+
+  mScrollingTextActor = Actor::New();
+  mScrollingTextActor.AddRenderer( renderer );
+  mScrollingTextActor.RegisterProperty( "uTextureSize", offScreenSize );
+  mScrollingTextActor.RegisterProperty( "uRtl", ((direction)?1.0f:0.0f) );
+  mScrollingTextActor.RegisterProperty( "uGap", mWrapGap );
+  mScrollingTextActor.SetSize( controlSize.width, std::min( offScreenSize.height, controlSize.height ) );
+  mScrollDeltaIndex = mScrollingTextActor.RegisterProperty( "uDelta", 0.0f );
+
+  float scrollAmount = std::max( offScreenSize.width + mWrapGap, controlSize.width );
+  float scrollDuration =  scrollAmount / mScrollSpeed;
+
+  if ( direction  )
+  {
+     scrollAmount = -scrollAmount; // reverse direction of scrollung
+  }
+
+  StartScrolling( scrollAmount, scrollDuration, mLoopCount );
+}
+
+void TextScroller::AutoScrollAnimationFinished( Dali::Animation& animation )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::AutoScrollAnimationFinished\n" );
+  CleanUp();
+  mScrollerInterface.ScrollingFinished();
+}
+
+void TextScroller::StartScrolling( float scrollAmount, float scrollDuration, int loopCount )
+{
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "TextScroller::StartScrolling scrollAmount[%f] scrollDuration[%f], loop[%d] speed[%d]\n", scrollAmount, scrollDuration, loopCount, mScrollSpeed );
+
+  mScrollAnimation = Animation::New( scrollDuration );
+  mScrollAnimation.AnimateTo( Property( mScrollingTextActor, mScrollDeltaIndex ), scrollAmount );
+  mScrollAnimation.SetEndAction( Animation::Discard );
+  mScrollAnimation.SetLoopCount( loopCount );
+  mScrollAnimation.FinishedSignal().Connect( this, &TextScroller::AutoScrollAnimationFinished );
+  mScrollAnimation.Play();
+}
+
+void TextScroller::CleanUp()
+{
+  if ( Stage::IsInstalled() )
+  {
+    Stage stage = Stage::GetCurrent();
+    RenderTaskList taskList = stage.GetRenderTaskList();
+    UnparentAndReset( mScrollingTextActor );
+    UnparentAndReset( mOffscreenCameraActor );
+    taskList.RemoveTask( mRenderTask );
+  }
+}
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
diff --git a/dali-toolkit/internal/text/text-scroller.h b/dali-toolkit/internal/text/text-scroller.h
new file mode 100644 (file)
index 0000000..d4f92b9
--- /dev/null
@@ -0,0 +1,177 @@
+#ifndef __DALI_TOOLKIT_TEXT_SCROLLER_H__
+#define __DALI_TOOLKIT_TEXT_SCROLLER_H__
+
+/*
+ * Copyright (c) 2016 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/actors/camera-actor.h>
+#include <dali/public-api/animation/animation.h>
+#include <dali/public-api/render-tasks/render-task.h>
+
+// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/text-definitions.h>
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Text
+{
+
+class TextScroller;
+class ScrollerInterface;
+
+typedef IntrusivePtr<TextScroller> TextScrollerPtr;
+
+/**
+ * @brief A helper class for scrolling text
+ */
+class TextScroller : public RefObject, public ConnectionTracker
+{
+public:
+
+  /**
+   * @brief Text Scrolling helper, used to automatically scroll text, SetParameters should be called before scrolling is needed.
+   * CleanUp removes the Scrolling actors from stage whilst keeping the Scroller object alive and preserving Speed, Gap and Loop count.
+   *
+   * @param[in] scrollerInterface scroller interface
+   */
+  static TextScrollerPtr New( ScrollerInterface& scrollerInterface );
+
+  /**
+   * @brief Set parameters relating to source required for scrolling
+   *
+   * @param[in] sourceActor source actor to be scrolled
+   * @param[in] controlSize size of the control to scroll within
+   * @param[in] offScreenSize size of the sourceActor
+   * @param[in] direction text direction true for right to left text
+   * @param[in] alignmentOffset alignment of source text
+   *
+   */
+  void SetParameters( Actor sourceActor, const Size& controlSize, const Size& offScreenSize, CharacterDirection direction, const Vector2 alignmentOffset );
+
+  /**
+   * @brief Set the gap distance to elapse before the text wraps around
+   * @param[in] gap distance to elapse
+   */
+  void SetGap( int gap );
+
+  /**
+   * @brief Get the distance before scrolling wraps
+   * @return gap distance to elapse
+   */
+  int GetGap() const;
+
+  /**
+   * @brief Set speed the text should scroll
+   * @param[in] scrollSpeed pixels per second
+   */
+  void SetSpeed( int scrollSpeed );
+
+  /**
+   * @brief Get the speed of text scrolling
+   * @return speed in pixels per second
+   */
+  int GetSpeed() const;
+
+  /**
+   * @brief Set the number of times the text scrolling should loop, can stop current scrolling by passing in 0;
+   * @param[in] loopCount number of times the scrolled text should loop, 0 to stop scrolling
+   */
+  void SetLoopCount( int loopCount );
+
+  /**
+   * @brief Get the number of loops
+   * @return int number of loops
+   */
+  int GetLoopCount() const;
+
+  /**
+   * @brief Get the camera used to look at source, should be added to the parent of target actor.
+   * @return camera Actor
+   */
+  Actor GetSourceCamera() const;
+
+  /**
+   * @brief Get the resulting scrolling text actor, add to target actor which will show scrolling text
+   * @return mesh Actor
+   */
+  Actor GetScrollingText() const;
+
+private: // Implementation
+
+  /**
+   * Constructor
+   */
+  TextScroller( ScrollerInterface& scrollerInterface );
+
+  /**
+   * Destructor
+   */
+  ~TextScroller();
+
+  // Undefined
+  TextScroller( const TextScroller& handle );
+
+  // Undefined
+  TextScroller& operator=( const TextScroller& handle );
+
+  /**
+   * @brief Callback for end of animation
+   * @param[in] animation Animation handle
+   */
+  void AutoScrollAnimationFinished( Dali::Animation& animation );
+
+  /**
+   * @brief variables required to set up scrolling animation
+   * @param[in] scrollAmount distance to animate text for the given duration
+   * @param[in] scrollDuration duration of aninmation
+   * @param[in] loopCount number of times to loop the scrolling text
+   */
+  void StartScrolling( float scrollAmount, float scrollDuration, int loopCount );
+
+  /**
+   * @brief When scrolling ended, the actors are cleaned up so no longer staged.
+   */
+  void CleanUp();
+
+private:
+
+  RenderTask         mRenderTask;               // Renders full text to a FrameBuffer which is then scrolled.
+  CameraActor        mOffscreenCameraActor;     // Camera used by render task
+  Actor              mScrollingTextActor;       // Actor used to show scrolling text
+  ScrollerInterface& mScrollerInterface;        // Interface implemented by control that requires scrolling
+  Property::Index    mScrollDeltaIndex;         // Property used by shader to represent distance to scroll
+  Animation          mScrollAnimation;          // Animation used to update the mScrollDeltaIndex
+
+  int mScrollSpeed;            ///< Speed which text should automatically scroll at
+  int mLoopCount;              ///< Number of time the text should scroll
+  int mWrapGap;                ///< Gap before text wraps around when scrolling
+
+}; // TextScroller class
+
+} // namespace Text
+
+} // namespace Toolkit
+
+} // namespace Dali
+
+#endif // __DALI_TOOLKIT_TEXT_SCROLLER_H__
+
index f5f1c49..eaa191d 100644 (file)
@@ -36,7 +36,7 @@ namespace Text
 struct GlyphRun;
 
 /**
- * @brief Abstract interface to provide the information necessary displaying text.
+ * @brief Abstract interface to provide the information necessary to display text.
  *
  * This includes:
  * - The font & glyph IDs needed to get bitmaps etc. from TextAbstraction
@@ -60,7 +60,7 @@ public:
   /**
    * @brief Retrieves the target size of the UI control.
    *
-   * @return The text's size.
+   * @return The control's size.
    */
   virtual const Vector2& GetControlSize() const = 0;
 
index 88e3930..7c1accb 100644 (file)
@@ -332,7 +332,6 @@ public:
 
   bool                   mUnderlineEnabled:1;   ///< Underline enabled flag
   bool                   mUnderlineColorSet:1;  ///< Has the underline color been explicitly set?
-
 };
 
 } // namespace Text
index 10ffbff..3026d9c 100644 (file)
@@ -105,8 +105,7 @@ void CubeTransitionCrossEffect::OnStartTransition( Vector2 panPosition, Vector2
     }
   }
 
-  const Vector2& size = Self().GetCurrentSize().GetVectorXY();
-  Vector2 halfSize = size * 0.5f;
+  const Vector2 halfSize = Self().GetCurrentSize().GetVectorXY() * 0.5f;
   //the centre to "explode" the tiles outwards from
   Vector3 centre( halfSize.x, halfSize.y, -1.0f / mDisplacementSpreadFactor );
 
@@ -130,7 +129,7 @@ void CubeTransitionCrossEffect::OnStartTransition( Vector2 panPosition, Vector2
 
 void CubeTransitionCrossEffect::SetupAnimation( unsigned int actorIndex, unsigned int x, unsigned int y, float angle, const Vector3 axis, const Vector3& displacementCentre )
 {
-  const Vector2& size = Self().GetCurrentSize().GetVectorXY();
+  const Vector2 size = Self().GetCurrentSize().GetVectorXY();
   Vector2 halfSize = size * 0.5f;
 
   //the position of the centre of the front face tile
index 1cee6e1..3a31a49 100644 (file)
@@ -84,33 +84,6 @@ Actor CreateTile( const Vector4& samplerRect )
   return tile;
 }
 
-
-Geometry CreateQuadGeometry()
-{
-  const float halfWidth = 0.5f;
-  const float halfHeight = 0.5f;
-  struct QuadVertex { Vector2 position;};
-  QuadVertex quadVertexData[4] =
-  {
-      { Vector2(-halfWidth, -halfHeight) },
-      { Vector2( halfWidth, -halfHeight) },
-      { Vector2(-halfWidth, halfHeight)  },
-      { Vector2( halfWidth, halfHeight)  }
-  };
-
-  Property::Map quadVertexFormat;
-  quadVertexFormat["aPosition"] = Property::VECTOR2;
-  PropertyBuffer quadVertices = PropertyBuffer::New( quadVertexFormat );
-  quadVertices.SetData( quadVertexData, 4 );
-
-  // Create the geometry object
-  Geometry geometry = Geometry::New();
-  geometry.AddVertexBuffer( quadVertices );
-  geometry.SetGeometryType( Geometry::TRIANGLE_STRIP );
-
-  return geometry;
-}
-
 }
 
 const Vector4 CubeTransitionEffect::FULL_BRIGHTNESS( 1.0f, 1.0f, 1.0f, 1.0f );
@@ -272,7 +245,7 @@ void CubeTransitionEffect::OnStageConnection( int depth )
 {
   Control::OnStageConnection( depth );
 
-  Geometry geometry = CreateQuadGeometry();
+  Geometry geometry = Geometry::QUAD();
   Shader shader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
 
   TextureSet textureSet = TextureSet::New();
index d4ce91d..525a61e 100644 (file)
@@ -109,7 +109,7 @@ void CubeTransitionWaveEffect::OnStartTransition( Vector2 panPosition, Vector2 p
 
 void  CubeTransitionWaveEffect::CalculateSaddleSurfaceParameters( Vector2 position, Vector2 displacement )
 {
-  const Vector2& size = Self().GetCurrentSize().GetVectorXY();
+  const Vector2 size = Self().GetCurrentSize().GetVectorXY();
   // the line passes through 'position' and has the direction of 'displacement'
   float coefA, coefB, coefC; //line equation: Ax+By+C=0;
   coefA = displacement.y;
@@ -16,7 +16,7 @@
  */
 
 // CLASS HEADER
-#include <dali-toolkit/devel-api/controls/flex-container/flex-container.h>
+#include <dali-toolkit/public-api/controls/flex-container/flex-container.h>
 
 // INTERNAL INCLUDES
 #include <dali-toolkit/internal/controls/flex-container/flex-container-impl.h>
@@ -92,12 +92,13 @@ class FlexContainer;
  * "name":"icon",
  * "type":"ImageView",
  * "image":"image.png",
- *   "customProperties": {
- *     "flex":1,                        // property to make the item to receive the specified proportion of the free space in the container. If all items in the container use this pattern, their sizes will be proportional to the specified flex factor.
- *     "alignSelf":"flexStart",         // property to specify how the item will align along the cross axis, if set, this overides the default alignment for all items in the container
- *     "flexMargin":[10, 10, 10, 10]    // property to specify the space around the item, if not set, default value is [0, 0, 0, 0]
+ *   "properties": {
+ *     "flex":1,                        // property to make the item to receive the specified proportion of the free space in the container.
+ *     "alignSelf":"flexStart",         // property to specify how the item will align along the cross axis.
+ *     "flexMargin":[10, 10, 10, 10]    // property to specify the space around the item.
  *   }
  * @endcode
+ * @SINCE_1_1.35
  */
 
 class DALI_IMPORT_API FlexContainer : public Control
@@ -107,122 +108,161 @@ public:
   /**
    * @brief The direction of the main axis in the flex container. This determines
    * the direction that flex items are laid out in the flex container.
+   * @SINCE_1_1.35
    */
   enum FlexDirection
   {
-    COLUMN,                  ///< The flexible items are displayed vertically as a column
-    COLUMN_REVERSE,          ///< The flexible items are displayed vertically as a column, but in reverse order
-    ROW,                     ///< The flexible items are displayed horizontally as a row
-    ROW_REVERSE              ///< The flexible items are displayed horizontally as a row, but in reverse order
+    COLUMN,                  ///< The flexible items are displayed vertically as a column @SINCE_1_1.35
+    COLUMN_REVERSE,          ///< The flexible items are displayed vertically as a column, but in reverse order @SINCE_1_1.35
+    ROW,                     ///< The flexible items are displayed horizontally as a row @SINCE_1_1.35
+    ROW_REVERSE              ///< The flexible items are displayed horizontally as a row, but in reverse order @SINCE_1_1.35
   };
 
   /**
    * @brief The primary direction in which content is ordered in the flex container
    * and on which sides the “start” and “end” are.
+   * @SINCE_1_1.35
    */
   enum ContentDirection
   {
-    INHERIT,                 ///< Inherits the same direction from the parent
-    LTR,                     ///< From left to right
-    RTL                      ///< From right to left
+    INHERIT,                 ///< Inherits the same direction from the parent @SINCE_1_1.35
+    LTR,                     ///< From left to right @SINCE_1_1.35
+    RTL                      ///< From right to left @SINCE_1_1.35
   };
 
   /**
    * @brief Alignment of the flex items when the items do not use all available
    * space on the main-axis.
+   * @SINCE_1_1.35
    */
   enum Justification
   {
-    JUSTIFY_FLEX_START,      ///< Items are positioned at the beginning of the container
-    JUSTIFY_CENTER,          ///< Items are positioned at the center of the container
-    JUSTIFY_FLEX_END,        ///< Items are positioned at the end of the container
-    JUSTIFY_SPACE_BETWEEN,   ///< Items are positioned with equal space between the lines
-    JUSTIFY_SPACE_AROUND     ///< Items are positioned with equal space before, between, and after the lines
+    JUSTIFY_FLEX_START,      ///< Items are positioned at the beginning of the container @SINCE_1_1.35
+    JUSTIFY_CENTER,          ///< Items are positioned at the center of the container @SINCE_1_1.35
+    JUSTIFY_FLEX_END,        ///< Items are positioned at the end of the container @SINCE_1_1.35
+    JUSTIFY_SPACE_BETWEEN,   ///< Items are positioned with equal space between the lines @SINCE_1_1.35
+    JUSTIFY_SPACE_AROUND     ///< Items are positioned with equal space before, between, and after the lines @SINCE_1_1.35
   };
 
   /**
    * @brief Alignment of the flex items or lines when the items or lines do not
    * use all available space on the cross-axis.
+   * @SINCE_1_1.35
    */
   enum Alignment
   {
-    ALIGN_AUTO,              ///< Inherits the same alignment from the parent (only valid for "alignSelf" property)
-    ALIGN_FLEX_START,        ///< At the beginning of the container
-    ALIGN_CENTER,            ///< At the center of the container
-    ALIGN_FLEX_END,          ///< At the end of the container
-    ALIGN_STRETCH            ///< Stretch to fit the container
+    ALIGN_AUTO,              ///< Inherits the same alignment from the parent (only valid for "alignSelf" property) @SINCE_1_1.35
+    ALIGN_FLEX_START,        ///< At the beginning of the container @SINCE_1_1.35
+    ALIGN_CENTER,            ///< At the center of the container @SINCE_1_1.35
+    ALIGN_FLEX_END,          ///< At the end of the container @SINCE_1_1.35
+    ALIGN_STRETCH            ///< Stretch to fit the container @SINCE_1_1.35
   };
 
   /**
    * @brief The wrap type of the flex container when there is no enough room for
    * all the items on one flex line.
+   * @SINCE_1_1.35
    */
   enum WrapType
   {
-    NO_WRAP,                 ///< Flex items laid out in single line (shrunk to fit the flex container along the main axis)
-    WRAP                     ///< Flex items laid out in multiple lines if needed
+    NO_WRAP,                 ///< Flex items laid out in single line (shrunk to fit the flex container along the main axis) @SINCE_1_1.35
+    WRAP                     ///< Flex items laid out in multiple lines if needed @SINCE_1_1.35
   };
 
 public:
 
   /**
    * @brief The start and end property ranges for this control.
+   * @SINCE_1_1.35
    */
   enum PropertyRange
   {
-    PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,
-    PROPERTY_END_INDEX =   PROPERTY_START_INDEX + 1000              ///< Reserve property indices
+    PROPERTY_START_INDEX = Control::CONTROL_PROPERTY_END_INDEX + 1,               ///< @SINCE_1_1.35
+    PROPERTY_END_INDEX =   PROPERTY_START_INDEX + 1000,                           ///< Reserve property indices @SINCE_1_1.35
+
+    CHILD_PROPERTY_START_INDEX = CHILD_PROPERTY_REGISTRATION_START_INDEX,         ///< @SINCE_1_1.35
+    CHILD_PROPERTY_END_INDEX =   CHILD_PROPERTY_REGISTRATION_START_INDEX + 1000   ///< Reserve child property indices @SINCE_1_1.35
   };
 
   /**
    * @brief An enumeration of properties belonging to the FlexContainer class.
+   * @SINCE_1_1.35
    */
   struct Property
   {
     enum
     {
-      CONTENT_DIRECTION = PROPERTY_START_INDEX, ///< name "contentDirection",   The primary direction in which content is ordered,                                                 @see FlexContainer::ContentDirection,  type INTEGER
-      FLEX_DIRECTION,                           ///< name "flexDirection",      The direction of the main-axis which determines the direction that flex items are laid out,        @see FlexContainer::FlexDirection,     type INTEGER
-      FLEX_WRAP,                                ///< name "flexWrap",           Whether the flex items should wrap or not if there is no enough room for them on one flex line,    @see FlexContainer::WrapType,          type INTEGER
-      JUSTIFY_CONTENT,                          ///< name "justifyContent",     The alignment of flex items when the items do not use all available space on the main-axis,        @see FlexContainer::Justification,     type INTEGER
-      ALIGN_ITEMS,                              ///< name "alignItems",         The alignment of flex items when the items do not use all available space on the cross-axis,       @see FlexContainer::Alignment,         type INTEGER
-      ALIGN_CONTENT                             ///< name "alignContent",       Similar to "alignItems", but it aligns flex lines, so only works when there are multiple lines,    @see FlexContainer::Alignment,         type INTEGER
+      // Event side properties
+      CONTENT_DIRECTION = PROPERTY_START_INDEX, ///< name "contentDirection",   The primary direction in which content is ordered,                                                 @see FlexContainer::ContentDirection,  type INTEGER @SINCE_1_1.35
+      FLEX_DIRECTION,                           ///< name "flexDirection",      The direction of the main-axis which determines the direction that flex items are laid out,        @see FlexContainer::FlexDirection,     type INTEGER @SINCE_1_1.35
+      FLEX_WRAP,                                ///< name "flexWrap",           Whether the flex items should wrap or not if there is no enough room for them on one flex line,    @see FlexContainer::WrapType,          type INTEGER @SINCE_1_1.35
+      JUSTIFY_CONTENT,                          ///< name "justifyContent",     The alignment of flex items when the items do not use all available space on the main-axis,        @see FlexContainer::Justification,     type INTEGER @SINCE_1_1.35
+      ALIGN_ITEMS,                              ///< name "alignItems",         The alignment of flex items when the items do not use all available space on the cross-axis,       @see FlexContainer::Alignment,         type INTEGER @SINCE_1_1.35
+      ALIGN_CONTENT                             ///< name "alignContent",       Similar to "alignItems", but it aligns flex lines, so only works when there are multiple lines,    @see FlexContainer::Alignment,         type INTEGER @SINCE_1_1.35
     };
   };
 
   /**
-   * Create a FlexContainer handle; this can be initialised with FlexContainer::New()
+   * @brief An enumeration of child properties belonging to the FlexContainer class.
+   * @SINCE_1_1.35
+   */
+  struct ChildProperty
+  {
+    enum
+    {
+      // Event side child properties
+      FLEX = CHILD_PROPERTY_START_INDEX,        ///< name "flex",               The proportion of the free space in the container the flex item will receive. If all items in the container set this property, their sizes will be proportional to the specified flex factor,  type FLOAT @SINCE_1_1.35
+      ALIGN_SELF,                               ///< name "alignSelf",          The alignment of the flex item along the cross axis, which, if set, overides the default alignment for all items in the container,                          @see FlexContainer::Alignment,     type INTEGER @SINCE_1_1.35
+      FLEX_MARGIN                               ///< name "flexMargin",         The space around the flex item,                                                                                                                                                                type VECTOR4 @SINCE_1_1.35
+    };
+  };
+
+  /**
+   * @brief Create a FlexContainer handle; this can be initialised with FlexContainer::New()
    * Calling member functions with an uninitialised handle is not allowed.
+   * @SINCE_1_1.35
    */
   FlexContainer();
 
   /**
-   * Copy constructor. Creates another handle that points to the same real object
-   * @param handle to copy from
+   * @brief Copy constructor. Creates another handle that points to the same real object
+   * @SINCE_1_1.35
+   *
+   * @param[in] handle The handle to copy from
    */
   FlexContainer( const FlexContainer& handle );
 
   /**
-   * Assignment operator. Changes this handle to point to another real object
+   * @brief Assignment operator. Changes this handle to point to another real object
+   * @SINCE_1_1.35
    */
   FlexContainer& operator=( const FlexContainer& handle );
 
   /**
    * @brief Destructor
    *
-   * This is non-virtual since derived Handle types must not contain data or virtual methods.
+   * @details This is non-virtual since derived Handle types must not contain data or virtual methods.
+   *
+   * @SINCE_1_1.35
    */
   ~FlexContainer();
 
   /**
-   * Create the FlexContainer control.
+   * @brief Create the FlexContainer control.
+   * @SINCE_1_1.35
+   *
    * @return A handle to the FlexContainer control.
    */
   static FlexContainer New();
 
   /**
-   * Downcast an Object handle to FlexContainer. If handle points to a FlexContainer the
-   * downcast produces valid handle. If not the returned handle is left uninitialized.
+   * @brief Downcast an Object handle to FlexContainer.
+   *
+   * @details If handle points to a FlexContainer the downcast produces
+   * valid handle. If not the returned handle is left uninitialized.
+   *
+   * @SINCE_1_1.35
+   *
    * @param[in] handle Handle to an object
    * @return handle to a FlexContainer or an uninitialized handle
    */
@@ -233,6 +273,7 @@ public: // Not intended for application developers
 
   /**
    * @brief Creates a handle using the Toolkit::Internal implementation.
+   * @SINCE_1_1.35
    *
    * @param[in] implementation The Control implementation.
    */
@@ -240,6 +281,7 @@ public: // Not intended for application developers
 
   /**
    * @brief Allows the creation of this Control from an Internal::CustomActor pointer.
+   * @SINCE_1_1.35
    *
    * @param[in] internal A pointer to the internal CustomActor.
    */
index 317918e..33e95f1 100644 (file)
@@ -40,6 +40,30 @@ class TextLabel;
  * @brief A control which renders a short text string.
  *
  * Text labels are lightweight, non-editable and do not respond to user input.
+ *
+ * @section TextLabelProperties Properties
+ * |%Property enum                    |String name          |Type          |Writable|Animatable|
+ * |----------------------------------|---------------------|--------------|--------|----------|
+ * | Property::RENDERING_BACKEND      | renderingBackend    |  INTEGER     | O      | X        |
+ * | Property::TEXT                   | text                |  STRING      | O      | X        |
+ * | Property::FONT_FAMILY            | fontFamily          |  STRING      | O      | X        |
+ * | Property::FONT_STYLE             | fontStyle           |  STRING      | O      | X        |
+ * | Property::POINT_SIZE             | pointSize           |  FLOAT       | O      | X        |
+ * | Property::MULTI_LINE             | multiLine           |  BOOLEAN     | O      | X        |
+ * | Property::HORIZONTAL_ALIGNMENT   | horizontalAlignment |  STRING      | O      | X        |
+ * | Property::VERTICAL_ALIGNMENT     | verticalAlignment   |  STRING      | O      | X        |
+ * | Property::TEXT_COLOR             | textColor           |  VECTOR4     | O      | X        |
+ * | Property::SHADOW_OFFSET          | shadowOffset        |  VECTOR2     | O      | X        |
+ * | Property::SHADOW_COLOR           | shadowColor         |  VECTOR4     | O      | X        |
+ * | Property::UNDERLINE_ENABLED      | underlineEnabled    |  BOOLEAN     | O      | X        |
+ * | Property::UNDERLINE_COLOR        | underlineColor      |  VECTOR4     | O      | X        |
+ * | Property::UNDERLINE_HEIGHT       | underlineHeight     |  FLOAT       | O      | X        |
+ * | Property::ENABLE_MARKUP          | enableMarkup        |  BOOLEAN     | O      | X        |
+ * | Property::ENABLE_AUTO_SCROLL     | enableAutoScroll    |  BOOLEAN     | O      | X        |
+ * | Property::AUTO_SCROLL_SPEED      | autoScrollSpeed     |  INTEGER     | O      | X        |
+ * | Property::AUTO_SCROLL_LOOP_COUNT | autoScrollLoopCount |  INTEGER     | O      | X        |
+ * | Property::AUTO_SCROLL_GAP        | autoScrollGap       |  INTEGER     | O      | X        |
+ *
  * @SINCE_1_0.0
  */
 class DALI_IMPORT_API TextLabel : public Control
@@ -64,21 +88,138 @@ public:
   {
     enum
     {
-      RENDERING_BACKEND = PROPERTY_START_INDEX, ///< name "renderingBackend",     The type or rendering e.g. bitmap-based,          type INT @SINCE_1_0.0
-      TEXT,                                     ///< name "text",                 The text to display in UTF-8 format,              type STRING @SINCE_1_0.0
-      FONT_FAMILY,                              ///< name "fontFamily",           The requested font family,                        type STRING @SINCE_1_0.0
-      FONT_STYLE,                               ///< name "fontStyle",            The requested font style,                         type STRING @SINCE_1_0.0
-      POINT_SIZE,                               ///< name "pointSize",            The size of font in points,                       type FLOAT @SINCE_1_0.0
-      MULTI_LINE,                               ///< name "multiLine",            The single-line or multi-line layout option,      type BOOLEAN @SINCE_1_0.0
-      HORIZONTAL_ALIGNMENT,                     ///< name "horizontalAlignment",  The line horizontal alignment,                    type STRING,  values "BEGIN", "CENTER", "END" @SINCE_1_0.0
-      VERTICAL_ALIGNMENT,                       ///< name "verticalAlignment",    The line vertical alignment,                      type STRING,  values "TOP",   "CENTER", "BOTTOM" @SINCE_1_0.0
-      TEXT_COLOR,                               ///< name "textColor",            The text color,                                   type VECTOR4 @SINCE_1_0.0
-      SHADOW_OFFSET,                            ///< name "shadowOffset",         The drop shadow offset 0 indicates no shadow,     type VECTOR2 @SINCE_1_0.0
-      SHADOW_COLOR,                             ///< name "shadowColor",          The color of a drop shadow,                       type VECTOR4 @SINCE_1_0.0
-      UNDERLINE_ENABLED,                        ///< name "underlineEnabled",     The underline enabled flag,                       type BOOLEAN @SINCE_1_0.0
-      UNDERLINE_COLOR,                          ///< name "underlineColor",       The color of the underline,                       type VECTOR4 @SINCE_1_0.0
-      UNDERLINE_HEIGHT,                         ///< name "underlineHeight",      Overrides the underline height from font metrics, type FLOAT @SINCE_1_0.0
-      ENABLE_MARKUP                             ///< name "enableMarkup",         Whether the mark-up processing is enabled.        type BOOLEAN @SINCE_1_0.0
+      /**
+       * @brief The type of rendering e.g. bitmap-based
+       * @details name "renderingBackend", type INT, default RENDERING_SHARED_ATLAS
+       * @SINCE_1_0.0
+       */
+      RENDERING_BACKEND = PROPERTY_START_INDEX,
+
+      /**
+       * @brief The text to display in UTF-8 format,
+       * @details name "text", type STRING
+       * @SINCE_1_0.0
+       */
+      TEXT,
+
+      /**
+       * @brief The requested font family to use,
+       * @details name "fontFamily", type STRING
+       * @SINCE_1_0.0
+       */
+      FONT_FAMILY,
+
+      /**
+       * @brief The requested font style to use,
+       * @details name "fontStyle", type STRING
+       * @SINCE_1_0.0
+       */
+      FONT_STYLE,
+
+      /**
+       * @brief The size of font in points
+       * @details name "pointSize", type FLOAT
+       * @SINCE_1_0.0
+       */
+      POINT_SIZE,
+
+      /**
+       * @brief The single-line or multi-line layout option
+       * @details name "multiLine", type FLOAT, default SINGLE_LINE_BOX
+       * @SINCE_1_0.0
+       */
+      MULTI_LINE,
+
+      /**
+       * @brief The line horizontal alignment
+       * @details name "horizontalAlignment", type STRING,  values "BEGIN", "CENTER", "END", default BEGIN
+       * @SINCE_1_0.0
+       */
+      HORIZONTAL_ALIGNMENT,
+
+      /**
+       * @brief The line vertical alignment
+       * @details name "verticalAlignment", type STRING,  values "TOP",   "CENTER", "BOTTOM" @SINCE_1_0.0, default TOP
+       * @SINCE_1_0.0
+       */
+      VERTICAL_ALIGNMENT,
+
+      /**
+       * @brief The color of the text
+       * @details name "textColor", type VECTOR4
+       * @SINCE_1_0.0
+       */
+      TEXT_COLOR,
+
+      /**
+       * @brief The drop shadow offset 0 indicates no shadow
+       * @details name "shadowOffset", type VECTOR4
+       * @SINCE_1_0.0
+       */
+      SHADOW_OFFSET,
+
+      /**
+       * @brief The color of a drop shadow
+       * @details name "shadowColor", type VECTOR4
+       * @SINCE_1_0.0
+       */
+      SHADOW_COLOR,
+
+      /**
+       * @brief The underline enabled flag
+       * @details name "underlineEnabled", type BOOLEAN
+       * @SINCE_1_0.0
+       */
+      UNDERLINE_ENABLED,
+
+      /**
+       * @brief The color of the underline
+       * @details name "underlineColor", type VECTOR4
+       * @SINCE_1_0.0
+       */
+      UNDERLINE_COLOR,
+
+      /**
+       * @brief Overrides the underline height from font metrics
+       * @details name "underlineHeight", type FLOAT
+       * @SINCE_1_0.0
+       */
+      UNDERLINE_HEIGHT,
+
+      /**
+       * @brief  Whether the mark-up processing is enabled
+       * @details name "enableMarkup", type BOOLEAN
+       * @SINCE_1_0.0
+       */
+      ENABLE_MARKUP,
+
+      /**
+       * @brief  Start or stop auto scrolling,
+       * @details name "enableMarkup", type BOOLEAN, default is false
+       * @SINCE_1_1.35
+       */
+      ENABLE_AUTO_SCROLL,
+
+      /**
+       * @brief  Start or stop auto scrolling,
+       * @details name "autoScrollSpeed", type INT, default in style sheet
+       * @SINCE_1_1.35
+       */
+      AUTO_SCROLL_SPEED,
+
+      /**
+       * @brief  Number of complete loops when scrolling enabled
+       * @details name "autoScrollLoopCount", type INT, default in style sheet
+       * @SINCE_1_1.35
+       */
+      AUTO_SCROLL_LOOP_COUNT,
+
+      /**
+       * @brief  Gap before before scrolling wraps
+       * @details name "autoScrollGap", type INT, default in style sheet but can be overridden to prevent same text being show at start and end.
+       * @SINCE_1_1.35
+       */
+      AUTO_SCROLL_GAP
     };
   };
 
index 7bead86..5f42b15 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 = 34;
+const unsigned int TOOLKIT_MICRO_VERSION = 35;
 const char * const TOOLKIT_BUILD_DATE    = __DATE__ " " __TIME__;
 
 #ifdef DEBUG_ENABLED
index 16d923f..a7b1a02 100755 (executable)
@@ -9,6 +9,7 @@ public_api_src_files = \
   $(public_api_src_dir)/controls/buttons/push-button.cpp \
   $(public_api_src_dir)/controls/buttons/radio-button.cpp \
   $(public_api_src_dir)/controls/default-controls/solid-color-actor.cpp \
+  $(public_api_src_dir)/controls/flex-container/flex-container.cpp \
   $(public_api_src_dir)/controls/image-view/image-view.cpp \
   $(public_api_src_dir)/controls/model3d-view/model3d-view.cpp \
   $(public_api_src_dir)/controls/page-turn-view/page-turn-landscape-view.cpp \
@@ -58,6 +59,9 @@ public_api_default_controls_header_files = \
 public_api_model3d_view_header_files = \
   $(public_api_src_dir)/controls/model3d-view/model3d-view.h
 
+public_api_flex_container_header_files = \
+  $(public_api_src_dir)/controls/flex-container/flex-container.h
+
 public_api_gaussian_blur_view_header_files = \
   $(public_api_src_dir)/controls/gaussian-blur-view/gaussian-blur-view.h
 
index 4ecc335..725a71a 100644 (file)
   {
     "textlabel":
     {
-      "pointSize":18
+      "pointSize":18,
+      "enableAutoScroll":false,
+      "autoScrollLoopCount":2,
+      "autoScrollGap":50,
+      "autoScrollSpeed":80
     },
 
     "textlabelFontSize0":
index ffe9326..3297e51 100644 (file)
   {
     "textlabel":
     {
-      "pointSize":18
+      "pointSize":18,
+      "enableAutoScroll":false,
+      "autoScrollLoopCount":2,
+      "autoScrollGap":50,
+      "autoScrollSpeed":80
     },
 
     "textlabelFontSize0":
diff --git a/docs/content/images/text-controls/AutoScroll.gif b/docs/content/images/text-controls/AutoScroll.gif
new file mode 100644 (file)
index 0000000..663cd3b
Binary files /dev/null and b/docs/content/images/text-controls/AutoScroll.gif differ
index 8acacaa..056ea1e 100644 (file)
@@ -249,23 +249,23 @@ flexContainer.SetProperty( Dali::Toolkit::FlexContainer::Property::FLEX_DIRECTIO
 
 // Create flex items and set the proportion
 Dali::Toolkit::Control item1 = Dali::Toolkit::Control::New();
-item1.RegisterProperty( "flex", 1.0f, Dali::Property::READ_WRITE );
+item1.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 1.0f );
 flexContainer.Add( item1 );
 
 Dali::Toolkit::Control item2 = Dali::Toolkit::Control::New();
-item2.RegisterProperty( "flex", 3.0f, Dali::Property::READ_WRITE );
+item2.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 3.0f );
 flexContainer.Add( item2 );
 
 Dali::Toolkit::Control item3 = Dali::Toolkit::Control::New();
-item3.RegisterProperty( "flex", 1.0f, Dali::Property::READ_WRITE );
+item3.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 1.0f );
 flexContainer.Add( item3 );
 
 Dali::Toolkit::Control item4 = Dali::Toolkit::Control::New();
-item4.RegisterProperty( "flex", 2.0f, Dali::Property::READ_WRITE );
+item4.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 2.0f );
 flexContainer.Add( item4 );
 
 Dali::Toolkit::Control item5 = Dali::Toolkit::Control::New();
-item5.RegisterProperty( "flex", 1.0f, Dali::Property::READ_WRITE );
+item5.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 1.0f );
 flexContainer.Add( item5 );
 
 ~~~
@@ -338,14 +338,14 @@ flexContainer.SetProperty( Dali::Toolkit::FlexContainer::Property::ALIGN_ITEMS,
 
 // Create flex items and add them to the flex container
 Dali::Toolkit::Control item1 = Dali::Toolkit::Control::New();
-item1.RegisterProperty( "alignSelf", Dali::Toolkit::FlexContainer::ALIGN_CENTER, Dali::Property::READ_WRITE ); // Align item1 at the center of the container
+item1.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::ALIGN_SELF, Dali::Toolkit::FlexContainer::ALIGN_CENTER ); // Align item1 at the center of the container
 flexContainer.Add( item1 );
 
 Dali::Toolkit::Control item2 = Dali::Toolkit::Control::New();
 flexContainer.Add( item2 ); // item2 is aligned at the beginning of ther container
 
 Dali::Toolkit::Control item3 = Dali::Toolkit::Control::New();
-item3.RegisterProperty( "alignSelf", Dali::Toolkit::FlexContainer::ALIGN_FLEX_END, Dali::Property::READ_WRITE ); // Align item3 at the bottom of the container
+item3.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::ALIGN_SELF, Dali::Toolkit::FlexContainer::ALIGN_FLEX_END ); // Align item3 at the bottom of the container
 flexContainer.Add( item3 );
 
 Dali::Toolkit::Control item4 = Dali::Toolkit::Control::New();
@@ -411,7 +411,7 @@ Dali::Toolkit::FlexContainer flexContainer = Dali::Toolkit::FlexContainer::New()
 Dali::Toolkit::Control item = Dali::Toolkit::Control::New();
 
 // Add the margin around the item
-item.RegisterProperty( "flexMargin", Vector4(10.0f, 10.0f, 10.0f, 10.0f), Dali::Property::READ_WRITE );
+item.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX_MARGIN, Vector4(10.0f, 10.0f, 10.0f, 10.0f) );
 
 // Add the item to the container
 flexContainer.Add( item );
@@ -526,7 +526,7 @@ This can be achieved by setting the flex property.
 
 toolBar.SetProperty( Dali::Toolkit::FlexContainer::Property::FLEX_DIRECTION, Dali::Toolkit::FlexContainer::ROW ); // display toolbar items horizontally
 toolBar.SetProperty( Dali::Toolkit::FlexContainer::Property::ALIGN_ITEMS, Dali::Toolkit::FlexContainer::ALIGN_CENTER ); // align toolbar items vertically center
-toolBar.RegisterProperty( "flex", 0.1f, Dali::Property::READ_WRITE ); // 10 percent of available space in the cross axis
+toolBar.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 0.1f ); // 10 percent of available space in the cross axis
 ~~~
 
 ~~~{.js}
@@ -550,7 +550,7 @@ content.SetAnchorPoint( Dali::AnchorPoint::TOP_LEFT );
 content.SetProperty( Dali::Toolkit::FlexContainer::Property::FLEX_DIRECTION, Dali::Toolkit::FlexContainer::ROW ); // display items horizontally
 content.SetProperty( Dali::Toolkit::FlexContainer::Property::JUSTIFY_CONTENT, Dali::Toolkit::FlexContainer::JUSTIFY_CENTER ); // align items horizontally center
 content.SetProperty( Dali::Toolkit::FlexContainer::Property::ALIGN_ITEMS, Dali::Toolkit::FlexContainer::ALIGN_CENTER ); // align items vertically center
-content.RegisterProperty( "flex", 0.9f, Dali::Property::READ_WRITE ); // 90 percent of available space in the cross axis
+content.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 0.9f ); // 90 percent of available space in the cross axis
 
 // Add it to the main container
 flexContainer.Add( content );
@@ -584,7 +584,7 @@ Dali::Toolkit::PushButton prevButton = Dali::Toolkit::PushButton::New();
 prevButton.SetParentOrigin( Dali::ParentOrigin::TOP_LEFT );
 prevButton.SetAnchorPoint( Dali::AnchorPoint::TOP_LEFT );
 prevButton.SetMinimumSize( Dali::Vector2( 100.0f, 60.0f ) ); // this is the minimum size the button should keep
-prevButton.RegisterProperty( "flexMargin", Dali::Vector4(10.0f, 10.0f, 10.0f, 10.0f), Dali::Property::READ_WRITE ); // set 10 pixel margin around the button
+prevButton.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX_MARGIN, Dali::Vector4(10.0f, 10.0f, 10.0f, 10.0f) ); // set 10 pixel margin around the button
 toolBar.Add( prevButton );
 
 // Set the button text
@@ -600,8 +600,8 @@ title.SetAnchorPoint( Dali::AnchorPoint::TOP_LEFT );
 title.SetResizePolicy( Dali::ResizePolicy::USE_NATURAL_SIZE, Dali::Dimension::ALL_DIMENSIONS );
 title.SetProperty( Dali::Toolkit::TextLabel::Property::HORIZONTAL_ALIGNMENT, "CENTER" );
 title.SetProperty( Dali::Toolkit::TextLabel::Property::VERTICAL_ALIGNMENT, "CENTER" );
-title.RegisterProperty( "flex", 1.0f, Dali::Property::READ_WRITE ); // take all the available space left apart from the two buttons
-title.RegisterProperty( "flexMargin", Dali::Vector4(10.0f, 10.0f, 10.0f, 10.0f), Dali::Property::READ_WRITE ); // set 10 pixel margin around the title
+title.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX, 1.0f ); // take all the available space left apart from the two buttons
+title.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX_MARGIN, Dali::Vector4(10.0f, 10.0f, 10.0f, 10.0f) ); // set 10 pixel margin around the title
 toolBar.Add( title );
 
 // Add a button to the right of the toolbar
@@ -609,7 +609,7 @@ Dali::Toolkit::PushButton nextButton = Dali::Toolkit::PushButton::New();
 nextButton.SetParentOrigin( Dali::ParentOrigin::TOP_LEFT );
 nextButton.SetAnchorPoint( Dali::AnchorPoint::TOP_LEFT );
 nextButton.SetMinimumSize( Dali::Vector2( 100.0f, 60.0f ) ); // this is the minimum size the button should keep
-nextButton.RegisterProperty( "flexMargin", Dali::Vector4(10.0f, 10.0f, 10.0f, 10.0f), Dali::Property::READ_WRITE ); // set 10 pixel margin around the button
+nextButton.SetProperty( Dali::Toolkit::FlexContainer::ChildProperty::FLEX_MARGIN, Dali::Vector4(10.0f, 10.0f, 10.0f, 10.0f) ); // set 10 pixel margin around the button
 toolBar.Add( nextButton );
 
 // Set the button text
diff --git a/docs/content/shared-javascript-and-cpp-documentation/text-auto-scrolling.md b/docs/content/shared-javascript-and-cpp-documentation/text-auto-scrolling.md
new file mode 100644 (file)
index 0000000..ba7270d
--- /dev/null
@@ -0,0 +1,63 @@
+<!--
+/**-->
+
+# Text auto scrolling {#text-auto-scrolling}
+
+## Overview
+
+Auto TextLabel scrolling enables the text to scroll within the control, it can be used if text exceeds the boundary of the control hence showing the full content.
+It will also scroll text that is smaller than the control and ensure the same bit of text is not visible at the same time, this gap can be configured to be larger.
+
+If the number of loops (repetitions) is not set then once triggered to start it will scroll until requested to stop.
+If loop count is set to 3 for example it will scroll the text 3 times.
+
+![ ](../assets/img/text-controls/AutoScroll.gif)
+![ ](AutoScroll.gif)
+
+### Usage
+
+At version 1.1.35 auto scrolling is only supported in single line, mutliline text will not scroll and Text should be BEGIN aligned.
+
+The ENABLE_AUTO_SCROLL property should be set to TRUE to enable scrolling.
+
+The scroll speed, gap and loop count can be set in the stylesheet or provided by Dali::Handle::SetProperty. See the description of each below.
+
+Once enabled it will start scrolling until the loop count is completed or the ENABLE_AUTO_SCROLL set to false, setting ENABLE_AUTO_SCROLL to false will let the
+text complete it's current scrolling loop then stop.
+
+## The additional properties below can be set to customise the scrolling behaviour
+
+#### AUTO_SCROLL_SPEED
+
+This controls the speed of the scrolling, the speed should be provided as pixels/second.
+
+#### AUTO_SCROLL_LOOP_COUNT
+
+This specifies how many times the text will complete a full scroll cycle.
+If not set then it will keep scrolling until ENABLE_AUTO_SCROLL is set to false.
+
+Setting ENABLE_AUTO_SCROLL to false will stop scrolling whilst still maintaining the original loop count value for when it is next started.
+
+#### AUTO_SCROLL_GAP
+
+This specifies the amount of whitespace to display before the scrolling text is shown again.
+
+This will be increased if the given value is not large enough to prevent the same bit of text being visible at two locations in the control.
+
+Provide the distance in pixels.
+
+### Scroll Direction
+
+The scroll direction is choosen automatically with the following rules:
+
+If the text is single-lined it will scroll left when the text is Left to Right (LTR) or scroll right if text is Right to Left (RTL).
+
+If the text is multi-lined it will scroll upwards. ( Not supported at 1.1.35 )
+
+### Text Label Scrolling Properties
+
+The properties used by TextLabel for Auto Scrolling are listed [here](@ref TextLabelProperties)
+
+@class TextLabel_Scrolling
+
+*/
index 5247e92..ae03364 100644 (file)
@@ -316,27 +316,16 @@ label1.underlineHeight = 1;
 ![ ](../assets/img/text-controls/TextWith1pxUnderline.png)
 ![ ](TextWith1pxUnderline.png)
 
-### Text Label Properties
+### Auto Scrolling
+
+![ ](../assets/img/text-controls/AutoScroll.gif)
+![ ](AutoScroll.gif)
 
- Name (JavaScript)   |  Name (C++)          |  Type        | Writable     | Animatable
----------------------|----------------------|--------------|--------------|-----------
- renderingBackend    | RENDERING_BACKEND    |  INTEGER     | O            | X
- text                | TEXT                 |  STRING      | O            | X
- fontFamily          | FONT_FAMILY          |  STRING      | O            | X
- fontStyle           | FONT_STYLE           |  STRING      | O            | X
- pointSize           | POINT_SIZE           |  FLOAT       | O            | X
- multiLine           | MULTI_LINE           |  BOOLEAN     | O            | X
- horizontalAlignment | HORIZONTAL_ALIGNMENT |  STRING      | O            | X
- verticalAlignment   | VERTICAL_ALIGNMENT   |  STRING      | O            | X
- textColor           | TEXT_COLOR           |  VECTOR4     | O            | X
- shadowOffset        | SHADOW_OFFSET        |  VECTOR2     | O            | X
- shadowColor         | SHADOW_COLOR         |  VECTOR4     | O            | X
- underlineEnabled    | UNDERLINE_ENABLED    |  BOOLEAN     | O            | X
- underlineColor      | UNDERLINE_COLOR      |  VECTOR4     | O            | X
- underlineHeight     | UNDERLINE_HEIGHT     |  FLOAT       | O            | X
- enableMarkup        | ENABLE_MARKUP        |  BOOLEAN     | O            | X
+The \link text-auto-scrolling Auto text scrolling \endlink section details how to scroll text automatically.
 
+### Text Label Properties
 
+The properties used by TextLabel are listed [here](@ref TextLabelProperties)
 
 @class TextLabel
 
index d558701..c80971f 100644 (file)
@@ -1,6 +1,6 @@
 Name:       dali-toolkit
 Summary:    The OpenGLES Canvas Core Library Toolkit
-Version:    1.1.34
+Version:    1.1.35
 Release:    1
 Group:      System/Libraries
 License:    Apache-2.0 and BSD-2-Clause and MIT
index 0c993d4..9255574 100644 (file)
@@ -18,6 +18,9 @@
 // CLASS HEADER
 #include "module-loader.h"
 
+// EXTERNAL INCLUDES
+#include <dali/public-api/common/vector-wrapper.h>
+
 // INTERNAL INCLUDES
 #include <v8-utils.h>
 
index be1739d..fed77ce 100644 (file)
@@ -179,8 +179,14 @@ void HandleWrapper::PropertySet( v8::Local<v8::String> propertyName,
   }
   else
   {
-    std::string error="Invalid property Set for "+name + "\n";
-    DALI_SCRIPT_EXCEPTION( isolate, error );
+    // Trying to set the value for a property that is not registered yet.
+    std::stringstream msg;
+    msg << "Trying to set the value of an unregistered property: ";
+    msg << name;
+    DALI_SCRIPT_WARNING( msg.str().c_str() );
+
+    // Register the custom property automatically.
+    handle.RegisterProperty( name, PropertyValueWrapper::ExtractPropertyValue( isolate, javaScriptValue), Property::READ_WRITE );
   }
 }
 
index 8469d7f..b160642 100644 (file)
@@ -785,6 +785,62 @@ Dali::Property::Value PropertyValueWrapper::ExtractPropertyValue( v8::Isolate* i
   return daliPropertyValue;
 }
 
+Dali::Property::Value PropertyValueWrapper::ExtractPropertyValue( v8::Isolate* isolate, v8::Local< v8::Value> v8Value)
+{
+  v8::HandleScope handleScope( isolate);
+
+  Dali::Property::Value daliPropertyValue;
+
+  // Check if it's a javascript Array
+  Dali::Property::Value array = VectorOrMatrixFromV8Array( isolate, v8Value );
+
+  if( V8Utils::IsBooleanPrimitiveOrObject( v8Value ) )
+  {
+    daliPropertyValue = Dali::Property::Value( V8Utils::GetBooleanValue( isolate, v8Value));
+  }
+  else if( V8Utils::IsNumberPrimitiveOrObject( v8Value )  )
+  {
+    daliPropertyValue = Dali::Property::Value( V8Utils::GetNumberValue( isolate, v8Value) );
+  }
+  else if( v8Value->IsInt32() )
+  {
+    daliPropertyValue = Dali::Property::Value(  v8Value->Int32Value()  ) ;
+  }
+  else if( V8Utils::IsStringPrimitiveOrObject( v8Value) )
+  {
+    daliPropertyValue = Dali::Property::Value( V8Utils::GetStringValue( isolate, v8Value) );
+  }
+  else if( array.GetType() == Dali::Property::VECTOR2
+         || array.GetType() == Dali::Property::VECTOR3
+         || array.GetType() == Dali::Property::VECTOR4 )
+  {
+    daliPropertyValue = array;
+  }
+  else if( array.GetType() == Dali::Property::MATRIX )
+  {
+    Dali::Matrix mat = array.Get<Dali::Matrix>();
+    daliPropertyValue = mat;
+  }
+  else if( array.GetType() == Dali::Property::MATRIX3 )
+  {
+    Dali::Matrix3 mat = array.Get<Dali::Matrix3>();
+    daliPropertyValue = mat;
+  }
+  else if( array.GetType() == Dali::Property::ARRAY )
+  {
+    daliPropertyValue = ArrayFromV8Array( isolate, v8Value );
+  }
+  else if( v8Value->IsObject() )
+  {
+    // Assume this is a property map
+    v8::Local<v8::Object> object = v8::Handle<v8::Object>::Cast(v8Value);
+    Dali::Property::Map propertyMap = V8Utils::GetPropertyMapFromObject(isolate, object);
+    daliPropertyValue = Dali::Property::Value( propertyMap );
+  }
+
+  return daliPropertyValue;
+}
+
 void PropertyValueWrapper::NewRotation( const v8::FunctionCallbackInfo< v8::Value >& args)
 {
   v8::Isolate* isolate = args.GetIsolate();
index 8cb2dac..05a3e38 100644 (file)
@@ -90,6 +90,12 @@ public:
   static Dali::Property::Value ExtractPropertyValue( v8::Isolate* isolate, v8::Local< v8::Value> v8Value, Dali::Property::Type type);
 
   /**
+   * Extract a property value from a javascript object
+   * @return property value
+   */
+  static Dali::Property::Value ExtractPropertyValue( v8::Isolate* isolate, v8::Local< v8::Value> v8Value);
+
+  /**
    * @brief Extract a vector or a matrix from a JavaScript array
    * @return property value ( vector or matrix)
    */
index b77d458..193836d 100644 (file)
@@ -378,8 +378,6 @@ std::string PropertyNameToJavaScriptName(const std::string& hyphenatedName)
   return ret;
 }
 
-
-
 void ScriptError( const char* function, v8::Isolate* isolate, std::string errorString )
 {
   v8::EscapableHandleScope scope( isolate);
@@ -393,6 +391,12 @@ void ScriptError( const char* function, v8::Isolate* isolate, std::string errorS
   isolate->ThrowException( v8::String::NewFromUtf8( isolate, errorMsg.c_str()) );
 }
 
+void ScriptWarning( const char* function, std::string warningString )
+{
+  std::string warningMsg = std::string(function) + std::string("(), ") + warningString;
+  DALI_LOG_WARNING("%s \n", warningMsg.c_str() );
+}
+
 bool IsBooleanPrimitiveOrObject( const v8::Local<v8::Value>& value )
 {
   return ( value->IsBoolean() || value->IsBooleanObject());
@@ -504,6 +508,13 @@ Property::Value GetPropertyValueFromObject( bool& found, v8::Isolate* isolate, c
     v8::Local<v8::Int32> v = value->ToInt32();
     return Dali::Property::Value(static_cast<int>(v->Value()));
   }
+  else if( value->IsString() )
+  {
+    found = true;
+    std::string valueString = V8Utils::v8StringToStdString( value );
+    return Dali::Property::Value(valueString);
+  }
+
   return daliPropertyValue;
 
 }
index 5a86f39..63ff2c6 100644 (file)
@@ -50,6 +50,7 @@ enum
 };
 
 #define DALI_SCRIPT_EXCEPTION( isolate, message ) V8Utils::ScriptError( __FUNCTION__ , isolate, message );
+#define DALI_SCRIPT_WARNING( message ) V8Utils::ScriptWarning( __FUNCTION__ , message );
 
 namespace V8Utils
 {
@@ -146,6 +147,11 @@ std::string GetJavaScriptFunctionName(  const char* functionName );
 void ScriptError( const char* function, v8::Isolate* isolate, std::string errorString );
 
 /**
+ * Script warning
+ */
+void ScriptWarning( const char* function, std::string warningString );
+
+/**
  * @return in the value is a boolean primitive or a boolean object
  */
 bool IsBooleanPrimitiveOrObject( const v8::Local<v8::Value>& value );