如何禁用按钮的 Enter 键
Posted
技术标签:
【中文标题】如何禁用按钮的 Enter 键【英文标题】:How to disable Enter Key for a Button 【发布时间】:2022-01-09 05:01:37 【问题描述】:我有一个绑定了命令的按钮以及 F1 键的键绑定。当焦点位于该按钮上时, Enter 键也会触发我不想要的命令。我希望仅在 F1 和鼠标单击时触发按钮。如何禁用此 Enter 键?
<Button Name="TestButton" Content="Run (F1)" Margin="10,4" Width="100" FontSize="16" Command="Binding TestRunCommand">
<Button.Style>
<Style TargetType="Button" BasedOn="StaticResource ResourceKey=BlackButton">
<Style.Triggers>
<DataTrigger Binding="Binding IsEnabled,ElementName=TestButton" Value="True">
<Setter Property="FocusManager.FocusedElement" Value="Binding ElementName=TestButton"/>
</DataTrigger>
</Style.Triggers>
</Style>
</Button.Style>
</Button>
我的按键绑定如下:
<UserControl.InputBindings>
<KeyBinding Key="F1" Command="Binding Path=TestViewModel.TestRunCommand"/>
</UserControl.InputBindings>
当我移除焦点触发器时,F1 键也不起作用。所以,我让 F1 键的这个 Setter
属性起作用。
【问题讨论】:
【参考方案1】:您可以为PreviewKeyDown
事件附加事件处理程序:
<Button Name="TestButton" Content="Run (F1)" Margin="10,4" Width="100" FontSize="16" Command="Binding TestRunCommand" PreviewKeyDown="OnPreviewKeyDown">
在事件处理程序中,检查 Enter 键并处理事件。
private void OnPreviewKeyDown(object sender, KeyEventArgs e)
e.Handled = (e.Key == Key.Enter || e.Key == key.Return);
一个更有创意的变体是创建一个不做任何事情的ICommand
。它将作为KeyBinding
绑定到 Enter 键,从而阻止原始命令。我创建了一个标记扩展,只是为了方便使用。
public class IgnoreCommandExtension : MarkupExtension
private static readonly IgnoreCommand IgnoreCommandInstance = new IgnoreCommand();
private class IgnoreCommand : ICommand
public bool CanExecute(object parameter)
return true;
public void Execute(object parameter)
public event EventHandler CanExecuteChanged;
public override object ProvideValue(IServiceProvider serviceProvider)
return IgnoreCommandInstance;
<Button Name="TestButton" Content="Run (F1)" Margin="10,4" Width="100" FontSize="16" Command="Binding TestRunCommand">
<Button.InputBindings>
<KeyBinding Key="Enter" Command="local:IgnoreCommand"/>
<KeyBinding Key="Return" Command="local:IgnoreCommand"/>
</Button.InputBindings>
<!-- ...other code. -->
</Button>
【讨论】:
添加了另一个使用键绑定而不是事件处理程序的变体。【参考方案2】:只需从<Button ...>
中删除Command="Binding TestRunCommand"
,按钮被按下时不会做任何事情。
这是一个最小且完整的示例:
<Window x:Class="WpfApp1.MainWindow"
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"
xmlns:local="clr-namespace:WpfApp1"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800">
<Window.DataContext>
<local:DC/>
</Window.DataContext>
<Window.InputBindings>
<KeyBinding Key="F1" Command="Binding Path=F1Command"/>
</Window.InputBindings>
<StackPanel>
<Button Name="TestButton" Content="Run (F1)" Margin="10,4" Width="100" FontSize="16"
Command="Binding TestRunCommand">
<!-- ^- remove this if you want it to do nothing -->
<Button.Style>
<Style TargetType="Button" >
<Style.Triggers>
<DataTrigger Binding="Binding IsEnabled,ElementName=TestButton" Value="True">
<Setter Property="FocusManager.FocusedElement" Value="Binding ElementName=TestButton"/>
</DataTrigger>
</Style.Triggers>
</Style>
</Button.Style>
</Button>
</StackPanel>
</Window>
以及背后的代码:
public class DC
public ICommand TestRunCommand
get return new CommandHandler(() => MessageBox.Show("Enter / Space / Click"), () => true);
public ICommand F1Command
get return new CommandHandler(() => MessageBox.Show("F1"), () => true);
public class CommandHandler : ICommand
private readonly Action _action;
private readonly Func<bool> _canExecute;
public CommandHandler(Action action, Func<bool> canExecute)
_action = action;
_canExecute = canExecute;
public event EventHandler CanExecuteChanged
add => CommandManager.RequerySuggested += value;
remove => CommandManager.RequerySuggested -= value;
public bool CanExecute(object parameter) => _canExecute.Invoke();
public void Execute(object parameter) => _action();
【讨论】:
删除该命令后,鼠标单击功能将不起作用。我希望在 2 种情况下触发按钮命令 - 鼠标单击和 F1 键。不使用 Enter。 好的...下次您可能希望保留原始要求而不更改问题。由于您不希望您的产品负责人在冲刺期间更改需求,因此我们不喜欢在这里更改问题。【参考方案3】:我终于想出了一个简单的方法来通过添加KeyboardNavigation.AcceptsReturn="False"
来阻止Enter Key。
<Button Name="TestButton" Content="Run (F1)" Margin="10,4" Width="100" FontSize="16" Command="Binding TestRunCommand" KeyboardNavigation.AcceptsReturn="False">
这行得通。
【讨论】:
以上是关于如何禁用按钮的 Enter 键的主要内容,如果未能解决你的问题,请参考以下文章