Click here to Skip to main content
15,884,177 members
Articles / Desktop Programming / MFC
Article

About the Windows Message Queue

Rate me:
Please Sign up or sign in to vote.
3.67/5 (5 votes)
17 Apr 20023 min read 171.6K   1.7K   37   26
This article is written for the Win32 API programmers on the subject of Windows message queues.

Sample Image - queue.gif

Introduction

Everybody knows MFC as the most powerful instrument for developing applications on the Windows system. Its classes are specialized on the entire family of difficult tasks you can imagine and the flexibility of the chosen solutions is remarkable. It's the best approach on developing large software and keeps the programmer away from several kind of detail problems. This should be the greatest advantage when having to deal with a window-based system but...

The Thread

We're not talking about a window-based system here. "The atomic working entity of a program is the thread", says the MSDN book. Among many background details like  stack and paths of execution, it also has to cover the implementation of a message queue. It's not a rule but you will find it on every thread that sustains a window. This is the reason for a very popular confusion: the window has a message queue. Wrong! The message queue belongs to the thread and the messages posted to the window are dispatched to it by the message loop in the thread. I will illustrate this by the program attached to this article.

The Program

Is a console based application; the modeless dialog manages its messages through the console's message queue, so it's not about having two queues at a time. The code offers you a class and the main function.

CConsoleQueue

This class implements the message loop and a primitive system of handling messages. It has the following methods:

RunQueue - runs the classical message loop

while (GetMessage(&msg, NULL, 0, 0))    // extract the message
                                        // from the queue
{
  if (fctMan=(*this)[msg.message])
    fctMan((void *)msg.wParam);
  else
  {
    TranslateMessage(&msg); // necessary to listen the keyboard
    DispatchMessage(&msg);  // message goes to the default
                            // procedure
  }
}

EndQueue - terminates the message loop by posting WM_QUIT

PostMessage(NULL, WM_QUIT, 0, 0);     // message to interrupt
                                      // the loop by returning
                                      // FALSE on GetMessage

RegisterMessageHandler - registers a handler function to a particular message. When the message is received in the message loop, the handler is called. To pass a value for the handle, you should put it through the WPARAM when calling PostMessage.

Note: this could be considered as a skeleton of the reactor concept proposed by The Adaptive Communication Environment (ACE).

RemoveAll - removes all the associations (from the reactor)

main

The purposes of this function are - step by step - the following:

1. Creating a modeless dialog box used to send messages to the queue:

hWndDialog=CreateDialog(NULL, MAKEINTRESOURCE(IDD_DIALOG_TEST),
  NULL, DialogProcedure);
ShowWindow(hWndDialog, SW_SHOW);

2. Setting a timer on the thread:

nTimer=SetTimer(NULL, 0, nDelay*1000, TimerProcedure);

3. Registering a handler for an user-defined message:

queue.RegisterMessageHandler(WM_USER_DEFINED, UserDefined);

4. Running the queue:

queue.RunQueue();

Behavior

The purpose is to drop WM_TIMER messages in the message queue; each
WM_TIMER
will print to console a global buffer. If the buffer doesn't modify for the last
nKeepQueueSteps WM_TIMER
s, the last one will kill the timer and will end the message queue. Modifying the buffer is done in the modeless dialog box by writing in the edit box and pressing "send buffer". Pressing "send user-defined" will post the WM_USER_DEFINED message to the queue.

Final

Observe that calling PostMessage with NULL for the first parameter will drop the message in the current thread's message queue.

Another observation is about setting the timer. This one lives only among the queue's events and is not a window's resource. It belongs to the thread and could reach a window only if is set to and only by a call of DispatchMessage.

The last word is about the message loop. This expression is a source of limitation for the programmer. In fact you could have more message loops in a single thread's execution. To test this, simply multiply the actual content of main in the function's body like this:

hWndDialog=CreateDialog(NULL, MAKEINTRESOURCE(IDD_DIALOG_TEST),
  NULL, DialogProcedure);
// ...
cout<<endl<<"program ends here..."<<endl;

hWndDialog=CreateDialog(NULL, MAKEINTRESOURCE(IDD_DIALOG_TEST),
  NULL, DialogProcedure);
// ...
cout<<endl<<"program ends here..."<<endl;

// ...

hWndDialog=CreateDialog(NULL, MAKEINTRESOURCE(IDD_DIALOG_TEST),
  NULL, DialogProcedure);
// ...
cout<<endl<<"program ends here..."<<endl;

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here


Written By
Software Developer (Senior)
Europe Europe
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions

 
Generalshow desktop Pin
amt_alla7-May-04 0:56
amt_alla7-May-04 0:56 
Generalcontrol client resorces Pin
amt_alla6-May-04 9:30
amt_alla6-May-04 9:30 
GeneralRe: control client resorces Pin
Hans Ruck6-May-04 22:52
Hans Ruck6-May-04 22:52 
GeneralRe: control client resorces Pin
amt_alla7-May-04 1:15
amt_alla7-May-04 1:15 
GeneralRe: control client resorces Pin
Hans Ruck7-May-04 1:33
Hans Ruck7-May-04 1:33 
GeneralPassing strings using Post Message Pin
hedonist23-Apr-04 15:06
hedonist23-Apr-04 15:06 
GeneralRe: Passing strings using Post Message Pin
Garth J Lancaster23-Apr-04 15:36
professionalGarth J Lancaster23-Apr-04 15:36 
GeneralRe: Passing strings using Post Message Pin
hedonist23-Apr-04 19:16
hedonist23-Apr-04 19:16 
GeneralRe: Passing strings using Post Message Pin
Garth J Lancaster24-Apr-04 1:20
professionalGarth J Lancaster24-Apr-04 1:20 
GeneralRe: Passing strings using Post Message Pin
hedonist25-Apr-04 21:44
hedonist25-Apr-04 21:44 
GeneralRe: Passing strings using Post Message Pin
Garth J Lancaster26-Apr-04 0:04
professionalGarth J Lancaster26-Apr-04 0:04 
GeneralRe: Passing strings using Post Message Pin
hedonist26-Apr-04 2:24
hedonist26-Apr-04 2:24 
Hail the 'G',

Yup, It got everything working!

Just for more understanding.
What's the difference between using ON_MESSAGE and ON_REGISTERED_MESSAGE?
What's the difference between using wParam and lparam?

Great, Really learn quite a lot from UBig Grin | :-D
Wondered whether there'll be a day when I could be as goodFrown | :(


I'll keep trying. help from professionals like you is really encouraging.
Cheers;P

Learner
GeneralRe: Passing strings using Post Message Pin
Garth J Lancaster26-Apr-04 11:53
professionalGarth J Lancaster26-Apr-04 11:53 
GeneralRe: Passing strings using Post Message Pin
hedonist26-Apr-04 19:54
hedonist26-Apr-04 19:54 
GeneralRe: Passing strings using Post Message Pin
Garth J Lancaster26-Apr-04 20:42
professionalGarth J Lancaster26-Apr-04 20:42 
GeneralRe: Passing strings using Post Message Pin
hedonist27-Apr-04 6:01
hedonist27-Apr-04 6:01 
GeneralRe: Passing strings using Post Message Pin
hedonist27-Apr-04 6:06
hedonist27-Apr-04 6:06 
GeneralRe: Passing strings using Post Message Pin
Tom Wright11-Nov-04 10:35
Tom Wright11-Nov-04 10:35 
GeneralRe: Passing strings using Post Message Pin
Garth J Lancaster11-Nov-04 12:05
professionalGarth J Lancaster11-Nov-04 12:05 
GeneralIt isn't working in an other project Pin
TPSC2-Mar-04 21:37
TPSC2-Mar-04 21:37 
GeneralRe: It isn't working in an other project Pin
Hans Ruck2-Mar-04 23:22
Hans Ruck2-Mar-04 23:22 
GeneralRe: It isn't working in an other project Pin
Anonymous3-Mar-04 0:13
Anonymous3-Mar-04 0:13 
GeneralRe: It isn't working in an other project Pin
TPSC3-Mar-04 0:15
TPSC3-Mar-04 0:15 
GeneralRe: It isn't working in an other project Pin
Hans Ruck3-Mar-04 1:02
Hans Ruck3-Mar-04 1:02 
Questionwhy? Pin
Prakash Nadar27-Feb-04 4:06
Prakash Nadar27-Feb-04 4:06 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.