Prism 的 Unity 容器之註冊與解析
這是我第一篇關於 Prism 方面的文章,在這篇筆記中,將會說明如何透過 Prism 容器 (Container),進行型別、物件的註冊,並且稍後可以解析方式,取得當初註冊的內容值。
擴充 RegisterTypes 方法
在 App.xaml.cs檔案內,因為,App 類別是繼承 PrismApplication 類別,因此,在 App 類別內,可以覆寫 RegisterTypes,在這個方法之內,可以註冊其他的型別到容器內。
當您僅僅使用 Xamarin.Forms 的 MVVM 架構來開發,可以在這裡簡單的使用 Container.RegisterTypeForNavigation 來註冊 View & ViewModle 的類別,當View產生的時候,會自動注入。
App.xaml.cs
public partial class App : PrismApplication
{
protected override void OnInitialized()
{
InitializeComponent();
NavigationService.Navigate("MainPage?title=Hello%20from%20Xamarin.Forms");
}
protected override void RegisterTypes()
{
Container.RegisterTypeForNavigation<MainPage>();
}
}
其他的使用方法
底下的程式碼說明了
註冊介面對應到一個類別或這具體的型別
, 註冊一個類別或者型別,但具有 singleton 執行個體
這兩件事情,但是,不論要做哪件事情,都需要先取得系統預設的容器,您可以透過這段程式碼 :IUnityContainer myContainer = (App.Current as PrismApplication).Container;
,隨時取得系統內的容器。 IUnityContainer myContainer = (App.Current as PrismApplication).Container;
#region 註冊介面對應到一個類別或這具體的型別
// 註冊一個預設、沒有命名名稱的型別對應,並且使用短暫(transient)生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>();
// 取得新產生的執行個體
var fooObject = myContainer.Resolve<IMyClass>();
// 註冊一個預設、有命名名稱的型別對應,並且使用短暫(transient)生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>("MyMapping");
// 使用已經命名名稱,取得新產生的執行個體
fooObject = myContainer.Resolve<IMyClass>("MyMapping");
// 註冊一個預設、沒有命名名稱的型別對應,並且使用每個執行緒(per thread)生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>(new PerThreadLifetimeManager());
// 在相同執行續下,將會取得相同 singleton 執行個體,容器將會持有僅僅一個弱參考的執行個體
// https://msdn.microsoft.com/zh-tw/library/ms404247(v=vs.110).aspx
fooObject = myContainer.Resolve<IMyClass>();
// 註冊一個預設、沒有命名名稱的型別對應,並且使用額外控制(externally-controlled)生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>(new ExternallyControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會持有僅僅一個弱參考的執行個體
fooObject = myContainer.Resolve<IMyClass>();
// 註冊一個預設、有命名名稱的型別對應,並且使用額外控制(externally-controlled)生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>("MyMapping", new ExternallyControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會持有僅僅一個弱參考的執行個體
fooObject = myContainer.Resolve<IMyClass>("MyMapping");
#endregion
#region 註冊一個類別或者型別,但具有 singleton 執行個體
// https://msdn.microsoft.com/en-us/library/dn507499(v=pandp.30).aspx
// 註冊一個預設、沒有命名名稱的型別對應,並且使用 singleton 生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>(new ContainerControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會負責接管該物件生命週期管理
fooObject = myContainer.Resolve<IMyClass>();
// 註冊一個預設、有命名名稱的型別對應,並且使用 singleton 生命週期(lifetime)管理
myContainer.RegisterType<IMyClass, MyClass>("MyMapping", new ContainerControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會負責接管該物件生命週期管理
myContainer.Resolve<IMyClass>();
// 註冊一個沒有型別對應,並且使用 singleton 生命週期(lifetime)管理,使用容器僅建置 singletone 行為
myContainer.RegisterType<MyClass>(new ContainerControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會負責接管該物件生命週期管理
fooObject = myContainer.Resolve<MyClass>();
// 註冊一個有命名名稱,但沒有型別對應,並且使用 singleton 生命週期(lifetime)管理,使用容器僅建置 singletone 行為
myContainer.RegisterType<MyClass>("MyMapping", new ContainerControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會負責接管該物件生命週期管理
fooObject = myContainer.Resolve<MyClass>("MyMapping");
#endregion
底下的程式碼說明了
註冊一個存在物件,使其成為 singleton 執行個體
IUnityContainer myContainer = (App.Current as PrismApplication).Container;
#region 註冊一個存在物件,使其成為 singleton 執行個體
var fooMyClassObject = new MyClass();
// 註冊一個存在物件為預設、沒有命名名稱、使用預設容器控制器(container-controlled)生命週期管理
myContainer.RegisterInstance<IMyClass>(fooMyClassObject);
// 取得 singleton 執行個體,容器將會接管這個物件的生命週期管理
var fooObject = myContainer.Resolve<IMyClass>();
// 註冊一個存在物件為預設、有命名名稱、使用預設容器控制器(container-controlled)生命週期管理
myContainer.RegisterInstance<IMyClass>("MySingleton", fooMyClassObject);
// 取得 singleton 執行個體,容器將會接管這個物件的生命週期管理
fooObject = myContainer.Resolve<IMyClass>("MySingleton");
// 註冊一個存在物件為預設、有命名名稱、使用指定容器控制器(container-controlled) ContainerControlledLifetimeManager 生命週期管理
myContainer.RegisterInstance<IMyClass>("MySingleton", fooMyClassObject, new ContainerControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會接管這個物件的生命週期管理
fooObject = myContainer.Resolve<IMyClass>("MySingleton");
// 註冊一個存在物件為預設、沒有命名名稱、使用額外控制(externally controlled)生命週期管理
myContainer.RegisterInstance<IMyClass>(fooMyClassObject, new ExternallyControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會持有僅僅一個弱參考的物件
fooObject = myContainer.Resolve<IMyClass>();
// 註冊一個存在物件為預設、有命名名稱、使用額外控制(externally controlled)生命週期管理
myContainer.RegisterInstance<IMyClass>("MySingleton", fooMyClassObject, new ExternallyControlledLifetimeManager());
// 取得 singleton 執行個體,容器將會持有僅僅一個弱參考的物件
fooObject = myContainer.Resolve<IMyClass>("MySingleton");
// 註冊一個存在物件為預設、有命名名稱、使用每個執行續(per thread)生命週期管理
myContainer.RegisterInstance<IMyClass>("MySingleton", fooMyClassObject, new PerThreadLifetimeManager());
// 取得 singleton 執行個體,容器將會持有僅僅一個弱參考的物件
fooObject = myContainer.Resolve<IMyClass>("MySingleton");
#endregion