# HG changeset patch # User mvbarracuda@33b003aa-7bff-0310-803a-e67f0ece8222 # Date 1237155620 0 # Node ID 044d1fead5d2cc9cbaea7781e9fb754a6789de94 # Parent e281223a03a66b0880d48a8908bca50909f11119 * Applying icelus' "leader is not around anymore" patch from #350 * Close #350 diff -r e281223a03a6 -r 044d1fead5d2 engine/core/model/structures/instance.cpp --- a/engine/core/model/structures/instance.cpp Sun Mar 15 18:59:49 2009 +0000 +++ b/engine/core/model/structures/instance.cpp Sun Mar 15 22:20:20 2009 +0000 @@ -170,6 +170,17 @@ } Instance::~Instance() { + std::vector::iterator itor; + for(itor = m_deletelisteners.begin(); + itor != m_deletelisteners.end(); + ++itor) { + (*itor)->onInstanceDeleted(this); + } + if(m_activity && + m_activity->m_actioninfo && + m_activity->m_actioninfo->m_leader) { + m_activity->m_actioninfo->m_leader->removeDeleteListener(this); + } delete m_activity; delete m_facinglocation; delete m_visual; @@ -271,6 +282,7 @@ m_activity->m_actioninfo->m_target = new Location(leader->getLocationRef()); m_activity->m_actioninfo->m_speed = speed; m_activity->m_actioninfo->m_leader = leader; + leader->addDeleteListener(this); setFacingLocation(*m_activity->m_actioninfo->m_target); FL_DBG(_log, LMsg("starting action ") << action_name << " from" << m_location << " to " << *m_activity->m_actioninfo->m_target << " with speed " << speed); } @@ -510,4 +522,25 @@ } return TimeManager::instance()->getTime(); } + void Instance::addDeleteListener(InstanceDeleteListener *listener) const { + m_deletelisteners.push_back(listener); + } + void Instance::removeDeleteListener(InstanceDeleteListener *listener) const { + std::vector::iterator itor; + itor = std::find(m_deletelisteners.begin(), + m_deletelisteners.end(), + listener); + if(itor != m_deletelisteners.end()) { + m_deletelisteners.erase(itor); + } else { + FL_WARN(_log, "Cannot remove unknown listener"); + } + } + void Instance::onInstanceDeleted(Instance* instance) { + if(m_activity && + m_activity->m_actioninfo && + m_activity->m_actioninfo->m_leader == instance) { + m_activity->m_actioninfo->m_leader = NULL; + } + } } diff -r e281223a03a6 -r 044d1fead5d2 engine/core/model/structures/instance.h --- a/engine/core/model/structures/instance.h Sun Mar 15 18:59:49 2009 +0000 +++ b/engine/core/model/structures/instance.h Sun Mar 15 22:20:20 2009 +0000 @@ -70,10 +70,17 @@ virtual void onInstanceChanged(Instance* instance, InstanceChangeInfo info) = 0; }; + + class InstanceDeleteListener { + public: + virtual ~InstanceDeleteListener() {}; + virtual void onInstanceDeleted(Instance* instance) =0; + }; + /** * An Instance is an "instantiation" of an Object at a Location. */ - class Instance : public ResourceClass { + class Instance : public ResourceClass, public InstanceDeleteListener { public: /** Constructor @@ -169,6 +176,16 @@ */ void removeChangeListener(InstanceChangeListener* listener); + /** Adds new instance delete listener + * @param listener to add + */ + void addDeleteListener(InstanceDeleteListener* listener) const; + + /** Removes associated instance delete listener + * @param listener to remove + */ + void removeDeleteListener(InstanceDeleteListener* listener) const; + /** Gets the currently active action. This is owned by * the instance's object, so don't delete it! * @return current action, NULL in case there is none @@ -261,6 +278,10 @@ */ inline InstanceChangeInfo getChangeInfo(); + /** callback so other instances we depend on can notify us if they go away + */ + void onInstanceDeleted(Instance* instance); + private: std::string m_id; @@ -312,6 +333,8 @@ InstanceActivity* m_activity; // bitmask stating current changes InstanceChangeInfo m_changeinfo; + // listeners for deletion of the instance + mutable std::vector m_deletelisteners; // object where instantiated from Object* m_object;