WIN32汇编语言教程:第05章 使用资源 · 5.4 对话框(6)
.if ax == CBN_SELENDOK invoke SendDlgItemMessage,hWnd,\ IDC_TITLETEXT,CB_GETCURSEL,0,0 .if eax == 2 invoke GetDlgItem,hWnd,IDC_CUSTOMTEXT invoke EnableWindow,eax,TRUE .else mov ebx,eax invoke SendDlgItemMessage,hWnd,IDC_TITLETEXT,\ CB_GETLBTEXT,ebx,addr @szBuffer invoke SetWindowText,hWnd,addr @szBuffer invoke GetDlgItem,hWnd,IDC_CUSTOMTEXT invoke EnableWindow,eax,FALSE .endif .endif ;******************************************************************** ; 在文本框中输入文字 ;******************************************************************** .elseifax == IDC_CUSTOMTEXT invoke GetDlgItemText,hWnd,IDC_CUSTOMTEXT,\ addr @szBuffer,sizeof @szBuffer invoke SetWindowText,hWnd,addr @szBuffer .endif ;******************************************************************** ;恢复代码的缩进格式,请读者注意 ;******************************************************************** ; 处理滚动条消息 ;******************************************************************** .elseif eax == WM_HSCROLL mov eax,wParam .if ax == SB_LINELEFT dec dwPos .elseif ax == SB_LINERIGHT inc dwPos .elseif ax == SB_PAGELEFT sub dwPos,10 .elseif ax == SB_PAGERIGHT add dwPos,10 .elseif ax == SB_THUMBPOSITION || ax == SB_THUMBTRACK mov eax,wParam shr eax,16 mov dwPos,eax .else mov eax,TRUE ret .endif cmp dwPos,0 jge @F mov dwPos,0 @@: cmp dwPos,100 jle @F mov dwPos,100 @@: invoke SetDlgItemInt,hWnd,IDC_VALUE,dwPos,FALSE invoke SendDlgItemMessage,hWnd,\ IDC_SCROLL,SBM_SETPOS,dwPos,TRUE ;******************************************************************** .else mov eax,FALSE ret .endif mov eax,TRUE ret _ProcDlgMain endp ;#################################################################### start: invoke GetModuleHandle,NULL mov hInstance,eax invoke DialogBoxParam,hInstance,DLG_MAIN,\ NULL,offset _ProcDlgMain,NULL invoke ExitProcess,NULL ;#################################################################### end start
2. 子窗口控件的通用使用方法
由于子窗口控件实际上就是窗口,大部分窗口函数对它们都是适用的,如可以用EnableWindow在灰化和允许状态之间切换,可以用ShowWindow在显示和隐藏之间切换,可以用GetWindowText和SetWindowText来改变上面的文字,也可以用MoveWindow来改变大小和移动位置等。在Control.asm中用“显示图片”复选框切换图片框的隐藏和显示,用的就是ShowWindow函数,处理“允许更换图片”复选框时切换“更换图片”按钮的状态,用的是EnableWindow函数。
除了可以用对子窗口控件使用窗口的通用函数外,还可以使用针对它们的专用函数。下面介绍一些常用的函数。
在资源脚本文件中定义的是控件的ID,当这些子窗口控件被创建以后同样会有一个窗口句柄,但既然它们不是由我们自己创建的,那么怎么知道它们的窗口句柄呢?有一个函数可以从ID中获取子窗口句柄:
invoke GetDlgItem,hDlg,dwIDDlgItem mov hDlgItem,eax
函数的输入参数是对话框句柄和ID值,返回值是子窗口句柄;反过来,有两种方法可以从子窗口句柄获取ID:
(1) invoke GetDlgCtrlID,hWndCtrl ;输入子窗口句柄,返回值是控件ID
(2) invoke GetWindowLong,hWndCtrl,GWL_ID
当需要向控件发送消息的时候,当然可以先用GetDlgItem获取子窗口句柄再用SendMessage函数,但有一个函数更为简便:
invoke SendDlgItemMessage,hDlg,dwIDDlgItem,Msg,wParam,lParam
这个函数可以直接向控件发送消息,只需要在参数中指定对话框句柄和子窗口ID(注意:并没有PostDlgItemMessage这样的函数!)。
如果要想知道在一个控件上按下了Tab键或Shift+Tab键会跳到哪一个控件上去,也就是说下一个或上一个Tab停留位在哪里,可以使用GetNextDlgTabItem函数:
invoke GetNextDlgTabItem,hDlg,hCtl,bPrevious .if eax mov hWinNext,eax .endif
其中的bPrevious参数指定了搜索的方向;与之相似,使用GetNextDlgGroupItem 函数可以返回下一个分组的位置:
invoke GetNextDlgGroupItem,hDlg,hCtl,bPrevious .if eax mov hWinNext,eax .endif
3. 使用单选钮和复选框
单选钮是互斥的选择钮,同一组的多个单选钮只能有一个被选中,单选钮的外形是一个圆形的标记加上文本,圆形中有黑点表示被选中。复选框不是互斥的,多个复选框的状态不会互相影响,复选框的外形是一个方框加上文本,方框中可以用有无对钩来表示是否被选中。
单选钮和复选框控件都是基于Button类的,只不过它们的窗口风格分别是BS_RADIOBUTTON和BS_CHECKBOX。既然它们是特殊的“按钮”,所以和它们有关的函数都带有“Button”一词,查看一个单选钮或复选框是否被选中可以用下面的函数来检测:
invoke IsDlgButtonChecked,hDlg,nIDButton
函数的返回值可能是BST_CHECKED(选中状态),BST_INDETERMINATE(3态复选框的灰化状态)或BST_UNCHECKED(未选中状态)。也可以用向子窗口控件发送BM_GETCHECK消息的方法来检测,返回值和上面的函数是一样的。
如果想设置单选钮或复选框的状态,可以使用下面的语句:
invoke CheckDlgButton,hDlg,nIDButton,uCheck