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

上页:第05章 使用资源 · 5.4 对话框(5) 下页:第05章 使用资源 · 5.4 对话框(7)

第05章 使用资源

版权所有 © 云南伯恩科技 证书:粤ICP备09170368号