我有以下设置:
我使用MEF作为DI框架进行连接 我申请的各个部分。
我有两个地区:
填充一个(左侧) 列表视图(例如客户)
填充一个(右侧) 包含tabcontrol的视图 我居住的地区(根据 选择哪个客户) 另一个视图包含选项卡控件 与一个地区。
右侧结果:
要填充第一级tabcontrol,我正在听“客户更改的事件” - (这很有效)当我收到事件时,我会在第一级选项卡区域填充视图:
Dim lReg As IRegion = Me.mRegionManager.Regions("FirstLevelTabReqion")
Dim lViewID As String = CommonDefinitions.Constants.BuildFirstLevelViewName(lUniqueID)
Dim lFirstLevelView FirstLevelView = TryCast(lReg.GetView(lRqViewID), FirstLevelView)
If lFirstLevelView Is Nothing Then
lFirstLevelView = New FirstLevelView()
Dim lRegMan1 As IRegionManager = lReg.Add(lFirstLevelView, lViewID, True)
lFirstLevelView.SetRegionManager(lRegMan1)
...
End If
注意:创建FirstLevelView时,我必须进行CompositionInitializer.SatisfyImports
调用,以确保FirstLevelView解析其ViewModel引用。
要在SecondLevel ViewModel中获取EventsAggregator的实例,我使用:
<ImportingConstructor()>
Public Sub New(ByVal iEvAggregator As IEventAggregator)
EventAggregator = iEvAggregator
EventAggregator.GetEvent(Of DoStuffSecondLevel).Subscribe(AddressOf OnDoStuffSecondLevel, True)
End Sub
我的问题是我在第二级视图模型中获得的EventAggregator实例与第一级中的EventAggregator实例不同,因此如果我在第一级发布DoStuffSecondLevel,它将不会在第二级捕获。
为什么我得到2个不同的EventAggregator实例?
如何在整个应用程序中共享同一个EventAggregator实例?
提前致谢
答案 0 :(得分:3)
问题是MefBootstrapper创建了一个Container,但没有将它注册为DEFAULT容器。当调用SatisfyImports时,MEF看不到任何容器,因此它会创建一个新容器。这就是实例不同的原因,因为正在创建2个不同的容器。要解决此问题,只需将Prism容器设置为MEF的默认容器即可使用。
Silverlight解决方案(在您的引导程序中):
protected override void InitializeShell()
{
base.InitializeShell();
//Make the container the default one.
CompositionHost.Initialize(this.Container);
//Etc.
}
WPF(桌面)解决方案:
目前,我无法使桌面解决方案正常运行。问题是MEF的ExportFactory<T>
和ComponentInitializer
仅适用于Silverlight应用(为什么!?)。 Glen Block创建了一个库,可以访问System.ComponentModel.Composition.Initialization.dll
库的桌面版本。我试图使用它,但它失败了,因为在代码中,如果容器已经存在则设置为失败...再次,为什么?我没有尝试使用MEF2(Codeplex预览版)和这个解决方案,但我想它会更好(也许)。令人讨厌的部分是,如果您选择使用MEF2(Codeplex),您必须重建Prism二进制文件并用Codeplex MEF2库替换.NET 4 MEF库的所有引用。这使得Prism能够在没有抱怨的情况下使用Codeplex MEF2库。我将尝试看看是否这样做使得这个解决方案适用于WPF。