Sign in to follow this  
Verminox

OpenGL GLUT: Registering Class Members as Callback Handlers

Recommended Posts

I am using OpenGL with GLUT. When I use the event handling functions to register callbacks I can only see to be able to do this for global functions or static members of classes. If I have say a class CGame and want to register CGame::Render() as my display handler via glutDisplayFunc, I am not able to do this for an instance of CGame. My code looks somewhat like this:
Game = new CGame();
glutDisplayFunc(Game->Render);
Error: argument of type `void (CGame::)()' does not match `void (*)()' So i tried to pass it's address...
Game = new CGame();
glutDisplayFunc(&(Game->Render));
Error: ISO C++ forbids taking the address of a bound member function to form a pointer to member function. Say `&CGame::Render' The only way I was able to get it to work was, making a global function called DoRender() and pass that to GLUT, then inside DoRender() call Game->Render, but isn't there any other way?

Share this post


Link to post
Share on other sites
Unfortunately: no, there isn't another way. The problem lies with the predetermined callback signature used by GLUT, which you cannot chance. A C++ compiler can't cast between a function pointer and a pointer-to-member, because it needs more information to do so. Without going into much detail, they are (as far as the compiler is concerned) two different signatures, although their characteristics are roughly the same.

Two possible solutions are to use the singleton pattern or the monostate pattern (these are different patterns, although they yield equal results) for you CGame class, and access that instance in your global callback. For example:


class CMyClass
{
public:
// just a member
void DoSomething();

public:
// singleton access -- google it
static CMyClass &GetInstance();
// static callback "void ( void )" sig
static void MyCallback();
};

...

void CMyClass::MyCallback()
{
CMyClass.GetInstance().DoSomething();
}





You could also use boost::function or stl binders to achieve something similar, but you'd have to store their functors somewhere, which (I suppose) boils down to the same thing.

EDIT: also, GLUT is purely portable C, no? It has no notion of objects. Perhaps you could look for a GLUT C++ wrapper.

Share this post


Link to post
Share on other sites
I know what the singleton pattern is and I am not really a very big fan of it, but I was able to achieve the same effect by using global functions instead.

Well thanks for your help :)

Share this post


Link to post
Share on other sites
Guest Anonymous Poster
Honestly, drop your usage of GLUT. It's old and I don't think anyone is really maintaining it. OpenGL is NOT that difficult and learning to get a basic window up in Windows or Linux should take minutes. You'll be a better programmer for it too.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this