Im currently creating a AFKChecker for my application. The problem is that the low level mouse hook doesnt get called. I have checked if it returns 0 which it doesnt. So the keyboard hook works but not the mouse hook. I have googled, but I have still not found a solution for my problem.
using System;
using System.Diagnostics;
using System.Runtime.InteropServices;
namespace AFKChecker
{
public static class ActivityChecker
{
public static Int64 LastKeypress = 0;
public static int AFKTime = 300;
private const int WH_KEYBOARD_LL = 13;
public const int WH_MOUSE_LL = 14;
private static HookProc _keyproc = HookCallback;
private static IntPtr _keyhookID = IntPtr.Zero;
private static HookProc _mouseproc = HookCallback;
private static IntPtr _mousehookID = IntPtr.Zero;
public static void AddHook()
{
LastKeypress = Tools.UnixTime();
_keyhookID = SetKeyboardHook(_keyproc);
_mousehookID = SetKeyboardHook(_mouseproc);
}
private static IntPtr HookCallback(
int nCode, IntPtr wParam, IntPtr lParam)
{
LastKeypress = Tools.UnixTime();
return CallNextHookEx(_keyhookID, nCode, wParam, lParam);
}
public static void RemoveHook()
{
UnhookWindowsHookEx(_keyhookID);
UnhookWindowsHookEx(_mousehookID);
}
public static Boolean IsAFK()
{
return (LastKeypress + AFKTime > Tools.UnixTime());
}
private static IntPtr SetKeyboardHook(HookProc proc)
{
using (Process curProcess = Process.GetCurrentProcess())
using (ProcessModule curModule = curProcess.MainModule)
{
return SetWindowsHookEx(WH_KEYBOARD_LL, proc,
GetModuleHandle(curModule.ModuleName), 0);
}
}
private static IntPtr SetMouseHook(HookPr开发者_运维技巧oc proc)
{
using (Process curProcess = Process.GetCurrentProcess())
using (ProcessModule curModule = curProcess.MainModule)
{
return SetWindowsHookEx(WH_MOUSE_LL, proc,
GetModuleHandle(curModule.ModuleName), 0);
}
}
private delegate IntPtr HookProc(
int nCode, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr SetWindowsHookEx(int idHook,
HookProc lpfn, IntPtr hMod, uint dwThreadId);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool UnhookWindowsHookEx(IntPtr hhk);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode,
IntPtr wParam, IntPtr lParam);
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr GetModuleHandle(string lpModuleName);
}
}
Best regards
Installing a mouse/keyboard hook just to find the idle time of the user strikes me as conceptually wrong. This should only be the last resort if windows doesn't offer any better API.
A quick search reveals the GetLastInputInfo API which is designed for this purpose. And a codeproject article describing how to do that in C#: Getting the user idle time with C#
It seems like you are not calling SetMouseHook
, re-check your AddHook()
function:
public static void AddHook()
{
LastKeypress = Tools.UnixTime();
_keyhookID = SetKeyboardHook(_keyproc);
_mousehookID = SetKeyboardHook(_mouseproc); // SetMouseHook() here?
}
精彩评论