Processing Global Mouse and Keyboard Hooks in C#
2008-10-25 10:49
471 查看
原文:http://www.codeproject.com/KB/cs/globalhook.aspx
Download source files - 12.4 Kb
Download demo application - 5.58 Kb
The second step was to extract the information received into a .NET
I found a similar article in CodeProject, under Global System Hooks in .NET by Michael Kennedy, but what I dislike is, there is an unmanaged DLL in C++ that is a main part of this solution. This unmanaged DLL is in C++, and a number of classes make it complicated to integrate it in my own tiny application.
Now, an example of how to process an event:
The project was converted into Visual Studio 2005
The problem with upper case characters is solved
Mouse wheel information is now included in event arguments
Better exception handling
Cancellation of keyboard events using the
XML documentation of functions
everywhere, instead of:
Download source files - 12.4 Kb
Download demo application - 5.58 Kb
Introduction
This class allows you to tap keyboard and mouse and/or to detect their activity even when an application runs in the background or does not have any user interface at all. This class raises common .NET events withKeyEventArgsand
MouseEventArgs, so you can easily retrieve any information you need.
Background
There are a number of applications that run in the background and detect user inactivity to change their mode. For example, MSN Messenger (or any other messenger). I was going to write such an application, so I searched MSDN and found "exactly" what I needed: 318804 - HOW TO: Set a Windows Hook in Visual C# .NET. This article describes how to tap the mouse movement, but it works only when an application is active. At the end of this article, I found this explanation: "Global hook is not supported in .NET Framework. You cannot implement global hooks in Microsoft .NET Framework...". Anyway, I continued my research and found out that there are exceptions. There areWH_KEYBOARD_LLand
WH_MOUSE_LLhooks that can be installed globally. So, I have basically replaced
WH_MOUSEwith
WH_MOUSE_LLin the MSDN example, and it works.
The second step was to extract the information received into a .NET
EventArgsand raise the appropriate events.
I found a similar article in CodeProject, under Global System Hooks in .NET by Michael Kennedy, but what I dislike is, there is an unmanaged DLL in C++ that is a main part of this solution. This unmanaged DLL is in C++, and a number of classes make it complicated to integrate it in my own tiny application.
Using the code
To use this class in your application, you need just to create an instance of it and hang on events you would like to process. Hooks are automatically installed when the object is created, but you can stop and start listening using appropriate public methods.UserActivityHook actHook; void MainFormLoad(object sender, System.EventArgs e) { actHook= new UserActivityHook(); // crate an instance // hang on events actHook.OnMouseActivity+=new MouseEventHandler(MouseMoved); actHook.KeyDown+=new KeyEventHandler(MyKeyDown); actHook.KeyPress+=new KeyPressEventHandler(MyKeyPress); actHook.KeyUp+=new KeyEventHandler(MyKeyUp); }
Now, an example of how to process an event:
public void MouseMoved(object sender, MouseEventArgs e) { labelMousePosition.Text=String.Format("x={0} y={1}", e.X, e.Y); if (e.Clicks>0) LogWrite("MouseButton - " + e.Button.ToString()); }
Changes and updates in the new version
I'd like to thank you all for all the useful comments in the discussion forum. There were a lot of bugs and proposals posted after this article was published on 4 Jun 2004. Over and over again came the same topics, and I had to refer to previous posts in the discussion, that is why I have decided to revise the code and publish a FAQ. Here is the list of the most important changes:The project was converted into Visual Studio 2005
The problem with upper case characters is solved
Mouse wheel information is now included in event arguments
Better exception handling
Cancellation of keyboard events using the
Handledproperty of event arguments
XML documentation of functions
FAQ
Question:
The project cannot be run in Visual Studio .NET 2005 in debug mode because of an exception error caused by calling theSetWindowsHookEx. Why? Is it a problem of .NET 2.0?
Answer:
The compiled release version works well so that can not be a .NET 2.0 problem. To workaround, you just need to uncheck the check box in the project properties that says: "Enable Visual Studio hosting process". In the menu: Project -> Project Properties... -> Debug -> Enable the Visual Studio hosting process.Question:
I need to suppress some keystrokes after I have processed them.Answer:
Just set thee.Handledproperty to
truein the key events you have processed. It prevent the keystrokes being processed by other applications.
Question:
Is it possible to convert your global hooks to application hooks which capture keystrokes and mouse movements only within the application?Answer:
Yes. Just use:private const int WH_MOUSE = 7; private const int WH_KEYBOARD = 2;
everywhere, instead of:
private const int WH_MOUSE_LL = 14; private const int WH_KEYBOARD_LL = 13;
Question:
Does it work on Win98 (Windows ME, Windows 95)?Answer:
Yes and No. The global hooksWH_MOUSE_LLand
WH_KEYBOARD_LLcan be monitored only under Windows NT/2000/XP. In other cases, you can only use application hooks (
WH_MOUSE and WH_KEYBOARD) which capture keystrokes and mouse movement only within the application.
Question:
I have a long delay when closing applications using hooks by clicking the x button in the titlebar. If I close the application via another event (button click) for example, that works fine.Answer:
It's a know bug of Microsoft. It has to do with the Windows themes. If you disable the Windows themes, the problem goes away. Another choice is to have the hook code run in a secondary thread.Question:
How do I catch key combinations like Ctrl+Shift+A?Answer:
You'll have to track which keys have gone down but not up. Only the most recently pressed key keeps sendingKeyDownmessages, but the others will still send a
KeyUpwhen released. So if you make three flags
IsCtrlDown,
IsShiftDown, and
IsADown, and set them to
trueat
KeyDownand
falseat
KeyUp, the expression
(IsCtrlDown && IsShiftDown && IsADown)will give you the required result.
Question:
Does it works with .NET Framework 1.1 and Visual Studio 2003?Answer:
Yes. The file UserActivityHook.cs can be used without any changes, in a VS2003 .NET 1.1 project.License
This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)相关文章推荐
- Processing Global Mouse and Keyboard Hooks in C#
- Processing Global Mouse and Keyboard Hooks in C#
- Processing Global Mouse and Keyboard Hooks in C#
- Processing Global Mouse and Keyboard Hooks in C#
- Global Mouse and Keyboard Library
- Mouse and keyboard operation in windows using python
- 图像处理中的全局优化技术(Global optimization techniques in image processing and computer vision) (三)
- 图像处理中的全局优化技术(Global optimization techniques in image processing and computer vision) (一)
- 图像处理中的全局优化技术(Global optimization techniques in image processing and computer vision) (一)
- 图像处理中的全局优化技术(Global optimization techniques in image processing and computer vision) (二)
- 图像处理中的全局优化技术(Global optimization techniques in image processing and computer vision) (二)
- Using keyboard hooks in WinCE
- How to Determine if a file is a .Net assembly (in Delphi and C#)
- Delegates and Events in C# .NET
- Applying Domain-Driven Design and Patterns(ADDDP) With examples in C# and .NET
- Thread and Sync In C# (C#中的线程与同步)
- Stereo Processing by Semiglobal Matching and Mutual Information
- Set Font Properties On Mouse Hover Of Push Button And Text Items At Run time In Oracle Forms
- Silverlight and C# in Orcas Beta 1(转载)
- Creating custom headers and footers in Application level events using global.asax