我明白你在想什么,但是提出的解决方案并没有真正满足RegionManager的设计目标。特别是:
- 区域请求是类型不可知的。如果您没有对模块B中的模块A中的某个类型的引用,但想要在那里导航,那么如何在没有这些模块相互引用或将这些类型重构为第三个程序集的情况下进行导航?
- 根据需要,区域可以有多个特定类型的视图。您提出的解决方案会将特定类型的视图数量限制为一个,这并不是区域的工作方式。
虽然这并不回答你的问题。
至于减少冗长度,除了在RegionManager前封装您想要的行为的自己的解决方案之外,您可以做的不多。就我个人而言,我不会走这条路,但它肯定是你可以做的。您可以将其作为您自己的服务编写,或者只是IRegionManager或IRegion上的扩展方法。
public interface IMyNavigationService
{
//Your own implementation could use (typeof(T)).Name (or
//AttributedModelServices.GetContractName(typeof(T)) if using MEF)
//as the Key, if thatis appropriate for your solution
//(1 instance T per region and references to T from all Modules)
void RequestNavigation<T>();
}
它看起来像一个开关,以MEF作为IoC容器可以帮助您的需求...它只是取决于它的几行代码,你不关心的。对我而言,我不喜欢RegisterType<object, InboxView>
。在MEF相当于是:
[Export]
public class InboxView { .. }
你可以在这里提供一份合同名称([Export("InboxView")]
),但默认情况下它会提供的AttributedModelServices.GetContractName(typeof(InboxView))
合同名称。只要您选择的内容与您选择在IMyNavigationService的实现中生成名称的方式一致,它应该可以正常工作。
下面是同样的事情,但是使用扩展方法实现(使用MEF实现...如果您使用Unity,您可以选择一些其他密钥生成方法...你只需要添加该类型的登记方法以及)
public static class RegionExtensions
{
public static void RequestNavigate<T>(this IRegion region)
{
region.RequestNavigate(AttributedModelServices.GetContractName(typeof(T)));
}
}
如果您担心切换一切MEF,有MefContrib project,使这更简单...它基本上结合了团结和MEF在一个。
希望这会有所帮助。
是你的问题,你必须注册所有视图模型或所有视图?你的例子并不清楚。除此之外,不需要映射名称“InboxView”作为RegisterType的参数。 –
PVitt
2011-05-16 11:52:57
@PVitt,是的。那是我的问题。我希望这些映射是自动化的,实际上我正在考虑通过继承区域并重写或映射RequestNavigate方法(在其中添加视图注册表)(IUnityContiner将注入其构造函数),您怎么看?顺便说一句,我已经向Prism codeplex网站发布了一个[建议](http://compositewpf.codeplex.com/workitem/8255),请查看/投票。 – Shimmy 2011-05-17 19:32:38
@Shimmy:对于具体的类型,你不必做一个RegisterType来允许容器实例化它。但是,出于某种原因,您正在映射所有请求以将“object”类型的对象实例化为InboxView类型。我会直言不讳地说,如果你必须这样做,那么你做错了什么。 – 2011-05-20 00:33:17