0

MEF とMEFedMVVMというサードパーティ ライブラリを使用して WPF アプリケーションを作成しています。

親ビュー モデルが子ビュー モデルのコレクションを持つデザインを作成しようとしています。ビュー モデルをビュー モデルの外側に保持し、コードをより多くのビュー モデルに保つため、ビュー モデル ファーストのアプローチを使用したいと考えています。中心的で、より単体テストが可能です。

ビューに DataTemplate を使用することに関するこのディスカッションこのディスカッション、および汎用ビューを使用してモデル マッピング リソースを表示するというReed Copsy, Jr の提案を読みましたしかし、実際に機能するものを実装するのに苦労しています。

私の親ビューは非常に単純です:

<UserControl x:Class="MyParentView"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:meffed="clr-namespace:MEFedMVVM.ViewModelLocator;assembly=MEFedMVVM.WPF"
             meffed:ViewModelLocator.ViewModel="MyParentViewModel" />

親ビュー モデルは、IContextAwareを実装する基本型から派生します。

[ExportViewModel("MyParentViewModel")]
public class MyParentViewModel : ViewModelBase
{
    [ImportingConstructor]
    public MyParentViewModel()
    {
        var myChildVM = ServiceLocator.Current.GetInstance<MyChildViewModel>());
    }
}

これは子ビュー モデルです。

[Export(typeof(MyChildViewModel))]
[ExportViewModel("MyChildViewModel", true)]
public class MyChildViewModel : ViewModelBase
{
}

そして、これには対応するビューがあります:

<UserControl x:Class="MyChildView"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:meffed="clr-namespace:MEFedMVVM.ViewModelLocator;assembly=MEFedMVVM.WPF"
             meffed:ViewModelLocator.ViewModel="MyChildViewModel" />

最初は、 MyChildViewModelのExportViewModel属性に2 番目のブール値パラメーターを指定すると、ビューとビュー モデルがビューの XAML コードで一緒に MEF されるため、ビュー モデル ファーストのアプローチを使用してすべてが機能すると考えていました。しかし、これは事実ではなく、実際にMyParentViewModelコンストラクターでMyChildViewModelオブジェクトをインスタンス化するときにIContextAware.InjectContext()に渡されるのはMyParentViewオブジェクトです。私が期待して望んでいたMyChildViewオブジェクトではありません。明らかに、それらを結び付けるために何かを追加する必要があります。誰かがこれを行う方法の例を提供できますか?

ありがとう!

4

1 に答える 1

4

本当にview-model-firstを使用したい場合は、次のようにする必要があります。

[ExportViewModel("MyParentViewModel")]
public class MyParentViewModel : ViewModelBase
{
    // Create property for your child vm
    public MyChildViewModel Child {get; private set}

    // If you do MEF use constructor injection instead of servicelocator
    [ImportingConstructor]
    public MyParentViewModel(MyChildViewModel child)
    {
        this.Child = child;
    }
 }

次に、childvm のデータ テンプレートを定義します。

 <DataTemplate DataType="{x:Type local:MyChildViewModel}">
     <view:MyChildViewUserControl />
 </DataTemplate>

MainView では、子データを表示する場所を知っています。それ以外の場合は、子プロパティは必要ありません;) したがって、子データが移動する場所に ContentControl を配置し、プロパティにバインドするだけです。

例えば

<TabControl>
   <TabItem Header="MyChildData">
      <ContentControl Content="{Binding Child}" />
   </TabItem>
</TabControl>

PS: コードは IDE なしで記述されているため、エラーが発生する可能性があります :)

于 2012-04-30T05:58:40.240 に答える