在WPF中如何注冊熱鍵(轉)
WPF注冊熱鍵大薈萃
源碼下載:http://www.rzrgm.cn/dabaopku/archive/2010/02/22/1671267.html
研究了一晚上,終于搞定了啦~~~~~
首先完整復制下面的第一篇文章中的代碼
然后以下代碼是
其中Id隨意取值,好像都沒有問題
一直受第三篇文章干擾(說實在的,確實讓人惱火,它的RegisterHotkey(Keys Key, KeyFlags keyflags)
明明是Key在前 keyflags在后,可是帶入APi的
結底還是自己不夠細心,足足浪費了半小時,郁悶!)
RegisterHotKey后卻是反過來的,結果我也跟著他的弄反了control和F12,歸根
然后反注冊就很簡單了,唉,累死了~~
在WPF中如何注冊熱鍵
來源:http://www.rzrgm.cn/zengezenge/archive/2009/07/09/1519582.html
不說廢話,直接看代碼吧
,其關鍵就是 System.Windows.Interop.HwndSource類。
第一步:注冊熱鍵,需要使用API函數(shù),具體的參照網上的其它文章。唯一需要注意的是需要使用KeyInterop.VirtualKeyFromKey函數(shù)將
WPF的Key枚舉轉化為API函數(shù)可以使用的VirtualKeyCode :
/// <summary>
/// 注冊熱鍵處理函數(shù)
/// </summary>
/// <param name="hWnd">用于處理熱鍵消息的窗體句柄</param>
/// <param name="id">熱鍵的編號</param>
/// <param name="controlKey">控制鍵</param>
/// <param name="virtualKey">熱鍵的虛鍵編碼</param>
/// <returns>
/// <c>true</c>:注冊成功<br/>
/// <c>false</c>:注冊失敗
/// </returns>
/// <remarks></remarks>
/// <history>
/// [ZengE] 2009-7-8 22:28 創(chuàng)建
/// </history>
[System.Runtime.InteropServices.DllImport("user32")]
public static extern bool RegisterHotKey(IntPtr hWnd, int id, uint controlKey, uint virtualKey);
/// <summary>
/// 注銷指定的熱鍵
/// </summary>
/// <param name="hWnd">用于處理熱鍵消息的窗體句柄</param>
/// <param name="id">要注銷的熱鍵編號</param>
/// <returns>
/// <c>true</c>:注銷成功<br/>
/// <c>false</c>:注銷失敗
/// </returns>
/// <remarks></remarks>
/// <history>
/// [ZengE] 2009-7-8 22:30 創(chuàng)建
/// </history>
[System.Runtime.InteropServices.DllImport("user32")]
public static extern bool UnregisterHotKey(IntPtr hWnd, int id);
第二步:注冊熱鍵處理函數(shù),主要的難點就在這里,在.NET的WinForm程序中一般使用重寫Form的WinProc方法或者注冊IMessageFilter來實現(xiàn)的,
但是在WPF中以上兩種方式都無法獲得熱鍵消息的處理機會,除非是在WPF程序中隱藏一個常規(guī)的Form
(最開始就是這么弄得,后來覺得實在是太丑陋了)
1
/// <summary>2
/// 安裝熱鍵處理掛鉤3
/// </summary>4
/// <param name="window">The window.</param>5
/// <returns>6
/// <c>true</c>:安裝成功<br/>7
/// <c>false</c>:安裝失敗8
/// </returns>9
/// <value>消息源</value>10
/// <remarks></remarks>11
/// <history>12
/// [ZengE] 2009-7-8 23:57 創(chuàng)建13
/// </history> 14
public static bool InstallHotKeyHook( Window window )15
{16
//判斷組件是否有效17
if ( null == window )18
{19
//如果無效,則直接返回20
return false;21
}22

23
//獲得窗體的句柄24
System.Windows.Interop.WindowInteropHelper helper = new System.Windows.Interop.WindowInteropHelper( window );25

26
//判斷窗體句柄是否有效27
if ( IntPtr.Zero == helper.Handle )28
{29
//如果句柄無效,則直接返回30
return false;31
}32

33
//獲得消息源34
System.Windows.Interop.HwndSource source = System.Windows.Interop.HwndSource.FromHwnd( helper.Handle );35

36
//判斷消息源是否有效37
if ( null == source )38
{39
//如果消息源無效,則直接返回40
return false;41
}42

43
//掛接事件44
source.AddHook( HotKeyHook );45

46
//返回安裝成功47
return true;48
}49

50
/// <summary>51
/// 熱鍵處理過程52
/// </summary>53
/// <param name="hwnd">觸發(fā)消息的窗口句柄</param>54
/// <param name="msg">要被處理的消息編號</param>55
/// <param name="wParam">消息參數(shù)</param>56
/// <param name="lParam">消息參數(shù)</param>57
/// <param name="handled">消息是否被處理</param>58
/// <returns></returns>59
/// <remarks></remarks>60
/// <history>61
/// [ZengE] 2009-7-8 23:54 創(chuàng)建62
/// </history> 63
private static IntPtr HotKeyHook( IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled )64
{65
//判斷是否為熱鍵消息66
if ( msg == WM_HOTKEY )67
{68

69
}70

71
//返回72
return IntPtr.Zero;73
}74

75
/// <summary>76
/// 熱鍵消息編號77
/// </summary> 78
private const int WM_HOTKEY = 0x0312;
以上代碼在Windows2008下測試通過。
|
在c#中使用全局快捷鍵
來源:http://hi.baidu.com/55csharp/blog/item/de6fef88efcebdbb0e24442f.html 由于.net并沒有提供快捷鍵的庫,所以要使用該功能得通過api實現(xiàn)。 在winapi中,注冊和注銷全局快捷鍵分別是通過RegisterHotKey和UnregisterHotKey函數(shù)實現(xiàn)。在c#中直接使用該api顯得不夠簡潔,這里我提供了一個友好點的封裝。 代碼如下: static class Hotkey [DllImport("user32.dll")] /**//// <summary> /**//// <summary> /**//// <summary> const int WM_HOTKEY = 0x312; public delegate void HotKeyCallBackHanlder(); enum HotkeyModifiers
這里通過Hotkey類實現(xiàn)功能的封裝,使用非常簡單。下面為參考測試代碼。
void Test() protected override void WndProc(ref Message m) private void button1_Click(object sender, EventArgs e) 當程序form1啟動時,注冊了兩個快捷鍵Alt+T和Ctrl+Shift+K,單擊button1的時候會注銷快捷鍵Alt+T。代碼比較簡單,這里就不多介紹了。 注:快捷鍵是通過消息觸發(fā)的,因此要重載WndProc函數(shù),在里面添加對快捷鍵回調消息的處理方法Hotkey.ProcessHotKey(m)。
|
C# 設置全局熱鍵
來源:http://www.rzrgm.cn/lhking/archive/2009/03/16/1413245.html
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using System.Collections;
namespace HotKey1
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
public delegate void HotkeyEventHandler(int HotKeyID);
private int Hotkey1;
public class Hotkey : System.Windows.Forms.IMessageFilter
{
Hashtable keyIDs = new Hashtable();
IntPtr hWnd;
public event HotkeyEventHandler OnHotkey;
public enum KeyFlags
{
MOD_ALT = 0x1,
MOD_CONTROL = 0x2,
MOD_SHIFT = 0x4,
MOD_WIN = 0x8
}
[DllImport("user32.dll")]
public static extern UInt32 RegisterHotKey(IntPtr hWnd, UInt32 id, UInt32 fsModifiers, UInt32 vk);
[DllImport("user32.dll")]
public static extern UInt32 UnregisterHotKey(IntPtr hWnd, UInt32 id);
[DllImport("kernel32.dll")]
public static extern UInt32 GlobalAddAtom(String lpString);
[DllImport("kernel32.dll")]
public static extern UInt32 GlobalDeleteAtom(UInt32 nAtom);
public Hotkey(IntPtr hWnd)
{
this.hWnd = hWnd;
Application.AddMessageFilter(this);
}
public int RegisterHotkey(Keys Key, KeyFlags keyflags)
{
UInt32 hotkeyid = GlobalAddAtom(System.Guid.NewGuid().ToString());
RegisterHotKey((IntPtr)hWnd, hotkeyid, (UInt32)keyflags, (UInt32)Key);
keyIDs.Add(hotkeyid, hotkeyid);
return (int)hotkeyid;
}
public void UnregisterHotkeys()
{
Application.RemoveMessageFilter(this);
foreach (UInt32 key in keyIDs.Values)
{
UnregisterHotKey(hWnd, key);
GlobalDeleteAtom(key);
}
}
public bool PreFilterMessage(ref System.Windows.Forms.Message m)
{
if (m.Msg == 0x312)
{
if (OnHotkey != null)
{
foreach (UInt32 key in keyIDs.Values)
{
if ((UInt32)m.WParam == key)
{
OnHotkey((int)m.WParam);
return true;
}
}
}
}
return false;
}
}
public void OnHotkey(int HotkeyID) //Ctrl+F2隱藏窗體,再按顯示窗體。
{
if (HotkeyID == Hotkey1)
{
if (this.Visible == true)
this.Visible = false;
else
this.Visible = true;
}
else
{
this.Visible = false;
}
}
private void Form1_Load(object sender, EventArgs e)
{
Hotkey hotkey;
hotkey = new Hotkey(this.Handle);
Hotkey1 = hotkey.RegisterHotkey(System.Windows.Forms.Keys.F2, Hotkey.KeyFlags.MOD_CONTROL); //定義快鍵(Ctrl + F2)
hotkey.OnHotkey += new HotkeyEventHandler(OnHotkey);
}
}
}
浙公網安備 33010602011771號