プロジェクト内のすべてのWPFウィンドウに「Escape-Key Press」動作を割り当てるにはどうすればよいですか?

StackOverflow https://stackoverflow.com/questions/3863431

質問

WPFアプリケーション全体に、現在焦点を絞った未亡人を閉鎖しようとすることでキープレスを逃れるために反応するように伝える簡単な方法はありますか?コマンドと入力のバインディングを手動でセットアップすることはあまり面倒ではありませんが、すべてのWindowsでこのXAMLを繰り返すことが最もエレガントなアプローチであるのだろうか?

<Window.CommandBindings>
        <CommandBinding Command="Close" Executed="CommandBinding_Executed" />
</Window.CommandBindings>
<Window.InputBindings>
        <KeyBinding Key="Escape" Command="Close" />
</Window.InputBindings>

建設的な提案は歓迎されます!

役に立ちましたか?

解決

それを改善することを提案できるのは、静的コマンドインスタンスにバインドすることにより、イベントハンドラーの必要性を削除することです。

注:これは.NET 4以降のみに機能します。 KeyBinding プロパティ。

まず、ウィンドウをパラメーターとして取得して呼び出すコマンドを作成します Close 以内 Execute 方法:

public class CloseThisWindowCommand : ICommand
{
    #region ICommand Members

    public bool CanExecute(object parameter)
    {
        //we can only close Windows
        return (parameter is Window);
    }

    public event EventHandler CanExecuteChanged;

    public void Execute(object parameter)
    {
        if (this.CanExecute(parameter))
        {
            ((Window)parameter).Close();
        }
    }

    #endregion

    private CloseThisWindowCommand()
    {

    }

    public static readonly ICommand Instance = new CloseThisWindowCommand();
}

その後、あなたはあなたをバインドすることができます KeyBinding 静的に Instance 財産:

<Window.InputBindings>
    <KeyBinding Key="Escape" Command="{x:Static local:CloseThisWindowCommand.Instance}" CommandParameter="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=Window}}" />
</Window.InputBindings>

私はこれが必ずしもそうであることを知りません より良い あなたのアプローチよりもですが、それはすべての上部でわずかに少ないボイラープレートを意味します Window そして、それぞれにイベントハンドラーを含める必要がないこと

他のヒント

または、キャンセルをテキストとして設定して設定したボタンを追加することもできます IsCancel = True. 。その後、エスケープはデフォルトのコマンドとして機能し、閉じることができます。

作成 RoutedUICommand 以下のように

 private static RoutedUICommand EscUICommand = new RoutedUICommand("EscBtnCommand"
       , "EscBtnCommand"
       , typeof(WindowName)
       , new InputGestureCollection(new InputGesture[] 
           { new KeyGesture(Key.Escape, ModifierKeys.None, "Close") }));

コンストラクターにコマンドバインディングを追加します

CommandBindings.Add(new CommandBinding(EscUICommand, (sender, e) => { this.Hide(); }));

の上 Windowで表示されます ShowDialog() 使用できます:

<!-- Button to close on Esc -->
<Button IsCancel="True" Width="0" Height="0"/>

PreviewKeyDownイベントを使用することもできます

PreviewKeyDown="UserControl_PreviewKeyDown"

Call You Closeコマンドの背後にあるコード

private void UserControl_PreviewKeyDown(object sender, System.Windows.Input.KeyEventArgs e)
        {
            if (e.Key == Key.Escape)
            {
                _vm.OnCloseCommand(sender);
            }
        }

別の可能な方法は、添付のプロパティを使用することです

Bellowは要点です:

<script src="https://gist.github.com/meziantou/1e98d7d7aa6aa859d916.js"></script>

上記のいずれも私のために働いていませんでしたが、カイのものを除いて。私は彼の答えを修正しました:「btn_close.iscancel = true;」を追加しました。コンストラクターへ。 SettingsWindowは私の2番目のウィンドウであり、メインウィンドウは(デフォルト)MainWindowです。

  public partial class SettingsWindow : Window {
    public SettingsWindow() {
      InitializeComponent();
      btn_close.IsCancel = true;
    }
    private void btn_close_Click(object sender, RoutedEventArgs e) {
      this.Close();
    }
  }

それが役に立てば幸い、

サイモンの愛ニア

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top