bool ComponentCollection::ValidateComponent( const ComponentPtr &component, std::string& error ) const { HELIUM_ASSERT( component->GetSlot() != NULL ); // Check for duplicates. if ( ContainsComponent( component->GetSlot() ) ) { std::string name; Helium::ConvertString( component->GetMetaClass()->m_Name, name ); error = std::string( TXT( "The component '" ) )+ name + TXT( "' is a duplicate (a component already occupies that slot in the collection)." ); return false; } // Check to make sure this type of collection accepts this type of component. if ( !ValidateCompatible( component, error ) ) { return false; } // Check to make sure that each component already within the collection is valid with the new one. M_Component::const_iterator itr = m_Components.begin(); M_Component::const_iterator end = m_Components.end(); for ( ; itr != end; ++itr ) { // Check both directions so that the validation rule only has to be implemented in one place. if ( !itr->second->ValidateSibling( component, error ) || !component->ValidateSibling( itr->second.Ptr(), error ) ) { return false; } } return true; }
bool ComponentCollection::ValidateCompatible( const ComponentPtr& component, std::string& error ) const { HELIUM_ASSERT( component->GetSlot() != NULL ); if ( component->GetComponentBehavior() == ComponentBehaviors::Exclusive ) { error = *component->GetMetaClass()->m_Name; error += TXT( " cannot be added to a(n) " ); error += *GetMetaClass()->m_Name; error += TXT( " because it is an exclusive component." ); return false; } return true; }
bool ComponentCollection::SetComponent(const ComponentPtr& component, bool validate, std::string* error ) { HELIUM_ASSERT( component->GetSlot() != NULL ); M_Component::const_iterator found = m_Components.find( component->GetSlot() ); if (found != m_Components.end() && found->second == component) { return true; // nothing to do, this is already in the collection } std::string errorMessage; if ( validate && !ValidateComponent( component, errorMessage ) ) { if ( error ) { std::string componentName; Helium::ConvertString( component->GetMetaClass()->m_Name, componentName ); std::string collectionName; Helium::ConvertString( GetMetaClass()->m_Name, collectionName ); *error = std::string( TXT( "Component '" ) ) + componentName + TXT( "' is not valid for collection '" ) + collectionName + TXT( "': " ) + errorMessage; } return false; } // Event args ComponentCollectionChanged args ( this, component ); // Set the component and connect the collection m_Components[ component->GetSlot() ] = component; component->SetCollection( this ); // Start caring about change to the component component->e_Changed.Add( ObjectChangeSignature::Delegate::Create<ComponentCollection, void (ComponentCollection::*)( const Reflect::ObjectChangeArgs& )> ( this, &ComponentCollection::ComponentChanged ) ); // Raise event m_Modified = true; m_ComponentAdded.Raise( args ); return true; }