MFC allows you to override CWinApp::OnIdle
function to perform idle-time processing.
This function is called whenever there're no messages waiting for processing in the message queue.
In this function, you can perform some secondary processing like updating the status bar, toolbar, etc.
The definition of this function is as follows:
virtual BOOL OnIdle(LONG lCount);
If you are interested, you can override this function and do some processing. The following example paints a random rectangle while the application is idle (that is no processing is carried on). Thus, this code doesn't make the application irresponsive.
BOOL OnIdle(LONG lCount)
{
CWinApp::OnIdle(lCount);
CClientDC dc(m_pMainWnd);
RECT rct;
m_pMainWnd->GetClientRect(&rct);
SetRect(&rct,
rand() % rct.right,
rand() % rct.bottom,
rand() % rct.right,
rand() % rct.bottom);
dc.Rectangle(&rct);
return TRUE;
}
This function receives only a single argument, lCount
; it contains a value incremented each time OnIdle
is called, and it is reset to 0
each time a new session is established. A new session is established each time your application finishes processing pending messages and no messages are left.
MFC continues to call CWinApp::OnIdle
(incrementing lCount
each time) as long as there’re no messages waiting for processing. If the application received a new message, MFC ends the current session and stops calling OnIdle
until it establishes a new session again. If you want, you can return TRUE
to indicate that further processing is required and MFC should call OnIdle
again (as long as we are in the current session,) or FALSE
to indicate that processing has been finished and MFC should not call OnIdle
again until a new session is established.
Notice that, you should call the base implementation of CWinApp::OnIdle
because the default implementation of OnIdle
updates command UI objects like menu items and toolbars besides doing some internal structure cleanup.
Unfortunately, C doesn't include OnIdle
function. However, we could work out ours.
The following C example shows our new handmade message queue that simulates CWinApp::OnIdle
:
while (TRUE) {
if (PeekMessage(&msg, 0, 0, 0, PM_REMOVE)) {
if (WM_QUIT == msg.message)
break;
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else {
}
}
The key function is PeekMessage
. This function checks the message queue and if a message was found, it removes the message from the queue (if PM_REMOVE
specified,) initializes the MSG
object with message data, and returns TRUE
to the caller. If no message was found, PeekMessage
returns FALSE
thus executing the code (secondary processing) in the else statement.
You can also create your fully-featured handmade OnIdle
. Consider the following code:
BOOL OnIdle(LONG lCount);
int WINAPI WinMain(. . .)
{
MSG msg;
LONG lCount;
. . .
while (TRUE) {
if (PeekMessage(&msg, 0, 0, 0, PM_REMOVE)) {
lCount = 0;
if (WM_QUIT == msg.message)
break;
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else {
if (lCount >= 0) {
if (!OnIdle(lCount)) {
lCount = -1;
}
lCount++;
}
}
}
return msg.wParam;
}
BOOL OnIdle(LONG lCount)
{
return FALSE;
}
Have a nice day!
Filed under:
Windows Management Tagged:
C,
CodeProject,
CPP,
MFC,
Windows Management