当前位置: 首页 > news >正文

使用qt 定义全局钩子 捕获系统的键盘事件

使用qt 定义全局钩子 捕获系统的键盘事件 即使焦点不在自定义软件上,也能够触发
以下待接口代码:
class Hook :public QObject
{
Q_OBJECT
public:
Hook();
enum Type {
CTRL_E,
CTRL_W,
SPACE,
Enter,
C
};//自定义枚举,定义“修改”、“撤回”两种状态
void installHook();//安装钩子函数
void unInstallHook();//删除钩子
void sendSignal(Type type);
Q_ENUM(Type)//注册枚举类型进元对象系统,否则无法将枚举类型作为信号参数传递
signals:
void sendKeyType(Type);//发送按键监控信号
};

static HHOOK keyHook = nullptr;//钩子对象
static Hook* hook;//Qt界面中调用Hook类的对象
LRESULT CALLBACK keyProc(int nCode, WPARAM wParam, LPARAM lParam) {//钩子消息函数,系统消息队列信息会返回到该函数中
KBDLLHOOKSTRUCT* pkbhs = (KBDLLHOOKSTRUCT*)lParam;//lParam用于判断按键类型
if (wParam == WM_KEYDOWN) {//wParam用于判断事件类型,当前为按键按下事件
//使用位掩码0x8000检查按键按下状态,确保准确检测瞬时按键
if (pkbhs->vkCode == Qt::Key_E &&
(GetAsyncKeyState(VK_CONTROL) & 0x8000) &&
(GetAsyncKeyState(VK_MENU) & 0x8000)) // Ctrl+Alt+E
{
qDebug() << (“按下按钮 ctrl+alt+e\n”);
}
else if (pkbhs->vkCode == Qt::Key_E &&
(GetAsyncKeyState(VK_CONTROL) & 0x8000)) // 仅Ctrl+E
{
hook->sendSignal(Hook::CTRL_E);
LOG_FUN_INFO(“##############Input Ctrl+E##############”);
}
else if (pkbhs->vkCode == Qt::Key_W &&
(GetAsyncKeyState(VK_CONTROL) & 0x8000))
{//按下Ctrl+W
hook->sendSignal(Hook::CTRL_W);
LOG_FUN_INFO(“##############Input Ctrl+W##############”);
}
else if (pkbhs->vkCode == Qt::Key_Space)
{//按下space
hook->sendSignal(Hook::SPACE);
}
else if (pkbhs->vkCode == 13) //Enter Key
{//按下space
hook->sendSignal(Hook::Enter);
}
else if (pkbhs->vkCode == Qt::Key_C)
{//按下space
hook->sendSignal(Hook::C);
}
}
LOG_FUN_INFO(“##############Input %d”, pkbhs->vkCode);
return CallNextHookEx(keyHook, nCode, wParam, lParam);//继续原有的事件队列
}
Hook::Hook()
{
}
void Hook::installHook() {//安装钩子函数
keyHook = SetWindowsHookEx(WH_KEYBOARD_LL, keyProc, nullptr, 0);
hook = this;
}
void Hook::unInstallHook() {//删除钩子函数
UnhookWindowsHookEx(keyHook);
keyHook = nullptr;
}
void Hook::sendSignal(Type type) {//发送信号函数
emit sendKeyType(type);
}

http://www.lqws.cn/news/139897.html

相关文章:

  • 聊聊芯片Debug模块及其应用
  • 如何快速找出某表的重复记录 - 数据库专家面试指南
  • 618浴室柜推荐,小户型浴室柜怎么选才省心?
  • JAVA 集合进阶 Map集合的实现类 TreeMap
  • 第八部分:第三节 - 事件处理:响应顾客的操作
  • C++ 变量二
  • c++中char *p指针指向字符串输出问题
  • day46 python预训练模型补充
  • Java八股文——Redis篇
  • CCPC题目
  • Java 创建线程池的几种方式
  • .net jwt实现
  • Linux-linux和windows创建新进程的区别以及posix_spawn
  • ROS 2 环境下使用 Astra Pro 深度相机实现目标距离检测及远程可视化全流程总结
  • 卫星的“太空陀螺”:反作用轮如何精准控制姿态?
  • JavaWeb:前端工程化-ElementPlus
  • Python应用函数的定义与调用(一)
  • 嵌入式分析利器:DuckDB与SqlSugar实战
  • 前端组件推荐 Swiper 轮播与 Lightbox 灯箱组件深度解析
  • 半导体制冷片(Thermoelectric Cooler,TEC)
  • vue封装gsap自定义动画指令
  • JAVA容器
  • BERT vs Rasa 如何选择 Hugging Face 与 Rasa 的区别 模型和智能体的区别
  • 【拓扑】1639.拓扑排序
  • 六种高阶微分方程的特解(原创:daode3056)
  • 近端策略优化(PPO,Proximal Policy Optimization)
  • JavaScript 深入探索:高级应用与前沿技术
  • Java异步编程难题拆解技术
  • MySQL范式和反范式
  • 在 Windows 系统下配置 VSCode + CMake + Ninja 进行 C++ 或 Qt 开发