2017-03-01 40 views
1

最近我通过一些旧代码去,发现下面的代码如何统一容器将解决注册类型

public class ProfileModule : IModule 
{ 
    private readonly IRegionManager regionManager; 
    private readonly IUnityContainer container; 
    private IEventAggregator eventAggregator; 

    public ProfileModule(IUnityContainer c, IRegionManager r, IEventAggregator e) 
    { 
     container = c; 
     regionManager = r; 
     eventAggregator = e; 
    } 

    public void Initialize() 
    {  
     // Create and add profiles as new Tab items 
     container.RegisterType<IProfileViewModel, Profile1ViewModel>(new ContainerControlledLifetimeManager()); 
     regionManager.Regions[RegionNames.HomeRegion].Add(container.Resolve<ProfileView>());// HomeRegion is of type TabControl 

     container.RegisterType<IProfileViewModel, Profile2ViewModel>(new ContainerControlledLifetimeManager()); 
     regionManager.Regions[RegionNames.HomeRegion].Add(container.Resolve<ProfileView>()); 

     container.RegisterType<IProfileViewModel, Profile3ViewModel>(new ContainerControlledLifetimeManager()); 
     regionManager.Regions[RegionNames.HomeRegion].Add(container.Resolve<ProfileView>()); 
    } 
} 

下面是ProfileView.xaml.cs

public partial class ProfileView : INotifyPropertyChanged 
{ 
    [InjectionConstructor] 
    public ProfileView(IProfileViewModel vm) 
    { 
     DataContext = vm; 
     InitializeComponent(); 
    } 
} 

下面是viewModels

public abstract class ProfileViewModelBase : IProfileViewModel, IDataErrorInfo, INotifyPropertyChanged 
{ 
    public ProfileViewModelBase(IEventAggregator eventAggregator, IRegionManager regionManager) 
    { 

    } 
} 


public class Profile1ViewModel : ProfileViewModelBase 
{ 
    [InjectionConstructor] 
    public Profile1ViewModel(IEventAggregator eventAggregator, IRegionManager regionManager) 
     : base (eventAggregator, regionManager) 
    { 

    } 
} 

public class Profile2ViewModel : ProfileViewModelBase 
{ 
    [InjectionConstructor] 
    public Profile2ViewModel(IEventAggregator eventAggregator, IRegionManager regionManager) 
     : base (eventAggregator, regionManager) 
    { 

    } 
} 


public class Profile3ViewModel : ProfileViewModelBase 
{ 
    [InjectionConstructor] 
    public Profile3ViewModel(IEventAggregator eventAggregator, IRegionManager regionManager) 
     : base (eventAggregator, regionManager) 
    { 

    } 
} 

对我来说不清楚的部分代码是ProfileModule.Initialise()。 区域管理器每次添加视图时,都会创建一个新的ProfileView新实例,并且viewModel是最后一次注册的视图模型。

首次使用Profile1ViewModel创建ProfileView作为Datacontext。 第二次使用Profile2ViewModel创建ProfileView作为Datacontext。 第三次使用Profile3ViewModel创建ProfileView作为Datacontext。

  1. 容器如何确切地知道在创建视图时要创建哪个视图模型。
  2. 另外我明白,container.Resolve将返回视图,如果它已经有一个,第一次视图被创建并返回,第二次我除了相同的视图将被返回,但一个新的视图被创建。与第三个相同。

任何人都可以解释发生了什么?

回答

0

这里所说:

  1. 你能在Initialize方法里面看到的是,在注册后IProfileViewModel的代码,然后立即调用Resolve<ProfileView>其中第一Resolve正在提供Profile1ViewModelProfileView构造。然后第二个Register取代第一次注册Profile2ViewModel。因此,对Resolve的后续调用绝不会为您提供Profile1ViewModel的实例(或单例实例)。

  2. 如果由于某种原因,你真的想解析ProfileView的同一个实例,那么你需要将这个与Unity容器一起作为如下所示的单例使用:Register

    container.RegisterType(new ContainerControlledLifetimeManager());

这显然是假设你有一个interface定义了一个名为IProfileView

+0

的代码格式不显示 – Bijington

+0

谢谢Bijington一些很奇怪的原因。这回答我。 – JSR

+0

如果我们再次注册,我绝不会进行替换。在'Initilaise()'中,代码只是'regionManager.Regions [RegionNames.HomeRegion] .Add(new profileView(new profile1ViewModel()); regionManager.Regions [RegionNames.HomeRegion] .Add(new profileView(new profile2ViewModel() ); regionManager.Regions [RegionNames.HomeRegion] .Add(new profileView(new profile3ViewModel());'作为'container'将不会有任何对视图的引用并失去对viewModels的引用。 – JSR

相关问题