博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Prism 5程序初始化过程
阅读量:5161 次
发布时间:2019-06-13

本文共 10394 字,大约阅读时间需要 34 分钟。

Prism在运行程序前,需要的组件像其他大部分程序架构一样在初始化阶段完成。Prism将这个启动加载器命名为Bootstarpper。在Bootstarpper中,按顺序加载一系列组件,如,moduleCatalog,container,还有UI的 regionAdapter,shell和module等等。

Bootstrapper

在Prism中,自带有基于Unity和MEF两种DI容器的Bootstrapper,分别为UnityBootstrapper和MEFBootstrapper。此文所有介绍都基于UnityBootstrapper,当然我们也可以定义自己的启动器(开闭原则,在后面的文章中还有很多类似的设计原则和设计模式)。Bootstrapper大部分方法是虚拟方法,定义如下:

1 #region 程序集 Microsoft.Practices.Prism.Composition.dll, v5.0.0.0  2 // F:\RefrenceProject\compositewpf-ff6316df3dadd0d24083d51aa1dea922d07fb47e\V5\Quickstarts\Hello World\HelloWorld.Desktop\packages\Prism.Composition.5.0.0\lib\NET45\Microsoft.Practices.Prism.Composition.dll  3 #endregion  4   5 using Microsoft.Practices.Prism.Logging;  6 using Microsoft.Practices.Prism.Modularity;  7 using Microsoft.Practices.Prism.Regions;  8 using System;  9 using System.Windows; 10  11 namespace Microsoft.Practices.Prism 12 { 13     // 摘要:  14     //     Base class that provides a basic bootstrapping sequence and hooks that specific 15     //     implementations can override 16     // 17     // 备注:  18     //     This class must be overridden to provide application specific configuration. 19     public abstract class Bootstrapper 20     { 21         protected Bootstrapper(); 22  23         // 摘要:  24         //     Gets the Microsoft.Practices.Prism.Logging.ILoggerFacade for the application. 25         protected ILoggerFacade Logger { get; set; } 26         // 27         // 摘要:  28         //     Gets the default Microsoft.Practices.Prism.Modularity.IModuleCatalog for 29         //     the application. 30         protected IModuleCatalog ModuleCatalog { get; set; } 31         // 32         // 摘要:  33         //     Gets the shell user interface 34         protected DependencyObject Shell { get; set; } 35  36         // 摘要:  37         //     Configures the Microsoft.Practices.Prism.Regions.IRegionBehaviorFactory. 38         //     This will be the list of default behaviors that will be added to a region. 39         protected virtual IRegionBehaviorFactory ConfigureDefaultRegionBehaviors(); 40         // 41         // 摘要:  42         //     Configures the Microsoft.Practices.Prism.Modularity.IModuleCatalog used by 43         //     Prism. 44         protected virtual void ConfigureModuleCatalog(); 45         // 46         // 摘要:  47         //     Configures the default region adapter mappings to use in the application, 48         //     in order to adapt UI controls defined in XAML to use a region and register 49         //     it automatically.  May be overwritten in a derived class to add specific 50         //     mappings required by the application. 51         // 52         // 返回结果:  53         //     The Microsoft.Practices.Prism.Regions.RegionAdapterMappings instance containing 54         //     all the mappings. 55         protected virtual RegionAdapterMappings ConfigureRegionAdapterMappings(); 56         // 57         // 摘要:  58         //     Configures the LocatorProvider for the Microsoft.Practices.ServiceLocation.ServiceLocator. 59         protected abstract void ConfigureServiceLocator(); 60         // 61         // 摘要:  62         //     Create the Microsoft.Practices.Prism.Logging.ILoggerFacade used by the bootstrapper. 63         // 64         // 备注:  65         //     The base implementation returns a new TextLogger. 66         protected virtual ILoggerFacade CreateLogger(); 67         // 68         // 摘要:  69         //     Creates the Microsoft.Practices.Prism.Modularity.IModuleCatalog used by Prism. 70         // 71         // 备注:  72         //     The base implementation returns a new ModuleCatalog. 73         protected virtual IModuleCatalog CreateModuleCatalog(); 74         // 75         // 摘要:  76         //     Creates the shell or main window of the application. 77         // 78         // 返回结果:  79         //     The shell of the application. 80         // 81         // 备注:  82         //     If the returned instance is a System.Windows.DependencyObject, the Microsoft.Practices.Prism.Bootstrapper 83         //     will attach the default Microsoft.Practices.Prism.Regions.IRegionManager 84         //     of the application in its Microsoft.Practices.Prism.Regions.RegionManager.RegionManagerProperty 85         //     attached property in order to be able to add regions by using the Microsoft.Practices.Prism.Regions.RegionManager.RegionNameProperty 86         //     attached property from XAML. 87         protected abstract DependencyObject CreateShell(); 88         // 89         // 摘要:  90         //     Initializes the modules. May be overwritten in a derived class to use a custom 91         //     Modules Catalog 92         protected virtual void InitializeModules(); 93         // 94         // 摘要:  95         //     Initializes the shell. 96         protected virtual void InitializeShell(); 97         // 98         // 摘要:  99         //     Registers the System.Types of the Exceptions that are not considered root100         //     exceptions by the Microsoft.Practices.Prism.ExceptionExtensions.101         protected virtual void RegisterFrameworkExceptionTypes();102         //103         // 摘要: 104         //     Runs the bootstrapper process.105         public void Run();106         //107         // 摘要: 108         //     Run the bootstrapper process.109         //110         // 参数: 111         //   runWithDefaultConfiguration:112         //     If true, registers default Prism Library services in the container. This113         //     is the default behavior.114         public abstract void Run(bool runWithDefaultConfiguration);115     }116 }
View Code

Bootstrapper初始化的顺序如下:

Basic stages of the bootstrapping process

 

上图不难理解,软件记录日志,包括Bootstrapper的启动过程,所以Logger启动在第一位,生成和配置DI容器放在第三位,因为下面所有的操作依赖于使用容器解耦,,ModuleCatalog,并不依赖DI容器,可以放在第二位,下面的RegionAdapter和RegionBehavior也差不多意思,至于为什么Module放在最后,其实也无他,也是因为Module(模块)属于Shell(主窗体)。

因此,在使用Prism前,你必须先决定:

  1. 使用Unity或MEF,或其他DI容器。当然,如果使用其他注入容器,也决定了要自定义Bootstrapper。
  2. 你还可能需要把你程序的服务注册到container(DI容器),以方便各个Module(模块)的解释使用。
  3. 决定内置的日志组件是否适合,否则重写CreateLogger。
  4. 决定如何注册你的Module,使用配置文件还是XAML还是目录发现(需要在模块类使用特征标识 )还是直接写死在代码。

选择DI容器,很easy,熟悉哪种选哪种,使用也很简单,只需要继承一下就可以。

using System.Windows;using Microsoft.Practices.Prism.Modularity;using Microsoft.Practices.Unity;using Microsoft.Practices.Prism.UnityExtensions;namespace HelloWorld{    class Bootstrapper : UnityBootstrapper    {                   }

 

Bootstrapper是Prism的入口,因此,要指定APP.xaml的Bootstrapper

1 using System.Windows; 2  3 namespace HelloWorld 4 { 5     ///  6     /// Interaction logic for App.xaml 7     ///  8     public partial class App : Application 9     {10         protected override void OnStartup(StartupEventArgs e)11         {12             base.OnStartup(e);13             Bootstrapper bootstrapper = new Bootstrapper();14             bootstrapper.Run();15         }16     }17 }
View Code

 

CreateShell

createShell是必须要继承的,因为必须指定主窗体。

class Bootstrapper : UnityBootstrapper    {        protected override DependencyObject CreateShell()        {            return this.Container.Resolve
(); } }

这里使用DI容器的Resolve方法,这种方法的好处是把Shell所有需要的引用的DLL都自动引入。当然也可直接new一个主窗体对象出来。

进一步,可以使用ServiceLocator,ServiceLocator也是IOC的一种实现,类似DI也是IOC的一种实现。ServiceLocator最终还是调用DI容器,至于是Unity还是MEF,这是ServiceLocator要关心的事了,我们在这不作更深入的了解。

protected override DependencyObject CreateShell(){    return ServiceLocator.Current.GetInstance
();}

InitializeShell 

Shell初始化所需的工作应该写在这里。

protected override void InitializeShell(){    Application.Current.MainWindow = Shell;    Application.Current.MainWindow.Show();}

当然也可以把所有初始化工作写到CreateShell()里,IntializeShell不重写,但总感觉有点怪怪的。

CreateModuleCatalog

在调用CreateModuleCatalog之前,Prism会调用CreateModuleCatalog,生成ModuleCatalog。使用模块化开发,需要实现CreateModuleCatalog方法添加Module。

protected override void ConfigureModuleCatalog()        {            base.ConfigureModuleCatalog();            ModuleCatalog moduleCatalog = (ModuleCatalog)this.ModuleCatalog;            moduleCatalog.AddModule(typeof(HelloWorldModule.HelloWorldModule));        }

ConfigureContainer

配置Container(DI容器),Container在Prism中具有非常重要的角色,在使用Prism开发的代码中,常常见到这个家伙。在Container的配置阶段,需要把核心服务注册到Container,当然也要把业务上的关键服务注册到Container。

基类代码实现如下:

1         protected virtual void ConfigureContainer() 2         { 3             this.Logger.Log(Resources.AddingUnityBootstrapperExtensionToContainer, Category.Debug, Priority.Low); 4             this.Container.AddNewExtension
(); 5 6 Container.RegisterInstance
(Logger); 7 8 this.Container.RegisterInstance(this.ModuleCatalog); 9 10 if (useDefaultConfiguration)11 {12 RegisterTypeIfMissing(typeof(IServiceLocator), typeof(UnityServiceLocatorAdapter), true);13 RegisterTypeIfMissing(typeof(IModuleInitializer), typeof(ModuleInitializer), true);14 RegisterTypeIfMissing(typeof(IModuleManager), typeof(ModuleManager), true);15 RegisterTypeIfMissing(typeof(RegionAdapterMappings), typeof(RegionAdapterMappings), true);16 RegisterTypeIfMissing(typeof(IRegionManager), typeof(RegionManager), true);17 RegisterTypeIfMissing(typeof(IEventAggregator), typeof(EventAggregator), true);18 RegisterTypeIfMissing(typeof(IRegionViewRegistry), typeof(RegionViewRegistry), true);19 RegisterTypeIfMissing(typeof(IRegionBehaviorFactory), typeof(RegionBehaviorFactory), true);20 RegisterTypeIfMissing(typeof(IRegionNavigationJournalEntry), typeof(RegionNavigationJournalEntry), false);21 RegisterTypeIfMissing(typeof(IRegionNavigationJournal), typeof(RegionNavigationJournal), false);22 RegisterTypeIfMissing(typeof(IRegionNavigationService), typeof(RegionNavigationService), false);23 RegisterTypeIfMissing(typeof(IRegionNavigationContentLoader), typeof(UnityRegionNavigationContentLoader), true);24 }25 }
View Code

如果我们只是实现业务,不需要对Prism二次开发的话,对业务服务的注册,只需要重写ConfigureContainer即可。

class Bootstrapper : UnityBootstrapper    {        protected override void ConfigureContainer()        {            base.ConfigureContainer();            this.RegisterTypeIfMissing(typeof(IModuleTracker), typeof(ModuleTracker), true);            this.Container.RegisterInstance
(this.callbackLogger); } }

 

至此,Prism的初始化已介绍完毕。

 

转载于:https://www.cnblogs.com/andyho/p/5160520.html

你可能感兴趣的文章
[NOIp提高组2016]组合数问题
查看>>
[转]反向迭代器(rbegin,rend)
查看>>
perl的正则表达式
查看>>
[BOT]自己动手实现android 饼状图,PieGraphView,附源码解析
查看>>
java程序设计基础篇 复习笔记 第一单元
查看>>
ANDROID笔记:ListView和CheckBox的简单使用
查看>>
Oracle截取字符串和查找字符串
查看>>
Heaps(Contest2080 - 湖南多校对抗赛(2015.05.10)(国防科大学校赛决赛-Semilive)+scu1616)...
查看>>
PIL
查看>>
IOS之weak
查看>>
打开局域网共享文件(映射)
查看>>
spark2.1:读取hive中存储的多元组(string,double)失败
查看>>
轮胎在地面上滚动压出轮胎的痕迹的动画
查看>>
HttpSession与Hibernate中Session的区别
查看>>
平面二维DP
查看>>
移动端适配
查看>>
csharp: datatable get Column datatype or Column Name
查看>>
ci框架基础知识点
查看>>
BZOJ 1835 [ZJOI2010]基站选址 (线段树优化DP)
查看>>
rman命令
查看>>