WPF WebBrowser control – part 3

Showing the Windows 8 touch keyboard

The WPF WebBrowser control does not natively support touchscreens. To make an application easily usable even on touch devices, you need to provide at least one capability: the tablet keyboard must appear whenever the user touches an editable field and moves the focus there.

In part 2 we saw how you can register to DOM events and handle them in .NET code. Ideally, to make the keyboard appear, you will register a handler for every significant field (input, textarea, etc…) and lauch the keyboard process in the body of the callback.

Making the keyboard appear is quite trivial. In Windows 8/8.1, it is as simple as starting the executable at C:\Program Files\Common Files\microsoft shared\ink\TabTip.exe. The following code will do the trick:


    public static void ShowTouchKeyboard()
    {
        using (var keyboard = new Process())
        {
            keyboard.StartInfo = new ProcessStartInfo(@"C:\Program Files\Common Files\microsoft shared\ink\TabTip.exe", "/ManualLaunch");
            keyboard.Start();
        }
    }

Once the field has lost the focus, you may want to hide the keyboard. This is a bit more complicated. First, also for this case, you need to register to the appropriate DOM event on the managed elements (e.g. onblur). Then, you need to rely on the Windows API in order to find the window corresponding to the keyboard process and send it a message to close it. The following code fragment can be added to the WebBrowserAdapter class that we already know from part 2 of this series:


public static readonly int WM_SYSCOMMAND = 274;
public static readonly uint SC_CLOSE = 61536;

[DllImport("user32.dll")]
public static extern IntPtr FindWindow(String sClassName, String sAppName);

[DllImport("user32.dll")]
public static extern IntPtr PostMessage(IntPtr KeyboardWnd, int WM_SYSCOMMAND, uint SC_CLOSE, int p);

public static void ShowTouchKeyboard()
{
    using (var keyboard = new Process())
    {
        keyboard.StartInfo = new ProcessStartInfo(@"C:\Program Files\Common Files\microsoft shared\ink\TabTip.exe", "/ManualLaunch");
        keyboard.Start();
    }
}

public static void CloseTouchKeyboard()
{
    IntPtr keyboardWnd = FindWindow("IPTip_Main_Window", null);
    if (!keyboardWnd.Equals(IntPtr.Zero))
    {
        PostMessage(keyboardWnd, WM_SYSCOMMAND, SC_CLOSE, 0);
    }
}

Leave a comment