带有Unity容器的WPF - 如何注册ViewModels并将其解析为视图

isa*_*vis 6 wpf unity-container

嗨,我想在WPF MVVM应用程序中使用Unity容器.我没有使用Prism,因为它似乎很重.这是应用程序结构.我试图弄清楚如何解决视图到ViewModels和视图模型(服务)的依赖关系.

应用:

查看

MainWindow.xaml
CustomerList.xaml
CustomerDetail.xaml
BookList.xaml
BookDetail.xaml
Run Code Online (Sandbox Code Playgroud)

的ViewModels

MainViewModel

CustomerListViewModel

BoolListViewModel

BookDetailViewModel

CustomerDetailViewModel
Run Code Online (Sandbox Code Playgroud)

图书馆

ICustomerService (AddCustomer, SaveCustomer, GetCustomers, GetCustomer)

CustomerService:ICustomerService

IBookService (GetBooks, GetBook)

BookService:IBookService

IBookReserveService(Reserve, Return)

BookReserveService:IBookReserveService
Run Code Online (Sandbox Code Playgroud)
  1. MainViewModel需要引用ICustomerService和IBookService

  2. CustomerListViewModel需要引用ICustomerService

  3. BoolListViewModel需要引用IBookService

  4. BookDetailViewModel需要引用ICustomerService和IBookReserveService

  5. CustomerDetailViewModel需要引用ICustomerService和IBookReserveService

我在每个视图模型中都有getter setter属性.

我遇到的问题是如何在WPF中使用依赖注入,特别是对于Views和ViewModel.我尝试使用Unity在一个工作正常的控制台应用程序中注册和解决.但我想了解如何为WPF应用程序做到这一点.我试过注册

 container.RegisterType<ICustomerService, CustomerService>()
 container.RegisterType<IBookReserveService, BookReserveService>()
 container.RegisterType<IBookService, BookService>()
Run Code Online (Sandbox Code Playgroud)

并使用container.Resolve();

但我不知道如何判断哪个视图必须使用哪个视图模型并在需要时解决它们而不是应用程序启动时.此外,我不解决应用程序启动中的所有映射.应该在选择菜单(选择客户以查看详细信息,选择书籍以查看详细信息,保存客户,预订簿等)时执行此操作.

我读到的大部分内容都想使用IView和IViewModel.但不确定我是否理解其中的优势.

任何帮助是极大的赞赏.

Big*_*ddy 12

这是你可以做到这一点的一种方式.首先,使用Unity注册您的视图模型和服务:

// Unity is the container
_container.RegisterType<IMainViewModel, MainViewModel>();
_container.RegisterType<IBookService, BookService>();
Run Code Online (Sandbox Code Playgroud)

其次,将视图的DataContext设置为视图构造函数中的视图模型,如下所示:

public partial class MainView:UserControl
{
   private readonly IUnityContainer _container;

   public MainView(IUnityContainer container)
        {
            InitializeComponent();
            _container = container;   
            this.DataContext = _container.Resolve<IMainViewModel>();            
        }      
}
Run Code Online (Sandbox Code Playgroud)

第三,您需要将服务注入视图模型:

public MainViewModel(ICustomerService custService, IBookService bookService ){}
Run Code Online (Sandbox Code Playgroud)

还有其他方法可以使用.config文件等来完成此操作,但这应该足以让您开始使用,如果您需要更多,请告诉我.你问过DI的优点是什么,有很多,我觉得.仅举几例:促进组件之间的松散耦合和提高可测试性.我觉得这是一个好的设计/实现的关键之一.

更新:

使用Unity> = 3,如果您遵循以下命名约定,则可以跳过容器注册:

// This will register all types with a ISample/Sample naming convention 
            container.RegisterTypes(
                AllClasses.FromLoadedAssemblies(),
                WithMappings.FromMatchingInterface,
                WithName.Default);
Run Code Online (Sandbox Code Playgroud)