Remove std::map from custom property lookup, removes some 577 map.find calls from... 62/32162/4
authorKimmo Hoikka <kimmo.hoikka@samsung.com>
Tue, 16 Dec 2014 12:10:37 +0000 (12:10 +0000)
committerKimmo Hoikka <kimmo.hoikka@samsung.com>
Wed, 17 Dec 2014 10:42:50 +0000 (02:42 -0800)
[Problem] too much processing, too much memory consumption
[Cause] std::map used to store properties
[Solution] change to dali ownercontainer instead

Change-Id: I4653f3e26a83989a10eb22c45852efab27cd703f

dali/internal/event/actors/actor-impl.cpp
dali/internal/event/common/custom-property.h
dali/internal/event/common/proxy-object.cpp
dali/internal/event/common/proxy-object.h
dali/internal/event/effects/shader-effect-impl.cpp
dali/internal/event/events/pan-gesture-detector-impl.cpp
dali/internal/event/object/custom-object-internal.cpp

index 1ba9bd1..0e48d60 100644 (file)
@@ -3061,11 +3061,10 @@ const PropertyBase* Actor::GetSceneObjectAnimatableProperty( Property::Index ind
 
   if ( static_cast<unsigned int>(index) >= DEFAULT_PROPERTY_MAX_COUNT )
   {
-    CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
+    CustomProperty* custom = FindCustomProperty( index );
+    DALI_ASSERT_ALWAYS( custom && "Property index is invalid" );
 
-    DALI_ASSERT_ALWAYS( GetCustomPropertyLookup().end() != entry && "index is invalid" );
-
-    property = dynamic_cast<const PropertyBase*>( entry->second.GetSceneGraphProperty() );
+    property = custom->GetSceneGraphProperty();
   }
   else if( NULL != mNode )
   {
@@ -3167,11 +3166,9 @@ const PropertyInputImpl* Actor::GetSceneObjectInputProperty( Property::Index ind
 
   if ( index >= DEFAULT_PROPERTY_MAX_COUNT )
   {
-    CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
-
-    DALI_ASSERT_ALWAYS( GetCustomPropertyLookup().end() != entry && "property index is invalid" );
-
-    property = entry->second.GetSceneGraphProperty();
+    CustomProperty* custom = FindCustomProperty( index );
+    DALI_ASSERT_ALWAYS( custom && "Property index is invalid" );
+    property = custom->GetSceneGraphProperty();
   }
   else if( NULL != mNode )
   {
index f2f62ab..7034468 100644 (file)
@@ -23,7 +23,6 @@
 #include <utility>
 
 // INTERNAL INCLUDES
-#include <dali/public-api/common/map-wrapper.h>
 #include <dali/public-api/common/constants.h>
 #include <dali/public-api/object/property.h>
 
@@ -56,77 +55,85 @@ class PropertyBase;
 class CustomProperty
 {
 public:
-  /**
-   * Default constructor.
-   */
-  CustomProperty()
-  : type(Property::NONE),
-    mProperty(NULL),
-    mAccessMode(Property::READ_ONLY)
-  {
-  }
 
   /**
-   * Convenience constructor.
+   * Constructor for scene graph based properties
    * @param [in] newName The name of the custom property.
    * @param [in] newType The type ID of the custom property.
    * @param [in] newProperty A pointer to the scene-graph owned property.
    */
-  CustomProperty(const std::string& newName,
+  CustomProperty( const std::string& newName,
                   Property::Type newType,
                   const SceneGraph::PropertyBase* newProperty)
   : name(newName),
     type(newType),
+    value(), // value is held by newProperty
     mProperty(newProperty),
     mAccessMode(Property::ANIMATABLE)
   {
     DALI_ASSERT_DEBUG(mProperty && "Uninitialized scenegraph property") ;
   }
 
-  CustomProperty(const std::string& newName,
+  /**
+   * Constructor for event side only properties
+   * @param [in] newName The name of the custom property.
+   * @param [in] newIndex The index of the custom property.
+   * @param [in] newType The type ID of the custom property.
+   * @param [in] newProperty A pointer to the scene-graph owned property.
+   */
+  CustomProperty( const std::string& newName,
                   Property::Value newValue,
-                  Property::AccessMode accessMode)
+                  Property::AccessMode accessMode )
   : name(newName),
+    type(newValue.GetType()),
     value(newValue),
     mProperty(NULL),
     mAccessMode(accessMode)
   {
-    type = value.GetType() ;
     DALI_ASSERT_DEBUG(accessMode != Property::ANIMATABLE && "Animatable must have scenegraph property") ;
   }
 
+  /**
+   * @return true if the property is animatable (i.e. if its a scene graph property)
+   */
   bool IsAnimatable(void) const
   {
-    return NULL != mProperty ;
+    return NULL != mProperty;
   }
 
+  /**
+   * @return true if the property can be written to
+   */
   bool IsWritable(void) const
   {
     return (mAccessMode == Property::ANIMATABLE) || (mAccessMode == Property::READ_WRITE) ;
   }
 
-  std::string name; ///< The name of the property
-
-  Property::Type type; ///< The type of the property
-
-  Property::Value value ; ///< The property value for a non animatable and custom property
-
+  /**
+   * @return the scene graph property
+   */
   const SceneGraph::PropertyBase* GetSceneGraphProperty() const
   {
     DALI_ASSERT_DEBUG(mProperty && "Get on uninitialized SceneGraph property") ;
     return mProperty ;
   }
 
+  std::string name;       ///< The name of the property
+  Property::Type type;    ///< The type of the property
+  Property::Value value;  ///< The property value for a non animatable and custom property
+
+private:
+
+  // Not implemented
+  CustomProperty();
+  CustomProperty( const CustomProperty& );
+  CustomProperty& operator=( const CustomProperty& );
+
 private:
   const SceneGraph::PropertyBase* mProperty; ///< A pointer to a scene-graph property; should not be modified from actor-thread.
   Property::AccessMode mAccessMode; ///< The mode of the property
 };
 
-/**
- * Used for accessing scene-graph properties by property index
- */
-typedef std::map<Property::Index, CustomProperty> CustomPropertyLookup;
-
 } // namespace Internal
 
 } // namespace Dali
index 583fd95..c9bbbc2 100644 (file)
@@ -48,17 +48,13 @@ const int SUPPORTED_CAPABILITIES = Dali::Handle::DYNAMIC_PROPERTIES;  // ProxyOb
 typedef Dali::Vector<ProxyObject::Observer*>::Iterator ObserverIter;
 typedef Dali::Vector<ProxyObject::Observer*>::ConstIterator ConstObserverIter;
 
-static std::string EMPTY_PROPERTY_NAME;
-
 #if defined(DEBUG_ENABLED)
 Debug::Filter* gLogFilter = Debug::Filter::New(Debug::NoLogging, false, "LOG_PROXY_OBJECT" );
 #endif
 } // unnamed namespace
 
 ProxyObject::ProxyObject()
-: mNextCustomPropertyIndex( 0u ),
-  mCustomProperties( NULL ),
-  mTypeInfo( NULL ),
+: mTypeInfo( NULL ),
   mConstraints( NULL ),
   mPropertyNotifications( NULL )
 {
@@ -159,13 +155,9 @@ unsigned int ProxyObject::GetPropertyCount() const
     DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Manual Properties:  %d\n", manual );
   }
 
-  if( mCustomProperties )
-  {
-    unsigned int custom( mCustomProperties->size() );
-    count += custom;
-
-    DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Custom Properties:  %d\n", custom );
-  }
+  unsigned int custom( mCustomProperties.Count() );
+  count += custom;
+  DALI_LOG_INFO( gLogFilter, Debug::Verbose, "Custom Properties:  %d\n", custom );
 
   DALI_LOG_INFO( gLogFilter, Debug::Concise, "Total Properties:   %d\n", count );
 
@@ -194,14 +186,12 @@ std::string ProxyObject::GetPropertyName( Property::Index index ) const
     }
   }
 
-  if( mCustomProperties )
+  CustomProperty* custom = FindCustomProperty( index );
+  if( custom )
   {
-    CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Property index is invalid" );
-
-    return entry->second.name;
+    return custom->name;
   }
-  return EMPTY_PROPERTY_NAME;
+  return "";
 }
 
 Property::Index ProxyObject::GetPropertyIndex(const std::string& name) const
@@ -217,14 +207,16 @@ Property::Index ProxyObject::GetPropertyIndex(const std::string& name) const
     }
   }
 
-  if( index == Property::INVALID_INDEX && mCustomProperties )
+  if( ( index == Property::INVALID_INDEX )&&( mCustomProperties.Count() > 0 ) )
   {
-    // This is slow, but we're not (supposed to be) using property names frequently
-    for ( CustomPropertyLookup::const_iterator iter = mCustomProperties->begin(); mCustomProperties->end() != iter; ++iter )
+    Property::Index count = PROPERTY_CUSTOM_START_INDEX;
+    const CustomPropertyLookup::ConstIterator end = mCustomProperties.End();
+    for( CustomPropertyLookup::ConstIterator iter = mCustomProperties.Begin(); iter != end; ++iter, ++count )
     {
-      if (iter->second.name == name)
+      CustomProperty* custom = *iter;
+      if ( custom->name == name )
       {
-        index = iter->first;
+        index = count;
         break;
       }
     }
@@ -251,17 +243,15 @@ bool ProxyObject::IsPropertyWritable( Property::Index index ) const
     }
     else
     {
-      DALI_ASSERT_ALWAYS( ! "Cannot find property index" );
+      DALI_ASSERT_ALWAYS( ! "Invalid property index" );
     }
   }
 
-  if( mCustomProperties)
+  CustomProperty* custom = FindCustomProperty( index );
+  if( custom )
   {
     // Check that the index is valid
-    CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find property index" );
-
-    return entry->second.IsWritable();
+    return custom->IsWritable();
   }
   return false;
 }
@@ -281,18 +271,15 @@ bool ProxyObject::IsPropertyAnimatable( Property::Index index ) const
     return false;
   }
 
-  if( mCustomProperties )
+  CustomProperty* custom = FindCustomProperty( index );
+  if( custom )
   {
-    // Check custom property
-    CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find property index" );
-
-    return entry->second.IsAnimatable();
+    return custom->IsAnimatable();
   }
   return false;
 }
 
-bool ProxyObject::IsPropertyAConstraintInput(Property::Index index) const
+bool ProxyObject::IsPropertyAConstraintInput( Property::Index index ) const
 {
   DALI_ASSERT_ALWAYS(index > Property::INVALID_INDEX && "Property index is out of bounds");
 
@@ -307,12 +294,9 @@ bool ProxyObject::IsPropertyAConstraintInput(Property::Index index) const
     return false;
   }
 
-  if( mCustomProperties )
+  CustomProperty* custom = FindCustomProperty( index );
+  if( custom )
   {
-    // Check custom property
-    CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find property index" );
-
     // ... custom properties can be used as input to a constraint.
     return true;
   }
@@ -341,12 +325,10 @@ Property::Type ProxyObject::GetPropertyType( Property::Index index ) const
     }
   }
 
-  if( mCustomProperties )
+  CustomProperty* custom = FindCustomProperty( index );
+  if( custom )
   {
-    CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find Property index" );
-
-    return entry->second.type;
+    return custom->type;
   }
   return Property::NONE;
 }
@@ -373,19 +355,16 @@ void ProxyObject::SetProperty( Property::Index index, const Property::Value& pro
       DALI_ASSERT_ALWAYS( ! "Cannot find property index" );
     }
   }
-  else if( mCustomProperties )
+  else
   {
-    CustomPropertyLookup::iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find property index" );
-    DALI_ASSERT_ALWAYS( entry->second.IsWritable() && "Property is read-only" );
-
-    // this is only relevant for non animatable properties
-    if(entry->second.IsWritable())
-    {
-      entry->second.value = propertyValue;
-    }
+    CustomProperty* custom = FindCustomProperty( index );
+    DALI_ASSERT_ALWAYS( custom && "Invalid property index" );
+    DALI_ASSERT_ALWAYS( custom->IsWritable() && "Property is read-only" );
 
-    SetCustomProperty(index, entry->second, propertyValue);
+    // this is only relevant for non animatable properties, but we'll do it anyways
+    custom->value = propertyValue;
+    // set the scene graph property value
+    SetCustomProperty(index, *custom, propertyValue);
   }
 }
 
@@ -411,24 +390,24 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
       DALI_ASSERT_ALWAYS( ! "Cannot find property index" );
     }
   }
-  else if( mCustomProperties )
+  else if( mCustomProperties.Count() > 0 )
   {
-    CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-    DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find property index" );
+    CustomProperty* custom = FindCustomProperty( index );
+    DALI_ASSERT_ALWAYS( custom && "Invalid property index" );
 
-    if( !entry->second.IsAnimatable() )
+    if( !custom->IsAnimatable() )
     {
-      value = entry->second.value;
+      value = custom->value;
     }
     else
     {
       BufferIndex bufferIndex( Stage::GetCurrent()->GetEventBufferIndex() );
 
-      switch ( entry->second.type )
+      switch ( custom->type )
       {
         case Property::BOOLEAN:
         {
-          const AnimatableProperty<bool>* property = dynamic_cast< const AnimatableProperty<bool>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<bool>* property = dynamic_cast< const AnimatableProperty<bool>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -437,7 +416,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::FLOAT:
         {
-          const AnimatableProperty<float>* property = dynamic_cast< const AnimatableProperty<float>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<float>* property = dynamic_cast< const AnimatableProperty<float>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -446,7 +425,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::INTEGER:
         {
-          const AnimatableProperty<int>* property = dynamic_cast< const AnimatableProperty<int>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<int>* property = dynamic_cast< const AnimatableProperty<int>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -455,7 +434,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::VECTOR2:
         {
-          const AnimatableProperty<Vector2>* property = dynamic_cast< const AnimatableProperty<Vector2>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<Vector2>* property = dynamic_cast< const AnimatableProperty<Vector2>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -464,7 +443,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::VECTOR3:
         {
-          const AnimatableProperty<Vector3>* property = dynamic_cast< const AnimatableProperty<Vector3>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<Vector3>* property = dynamic_cast< const AnimatableProperty<Vector3>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -473,7 +452,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::VECTOR4:
         {
-          const AnimatableProperty<Vector4>* property = dynamic_cast< const AnimatableProperty<Vector4>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<Vector4>* property = dynamic_cast< const AnimatableProperty<Vector4>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -482,7 +461,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::MATRIX:
         {
-          const AnimatableProperty<Matrix>* property = dynamic_cast< const AnimatableProperty<Matrix>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<Matrix>* property = dynamic_cast< const AnimatableProperty<Matrix>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -491,7 +470,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::MATRIX3:
         {
-          const AnimatableProperty<Matrix3>* property = dynamic_cast< const AnimatableProperty<Matrix3>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<Matrix3>* property = dynamic_cast< const AnimatableProperty<Matrix3>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -500,7 +479,7 @@ Property::Value ProxyObject::GetProperty(Property::Index index) const
 
         case Property::ROTATION:
         {
-          const AnimatableProperty<Quaternion>* property = dynamic_cast< const AnimatableProperty<Quaternion>* >( entry->second.GetSceneGraphProperty() );
+          const AnimatableProperty<Quaternion>* property = dynamic_cast< const AnimatableProperty<Quaternion>* >( custom->GetSceneGraphProperty() );
           DALI_ASSERT_DEBUG( NULL != property );
 
           value = (*property)[ bufferIndex ];
@@ -535,23 +514,22 @@ void ProxyObject::GetPropertyIndices( Property::IndexContainer& indices ) const
   }
 
   // Custom Properties
-  if ( mCustomProperties )
+  if ( mCustomProperties.Count() > 0 )
   {
-    indices.reserve( indices.size() + mCustomProperties->size() );
+    indices.reserve( indices.size() + mCustomProperties.Count() );
 
-    const CustomPropertyLookup::const_iterator endIter = mCustomProperties->end();
-    for ( CustomPropertyLookup::const_iterator iter = mCustomProperties->begin(); iter != endIter; ++iter )
+    CustomPropertyLookup::ConstIterator iter = mCustomProperties.Begin();
+    const CustomPropertyLookup::ConstIterator endIter = mCustomProperties.End();
+    int i=0;
+    for ( ; iter != endIter; ++iter, ++i )
     {
-      indices.push_back( iter->first );
+      indices.push_back( PROPERTY_CUSTOM_START_INDEX + i );
     }
   }
 }
 
 Property::Index ProxyObject::RegisterProperty( std::string name, const Property::Value& propertyValue)
 {
-  // Assert that property name is unused
-  DALI_ASSERT_ALWAYS( Property::INVALID_INDEX == GetPropertyIndex(name) && "Property index is out of bounds" );
-
   // Create a new property
   Dali::Internal::OwnerPointer<PropertyBase> newProperty;
 
@@ -630,19 +608,8 @@ Property::Index ProxyObject::RegisterProperty( std::string name, const Property:
     }
   }
 
-  // Default properties start from index zero
-  if ( 0u == mNextCustomPropertyIndex )
-  {
-    mNextCustomPropertyIndex = PROPERTY_CUSTOM_START_INDEX;
-  }
-
-  // Add entry to the property lookup
-  const Property::Index index = mNextCustomPropertyIndex++;
-
-  CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
-  DALI_ASSERT_ALWAYS( mCustomProperties->end() == entry && "Custom property already registered" );
-
-  (*mCustomProperties)[ index ] = CustomProperty( name, propertyValue.GetType(), newProperty.Get() );
+  const Property::Index index = PROPERTY_CUSTOM_START_INDEX + mCustomProperties.Count();
+  mCustomProperties.PushBack( new CustomProperty( name, propertyValue.GetType(), newProperty.Get() ) );
 
   // The derived class now passes ownership of this new property to a scene-object
   // TODO: change this so that OwnerPointer is passed all the way as owership passing cannot be done with a reference
@@ -661,15 +628,9 @@ Property::Index ProxyObject::RegisterProperty( std::string name, const Property:
   }
   else
   {
-    // Default properties start from index zero
-    if ( 0u == mNextCustomPropertyIndex )
-    {
-      mNextCustomPropertyIndex = PROPERTY_CUSTOM_START_INDEX;
-    }
-
     // Add entry to the property lookup
-    index = mNextCustomPropertyIndex++;
-    GetCustomPropertyLookup()[ index ] = CustomProperty( name, propertyValue, accessMode );
+    index = PROPERTY_CUSTOM_START_INDEX + mCustomProperties.Count();
+    mCustomProperties.PushBack( new CustomProperty( name, propertyValue, accessMode ) );
   }
 
   return index;
@@ -683,14 +644,13 @@ Dali::PropertyNotification ProxyObject::AddPropertyNotification(Property::Index
   {
     if ( index <= PROPERTY_REGISTRATION_MAX_INDEX )
     {
-      DALI_ASSERT_ALWAYS( false && "Property notification added to non animatable property." );
+      DALI_ASSERT_ALWAYS( false && "Property notification added to event side only property." );
     }
-    else if ( mCustomProperties )
+    else if ( mCustomProperties.Count() > 0 )
     {
-      CustomPropertyLookup::const_iterator entry = mCustomProperties->find( index );
-      DALI_ASSERT_ALWAYS( mCustomProperties->end() != entry && "Cannot find property index" );
-
-      DALI_ASSERT_ALWAYS( entry->second.IsAnimatable() && "Property notification added to non animatable property (currently not suppported )");
+      CustomProperty* custom = FindCustomProperty( index );
+      DALI_ASSERT_ALWAYS( custom && "Invalid property index" );
+      DALI_ASSERT_ALWAYS( custom->IsAnimatable() && "Property notification added to event side only property." );
     }
   }
 
@@ -918,16 +878,6 @@ void ProxyObject::SetCustomProperty( Property::Index index, const CustomProperty
   }
 }
 
-CustomPropertyLookup& ProxyObject::GetCustomPropertyLookup() const
-{
-  // lazy create
-  if( !mCustomProperties )
-  {
-    mCustomProperties = new CustomPropertyLookup;
-  }
-  return *mCustomProperties;
-}
-
 const TypeInfo* ProxyObject::GetTypeInfo() const
 {
   if ( !mTypeInfo )
@@ -1044,11 +994,24 @@ ProxyObject::~ProxyObject()
     (*iter)->ProxyDestroyed(*this);
   }
 
-  delete mCustomProperties;
   delete mConstraints;
   delete mPropertyNotifications;
 }
 
+CustomProperty* ProxyObject::FindCustomProperty( Property::Index index ) const
+{
+  CustomProperty* property( NULL );
+  int arrayIndex = index - PROPERTY_CUSTOM_START_INDEX;
+  if( arrayIndex >= 0 )
+  {
+    if( arrayIndex < (int)mCustomProperties.Count() ) // we can only access the first 2 billion custom properties
+    {
+      property = mCustomProperties[ arrayIndex ];
+    }
+  }
+  return property;
+}
+
 } // namespace Internal
 
 } // namespace Dali
index 8cfef1b..c42be6c 100644 (file)
@@ -30,6 +30,7 @@
 #include <dali/public-api/object/property-index.h>
 #include <dali/public-api/object/property-input.h>
 #include <dali/public-api/object/property-notification.h>
+#include <dali/internal/common/owner-container.h>
 #include <dali/internal/event/common/object-impl.h>
 #include <dali/internal/event/common/custom-property.h>
 #include <dali/internal/event/common/property-input-impl.h>
@@ -41,6 +42,12 @@ namespace Dali
 namespace Internal
 {
 
+class Stage;
+class PropertyInputImpl;
+class ProxyObject;
+class Constraint;
+class TypeInfo;
+
 /**
  * @brief Structure for setting up default properties and their details.
  */
@@ -53,12 +60,6 @@ struct PropertyDetails
   bool constraintInput:1;   ///< Whether the property can be used as an input to a constraint.
 };
 
-class Stage;
-class PropertyInputImpl;
-class ProxyObject;
-class Constraint;
-class TypeInfo;
-
 namespace SceneGraph
 {
 class PropertyBase;
@@ -231,24 +232,24 @@ public: // Property system interface from Internal::Object
   virtual Property::Index RegisterProperty(std::string name, const Property::Value& propertyValue);
 
   /**
-   * @copydoc Dali::Handle::RegisterProperty(std::string name, Property::Value propertyValue, Property::AccessMode accessMode)
+   * @copydoc Dali::Internal::Object::RegisterProperty(std::string name, Property::Value propertyValue, Property::AccessMode accessMode)
    */
   virtual Property::Index RegisterProperty(std::string name, const Property::Value& propertyValue, Property::AccessMode accessMode);
 
   /**
-   * @copydoc Dali::Handle::AddPropertyNotification()
+   * @copydoc Dali::Internal::Object::AddPropertyNotification()
    */
   virtual Dali::PropertyNotification AddPropertyNotification(Property::Index index,
                                                              int componentIndex,
                                                              const Dali::PropertyCondition& condition);
 
   /**
-   * @copydoc Dali::Handle::RemovePropertyNotification()
+   * @copydoc Dali::Internal::Object::RemovePropertyNotification()
    */
   virtual void RemovePropertyNotification(Dali::PropertyNotification propertyNotification);
 
   /**
-   * @copydoc Dali::Handle::RemovePropertyNotifications()
+   * @copydoc Dali::Internal::Object::RemovePropertyNotifications()
    */
   void RemovePropertyNotifications();
 
@@ -442,23 +443,23 @@ private: // Default property extensions for derived classes
 protected:
 
   /**
-   * Not all proxy objects will have custom properties so we want to only create the lookup when its actually needed
-   * @return the custom property lookup
-   */
-  CustomPropertyLookup& GetCustomPropertyLookup() const;
-
-  /**
    * Retrieves the TypeInfo for this object. Only retrieves it from the type-registry once and then stores a pointer
    * to it locally there-after. The type info will not change during the life-time of the application.
    * @return The type-info for this object (Can be NULL)
    */
   const TypeInfo* GetTypeInfo() const;
 
-private:
+  /**
+   * Helper to find custom property
+   * @param index
+   * @return pointer to the property
+   */
+  CustomProperty* FindCustomProperty( Property::Index index ) const;
 
-  Property::Index mNextCustomPropertyIndex; ///< The ID of the next custom property to be registered
+private:
 
-  mutable CustomPropertyLookup* mCustomProperties; ///< Used for accessing custom Node properties, mutable so it can be lazy initialized from const function
+  typedef OwnerContainer<CustomProperty*> CustomPropertyLookup;
+  CustomPropertyLookup mCustomProperties; ///< Used for accessing custom Node properties
   mutable TypeInfo const *  mTypeInfo; ///< The type-info for this object, mutable so it can be lazy initialized from const method if it is required
 
   Dali::Vector<Observer*> mObservers;
index ab85eb8..c98419e 100644 (file)
@@ -43,7 +43,6 @@ using Dali::Internal::SceneGraph::UniformMeta;
 using Dali::Internal::SceneGraph::Shader;
 using Dali::Internal::SceneGraph::AnimatableProperty;
 using Dali::Internal::SceneGraph::PropertyBase;
-using Dali::Internal::SceneGraph::PropertyBase;
 using Dali::Internal::SceneGraph::RenderQueue;
 using std::string;
 
@@ -614,24 +613,14 @@ const SceneGraph::PropertyOwner* ShaderEffect::GetSceneObject() const
 
 const PropertyBase* ShaderEffect::GetSceneObjectAnimatableProperty( Property::Index index ) const
 {
-  CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
-
-  DALI_ASSERT_ALWAYS( GetCustomPropertyLookup().end() != entry && "Property index is invalid" );
-
-  DALI_ASSERT_ALWAYS( entry->second.IsAnimatable() && "shader effect has only animatable properties" );
-
-  return dynamic_cast<const PropertyBase*>( entry->second.GetSceneGraphProperty() );
+  CustomProperty* custom = FindCustomProperty( index );
+  DALI_ASSERT_ALWAYS( custom && "Property index is invalid" );
+  return custom->GetSceneGraphProperty();
 }
 
 const PropertyInputImpl* ShaderEffect::GetSceneObjectInputProperty( Property::Index index ) const
 {
-  CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
-
-  DALI_ASSERT_ALWAYS( GetCustomPropertyLookup().end() != entry && "Property index is invalid" );
-
-  DALI_ASSERT_ALWAYS( entry->second.IsAnimatable() && "shader effect has only animatable properties" );
-
-  return entry->second.GetSceneGraphProperty();
+  return GetSceneObjectAnimatableProperty( index );
 }
 
 } // namespace Internal
index ada772d..00c1efb 100644 (file)
@@ -556,11 +556,9 @@ const PropertyInputImpl* PanGestureDetector::GetSceneObjectInputProperty( Proper
 
   if ( index >= DEFAULT_PROPERTY_MAX_COUNT )
   {
-    CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
-
-    DALI_ASSERT_ALWAYS( GetCustomPropertyLookup().end() != entry && "property index is invalid" );
-
-    property = entry->second.GetSceneGraphProperty();
+    CustomProperty* custom = FindCustomProperty( index );
+    DALI_ASSERT_ALWAYS( custom && "Property index is invalid" );
+    property = custom->GetSceneGraphProperty();
   }
   else
   {
index b16d254..4a0ae90 100644 (file)
@@ -54,15 +54,9 @@ const SceneGraph::PropertyOwner* CustomObject::GetSceneObject() const
 
 const PropertyBase* CustomObject::GetSceneObjectAnimatableProperty( Property::Index index ) const
 {
-  const PropertyBase* property( NULL );
-
-  CustomPropertyLookup::const_iterator entry = GetCustomPropertyLookup().find( index );
-
-  DALI_ASSERT_ALWAYS( GetCustomPropertyLookup().end() != entry && "index is invalid" );
-
-  property = dynamic_cast<const PropertyBase*>( entry->second.GetSceneGraphProperty() );
-
-  return property;
+  CustomProperty* custom = FindCustomProperty( index );
+  DALI_ASSERT_ALWAYS( custom && "Property index is invalid" );
+  return custom->GetSceneGraphProperty();;
 }
 
 const PropertyInputImpl* CustomObject::GetSceneObjectInputProperty( Property::Index index ) const