I have a message handling problem. (C++, win32)

Started by
3 comments, last by Wavarian 19 years, 4 months ago
You know, when you've got a WndProc, but its not global? You have to have a msg Router to pass the buck on to your own custom WndProc? Here's an example:

//Application message router.
//This message router just passes the buck over to WndProc.
LRESULT CALLBACK ApplicationGL::msgRouter(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
	ApplicationGL *app = 0;
	if(message == WM_NCCREATE)
	{
		// retrieve Window instance from window creation data and associate
		//it with our class
		app = (ApplicationGL *)((LPCREATESTRUCT)lParam)->lpCreateParams;
//		SetWindowLong(hwnd, GWL_USERDATA, reinterpret_cast<long>(app));
		SetWindowLong(hwnd, GWL_USERDATA, (long)(app));
	}
	else
	{
		// retrieve associated Window instance (its possible to have more than one window, even though this app only has one)
		app = reinterpret_cast<ApplicationGL *>(GetWindowLong(hwnd, GWL_USERDATA));
		//app = (ApplicationGL *)(GetWindowLong(hwnd, GWL_USERDATA));

	}
	return app->WndProc(hwnd, message, wParam, lParam); //call default message procedure
}

Without any code changes in this area, the code just stopped working. he "app" variable crashes the program because I'm trying to use a junk or NULL pointer. But... I've used this code a hundreds of times in the past, I don't know what's wrong now. I've noticed through debugging this one and another project where it doesn't crash that the first time msg router is called, the if statement always evaluates to false, and therefore this code is called: app = (ApplicationGL *)(GetWindowLong(hwnd, GWL_USERDATA)); And when looking at app's values (in debug), all of its member values evaluate to: ???, unknown, etc.. But that's the same here, and the same in the earlier project that works. Its like its always been using a junk pointer, but only just realised it now, and decides to crash. Like Wile E. Coyote falling off the cliff. the second time, it evaluates to true, calling this code: app = (ApplicationGL *)((LPCREATESTRUCT)lParam)->lpCreateParams; SetWindowLong(hwnd, GWL_USERDATA, (long)(app)); You're probably wondering: "Why don't you just go back to the previous project that works?" Well, the answer is: The other project is bloated with tons of stuff I don't need. It took me hours to get rid of it all, so that I could have a base to work with. This new, simpler project was working until it inexplicably stopped. By the way, how do I do that "textbox" thing again? so that the code is actually readable? [Edited by - EGD Eric on November 24, 2004 12:57:06 PM]
Advertisement
class Window{public:    Create()    {        m_hWnd = CreateWindow....... //         SetWindowLong( m_hWnd, GWL_USERDATA, reinterpret_cast<long>(this));    }    static LRESULT CALLBACK WndProc( HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam )    {        Window* pThis = reinterpret_cast<Window*>(GetWindowLong( hWnd, GWL_USERDATA ));        if( pThis )        {            ... // Handle messages here        }    }private:    HWND m_hWnd;};


Something like this should work.
Also, I remember seeing a tutorial about this kind of stuff here on gamedev some time ago.

Hope I helped
Indeed you did. Oluseyi wrote an excellent article on the subject of Creating a Win32 Window Wrapper Class. Might be worth a read.

EDIT: The codeboxes are done via [ source][ /source] tags (remove the spacing). Check the FAQ if you're unsure.
Yeah, that's what my Wrapper class was based on. That same article. I decided to read through it again, and early on I realised one difference between my project now, and the previous "working one". The WndProc is virtual. While re-doing my framework, I was looking at the OpenGL game programming book, thinking of improving it by using inheritance, but then changed my mind, leaving the virtual there. Does anyone have any idea why "virtual" would make it crash?

BTW: Thanks for the FAQ, I was looking for it, but couldn't find the link to it.
Your orginal code crashes because WM_NCCREATE isn't the only first possible message that gets sent to your window instance.

This topic is closed to new replies.

Advertisement