7

I'm working on wpf c# application and I need to detect when user press "/" but I'm having trouble with finding " / " e.Key, I saw there is Key.OemBackslash and stuffs like that, but I can't find right event for " / " (forward slash) ...

Thanks guys, Cheers

Roxy'Pro
  • 4,216
  • 9
  • 40
  • 102

2 Answers2

2

It should be Key.OemQuestion on a US keyboard. But on a Swedish keyboard it is D7 so it depends. The keys on the keyboard doesn't always produce the same character.

Depending on what you are trying to do you may be better off handling the PreviewTextInput event:

protected override void OnPreviewTextInput(TextCompositionEventArgs e)
{
    base.OnPreviewTextInput(e);
    if (e.Text == "/")
    {
        Debug.WriteLine("...");
    }
}
mm8
  • 163,881
  • 10
  • 57
  • 88
  • @I'm working with WPF and I'm using this event Window_PreviewKeyDown and looks like there is no propery Text for e.. – Roxy'Pro Feb 06 '17 at 13:23
  • No there isn't. That's why you could handle the PreviewTextInput of the WPF window instead of the PreviewKeyDown event...Otherwise Key.OemQuestion is the closest you get to a "/" key. – mm8 Feb 06 '17 at 13:24
  • by the way mate, then is there way to detect when enter is pressed? for example first check for a e.Text and after that check if enter is pressed, how could I do it if my sender is not KeyEventArgs, instead of that it is TextCompositionEventArgs .. and TextCompositionEventArgs does not contain e.Key== Key.Return.. – Roxy'Pro Feb 06 '17 at 19:39
  • Handle the PreviewKeyDown event to detect ENTER key presses and the PreviewTextInput event to detect "/"? ENTER is not a character and "/" is not a key. – mm8 Feb 06 '17 at 20:56
1

You can the following methods (see this site) to get the character from the key.

protected override void OnPreviewKeyDown(KeyEventArgs e)
{
        bool toUnicodeIsTrue=false;
        char t = GetCharFromKey(e.Key, ref toUnicodeIsTrue);
        if ( t == '/')
        {
            // do stuff
        }
        base.OnPreviewKeyDown(e);  
}


    public static char GetCharFromKey(System.Windows.Input.Key key, ref bool toUnicodeIsTrue)
    {
        toUnicodeIsTrue = true;
        char ch = ' ';

        // First, you need to get the VirtualKey code. Thankfully, there’s a simple class 
        // called KeyInterop, which exposes a static method VirtualKeyFromKey 
        // that gets us this information
        int virtualKey = System.Windows.Input.KeyInterop.VirtualKeyFromKey(key);
        //Then, we need to get the character. This is much trickier. 
        //First we have to get the keyboard state and then we have to map that VirtualKey 
        //we got in the first step to a ScanCode, and finally, convert all of that to Unicode, 
        //because .Net doesn’t really speak ASCII
        byte[] keyboardState = new byte[256];
        GetKeyboardState(keyboardState);

        uint scanCode = MapVirtualKey((uint)virtualKey, MapType.MAPVK_VK_TO_VSC);
        StringBuilder stringBuilder = new StringBuilder(2);

        int result = ToUnicode((uint)virtualKey, scanCode, keyboardState, stringBuilder, stringBuilder.Capacity, 0);
        switch (result)
        {
            case -1:
                toUnicodeIsTrue = false;
                break;
            case 0:
                toUnicodeIsTrue = false;
                break;
            case 1:
                {
                    ch = stringBuilder[0];
                    break;
                }
            default:
                {
                    ch = stringBuilder[0];
                    break;
                }
        }
        return ch;
    }

    [System.Runtime.InteropServices.DllImport("user32.dll")]
    public static extern bool GetKeyboardState(byte[] lpKeyState);
    [System.Runtime.InteropServices.DllImport("user32.dll")]
    public static extern uint MapVirtualKey(uint uCode, MapType uMapType);
    public enum MapType : uint
    {
        MAPVK_VK_TO_VSC = 0x0,
        MAPVK_VSC_TO_VK = 0x1,
        MAPVK_VK_TO_CHAR = 0x2,
        MAPVK_VSC_TO_VK_EX = 0x3,
    }
    [System.Runtime.InteropServices.DllImport("user32.dll")]
    public static extern int ToUnicode(
        uint wVirtKey,
        uint wScanCode,
        byte[] lpKeyState,
        [System.Runtime.InteropServices.Out, System.Runtime.InteropServices.MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPWStr, SizeParamIndex = 4)]
        StringBuilder pwszBuff,
        int cchBuff,
        uint wFlags);
}

My old Answer:

protected override void OnPreviewKeyDown(KeyEventArgs e)
{ //***
    if (e.Key == Key.Oem2)
    {  
        // do stuff
    }
    base.OnPreviewKeyDown(e);
}

Note that the name starts with "oem" (Original Equipment Manufacturer), which means the keyboard manufacturer is responsible for its functionality and it varies in local keyboards. So, you can set a break point in

{//*** 

line of my code and check e.Key property.

rmojab63
  • 3,513
  • 1
  • 15
  • 28