Windows Message Queue Introduction
Windows 的消息队列和消息处理方式一直没有非常系统的学习过。正如某位名人所说的“一知半解,最危险”。
“一知半解”就是对事物的吸收囫囵吞枣、不求甚解,导致判断失准而不自知。因为不彻底了解事物,不精准分辨事物细微差异,以致陷入断章取义、冯京当马凉、张飞打岳飞打得满天飞。而且正因为自以为很懂,他甚至听不进去别人的观点、劝告,当然赖之作出的判断,就会差之毫厘失之千里,甚至造成很大的错误。
创建消息循环
系统只会为那些须要消息队列来执行某些操作的线程创建消息队列。如果一个线程创建了一个或多个窗口,那么就必须创建一个消息循环来处理消息队列中的消息。(窗口都会有显示和关闭的消息),这个消息循环会从线程的消息队列中检索消息(PeekMessage
和GetMessage
),然后分发给相应的处理过程。
由于应用程序中系统会把消息分发给各个窗口,所以线程在创建消息循环之前至少要创建一个窗口。传统的应用程序中,应用会WinMain函数中注册一个窗口类作为主窗口,创建和显示窗口,然后启动消息循环。
我们可以使用GetMessage
和DispatchMessage
函数来创建消息循环。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 |
|
线程,窗口,消息队列,消息循环,消息处理过程
如果一个线程须要消息来处理某些操作,那么可以创建一个(只可以是一个)消息循环来检查消息队列,获取有取的消息并做处理。每个线程有它自己的一个消息队列(如其它线程可以通过PostThreadMessage 来向某个线程发送消息,这个消息会被发到相应的消息队列中),线程可以用PeekMessage来获取消息并处理。线程可以创建一个窗口,这个窗口有自己的消息处理程序如WndProc。线程在接收到消息后可以通过DispatchMessage来分发消息到各个窗口中。
什么是UI线程
UI线程指的是有窗口,或控件的线程,有消息队列和消息循环。UI线程有以下几个特点 1. UI线程有一个消息队列,这个消息队列由操作系统分配。在创建第一个窗体时就分配。 2. UI线程需要一个消息汞(消息循环)来检索消息,然后分发消息给各个窗体或者控件。 3. COM在这个线程止初始化.一个STA(单线程单元需要让许多窗体特征正常运行,因为这些不是线程安全的)COM确保这些特性是线程安全的。 4. 线程不会在任何操作阻塞。 5. UI线程可以创建多个窗体和控件,这些控件都是由一个消息循环来分发消息的。
在Windows中操作系统只会为UI线程创建消息队列。基本上我们只需要一个UI线程。 MSDN: The system does not automatically create a message queue for each thread,Instead, the system creates a message queue only for threads that perform operations which require a message queue.
消息队列函数
DispatchMessage
1 2 |
|
这个函数会分发消息到窗口的处理过程中,一般和GetMessage一起用。note: 这个函数会等待窗口处理过程的返回 是阻塞式的
如果lpmsg指向一个WM_TIMER
和lParam参数不为空,那么这个lParam指向的函数将会被调用,而不会调用窗口的处理过程。
PeekMessage
1 2 3 4 5 6 7 |
|