RegisterVisuals has option not to auto stage visual 71/92171/10
authorAgnelo Vaz <agnelo.vaz@samsung.com>
Thu, 13 Oct 2016 10:30:32 +0000 (11:30 +0100)
committerAgnelo Vaz <agnelo.vaz@samsung.com>
Fri, 14 Oct 2016 14:14:28 +0000 (15:14 +0100)
Currenly RegisterVisual stages it too. This may not always be desirable hence offering second API.
Adding EnableVisual API

Change-Id: Id4f54bf3f19ac8a650f0db21d3fc62efda60092f

automated-tests/src/dali-toolkit/dali-toolkit-test-utils/dummy-control.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/dummy-control.h
automated-tests/src/dali-toolkit/utc-Dali-ControlImpl.cpp
dali-toolkit/public-api/controls/control-impl.cpp
dali-toolkit/public-api/controls/control-impl.h

index 80fb6ec..7e102f5 100644 (file)
@@ -80,6 +80,11 @@ void DummyControlImpl::RegisterVisual( Property::Index index, Actor placementAct
   Control::RegisterVisual( index, placementActor, visual );
 }
 
+void DummyControlImpl::RegisterVisual( Property::Index index, Actor placementActor, Toolkit::Visual::Base visual, bool enabled )
+{
+  Control::RegisterVisual( index, placementActor, visual, enabled );
+}
+
 void DummyControlImpl::UnregisterVisual( Property::Index index )
 {
   Control::UnregisterVisual( index );
@@ -90,6 +95,16 @@ Toolkit::Visual::Base DummyControlImpl::GetVisual( Property::Index index )
   return Control::GetVisual( index );
 }
 
+void DummyControlImpl::EnableVisual( Property::Index index, bool enabled )
+{
+  Control::EnableVisual( index, enabled );
+}
+
+bool DummyControlImpl::IsVisualEnabled( Property::Index index )
+{
+  return Control::IsVisualEnabled( index );
+}
+
 Actor DummyControlImpl::GetPlacementActor( Property::Index index )
 {
   return Control::GetPlacementActor( index );
index 3c88685..3e5e56f 100644 (file)
@@ -72,7 +72,11 @@ public:
   inline LongPressGestureDetector GetLongPressGestureDetector() const { return Internal::Control::GetLongPressGestureDetector(); }
 
   void RegisterVisual( Property::Index index, Actor placementActor, Toolkit::Visual::Base visual);
+  void RegisterVisual( Property::Index index, Actor placementActor, Toolkit::Visual::Base visual, bool enabled );
   void UnregisterVisual( Property::Index index );
+  void EnableVisual( Property::Index index, bool enabled );
+  bool IsVisualEnabled( Property::Index index );
+
   Toolkit::Visual::Base GetVisual( Property::Index index );
   Actor GetPlacementActor( Property::Index index );
 
index 2e691af..6fe4af6 100644 (file)
@@ -1054,6 +1054,7 @@ int UtcDaliControlImplRegisterVisualToSelf(void)
 
     // Register to self
     dummyImpl.RegisterVisual( index, dummy, visual );
+
     DALI_TEST_EQUALS( objectDestructionTracker.IsDestroyed(), false, TEST_LOCATION ); // Control not destroyed yet
     DALI_TEST_CHECK( dummyImpl.GetVisual( index ) == visual );
     DALI_TEST_CHECK( dummyImpl.GetPlacementActor( index ) == dummy );
@@ -1144,3 +1145,215 @@ int UtcDaliControlImplRegisterUnregisterVisual(void)
 
   END_TEST;
 }
+
+int UtcDaliControlImplRegisterDisabledVisual(void)
+{
+  ToolkitTestApplication application;
+
+  DummyControl dummy = DummyControl::New();
+  DummyControlImpl& dummyImpl = static_cast<DummyControlImpl&>(dummy.GetImplementation());
+
+  Property::Index TEST_PROPERTY =1;
+
+  Toolkit::VisualFactory visualFactory = Toolkit::VisualFactory::Get();
+  Toolkit::Visual::Base visual;
+
+  Property::Map map;
+  map[Visual::Property::TYPE] = Visual::COLOR;
+  map[ColorVisual::Property::MIX_COLOR] = Color::RED;
+
+  visual = visualFactory.CreateVisual( map );
+  DALI_TEST_CHECK(visual);
+
+  // Register index with a color visual
+  dummyImpl.RegisterVisual( TEST_PROPERTY, dummy, visual, false );
+
+  DALI_TEST_CHECK( dummyImpl.GetVisual( TEST_PROPERTY ) == visual );
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == false );
+
+  Stage::GetCurrent().Add(dummy);
+
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == false );
+
+  DALI_TEST_CHECK( dummy.OnStage() == true );
+
+  dummyImpl.EnableVisual( TEST_PROPERTY, true );
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == true );
+
+  END_TEST;
+}
+
+int UtcDaliControlImplDisableRegisteredVisual(void)
+{
+  ToolkitTestApplication application;
+
+  DummyControl dummy = DummyControl::New();
+  DummyControlImpl& dummyImpl = static_cast<DummyControlImpl&>(dummy.GetImplementation());
+
+  Property::Index TEST_PROPERTY =1;
+
+  Toolkit::VisualFactory visualFactory = Toolkit::VisualFactory::Get();
+  Toolkit::Visual::Base visual;
+
+  Property::Map map;
+  map[Visual::Property::TYPE] = Visual::COLOR;
+  map[ColorVisual::Property::MIX_COLOR] = Color::RED;
+
+  visual = visualFactory.CreateVisual( map );
+  DALI_TEST_CHECK(visual);
+
+  // Register index with a color visual
+  dummyImpl.RegisterVisual( TEST_PROPERTY, dummy, visual );
+
+  Stage::GetCurrent().Add(dummy);
+
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == true);
+
+  DALI_TEST_CHECK( dummy.OnStage() == true );
+
+  dummyImpl.EnableVisual( TEST_PROPERTY, false );
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == false );
+
+  END_TEST;
+}
+
+int UtcDaliControlImplEnabledVisualParentRemovedFromStage(void)
+{
+  // Visual enabled but then parent removed from stage, test ensures visual/renderer are also removed from stage.
+  // Then adding parent back to stage should automatically put visual/renderer back
+
+  ToolkitTestApplication application;
+
+  DummyControl dummy = DummyControl::New();
+  DummyControlImpl& dummyImpl = static_cast<DummyControlImpl&>(dummy.GetImplementation());
+
+  Property::Index TEST_PROPERTY =1;
+
+  Toolkit::VisualFactory visualFactory = Toolkit::VisualFactory::Get();
+  Toolkit::Visual::Base visual;
+
+  Property::Map map;
+  map[Visual::Property::TYPE] = Visual::COLOR;
+  map[ColorVisual::Property::MIX_COLOR] = Color::RED;
+
+  visual = visualFactory.CreateVisual( map );
+  DALI_TEST_CHECK(visual);
+
+  // Register index with a color visual
+  dummyImpl.RegisterVisual( TEST_PROPERTY, dummy, visual, false );
+
+  Stage::GetCurrent().Add(dummy);
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == false );
+  DALI_TEST_CHECK( dummy.OnStage() == true );
+  dummyImpl.EnableVisual( TEST_PROPERTY, true );
+
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 1u );
+
+  // Remove control from stage, visual should be removed from stage too
+  Stage::GetCurrent().Remove(dummy);
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 0u );
+
+  Stage::GetCurrent().Add(dummy);
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 1u );
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY ) == true );
+
+  END_TEST;
+}
+
+int UtcDaliControlImplRegisterTwoVisualsAndEnableOnlyOne(void)
+{
+  // Register 2 visuals and enable by default
+  // Disable 1 visual
+  // Remove control from stage then put it back
+  // Check that only 1 visual/renderer is staged.
+
+  ToolkitTestApplication application;
+
+  DummyControl dummy = DummyControl::New();
+  DummyControlImpl& dummyImpl = static_cast<DummyControlImpl&>(dummy.GetImplementation());
+
+  Property::Index TEST_PROPERTY1 =1;
+  Property::Index TEST_PROPERTY2 =2;
+
+  Toolkit::VisualFactory visualFactory = Toolkit::VisualFactory::Get();
+  Toolkit::Visual::Base visual1;
+  Toolkit::Visual::Base visual2;
+
+  Property::Map map;
+  map[Visual::Property::TYPE] = Visual::COLOR;
+  map[ColorVisual::Property::MIX_COLOR] = Color::RED;
+
+  Property::Map map2;
+  map[Visual::Property::TYPE] = Visual::COLOR;
+  map[ColorVisual::Property::MIX_COLOR] = Color::BLUE;
+
+  visual1 = visualFactory.CreateVisual( map );
+  DALI_TEST_CHECK(visual1);
+
+  visual2 = visualFactory.CreateVisual( map );
+  DALI_TEST_CHECK(visual2);
+
+  // Register index with a color visual
+  dummyImpl.RegisterVisual( TEST_PROPERTY1, dummy, visual1 );
+  // Register second index with a color visual
+  dummyImpl.RegisterVisual( TEST_PROPERTY2, dummy, visual2 );
+
+  Stage::GetCurrent().Add(dummy);
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 2u );
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY1 ) == true );
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY1 ) == true);
+  DALI_TEST_CHECK( dummy.OnStage() == true );
+  dummyImpl.EnableVisual( TEST_PROPERTY2, false );
+
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 1u );
+
+  // Remove control from stage, visual should be removed from stage too
+  Stage::GetCurrent().Remove(dummy);
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 0u );
+
+  Stage::GetCurrent().Add(dummy);
+  // Render and notify
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_CHECK( dummy.GetRendererCount() == 1u );
+
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY1 ) == true );
+  DALI_TEST_CHECK( dummyImpl.IsVisualEnabled( TEST_PROPERTY2 ) == false );
+
+  END_TEST;
+}
+
index 53c9293..58d2d92 100644 (file)
@@ -60,16 +60,18 @@ 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;
+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++ )
   {
@@ -397,7 +399,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
@@ -661,6 +663,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 +679,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 +702,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 +713,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 +722,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 +731,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 )
@@ -928,10 +977,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 +997,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 )
index 9cee83e..eb7d6a9 100644 (file)
@@ -296,8 +296,8 @@ public:
 protected: // For derived classes to call
 
   /**
-   * @brief Register a visual by Property Index, linking an Actor to controlRenderer when required.
-   * In the case of the visual being an actor or control deeming controlRenderer not required then controlRenderer should be an empty handle.
+   * @brief Register a visual by Property Index, linking an Actor to visual when required.
+   * In the case of the visual being an actor or control deeming visual not required then visual should be an empty handle.
    * No parenting is done during registration, this should be done by derived class.
    *
    * @SINCE_1_2.0
@@ -305,11 +305,28 @@ protected: // For derived classes to call
    * @param[in] index The Property index of the visual, used to reference visual
    * @param[in] placementActor The actor used to by the visual.
    * @param[in] visual The visual to register
-   * @note Derived class must NOT call visual.SetOnStage(placementActor). It is the responsibility of the base class to connect/disconnect registered visual to stage.
+   * @note Derived class should not call visual.SetOnStage(placementActor). It is the responsibility of the base class to connect/disconnect registered visual to stage.
+   *       Use below API with enabled set to false if derived class wishes to control when visual is staged.
    */
    void RegisterVisual( Property::Index index, Actor& placementActor, Toolkit::Visual::Base& visual );
 
    /**
+    * @brief Register a visual by Property Index, linking an Actor to visual when required.
+    * In the case of the visual being an actor or control deeming visual not required then visual should be an empty handle.
+    * If enabled is false then the visual is not set on stage until enabled by the derived class.
+    * @see EnableVisual
+    *
+    * @SINCE_1_2.11
+    *
+    * @param[in] index The Property index of the visual, used to reference visual
+    * @param[in] placementActor The actor used to by the visual.
+    * @param[in] visual The visual to register
+    * @param[in] enabled false if derived class wants to control when visual is set on stage.
+    *
+    */
+   void RegisterVisual( Property::Index index, Actor& placementActor, Toolkit::Visual::Base& visual, bool enabled );
+
+   /**
     * @brief Erase the entry matching the given index from the list of registered visuals
     * @param[in] index The Property index of the visual, used to reference visual
     *
@@ -329,6 +346,26 @@ protected: // For derived classes to call
    Toolkit::Visual::Base GetVisual( Property::Index index ) const;
 
    /**
+    * @brief Sets the given visual to be displayed or not when parent staged.
+    *
+    * @SINCE_1_2.11
+    *
+    * @param[in] index The Property index of the visual
+    * @param[in] enable flag to set enabled or disabled.
+    */
+   void EnableVisual( Property::Index index, bool enable );
+
+   /**
+    * @brief Queries if the given visual is to be displayed when parent staged.
+    *
+    * @SINCE_1_2.11
+    *
+    * @param[in] index The Property index of the visual
+    * @return bool whether visual is enabled or not
+    */
+   bool IsVisualEnabled( Property::Index index ) const;
+
+   /**
     * @brief Retrieve the placement actor associated with the given index.
     *
     * @SINCE_1_2.2