Hello,
few days ago i start to try to implement/learn in general the mediator pattern. Now I am at a point where i need help!
The problem is my Compiler (G++) say i would use something that not in that form exist. But that's wrong. To be more specific:
I have 3 classes:
- Mediator ( as singleton implemented + templated )
- ColleagueEvent ( templated )
- ColleagueInterface ( Interface, obviously )
If i try now to create an instance of ColleagueEvent<TestColleague>. The compiler means then that Mediator<TestColleague> would be first incomplete and second used in nested name specifier. Okay, i thought include the specific header and the problem
should be resolved... pustekuchen
Suddenly the compiler means the class mediator would not has a static member >instance< and from here my problem starts. I cannot understand why the compiler don't see that >instance< is static. So that you can me follow a bit better here the code i use:
Perhaps i cannot see the wood for the trees but it would be nice if you suggest ideas why that so is or how could try to fix it.
The ColleagueEvent class:
#include "ColleagueInterface.h"
#include "Mediator.h"
namespace utilities
{
template<typename EventArgType>
class Mediator;
template<typename EventArgType>
class ColleagueEvent
{
protected:
typedef void (*ColleagueEventHandler)(interfaces::ColleagueInterface *source,EventArgType eventArg, interfaces::ColleagueInterface* context);
private:
interfaces::ColleagueInterface * eventContext; //Context colleague who fires the event
ColleagueEventHandler handlerProc; //Event handler function pointer
public:
/*
* Constructor receives the event source context and the EventHandler
* function pointer. Also register this object with the Mediator<> -
* to join the community.
*/
ColleagueEvent(interfaces::ColleagueInterface *source, ColleagueEventHandler eventProc) :
eventContext(source), handlerProc(eventProc)
{
//Register with mediator
Mediator<EventArgType>::GetInstance().RegisterColleague(this);
}
/*
* Destructor - unregister the object from community.
*/
virtual ~ColleagueEvent()
{
Mediator<EventArgType>::GetInstance().UnregisterColleague(this);
}
/*
* FireEvent - Inform the Mediator<> that the event object is triggered.
* The Mediator<> then will broadcast this to other ColleagueEvents -
* in this community.
*/
void FireEvent(EventArgType eventArg)
{
Mediator<EventArgType>::GetInstance().FireEvent(this, eventArg);
}
friend class Mediator<EventArgType> ;
};
}
The Mediator
namespace utilities
{
template<typename EventArgType>
class ColleagueEvent;
template<typename EventArgType>
class Mediator
{
typedef std::vector<ColleagueEvent<EventArgType>* > EventList;
private:
EventList m_colleagues;
static Mediator<EventArgType>* m_instance;
static Mediator<EventArgType>& GetInstance()
{
if(!m_instance)
{
m_instance = new Mediator();
}
return *m_instance;
}
void RegisterColleague(ColleagueEvent<EventArgType>* colEvent)
{
m_colleagues.push_back(colEvent);
}
void FireEvent(ColleagueEvent<EventArgType>* source, EventArgType eventArg)
{
for(unsigned i = 0; i < m_colleagues.size(); i++)
{
if(m_colleagues[i] != source)
{
m_colleagues[i]->handlerProc(source->eventContext,eventArg,m_colleagues[i]->eventContext);
}
}
}
void UnregisterColleague(ColleagueEvent<EventArgType>* colEvent)
{
typename EventList::iterator itr = std::find(m_colleagues.begin(),m_colleagues.end(), colEvent);
if (itr != m_colleagues.end())
{
m_colleagues.erase(itr);
}
}
friend class ColleagueEvent<EventArgType> ;
protected:
public:
};
//Define the static member of Mediator<> class
template<typename EventArgType>
Mediator<EventArgType>* Mediator<EventArgType>::instance = 0;
}