Skip to content

Instantly share code, notes, and snippets.

Created December 19, 2012 18:24
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save anonymous/4339044 to your computer and use it in GitHub Desktop.
Save anonymous/4339044 to your computer and use it in GitHub Desktop.
public sealed class HotKey : IDisposable
{
private readonly IntPtr _handle;
private readonly int _id;
private bool _isKeyRegistered;
public HotKey(ModifierKeys modifierKeys, Key key, Window window)
: this(modifierKeys, key, new WindowInteropHelper(window))
{
}
public HotKey(ModifierKeys modifierKeys, Key key, WindowInteropHelper window)
: this(modifierKeys, key, window.Handle)
{
}
public HotKey(ModifierKeys modifierKeys, Key key, IntPtr windowHandle)
{
Key = key;
KeyModifier = modifierKeys;
_id = GetHashCode();
_handle = windowHandle;
RegisterHotKey();
ComponentDispatcher.ThreadPreprocessMessage += ThreadPreprocessMessageMethod;
}
~HotKey()
{
Dispose();
}
public event Action<HotKey> HotKeyPressed;
public Key Key { get; private set; }
public ModifierKeys KeyModifier { get; private set; }
private int InteropKey
{
get
{
return KeyInterop.VirtualKeyFromKey(Key);
}
}
public void Dispose()
{
ComponentDispatcher.ThreadPreprocessMessage -= ThreadPreprocessMessageMethod;
UnregisterHotKey();
}
private void OnHotKeyPressed()
{
if (HotKeyPressed != null)
{
HotKeyPressed(this);
}
}
private void RegisterHotKey()
{
if (Key == Key.None)
{
return;
}
if (_isKeyRegistered)
{
UnregisterHotKey();
}
_isKeyRegistered = HotKeyWinApi.RegisterHotKey(_handle, _id, KeyModifier, InteropKey);
if (!_isKeyRegistered)
{
throw new ApplicationException("Hotkey already in use");
}
}
private void ThreadPreprocessMessageMethod(ref MSG msg, ref bool handled)
{
if (handled)
{
return;
}
if (msg.message != HotKeyWinApi.WmHotKey || (int)(msg.wParam) != _id)
{
return;
}
OnHotKeyPressed();
handled = true;
}
private void UnregisterHotKey()
{
_isKeyRegistered = !HotKeyWinApi.UnregisterHotKey(_handle, _id);
}
}
public class HotKeyWinApi
{
public const int WmHotKey = 0x0312;
[DllImport("user32.dll", SetLastError = true)]
public static extern bool RegisterHotKey(IntPtr hWnd, int id, ModifierKeys fsModifiers, int vk);
[DllImport("user32.dll", SetLastError = true)]
public static extern bool UnregisterHotKey(IntPtr hWnd, int id);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment