X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=dali%2Finternal%2Fevent%2Fcommon%2Ftype-info-impl.cpp;h=81155efefda5500a95483bb4831141bf2008960e;hb=f15d1ed84355ced4b6c5115b8aebb68d897cd374;hp=e3f8d7959b4bb1ae560ddf0a7295686f4b3d1630;hpb=73eb065ebb6ea7914a1dc05da5b0f185ab673a2b;p=platform%2Fcore%2Fuifw%2Fdali-core.git diff --git a/dali/internal/event/common/type-info-impl.cpp b/dali/internal/event/common/type-info-impl.cpp index e3f8d79..81155ef 100644 --- a/dali/internal/event/common/type-info-impl.cpp +++ b/dali/internal/event/common/type-info-impl.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017 Samsung Electronics Co., Ltd. + * Copyright (c) 2018 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. @@ -29,6 +29,12 @@ using std::find_if; +namespace Dali +{ + +namespace Internal +{ + namespace { @@ -80,7 +86,7 @@ private: template struct PropertyComponentFinder { - PropertyComponentFinder( Dali::Property::Index basePropertyIndex, const int find ) + PropertyComponentFinder( Property::Index basePropertyIndex, const int find ) : mBasePropertyIndex( basePropertyIndex ), mFind( find ) { @@ -93,27 +99,78 @@ struct PropertyComponentFinder private: - Dali::Property::Index mBasePropertyIndex; + Property::Index mBasePropertyIndex; const int mFind; }; -} // namespace anon - -namespace Dali +/** + * Helper function to find the right default property with given index and return the desired detail of it + */ +template< typename Parameter, typename Member > +inline bool GetDefaultPropertyField( const Dali::PropertyDetails* propertyTable, Property::Index count, Property::Index index, Member member, Parameter& parameter ) { + bool found = false; + // is index inside this table (bigger than first index but smaller than first + count) + if( ( index >= propertyTable->enumIndex ) && ( index < ( propertyTable->enumIndex + count ) ) ) + { + // return the match. we're assuming here that there is no gaps between the indices in a table + parameter = propertyTable[ index - propertyTable->enumIndex ].*member; + found = true; + } + // should never really get here + return found; +} -namespace Internal +// static pointer value to mark that a base class address has not been resolved +// 0x01 is not a valid pointer but used here to differentiate from nullptr +// unfortunately it cannot be constexpr as C++ does not allow them to be initialised with reinterpret_cast +Internal::TypeInfo* const UNRESOLVED = reinterpret_cast( 0x1 ); + +/** + * Helper function to resolve and return the pointer to the base type info + * Not a member function to avoid having to #include additional headers and to make sure this gets inlined inside this cpp + * @param[in/out] baseType pointer to resolve and set + * @param[in] typeRegistry reference to the type registry + * @param[in] baseTypeName string name of the base type + * @return true is base type exists + */ +inline bool GetBaseType( Internal::TypeInfo*& baseType, TypeRegistry& typeRegistry, const std::string& baseTypeName ) { + // if greater than unresolved means we have a base type, null means no base + bool baseExists = ( baseType > UNRESOLVED ); + // base only needs to be resolved once + if( UNRESOLVED == baseType ) + { + TypeRegistry::TypeInfoPointer base = typeRegistry.GetTypeInfo( baseTypeName ); + if( base ) + { + baseType = base.Get(); // dont pass ownership, just return raw pointer + baseExists = true; + } + else + { + // no type info found so assuming no base as all type registration is done in startup for now + baseType = nullptr; + } + } + return baseExists; +} + +} // unnamed namespace -TypeInfo::TypeInfo(const std::string &name, const std::string &baseTypeName, Dali::TypeInfo::CreateFunction creator) - : mTypeName(name), mBaseTypeName(baseTypeName), mCSharpType(false), mCreate(creator) +TypeInfo::TypeInfo( const std::string &name, const std::string &baseTypeName, Dali::TypeInfo::CreateFunction creator, + const Dali::PropertyDetails* defaultProperties, Property::Index defaultPropertyCount ) +: mTypeRegistry( *TypeRegistry::Get() ), mBaseType( UNRESOLVED ), + mTypeName( name ), mBaseTypeName( baseTypeName ), mCreate( creator ), mDefaultProperties( defaultProperties ), + mDefaultPropertyCount( defaultPropertyCount ), mCSharpType( false ) { DALI_ASSERT_ALWAYS(!name.empty() && "Type info construction must have a name"); DALI_ASSERT_ALWAYS(!baseTypeName.empty() && "Type info construction must have a base type name"); } TypeInfo::TypeInfo(const std::string &name, const std::string &baseTypeName, Dali::CSharpTypeInfo::CreateFunction creator) - : mTypeName(name), mBaseTypeName(baseTypeName), mCSharpType(true), mCSharpCreate(creator) +: mTypeRegistry( *TypeRegistry::Get() ), mBaseType( UNRESOLVED ), + mTypeName( name ), mBaseTypeName( baseTypeName ), mCSharpCreate( creator ), mCSharpType( true ) { DALI_ASSERT_ALWAYS(!name.empty() && "Type info construction must have a name"); DALI_ASSERT_ALWAYS(!baseTypeName.empty() && "Type info construction must have a base type name"); @@ -154,7 +211,7 @@ BaseHandle TypeInfo::CreateInstance() const return ret; } - bool TypeInfo::DoActionTo(BaseObject *object, const std::string &actionName, const Property::Map &properties) +bool TypeInfo::DoActionTo(BaseObject *object, const std::string &actionName, const Property::Map &properties) { bool done = false; @@ -164,22 +221,13 @@ BaseHandle TypeInfo::CreateInstance() const { done = (iter->second)(object, actionName, properties); } - else - { - DALI_LOG_WARNING("Type '%s' cannot do action '%s'\n", mTypeName.c_str(), actionName.c_str()); - } - if(!done) + if( !done ) { - Dali::TypeInfo base = Dali::TypeRegistry::Get().GetTypeInfo( mBaseTypeName ); - while( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - done = GetImplementation(base).DoActionTo(object, actionName, properties); - if( done ) - { - break; - } - base = Dali::TypeRegistry::Get().GetTypeInfo( base.GetBaseName() ); + // call base type recursively + done = mBaseType->DoActionTo( object, actionName, properties ); } } @@ -198,6 +246,15 @@ bool TypeInfo::ConnectSignal( BaseObject* object, ConnectionTrackerInterface* co connected = (iter->second)( object, connectionTracker, signalName, functor ); } + if( !connected ) + { + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + connected = mBaseType->ConnectSignal( object, connectionTracker, signalName, functor ); + } + } + return connected; } @@ -216,92 +273,68 @@ Dali::TypeInfo::CreateFunction TypeInfo::GetCreator() const return mCreate; } -size_t TypeInfo::GetActionCount() const +uint32_t TypeInfo::GetActionCount() const { - size_t count = mActions.size(); + uint32_t count = static_cast( mActions.size() ); - Dali::TypeInfo base = Dali::TypeRegistry::Get().GetTypeInfo( mBaseTypeName ); - while( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - count += GetImplementation(base).mActions.size(); - base = Dali::TypeRegistry::Get().GetTypeInfo( base.GetBaseName() ); + // call base type recursively + count += mBaseType->GetActionCount(); } return count; } -std::string TypeInfo::GetActionName(size_t index) const +std::string TypeInfo::GetActionName( uint32_t index ) const { std::string name; + const uint32_t count = static_cast( mActions.size() ); - if( index < mActions.size() ) + if( index < count ) { name = mActions[index].first; } else { - size_t count = mActions.size(); - - Dali::TypeInfo base = Dali::TypeRegistry::Get().GetTypeInfo( mBaseTypeName ); - while( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - size_t baseCount = GetImplementation(base).mActions.size(); - - if( index < count + baseCount ) - { - name = GetImplementation(base).mActions[ index - count ].first; - break; - } - - count += baseCount; - - base = Dali::TypeRegistry::Get().GetTypeInfo( base.GetBaseName() ); + // call base type recursively + return mBaseType->GetActionName( index - count ); } } return name; } -size_t TypeInfo::GetSignalCount() const +uint32_t TypeInfo::GetSignalCount() const { - size_t count = mSignalConnectors.size(); + uint32_t count = static_cast( mSignalConnectors.size() ); - Dali::TypeInfo base = Dali::TypeRegistry::Get().GetTypeInfo( mBaseTypeName ); - while( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - count += GetImplementation(base).mSignalConnectors.size(); - base = Dali::TypeRegistry::Get().GetTypeInfo( base.GetBaseName() ); + // call base type recursively + count += mBaseType->GetSignalCount(); } return count; } -std::string TypeInfo::GetSignalName(size_t index) const +std::string TypeInfo::GetSignalName( uint32_t index ) const { std::string name; + const uint32_t count = static_cast( mSignalConnectors.size() ); - if( index < mSignalConnectors.size() ) + if( index < count ) { name = mSignalConnectors[index].first; } else { - size_t count = mSignalConnectors.size(); - - Dali::TypeInfo base = Dali::TypeRegistry::Get().GetTypeInfo( mBaseTypeName ); - while( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - size_t baseCount = GetImplementation(base).mSignalConnectors.size(); - - if( index < count + baseCount ) - { - name = GetImplementation(base).mSignalConnectors[ index - count ].first; - break; - } - - count += baseCount; - - base = Dali::TypeRegistry::Get().GetTypeInfo( base.GetBaseName() ); + // call base type recursively + return mBaseType->GetSignalName( index - count ); } } @@ -310,47 +343,107 @@ std::string TypeInfo::GetSignalName(size_t index) const void TypeInfo::GetPropertyIndices( Property::IndexContainer& indices ) const { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + // Default Properties + if( mDefaultProperties ) + { + indices.Reserve( indices.Size() + mDefaultPropertyCount ); + for( Property::Index index = 0; index < mDefaultPropertyCount; ++index ) + { + indices.PushBack( mDefaultProperties[ index ].enumIndex ); + } + } + + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + mBaseType->GetPropertyIndices( indices ); + } + + AppendProperties( indices, mRegisteredProperties ); +} + +void TypeInfo::GetChildPropertyIndices( Property::IndexContainer& indices ) const +{ + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - const TypeInfo& baseImpl( GetImplementation( base ) ); - baseImpl.GetPropertyIndices( indices ); + // call base type recursively + mBaseType->GetChildPropertyIndices( indices ); } - if ( ! mRegisteredProperties.empty() ) + AppendProperties( indices, mRegisteredChildProperties ); +} + +/** + * Append the indices in RegisteredProperties to the given index container. + */ +void TypeInfo::AppendProperties( Dali::Property::IndexContainer& indices, + const TypeInfo::RegisteredPropertyContainer& registeredProperties ) const +{ + if ( ! registeredProperties.empty() ) { - indices.Reserve( indices.Size() + mRegisteredProperties.size() ); + indices.Reserve( indices.Size() + registeredProperties.size() ); - const RegisteredPropertyContainer::const_iterator endIter = mRegisteredProperties.end(); - for ( RegisteredPropertyContainer::const_iterator iter = mRegisteredProperties.begin(); iter != endIter; ++iter ) + for( auto&& elem : registeredProperties ) { - indices.PushBack( iter->first ); + indices.PushBack( elem.first ); } } } -const std::string& TypeInfo::GetPropertyName( Property::Index index ) const +const std::string& TypeInfo::GetRegisteredPropertyName( Property::Index index ) const { RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); - if ( iter != mRegisteredProperties.end() ) { return iter->second.name; } + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + return mBaseType->GetRegisteredPropertyName( index ); + } + static std::string empty; + return empty; +} - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) +std::string TypeInfo::GetPropertyName( Property::Index index ) const +{ + std::string propertyName; + // default or custom + if ( mDefaultProperties && ( index < DEFAULT_PROPERTY_MAX_COUNT ) ) { - return GetImplementation(base).GetPropertyName( index ); + std::string_view name; + if( GetDefaultPropertyField( mDefaultProperties, mDefaultPropertyCount,index, &Dali::PropertyDetails::name, name ) ) + { + propertyName = name; + } + } + else + { + RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), + PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); + if ( iter != mRegisteredProperties.end() ) + { + return iter->second.name; + } + } + // if not our property, go to parent + if( propertyName.empty() ) + { + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + return mBaseType->GetPropertyName( index ); + } } - DALI_ASSERT_ALWAYS( ! "Cannot find property index" ); // use the same assert as Object + return propertyName; } -void TypeInfo::AddActionFunction( const std::string &actionName, Dali::TypeInfo::ActionFunction function ) +void TypeInfo::AddActionFunction(std::string actionName, Dali::TypeInfo::ActionFunction function) { - if( NULL == function) + if( nullptr == function) { DALI_LOG_WARNING("Action function is empty\n"); } @@ -361,7 +454,7 @@ void TypeInfo::AddActionFunction( const std::string &actionName, Dali::TypeInfo: if( iter == mActions.end() ) { - mActions.push_back( ActionPair( actionName, function ) ); + mActions.push_back(ActionPair(std::move(actionName), function)); } else { @@ -370,9 +463,9 @@ void TypeInfo::AddActionFunction( const std::string &actionName, Dali::TypeInfo: } } -void TypeInfo::AddConnectorFunction( const std::string& signalName, Dali::TypeInfo::SignalConnectorFunction function ) +void TypeInfo::AddConnectorFunction(std::string signalName, Dali::TypeInfo::SignalConnectorFunction function) { - if( NULL == function) + if( nullptr == function) { DALI_LOG_WARNING("Connector function is empty\n"); } @@ -383,7 +476,7 @@ void TypeInfo::AddConnectorFunction( const std::string& signalName, Dali::TypeIn if( iter == mSignalConnectors.end() ) { - mSignalConnectors.push_back( ConnectionPair( signalName, function ) ); + mSignalConnectors.push_back(ConnectionPair(std::move(signalName), function)); } else { @@ -392,11 +485,11 @@ void TypeInfo::AddConnectorFunction( const std::string& signalName, Dali::TypeIn } } -void TypeInfo::AddProperty( const std::string& name, Property::Index index, Property::Type type, Dali::TypeInfo::SetPropertyFunction setFunc, Dali::TypeInfo::GetPropertyFunction getFunc ) +void TypeInfo::AddProperty(std::string name, Property::Index index, Property::Type type, Dali::TypeInfo::SetPropertyFunction setFunc, Dali::TypeInfo::GetPropertyFunction getFunc) { // The setter can be empty as a property can be read-only. - if ( NULL == getFunc ) + if ( nullptr == getFunc ) { DALI_ASSERT_ALWAYS( ! "GetProperty Function is empty" ); } @@ -407,7 +500,7 @@ void TypeInfo::AddProperty( const std::string& name, Property::Index index, Prop if ( iter == mRegisteredProperties.end() ) { - mRegisteredProperties.push_back( RegisteredPropertyPair( index, RegisteredProperty( type, setFunc, getFunc, name, Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX ) ) ); + mRegisteredProperties.push_back(RegisteredPropertyPair(index, RegisteredProperty(type, setFunc, getFunc, std::move(name), Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX))); } else { @@ -416,12 +509,12 @@ void TypeInfo::AddProperty( const std::string& name, Property::Index index, Prop } } -void TypeInfo::AddProperty( const std::string& name, Property::Index index, Property::Type type, Dali::CSharpTypeInfo::SetPropertyFunction setFunc, Dali::CSharpTypeInfo::GetPropertyFunction getFunc) +void TypeInfo::AddProperty(std::string name, Property::Index index, Property::Type type, Dali::CSharpTypeInfo::SetPropertyFunction setFunc, Dali::CSharpTypeInfo::GetPropertyFunction getFunc) { // The setter can be empty as a property can be read-only. - if ( NULL == getFunc ) + if ( nullptr == getFunc ) { DALI_ASSERT_ALWAYS( ! "GetProperty Function is empty" ); } @@ -432,7 +525,7 @@ void TypeInfo::AddProperty( const std::string& name, Property::Index index, Prop if ( iter == mRegisteredProperties.end() ) { - mRegisteredProperties.push_back( RegisteredPropertyPair( index, RegisteredProperty( type, setFunc, getFunc, name, Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX ) ) ); + mRegisteredProperties.push_back(RegisteredPropertyPair(index, RegisteredProperty(type, setFunc, getFunc, std::move(name), Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX))); } else { @@ -442,15 +535,14 @@ void TypeInfo::AddProperty( const std::string& name, Property::Index index, Prop } - -void TypeInfo::AddAnimatableProperty( const std::string& name, Property::Index index, Property::Type type ) +void TypeInfo::AddAnimatableProperty(std::string name, Property::Index index, Property::Type type) { RegisteredPropertyContainer::iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), PairFinder< Property::Index, RegisteredPropertyPair>(index) ); if ( iter == mRegisteredProperties.end() ) { - mRegisteredProperties.push_back( RegisteredPropertyPair( index, RegisteredProperty( type, name, Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX ) ) ); + mRegisteredProperties.push_back(RegisteredPropertyPair(index, RegisteredProperty(type, std::move(name), Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX))); } else { @@ -458,15 +550,15 @@ void TypeInfo::AddAnimatableProperty( const std::string& name, Property::Index i } } -void TypeInfo::AddAnimatableProperty( const std::string& name, Property::Index index, const Property::Value& defaultValue ) +void TypeInfo::AddAnimatableProperty(std::string name, Property::Index index, Property::Value defaultValue) { RegisteredPropertyContainer::iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), PairFinder< Property::Index, RegisteredPropertyPair>(index) ); if ( iter == mRegisteredProperties.end() ) { - mRegisteredProperties.push_back( RegisteredPropertyPair( index, RegisteredProperty( defaultValue.GetType(), name, Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX ) ) ); - mPropertyDefaultValues.push_back( PropertyDefaultValuePair( index, defaultValue ) ); + mRegisteredProperties.push_back(RegisteredPropertyPair(index, RegisteredProperty(defaultValue.GetType(), std::move(name), Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX))); + mPropertyDefaultValues.push_back(PropertyDefaultValuePair(index, std::move(defaultValue))); } else { @@ -474,7 +566,7 @@ void TypeInfo::AddAnimatableProperty( const std::string& name, Property::Index i } } -void TypeInfo::AddAnimatablePropertyComponent( const std::string& name, Property::Index index, Property::Index baseIndex, unsigned int componentIndex ) +void TypeInfo::AddAnimatablePropertyComponent(std::string name, Property::Index index, Property::Index baseIndex, uint32_t componentIndex) { Property::Type type = GetPropertyType( baseIndex ); DALI_ASSERT_ALWAYS( ( type == Property::VECTOR2 || type == Property::VECTOR3 || type == Property::VECTOR4 ) && "Base property does not support component" ); @@ -491,7 +583,7 @@ void TypeInfo::AddAnimatablePropertyComponent( const std::string& name, Property if ( iter == mRegisteredProperties.end() ) { - mRegisteredProperties.push_back( RegisteredPropertyPair( index, RegisteredProperty( type, name, baseIndex, componentIndex ) ) ); + mRegisteredProperties.push_back(RegisteredPropertyPair(index, RegisteredProperty(type, std::move(name), baseIndex, componentIndex))); success = true; } } @@ -499,14 +591,14 @@ void TypeInfo::AddAnimatablePropertyComponent( const std::string& name, Property DALI_ASSERT_ALWAYS( success && "Property component already registered" ); } -void TypeInfo::AddChildProperty( const std::string& name, Property::Index index, Property::Type type ) +void TypeInfo::AddChildProperty(std::string name, Property::Index index, Property::Type type) { RegisteredPropertyContainer::iterator iter = find_if( mRegisteredChildProperties.begin(), mRegisteredChildProperties.end(), PairFinder< Property::Index, RegisteredPropertyPair>(index) ); if ( iter == mRegisteredChildProperties.end() ) { - mRegisteredChildProperties.push_back( RegisteredPropertyPair( index, RegisteredProperty( type, name, Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX ) ) ); + mRegisteredChildProperties.push_back(RegisteredPropertyPair(index, RegisteredProperty(type, std::move(name), Property::INVALID_INDEX, Property::INVALID_COMPONENT_INDEX))); } else { @@ -514,16 +606,14 @@ void TypeInfo::AddChildProperty( const std::string& name, Property::Index index, } } -size_t TypeInfo::GetPropertyCount() const +uint32_t TypeInfo::GetPropertyCount() const { - size_t count( mRegisteredProperties.size() ); + uint32_t count = mDefaultPropertyCount + static_cast( mRegisteredProperties.size() ); - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - while ( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - const TypeInfo& baseImpl( GetImplementation(base) ); - count += baseImpl.mRegisteredProperties.size(); - base = TypeRegistry::Get()->GetTypeInfo( baseImpl.mBaseTypeName ); + // call base type recursively + count += mBaseType->GetPropertyCount(); } return count; @@ -532,21 +622,34 @@ size_t TypeInfo::GetPropertyCount() const Property::Index TypeInfo::GetPropertyIndex( const std::string& name ) const { Property::Index index = Property::INVALID_INDEX; + bool found = false; - // Slow but should not be done that often - RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), - PropertyNameFinder< RegisteredPropertyPair >( name ) ); - - if ( iter != mRegisteredProperties.end() ) + // check default properties + if( mDefaultProperties ) { - index = iter->first; + for( Property::Index tableIndex = 0; tableIndex < mDefaultPropertyCount; ++tableIndex ) + { + if(mDefaultProperties[tableIndex].name == name) + { + index = mDefaultProperties[ tableIndex ].enumIndex; + found = true; + break; + } + } } - else + if( !found ) { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + // Slow but should not be done that often + RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), + PropertyNameFinder< RegisteredPropertyPair >( name ) ); + if ( iter != mRegisteredProperties.end() ) + { + index = iter->first; + } + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - index = GetImplementation(base).GetPropertyIndex( name ); + // call base type recursively + index = mBaseType->GetPropertyIndex( name ); } } @@ -564,19 +667,16 @@ Property::Index TypeInfo::GetBasePropertyIndex( Property::Index index ) const { basePropertyIndex = iter->second.basePropertyIndex; } - else + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) - { - basePropertyIndex = GetImplementation(base).GetBasePropertyIndex( index ); - } + // call base type recursively + basePropertyIndex = mBaseType->GetBasePropertyIndex( index ); } return basePropertyIndex; } -int TypeInfo::GetComponentIndex( Property::Index index ) const +int32_t TypeInfo::GetComponentIndex( Property::Index index ) const { int componentIndex = Property::INVALID_COMPONENT_INDEX; @@ -587,13 +687,10 @@ int TypeInfo::GetComponentIndex( Property::Index index ) const { componentIndex = iter->second.componentIndex; } - else + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) - { - componentIndex = GetImplementation(base).GetComponentIndex( index ); - } + // call base type recursively + componentIndex = mBaseType->GetComponentIndex( index ); } return componentIndex; @@ -611,13 +708,10 @@ Property::Index TypeInfo::GetChildPropertyIndex( const std::string& name ) const { index = iter->first; } - else + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) - { - index = GetImplementation(base).GetChildPropertyIndex( name ); - } + // call base type recursively + index = mBaseType->GetChildPropertyIndex( name ); } return index; @@ -633,16 +727,16 @@ const std::string& TypeInfo::GetChildPropertyName( Property::Index index ) const return iter->second.name; } - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - return GetImplementation(base).GetChildPropertyName( index ); + // call base type recursively + return mBaseType->GetChildPropertyName( index ); } - DALI_LOG_WARNING("Cannot find property index"); + DALI_LOG_ERROR( "Property index %d not found\n", index ); - static std::string emptyString; - return emptyString; + static std::string empty; + return empty; } Property::Type TypeInfo::GetChildPropertyType( Property::Index index ) const @@ -656,17 +750,14 @@ Property::Type TypeInfo::GetChildPropertyType( Property::Index index ) const { type = iter->second.type; } + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + type = mBaseType->GetChildPropertyType( index ); + } else { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) - { - type = GetImplementation(base).GetChildPropertyType( index ); - } - else - { - DALI_ASSERT_ALWAYS( ! "Cannot find property index" ); // use the same assert as Object - } + DALI_LOG_ERROR( "Property index %d not found\n", index ); } return type; @@ -674,67 +765,167 @@ Property::Type TypeInfo::GetChildPropertyType( Property::Index index ) const bool TypeInfo::IsPropertyWritable( Property::Index index ) const { - bool writable( false ); + bool writable = false; + bool found = false; - RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), - PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); + // default property? + if ( ( index < DEFAULT_PROPERTY_MAX_COUNT ) && mDefaultProperties ) + { + found = GetDefaultPropertyField( mDefaultProperties, mDefaultPropertyCount,index, &Dali::PropertyDetails::writable, writable ); + } + else if( ( index >= ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX ) && ( index <= ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX ) ) + { + writable = true; // animatable property is writable + found = true; + } + else + { + RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), + PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); + if ( iter != mRegisteredProperties.end() ) + { + writable = iter->second.setFunc ? true : false; + found = true; + } + } - if ( iter != mRegisteredProperties.end() ) + // if not found, continue to base + if( !found ) { - if( ( index >= ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX ) && ( index <= ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX ) ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - writable = true; // animatable property is writable + // call base type recursively + writable = mBaseType->IsPropertyWritable( index ); } else { - writable = iter->second.setFunc ? true : false; + DALI_LOG_ERROR( "Property index %d not found\n", index ); } } - else + + return writable; +} + +bool TypeInfo::IsPropertyAnimatable( Property::Index index ) const +{ + bool animatable = false; + bool found = false; + + // default property? + if ( ( index < DEFAULT_PROPERTY_MAX_COUNT ) && mDefaultProperties ) + { + found = GetDefaultPropertyField( mDefaultProperties, mDefaultPropertyCount,index, &Dali::PropertyDetails::animatable, animatable ); + } + else if ( ( index >= PROPERTY_REGISTRATION_START_INDEX ) && ( index <= PROPERTY_REGISTRATION_MAX_INDEX ) ) { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + // Type Registry event-thread only properties are not animatable. + animatable = false; + found = true; + } + else if( ( index >= ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX ) && ( index <= ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX ) ) + { + animatable = true; + found = true; + } + + // if not found, continue to base + if( !found ) + { + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - writable = GetImplementation(base).IsPropertyWritable( index ); + // call base type recursively + animatable = mBaseType->IsPropertyAnimatable( index ); } else { - DALI_ASSERT_ALWAYS( ! "Cannot find property index" ); // use the same assert as Object + DALI_LOG_ERROR( "Property index %d not found\n", index ); } } - return writable; + return animatable; } -Property::Type TypeInfo::GetPropertyType( Property::Index index ) const +bool TypeInfo::IsPropertyAConstraintInput( Property::Index index ) const { - Property::Type type( Property::NONE ); + bool constraintInput = false; + bool found = false; - RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), - PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); + // default property? + if ( ( index < DEFAULT_PROPERTY_MAX_COUNT ) && mDefaultProperties ) + { + found = GetDefaultPropertyField( mDefaultProperties, mDefaultPropertyCount,index, &Dali::PropertyDetails::constraintInput, constraintInput ); + } + else if ( ( index >= PROPERTY_REGISTRATION_START_INDEX ) && ( index <= PROPERTY_REGISTRATION_MAX_INDEX ) ) + { + // Type Registry event-thread only properties cannot be used as constraint input + constraintInput = false; + found = true; + } + else if( ( index >= ANIMATABLE_PROPERTY_REGISTRATION_START_INDEX ) && ( index <= ANIMATABLE_PROPERTY_REGISTRATION_MAX_INDEX ) ) + { + constraintInput = true; + found = true; + } - if ( iter != mRegisteredProperties.end() ) + // if not found, continue to base + if( !found ) { - if( iter->second.componentIndex == Property::INVALID_COMPONENT_INDEX ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - type = iter->second.type; + // call base type recursively + constraintInput = mBaseType->IsPropertyAConstraintInput( index ); } else { - // If component index is set, then we should return FLOAT - type = Property::FLOAT; + DALI_LOG_ERROR( "Property index %d not found\n", index ); } } + + return constraintInput; +} + + +Property::Type TypeInfo::GetPropertyType( Property::Index index ) const +{ + Property::Type type( Property::NONE ); + bool found = false; + + // default property? + if ( ( index < DEFAULT_PROPERTY_MAX_COUNT ) && mDefaultProperties ) + { + found = GetDefaultPropertyField( mDefaultProperties, mDefaultPropertyCount,index, &Dali::PropertyDetails::type, type ); + } else { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), + PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); + + if ( iter != mRegisteredProperties.end() ) { - type = GetImplementation(base).GetPropertyType( index ); + if( iter->second.componentIndex == Property::INVALID_COMPONENT_INDEX ) + { + type = iter->second.type; + found = true; + } + else + { + // If component index is set, then we should return FLOAT + type = Property::FLOAT; + found = true; + } + } + } + + if( !found ) + { + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + type = mBaseType->GetPropertyType( index ); } else { - DALI_ASSERT_ALWAYS( ! "Cannot find property index" ); // use the same assert as Object + DALI_LOG_ERROR( "Property index %d not found\n", index ); } } @@ -745,17 +936,20 @@ Property::Value TypeInfo::GetPropertyDefaultValue( Property::Index index ) const { PropertyDefaultValueContainer::const_iterator iter = find_if( mPropertyDefaultValues.begin(), mPropertyDefaultValues.end(), PairFinder< Property::Index, PropertyDefaultValuePair >( index ) ); - if( iter != mPropertyDefaultValues.end() ) + if( iter != mPropertyDefaultValues.end() ) { return iter->second; } - else + // we didn't have a value so ask base + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - return Property::Value( GetPropertyType( index ) ); + // call base type recursively + return mBaseType->GetPropertyDefaultValue( index ); } + return Property::Value(); // return none } -void TypeInfo::SetProperty( BaseObject *object, Property::Index index, const Property::Value& value ) const +void TypeInfo::SetProperty(BaseObject* object, Property::Index index, Property::Value value) const { RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), PairFinder< Property::Index, RegisteredPropertyPair >( index ) ); @@ -772,25 +966,22 @@ void TypeInfo::SetProperty( BaseObject *object, Property::Index index, const Pro } else { - iter->second.setFunc( object, index, value ); + iter->second.setFunc(object, index, std::move(value)); } } } + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + mBaseType->SetProperty(object, index, std::move(value)); + } else { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) - { - GetImplementation(base).SetProperty( object, index, value ); - } - else - { - DALI_ASSERT_ALWAYS( ! "Cannot find property index" ); // use the same assert as Object - } + DALI_LOG_ERROR( "Property index %d not found\n", index ); } } -void TypeInfo::SetProperty( BaseObject *object, const std::string& name, const Property::Value& value ) const +void TypeInfo::SetProperty(BaseObject* object, const std::string& name, Property::Value value) const { RegisteredPropertyContainer::const_iterator iter = find_if( mRegisteredProperties.begin(), mRegisteredProperties.end(), PropertyNameFinder< RegisteredPropertyPair >( name ) ); @@ -805,20 +996,17 @@ void TypeInfo::SetProperty( BaseObject *object, const std::string& name, const P } else { - iter->second.setFunc( object, iter->first, value ); + iter->second.setFunc(object, iter->first, std::move(value)); } } + else if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) + { + // call base type recursively + mBaseType->SetProperty(object, name, std::move(value)); + } else { - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) - { - GetImplementation(base).SetProperty( object, name, value ); - } - else - { - DALI_ASSERT_ALWAYS( ! "Cannot find property name" ); - } + DALI_LOG_ERROR( "Property %s not found", name.c_str() ); } } @@ -845,13 +1033,14 @@ Property::Value TypeInfo::GetProperty( const BaseObject *object, Property::Index } } - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - return GetImplementation( base ).GetProperty( object, index ); + // call base type recursively + return mBaseType->GetProperty( object, index ); } - DALI_ASSERT_ALWAYS( ! "Cannot find property index" ); // use the same assert as Object + DALI_LOG_ERROR( "Property index %d not found\n", index ); + return Property::Value(); } Property::Value TypeInfo::GetProperty( const BaseObject *object, const std::string& name ) const @@ -878,13 +1067,14 @@ Property::Value TypeInfo::GetProperty( const BaseObject *object, const std::stri } } - Dali::TypeInfo base = TypeRegistry::Get()->GetTypeInfo( mBaseTypeName ); - if ( base ) + if( GetBaseType( mBaseType, mTypeRegistry, mBaseTypeName ) ) { - return GetImplementation( base ).GetProperty( object, name ); + // call base type recursively + return mBaseType->GetProperty( object, name ); } - DALI_ASSERT_ALWAYS( ! "Cannot find property name" ); + DALI_LOG_ERROR( "Property %s not found", name.c_str() ); + return Property::Value(); } } // namespace Internal