2025年Qt之Hook(键盘钩子)的简单使用(挂接截图程序,含源码+注释)

Qt之Hook(键盘钩子)的简单使用(挂接截图程序,含源码+注释)一 后台钩子截图调用示例 二 钩子的个人理解 挂接钩子的步骤 SetWindowsHo gt UnhookWindow 直接用 SetWindowsHo 函数挂接到对应的钩子类型和处理函数中 当钩子使用完后需要调用 UnhookWindow 函数卸载

大家好,我是讯享网,很高兴认识大家。

一、后台钩子截图调用示例

在这里插入图片描述
讯享网

二、钩子的个人理解

  1. 挂接钩子的步骤:SetWindowsHookEx -> UnhookWindowsHookEx,直接用SetWindowsHookEx 函数挂接到对应的钩子类型和处理函数中;当钩子使用完后需要调用UnhookWindowsHookEx函数卸载(因为钩子消耗系统性能)。
    SetWindowsHookEx 函数原型如下:
 //! int idHook 所监控的挂钩类型 //! HOOKPROC lpfn 监控信息的处理函数 //! HINSTANCEhMod 监控信息的动态链接位置 nullptr则与本线程相关 //! DWORD dwThreadId 挂钩线程id 0则代表当前 决定了此钩子是系统钩子还是线程钩子 //! 返回值 函数执行成功,则返回值为对应的钩子句柄;若此函数执行失败,则返回值为NULL(0) HHOOK SetWindowsHookEx(int idHook, HOOKPROC lpfn, HINSTANCE hMod, DWORD dwThreadId); 

讯享网

SetWindowsHookEx 函数原型如下:

讯享网 //! hHook 要卸载的钩子句柄 BOOL UnhookWindowsHookEx(HHOOK hHook); 
  1. 各个类型的钩子原型一致,如下:
 / * @brief Hookproc * @param code 这是一个整数值,用于指定发送到钩子过程的消息类型。它可以是几个值中的一个,例如HC_ACTION、HC_NOREMOVE或HC_CREATE * @param wParam 一个指向宽字符值的指针,其中包含有关发送到钩子过程的消息的附加信息,其值取决于code的值 * @param lParam 一个指向长字符值的指针,其中包含有关发送到钩子过程的消息的附加信息,其值取决于code的值 * @return 如果返回0,则消息未被处理,将继续由其他钩子或目标窗口处理。如果返回非零值,则消息已被钩子过程处理,不会被其他钩子或目标窗口处理 */ LRESULT Hookproc(int code, WPARAM wParam, LPARAM lParam) 
  1. 不同的钩子对应的数据结构体及参数含义不同,如当关联键盘钩子(WH_KEYBOARD_LL)时,其lParam参数代表的结构体为KBDLLHOOKSTRUCT;当关联鼠标钩子(WH_MOUSE_LL)时,其wParam代表鼠标操作的类型(如左键按下、放开等),lParam参数代表的结构体为MSLLHOOKSTRUCT。具体可按需求查看对应内容。
  2. 推荐的链接:官方链接、钩子(HOOK)函数教程

三、源码

CHook.h

讯享网#ifndef CHOOK_H #define CHOOK_H // 干净的钩子类 class CHook { 
    public: explicit CHook(); ~CHook(); }; #endif // CHOOK_H 

CHook.cpp

#include "CHook.h" #include "CMainWindow.h" #include <windows.h> #include <QDebug> // 引用全局变量 extern CMainWindow *g_mainWdindow; HHOOK g_hook; // 钩子对象 / * @brief Hookproc * @param code 这是一个整数值,用于指定发送到钩子过程的消息类型。它可以是几个值中的一个,例如HC_ACTION、HC_NOREMOVE或HC_CREATE * @param wParam 一个指向宽字符值的指针,其中包含有关发送到钩子过程的消息的附加信息,其值取决于code的值 * @param lParam 一个指向长字符值的指针,其中包含有关发送到钩子过程的消息的附加信息,其值取决于code的值 * @return 如果返回0,则消息未被处理,将继续由其他钩子或目标窗口处理。如果返回非零值,则消息已被钩子过程处理,不会被其他钩子或目标窗口处理 */ LRESULT Hookproc(int code, WPARAM wParam, LPARAM lParam) { 
    // lParam强转为键盘数据结构体 KBDLLHOOKSTRUCT *data = (KBDLLHOOKSTRUCT *)lParam; //! GetAsyncKeyState //! 获取指定按钮状态:非0则为按下状态,为0则为未按下状态 // 当Ctrl、Alt、X都按下时进入 if(GetAsyncKeyState(VK_LCONTROL) && GetAsyncKeyState(VK_LMENU) && 0x58 == data->vkCode && g_mainWdindow->screenShotFlag()) { 
    // 调用截图 g_mainWdindow->startScreenShot(); } return CallNextHookEx(g_hook, code, wParam, lParam); } CHook::CHook() { 
    //! SetWindowsHookEx 函数解释 //! int idHook 所监控的挂钩类型 //! HOOKPROC lpfn 监控信息的处理函数 //! HINSTANCEhMod 监控信息的动态链接位置 nullptr则与本线程相关 //! DWORD dwThreadId 挂钩线程id 0则代表当前 决定了此钩子是系统钩子还是线程钩子 //! 返回值 函数执行成功,则返回值就是该挂钩处理过程的句柄;若此函数执行失败,则返回值为NULL(0) g_hook = SetWindowsHookEx(WH_KEYBOARD_LL, Hookproc, nullptr, 0); } CHook::~CHook() { 
    // 卸载钩子 UnhookWindowsHookEx(g_hook); } 

main.cpp

讯享网#include "CMainWindow.h" #include <QApplication> #include "CHook.h" CMainWindow *g_mainWdindow; int main(int argc, char *argv[]) { 
    QApplication a(argc, argv); // 创建钩子对象 CHook hook; // 创建程序对象 g_mainWdindow = new CMainWindow; // 初始化程序 g_mainWdindow->initialize(); int ret = a.exec(); // 反初始化 g_mainWdindow->uninitialize(); delete g_mainWdindow; return ret; } 

总结

使用钩子时注意数据的类型及参数的含义,不同的钩子其参数及含义不同需要好好记一下;包括钩子可以封装在库中或子线程中调用,该部分文中没有体现,值得研究一下。

相关文章

Qt之QGraphicsView实现截图(漏洞百出且BUG丛生版,部分源码+注释)

小讯
上一篇 2025-03-08 11:23
下一篇 2025-02-17 20:53

相关推荐

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容,请联系我们,一经查实,本站将立刻删除。
如需转载请保留出处:https://51itzy.com/kjqy/69663.html