• We’re currently investigating an issue related to the forum theme and styling that is impacting page layout and visual formatting. The problem has been identified, and we are actively working on a resolution. There is no impact to user data or functionality, this is strictly a front-end display issue. We’ll post an update once the fix has been deployed. Thanks for your patience while we get this sorted.

Windows / C++ Question... (Callback Function)

Kntx

Platinum Member
I have this function pointer as a protected member of a class. Since the class in question is for a window, it needs to have a callback function. I'm sure we'd all love to have callback fuctions as methods... But it just doesn't work that way. So what I'm doing here is having a function pointer as a protected member variable so I can switch it up to point to a different function when I subclass the window.

How I originally declared the pointer was like this...

LRESULT (*_callPtr) (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);

which of course didn't work when i got around to assigning it because... the class member is a __cdecl and the global function is a __stdcall

so... i said... ok duh... I'll do this.

LRESULT (__stdcall *_callPtr) (HWND g_hWnd, UINT message, WPARAM wParam, LPARAM lParam);

Which of course works like a charm. But, I'm wondering wheather there is some hidden disadvantage to this I'm not seeing. Or if there is something horribly wrong which has gone right over my head.

Anything?

EDIT:::

To clarify... is there anything wrong with decalring it in the class as a __stdcall rather than a __cdecl
 
Originally posted by: singh
Only _static_ member functions can be declared as callback functions.

Yes, which leaves you in the same boat as having it as a global function.

What I'm talking about is a pointer to a global callback function.

 
I guess I don't understand what the problem is. Here's the way I would do it:

// typedef a pointer to a window proc
typedef LRESULT (CALLBACK* WindowProcPtr) (HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam);

// example usage
class Test
{
protected:
WindowProcPtr pWindowProc;

public:
Test()
{
pWindowProc = 0;
}

void setFunc(WindowProcPtr proc)
{
pWindowProc = proc;
}

void test()
{
(*pWindowProc)(0, WM_TIMER, 0, 0);
}
};


 
Originally posted by: singh
I guess I don't understand what the problem is. Here's the way I would do it:

//  typedef  a  pointer  to  a  window  proc
typedef  LRESULT  (CALLBACK*  WindowProcPtr)  (HWND  hwnd,  UINT  msg,  WPARAM  wparam,  LPARAM  lparam);

//  example  usage
class  Test
{
protected:
        WindowProcPtr  pWindowProc;

public:
        Test()
        {
                pWindowProc  =  0;
        }

        void  setFunc(WindowProcPtr  proc)
        {
                pWindowProc  =  proc;
        }

        void  test()
        {
                (*pWindowProc)(0,  WM_TIMER,  0,  0);
        }
};


yea... that wouldn't work because global funcs are __stdcall and a function pointer in a class would try and use a __cdecl.

What I was trying to say is... is there any problem with explicitly declaring a function pointer in a class to be a __stdcall ?
 
Originally posted by: Kntxyea... that wouldn't work because global funcs are __stdcall and a function pointer in a class would try and use a __cdecl.

What I was trying to say is... is there any problem with explicitly declaring a function pointer in a class to be a __stdcall ?

Yes, there is. The problem lies in the fact that a member functions are NOT normally __cdecl, they are __thiscall, which is a calling convention you can't do explicitly if you wanted to. The main difference is there is an extra implicit parameter in __thiscall functions which holds the address of the object instance so the member function knows where to find the rest of the interface and all the data elements. The reason this might be working with stdcall is this extra parameter ends up passed by register, and stdcall doesn't use any registers.
 
Back
Top