luqingfei@C++

为中华之崛起而崛起!
兼听则明,偏听则暗。

Win32汇编--使用资源--对话框--在对话框中使用子窗口控件(3)

 

使用资源--对话框--在对话框中使用子窗口控件

 

8、使用列表框

列表框提供一个可供用户选择的列表,用户可以一次选择一个项目,也可以同时选中多个项目。

//Listbox.rc

//>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

#include <resource.h>

//>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

#define ICO_MAIN 0x1000 //图标

#define DLG_MAIN 1

#define IDC_LISTBOX1 101

#define IDC_LISTBOX2 102

#define IDC_SEL1 103

#define IDC_RESET 104

//>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

ICO_MAIN   ICON    "Main.ico"

//>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

DLG_MAIN DIALOG 163, 160, 190, 108

STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU

CAPTION "列表框控件示例"

FONT 9, "宋体"

{

    LISTBOX IDC_LISTBOX1, 6, 5, 55, 86, LBS_STANDARD

    LISTBOX IDC_LISTBOX2, 68, 5, 115, 86, LBS_STANDARD | LBS_MULTIPLESEL

    LTEXT "", IDC_SEL1, 6, 93, 55, 8

    PUSHBUTTON "复位(&R)", IDC_RESET, 89, 90, 45, 14

    DEFPUSHBUTTON "查看(&S)", IDOK, 139, 90, 45, 14, WS_DISABLED

}

 

//Listbox.asm

                .386

                .model flat, stdcall

                option casemap :none

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

; Include 文件定义

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

include         windows.inc

include         user32.inc

includelib      user32.lib

include         kernel32.inc

includelib      kernel32.lib

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

; Equ等值定义

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

ICO_MAIN        equ     1000h

DLG_MAIN        equ     1

IDC_LISTBOX1    equ     101

IDC_LISTBOX2    equ     102

IDC_SEL1        equ     103

IDC_RESET       equ     104

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

; 数据段

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

 

                .data?

hInstance       dd      ?

                .const

szText1         db      '项目1',0

szText2         db      '项目2',0

szText3         db      '项目3',0

szPath          db      '*.*',0

szMessage       db      '选择结果:%s',0

szTitle         db      '您的选择',0

szSelect        db      '您选择了以下的项目:'

szReturn        db      0dh,0ah,0

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

; 代码段

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

                .code

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

_ProcDlgMain    proc    uses ebx edi esi hWnd, wMsg, wParam, lParam

                local   @szBuffer[128]:byte

                local   @szBuffer1[128]:byte

                local   @szTextBuff[2048]:byte

                local   @dwCount

               

                mov     eax, wMsg

                .if     eax == WM_CLOSE

                        invoke EndDialog, hWnd, NULL

                .elseif eax == WM_INITDIALOG

                        invoke LoadIcon, hInstance, ICO_MAIN

                        invoke SendMessage, hWnd, WM_SETICON, ICON_BIG, eax

;********************************************************************************

; 初始化列表框

;********************************************************************************

                        invoke SendDlgItemMessage, hWnd, IDC_LISTBOX1, LB_ADDSTRING, 0, addr szText1

                        invoke SendDlgItemMessage, hWnd, IDC_LISTBOX1, LB_ADDSTRING, 0, addr szText2

                        invoke SendDlgItemMessage, hWnd, IDC_LISTBOX1, LB_ADDSTRING, 0, addr szText3

                       

                        invoke SendDlgItemMessage, hWnd, IDC_LISTBOX2, LB_DIR, DDL_ARCHIVE or DDL_DRIVES or DDL_DIRECTORY, addr szPath

;********************************************************************************

                .elseif eax == WM_COMMAND

                        mov     eax, wParam

                        .if     ax == IDOK

                                invoke SendDlgItemMessage, hWnd, IDC_LISTBOX2, LB_GETSELCOUNT, 0, 0

                                mov @dwCount, eax

                                invoke SendDlgItemMessage, hWnd, IDC_LISTBOX2, LB_GETSELITEMS, 128/4, addr @szBuffer

                                invoke lstrcpy, addr @szTextBuff, addr szSelect

                                lea     esi, @szBuffer

                                .while @dwCount

                                        lodsd

                                        lea     ecx, @szBuffer1

                                        invoke SendDlgItemMessage, hWnd, IDC_LISTBOX2, LB_GETTEXT, eax, ecx

                                        invoke lstrcat, addr @szTextBuff, addr szReturn

                                        invoke lstrcat, addr @szTextBuff, addr @szBuffer1

                                        dec     @dwCount

                                .endw

                                invoke MessageBox, hWnd, addr @szTextBuff, addr szTitle, MB_OK

                        .elseif ax == IDC_RESET

                                invoke SendDlgItemMessage, hWnd, IDC_LISTBOX2, LB_SETSEL, FALSE, -1

                        .elseif ax == IDC_LISTBOX1

                                shr     eax, 16

                                .if     ax == LBN_SELCHANGE

;********************************************************************************

; 将鼠标点击结果显示在文本框中

;********************************************************************************

                                        invoke SendMessage, lParam, LB_GETCURSEL, 0, 0

                                        lea     ecx, @szBuffer

                                        invoke SendMessage, lParam, LB_GETTEXT, eax, ecx

                                        invoke SetDlgItemText, hWnd, IDC_SEL1, addr @szBuffer

;********************************************************************************

; 双击项目则弹出对话框

;********************************************************************************

                                .elseif ax == LBN_DBLCLK

                                        invoke SendMessage, lParam, LB_GETCURSEL, 0, 0

                                        lea     ecx, @szBuffer

                                        invoke SendMessage, lParam, LB_GETTEXT, eax, ecx

                                        invoke wsprintf, addr @szBuffer1, addr szMessage, addr @szBuffer

                                        invoke MessageBox, hWnd, addr @szBuffer1, addr szTitle, MB_OK

                                .endif

;********************************************************************************

                        .elseif ax == IDC_LISTBOX2

                                shr     eax, 16

                                .if     ax == LBN_SELCHANGE

                                        invoke SendMessage, lParam, LB_GETSELCOUNT, 0, 0

                                        mov     ebx, eax

                                        invoke GetDlgItem, hWnd, IDOK

                                        invoke EnableWindow, eax, ebx

                                .endif

                        .endif

                .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

 

程序中总共定义了两个列表框。左边列表框为IDC_LISTBOX1,这是一个单选的列表框,选择一个项目的时候下面的文本会显示出选择的项目,双击某个项目的时候会弹出消息框,显示所选中的项目。右边的列表框是IDC_LISTBOX2,是一个多选的列表框,选择完毕可以用“查看”按钮弹出消息框,消息框中显示了所有选中的项目。按下“复位”按钮清除列表框的选择。

列表框可以使用的风格

风格

说明

LBS_DISABLENOSCROLL

在不需滚动的时候也显示垂直滚动条

LBS_EXTENDEDSEL

在多选列表框中允许按住Shitf键同时选中一个范围

LBS_MULTIPLESEL

允许多选,如果不定义的话则是单选列表框

LBS_NOSEL

列表框项目只能查看不能选择

LBS_NOTIFY

用户点击或双击项目时向父窗口发送WM_COMMAND消息

LBS_SORT

自动按字母顺序排序插入的项目

LBS_USETABSTOPS

列表框项目的文本中允许将Tab字符的位置展开

LBS_STANDARD

组合LBS_NOTIFY, LBS_SORT, WS_VSCROLLWS_BORDER

 

一般单选列表框只需定义LBS_STANDARD就可以了。

 

列表框使用说明:

当列表框有 LBS——NOTIFY风格的时候,用户有所动作时列表框会向父窗口发送WM_COMMAND,同时在wParam的高16位中指定通知码,列表框的通知码种类很少,基本上就是以下几种:

l         LBN_DBLCLK                     用户双击了一个项目。

l         LBN_ERRSPACE                 插入项目时无法申请到足够的内存。

l         LBN_KILLFOCUS        输入焦点被切换到其他控件中,列表框丢失了焦点。

l         LBN_SELCANCEL        用户撤销了一个选择。

l         LBN_SELCHANGE              选定状态改变。

l         LBN_SETFOCUS                 列表框得到输入焦点。

 

 

我们最关心的是LBN_DBLCLKLBN_SELCHANGE通知码,在单选列表框中,如果程序用双击来选择项目,那么就要处理LBN_DBLCLK通知,例子程序中当用户双击IDC_LISTBOX1时弹出一个消息框,读者可以查看其使用方法。在多选列表框中,由于用户可能选择了多个项目,所以一般不用双击的方法选定:如果收到LBN_SELCHANGE通知的话,可以得知用户有一个选择动作,在这里可以进行相应的操作。

 

       列表框通知父窗口是通过发送WM_COMMAND消息,而程序控制列表框的时候是通过向列表框发送消息来完成的。

       常用的列表框消息如下表所示:

消息

wParam

lParam

说明

LB_ADDSTRING

0

字符串地址

添加一个项目,返回加入后的索引。

LB_DELETESTRING

位置索引

0

删除一个项目,返回剩余的项数。

LB_FINDSTRING

开始索引

字符串地址

查找以字符串开头的项目,找到则返回位置索引,未找到则返回LB_ERR

LB_FINDSTRINGEXACT

开始索引

字符串地址

精确查找一个项目,返回值同上。

LB_GETANCHORINGEX

0

0

返回多选列表框多选时的起始位置。

LB_GETCARETINGEX

0

0

多选列表框中的当前焦点项目位置。

LB_GETCOUNT

0

0

返回列表框中的项目总数

LB_GETCURSEL

0

0

返回单选列表框当前选中的项目。

LB_GETSEL

位置索引

0

检测指定项目的选中状态,返回非0为选中,返回0为未选中。

LB_GETSELCOUNT

0

0

返回多选列表框选中项目的总数

LB_GETSELITEMS

最大项数

缓冲区地址

返回多选列表框的选中项目索引列表到缓冲区中

LB_GETTEXT

位置索引

缓冲区地址

返回某个项目的字符串

LB_GETTEXTLEN

位置索引

0

返回某个项目的字符串长度

LB_GETTOPINDEX

0

0

返回当前可见的第一个项目位置

LB_INSERTSTRING

插入位置

字符串地址

在指定位置插入一个项目

LB_RESETCONTENT

0

0

删除所有项目

LB_SELECTSTRING

开始位置

字符串地址

将以指定字符串开头的项目选中

LB_SELITEMRANGE

选择状态

范围

在多选框中将一个范围选中或清除

LB_SETCURSEL

位置索引

0

在单选列表框中选中一个项目

LB_SETSEL

选择状态

位置索引

在多选框中将一个项目选中或清除

LB_SETTOPINDEX

位置索引

0

滚动显示到指定的项目

LB_DIR

属性

文件通配符

搜索目录并将符合文件通配符的文件名加入到列表框中

这些消息中LB_DIR是个比较有趣的消息,它可以将指定目录中的文件名自动列出来并加入列表框中,如例子中用*.*将当前目录中的全部文件名加到列表框中。LB_DIR消息中wParam参数可以指定的属性可以是是以下值的组合:

DDL_ARCHIVE            加入归档属性的文件。

DDL_DIRECTORY       加入目录。

DDL_DRIVES              加入驱动器名。

DDL_HIDDEN             包含隐含文件。

DDL_READONLY        包含只读文件。

DDL_READWRITE      包含可读写的文件。

DDL_SYSTEM             包含系统文件。

 

       在列表框中初始化时加入项目可以使用LB_ADDSTRINGLB_INSERTSTRING消息,删除项目可以用LB_DELETESTRING消息,删除全部项目用LB_RESETCONTENT消息。

       对于单选列表框,要获取选中项目可以发送LB_GETCURSEL消息,要得到这个项目的字符串需要用索引值通过LB_GETTEXT消息获取,读者可以查看例子中处理LBN_DBLCLK通知码的部分代码。

 

       对于多选列表框,需要用LB_GETSELITEMS消息获取全部选中项目,这个消息返回的是一个列表,所有选中项目的索引按顺序排列返回到缓冲区中,所以在例子中处理“查看”按钮消息(IDOK)的时候,程序先发送LB_GETSELCOUNT消息得到选中的项目数,以便在下面用一个循环获取所有的项目,得到数目数后,再用LB_GETSELITEMS将选中项目的索引取到@szBuffer中,接下来进入一个循环,循环的次数就是LB_GETSELCOUNT得到的数值,在循环中,程序从@szBuffer中将索引值逐个取出并用LB_GETTEXT消息获取每一项的字符串,最后用一个MessageBox显示出来。

 

posted on 2010-09-20 09:45 luqingfei 阅读(844) 评论(0)  编辑 收藏 引用 所属分类: Win32汇编程语言序设计


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理


导航

<2010年9月>
2930311234
567891011
12131415161718
19202122232425
262728293012
3456789

统计

留言簿(6)

随笔分类(109)

随笔档案(105)

Blogers

Game

Life

NodeJs

Python

Useful Webs

大牛

搜索

积分与排名

最新评论

阅读排行榜

评论排行榜