我需要使用C ++,Win API在鼠标点击上设置一个钩子。因此,当点击桌面上的图标时,我会收到该事件。这会怎么样?我认为我在鼠标钩子事件中获得的唯一信息是鼠标的坐标,对吧?现在,我如何确保点击的内容是桌面上的图标?
答案 0 :(得分:1)
在DLL中实现鼠标钩子并使用SetWindowsHookEx()为仅在桌面窗口管理的线程安装钩子。使用GetDesktopWindow()和GetWindowThreadProcessId()来获取该线程ID。然后,无论何时触发钩子,钩子都会告诉您用户正在单击哪个窗口,以及正在执行哪个鼠标操作。使用GetClassName()来确定触发钩子的窗口是否是ListView,如果是,则使用ListView API在提供的鼠标坐标处查询窗口中的图标信息。
答案 1 :(得分:0)
在MSDN上检出Microsoft Active Accessibility和SetWinEventHook。 我认为你可以有效地使用它们来实现它。
答案 2 :(得分:0)
此代码适用于我创建的钩子DLL。我认为这里的问题是从图标中获取文本等内容很容易,但是弄清楚如何到达快捷方式下的应用程序完全是另一个问题。这种知识存在于管理listview的应用程序中,在本例中为Explorer。
原谅那个绝对老式的代码,我把这个测试用于旧的ANSI钩子DLL。 DebugStr只是OutputDebugString的包装器。该代码基于Remy的帖子。
LRESULT DLL_CALL MouseFunc (int nCode, WPARAM wParam, LPARAM lParam)
{
BOOL bGoActive = TRUE;
char szDebug [200];
char szBuff [100];
MOUSEHOOKSTRUCT * pmhs = (MOUSEHOOKSTRUCT *)lParam;
LVFINDINFO lvfi;
LVITEM lvi;
int iIndexItem;
long lx = pmhs->pt.x;
long ly = pmhs->pt.y;
if (nCode >= 0)
{
if (wParam == WM_LBUTTONDOWN)
{
GetClassName (pmhs->hwnd, szBuff, sizeof(szBuff));
wsprintf (szDebug, "wparam=0x%X, nCode=%d, HTC=%d, class='%s', x=%d, y=%d",
wParam, nCode, pmhs->wHitTestCode, szBuff, lx, ly);
DebugStr (szDebug);
if (strcmpi (szBuff, TEXT("SysListView32")) == 0)
{
ZeroMemory (&lvfi, sizeof(lvfi));
lvfi.flags = LVFI_NEARESTXY;
lvfi.pt.x = lx;
lvfi.pt.y = ly;
ScreenToClient (pmhs->hwnd, &(lvfi.pt));
lvfi.vkDirection = VK_NEXT;
iIndexItem = ListView_FindItem (pmhs->hwnd, -1, &lvfi);
if (iIndexItem != -1)
{
ZeroMemory (&lvi, sizeof(lvi));
lvi.mask = LVIF_TEXT;
lvi.iItem = iIndexItem;
lvi.pszText = szBuff;
lvi.cchTextMax = sizeof(szBuff);
if (ListView_GetItem (pmhs->hwnd, &lvi))
{
wsprintf (szDebug, "item text = '%s'", szBuff);
DebugStr (szDebug);
}
}
}
}