2009-07-28 110 views
3

我的程序我需要捕获当打印屏幕键被按下但它不工作(但它与其他键)。我如何捕获打印屏幕键?

我想这与Windows劫持我的权威有关,因为我仍然在这个新的,我很想知道我如何解决这个问题。

这里是我当前的代码:

namespace Boom_Screenshot_ 
{ 
    /// <summary> 
    /// Interaction logic for Window1.xaml 
    /// </summary> 
    public partial class Window1 : Window 
    { 
     //SETTINGS 
     Key TRIGGER_KEY = Key.PrintScreen; 

     public Window1() 
     { 
      InitializeComponent(); 
     } 

     private void Window_KeyDown(object sender, KeyEventArgs e) 
     { 
      if (e.Key == TRIGGER_KEY) 
      { 
       MessageBox.Show("'PrintScreen' was pressed."); 
      } 
     } 
    } 
} 

回答

7

我对你的答案,我发现here(我不会说中国话,所以不要问我它说什么:)。你必须设置一个钩子。他提供了一个包装类。我在这里重复一些代码,但没有中文字符。 RegisterHotKey.cs ...

using System; 
using System.Runtime.InteropServices; 
using System.Windows.Forms; 

namespace TestKeydown 
{ 
    public class RegisterHotKeyClass 
    { 
     private IntPtr m_WindowHandle = IntPtr.Zero; 
     private MODKEY m_ModKey = MODKEY.MOD_CONTROL; 
     private Keys m_Keys = Keys.A; 
     private int m_WParam = 10000; 
     private bool Star = false; 
     private HotKeyWndProc m_HotKeyWnd = new HotKeyWndProc(); 

     public IntPtr WindowHandle 
     { 
      get { return m_WindowHandle; } 
      set { if (Star)return; m_WindowHandle = value; } 
     } 
     public MODKEY ModKey 
     { 
      get { return m_ModKey; } 
      set { if (Star)return; m_ModKey = value; } 
     } 
     public Keys Keys 
     { 
      get { return m_Keys; } 
      set { if (Star)return; m_Keys = value; } 
     } 
     public int WParam 
     { 
      get { return m_WParam; } 
      set { if (Star)return; m_WParam = value; } 
     } 

     public void StarHotKey() 
     { 
      if (m_WindowHandle != IntPtr.Zero) 
      { 
       if (!RegisterHotKey(m_WindowHandle, m_WParam, m_ModKey, m_Keys)) 
       { 
        throw new Exception(""); 
       } 
       try 
       { 
        m_HotKeyWnd.m_HotKeyPass = new HotKeyPass(KeyPass); 
        m_HotKeyWnd.m_WParam = m_WParam; 
        m_HotKeyWnd.AssignHandle(m_WindowHandle); 
        Star = true; 
       } 
       catch 
       { 
        StopHotKey(); 
       } 
      } 
     } 
     private void KeyPass() 
     { 
      if (HotKey != null) HotKey(); 
     } 
     public void StopHotKey() 
     { 
      if (Star) 
      { 
       if (!UnregisterHotKey(m_WindowHandle, m_WParam)) 
       { 
        throw new Exception(""); 
       } 
       Star = false; 
       m_HotKeyWnd.ReleaseHandle(); 
      } 
     } 


     public delegate void HotKeyPass(); 
     public event HotKeyPass HotKey; 


     private class HotKeyWndProc : NativeWindow 
     { 
      public int m_WParam = 10000; 
      public HotKeyPass m_HotKeyPass; 
      protected override void WndProc(ref Message m) 
      { 
       if (m.Msg == 0x0312 && m.WParam.ToInt32() == m_WParam) 
       { 
        if (m_HotKeyPass != null) m_HotKeyPass.Invoke(); 
       } 

       base.WndProc(ref m); 
      } 
     } 

     public enum MODKEY 
     { 
      MOD_ALT = 0x0001, 
      MOD_CONTROL = 0x0002, 
      MOD_SHIFT = 0x0004, 
      MOD_WIN = 0x0008, 
     } 

     [DllImport("user32.dll")] 
     public static extern bool RegisterHotKey(IntPtr wnd, int id, MODKEY mode, Keys vk); 

     [DllImport("user32.dll")] 
     public static extern bool UnregisterHotKey(IntPtr wnd, int id); 
    } 
} 

调用窗体中的代码...

private RegisterHotKeyClass _RegisKey = new RegisterHotKeyClass(); 

void _Regis_HotKey() 
{ 
    MessageBox.Show("ok"); 
} 

private void Form1_Load(object sender, EventArgs e) 
{ 
    _RegisKey.Keys = Keys.PrintScreen; 
    _RegisKey.ModKey = 0; 
    _RegisKey.WindowHandle = this.Handle; 
    _RegisKey.HotKey += new RegisterHotKeyClass.HotKeyPass(_Regis_HotKey); 
    _RegisKey.StarHotKey(); 
} 
1

下面是我纯粹的WPF解决方案。

我们可以通过使用NavigationCommands(命名空间:System.Window.Input)在XAML实现这一类,它提供了一组标准的导航命令(如下一页,|上一页,刷新,搜索等)

实现方法:

因此,我们可以调用任何自定义代码使用NavigationCommands.Refresh应用刷新为

<UserControl.CommandBindings> 
<CommandBinding Command='NavigationCommands.Refresh' 
        Executed="ApplicationRefresh_Executed"> 
</CommandBinding> 
</UserControl.CommandBindings> 

现在在代码执行隐藏类用户控件的,我们可以定义方法

private void ApplicationRefresh_Executed(object sender, ExecutedRoutedEventArgs e) 
{ 
      // Implementation goes here. 
}