12 Windows编程——子窗口和系统内置窗口类“BUTTON”
创建子窗口类,使得子窗口有自己的处理过程。
子窗口类型WS_CHILD不能和WS_POPUP一起使用!
为什么子窗口要有自己的处理过程?
如果使用主窗口类来创建子窗口,那么子窗口和主窗口将公用窗口处理过程,此时,窗口处理过程在进行消息处理的时候,必须判断是哪个窗口的消息,非常不方便。
子窗口必须有自己的窗口类型WSCHILD,并且子窗口的父窗口句柄一定不能使NULL,子窗口的坐标主窗口的映射方式和客户区有关。否则CreateWindow函数就会失败。
客户定制消息:WL_USER+N,其中N可以是0x7FFF-WM_USER之间的任何值。发送窗口消息的函数:
SendMessage
LRESULT WINAPI SendMessage(
_In_ HWND hWnd,
_In_ UINT Msg,
_In_ WPARAM wParam,
_In_ LPARAM lParam
);
将指定的消息发送到一个或多个窗口。此函数为指定的窗口调用窗口程序,直到窗口程序处理完消息再返回。和函数PostMessage不同,PostMessage是将一个消息寄送到一个线程的消息队列后就立即返回。
hWnd: 发送消息的目标窗口;
Msg: WMXXX消息;
wParam: 用户自定义的一个32位值;
1param: 用户自定义的一个32为值;
COLORREF SetBkColor(
HDC hdc,
COLORREF color
);
用指定的颜色值来设置当前的背景色,如果指定的颜色值超出了当前设备的表示范围,则设置为最近似的、设备可以表示的颜色。
改变窗口位置
BOOL WINAPI SetWindowPos(
_In_ HWND hWnd,
_In_opt_ HWND hWndInsertAfter,
_In_ int X,
_In_ int Y,
_In_ int cx,
_In_ int cy,
_In_ UINT uFlags
);
- HWND_BOTTOM:值为1,将窗口置于Z序的底部。如果参数hWnd标识了一个顶层窗口,则窗口失去顶级位置,并且被置在其他窗口的底部。
- HWND_NOTOPMOST:值为-2,将窗口置于所有非顶层窗口之上(即在所有顶层窗口之后)。如果窗口已经是非顶层窗口则该标志不起作用。
- HWND_TOP:值为0,将窗口置于Z序的顶部。
- HWND_TOPMOST:值为-1,将窗口置于所有非顶层窗口之上。即使窗口未被激活窗口也将保持顶级位置。
X:以客户坐标指定窗口新位置的左边界。
Y:以客户坐标指定窗口新位置的顶边界。
cx:以像素指定窗口的新的宽度。
cy:以像素指定窗口的新的高度。
uFlags:窗口尺寸和定位的标志。
改变指定窗口的属性
LONG WINAPI SetWindowLong(
_In_ HWND hWnd,
_In_ int nIndex,
_In_ LONG dwNewLong
);
hwnd: 窗口句柄;
nIndex: 要改变窗口的那个参数;
dwNewLong: 窗口参数的新值;
获取窗口类信息
BOOL WINAPI GetClassInfo(
_In_opt_ HINSTANCE hInstance,
_In_ LPCTSTR lpClassName,
_Out_ LPWNDCLASS lpWndClass
);
hInstance: 当前程序的基地址,也就是程序的句柄;
1pclassName: 类名;
1pwndclass: 指向 WNDCLASS类型的指针;
画矩形
BOOL Rectangle(
HDC hdc,
int left,
int top,
int right,
int bottom
);
画一个矩形,可以用当前的画笔画矩形轮廓,用当前画刷进行填充。
获得当前程序基地址,或者HINSTANCE的函数:GetModuleHandle(NULL);
系统内置的窗口类型“BUTTON”
WL_COMMAND消息:
wParam:
lparam:
不使用子窗口类创建一个按钮,点击按钮按钮会变色,源码
//#define _AFXDLL
//#include<afx.h>
#include<Windows.h>
#include<tchar.h> #ifndef _AFXDELL
#define TRACE(a,b)
#endif LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); int WinMain(HINSTANCE hInst, HINSTANCE tmp, LPSTR szCmd, int nShow)
{
WNDCLASS WndClass;
TCHAR* ClassName = TEXT("MyClass");
HWND hwnd;
MSG msg;
HBRUSH hBrush; hBrush = CreateSolidBrush(RGB(,,));
WndClass.cbClsExtra = ;
WndClass.cbWndExtra = ;
WndClass.hbrBackground = hBrush;
WndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
WndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
WndClass.hInstance = hInst;
WndClass.lpfnWndProc = WindProc;
WndClass.lpszClassName = ClassName;
WndClass.lpszMenuName = NULL;
WndClass.style = CS_VREDRAW | CS_HREDRAW; RegisterClass(&WndClass);
hwnd = CreateWindow(ClassName, TEXT("Hello"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, , , NULL, NULL, hInst, NULL);
ShowWindow(hwnd, nShow);
UpdateWindow(hwnd); while (GetMessage(&msg, NULL, , ))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return ;
}
LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
HDC hdc;
PAINTSTRUCT pt;
HBRUSH hBrush;
static int status;
switch (message)
{
case WM_CREATE:
return ;
case WM_SIZE:
return ;
case WM_PAINT:
hdc = BeginPaint(hwnd, &pt);
if(status == )
{
hBrush = CreateSolidBrush(RGB(, , ));
SelectObject(hdc, hBrush);
Rectangle(hdc, , , , );
SetBkColor(hdc, RGB(, , ));
TextOut(hdc, , , TEXT("OK"), );
TextOut(hdc, , , TEXT("Hit me!"), );
}
else
{
hBrush = CreateSolidBrush(RGB(, , ));
SelectObject(hdc, hBrush);
Rectangle(hdc, , , , );
SetBkColor(hdc, RGB(, , ));
TextOut(hdc, , , TEXT("OK"), );
TextOut(hdc, , , TEXT("Hit me!"), );
}
EndPaint(hwnd, &pt);
return ;
case WM_LBUTTONDOWN:
if (LOWORD(lParam)> && LOWORD(lParam)< && HIWORD(lParam)< && HIWORD(lParam)>)
{
status = ;
InvalidateRect(hwnd, NULL,TRUE);
}
return ;
case WM_LBUTTONUP:
InvalidateRect(hwnd, NULL,TRUE);
status = ;
return ;
case WM_DESTROY:
PostQuitMessage();
return ;
default:
break;
} return DefWindowProc(hwnd, message, wParam, lParam);
}
使用子窗口创建按钮
.h
//#pragma once
//#define _AFXDLL
//#include<afx.h>
#include<Windows.h>
#include<tchar.h> #ifndef _AFXDELL
#define TRACE(a,b)
#endif HWND CreateChild(HWND ParentHwnd, int x, int y, int cx, int cy);
extern HINSTANCE G_hInst;
.c
#include"1.h"
HINSTANCE G_hInst;
LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); int WinMain(HINSTANCE hInst, HINSTANCE tmp, LPSTR szCmd, int nShow)
{
WNDCLASS WndClass;
TCHAR* ClassName = TEXT("MyClass");
HWND hwnd;
MSG msg;
HBRUSH hBrush; hBrush = CreateSolidBrush(RGB(,,));
G_hInst = hInst;
WndClass.cbClsExtra = ;
WndClass.cbWndExtra = ;
WndClass.hbrBackground = hBrush;
WndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
WndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
WndClass.hInstance = hInst;
WndClass.lpfnWndProc = WindProc;
WndClass.lpszClassName = ClassName;
WndClass.lpszMenuName = NULL;
WndClass.style = CS_VREDRAW | CS_HREDRAW; RegisterClass(&WndClass);
hwnd = CreateWindow(ClassName, TEXT("Hello"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, , , NULL, NULL, hInst, NULL);
ShowWindow(hwnd, nShow);
UpdateWindow(hwnd); while (GetMessage(&msg, NULL, , ))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return ;
}
LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
HDC hdc;
PAINTSTRUCT pt;
HBRUSH hBrush;
static int status;
static HWND child1,child2,child3;
TCHAR buf[];
switch (message)
{
case WM_CREATE:
child1 = CreateChild(hwnd, , , , );
child2 = CreateChild(hwnd, , , , );
child3 = CreateChild(hwnd, , , , );
return ;
case WM_SIZE:
return ;
case WM_PAINT:
hdc = BeginPaint(hwnd, &pt);
EndPaint(hwnd, &pt);
return ;
case WM_USER+:
hdc = GetDC(hwnd);
if((LPARAM)child1==lParam)
{
TextOut(hdc,,,TEXT("Hit First button"),);
}
if((LPARAM)child2==lParam)
{
TextOut(hdc,,,TEXT("Hit Second button"),);
}
if((LPARAM)child3==lParam)
{
TextOut(hdc,,,TEXT("Hit Third button"),);
}
ReleaseDC(hwnd, hdc);
ValidateRect(hwnd, NULL);
return ;
case WM_USER + :
InvalidateRect(hwnd, NULL, TRUE);
return ;
case WM_DESTROY:
PostQuitMessage();
return ;
default:
break;
} return DefWindowProc(hwnd, message, wParam, lParam);
}
.c
#include"1.h"
extern HINSTANCE G_hInst;
static LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); HWND CreateChild(HWND ParentHwnd, int x, int y, int cx, int cy)
{
WNDCLASS WndClass,MyWnd;
TCHAR* ClassName = TEXT("MyChild");
HWND hwnd;
MSG msg;
HBRUSH hBrush; hBrush = CreateSolidBrush(RGB(, , ));
WndClass.cbClsExtra = ;
WndClass.cbWndExtra = ;
WndClass.hbrBackground = hBrush;
WndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
WndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
WndClass.hInstance = G_hInst;
WndClass.lpfnWndProc = WindProc;
WndClass.lpszClassName = ClassName;
WndClass.lpszMenuName = NULL;
WndClass.style = CS_VREDRAW | CS_HREDRAW; if (!GetClassInfo(G_hInst,ClassName,&MyWnd))
{
RegisterClass(&WndClass);
} hwnd = CreateWindow(ClassName, TEXT("OK"), WS_CHILD, x, y, cx, cy, ParentHwnd, NULL, G_hInst, NULL);
ShowWindow(hwnd, SW_SHOW);
UpdateWindow(hwnd); //GetMessage第二个参数为NULL时,会获取所有消息。因为父窗口已经获取消息了,所以没必要再获取了
/*while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}*/
return hwnd;
} LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
HDC hdc;
PAINTSTRUCT pt;
HBRUSH hBrush;
static int status;
static int cx,cy; switch (message)
{
case WM_CREATE:
return ;
case WM_SIZE:
cx=LOWORD(lParam);
cy=HIWORD(lParam);
return ;
case WM_PAINT:
hdc = BeginPaint(hwnd, &pt);
//TRACE(TEXT("status=%d\n"),status);
if (status == )
{
hBrush = CreateSolidBrush(RGB(, , ));
SelectObject(hdc, hBrush);
Rectangle(hdc, , , cx,cy);
SetBkColor(hdc, RGB(, , ));
TextOut(hdc, ,, TEXT("OK"), );
}
else
{
hBrush = CreateSolidBrush(RGB(, , ));
SelectObject(hdc, hBrush);
Rectangle(hdc, , , cx,cy);
SetBkColor(hdc, RGB(, , ));
TextOut(hdc, ,, TEXT("OK"), );
}
EndPaint(hwnd, &pt);
return ;
case WM_LBUTTONDOWN:
{
status = ;
InvalidateRect(hwnd, NULL, TRUE);
SendMessage(hwnd,WM_PAINT,NULL,NULL);
SendMessage(GetParent(hwnd), WM_USER + , NULL,(LPARAM)hwnd); }
return ;
case WM_LBUTTONUP:
status = ;
InvalidateRect(hwnd, NULL, TRUE);
SendMessage(GetParent(hwnd), WM_USER + , NULL,NULL);
return ;
case WM_DESTROY:
PostQuitMessage();
return ;
default:
break;
} return DefWindowProc(hwnd, message, wParam, lParam);
}
还可以使用WIndows自身的button控件
#include<Windows.h>
#include<Windowsx.h> LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam); int WinMain(HINSTANCE hInst, HINSTANCE tmp, LPSTR szCmd, int nShow)
{
WNDCLASS WndClass;
TCHAR* ClassName = TEXT("MyClass");
HWND hwnd;
MSG msg; WndClass.cbClsExtra = ;
WndClass.cbWndExtra = ;
WndClass.hbrBackground = (HBRUSH)(COLOR_WINDOW + );
WndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
WndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
WndClass.hInstance = hInst;
WndClass.lpfnWndProc = WindProc;
WndClass.lpszClassName = ClassName;
WndClass.lpszMenuName = NULL;
WndClass.style = CS_VREDRAW | CS_HREDRAW; if (!RegisterClass(&WndClass))
{
MessageBox(NULL, TEXT("Gegister Class Fail!!"), TEXT("error"), MB_OK);
return ;
} hwnd = CreateWindow(ClassName, TEXT("Hello"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, , , NULL, NULL, hInst, NULL);
if (hwnd == NULL)
{
MessageBox(NULL, TEXT("Create Window Fail!!"), TEXT("error"), MB_OK);
return ;
}
ShowWindow(hwnd, nShow);
UpdateWindow(hwnd); while (GetMessage(&msg, NULL, , ))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
} return ;
} LRESULT CALLBACK WindProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
HDC hdc;
static HWND button;
switch (message)
{
case WM_CREATE:
button = CreateWindow(TEXT("button"), TEXT("OK"), WS_CHILD | WS_VISIBLE, , , , , hwnd, NULL, GetModuleHandle(NULL), NULL);
//禁用按钮,按钮变灰色
//Button_Enable(button, FALSE);
Button_SetText(button,TEXT("测试"));
return ;
case WM_COMMAND:
hdc = GetDC(hwnd);
if (button == (HWND)lParam)
{
TextOut(hdc, , , TEXT("Hit Button"), );
}
if (BN_CLICKED == HIWORD(wParam)) //测试控件通知码
{
TextOut(hdc, , , TEXT("BN_CLICKED Hit Button"), );
}
ReleaseDC(hwnd, hdc);
ValidateRect(hwnd, NULL);
case WM_DESTROY:
PostQuitMessage();
return ;
default:
break;
} return DefWindowProc(hwnd, message, wParam, lParam);
}
HIWORD(wParam)控件通知码
LOWORD(wParam)控件标识
lParam控件的窗口句柄
12 Windows编程——子窗口和系统内置窗口类“BUTTON”的更多相关文章
- windows 服务管理器使用系统内置帐户时密码的输入
windows 服务管理器使用系统内置帐户时在选择帐户如network services后不需要输入密码,直接确认即可,系统会自动附加密码.
- windows 编程 —— 子窗口 与 子窗口控件
目录: 子窗口与主窗口的交互 子窗口控件 按钮类别 button 滚动条类别 scrollbar 静态类别 static 编辑框类别 edit 清单方块 listbox 子窗口与主窗口的交互 创建窗 ...
- windows 编程 —— 子窗口类别化(Window Subclassing)
对于子窗口控件,有时我们可能会想要获取子窗口的某些消息,比如在一个主窗口下有三个按钮,如果想要实现使用键盘Tab或者Shift-Tab键来使焦点切换于不同按钮之间,这时就可以使用子窗口类别化(Wind ...
- 【Windows编程】入门篇——win 32窗口的hello word!
✍ Windows编程基础 1.Win 32应用程序基本类型 1) 控制台程序 不需要完善的windows窗口,可以使用DOS窗口方式显示 2) Win 32窗口程序 包含窗口的程序,可以通过窗 ...
- 16 Windows编程——系统内置窗口子类型之edit、ComboBox、ownerbutton、listbox
edit类型的子窗口 ES_MULTILINE:多行输入文本框 窗口的消息: WL_COMMAND: EN_CHANGE:当edit窗口内的文本内容改变的时候,edit子窗口给父窗口发送一个WL_CO ...
- 13 Windows编程——系统内置窗口子类型之静态子窗口
静态子窗口类型 wndclass:static 源码 #include<Windows.h> #include<Windowsx.h> HINSTANCE G_h; LRESU ...
- 15 Windows编程——系统内置窗口子类型之button
button子类型BS_3STATE.BS_AUTO3STATE.BS_AUTOCHECKBOX 源码 #include<Windows.h> #include<Windowsx.h ...
- [Windows编程] 使用AttachThreadInput 来捕捉其它窗口的键盘输入
在一些情况下(比如屏幕软键盘或者输入法程序),自己的窗口没有输入焦点但是想要当前焦点窗口的键盘输入消息,可以使用Win32 API函数AttachThreadInput()来解决这个问题.Attach ...
- 走进windows编程的世界-----对话框、文本框、button
1 对话框的分类 2 对话框的基本使用方式 3 对话框资源 4 有模式对话框的使用 int DialogBox( HINSTANCE hInstance, LPCTSTR lpTemplate, ...
随机推荐
- Linux下通过shell进MySQL执行SQL或导入脚本
这条命令表示通过用户名和密码执行shell然后在shell里面执行一个建表语句: USER="root" PASS="root" mysql -u $USER ...
- git推送远程仓库以及分支介绍
1.介绍 我们要把本地仓库的项目推送到远程服务器,首先我们得有自己的服务器,一般我们选择码云和github,码云和github的操作差不多,今天我们再次介绍码云的使用 2.码云的使用 第一步:首先我们 ...
- 使用SWO代替UART,实现Printf打印功能
JTAG接口中,有个SWO引脚,一直没有在意,也没有去研究过是干嘛用的.直到发现ST-LINK V2-1上也有个SWO引脚,于是去研究学习它的作用,用起来相比UART方得便多. 本文内容已经整理成PD ...
- 区块链学习(四)truffle部署编译智能合约以太坊私有链
前面我们介绍了以太坊私有链的搭建以及多节点私有链网络,这次我们介绍如何使用truffle框架来部署编译智能合约到我们之前搭建的私有链网络中. 搭建环境及需使用的工具:ubuntu18.04 Truf ...
- 日常工作问题解决:rhel7下使用teamd配置双网卡绑定
目录 1.情景描述 2.准备工作 2.1 确认网卡信息 2.2 删除原有网卡配置信息 3.配置网卡绑定 3.1 配置千兆网卡双网卡热备用作心跳 3.2 配置网兆网卡双网卡负载均衡用作业务 1.情景描述 ...
- kolla安装Queens版本OpenStack(ceph后端)
OpenStack all-in-one部署: 本次部署为OpenStack Queens版本部署,使用All-in-one,单节点部署. 物理资源:8核,32GB,硬盘400GB(3个盘),2网卡. ...
- stub_status监控Nginx使用情况!
stub_status监控Nginx使用情况! 查看nginx安装的模块! # /usr/local/nginx/sbin/nginx -V nginx version: nginx/1.8.1 bu ...
- mq 探究
一 mq简介(message queue) 消息队列技术是分布式应用间交互信息的一种技术. 消息队列可驻留在内存或磁盘上,队列存储消息直到它们被应用程序读走 通过消息队列,应用程序可独立地执行-它们不 ...
- javaIO -- 流的体系设计思路、基础分类
一.流 1. 流的含义 在程序设计中,流是对于数据流动传输的一种抽象描述任何有能力产出数据的数据源,或者有能力接受数据的接收端对象都是一个流. 2. 流的源和目的 数据可能从本地文件读取,或者写入, ...
- 【坑】springMvc 信息校验,读取不到错误配置信息的问题
文章目录 前言 ResourceBundleMessageSource 后记 前言 springMvc 的一大利器,validation 检验,通过注解,可以帮我们完成校验,很是顺手. 终极偷懒检验, ...