窗体的消息处理

我们知道一个应用程序一般都不是仅仅有一个窗体组成的,往往是多窗体组成的,比方一个对话框的窗体上有一个button,这里对话框是一个窗体。button也是一个窗体。

假设一个对话框上有100个button。就是100个窗体。这样句柄会比較多。因而出现了DirectUI的设计方法,全部button和主窗体都是同一个窗体,採用分不同区域来绘画而成。这里就遇到了一个问题。每一个窗体是独立存在的,但在前面的样例里,能够看到每一个窗体都是调用PyWndProc函数来处理。

意味着多个窗体的消息都抛给PyWndProc函数处理,这样处理起来仅仅会越来越多。越来越复杂。站在面向对象设计角度来考虑,能否够有一个更好的方案解决呢?这个是能够的。由于Windows里给每一个窗体保留了一个用户数据字段。仅仅要利用这个字段,就能够关联起每一个窗体与消息类之间的关系。比方窗体1就调用窗体1的类来处理消息,窗体2就调用窗体2的类来处理消息,这样每一个窗体的独立性就得到保障。不用操心窗体1的消息会跑到窗体2去。为此。我声明了一个类Controller。用这个类来处理窗体的消息,当然不同的窗体都能够继承这个类,而实现其他的窗体消息处理。创建类Controller的实例之后,把这个实例对象保存到窗体的GWL_USERDATA字段里。參考《Windows API一日一练》介绍创建窗体的函数,例如以下:

HWND CreateWindowEx(

DWORD dwExStyle,//窗体的扩展风格

LPCTSTR lpClassName,//指向注冊类名的指针

LPCTSTR lpWindowName,//指向窗体名称的指针

DWORD dwStyle,//窗体风格

int x,//窗体的水平位置

int y,//窗体的垂直位置

int nWidth,//窗体的宽度

int nHeight,//窗体的高度

HWND hWndParent,//父窗体的句柄

HMENU hMenu,//菜单的句柄或是子窗体的标识符

HINSTANCE hInstance,//应用程序实例的句柄

LPVOID lpParam//指向窗体的创建数据

);

在这个API函数的最后字段lpParam。就是指向窗体用户自己定义的数据,在这里,我把消息处理类对象的指针放到这里。就能够让每一个窗体有自己的消息处理类了。

定义类Controller例如以下:

class Controller:
    def __init__(self):
        self.hWnd = HWND()
    def SetWnd(self, hWnd):
        self.hWnd = hWnd
    def MyWndProc(self, hWnd, Msg, wParam, lParam):
        if Msg == WM_DESTROY:
            windll.user32.PostQuitMessage(0)
            return 0
        else:
            return windll.user32.DefWindowProcW(hWnd, Msg, wParam, lParam)

在类Controller里。主要有成员变量self.hWnd。它是用来保存每一个窗体的句柄;成员函数MyWndProc是用来处理每一个窗体的消息,假设窗体没有处理。就会把这些消息传递给Windows系统默认处理,而这个处理默认消息的函数是DefWindowProcW函数。由于一个窗体的消息是有非常多的,并非每一个窗体都须要处理这么多消息,因此仅仅有须要的才处理,这样处理方式是非常方便的。

时间: 2024-11-29 09:09:48

窗体的消息处理的相关文章

窗体皮肤实现 - 重绘窗体非客户区(三)

窗体边框基本的绘制和控制完成,在第二篇中主要遗留的问题. 标题区域图标和按钮没绘制 缩放时客户区显示有问题 解决完下面的问题,皮肤处理基本完整.大致的效果GIF GIF中TShape的颜色表现有些问题,实际是正常的. 绘制标题区域内容 获取标题有效区域 绘制窗体图标 绘制按钮 绘制标题 标题区域主要考虑窗体是否在最大化状态,最大化后实际的标题绘制区域会有变化.可以通过 IsZoomed 或 GetWindowLong(Handle, GWL_STYLE) and WS_MAXIMIZE = WS

【转】MFC消息处理(一)

原文网址:http://blog.csdn.net/hyhnoproblem/article/details/6182120 1.MFC窗口如何与AfxWndProc建立联系. 当一个新的CWnd派生类创建时,在调用CWnd::CreateEx()过程中,MFC都会安装AfxCbtFilterHook().这个Hook将拦截HCBT_CREATEWND,将窗体的消息处理函数设置为AfxWndProc(). [cpp] view plaincopy // wincore.cpp 651 // CW

XE6 FMX之控件绘制与显示

FMX是一套UI类库,就相当于以前的VCL,但是相比VCL来说,支持了跨平台,同时也直接内部支持了各种特效动画甚至3D的效果,如果效率性能上来了,这个类库还是很有前景的.这次我主要学习的就是一个FMX窗体是如何绘制并显示出来的,相比较于VCL,有哪些不同之处,以及一个FMX程序的启动运转的最简单剖析.至于各种特效,动画,以及3D等,以后再慢慢的去啃食,贪多嚼不烂. 新建一个FireMonkey的HD Desktop Application,IDE会自动建立一个工程,进入工程,可以发现FMX的程序

PostMessage与SendMessage的区别

PostMessage只负责将消息放到消息队列中,不确定何时及是否处理 SendMessage要等到受到消息处理的返回码(DWord类型)后才继续 PostMessage执行后马上返回 SendMessage必须等到消息被处理后才会返回. 下面通过一个小例子来说明下这2个方法进行参数传递的不同点: //Win32 API 类 using System; using System.Runtime.InteropServices; namespace TestHwnd { public class

OD调试6—使未注册版软件的功能得以实现

OD调试6—使未注册版软件的功能得以实现 继续开始我OD调试教程的学习笔记. 本次试验对真正的程序进行逆向.(之前的都是为破解而专门设计的小程序) 这次试图对一个“太监版”的程序进行完整化,也就是把限制的功能恢复,把阉割的功能添加等等.用到的知识也是之前提到的,但是会有不同的地方. 试验软件:PixtopianBook.exe(一个通讯录软件) 打开原始程序运行,观察界面: 这是一个通讯录软件,老外写的,很显然,当前是未注册版,试验后发现有功能限制,限制是只能有三个分组,每组不能超过4个人.也就

MFC 如何添加自定义消息

MFC 如何添加自定义消息 分类: MFC2012-08-17 18:21 561人阅读 评论(0) 收藏 举报 mfcnullwindowsuser工作command MFC如何添加自定义消息   MFC自定义消息 图解VC添加自定义消息 MFC激活自定义消息 如果用户自定义的类要求响应普通的Windows消息(也就是以WM_开头,除了WM_COMMAND以外的消息,这类消息在WM_USER以下的是系统消息,WM_USER以上的可以由用户自己定义),那就要求自定义的类必须从CWnd中派生.这是

MFC中用户自定义类响应自定义消息

这篇技术文章不是讨论经典的MFC中的消息工作机理的,讨论消息工作原理.方式和路径的文章在网上和书本中随处可见.网上众多的讨论都是关于如何响应并进行用户自定义消息映射的:网上还有一些文章介绍如何在自定义类中响应Windows消息,在本文中都简略叙述.但是,网上大部分的文章没用透彻阐述如何在用户自定义类中响应自定义消息这一通用方法. 问题定义如下:用户自定义一个类,这个类不一定要有界面(完全可以是不可视的),要求自定义的类可以响应某个自定义消息. 首先能够响应消息的类必须都从CCmdTarget类中

.Net WinForm 控件键盘消息处理剖析

在WinForm控件上我们可以看到很多关于键盘消息处理的方法,比如OnKeyDown, OnKeyPress, ProcessCmdKey, ProcessDialogKey,IsInputKey等等,那么这些方法是如何被组织的,每一个方法的具体含义又是什么哪?Win32的键盘消息又是如何到达控件上的这些方法的,本文将着重阐述这些问题,对.Net WinForm控件的键盘消息处理过程进行剖析.  1.      WinForm消息循环 大家都知道WinForm也是依赖于底层的消息机制的,通常我们

13.安卓消息处理机制

1.Android消息处理机制(★★★★必会) 1.1.Looper.Message.Handler的关系 当我们的Android应用程序的进程一创建的时候,系统就给这个进程提供了一个Looper,Looper是一个死循环,它内部维护这个一个消息队列.Looper不停地从消息队列中取消息(Message),取到消息就发送给了Handler,最后Handler根据接收到的消息去修改UI.Handler的sendMessage方法就是将消息添加到消息队列中. 1.2.runOnUiThread Ac