Merge "Added devel-api mirroring of public enumeration." into devel/master
[platform/core/uifw/dali-toolkit.git] / dali-toolkit / public-api / controls / control-impl.cpp
index 53c9293..a2ddcbe 100644 (file)
 #include <dali-toolkit/public-api/styling/style-manager.h>
 #include <dali-toolkit/public-api/visuals/color-visual-properties.h>
 #include <dali-toolkit/devel-api/controls/control-depth-index-ranges.h>
+#include <dali-toolkit/devel-api/visual-factory/devel-visual-properties.h>
 #include <dali-toolkit/devel-api/visual-factory/visual-factory.h>
 #include <dali-toolkit/devel-api/focus-manager/keyinput-focus-manager.h>
 #include <dali-toolkit/internal/styling/style-manager-impl.h>
 #include <dali-toolkit/internal/visuals/color/color-visual.h>
+#include <dali-toolkit/internal/visuals/transition-data-impl.h>
 
 namespace Dali
 {
@@ -52,6 +54,10 @@ namespace Toolkit
 namespace
 {
 
+#if defined(DEBUG_ENABLED)
+Debug::Filter* gLogFilter = Debug::Filter::New( Debug::General, false, "LOG_CONTROL_VISUALS");
+#endif
+
 /**
  * Struct used to store Visual within the control, index is a unique key for each visual.
  */
@@ -60,16 +66,37 @@ struct RegisteredVisual
   Property::Index index;
   Toolkit::Visual::Base visual;
   Actor placementActor;
+  bool enabled;
 
-  RegisteredVisual( Property::Index aIndex, Toolkit::Visual::Base &aVisual, Actor &aPlacementActor) : index(aIndex), visual(aVisual), placementActor(aPlacementActor) {}
+  RegisteredVisual( Property::Index aIndex, Toolkit::Visual::Base &aVisual, Actor &aPlacementActor, bool aEnabled) :
+                   index(aIndex), visual(aVisual), placementActor(aPlacementActor), enabled(aEnabled) {}
 };
 
-typedef Dali::OwnerContainer< RegisteredVisual* > RegisteredVisuals;
+struct HandleIndex
+{
+  Handle handle; ///< a handle to the target object
+  Property::Index index; ///< The index of a property provided by the referenced object
+
+  HandleIndex( )
+  : handle(),
+    index( Property::INVALID_INDEX )
+  {
+  }
+
+  HandleIndex( Handle& handle, Property::Index index )
+  : handle( handle ),
+    index( index )
+  {
+  }
+};
+
+
+typedef Dali::OwnerContainer< RegisteredVisual* > RegisteredVisualContainer;
 
 /**
  *  Finds visual in given array, returning true if found along with the iterator for that visual as a out parameter
  */
-bool FindVisual( Property::Index targetIndex, RegisteredVisuals& visuals, RegisteredVisuals::Iterator& iter )
+bool FindVisual( Property::Index targetIndex, RegisteredVisualContainer& visuals, RegisteredVisualContainer::Iterator& iter )
 {
   for ( iter = visuals.Begin(); iter != visuals.End(); iter++ )
   {
@@ -81,6 +108,71 @@ bool FindVisual( Property::Index targetIndex, RegisteredVisuals& visuals, Regist
   return false;
 }
 
+HandleIndex GetVisualProperty(
+  Internal::Control& controlImpl,
+  RegisteredVisualContainer& visuals,
+  const std::string& visualName,
+  Property::Key propertyKey )
+{
+#if defined(DEBUG_ENABLED)
+  std::ostringstream oss;
+  oss << "Control::GetHandleIndex(" << visualName << ", " << propertyKey << ")" << std::endl;
+  DALI_LOG_INFO( gLogFilter, Debug::General, oss.str().c_str() );
+#endif
+
+  // Find visualName in the control
+  RegisteredVisualContainer::Iterator iter;
+  for ( iter = visuals.Begin(); iter != visuals.End(); iter++ )
+  {
+    if ( (*iter)->visual.GetName() == visualName )
+    {
+      break;
+    }
+  }
+
+  // Does either it's renderer or placement actor have an associated property?
+  if( iter != visuals.End() )
+  {
+    Actor placementActor = (*iter)->placementActor;
+    if( !placementActor )
+    {
+      placementActor = controlImpl.Self();
+    }
+
+    Property::Index index = placementActor.GetPropertyIndex( propertyKey );
+    if( index != Property::INVALID_INDEX )
+    {
+      // It's a placement actor property:
+      return HandleIndex( placementActor, index );
+    }
+    else
+    {
+      // Check if it is a renderer property:
+      if( placementActor.GetRendererCount() > 0 )
+      {
+        // @todo Need to use correct renderer index when placement actors
+        // are removed
+        Renderer renderer = placementActor.GetRendererAt(0);
+        Property::Index index = renderer.GetPropertyIndex( propertyKey );
+        if( index != Property::INVALID_INDEX )
+        {
+          // It's a renderer property:
+          return HandleIndex( renderer, index );
+        }
+      }
+      else
+      {
+        std::ostringstream oss;
+        oss << propertyKey;
+        DALI_LOG_WARNING( "Control::GetHandleIndex(%s, %s) No renderers\n", visualName.c_str(), oss.str().c_str() );
+      }
+    }
+  }
+  Handle handle;
+  return HandleIndex( handle, Property::INVALID_INDEX );
+}
+
+
 /**
  * Creates control through type registry
  */
@@ -205,21 +297,21 @@ public:
 
   // Construction & Destruction
   Impl(Control& controlImpl)
-: mControlImpl( controlImpl ),
-  mStyleName(""),
-  mBackgroundVisual(),
-  mBackgroundColor(Color::TRANSPARENT),
-  mStartingPinchScale( NULL ),
-  mKeyEventSignal(),
-  mPinchGestureDetector(),
-  mPanGestureDetector(),
-  mTapGestureDetector(),
-  mLongPressGestureDetector(),
-  mFlags( Control::ControlBehaviour( CONTROL_BEHAVIOUR_DEFAULT ) ),
-  mIsKeyboardNavigationSupported( false ),
-  mIsKeyboardFocusGroup( false )
-{
-}
+  : mControlImpl( controlImpl ),
+    mStyleName(""),
+    mBackgroundVisual(),
+    mBackgroundColor(Color::TRANSPARENT),
+    mStartingPinchScale( NULL ),
+    mKeyEventSignal(),
+    mPinchGestureDetector(),
+    mPanGestureDetector(),
+    mTapGestureDetector(),
+    mLongPressGestureDetector(),
+    mFlags( Control::ControlBehaviour( CONTROL_BEHAVIOUR_DEFAULT ) ),
+    mIsKeyboardNavigationSupported( false ),
+    mIsKeyboardFocusGroup( false )
+  {
+  }
 
   ~Impl()
   {
@@ -397,7 +489,7 @@ public:
   // Data
 
   Control& mControlImpl;
-  RegisteredVisuals mVisuals; // Stores visuals needed by the control, non trivial type so std::vector used.
+  RegisteredVisualContainer mVisuals; // Stores visuals needed by the control, non trivial type so std::vector used.
   std::string mStyleName;
   Toolkit::Visual::Base mBackgroundVisual;   ///< The visual to render the background
   Vector4 mBackgroundColor;                       ///< The color of the background visual
@@ -476,7 +568,7 @@ void Control::SetBackgroundColor( const Vector4& color )
   Actor self( Self() );
   mImpl->mBackgroundColor = color;
   Property::Map map;
-  map[ Toolkit::Visual::Property::TYPE ] = Toolkit::Visual::COLOR;
+  map[ Toolkit::VisualProperty::TYPE ] = Toolkit::Visual::COLOR;
   map[ Toolkit::ColorVisual::Property::MIX_COLOR ] = color;
   mImpl->mBackgroundVisual = Toolkit::VisualFactory::Get().CreateVisual( map );
   RegisterVisual( Toolkit::Control::Property::BACKGROUND, self, mImpl->mBackgroundVisual );
@@ -661,6 +753,11 @@ void Control::KeyboardEnter()
 
 void Control::RegisterVisual( Property::Index index, Actor& placementActor, Toolkit::Visual::Base& visual )
 {
+  RegisterVisual( index, placementActor, visual, true );
+}
+
+void Control::RegisterVisual( Property::Index index, Actor& placementActor, Toolkit::Visual::Base& visual, bool enabled )
+{
   bool visualReplaced ( false );
   Actor actorToRegister; // Null actor, replaced if placement actor not Self
   Actor self = Self();
@@ -672,7 +769,7 @@ void Control::RegisterVisual( Property::Index index, Actor& placementActor, Tool
 
   if ( !mImpl->mVisuals.Empty() )
   {
-      RegisteredVisuals::Iterator iter;
+      RegisteredVisualContainer::Iterator iter;
       // Check if visual (index) is already registered.  Replace if so.
       if ( FindVisual( index, mImpl->mVisuals, iter ) )
       {
@@ -695,10 +792,10 @@ void Control::RegisterVisual( Property::Index index, Actor& placementActor, Tool
 
   if ( !visualReplaced ) // New registration entry
   {
-    mImpl->mVisuals.PushBack( new RegisteredVisual( index, visual, actorToRegister ) );
+    mImpl->mVisuals.PushBack( new RegisteredVisual( index, visual, actorToRegister, enabled ) );
   }
 
-  if( visual && self.OnStage() )
+  if( visual && self.OnStage() && enabled )
   {
     visual.SetOnStage( placementActor );
   }
@@ -706,7 +803,7 @@ void Control::RegisterVisual( Property::Index index, Actor& placementActor, Tool
 
 void Control::UnregisterVisual( Property::Index index )
 {
-   RegisteredVisuals::Iterator iter;
+   RegisteredVisualContainer::Iterator iter;
    if ( FindVisual( index, mImpl->mVisuals, iter ) )
    {
      mImpl->mVisuals.Erase( iter );
@@ -715,7 +812,7 @@ void Control::UnregisterVisual( Property::Index index )
 
 Toolkit::Visual::Base Control::GetVisual( Property::Index index ) const
 {
-  RegisteredVisuals::Iterator iter;
+  RegisteredVisualContainer::Iterator iter;
   if ( FindVisual( index, mImpl->mVisuals, iter ) )
   {
     return (*iter)->visual;
@@ -724,9 +821,51 @@ Toolkit::Visual::Base Control::GetVisual( Property::Index index ) const
   return Toolkit::Visual::Base();
 }
 
+void Control::EnableVisual( Property::Index index, bool enable )
+{
+  RegisteredVisualContainer::Iterator iter;
+  if ( FindVisual( index, mImpl->mVisuals, iter ) )
+  {
+    if (  (*iter)->enabled == enable )
+    {
+      return;
+    }
+
+    (*iter)->enabled = enable;
+    Actor parentActor = Self();
+    if ( (*iter)->placementActor )
+    {
+      parentActor = (*iter)->placementActor;
+    }
+
+    if ( Self().OnStage() ) // If control not on Stage then Visual will be added when StageConnection is called.
+    {
+      if ( enable )
+      {
+
+        (*iter)->visual.SetOnStage( parentActor );
+      }
+      else
+      {
+        (*iter)->visual.SetOffStage( parentActor );  // No need to call if control not staged.
+      }
+    }
+  }
+}
+
+bool Control::IsVisualEnabled( Property::Index index ) const
+{
+  RegisteredVisualContainer::Iterator iter;
+  if ( FindVisual( index, mImpl->mVisuals, iter ) )
+  {
+    return (*iter)->enabled;
+  }
+  return false;
+}
+
 Actor Control::GetPlacementActor( Property::Index index ) const
 {
-  RegisteredVisuals::Iterator iter;
+  RegisteredVisualContainer::Iterator iter;
   if ( FindVisual( index, mImpl->mVisuals, iter ) )
   {
     if( (*iter)->placementActor )
@@ -742,6 +881,72 @@ Actor Control::GetPlacementActor( Property::Index index ) const
   return Actor();
 }
 
+Dali::Animation Control::CreateTransition( const Toolkit::TransitionData& handle )
+{
+  Dali::Animation transition;
+  const Internal::TransitionData& transitionData = Toolkit::GetImplementation( handle );
+
+  if( transitionData.Count() > 0 )
+  {
+    // Setup a Transition from TransitionData.
+    TransitionData::Iterator end = transitionData.End();
+    for( TransitionData::Iterator iter = transitionData.Begin() ;
+         iter != end; ++iter )
+    {
+      TransitionData::Animator* animator = (*iter);
+      HandleIndex handleIndex;
+
+      // Attempt to find the object name as a child actor
+      Actor child = Self().FindChildByName( animator->objectName );
+      if( child )
+      {
+        Property::Index propertyIndex = child.GetPropertyIndex( animator->propertyKey );
+        handleIndex = HandleIndex( child, propertyIndex );
+      }
+      else
+      {
+        // Is it a placement actor/visual pair?;
+        handleIndex = GetVisualProperty( *this, mImpl->mVisuals,
+                                            animator->objectName,
+                                            animator->propertyKey );
+      }
+
+      if( handleIndex.handle && handleIndex.index != Property::INVALID_INDEX )
+      {
+        if( animator->animate == false )
+        {
+          if( animator->targetValue.GetType() != Property::NONE )
+          {
+            handleIndex.handle.SetProperty( handleIndex.index, animator->targetValue );
+          }
+        }
+        else
+        {
+          if( animator->initialValue.GetType() != Property::NONE )
+          {
+            handleIndex.handle.SetProperty( handleIndex.index, animator->initialValue );
+          }
+
+          if( ! transition )
+          {
+            // Create an animation with a default .1 second duration - the animators
+            // will automatically force it to the 'right' duration.
+            transition = Dali::Animation::New( 0.1f );
+          }
+
+          transition.AnimateTo( Property( handleIndex.handle, handleIndex.index ),
+                                animator->targetValue,
+                                animator->alphaFunction,
+                                TimePeriod( animator->timePeriodDelay,
+                                            animator->timePeriodDuration ) );
+        }
+      }
+    }
+  }
+
+  return transition;
+}
+
 bool Control::OnAccessibilityActivated()
 {
   return false; // Accessibility activation is not handled by default
@@ -928,10 +1133,10 @@ void Control::EmitKeyInputFocusSignal( bool focusGained )
 
 void Control::OnStageConnection( int depth )
 {
-  for(RegisteredVisuals::Iterator iter = mImpl->mVisuals.Begin(); iter!= mImpl->mVisuals.End(); iter++)
+  for(RegisteredVisualContainer::Iterator iter = mImpl->mVisuals.Begin(); iter!= mImpl->mVisuals.End(); iter++)
   {
     // Check whether the visual is empty, as it is allowed to register a placement actor without visual.
-    if( (*iter)->visual )
+    if( (*iter)->visual && (*iter)->enabled )
     {
       if( (*iter)->placementActor )
       {
@@ -948,7 +1153,7 @@ void Control::OnStageConnection( int depth )
 
 void Control::OnStageDisconnection()
 {
-  for(RegisteredVisuals::Iterator iter = mImpl->mVisuals.Begin(); iter!= mImpl->mVisuals.End(); iter++)
+  for(RegisteredVisualContainer::Iterator iter = mImpl->mVisuals.Begin(); iter!= mImpl->mVisuals.End(); iter++)
   {
     // Check whether the visual is empty, as it is allowed to register a placement actor without visual.
     if( (*iter)->visual )