日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > asp.net >内容正文

asp.net

04Prism WPF 入门实战 - Module

發布時間:2024/9/3 asp.net 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 04Prism WPF 入门实战 - Module 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

  1.概要

  Module,具有特定功能,且獨立存在則稱為成為模塊。下圖為Prism體系中的關系結構圖。

  

  在Prism體系中Module的應用分為

  注冊/發現模塊

  加載模塊

  初始化模塊

  

  2.詳細內容

  (1)注冊/發現模塊

  通過重寫CreateModuleCatalog方法指定加載module的方式,這里我個人比較推薦使用反射的方式去指定目錄下讀取,當然還有其他方式這里就不一 一介紹了。

  首先我們將項目中的module編譯生成到項目運行目錄下的Apps文件夾下。

  

  這時需要在類庫右鍵->點擊屬性。

  

  將DLL編譯生成時拷貝到,指定目錄下(詳情見源碼)。

  ///

  /// Interaction logic for App.xaml

  ///

  public partial class App

  {

  ///

  /// 應用程序啟動時創建Shell

  ///

  ///

  protected override Window CreateShell

  {

  return Container.Resolve;

  }

  protected override void RegisterTypes(IContainerRegistry containerRegistry)

  {

  //注冊服務、依賴、View

  }

  ///

  /// 配置區域適配

  ///

  ///

  protected override void ConfigureRegionAdapterMappings(RegionAdapterMappings regionAdapterMappings)

  {

  base.ConfigureRegionAdapterMappings(regionAdapterMappings);

  }

  protected override IModuleCatalog CreateModuleCatalog

  {

  //new ConfigurationModuleCatalog

  //指定模塊加載方式為從文件夾中以反射發現并加載module(推薦用法)

  return new DirectoryModuleCatalog { ModulePath=@".\Apps" };

  }

  }

  (2)加載模塊

  加載模塊的代碼實現在DirectoryModuleCatalog內部實現大致如下:

  //

  // Summary:

  // Represets a catalog created from a directory on disk.

  //

  // Remarks:

  // The directory catalog will scan the contents of a directory, locating classes

  // that implement Prism.Modularityodule and add them to the catalog based on

  // contents in their associated Prism.Modularity.ModuleAttribute. Assemblies are

  // loaded into a new application domain with ReflectionOnlyLoad. The application

  // domain is destroyed once the assemblies have been discovered. The diretory catalog

  // does not continue to monitor the directory after it has created the initialze

  // catalog.

  publicclassDirectoryModuleCatalog:ModuleCatalog

  {

  privateclassInnerModuleInfoLoader:MarshalByRefObject

  {

  internal ModuleInfo GetModuleInfos(string path)

  {

  DirectoryInfo directory=newDirectoryInfo(path);

  ResolveEventHandlervalue=(objectsender, ResolveEventArgs args)=> OnReflectionOnlyResolve(args, directory);

  AppDomain.CurrentDomain.ReflectionOnlyAssemblyResolve +=value;

  ModuleInfo result=GetNotAlreadyLoadedModuleInfos(IModuleType: AppDomain.CurrentDomain.GetAssemblies.First((Assembly asm)=> asm.FullName==typeof(IModule).Assembly.FullName).GetType(typeof(IModule).FullName), directory: directory).ToArray;

  AppDomain.CurrentDomain.ReflectionOnlyAssemblyResolve -=value;

  returnresult;

  }

  private static IEnumerable?GetNotAlreadyLoadedModuleInfos(DirectoryInfo directory, Type IModuleType)

  {

  List?list=newList;

  Assembly alreadyLoadedAssemblies=(frompinAppDomain.CurrentDomain.GetAssemblies

  where!p.IsDynamic

  selectp).ToArray;

  foreach(FileInfo item in (from file in directory.GetFiles("*.dll")

  where alreadyLoadedAssemblies.FirstOrDefault((Assembly assembly)=>stringpare(Path.GetFileName(assembly.Location), file.Name, StringComparison.OrdinalIgnoreCase)==0)==

  selectfile).ToList)

  {

  try

  {

  list.Add(Assembly.LoadFrom(item.FullName));

  }

  catch(BadImageFormatException)

  {

  }

  }

  returnlist.SelectMany((Assembly assembly)=>fromtinassembly.GetExportedTypes.Where(newFunc(IModuleType.IsAssignableFrom))

  wheret !=IModuleType

  where!t.IsAbstract

  select t into type

  select CreateModuleInfo(type));

  }

  private static Assembly OnReflectionOnlyResolve(ResolveEventArgs args, DirectoryInfo directory)

  {

  Assembly assembly=AppDomain.CurrentDomain.ReflectionOnlyGetAssemblies.FirstOrDefault((Assembly asm)=>string.Equals(asm.FullName, args.Name, StringComparison.OrdinalIgnoreCase));

  if(assembly !=)

  {

  returnassembly;

  }

  AssemblyName assemblyName=newAssemblyName(args.Name);

  stringtext=Pathbine(directory.FullName, assemblyName.Name + ".dll");

  if(File.Exists(text))

  {

  returnAssembly.ReflectionOnlyLoadFrom(text);

  }

  returnAssembly.ReflectionOnlyLoad(args.Name);

  }

  internal void LoadAssemblies(IEnumerable?assemblies)

  {

  foreach(stringassemblyinassemblies)

  {

  try

  {

  Assembly.ReflectionOnlyLoadFrom(assembly);

  }

  catch(FileNotFoundException)

  {

  }

  }

  }

  private static ModuleInfo CreateModuleInfo(Type type)

  {

  stringname=type.Name;

  List?list=newList;

  boolflag=false;

  CustomAttributeData customAttributeData=CustomAttributeData.GetCustomAttributes(type).FirstOrDefault((CustomAttributeData cad)=> cad.Constructor.DeclaringType!.FullName==typeof(ModuleAttribute).FullName);

  if(customAttributeData !=)

  {

  foreach(CustomAttributeNamedArgument namedArgumentincustomAttributeData.NamedArguments)

  {

  switch(namedArgument.MemberInfo.Name)

  {

  case"ModuleName":

  name=(string)namedArgument.TypedValue.Value;

  break;

  case"OnDemand":

  flag=(bool)namedArgument.TypedValue.Value;

  break;

  case"StartupLoaded":

  flag=!(bool)namedArgument.TypedValue.Value;

  break;

  }

  }

  }

  foreach(CustomAttributeData iteminfromcadinCustomAttributeData.GetCustomAttributes(type)

  wherecad.Constructor.DeclaringType!.FullName==typeof(ModuleDependencyAttribute).FullName

  selectcad)

  {

  list.Add((string)item.ConstructorArguments[0].Value);

  }

  ModuleInfo obj=newModuleInfo(name, type.AssemblyQualifiedName)

  {

  InitializationMode=(flag ? InitializationMode.OnDemand : InitializationMode.WhenAvailable),

  Ref=type.Assembly.EscapedCodeBase

  };

  obj.DependsOn.AddRange(list);

  returnobj;

  }

  }

  //

  // Summary:

  // Directory containing modules to search for.

  publicstringModulePath

  {

  get;

  set;

  }

  //

  // Summary:

  // Drives the main logic of building the child domain and searching for the assemblies.

  protected override void InnerLoad

  {

  if(string.IsOrEmpty(ModulePath))

  {

  thrownewInvalidOperationException(Prismperties.Resources.ModulePathCannotBeOrEmpty);

  }

  if(!Directory.Exists(ModulePath))

  {

  thrownewInvalidOperationException(string.Format(CultureInfo.CurrentCulture, Prismperties.Resources.DirectoryNotFound, ModulePath));

  }

  AppDomain currentDomain=AppDomain.CurrentDomain;

  try

  {

  List?list=newList;

  IEnumerable?collection=fromAssembly assemblyinAppDomain.CurrentDomain.GetAssemblies

  where!(assemblyisAssemblyBuilder) && assembly.GetType.FullName !="System.Reflection.Emit.InternalAssemblyBuilder" && !string.IsOrEmpty(assembly.Location)

  selectassembly.Location;

  list.AddRange(collection);

  Type typeFromHandle=typeof(InnerModuleInfoLoader);

  if(typeFromHandle.Assembly !=)

  {

  InnerModuleInfoLoader innerModuleInfoLoader=(InnerModuleInfoLoader)currentDomain.CreateInstanceFrom(typeFromHandle.Assembly.Location, typeFromHandle.FullName)!.Unwrap;

  base.Items.AddRange(innerModuleInfoLoader.GetModuleInfos(ModulePath));

  }

  }

  catch(Exception innerException)

  {

  thrownewException("There was an error loading assemblies.", innerException);

  }

  }

  }

  (3)初始化模塊

  這些代碼在使用Prism項目模板創建Module的時候就已經自動創建好了。

  [Module(ModuleName="Contact")]

  public class ContactModule : IModule

  {

  //初始化

  public void OnInitialized(IContainerProvider containerProvider)

  {

  //通過注冊RegionManager,添加ContactView

  var regionManager=containerProvider.Resolve;

  //通過ContentRegion管理導航默認初始頁面ContactView

  var contentRegion=regionManager.Regions["ContentRegion"];

  contentRegion.RequestNavigate(nameof(ContactView));

  }

  public void RegisterTypes(IContainerRegistry containerRegistry)

  {

  containerRegistry.RegisterForNavigation;

  }

  }

  3.實戰應用

  Shell - MainWindow實現

  

  

  

  

  

  

  

  

  

  

  

  

  MainWindowViewModel中的實現

  public class MainWindowViewModel : BindableBase

  {

  private string _title="Prism Application";

  //Region管理對象

  private IRegionManager _regionManager;

  private IModuleCatalog _moduleCatalog;

  private ObservableCollection?_modules;

  private DelegateCommand _loadModules;

  private IModuleInfo _moduleInfo;

  public IView View { get; set; }

  public string Title

  {

  get { return _title; }

  set { SetProperty(ref _title, value); }

  }

  public ObservableCollection?Modules

  {

  get=> _modules (_modules=new ObservableCollection);

  }

  public DelegateCommand LoadModules { get=> _loadModules=new DelegateCommand(InitModules); }

  public IModuleInfo ModuleInfo

  {

  get

  {

  return _moduleInfo;

  }

  set

  {

  _moduleInfo=value;

  Navigate(value);

  }

  }

  public MainWindowViewModel(IRegionManager regionManager, IModuleCatalog moduleCatalog)

  {

  _regionManager=regionManager;

  _moduleCatalog=moduleCatalog;

  }

  public void InitModules

  {

  var dirModuleCatalog=_moduleCatalog as DirectoryModuleCatalog;

  Modules.AddRange(dirModuleCatalog.Modules);

  }

  private void Navigate(IModuleInfo info)

  {

  _regionManager.RequestNavigate("ContentRegion", $"{ info.ModuleName }View");

  }

  }

  Module - Wemail.Contact實現

  ContactModule.cs 模塊標記文件

  [Module(ModuleName="Contact")]

  public class ContactModule : IModule

  {

  public void OnInitialized(IContainerProvider containerProvider)

  {

  //通過注冊RegionManager,添加ContactView

  var regionManager=containerProvider.Resolve;

  //通過ContentRegion管理導航默認初始頁面ContactView

  var contentRegion=regionManager.Regions["ContentRegion"];

  contentRegion.RequestNavigate(nameof(ContactView));

  }

  public void RegisterTypes(IContainerRegistry containerRegistry)

  {

  containerRegistry.RegisterForNavigation;

  }

  }

  ContactView實現

  

  

  

  

  

  

  

  

  ContactViewModel實現

  public class ContactViewModel : BindableBase

  {

  private ObservableCollection?_contacts;

  private string _message;

  public string Message

  {

  get { return _message; }

  set { SetProperty(ref _message, value); }

  }

  public ObservableCollection?Contacts

  {

  get=> _contacts (_contacts=new ObservableCollection);

  }

  public ContactViewModel

  {

  Message="Wemail.Contact Prism Module";

  Contacts.Add("聯系人張某");

  Contacts.Add("聯系人王某");

  }

  }

總結

以上是生活随笔為你收集整理的04Prism WPF 入门实战 - Module的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。