c++ - access pointer to call method (using callbacks etc) - c++

I am trying to figure out how to do this.
I have 2 classes -
class Caller(){
//constructs Callee
void onEventFired(){
//need to call a function on an obj
//which I dont have access to here
//objptr->funcA
}
};
class Callee(){
//it has access to an instance of caller object
private:
void setup(){
std::unique_ptr objptr = make_unique<SampleClass>....
//create unique ptr of obj
//can pass the objptr to Caller through a
//separate function but probably not clean ??
}
};
Chain of events -
Caller creates the callee instance during its own construction, – later, callee's setup function is called which creates SampleClass pointer. at some point later, the periodic event starts to fire up thats when I want call SampleClass's funcA from within Caller
One way is to pass the raw SampleClass pointer to the Caller class through a separate function but ideally I don't want the class Caller to have access to that.
Is there a way using some callbacks which I can do this cleanly.

Your question is a little weak in motivation, so let's beef it up just a tad.
Suppose that Caller accepts registrations for things that want to be called back whenever EVENT_FIRED happens. So, the system has something like this:
//... initialize all callees
//... wait for event
switch (event) {
//...
case EVENT_FIRED:
//...
//callback all interested callees
Caller::instance().onEventFired();
break;
//...
default:
//...
break;
};
Typically, you will want the callees to register themselves with the Caller instance, so that they get notification of the event via their registered callback.
In order to accept registrations, you would use some kind of container in the caller to track them.
class Caller {
public:
struct Callback {
virtual ~Callback () = default;
virtual void fire () = 0;
};
static Caller & instance () {
static Caller one;
return one;
}
template <typename CALLBACK, int EVENT>
void subscribe () {
std::unique_ptr<Callback> cb(std::make_unique<CALLBACK>());
callbacks_[EVENT].push_back(std::move(cb));
}
//...
void onEventFired () {
for (auto &cb : callbacks_[EVENT_FIRED]) cb->fire();
}
private:
typedef std::list<std::unique_ptr<Callback>> CallbackList;
std::unordered_map<int, CallbackList> callbacks_;
Caller () = default;
Caller (const Caller &) = delete;
Caller & operator = (Caller) = delete;
~Caller () = default;
};
The Caller now implements the Callback interface, and makes its registration during setup.
class Callee : public Caller::Callback {
public:
static void setup () {
Caller::instance().subscribe<Callee, EVENT_FIRED>();
}
void fire () { std::cout << "You're fired!\n"; }
};
Try it online!

Here are 2 references may be what you're looking for.
The Attorney-Client idiom, and pass-key pattern.
The Attorney-Client idiom is a method that add a proxy class.
The proxy class is a friend of the class which needs access.
[Callee] - [Proxy] - [Caller] relationship is built.
Pass-Key pattern is a relatively simple method to solve the problem.
The main idea is same that uses friend keyword.
However, it's using class template, rooted in template meta programming.
For more sophisticated usage, take a look at this version. (the last answer)

Related

Listener class inheritor - const or non-const reference to class listened to?

A very common pattern for a codebase is a Listener affair like this:
class Frobulator
{
public:
class Listener
{
private:
// only frobulators can frob
friend class Frobulator;
virtual void onFrobbed() = 0;
}
void maybeFrob()
{
// assume we always frob, but maybe we only do it sometimes
// and the caller won't know if a call will do it
for (auto& l: listeners)
{
l->onFrobbed();
}
}
void addListener(Listener* l)
{
listeners.push_back(l);
}
private:
std::vector<Listener*> listeners;
}
Then, a class inherits Listener and can register as a listener with the Frobulator. When the Frobulator frobs after a call by some caller (not necessarily the listener), the listeners will be told.
The real question I have then is, should the listener listen "internally", and therefore need a non-const reference to the Frobulator, but manage with a private Listener nature?
class FrobReactor: private Frobulator::Listener
{
public:
FrobReactor(Frobulator& frobulator_)
frobulator(frobulator)
{
frobulator.addListener(this);
}
private:
void onFrobbed() override
{
// react!
}
Frobulator& frobulator;
}
// and externally ...
Frobulator theFrobber;
FrobReactor reactor(theFrobber);
theFrobber.maybeFrob();
Or should the listener take a const-reference (or even no reference if you don't need it), acknowledging that the FrobReactor doesn't modify the Frobulator, but advertising that it is a Frobulator::Listener and expecting the client code to hook it up:
class FrobReactor: public Frobulator::Listener
{
public:
FrobReactor(const Frobulator& frobulator_):
frobulator(frobulator_)
{
}
private:
void onFrobbed() override
{
// react!
}
const Frobulator& frobulator;
}
// and externally
Frobulator theFrobber;
FrobReactor reactor(theFrobber);
theFrobber.addListener(&reactor);
theFrobber.maybeFrob();
Alternatively the addListener method could be made const and the listener list mutable and then the first method also works with a non-const reference, but this feels like a hack.
Is there a "right" way to do this?
I would not store a reference to the observed (or listened-to) Frobulator in the FrobReactor. Rather, I would pass a const reference to the Frobulator instance to the onFrobbed method.
class Listener
{
private:
// only frobulators can frob
friend class Frobulator;
virtual void onFrobbed(const Frobulator& frobulator) = 0;
}
and, adapting maybeFrob:
void maybeFrob()
{
// assume we always frob, but maybe we only do it sometimes
// and the caller won't know if a call will do it
for (auto& l: listeners)
{
l->onFrobbed(*this);
}
}
As for whether addListener should be const or not (and therefore, whether the vector of listeners should be mutable or not), it depends on what you are trying to achieve. I agree that it feels hacky, but on the other hand, if you want to ensure that clients of your API only deal with const Frobulators, then this is one way to do this. Another would be to have a method somewhere in your API that handles adding listeners to Frobulators like so:
void addListener(const Frobulator& frobulator, Frobulator::Listener& listener) {
Frobulator& nonConst = // obtain non-const reference to this frobulator
nonConst.addListener(listener);
}
It really depends on your design. Otherwise, if all you wish to do is protect listeners from modifying Frobulators, then passing a const reference to the 'onFrobbed method seems sufficient.
Finally, I would change addListener like so:
void addListener(Listener& listener)
{
listeners.push_back(&listener);
}
It's a small change, but I prefer only to pass a pointer when I am transferring ownership, unless there are other reasons to pass a pointer. Of course you have to make sure that your listener doesn't get deleted (by falling out of scope) in either case.

how to setup a proper callback to retrieve data

I have the following situation, I have two classes. I pass an instance of class 1 to an instance of class two through a callback function. Ultimately the goal is to connect to something (say sql server) and retrieve some datasets maybe every x number of minutes. How would I amend the below so that after passing an object of class 1 to the object of class 2, I can somehow get the object 1 to do all the work. Essentially I need the implementation of connecting to SQl and getting data to be in the work() function of class foo. and more importantly how do I relay the result set back to the user in main();
Does that make sense at all? Is the correct? The ultimate goal is to latch onto a sql server and grab a dataset every 5 minutes and generate some statistics to be returned to the user, should this be modified at all? Should the connection be handled by the foo class or the bar class
class foo{
public:
void work(int id, &result){}
};
class bar{
private:
foo* foo_
public:
void callback(foo* tempfoo){
foo_ = tempfoo;
}
void work();
};
int main(){
foo send;
bar receive;
receive.callback(&send);
//do a bunch of stuff with the receive object to get the result
bar.work(//some parameters that are needed to generate the result);
}
Thanks a lot guys.
The class that wants to call a callback should take a function pointer and then call that pointer when appropriate (when work is done).
There are a couple of options as to how exactly to pass a function pointer. You could use Lambda (as in the example code below), or you could use std::bind with a member function.
Example below:
class foo(){
public:
foo()
~foo()
work(int id, &result){
//do work
//call callback with some params
callback(PARAMS);
}
void setCallback(std::function<void(PARAMETERS)> cb){
callback = cb;
}
private:
std::function<void(PARAMETERS)> callback = nullptr;
}
class bar(){
private:
foo* foo_
public:
bar()
~bar()
work();
}
int main(){
foo send;
bar receive;
receive.setCallback([](PARAMETERS){
//your callback code in lambda
//send and receive are not captured here
//if you wish to capture send and receive
//you should somehow maintain their existence in memory
//until the callback is called, otherwise you'll get bad access error
//due to those guys already destroyed
//to capture send and receive you should put them into [] of lambda declaration.
//Append & if you want to capture by reference.
});
receive.work(//some parameters that are needed to generate the result);
}

How to pass a Function pointer without exposing class details

I'm creating a library that needs to allow the user to set a callback function.
The interface of this library is as below:
// Viewer Class Interface Exposed to user
/////////////////////////////
#include "dataType_1.h"
#include "dataType_2.h"
class Viewer
{
void SetCallbackFuntion( dataType_1* (Func) (dataType_2* ) );
private:
dataType_1* (*CallbackFunction) (dataType_2* );
}
In a typical usage, the user needs to access an object of dataType_3 within the callback.
However, this object is only known only to his program, like below.
// User usage
#include "Viewer.h"
#include "dataType_3.h"
// Global Declaration needed
dataType_3* objectDataType3;
dataType_1* aFunction( dataType_2* a)
{
// An operation on object of type dataType_3
objectDataType3->DoSomething();
}
main()
{
Viewer* myViewer;
myViewer->SetCallbackFunction( &aFunction );
}
My Question is as follows:
How do I avoid using an ugly global variable for objectDataType3 ?
(objectDataType3 is part of libraryFoo and all the other objects dataType_1, dataType_2 & Viewer are part of libraryFooBar) Hence I would like them to remain as separate as possible.
Don't use C in C++.
Use an interface to represent the fact you want a notification.
If you want objects of type dataType_3 to be notified of an event that happens in the viewer then just make this type implement the interface then you can register the object directly with the viewer for notification.
// The interface
// Very close to your function pointer definition.
class Listener
{
public: virtual dataType_1* notify(dataType_2* param) = 0;
};
// Updated viewer to use the interface defineition rather than a pointer.
// Note: In the old days of C when you registered a callback you normally
// also registered some data that was passed to the callback
// (see pthread_create for example)
class Viewer
{
// Set (or Add) a listener.
void SetNotifier(Listener* l) { listener = l; }
// Now you can just inform all objects that are listening
// directly via the interface. (remember to check for NULL listener)
void NotifyList(dataType_2* data) { if (listener) { listener->notify(data); }
private:
Listener* listener;
};
int main()
{
dataType_3 objectDataType3; // must implement the Listener interface
Viewer viewer;
viewer.SetNotifier(&objectDataType3);
}
Use Boost.Function:
class Viewer
{
void SetCallbackFuntion(boost::function<datatype_1* (dataType_2*)> func);
private:
boost::function<datatype_1* (dataType_2*)> CallbackFunction;
}
Then use Boost.Bind to pass the member function pointer together with your object as the function.
If you don't want or can't use boost, the typical pattern around callback functions like this is that you can pass a "user data" value (mostly declared as void*) when registering the callback. This value is then passed to the callback function.
The usage then looks like this:
dataType_1* aFunction( dataType_2* a, void* user_ptr )
{
// Cast user_ptr to datatype_3
// We know it works because we passed it during set callback
datatype_3* objectDataType3 = reinterpret_cast<datatype_3*>(user_ptr);
// An operation on object of type dataType_3
objectDataType3->DoSomething();
}
main()
{
Viewer* myViewer;
dataType_3 objectDataType3; // No longer needs to be global
myViewer->SetCallbackFunction( &aFunction, &objectDataType3 );
}
The implementation on the other side only requires to save the void* along with the function pointer:
class Viewer
{
void SetCallbackFuntion( dataType_1* (Func) (dataType_2*, void*), void* user_ptr );
private:
dataType_1* (*CallbackFunction) (dataType_2*, void*);
void* user_ptr;
}
boost::/std:: function is the solution here. You can bind member functions to them, and in addition functors and lambdas, if you have a lambda compiler.
struct local {
datatype3* object;
local(datatype3* ptr)
: object(ptr) {}
void operator()() {
object->func();
}
};
boost::function<void()> func;
func = local(object);
func(); // calls object->func() by magic.
Something like this is simple to do:
class Callback
{
public:
virtual operator()()=0;
};
template<class T>
class ClassCallback
{
T* _classPtr;
typedef void(T::*fncb)();
fncb _cbProc;
public:
ClassCallback(T* classPtr,fncb cbProc):_classPtr(classPtr),_cbProc(cbProc){}
virtual operator()(){
_classPtr->*_cbProc();
}
};
Your Viewer class would take a callback, and call it using the easy syntax:
class Viewer
{
void SetCallbackFuntion( Callback* );
void OnCallCallback(){
m_cb->operator()();
}
}
Some other class would register the callback with the viewer by using the ClassCallback template specialization:
// User usage
#include "Viewer.h"
#include "dataType_3.h"
main()
{
Viewer* myViewer;
dataType_3 objectDataType3;
myViewer->SetCallbackFunction( new ClassCallback<dataType_3>(&objectDataType3,&dataType_3::DoSomething));
}
You're asking several questions mixed up in here and this is going to cause you lots of confusion in your answers.
I'm going to focus on your issue with dataType_3.
You state:
I would like to avoid declaring or
including dataType_3 in my library as
it has huge dependencies.
What you need to do is make an interface class for dataType_3 that gives the operations -- the footprint -- of dataType_3 without defining everything in it. You'll find tips on how to do that in this article (among other places). This will allow you to comfortably include a header that gives the footprint for dataType_3 without bringing in all of its dependencies. (If you've got dependencies in the public API you may have to reuse that trick for all of those as well. This can get tedious, but this is the price of having a poorly-designed API.)
Once you've got that, instead of passing in a function for callback consider having your "callback" instead be a class implementing a known interface. There are several advantages to doing this which you can find in the literature, but for your specific example there's a further advantage. You can inherit that interface complete with an instantiated dataType_3 object in the base class. This means that you only have to #include the dataType_3 interface specification and then use the dataType_3 instance provided for you by the "callback" framework.
If you have the option of forcing some form of constraints on Viewer, I would simply template that, i.e.
template <typename CallBackType>
class Viewer
{
public:
void SetCallbackFunctor(CallBackType& callback) { _callee = callback; }
void OnCallback()
{
if (_callee) (*_callee)(...);
}
private:
// I like references, but you can use pointers
boost::optional<CallBackType&> _callee;
};
Then in your dataType_3 implement the operator() to do as needed, to use.
int main(void)
{
dataType_3 objectDataType3;
// IMHO, I would construct with the objectDataType3, rather than separate method
// if you did that, you can hold a direct reference rather than pointer or boost::optional!
Viewer<dataType_3> viewer;
viewer.SetCallbackFunctor(objectDataType3);
}
No need for other interfaces, void* etc.

What's a good safe way to initialise memory for types I don't yet know about?

I started thinking about this after receiving an answer for this question. This is a bit tricky to explain, but I'll do my best.
I'm building a small(ish) 2D game engine. There are certain requirements that I need to satisfy, since this engine has to "work" with existing code that others have written for a different engine. Some change to existing code is inevitable, but I want to minimise it.
Users of my engine need to define entities called "gadgets". These are basically structs containing shapes and other state variables. These "gadgets" fall into classes, e.g. they may decide to define an icon gadget or a button gadget - or whatever.
They will also define a message handler for that class of gadgets.
E.g.
typedef struct
{
shape shapelist[5];
int num_options;
}interface;
static void interface_message_handler( interface * myself, message * msg )
{
switch( msg->type )
{
case NEW_MSG:
{
interface_descriptor * desc = msg->desc;
// initialize myself with contents of this message.
...
}
break;
....
}
}
Users have already given me the corresponding message handler function and also the number of bytes in a interface object. And they can then ask the engine to create new instances of their gadgets via IDs e.g:
engine->CreateNewGadget( interface_gadget_class_ID, welcome_interface_ID );
where interface_gadget_class_ID is the ID for that class of gadgets and welcome_interface_ID is the instance ID. At some point during CreateNewGadget I need to a) allocate memory to hold a new gadget and then call the gadget class's message handler on it, with a NEW_MSG so that it can initialize itself.
The problem is, if all I'm doing is allocating memory - that memory is uninitialized (and that means all the struct members are uninitialized - so if interface contains a vector, for example, then I'm going to get some wierd results if the message handler does anything with it ).
To avoid wierd results caused by doing stuff to unintialized memory, I really need to call a constructor for that memory as well before passing it to the gadget's message handler function.
e.g in the case of interface:
pfunc(new (memory) interface);
But my question is, if I have no knowledge of the types that users are creating, how can I do that?
// We create a typedef that refers to a function pointer
// which is a function that returns an interface pointer
typedef interface * (*GadgetFactory)(void);
// we'll actually create these functions by using this template function
// Different version of this function will produce different classes.
template<typename T>
interface * create_object()
{
return new T;
}
// This function takes care of setting everything up.
template<typename T>
void RegisterGadgetType(int gadget_type_id)
{
// Get outselves a copy of a pointer to the function that will make the object
GadgetFactory factory = create_object<T>;
// store factory somewhere
}
interface * CreateGadget(int gadget_type_id)
{
// get factory
GadgetFactory factory;
// factory will give me the actual object type I need.
return (*factory)();
}
RegisterGadgetType<S>(2);
CreateGadget(2);
as i see it, you always know because interface_gadget_class_ID defines the type to create.
you create a base c++ class: (corresponds to class interface in your example). this base class contains all of data members which are used by every interface subclass (that is, every gadget).
the base class also declares all methods common to every gadget. example: each gadget is able to receive a call handleMessage. handleMessage is pure virtual, because this method is the subclasses' role to fulfill.
then you extend/subclass to support the stuff you have to do with each gadget's specialization. at this point, you add the members and methods specific to each gadget subclass.
CreateNewGadget serves as a factory for all your subclasses, where the arguments determine which class you will create.
from there, c++ will handle construction/destruction, allocation sizes, etc..
if you're allowing plugins with their own factories in your engine, then you'll need another level, where third parties register their custom types and inherit from your base(s).
here's a simple layout of the interfaces (in non-compiled pseudo code):
namespace MONGadgets {
class t_interface {
protected:
t_interface(/* ... */);
public:
virtual ~t_interface();
/* each subclass must override handleMessage */
virtual t_result handleMessage(const t_message& message) = 0;
};
namespace InterfaceSubclasses {
class t_gadget1 : public t_interface {
public:
t_gadget1(const welcome_interface_ID& welcome);
virtual ~t_gadget1();
virtual t_result handleMessage(const t_message& message) {
std::cout << "t_gadget1\n";
}
/* gadget1 has no specific instance variables or methods to declare */
};
class t_gadget2 : public t_interface {
public:
t_gadget2(const welcome_interface_ID& welcome);
virtual ~t_gadget2();
virtual t_result handleMessage(const t_message& message) {
std::cout << "t_gadget2\n";
}
private:
/* here is an example of a method specific to gadget2: */
void drawShape(const unsigned& idx);
private:
/* here is gadget2's unique data: */
shape shapelist[5];
int num_options;
};
namespace ClassID {
enum { Gadget1 = 1, Gadget2 = 2 };
}
}
/* replaced by virtual t_result t_interface::handleMessage(const t_message&)
- static void interface_message_handler( interface * myself, message * msg );
*/
class t_gadget_factory {
public:
t_interface* CreateNewGadget(const interface_gadget_class_ID& classID, const welcome_interface_ID& welcome) {
switch (classID) {
case InterfaceSubclasses::ClassID::Gadget1 :
return new InterfaceSubclasses::gadget1(welcome);
case InterfaceSubclasses::ClassID::Gadget2 :
return new InterfaceSubclasses::gadget2(welcome);
/* ... */
}
}
};
}
Example code (ignoring my other suggestion, about factories and virtual functions):
typedef struct
{
shape shapelist[5];
int num_options;
} interface;
static void interface_message_handler( void * myself, message * msg )
{
switch( msg->type )
{
case NEW_MSG:
{
interface *self = new (myself) interface;
interface_descriptor * desc = msg->desc;
// initialize myself with contents of this message.
...
}
break;
case OTHER_MSG:
{
interface *self = static_cast<interface*>(myself);
...
}
break;
....
}
}
Then your CreateNewGadget code does:
void *ptr = malloc(some_amount);
msg newmsg;
newmsg.type = NEW_MSG;
// other fields
some_message_handler(ptr, &msg);
// now we have an initialized object, that we can add to our tree or whatever.
The less horrible version is more like this:
struct gadgetinterface {
virtual ~gadgetinterface() {}
virtual void handle_message(msg *) = 0;
};
struct mygadget : gadgetinterface {
void handle_message(msg *m) {
// no need for NEW_MSG, just do other messages
}
};
gadgetinterface *mygadget_factory(some parameters) {
// use some parameters, either passed to constructor or afterwards
return new mygadget();
}
Then we register a pointer to mygadget_factory with the gadget manager, and CreateNewGadget does this:
gadgetinterface *some_factory(some parameters); // that's it!
Where some_factory is the function pointer that was registered, so in the case of this gadget type, it points to mygadget_factory.

handling pointer to member functions within hierachy in C++

I'm trying to code the following situation:
I have a base class providing a framework for handling events. I'm trying to use an array of pointer-to-member-functions for that. It goes as following:
class EH { // EventHandler
virtual void something(); // just to make sure we get RTTI
public:
typedef void (EH::*func_t)();
protected:
func_t funcs_d[10];
protected:
void register_handler(int event_num, func_t f) {
funcs_d[event_num] = f;
}
public:
void handle_event(int event_num) {
(this->*(funcs_d[event_num]))();
}
};
Then the users are supposed to derive other classes from this one and provide handlers:
class DEH : public EH {
public:
typedef void (DEH::*func_t)();
void handle_event_5();
DEH() {
func_t f5 = &DEH::handle_event_5;
register_handler(5, f5); // doesn't compile
........
}
};
This code wouldn't compile, since DEH::func_t cannot be converted to EH::func_t. It makes perfect sense to me. In my case the conversion is safe since the object under this is really DEH. So I'd like to have something like that:
void EH::DEH_handle_event_5_wrapper() {
DEH *p = dynamic_cast<DEH *>(this);
assert(p != NULL);
p->handle_event_5();
}
and then instead of
func_t f5 = &DEH::handle_event_5;
register_handler(5, f5); // doesn't compile
in DEH::DEH()
put
register_handler(5, &EH::DEH_handle_event_5_wrapper);
So, finally the question (took me long enough...):
Is there a way to create those wrappers (like EH::DEH_handle_event_5_wrapper) automatically?
Or to do something similar?
What other solutions to this situation are out there?
Thanks.
Instead of creating a wrapper for each handler in all derived classes (not even remotely a viable approach, of course), you can simply use static_cast to convert DEH::func_t to EH::func_t. Member pointers are contravariant: they convert naturally down the hierarchy and they can be manually converted up the hierarchy using static_cast (opposite of ordinary object pointers, which are covariant).
The situation you are dealing with is exactly the reason the static_cast functionality was extended to allow member pointer upcasts. Moreover, the non-trivial internal structure of a member function pointer is also implemented that way specifically to handle such situations properly.
So, you can simply do
DEH() {
func_t f5 = &DEH::handle_event_5;
register_handler(5, static_cast<EH::func_t>(f5));
........
}
I would say that in this case there's no point in defining a typedef name DEH::func_t - it is pretty useless. If you remove the definition of DEH::func_t the typical registration code will look as follows
DEH() {
func_t f5 = static_cast<func_t>(&DEH::handle_event_5);
// ... where `func_t` is the inherited `EH::func_t`
register_handler(5, f5);
........
}
To make it look more elegant you can provide a wrapper for register_handler in DEH or use some other means (a macro? a template?) to hide the cast.
This method does not provide you with any means to verify the validity of the handler pointer at the moment of the call (as you could do with dynamic_cast in the wrapper-based version). I don't know though how much you care to have this check in place. I would say that in this context it is actually unnecessary and excessive.
Why not just use virtual functions? Something like
class EH {
public:
void handle_event(int event_num) {
// Do any pre-processing...
// Invoke subclass hook
subclass_handle_event( event_num );
// Do any post-processing...
}
private:
virtual void subclass_handle_event( int event_num ) {}
};
class DEH : public EH {
public:
DEH() { }
private:
virtual void subclass_handle_event( int event_num ) {
if ( event_num == 5 ) {
// ...
}
}
};
You really shouldn't be doing it this way. Check out boost::bind
http://www.boost.org/doc/libs/1_43_0/libs/bind/bind.html
Elaboration:
First, I urge you to reconsider your design. Most event handler systems I've seen involve an external registrar object that maintains mappings of events to handler objects. You have the registration embedded in the EventHandler class and are doing the mapping based on function pointers, which is much less desirable. You're running into problems because you're making an end run around the built-in virtual function behavior.
The point of boost::bindand the like is to create objects out of function pointers, allowing you to leverage object oriented language features. So an implementation based on boost::bind with your design as a starting point would look something like this:
struct EventCallback
{
virtual ~EventCallback() { }
virtual void handleEvent() = 0;
};
template <class FuncObj>
struct EventCallbackFuncObj : public IEventCallback
{
EventCallbackT(FuncObj funcObj) :
m_funcObj(funcObj) { }
virtual ~EventCallbackT() { }
virtual void handleEvent()
{
m_funcObj();
}
private:
FuncObj m_funcObj;
};
Then your register_handler function looks something like this:
void register_handler(int event_num, EventCallback* pCallback)
{
m_callbacks[event_num] = pCallback;
}
And your register call would like like:
register_handler(event,
new EventCallbackFuncObj(boost::bind(&DEH::DEH_handle_event_5_wrapper, this)));
Now you can create a callback object from an (object, member function) of any type and save that as the event handler for a given event without writing customized function wrapper objects.