IT rekvalifikace s garancí práce. Seniorní programátoři vydělávají až 160 000 Kč/měsíc a rekvalifikace je prvním krokem. Zjisti, jak na to!
Hledáme nové posily do ITnetwork týmu. Podívej se na volné pozice a přidej se do nejagilnější firmy na trhu - Více informací.
Avatar
matesax
Tvůrce
Avatar
matesax:14.9.2012 19:20

Dobrý den,
chtěl bych hlídat KeyDown mimo program. Ovšem funguje mi to jen v programu a navíc jen při rychle stisklých klávesách. Jinak dojde k selhání - viz nadpis. Chápu v čem je problém, ale co s tím? Děkuji.

https://gist.github.com/3723328

Kód použití:

public MainWindow()
{
    InitializeComponent();

    myKDP.KeyDown += new KeyEventHandler(Preview_KeyDown);
}

private void Preview_KeyDown(object sender, KeyEventArgs e)
{
    System.Windows.Forms.MessageBox.Show(e.KeyData.ToString());
    e.Handled = true;
}
 
Odpovědět
14.9.2012 19:20
Avatar
matesax
Tvůrce
Avatar
Odpovídá na matesax
matesax:15.9.2012 9:45

Vyřešeno nulováním delegáta...

using System;
using System.Windows.Forms;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.ComponentModel;

class KeyDownPreview
{
    #region Initialization

    private IntPtr Hook = IntPtr.Zero;

    public event KeyEventHandler KeyDown, KeyUp;

    [DllImport("user32.dll")]
    static extern IntPtr SetWindowsHookEx(int idHook, KeyboardHookProccess callback, IntPtr hInstance, uint threadId);

    [DllImport("user32.dll")]
    static extern bool UnhookWindowsHookEx(IntPtr hInstance);

    [DllImport("user32.dll")]
    static extern int CallNextHookEx(IntPtr idHook, int nCode, int wParam, ref KeyboardHookStruct lParam);

    [DllImport("kernel32.dll")]
    static extern IntPtr LoadLibrary(string lpFileName);

    public struct KeyboardHookStruct
    {
        public int KeyCode, ScanCode, Flags, Time, DwExtraInfo;
    }

    private delegate int KeyboardHookProccess(int code, int wParam, ref KeyboardHookStruct lParam);

    private const int WH_KEYBOARD_LL = 13, WM_KEYDOWN = 0x100, WM_KEYUP = 0x101, WM_SYSKEYDOWN = 0x104, WM_SYSKEYUP = 0x105;

    #endregion

    #region Main

    private static KeyboardHookProccess callbackDelegate;

    public KeyDownPreview()
    {
        var hInstance = LoadLibrary("User32");
        callbackDelegate = new KeyboardHookProccess(HookProccess);
        Hook = SetWindowsHookEx(WH_KEYBOARD_LL, callbackDelegate, hInstance, 0);

        if (Hook == IntPtr.Zero)
            throw new Win32Exception();
    }

    ~KeyDownPreview()
    {
        bool noOK = !UnhookWindowsHookEx(Hook);

        if (noOK)
            throw new Win32Exception();

        callbackDelegate = null;

    }

    public int HookProccess(int code, int wParam, ref KeyboardHookStruct lParam)
    {
        if (code >= 0)
        {
            var kea = new KeyEventArgs((Keys)lParam.KeyCode);

            if ((wParam == WM_KEYDOWN || wParam == WM_SYSKEYDOWN) && KeyDown != null)
            {
                KeyDown(this, kea);
            }
            else if ((wParam == WM_KEYUP || wParam == WM_SYSKEYUP) && KeyUp != null)
            {
                KeyUp(this, kea);
            }

            if (kea.Handled)
                return 1;
        }

        return CallNextHookEx(Hook, code, wParam, ref lParam);
    }

    #endregion
}

Jen to má nějakou divnou odezvu (dlouhou) - ale to snad půjde odchytit v programu...

 
Nahoru Odpovědět
15.9.2012 9:45
Děláme co je v našich silách, aby byly zdejší diskuze co nejkvalitnější. Proto do nich také mohou přispívat pouze registrovaní členové. Pro zapojení do diskuze se přihlas. Pokud ještě nemáš účet, zaregistruj se, je to zdarma.

Zobrazeno 2 zpráv z 2.