TextBox.TextChanged と ICommandSource
-
09-06-2019 - |
質問
私は以下をフォローしています M-V-VM 私の WPF UI のパターン。TextBox の TextChanged イベントへのコマンドを ViewModel クラス内のコマンドに接続したいと考えています。このタスクを完了する唯一の方法は、TextBox コントロールから継承し、ICommandSource を実装することです。その後、TextChanged イベントからコマンドを起動するように指示できます。とても単純そうに見えるものにとって、これは手間がかかりすぎるようです。
TextChanged イベントを ViewModel クラスにフックする簡単な方法 (TextBox をサブクラス化して ICommandSource を実装するよりも) はありますか?
解決
まず最初に、PropertyChanged の UpdateSourceTrigger を使用した、ビューモデルへの双方向データ バインディングを検討したことがあるはずです。そうすれば、テキストが変更されるたびにバインド先のプロパティのプロパティ セッターが呼び出されます。
それでも十分でない場合は、Attached Behaviours を使用してこの問題に取り組みます。Julian Dominguez のブログには、 記事 Silverlight で非常に似たことを行う方法について説明します。これは WPF にも簡単に適応できるはずです。
基本的に、静的クラス (たとえば TextBoxBehaviours と呼ばれる) で、(おそらく) ICommand 型の TextChangedCommand と呼ばれる添付プロパティを定義します。そのプロパティの OnPropertyChanged ハンドラーをフックし、ハンドラー内で、プロパティが TextBox に設定されていることを確認します。存在する場合は、プロパティで指定されたコマンドを呼び出すハンドラーをテキストボックスの TextChanged イベントに追加します。
次に、ビューモデルがビューの DataContext に割り当てられていると仮定すると、次のように使用します。
<TextBox
x:Name="MyTextBox"
TextBoxBehaviours.TextChangedCommand="{Binding ViewModelTextChangedCommand}" />
他のヒント
イベント バインディングとコマンド メソッドの使用は、適切な使用方法ではない可能性があります。このコマンドは具体的に何をするのでしょうか?
VM の文字列フィールドへのデータバインディングの使用を検討することをお勧めします。こうすることで、UI をまったく気にすることなく、そこからコマンドや関数を呼び出すことができます。
<TextBox Text="{Binding WorldName}"/>
....
public string WorldName
{
get
{
return WorldData.Name;
}
set
{
WorldData.Name = value;
OnPropertyChanged("WorldName");
// CallYourCustomFunctionHere();
}
}
TextChanged イベントを処理して、そこからコマンドを実行することはできないでしょうか?
private void _textBox_TextChanged(object sender, EventArgs e)
{
MyCommand.Execute(null);
}
あなたが言うように、代替案は、 TextBox
これはコマンド ソースとして機能しますが、多くの場所で共有して活用することを計画しているものでない限り、それはやりすぎのように思えます。