WPF开发经验-实现Win10虚拟触摸键盘
一 引入
項(xiàng)目有個(gè)需求,需要實(shí)現(xiàn)純觸控操作進(jìn)行鍵盤(pán)輸入。項(xiàng)目部署在Win10系統(tǒng)上,考慮有兩種方案來(lái)實(shí)現(xiàn)。
二 調(diào)用Win10自帶的觸摸鍵盤(pán)
簡(jiǎn)單附上一個(gè)調(diào)用Win10系統(tǒng)的TabTip.exe的操作類。
public class TabTipHelper {private const int WM_SYSCOMMAND = 274;private const uint SC_CLOSE = 61536;private const uint SC_RESTORE = 0xF120;private const uint SC_MAXIMIZE = 0xF030;private const uint SC_MINIMIZE = 0xF020;[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]private static extern bool PostMessage(IntPtr hWnd, int Msg, int wParam, int lParam);[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]private static extern bool PostMessage(IntPtr hWnd, int Msg, uint wParam, uint lParam);[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]private static extern bool PostMessage(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]private static extern IntPtr FindWindow(string lpClassName, string lpWindowName);[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]private static extern int RegisterWindowMessage(string lpString);public static int ShowTaptip(){try{dynamic file = "C:\\Program Files\\Common Files\\microsoft shared\\ink\\TabTip.exe";if (!System.IO.File.Exists(file))return -1;Process.Start(file);return 1;}catch (Exception){return 255;}}public static async Task ShowTaptipAsync(){await Task.Run(() => ShowTaptip());}public static void CloseTaptip(){var touchhWnd = new IntPtr(0);touchhWnd = FindWindow("IPTip_Main_Window", null);if (touchhWnd == IntPtr.Zero)return;PostMessage(touchhWnd, WM_SYSCOMMAND, SC_CLOSE, 0);} } View Code三 通過(guò)WPF實(shí)現(xiàn)一個(gè)觸摸鍵盤(pán)
下圖為demo效果:
當(dāng)TextBox獲取焦點(diǎn)時(shí),彈出鍵盤(pán)。當(dāng)TextBox失去焦點(diǎn)時(shí),隱藏鍵盤(pán)。
點(diǎn)擊鍵盤(pán)的右上角的關(guān)閉鍵或Esc鍵隱藏鍵盤(pán)。
因項(xiàng)目不需要全鍵位,所有針對(duì)性地對(duì)鍵位進(jìn)行了刪減和排列。
?3.1 SoftKeyboardControl控件
?使用WPF的UserControl實(shí)現(xiàn)虛擬鍵盤(pán),下附SoftKeyboardControl的后臺(tái)代碼。
/// <summary>/// SoftKeyboardControl.xaml 的交互邏輯/// </summary>public partial class SoftKeyboardControl : UserControl{/// <summary>/// Windows提供的一個(gè)模擬鍵盤(pán)API。/// Keybd_event()函數(shù)能觸發(fā)一個(gè)按鍵事件,生成一個(gè) WM_KEYDOWN 或 WM_KEYUP 消息。/// </summary>/// <param name="bVk" >按鍵的虛擬鍵值</param>/// <param name= "bScan" >掃描碼,一般不用設(shè)置,用0代替就行</param>/// <param name= "dwFlags" >選項(xiàng)標(biāo)志:0:表示按下,2:表示松開(kāi)</param>/// <param name= "dwExtraInfo">一般設(shè)置為0</param>[DllImport("User32.dll")]public static extern void keybd_event(byte bVK, byte bScan, int dwFlags, int dwExtraInfo);public SoftKeyboardControl(){InitializeComponent();CreateKeys();KeyCommand = new RoutedCommand();CommandBinding cmdBinding = new CommandBinding(KeyCommand, KeyCommand_Excuted, KeyCommand_CanExcute);CommandBindings.Add(cmdBinding);}#region 虛擬鍵值/// <summary>/// 鍵和虛擬鍵值的字典/// </summary>private Dictionary<string, byte> keys;/// <summary>/// 初始化虛擬鍵值的字典/// </summary>private void CreateKeys(){keys = new Dictionary<string, byte>(){#region 數(shù)字鍵盤(pán){ "0",0x60},{ "1",0x61},{ "2",0x62},{ "3",0x63},{ "4",0x64},{ "5",0x65},{ "6",0x66},{ "7",0x67},{ "8",0x68},{ "9",0x69},{ "-",0x6d},{ ".",0x6E},#endregion#region Q字母行{ "q", 0x51},{ "w", 0x57},{ "e", 0x45},{ "r", 0x52},{ "t", 0x54},{ "y", 0x59},{ "u", 0x55},{ "i", 0x49},{ "o", 0x4f},{ "p", 0x50},{ "Q", 0x51},{ "W", 0x57},{ "E", 0x45},{ "R", 0x52},{ "T", 0x54},{ "Y", 0x59},{ "U", 0x55},{ "I", 0x49},{ "O", 0x4f},{ "P", 0x50},#endregion#region A字母行{ "a", 0x41},{ "s", 0x53},{ "d", 0x44},{ "f", 0x46},{ "g", 0x47},{ "h", 0x48},{ "j", 0x4A},{ "k", 0x4B},{ "l", 0x4C},{ "A", 0x41},{ "S", 0x53},{ "D", 0x44},{ "F", 0x46},{ "G", 0x47},{ "H", 0x48},{ "J", 0x4A},{ "K", 0x4B},{ "L", 0x4C},#endregion#region Z字母行{ "z", 0x5A},{ "x", 0x58},{ "c", 0x43},{ "v", 0x56},{ "b", 0x42},{ "n", 0x4E},{ "m", 0x4D},{ "Z", 0x5A},{ "X", 0x58},{ "C", 0x43},{ "V", 0x56},{ "B", 0x42},{ "N", 0x4E},{ "M", 0x4D},#endregion#region other{"BackSpace",0x08 },{"Tab",0x09 },{"Enter",0x0d },{"Shift",0x10 },{"Ctrl",0x11 },{"CapsLock",0x14 },{"Space",0x20 },#endregion};}#endregion#region DependencyPropertypublic static readonly DependencyProperty CapsProperty = DependencyProperty.Register("Caps", typeof(bool), typeof(SoftKeyboardControl), new PropertyMetadata(default(bool)));public bool Caps{get { return (bool)GetValue(CapsProperty); }set { SetValue(CapsProperty, value); }}public static readonly DependencyProperty CtrlProperty = DependencyProperty.Register("Ctrl", typeof(bool), typeof(SoftKeyboardControl), new PropertyMetadata(default(bool)));public bool Ctrl{get { return (bool)GetValue(CtrlProperty); }set { SetValue(CtrlProperty, value); }}public static readonly DependencyProperty ShiftProperty = DependencyProperty.Register("Shift", typeof(bool), typeof(SoftKeyboardControl), new PropertyMetadata(default(bool)));public bool Shift{get { return (bool)GetValue(ShiftProperty); }set { SetValue(ShiftProperty, value); }}#endregion#region Commandpublic ICommand KeyCommand { get; set; }private void KeyCommand_CanExcute(object sender, CanExecuteRoutedEventArgs e){e.CanExecute = true;}private void KeyCommand_Excuted(object sender, ExecutedRoutedEventArgs e){if (e.Parameter != null){var code = e.Parameter.ToString();if (keys.ContainsKey(code)){byte b = keys[code];try{keybd_event(b, 0, 0, 0);}catch (Exception ex){Console.WriteLine(ex.Message);}}}}public ICommand CloseCommand { get; set; }#endregionprotected override void OnPropertyChanged(DependencyPropertyChangedEventArgs e){base.OnPropertyChanged(e);if (e.Property == CapsProperty){keybd_event(0x14, 0, 0, 0);//按下keybd_event(0x14, 0, 2, 0); //抬起}else if (e.Property == ShiftProperty){keybd_event(0x10, 0, 0, 0);keybd_event(0x10, 0, 2, 0);}else if (e.Property == CtrlProperty){keybd_event(0x11, 0, 0, 0);keybd_event(0x11, 0, 2, 0);}}}/// <summary>/// 大小寫(xiě)轉(zhuǎn)換/// </summary>public class UpperConverter : IValueConverter{public object Convert(object value, Type targetType, object parameter, CultureInfo culture){if (parameter == null){return "";}if (value == null){return parameter.ToString();}if ((bool)value){return parameter.ToString().ToUpper();}else{return parameter.ToString().ToLower();}}public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture){throw new NotImplementedException();}} View Code下附SoftKeyboardControl的前臺(tái)代碼。
注:其中按鈕的樣式是自己的控件庫(kù)中實(shí)現(xiàn)的,未貼出。
<UserControl x:Class="UI.View.SoftKeyboardControl"xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:d="http://schemas.microsoft.com/expression/blend/2008"xmlns:local="clr-namespace:UI.View"mc:Ignorable="d" Background="#E6E6E6"><UserControl.Resources><local:UpperConverter x:Key="UpperConverter"/></UserControl.Resources><StackPanel Margin="6 0 6 6"><StackPanel Height="40" Orientation="Horizontal" ><!--關(guān)閉按鈕--></StackPanel><StackPanel Orientation="Horizontal" Margin="0 6 0 0" ><StackPanel><WrapPanel><Button Content="Esc" Width="85" Height="Auto" Padding="0"Command="{Binding CloseCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" /><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=q}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=w}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=e}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=r}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=t}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=y}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=u}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=i}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=o}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=p}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/></WrapPanel><WrapPanel><ToggleButton Width="100" Content="Caps" IsChecked="{Binding Caps,Mode=TwoWay,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=a}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=s}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=d}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=f}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=g}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=h}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=j}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=k}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=l}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/></WrapPanel><WrapPanel><ToggleButton Width="115" Padding="-18 0 0 0 " Content="Shift" IsChecked="{Binding Shift,Mode=TwoWay,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=z}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=x}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=c}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=v}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=b}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=n}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="{Binding Path=Caps,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}},Converter={StaticResource UpperConverter},ConverterParameter=m}"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Width="125" Content="Enter"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/></WrapPanel><WrapPanel><ToggleButton Width="115" Padding="-28 0 0 0 " Content="Ctrl" IsChecked="{Binding Ctrl,Mode=TwoWay,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}"/><Button Content="Space" Width="185" Margin="50 0 0 0"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="BackSpace" Width="170" Margin="50 0 0 0"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/></WrapPanel></StackPanel><Grid Width="auto" Height="auto"><Grid.RowDefinitions><RowDefinition/><RowDefinition/><RowDefinition/><RowDefinition/></Grid.RowDefinitions><Grid.ColumnDefinitions><ColumnDefinition/><ColumnDefinition/><ColumnDefinition/><ColumnDefinition/></Grid.ColumnDefinitions><Button Content="7"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="8" Grid.Column="1" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="9" Grid.Column="2" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="4" Grid.Row="1" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="5" Grid.Row="1" Grid.Column="1" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="6" Grid.Row="1" Grid.Column="2" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="1" Grid.Row="2" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="2" Grid.Row="2" Grid.Column="1" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="3" Grid.Row="2" Grid.Column="2" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="-" Grid.Row="3" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="0" Grid.Row="3" Grid.Column="1" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="." Grid.Row="3" Grid.Column="2" Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/><Button Content="Esc" Grid.Row="0" Grid.Column="3" Grid.RowSpan="2" Margin="0,0,0,5" Width="56" Height="Auto" Padding="0"Command="{Binding CloseCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" /><Button Grid.Row="2" Grid.Column="3" Grid.RowSpan="2" Height="auto" Width="56" Margin="0 0 0 4" Padding="0" Content="Enter"Command="{Binding KeyCommand,RelativeSource={RelativeSource AncestorType={x:Type local:SoftKeyboardControl}}}" CommandParameter="{Binding Path=Content,RelativeSource={RelativeSource Self}}"/></Grid></StackPanel></StackPanel> </UserControl> View Code3.2 Demo界面的代碼
?下附Demo界面后臺(tái)代碼。
/// <summary>/// TestWindow.xaml 的交互邏輯/// </summary>public partial class TestWindow : Window{public TestWindow(){InitializeComponent();softKeyboard.CloseCommand = new RoutedCommand();CommandBinding cmdBinding = new CommandBinding(softKeyboard.CloseCommand, CloseCommand_Excuted, CloseCommand_CanExcute);CommandBindings.Add(cmdBinding);}private void CloseCommand_CanExcute(object sender, CanExecuteRoutedEventArgs e){e.CanExecute = popup.IsOpen;}private void CloseCommand_Excuted(object sender, ExecutedRoutedEventArgs e){popup.IsOpen = false;textBox.Focus();}private void TextBox_GotFocus(object sender, RoutedEventArgs e){popup.IsOpen = true;}private void TextBox_LostFocus(object sender, RoutedEventArgs e){popup.IsOpen = false;}} View Code下附Demo界面的前臺(tái)代碼。
<Window x:Class="UI.View.TestWindow"xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"xmlns:d="http://schemas.microsoft.com/expression/blend/2008"xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"mc:Ignorable="d"xmlns:view="clr-namespace:UI.View"Title="TestWindow" Height="800" Width="1400"><Grid x:Name="grid"><TextBox Margin="415,233,447,0" FontSize="30" Height="62" VerticalContentAlignment="Center" VerticalAlignment="Top"GotFocus="TextBox_GotFocus" LostFocus="TextBox_LostFocus" /><TextBox x:Name="textBox" Margin="470,343,503,364" /><Popup x:Name="popup"StaysOpen="True"AllowsTransparency="True"PopupAnimation="Fade"PlacementTarget="{Binding ElementName = grid}"Placement="Bottom"HorizontalOffset="250"VerticalOffset="-280"><view:SoftKeyboardControl x:Name="softKeyboard"/></Popup></Grid> </Window> View Code?四 參考鏈接
虛擬鍵碼 (Winuser.h) - Win32 apps | Microsoft Docs?
keybd_event函數(shù) (winuser.h) - Win32 應(yīng)用|微軟文檔 (microsoft.com)
WPF實(shí)現(xiàn)軟鍵盤(pán) - 我是剎那、 - 博客園 (cnblogs.com)
總結(jié)
以上是生活随笔為你收集整理的WPF开发经验-实现Win10虚拟触摸键盘的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: python 导出到excel ,打开e
- 下一篇: 2021年烟花爆竹产品涉药复审考试及烟花