日期:2014-05-17 浏览次数:20883 次
在 Windows应用程序中,窗体是由一种称为“ UI线程( User Interface Thread)”的特殊类型的线程创建的。
?????? 首先, UI线程是一种“线程”,所以它具有一个线程应该具有的所有特征,比如有一个线程函数和一个线程 ID。
?????? 其次,“ UI线程”又是“特殊”的,这是因为 UI线程的线程函数中会创建一种特殊的对象——窗体,同时,还一并负责创建窗体上的各种控件。
?????? 窗体和控件大家都很熟悉了,这些对象具有接收用户操作的功能,它们是用户使用整个应用程序的媒介,没有这样一个媒介,用户就无法控制整个应用程序的运行和停止,往往也无法直接看到程序的运行过程和最终结果。
?????? 那么,窗体和控件又是如何作到对用户操作进行响应的呢?这一响应是不是由窗体和控件自己“主动”完成的?
?????? 换句话说:
?????? 窗体和控件具不具备独立地响应用户操作(比如键盘和鼠标操作)的功能?
??????
?????? 答案是否定的。
?????? 那就奇怪了,比如我们用鼠标点击了一个按钮,并且看到它“陷”下去了,然后又还原,之后,我们确实看到了程序执行了此按钮所对应的任务。难道不是按钮来响应用户操作的吗?
?????? 这实际上是一个错觉。这个错觉产生的根源在于不了解 Windows内部的运作机理。
?????? 简单地说,窗体和控件之所以能响应用户操作,关键在于负责创建它们的 UI线程拥有一个“消息循环( Message Loop ) ”。这个消息循环由线程函数负责启动,通常具有以下的“模样”(以 C++代码表示):
?
?
??? MSG msg;?//代表一条消息
??? BOOL bRet;
??? //从 UI线程消息队列中取出一条消息
??? while( (bRet = GetMessage( &msg, NULL, 0, 0 )) != 0)
??? {
??? ??? if (bRet == -1)
??? ??? {
??????? ??? //错误处理代码,通常是直接退出程序
??? ??? }
??? ??? else
??? ??? {
??????? ??? TranslateMessage(&msg); //转换消息格式
??????? ??? DispatchMessage(&msg);?//分发消息给相应的窗体
??? ??? }
??? }
?
?
???? 可以看到, 所谓消息循环,其实就是一个While循环语句罢了。