用C++ 和 Win32 SDK 写的简单键盘锁
来源:互联网 发布:软件设计师教程 pdf 编辑:程序博客网 时间:2024/05/22 16:37
最近总要在笔记本电脑前面写东西,所以一般把本子放在键盘上。但是又容易不小心按了哪个键。所以写了个键盘锁,这样锁起来之后按什么键都不起作用了。主要是使用了 Hook 技术。
可能有谁也会需要到,就贴在这里了。
另外,关于气泡提示中的 timeout 的变量好像不是很准,我设置了 1000 毫秒,但是基本上要等上 10 秒左右才能消失。暂时还不知道是什么原因。
#define _WIN32_IE 0x0500
#include <windows.h>
enum
...{
WM_TRAYICON = WM_USER + 100, //自定义托盘消息
ID_LOCK,
ID_UNLOCK,
ID_EXIT
};
HHOOK KBhook = NULL;//钩子句柄
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK KeyboardHookProc(int nCode, WPARAM wParam, LPARAM lParam);//键盘钩子回调函数
void TrayMessage(HWND hwnd, LPCTSTR szText);//显示托盘气泡信息
void DestroyTrayIcon(HWND hwnd);//删除托盘图标
void CreateTrayMenu(HWND hwnd);//建立托盘菜单
int EnableKeyboardCapture();//激活键盘钩子
int DisableKeyboardCapture();//解除键盘钩子
void OnLock(HWND hwnd);
void OnUnlock(HWND hwnd);
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow)
...{
HWND hwnd;
MSG msg;
NOTIFYICONDATA IconData;
WNDCLASS wndclass;
static TCHAR szAppName[] = ...{"Keyboard Lock"};
//初始化窗口
wndclass.style = CS_HREDRAW | CS_VREDRAW;
wndclass.lpfnWndProc = WndProc;
wndclass.cbClsExtra = 0;
wndclass.cbWndExtra = 0;
wndclass.hCursor = LoadCursor(NULL, IDI_APPLICATION);
wndclass.hIcon = LoadIcon(NULL, IDC_ARROW);
wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wndclass.hInstance = hInstance;
wndclass.lpszMenuName = NULL;
wndclass.lpszClassName = szAppName;
RegisterClass(&wndclass);
hwnd = CreateWindow(szAppName, szAppName, WS_OVERLAPPEDWINDOW, 0, 0, 0, 0, 0, 0, hInstance, NULL);
//这里之后不需要显示窗口,新建托盘图标,操作全部在托盘图标上完成
//Warning: HWND 和 HINSTANCE 不对的话,就会有问题
IconData.cbSize = sizeof(NOTIFYICONDATA);
IconData.hWnd = hwnd;
IconData.uID = (UINT)hInstance;
IconData.hIcon = LoadIcon(0, MAKEINTRESOURCE(IDI_INFORMATION));
IconData.uFlags = NIF_MESSAGE + NIF_ICON + NIF_TIP;
IconData.uCallbackMessage = WM_TRAYICON;
strcpy(IconData.szTip, "键盘锁");
Shell_NotifyIcon(NIM_ADD, &IconData);
while(GetMessage(&msg, NULL, 0, 0))
...{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
...{
switch (message)
...{
case WM_COMMAND:
if(HIWORD(wParam) == 0)
...{
//菜单动作的消息
switch (LOWORD(wParam))
...{
case ID_LOCK:
OnLock(hwnd);
break;
case ID_UNLOCK:
OnUnlock(hwnd);
break;
case ID_EXIT:
::DestroyWindow(hwnd);
break;
}
}
break;
case WM_TRAYICON:
switch (lParam)
...{
case WM_LBUTTONDOWN:
CreateTrayMenu(hwnd);
break;
}
break;
case WM_DESTROY:
DestroyTrayIcon(hwnd);
PostQuitMessage(0);
break;
}
return DefWindowProc(hwnd, message, wParam, lParam);
}
LRESULT CALLBACK KeyboardHookProc(int nCode, WPARAM wParam, LPARAM lParam)
...{
//是键盘的动作全部忽略
if (nCode == HC_ACTION)
return 1;
return CallNextHookEx(NULL, nCode, wParam, lParam);
}
int EnableKeyboardCapture()
...{
// 13 表示使用低级键盘钩子,和 WM_KEYBOARD 不同
KBhook = !KBhook ? SetWindowsHookEx(13, (HOOKPROC)KeyboardHookProc, (HINSTANCE)GetModuleHandle(NULL), 0) : KBhook;
return (KBhook ? 1 : -1);
}
int DisableKeyboardCapture()
...{
if (KBhook == NULL)
...{
return 0;
}
else
...{
BOOL flag;
flag = UnhookWindowsHookEx(KBhook);
KBhook = NULL;
return (flag ? 1 : -1);
}
}
void TrayMessage(HWND hwnd, LPCTSTR szText)
...{
NOTIFYICONDATA nid;
nid.cbSize = sizeof(NOTIFYICONDATA);
nid.hWnd = hwnd;
nid.uID = (UINT)GetModuleHandle(NULL);
nid.uFlags = NIF_INFO | NIF_ICON;
nid.dwInfoFlags = NIIF_INFO;
nid.uTimeout = 1000;
nid.hIcon = LoadIcon(0, MAKEINTRESOURCE(IDI_INFORMATION));
wsprintf(nid.szInfo, szText);
strcpy(nid.szInfoTitle, "键盘锁");
Shell_NotifyIcon(NIM_MODIFY, &nid);
}
void DestroyTrayIcon(HWND hwnd)
...{
NOTIFYICONDATA nid;
nid.cbSize = sizeof(nid);
nid.uID = (UINT)GetModuleHandle(NULL);
nid.hWnd = hwnd;
nid.uFlags = 0;
Shell_NotifyIcon(NIM_DELETE, &nid);
}
void CreateTrayMenu(HWND hwnd)
...{
HMENU hMenu;
hMenu = CreatePopupMenu();
AppendMenu(hMenu, MF_STRING, ID_LOCK, "锁定键盘");
AppendMenu(hMenu, MF_STRING, ID_UNLOCK, "解锁键盘");
AppendMenu(hMenu, MF_SEPARATOR, 0, NULL);
AppendMenu(hMenu, MF_STRING, ID_EXIT, "退出");
POINT pt;
GetCursorPos(&pt);
TrackPopupMenu(hMenu, TPM_RIGHTALIGN, pt.x, pt.y, 0, hwnd, NULL);
}
void OnUnlock(HWND hwnd)
...{
switch (DisableKeyboardCapture())
...{
case 0:
TrayMessage(hwnd, "键盘没有锁定");
break;
case 1:
TrayMessage(hwnd, "键盘已经解锁");
break;
case -1:
TrayMessage(hwnd, "键盘解锁错误");
break;
}
}
void OnLock(HWND hwnd)
...{
switch (EnableKeyboardCapture())
...{
case 1:
TrayMessage(hwnd, "键盘已经锁定");
break;
case -1:
TrayMessage(hwnd, "键盘锁定错误");
break;
}
}
#include <windows.h>
enum
...{
WM_TRAYICON = WM_USER + 100, //自定义托盘消息
ID_LOCK,
ID_UNLOCK,
ID_EXIT
};
HHOOK KBhook = NULL;//钩子句柄
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK KeyboardHookProc(int nCode, WPARAM wParam, LPARAM lParam);//键盘钩子回调函数
void TrayMessage(HWND hwnd, LPCTSTR szText);//显示托盘气泡信息
void DestroyTrayIcon(HWND hwnd);//删除托盘图标
void CreateTrayMenu(HWND hwnd);//建立托盘菜单
int EnableKeyboardCapture();//激活键盘钩子
int DisableKeyboardCapture();//解除键盘钩子
void OnLock(HWND hwnd);
void OnUnlock(HWND hwnd);
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow)
...{
HWND hwnd;
MSG msg;
NOTIFYICONDATA IconData;
WNDCLASS wndclass;
static TCHAR szAppName[] = ...{"Keyboard Lock"};
//初始化窗口
wndclass.style = CS_HREDRAW | CS_VREDRAW;
wndclass.lpfnWndProc = WndProc;
wndclass.cbClsExtra = 0;
wndclass.cbWndExtra = 0;
wndclass.hCursor = LoadCursor(NULL, IDI_APPLICATION);
wndclass.hIcon = LoadIcon(NULL, IDC_ARROW);
wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wndclass.hInstance = hInstance;
wndclass.lpszMenuName = NULL;
wndclass.lpszClassName = szAppName;
RegisterClass(&wndclass);
hwnd = CreateWindow(szAppName, szAppName, WS_OVERLAPPEDWINDOW, 0, 0, 0, 0, 0, 0, hInstance, NULL);
//这里之后不需要显示窗口,新建托盘图标,操作全部在托盘图标上完成
//Warning: HWND 和 HINSTANCE 不对的话,就会有问题
IconData.cbSize = sizeof(NOTIFYICONDATA);
IconData.hWnd = hwnd;
IconData.uID = (UINT)hInstance;
IconData.hIcon = LoadIcon(0, MAKEINTRESOURCE(IDI_INFORMATION));
IconData.uFlags = NIF_MESSAGE + NIF_ICON + NIF_TIP;
IconData.uCallbackMessage = WM_TRAYICON;
strcpy(IconData.szTip, "键盘锁");
Shell_NotifyIcon(NIM_ADD, &IconData);
while(GetMessage(&msg, NULL, 0, 0))
...{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
...{
switch (message)
...{
case WM_COMMAND:
if(HIWORD(wParam) == 0)
...{
//菜单动作的消息
switch (LOWORD(wParam))
...{
case ID_LOCK:
OnLock(hwnd);
break;
case ID_UNLOCK:
OnUnlock(hwnd);
break;
case ID_EXIT:
::DestroyWindow(hwnd);
break;
}
}
break;
case WM_TRAYICON:
switch (lParam)
...{
case WM_LBUTTONDOWN:
CreateTrayMenu(hwnd);
break;
}
break;
case WM_DESTROY:
DestroyTrayIcon(hwnd);
PostQuitMessage(0);
break;
}
return DefWindowProc(hwnd, message, wParam, lParam);
}
LRESULT CALLBACK KeyboardHookProc(int nCode, WPARAM wParam, LPARAM lParam)
...{
//是键盘的动作全部忽略
if (nCode == HC_ACTION)
return 1;
return CallNextHookEx(NULL, nCode, wParam, lParam);
}
int EnableKeyboardCapture()
...{
// 13 表示使用低级键盘钩子,和 WM_KEYBOARD 不同
KBhook = !KBhook ? SetWindowsHookEx(13, (HOOKPROC)KeyboardHookProc, (HINSTANCE)GetModuleHandle(NULL), 0) : KBhook;
return (KBhook ? 1 : -1);
}
int DisableKeyboardCapture()
...{
if (KBhook == NULL)
...{
return 0;
}
else
...{
BOOL flag;
flag = UnhookWindowsHookEx(KBhook);
KBhook = NULL;
return (flag ? 1 : -1);
}
}
void TrayMessage(HWND hwnd, LPCTSTR szText)
...{
NOTIFYICONDATA nid;
nid.cbSize = sizeof(NOTIFYICONDATA);
nid.hWnd = hwnd;
nid.uID = (UINT)GetModuleHandle(NULL);
nid.uFlags = NIF_INFO | NIF_ICON;
nid.dwInfoFlags = NIIF_INFO;
nid.uTimeout = 1000;
nid.hIcon = LoadIcon(0, MAKEINTRESOURCE(IDI_INFORMATION));
wsprintf(nid.szInfo, szText);
strcpy(nid.szInfoTitle, "键盘锁");
Shell_NotifyIcon(NIM_MODIFY, &nid);
}
void DestroyTrayIcon(HWND hwnd)
...{
NOTIFYICONDATA nid;
nid.cbSize = sizeof(nid);
nid.uID = (UINT)GetModuleHandle(NULL);
nid.hWnd = hwnd;
nid.uFlags = 0;
Shell_NotifyIcon(NIM_DELETE, &nid);
}
void CreateTrayMenu(HWND hwnd)
...{
HMENU hMenu;
hMenu = CreatePopupMenu();
AppendMenu(hMenu, MF_STRING, ID_LOCK, "锁定键盘");
AppendMenu(hMenu, MF_STRING, ID_UNLOCK, "解锁键盘");
AppendMenu(hMenu, MF_SEPARATOR, 0, NULL);
AppendMenu(hMenu, MF_STRING, ID_EXIT, "退出");
POINT pt;
GetCursorPos(&pt);
TrackPopupMenu(hMenu, TPM_RIGHTALIGN, pt.x, pt.y, 0, hwnd, NULL);
}
void OnUnlock(HWND hwnd)
...{
switch (DisableKeyboardCapture())
...{
case 0:
TrayMessage(hwnd, "键盘没有锁定");
break;
case 1:
TrayMessage(hwnd, "键盘已经解锁");
break;
case -1:
TrayMessage(hwnd, "键盘解锁错误");
break;
}
}
void OnLock(HWND hwnd)
...{
switch (EnableKeyboardCapture())
...{
case 1:
TrayMessage(hwnd, "键盘已经锁定");
break;
case -1:
TrayMessage(hwnd, "键盘锁定错误");
break;
}
}
- 用C++ 和 Win32 SDK 写的简单键盘锁
- 用Win32 SDK写一个简单的计算器
- 用C写一个简单的win32服务程序
- 早年用WIN32汇编写的反键盘记录器
- 【源码】用Win32 SDK写的贪吃蛇,欢迎交流
- 一个简单的Win32 SDK窗口程序
- 用C写的 简单字符串加密和解密算法
- 刚刚写的一个Win32 SDK的工程扩展模板
- MFC和Win32 SDK的区别
- 一个使用纯Win32 SDK和C语言实现的五子棋游戏
- 用WIN32 SDK写记事本遇到了一个问题
- Win32 SDK基础(13)—— 键盘和鼠标消息
- C入门:简单的win32线程
- 二维线段裁剪程序的C/SDK WIN32实现
- C++win32 SDK下面如何修改应用程序的图标
- Win32 SDK函数MessageBox的模拟实现(C语言版)
- OpenGL + Win32 SDK 开发框架的搭建(C语言版)
- 用C写的简单学生成绩管理系统
- 嵌入式系统中Nand-Flash的原理及应用
- ABAP程序的移植性注意问题
- Leo谈交朋友与找工作
- Ext错误列表——回调函数如何传参
- oracle中列出某月所有天的sql语句
- 用C++ 和 Win32 SDK 写的简单键盘锁
- 利用Boost影响Lucene查询结果的排序
- msn web search 的访问地址
- YAFFS文件系统移植笔记
- NAND FLASH ECC校验原理与实现
- 企业如何应用PMO
- Ext错误列表——JS支不支持“函数重载”
- Direct3D纹理映射
- 喵喵说自动化持续集成