ID--HANDLE--HWND三者之间的互相转换

利用PreTranslateMessage,响应按钮控件的按下(WM_LBUTTONDOWN)和松开(WM_LBUTTONUP)安全

 
VC的button控制只有两个事件,一个是单击事件,一个事双击事件。在这个方面VB就方便多了。可是咱们有其余办法解决。首先咱们先学一些基础知识。
 

1...关于PreTranslateMessageide

PreTranslateMessage是消息在送给TranslateMessage函数以前被调用的,绝大多数本窗口的消息都要经过这里,比较经常使用,当你须要在MFC以前处理某些消息时,经常要在这里添加代码.
函数

2...关于MSG结构体
typedef struct tagMSG { // msg
HWND hwnd;
UINT message;
WPARAM wParam;
LPARAM lParam;
DWORD time;
POINT pt;
} MSG;
post

Members
hwnd
Handle to the window whose window procedure receives the message.
message
Specifies the message identifier. Applications can only use the low word; the high word is reserved by the system.
wParam
Specifies additional information about the message. The exact meaning depends on the value of the message member.
lParam
Specifies additional information about the message. The exact meaning depends on the value of the message member.
time
Specifies the time at which the message was posted.
pt
Specifies the cursor position, in screen coordinates, when the message was posted.
spa

3...ID--HANDLE--HWND三者之间的互相转换
id->句柄、、、、、hWnd = ::GetDlgItem(hParentWnd,id);
id->指针、、、、、CWnd::GetDlgItem();
句柄->id、、、、、id = GetWindowLong(hWnd,GWL_ID);
句柄->指针、、、、CWnd *pWnd=CWnd::FromHandle(hWnd);
指针->ID、、、、、id = GetWindowLong(pWnd->GetSafeHwnd,GWL_ID);
指针->句柄、、、、hWnd=cWnd.GetSafeHandle() or mywnd->m_hWnd;
指针

例程:orm

方法1:对象

BOOL AcameraCT::PreTranslateMessage(MSG* pMsg)
{
int buID;
buID= GetWindowLong(pMsg->hwnd,GWL_ID);//由窗口句柄得到ID号,GetWindowLong为得到窗口的ID号。
if(pMsg->message==WM_LBUTTONDOWN)
{
if(buID==IDC_BUTTON_CT1) //按下
{
//在这里添加单击按下事件的程序
}
}
if(pMsg->message==WM_LBUTTONUP)
{
if(buID==IDC_BUTTON_CT1)
{
//在这里添加单击松开事件的程序
}
}
return CDialog::PreTranslateMessage(pMsg);
}
接口

方法2:事件

BOOL AcameraCT::PreTranslateMessage(MSG* pMsg)
{
int buID;
CWnd* pWnd=WindowFromPoint(pMsg->pt); //得到指定点句柄
buID=pWnd->GetDlgCtrlID();//得到该句柄的ID号。
if(pMsg->message==WM_LBUTTONDOWN)
{
if(buID==IDC_BUTTON_CT1) //按下
{
//在这里添加单击按下事件的程序
}
}
if(pMsg->message==WM_LBUTTONUP)
{
if(buID==IDC_BUTTON_CT1)
{
//在这里添加单击松开事件的程序
}
}
return CDialog::PreTranslateMessage(pMsg);

}

VC_HWND和CWND的概念以及转换

下面先说下HWMD的概念,我也不是很理解,应该是SDK接口的概念,并无实际对象操做的地址空间。

它只是一个32bit的无符号整型数值,表明了句柄号handle

摘自网上的理论:

HWND是Windows系统中对全部窗口的一种标识,即窗口句柄。这是一个SDK概念。

CWnd是MFC类库中全部窗口类的基类。微软在MFC中将全部窗口的通用操做都封装到了这个类中,如:ShowWindow等等,同时它也封装了窗口句柄即m_hWnd成员。

 

由HWnd获得CWnd*:

CWnd wnd;

HWnd hWnd;

wnd.Attach(hWnd);

一般一个窗口资源已经和一个CWnd类的对象关联起来的,因为通常来讲这个类是本身建立的,因此天然知道怎么获得指向这个类的指针。若是没有就建立一个CWnd对象,将这个对象与窗口资源的hWnd句柄关联起来。(如上边的语句)。若是用

static CWnd* CWnd::FromHandle(HWND hWnd) ;

则返回值是一个暂时的CWnd对象,而且咱们确保返回值为非空,也就是hWnd是有效的。

static CWnd* CWnd::FromHandlePermanent(HWND hWnd) ;

返回的是一个永久的对象。只有在返回的CWnd在类表里已经存在是返回值为非空。

 

由CWnd获取HWnd就容易多了,由于它的一个成员m_hWnd就是所对应窗口的句柄。

wnd->m_hWnd。

——————————————————————————————————————————————————————————

 

CWnd* 和 HWND 差异很大

 

HWND 是 SDK 定义的类型, 是一个无确切意义的 32-bit 值,在调用 API 时用于指代窗体。

 

CWnd* 是一个有确切意义的指针,指向一个 MFC 窗体类 CWnd 的实例。由于 MFC 对 SDK 作了封装,大部分调用均可以用 CWnd* 做为参数,因此很容易混淆。从一个 CWnd* 获取句柄的方法是 pWnd->GetSafeHwnd(), 他比 pWnd->m_hWnd 安全,由于前者在 pWnd == NULL 的时候返回 NULL 然后者出现 access violation

 

从 hWnd 转换到 CWnd * 一个可使用的方法是 CWnd::FromHandle

CWnd *pTempWnd = CWnd::FromHandle(hWnd); // 若是 hWnd 存在对应的 CWnd* ,则返回其指针,不然,建立一个 MFC 临时窗体并返回其指针。

注意这个函数会返回临时窗体的指针,若是须要更安全,调用 CWnd::FromHandlePermanent ,他在不存在对应的 CWnd* 时返回 NULL。

 

——————————————————————————————————————————————————————————

 

CWnd是MFC的窗口基类。 HWND是Windows窗口句柄。前者是一个C++对象,后者是一个相似于指针地址的数字型对象。

CWnd能够当作是对Windows窗口操做的封装,而封装的核心就是使用Windows窗口句柄(即HWND)来操做窗口.

 

CWnd能够经过CWnd::GetSafeHwnd()或成员变量m_hWnd来得到该窗口对象的HWND窗口句柄。

HWND能够经过CWnd的静态函数:CWnd::FromHandle()由句柄实例化一个CWnd对象出来。

 

如下是本身VC6.0上编译的状况,验证了以上的理论

CWnd* mark1;mark1=FindWindow(NULL,"TEST");//TEST是个人当前实例窗口的title

 

//从CWND*转换成HWND

 

HWND tmp=mark1->GetSafeHwnd(); //获得它的HWND

相关文章
相关标签/搜索