3
\$\begingroup\$

I've been trying to learn some Windows programming using the Win32 API. Now, i'm used to working with the OS layer being abstracted away, mostly thanks to libraries like SFML or Allegro. Could you guys help me out and tell me if i'm thinking right here.

The place for my gameloop is where i'm reading the messages?

while (TRUE)
{
     if (PeekMessage (&msg, NULL, 0, 0, PM_REMOVE))
     {
          if (msg.message == WM_QUIT)
               break ;

          TranslateMessage (&msg) ;
          DispatchMessage (&msg) ;
     }
     else
     {
          //my game loop goes here
     }
}

Now the slightly bigger issue, that is, drawing. Do i run my drawing where i normaly do it, inside the game loop after the game logic? Or do i do it when WM_PAIN is being called and just call InvalidateRect (hwnd, NULL, TRUE); when i want to draw? This does feel weird, the WM_PAINT is a queued message, so i don't know for sure when it'll be called. So if i wanted to avoid this, do i just get the device handle inside the game loop and only ValidateRect (hwnd, NULL); in the WM_PAINT case (beside the ValidateRect (hwnd, NULL); called after drawing in the game loop)? Actually, now that i think about it, do i even need WM_PAINT in this situation or can i skip it and let DefWindowProc handle it (does it validate the screen if WM_PAINT isn't processed)?

If this is any important, i'm setting up my code for OpenGL.

\$\endgroup\$

1 Answer 1

3
\$\begingroup\$

You need to while that PeekMessage, and then loop. Something like

bool DoMessages() {
    while(PeekMessage (&msg, NULL, 0, 0, PM_REMOVE)) {
        if (msg.message == WM_QUIT)
            return false;

        TranslateMessage(&msg);
        DispatchMessage(&msg);
    }
    return true;
}

while(DoMessages()) {
    Draw();
}

It's not common for game architectures to draw in response to WM_PAINT- that's mostly for GDI rendering for applications whose states do not change without user interaction, as far as I'm aware. You can basically just ignore it.

Also, if you want to render to a window (how else would you render..?) then you need to pass the HWND in to PeekMessage.

\$\endgroup\$
4
  • \$\begingroup\$ Process all the windows messages before handling the game loop, was silly of me not to figure that one out, thanks. And you only send HWND to PeekMessage if you want the recieve messages for a specific window, i leave it as NULL because i want messages from all windows to be processed. It has nothing to do with rendering. \$\endgroup\$ Commented Apr 10, 2012 at 22:49
  • \$\begingroup\$ @dreta: Ah, cool. In that case, I think that this simple loop should work fine. \$\endgroup\$ Commented Apr 10, 2012 at 23:35
  • \$\begingroup\$ If you're ignoring WM_PAINT, you have to explicitly ignore it somehow, or else PeekMessage will just return WM_PAINT messages forever, and DoMessages will never return. So you'll either need a WM_PAINT handler in your window proc that does no drawing and just calls ValidateRect, or you'll need to specify in your call to PeekMessage that you want every kind of message except paint messages. \$\endgroup\$ Commented Apr 13, 2012 at 0:36
  • 1
    \$\begingroup\$ @Vincent Povirk the DefWindowProc will deal with the WM_PAINT message, you don't have to do anything. \$\endgroup\$ Commented Apr 29, 2012 at 9:40

You must log in to answer this question.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.