template<typename TR, typename T1, typename T2>
class CEventHandler
{
public:
typedef TR return_type;
typedef T1 first_type;
typedef T2 second_type;
private:
class CFunctionBase
{
public:
virtual return_type Invoke(first_type p1, second_type p2) = 0;
virtual CFunctionBase* Clone() = 0;
virtual ~CFunctionBase() { }
};
template<typename TFunType>
class CFunction: public CFunctionBase
{
public:
CFunction(const TFunType& f): _f(f) { }
virtual return_type Invoke(first_type p1, second_type p2)
{
return _f(p1, p2);
}
virtual CFunctionBase* Clone()
{
return new CFunction(this->_f);
}
private:
TFunType _f;
};
template<typename TClassPtr, typename TMemFunType>
class CClassMemFun: public CFunctionBase
{
public:
CClassMemFun(TClassPtr pObj, const TMemFunType& f): _pObj(pObj), _pMemFun(f) { }
virtual return_type Invoke(first_type p1, second_type p2)
{
return ((*_pObj).*_pMemFun)(p1, p2);
}
virtual CFunctionBase* Clone()
{
return new CClassMemFun(this->_pObj, this->_pMemFun);
}
private:
TClassPtr _pObj;
TMemFunType _pMemFun;
};
public:
template<typename TFunType>
CEventHandler(const TFunType& f): _pFun(new CFunction<TFunType>(f)) { }
template<typename TClassPtr, typename TMemFunType>
CEventHandler(TClassPtr pObj, TMemFunType pFun): _pFun(new CClassMemFun<TClassPtr, TMemFunType>(pObj, pFun)) { }
CEventHandler(const CEventHandler& f)
{
_pFun = f._pFun->Clone();
}
~CEventHandler()
{
delete _pFun;
}
CEventHandler& operator = (const CEventHandler& f)
{
if(this != &f)
{
delete _pFun;
_pFun = f._pFun->Clone();
}
return *this;
}
return_type operator()(first_type p1, second_type p2)
{
return_type ret = return_type();
if(_pFun != nullptr)
{
_pFun->Invoke(p1, p2);
}
else
{
assert(false);
}
return ret;
}
private:
CFunctionBase* _pFun;