Win32控件的创建

控件是指对数据和方法的封装。控件可以有自己的属性和方法,其中属性是控件数据的简单访问者,方法则是控件的一些简单而可见的功能、控件创建过程包括设计、开发、调试(就是所谓的3Ds开发流程,即Design、Develop、Debug)工作, 然后是控件的使用。

总体框架如下,控件代码在WM_COMMAND中替换

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
#include <Windows.h>
#include <tchar.h>
#include "resource.h"

BOOL CALLBACK DlgProc(
HWND hWnd,
UINT uMessage,
WPARAM wParam,
LPARAM lParam
) {
switch (uMessage)
{
case WM_COMMAND:
switch (LOWORD(wParam))
{
case IDC_BUTTON1:
{
//以下内容全部在此处替换

}
break;
}
break;
case WM_CLOSE:
EndDialog(hWnd, 0);
break;
default:
break;
}
return 0;
}

INT WINAPI _tWinMain(
HINSTANCE hInstance,
HINSTANCE hPreInstance,
LPTSTR szCmd,
int nShow
) {
DialogBox(
hInstance,
MAKEINTRESOURCE(IDD_DIALOG1),
NULL,
(DLGPROC)DlgProc
);
return 0;
}

复选框

获取被选中的复选框

1
2
3
4
5
6
7
8
9
10
11
12
//检查被选中的复选框
HWND hCheck1 = GetDlgItem(hWnd, IDC_CHECK1);
HWND hCheck2 = GetDlgItem(hWnd, IDC_CHECK2);
BOOL bCheck = 0;
bCheck = SendMessage(hCheck1, BM_GETCHECK, 0, 0);
if (bCheck == TRUE) {
MessageBox(0, _T("选择了第一个对话框"), 0, 0);
}
bCheck = SendMessage(hCheck2, BM_GETCHECK, 0, 0);
if (bCheck == TRUE) {
MessageBox(0, _T("选择了第二个对话框"), 0, 0);
}

复选框1

设置复选框被选中

1
2
3
4
5
//设置复选框被选中
HWND hCheck1 = GetDlgItem(hWnd, IDC_CHECK1);
HWND hCheck2 = GetDlgItem(hWnd, IDC_CHECK2);
SendMessage(hCheck1, BM_SETCHECK, 1, 0);
SendMessage(hCheck2, BM_SETCHECK, 1, 0);

复选框2

单选框

1
2
3
4
5
6
7
8
9
10
11
HWND hRadio1 = GetDlgItem(hWnd, IDC_RADIO1);
HWND hRadio2 = GetDlgItem(hWnd, IDC_RADIO2);
BOOL bCheck = 0;
bCheck = SendMessage(hRadio1, BM_GETCHECK, 0, 0);
if (bCheck == TRUE) {
MessageBox(0, _T("选择了第一个选项"), 0, 0);
}
bCheck = SendMessage(hRadio2, BM_GETCHECK, 0, 0);
if (bCheck == TRUE) {
MessageBox(0, _T("选择了第二个选项"), 0, 0);
}

单选框1

单选框时有一个问题,对于所有的Radio选项,只有一个组,如果需要用到两组就会出现问题。所以我们需要将Radio分组:

ctrl+d 令同一组的Radio序号连续

单选框2

每一组的第一个Radio的Group属性设置为True,就可以完成分组

单选框3

静态图片

拖拽一个Picture Control控件,修改Type为Bitmap

静态图片1

添加资源,导入Bitmap(这里不能用QQ截图后保存的图片,应该使用画图中的256色位图bmp类型的图片)

静态图片2

添加时要把文件类型改成所有文件,否则找不到图片

注意要修改pic控件的控件ID,默认的IDC_STATIC会报错

1
2
3
4
HINSTANCE hInstance = GetModuleHandle(NULL);
HWND hPicture = GetDlgItem(hWnd, IDC_STATIC1);
HBITMAP hBitmap = LoadBitmap(hInstance, MAKEINTRESOURCE(IDB_BITMAP1));
SendMessage(hPicture, STM_SETIMAGE, IMAGE_BITMAP, (LPARAM)hBitmap);

静态图片3

下拉框(ComboBox)

要修改下拉框高度应修改倒三角的高度

下拉框1

1.添加选项

1
2
3
4
5
6
7
8
9
10
11
TCHAR Buf[10][10] = {
_T("天安门"),
_T("故宫"),
_T("西二旗"),
_T("五道口"),
_T("大望路")
};
HWND hCombo = GetDlgItem(hWnd, IDC_COMBO1);
for (int i = 0; i < 5; i++) {
ComboBox_AddString(hCombo, Buf[i]); //需要包含windowsx.h
}

2.获取选项

1
2
3
4
5
6
7
8
9
HWND hCombo = GetDlgItem(hWnd, IDC_COMBO1);
int n = ComboBox_GetCurSel(hCombo); //获取位置
TCHAR szNum[10] = { 0 };
wsprintf(szNum, _T("%d"), n);
MessageBox(0, szNum, 0, 0);

TCHAR szText[10] = { 0 };
ComboBox_GetText(hCombo, szText, 10); //获取值
MessageBox(0, szText, 0, 0);

下拉框2

进度条

进度条控件Progress Control

1
2
3
4
5
6
7
static int n = 0;
HWND hProcess = GetDlgItem(hWnd, IDC_PROGRESS1);
SendMessage(hProcess, PBM_SETPOS, n, 0); //需包含CommCtrl.h
n += 5;
if (n >= 100) {
n = 0;
}

进度条

滑块

滑块控件Slider Control

滑块在被拖动的时候,会给父窗口发送WM_HSCROLL消息或WM_VSCROLL消息

滑块1

检测滑块位置:

1
2
3
HWND hSlider = GetDlgItem(hWnd, IDC_SLIDER1);
//需包含CommCtrl.h
int nLoc = SendMessage(hSlider, TBM_GETPOS, 0, 0);

nLoc中保存的即为滑块的值

设置滑块位置:

1
2
3
4
5
HWND hSlider = GetDlgItem(hWnd, IDC_SLIDER1);
//需包含CommCtrl.h
int nLoc = SendMessage(hSlider, TBM_GETPOS, 0, 0);
//获取滑块位置,+5再设置回去
SendMessage(hSlider, TBM_SETPOS, TRUE, nLoc + 5);

滑块2

列表框控件

列表框控件List Control

设置View设置为Report

列表框

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
//添加字段名
LVCOLUMN lc = { 0 };
HWND hList = GetDlgItem(hWnd, IDC_LIST1);
//设置启用的字段
lc.mask = LVCF_FMT | LVCF_WIDTH | LVCF_TEXT;
lc.fmt = LVCFMT_LEFT;
lc.cx = 100;
lc.pszText = (LPWSTR)_T("姓名");
ListView_InsertColumn(hList, 0, &lc);
lc.pszText = (LPWSTR)_T("年龄");
ListView_InsertColumn(hList, 1, &lc);
lc.pszText = (LPWSTR)_T("性别");
ListView_InsertColumn(hList, 2, &lc);
lc.pszText = (LPWSTR)_T("身高");
ListView_InsertColumn(hList, 3, &lc);

//插入行
LVITEM li = {};
hList = GetDlgItem(hWnd, IDC_LIST1);
li.mask = LVIF_TEXT;
li.pszText = (LPWSTR)_T("小明");
li.iItem = 0;
ListView_InsertItem(hList, &li);
//设置单元格文本
ListView_SetItemText(hList, 0, 1, (LPWSTR)_T("18"));
ListView_SetItemText(hList, 0, 2, (LPWSTR)_T("男"));
ListView_SetItemText(hList, 0, 3, (LPWSTR)_T("175"));
//插入第二行
li.pszText = (LPWSTR)_T("小红");
li.iItem = 1;
ListView_InsertItem(hList, &li);
ListView_SetItemText(hList, 1, 1, (LPWSTR)_T("20"));
ListView_SetItemText(hList, 1, 2, (LPWSTR)_T("女"));
ListView_SetItemText(hList, 1, 3, (LPWSTR)_T("160"));

//删除一行
hList = GetDlgItem(hWnd, IDC_LIST1);
ListView_DeleteItem(hList, 1);

附加内容:

1
2
3
//修改hList为整行选中
HWND hList = GetDlgItem(hWnd, IDC_LIST1);
ListView_SetExtendedListViewStyle(hList, LVS_EX_FULLROWSELECT | LVS_EX_GRIDLINES);

列表框1

处理List_View的WM_NOTIFY消息:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
case WM_NOTIFY:
{
switch (wParam)
{
case IDC_LIST1:
{
NMHDR* pNm = (NMHDR*)lParam;
if (pNm->code == NM_RCLICK) //右键单击
{
TCHAR Buf[10] = {};
LPNMITEMACTIVATE lpnmitem = (LPNMITEMACTIVATE)lParam;
//HWND hList = GetDlgItem(hWnd, IDC_LIST1);
HWND hList = lpnmitem->hdr.hwndFrom;//发送消息的控件句柄
ListView_GetItemText(
hList,
lpnmitem->iItem,
lpnmitem->iSubItem,
Buf,
10
);
MessageBox(0, Buf, 0, 0);
}
}
break;
default:
break;
}
}
break;

列表框2