Win32汇编笔记——窗口创建API函数

1.模块的概念

一个模块代表的是一个运行中的exe文件或dll文件,用来代表这个文件中所有的代码和资源,用来代表这个文件中所有的代码和资源,磁盘上的文件不是模块,装入内存后运行时就叫做模块。一个应用程序调用其他DLL中的API时,这些DLL文件被装入内存,就产生了不同的模块,为了区分地址空间中的不同模块,每个模块都有惟一的模块句柄来标识。

2.句柄

句柄只是一个数值,它的值对程序来说是没有意义的,它只是Windows用来表示各种资源的编号而已。

由于很多API函数中都要用到程序的模块句柄,以便利用程序中的各种资源,所以在程序的一开始就先取得模块句柄并存放到一个全局变量中可以省去很多的麻烦,在Win32中,模块句柄在数值上等于程序在内存中装入的起始地址。

注意:模块和句柄的概念。

3.API函数

取模块句柄函数:GetMoudleHandle

使用方法:invoke GetMoudleHandle,pMoudleName

lpMoudleName参数是一个指向含有模块名称字符串的指针,可以用这个函数取得程序地址空间中各个模块的句柄,如

szUserDll		db		'User32.dll',0
					...
					invoke	GetMoudleHandle,addr szUserDll
					.if			eax
								mov		hUserDllHandle,eax
					.endif
					...

如果使用参数NULL调用GetMoudleHandle,那么得到的是调用者本模块的句柄,如:
invoke GetMoudleHandle,NULL
mov hInstance,eax

在Win32中hInstance(实例句柄)就是hMoudle(模块句柄)。

在C语言中,hInstance通过WinMain由系统传入,WinMain的原型是:
WinMain (hInstance,hPrevInstance,lpzCmdPraram,nCmdShow),程序不用自己去获得hInstance,这个过程由C的初始化代码代劳。

注册窗口类API:RegisterClassEx,“Ex”是扩展的意思。

一个窗口类定义了窗口的一些主要属性,如:图标、光标、背景色、菜单和负责处理该窗口所属消息的函数。这些属性定义在一个WNDCLASSEX结构中,把结构的地址当参数一次性传递给RegisterClassEx,WNDCLASSEX是WNDCLASS结构的扩展。

WNDCLASSEX STRUCT
CbSize          DWORD 	? ;结构的字节数
Style           DWORD 	? ;类风格
LpfnWndProc    	DWORD 	? ;窗口过程的地址
CbClsExtra      DWORD 	?
CbWndExtra      DWORD 	?
HInstance 		DWORD 	? ;所属的实例句柄
HIcon 			DWORD 	? ;窗口图标
HCursor 		DWORD 	? ;窗口光标
HbrBackground 	DWORD 	? ;背景色
LpszMenuName 	DWORD 	? ;窗口菜单
LpszClassName 	DWORD 	? ;类名字符串的地址
HIconSm 		DWORD 	?	;小图标
WNDCLASSEX ENDS

参数:
hIcon——图标句柄,指定显示在窗口标题栏左上角的图标。Windows已经定义了一些图标,同样,程序也可以使用在资源文件中定义的图标,这些图标的句柄可以用LoadIcon函数获得,如果程序中没有用到图标,那么Windows给窗口显示默认的图标

hCursor——光标句柄,指定了鼠标在窗口中的光标形状。同样,Windows也预定义了一些光标,可以用LoadCursor获取他们的句柄,IDC_ARROW是Windows预定义的箭头光标,如果想使用自定义的光标,也可以自己在资源文件中定义。

lpszMenuName——指定窗口上显示的默认菜单,它指向一个字符串,描述资源文件中菜单的名称,如果资源文件中菜单是用数值定义的,那么这里使用菜单资源的数值。窗口中的菜单也可以在建立窗口函数CreateWindowEx的参数中指定。如果两个地方都没有指定,那么建立的窗口上就没有菜单。

hInstance——指定要注册的窗口类属于哪个模块,模块句柄在程序开始的地方已经用GetMoudleHandle函数获得。

cbSize——指定WNDCLASSE结构的长度,用sizeof伪操作来获取。很多Win32API参数中的结构都有cbSize字段,它主要是用来区分结构的版本,当以后新增了一个字段时,cbSize就相应增大,如果调用的时候cbSize还是旧的长度,表示运行的是基于旧结构的程序,这样可以防止使用无效的字段。

style——窗口风格。CS_HREDRAW和CS_VREDRAW表示窗口的宽度或高度改变时是否重画窗口。比较重要的是CS_DBLCLKS风格,指定了它,Windows才会把在窗口中快速两次单击鼠标的行为翻译成双击消息WM_LBUTTONDBLCLK发给窗口过程。

一些窗口类的style预定义值:
一些窗口类的style预定义值
可以看到,这些预定义值实际上在使用不重复的数据位,所以可以组合起来使用,同时使用不同的预定义值并不会引起混淆。

对于不同二进制位组合的计算,“加”和“或”的结果是一样的,但强烈建议使用or,因为如果不小心指定了两个同样的风格时就有 BUG 产生了,因为 1 or 1 = 1,而 1+1 = 2。

hbrBackground——窗口客户区的背景色。前面的hbr表示他是一个刷子(Brush)的句柄,“刷子”一词形象地表示了填充一个区域的着色模式。Windows预定义了一些刷子,如BLACK_BRUSH和WHITE_BRUSH等,可以用下列语句来得到它们的句柄:
invoke GetStockObject,WHITE_BRUSH
这里也可以使用颜色值,Windows已经预定义了一些颜色值,分别对应窗口各部分的颜色,如COLOR_BACKGROUND和COLOR_WINDOW等,使用颜色值的时候,Windows规定必须在颜色值上+1。

lpszClassName——指定程序员要建立的类命名,以便以后用这个名称来引用它。这个字段是一个字符串指针。

cbWndExtra和cbClsExtra——分别是在Windows内部保存的窗口结构和类结构中给程序员预留的空间大小,用来存放自定义数据,他们的单位是字节。不使用自定义数据的话,这两个字段就是0.

lpfnWndProc——最重要的参数,他指定了基于这个类建立的窗口的窗口过程地址。通过这个参数,Windows就知道了在DispatchMessage函数中把窗口消息发到哪里去,一个窗口过程可以为多个窗口服务,只要这些窗口是基于同一个窗口类建立的。

注册窗口时是用一个结构传递参数,建立窗口时所有的属性都是用单个参数的方式传递的。

建立窗口函数CreateWindowEx

它是Win16中CreateWindow函数的扩展,CreateWindowEx函数的使用方法是:

	invoke	CreateWindowEx,dwExStyle,lpClassName,\
	lpWindowName,dwStyle,x,y,nWidth,nHeight,\
	hWndParent,hMenu,hInstance,lpParam

lpClassName——建立窗口使用的类名字符串指针。

lpWindowName——指向表示窗口名称的字符串,该名称会显示在标题栏上。如果该参数空白,则标题栏上什么都没有。

hMenu——窗口上要出现的菜单的句柄。在注册窗口类的时候也定义了一个菜单,那是窗口的默认菜单,意思是如果这里没有定义菜单(用参数NULL)而注册窗口类时定义了菜单,则使用窗口类中定义的菜单;如果这里指定了菜单句柄,则不管窗口类中有没有定义都将使用这里定义的菜单;两个地方都没有定义菜单句柄,则窗口上没有菜单。另外,当建立的窗口是子窗口时(dwStyle中指定了WS_CHILD),这个参数是另一个含义,这时hMenu参数指定的是子窗口的ID号(这样可以节省一个参数的位置,因为子窗口不会有菜单)。

lpParam——这是一个指针,指向一个欲传给窗口的参数,这个参数在WM_CREATE消息中可以被获取,一般情况下用不到这个字段。

hInstance——模块句柄,和注册窗口类时一样,指定了窗口所属的程序模块。

hWndParent——窗口所属的父窗口,这里的“父子”关系只是从属关系,主要用来在父窗口销毁时一同将其“子”窗口销毁,并不会把窗口位置限制在父窗口的客户区范围内,但如果要建立的是真正的子窗口(dwStyle中指定了WS_CHILD的时候),这时窗口位置会被限制在父窗口的客户区范围内,同时窗口的坐标(x,y)也是以父窗口的左上角为基准的。

x,y——指定窗口左上角位置,单位是像素(px)。默认时可指定为 CW_USEDEFAULT,这样Windows会自动为窗口指定最合适的位置,当建立子窗口时,位置是以父窗口的左上角为基准的,否则,以屏幕左上角为基准。

nWidth,nHeight——窗口的宽度和高度,也就是窗口的大小,同样是以像素为单位的。默认时可指定为 CW_USEDEFAULT,这样Windows会自动为窗口指定最合适的大小。

dwStyle——窗口的两个参数dwStyle和dwExStyle决定了窗口的外形和行为,dwStyle是从win16开始就有的属性,下表列出了一些常见的dwStyle定义。
窗口风格的预定义值
等效的窗口风格预定义值
dwExStyle——dwExStyle是Win32中扩展的,它们是一些以WS_EX_开头的预定义值,主要定义了一些特殊的风格,下表给出了一些最常用的特殊风格。
窗口扩展风格的预定义值

建立窗口后,eax中传回来的是窗口句柄,要把它保存起来以后备用,然后要用ShowWindow把它显示出来,ShowWindow用窗口句柄做第一个参数,第二个参数则是显示方式。

invoke ShowWindow,hWinMain,SW_SHOWNORMAL
ShowWindow函数显示方式的定义

窗口显示以后,用UpdateWindow绘制客户区,它实际就是向窗口发送了一条WM_PAINT消息。它绕过应用程序的消息队列,直接发送WM_PAINT消息给窗口过程。到此为止,一个顶层窗口就正常建立并显示了。

invoke UpdateWindow,hWinMain

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值