I often create little projects, and I at the moment I have a basic window creation & message loop (handling) set up. But often, my message loops result in the "infinite window" bug when moving the window. This is just minor of course, but this always bugs me out.

Does anybody know what actually causes this? Is it because I'm not double buffering yet?

Here's a link to a screenshot if you don't know what I mean with the "Infinite Window" bug.

Well, there's your problem! PeekMessage doesn't wait if there's no message available, so your app just sits in that tight loop taking up 100% CPU and not giving the other apps much chance to run.

It doesn't look like you're doing any rendering yet. Once you do, you'll presumably be waiting on vsync at the end of rendering, so this problem will go away. You could also put a Sleep(0) call in the loop, although it's probably not good to have that in there long-term.

NOISEcore
—
2011-09-28T01:06:35Z —
#6

Yeah, basically how I usually do it, I set an if else loop, where in the if it checks for a message, if none is found, it checks if the minimum time for a frame (max frame cap) has elapsed yet and renders/thinks if so.

Will this make the "infinite window" go away? Because usually when I get to that point in programming, I already use a fullscreen (which I won't in this program)

Reedbeta
—
2011-09-28T01:53:26Z —
#7

Well, what does it do if the minimum time for a frame *hasn't* elapsed yet? If you do a Sleep(0) or something in that case, you should be fine, as you'll yield the rest of your time-slice back to the OS. But if you just sit in a loop and don't do anything that suspends the thread, you'll keep taking up 100% CPU and making it hard for anything else to run.

IMO, the right way to do this is to configure your rendering API to wait for vsync, and if the API is built properly this should suspend the thread until the vsync clears, which will have the side effect of reducing the CPU utilization to a more reasonable level.

The g_fRendering flag gets set to false when you minimize the app, or when it starts shutting down; in that case I use GetMessage, which waits for a message, rather than PeekMessage. Down inside the Render() call I'm eventually calling Present() (since I'm using D3D) and telling it to wait for vsync, which both prevents tearing (usually...) and suspends the thread so that other apps can run.

It's also important to handle *all* available messages after each rendered frame, not just one, hence the PeekMessage in the inner while loop. Otherwise messages can back up and overflow the queue because you don't process them fast enough. Mouse moves especially can generate several messages per frame.

oisyn
—
2011-09-28T10:58:42Z —
#8

What I usually do is using SetTimer() to let Windows post a WM_TIMER to my message queue every x milliseconds (the minimum is 10, which gives you 100 messages per second), and then do my rendering in response to a WM_TIMER. Automatic frame limiter

The g_fRendering flag gets set to false when you minimize the app, or when it starts shutting down; in that case I use GetMessage, which waits for a message, rather than PeekMessage. Down inside the Render() call I'm eventually calling Present() (since I'm using D3D) and telling it to wait for vsync, which both prevents tearing (usually...) and suspends the thread so that other apps can run. It's also important to handle *all* available messages after each rendered frame, not just one, hence the PeekMessage in the inner while loop. Otherwise messages can back up and overflow the queue because you don't process them fast enough. Mouse moves especially can generate several messages per frame.

If you do this, how would you then set in a frame limiter? Would you do that inside the scope where Update & Render get called?

oisyn
—
2011-09-28T14:49:59Z —
#10

No, I would do that in the message loop itself. Calculate how much time there's left before you want to do another frame, and use MsgWaitForMultipleObjects() to wait for a message with a timeout, and use as the timeout the time until the next frame you just calculated.

But as said, I would just stick to SetTimer(), it makes your code clean and simple.

Reedbeta
—
2011-09-28T16:59:00Z —
#11

@_NOISEcore

If you do this, how would you then set in a frame limiter? Would you do that inside the scope where Update & Render get called?

Frame limiting is taken care of by the vsync. I don't have a need to limit to some arbitrary rate like 100 fps; I only ever want to run at the refresh rate (or divisors thereof).

oisyn
—
2011-09-28T17:09:03Z —
#12

Some people turn off vsync. You'd better still have some other means to limit the framerate available as well. Besides, there is no vsync in windowed mode.

Reedbeta
—
2011-09-28T18:10:51Z —
#13

@.oisyn

Besides, there is no vsync in windowed mode.

Uhm...what? I'm using vsync just fine in windowed mode in my own Direct3D app...

NOISEcore
—
2011-09-28T18:36:41Z —
#14

Well, the problem is that I'm currently working on a little project for school (sort of) that tries to make as much use of GDI as possible.

So I don't really have access to VSYNC (I think), in which I just switch to limiting the framerate to the refresh rate of the screen (or more if desired)

That's why I need to implement the timer

Smile_
—
2011-09-28T19:36:00Z —
#15

For simple game you don't need to redraw every frame (for tetris you must redraw on button press & timer tick only). Put you drawing code in WM_PAINT handler (together with ValidateRect if needed) and call InvalidateRect when you need to update window contents.

Uhm...what? :huh: I'm using vsync just fine in windowed mode in my own Direct3D app...

It appears that you are right. I don't know where I got this from

NOISEcore
—
2011-09-29T09:50:26Z —
#17

@'

']For simple game you don't need to redraw every frame (for tetris you must redraw on button press & timer tick only). Put you drawing code in WM_PAINT handler (together with ValidateRect if needed) and call InvalidateRect when you need to update window contents.

I actually haven't thought of that. I still need alot of "lessons" on effeciency Thank you !

EDIT: I do have an additional problem atm. Well 2, concerning the same things. First of all, my message loop looks like this:

The problem is, m_bActive gets set to false when WM_ACTIVATE with wParam being WA_INACTIVE, and else it gets set back to true. When I click away, this works, but when I just minimize it keeps using thesame CPU amount as when activated.

This comes to my second problem, at the moment my program doesn't do that much, but yet it uses 25% of my CPU (dual core so..) This is probably because of me not returning the remainder of my time slice, but I don't know how to do this. They say with Sleep(0) but this doesn't seem to do anything.

oisyn
—
2011-09-29T11:01:29Z —
#18

Please, don't resort to Sleep(0), it's bad practice for the purpose you're using it for.

hey say with Sleep(0) but this doesn't seem to do anything.

It does, but if there's no other process who wants CPU time it still goes to your app.

NOISEcore
—
2011-09-29T14:32:33Z —
#19

If sleep is a bad practice, what should I use then? MsgWaitForMultipleObjects ?

oisyn
—
2011-09-29T14:47:27Z —
#20

I'm not saying Sleep is bad practice, I was talking about Sleep(0). You don't want to just give up the remainded of the time slice, you want to wait until it's time for the next frame. So you should calculate how long you'd like to wait.

And you can implement the wait with Sleep(), but the downside is that you're unable to process messages when you're sleeping. So MsgWaitForMultipleObjects() is, in my opinion, the better choice.