1

アプリケーションがあり、アセンブリがあります。

アプリケーションにはウィンドウがあり、アセンブリにはユーザー コントロールがあります。

ウィンドウにユーザー コントロールのインスタンスがあります。

ユーザー コントロールとウィンドウの両方が、個別のビューモデルによって支えられています。

ユーザーコントロールにはボタンがあります。ボタンは、ユーザー コントロールのビューモデルの状態に基づいて有効/無効にする必要があります。ボタンがクリックされると、ユーザー コントロールのビューモデルの情報に基づいて処理を実行する必要がありますが、ウィンドウのビューモデルで実行する必要があります。(ユーザー コントロールの範囲外で、実行する必要があることの側面があります。)

ここにねじれがあります。このユーザー コントロールは、このウィンドウだけで使用されるのではなく、別のウィンドウで使用されるか、3 番目のウィンドウで使用されるコントロールで使用される可能性があります。ユーザーコントロールは、それが含まれているウィンドウまたはコントロールの種類、またはボタンがクリックされたときにプロセスを処理していることを知ることはできません。

じゃあ何をすればいいの?

アセンブリでコマンドを定義し、ユーザー コントロールのボタンをそれにバインドして、ユーザー コントロールのビューモデルをコマンド パラメーターとして渡しますか? では、コマンドをウィンドウのビューモデルにバインドするにはどうすればよいでしょうか?

または、ユーザー コントロールのビューモデルでコマンドを定義し、イベントを発生させて、適切なアクションを実行する必要があることを親ウィンドウに通知する必要がありますか?

どちらがきれいかは私にはわかりません。

4

4 に答える 4

3

親のプロパティが同じ名前で同じように公開されることが常にわかっている場合は、次のようなことができます。これは私にとって何度もうまくいきました。

Command={Binding Parent.DataContext.SomeCommand, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}}

これはユーザーコントロールを取得し、次に親に行き、そのデータコンテキストを取得してそのコマンドにバインドします。これは、同じコマンドを公開する多くのウィンドウ/コントロールにユーザー コントロールが含まれる場合に機能します (ここでインターフェイスを実装できます)。

次のように、ユーザー コントロールのビューモデルをコマンドに渡すことができます (ここでも、何らかのインターフェイスを実装します)。

CommandParaemter={Binding }
于 2012-07-31T20:35:34.390 に答える
0

戦略パターンのケースのように聞こえます。http://en.wikipedia.org/wiki/Strategy_pattern

UserControl のビューモデルに割り当てることができる (または初期化に使用する) 戦略オブジェクトのインターフェイスを定義します。インターフェイスは、戦略オブジェクトが処理に必要なデータを UserControl ビューモデルから取得できるようにするために必要なプロパティ/メソッド/イベントを定義し、さらに処理の結果を UserControl ビューモデルに返す手段を定義します。

次に、ウィンドウのビューモデルと連携して必要なタスクを実行する戦略オブジェクトの具体的な実装を作成します。この場合、ウィンドウのビューモデルは戦略インターフェース自体を実装することさえあります。

他のシナリオの UserControl の他のインスタンスは、同じ必要なタスクを実行する戦略オブジェクトの他の具体的な実装で初期化できますが、方法が大きく異なる可能性があります。

于 2012-07-31T21:12:56.647 に答える
0

Messenger 構造を使用して ViewModel 間で通信できます。

MVVMLight には、使用できるもの、または独自に作成できるものが含まれています。

これを行う前に、責任を正しく分離したことを確認してください。そうしないと、スパゲッティ メッセージ コードになってしまいます。

于 2012-07-31T20:34:57.573 に答える
0

コントロールと同じように、ビュー モデルにも階層が必要です。メイン ウィンドウには子ユーザー コントロールがあります。メイン ビュー モデルは、ユーザー コントロール ビュー モデルに接続できる (必要に応じて割り当てられる) 必要があります。これが私がそれを行う方法です:

public class MainVM:NotificationObject
{
  // Make this a Notify Property
  public UserVM userVM { get{return _userVM;}; set {_userVM = value; RaisePropertyChanged("userVM");}

  public MainVM
{
  userVM = new UserVM();
  userVM.ExecuteCmd = new DelegateCommand (yourAction);

}

}

public class UserVM:NotificationObject
{

public DelegateCommand ExecuteCmd {get{return _executeCmd;} set{_executeCmd = value; RaisePropertyChanged("ExecuteCmd");
}

}

XAML:

<local:urUserCtrl DataContext={Binding userVM}/>

これはもちろん疑似コードです

于 2012-07-31T20:59:06.097 に答える