class CFindWnd {
private:
//////////////////
// This private function is used with EnumChildWindows to find the child
// with a given class name. Returns FALSE if found (to stop enumerating).
//
static BOOL CALLBACK FindChildClassHwnd(HWND hwndParent, LPARAM lParam) {
CFindWnd *pfw = (CFindWnd*)lParam;
HWND hwnd = FindWindowEx(hwndParent, NULL, pfw->m_classname, NULL);
if (hwnd) {
pfw->m_hWnd = hwnd; // found: save it
return FALSE; // stop enumerating
}
EnumChildWindows(hwndParent, FindChildClassHwnd, lParam); // recurse
return TRUE; // keep looking
}
public:
LPCSTR m_classname; // class name to look for
HWND m_hWnd; // HWND if found
// ctor does the work--just instantiate and go
CFindWnd(HWND hwndParent, LPCSTR classname)
: m_hWnd(NULL), m_classname(classname)
{
FindChildClassHwnd(hwndParent, (LPARAM)this);
}
};
该类来自于MSDN Magazine -- August 2003。
用法:CFindWnd fw(hwndParent,classname);
fw.m_hWnd就是你要找到的窗口句柄。如果目标窗口是顶层窗口,则hwndParent填为NULL.
某些情况下,如果说你要找到一个对话框框中的密码框,那么该对话框中可能有多个Edit。
用该类显然不能满足要求。
很多情况下,我们要找到一个对话框中的所有Edit,怎么办呢?
因此,我按照他的思想,来定制了一个类。
#include <vector>
using namespace std;
class CFindWndEx {
private:
//////////////////
// This private function is used with EnumChildWindows to find the child
// with a given class name. Returns FALSE if found (to stop enumerating).
//
static BOOL CALLBACK FindChildClassHwnd(HWND hwndParent, LPARAM lParam)
{
CFindWndEx *pfw = (CFindWndEx*)lParam;
//判断该窗口
char sClassName[1024]={0};
::GetClassName(hwndParent,sClassName,sizeof(sClassName)-1);
if(strcmp(sClassName,pfw->m_classname)==0)
{//本窗口!
pfw->m_listWnd.push_back(hwndParent);
}
HWND hwnd = ::GetWindow(hwndParent,GW_CHILD);//第一个子窗口
while(hwnd)
{
if(::GetWindow(hwnd,GW_CHILD))
{//如果具有子窗口
FindChildClassHwnd(hwnd, lParam); // 递归到该窗口下所有窗口
}
else
{//如果非子窗口
::GetClassName(hwnd,sClassName,sizeof(sClassName)-1);
if(strcmp(sClassName,pfw->m_classname)==0)
{//该窗口!
pfw->m_listWnd.push_back(hwnd);
}
}
hwnd = ::GetWindow(hwnd,GW_HWNDNEXT);//下一个子窗口
}
return TRUE; // keep looking
}
public:
vector<HWND> m_listWnd;
public:
LPCSTR m_classname; // class name to look for
HWND m_hWnd; // HWND if found
// ctor does the work--just instantiate and go
CFindWndEx(HWND hwndParent, LPCSTR classname)
: m_hWnd(NULL), m_classname(classname)
{
m_listWnd.clear();
if(!hwndParent)
{//所有顶层窗口
HWND hwnd = ::FindWindow(m_classname,NULL);//第一个子窗口
while(hwnd)
{
FindChildClassHwnd(hwnd, (LPARAM)this);
hwnd=::GetWindow(hwnd,GW_HWNDNEXT);
}
}
else
{
FindChildClassHwnd(hwndParent, (LPARAM)this);
}
TRACE("Start=======================>\n");
int nWndCount=m_listWnd.size();
for(int n=0;n<nWndCount;n++)
{
TRACE("Index:%d\tHWND:%x\n",n,m_listWnd[n]);
}
TRACE("End=========================>\n");
}
};
用法:CFindWnd fw(hwndParent,classname);
fw.m_listWnd就是目标的所有窗口列表。
如果你要得到密码框,你可以遍历,一个一个取属性后得到。
如果有任何疑问,欢迎指出。