• [织梦吧]唯一域名:www.dedecms8.com,织梦DedeCMS学习平台.

当前位置: > 编程与数据库 > net编程 >

如何使用托管扩展框架

来源: www.dedecms8.com 编辑:织梦吧 时间:2012-06-27点击:

 最近听到很多关于托管扩展框架的描述,虽然很多人明白它的意思,但是却不理解该工具的工作原理。这一工具能帮助客户向WPF程序添加自己的表单吗?我们的菜单中需要这些新表单不过不希望VB源代码被客户重新编译。本文会教大家如何使用托管扩展框架。

听起来这似乎是对MEF的有效应用。你也可以使用相同的方法来应用到WinForms或ASP.NET中,而且c#代码与下文要展示的代码相似。

MEF是一种能够通过简单模型使元件进行互动的扩展模型。MEF会调用部分元件。MEF对于不同模式类型都具有可扩展性,但同时会配备一个属性模型。这样你就可以通过.NET属性定义部件的互动。如果某部件需要什么,它会使用Import属性,如果部件要供给什么,它会使用Export属性。任何部件都可用作主机或客户端,供应商或客户。MEF的这些互动以协议会基础并提供灵活的发掘模型。你的应用程序会向MEF发送请求以提供执行。这样应用程序就可以脱离依赖并让你进行替换执行。

MEF目前还只是在CodePlex上作为一个预览版推出。它位于System.ComponentModel命名空间中,这表明它将会以.NET Framework 4.0中的正式一员出现。某些微软项目都将与之相关,包括VS 2010代码编辑器。在它还未出现在.NET框架中以前,我们都需要下载MEF并将 System.ComponentModel.Composition.dll放到可访问的文章。你还要意识到应用程序接口可能会发生变化。

应用程序将是MEF的主机而客户会写出MEF客户端或扩展。扩展要易于写客户端因为主机必须管理CompositionContainer。我们会按照创建接口,创建扩展,创建WPF主机的步骤来讲解整个过程。WPF主机会向CompositionContainer穿送一个目录,它会指定用于搜索菜单扩展的目录。

扩展支持所订立的协议。最普遍的协议是接口,而这些接口都很简单。

Public Interface IExtension
Sub ShowWindow()
End Interface
客户可以通过执行这一接口来添加扩展并从System.ComponentModel.Composition命名空间中指定Export属性:
Export(GetType(IExtension))> _
_
Partial Public Class First
Implements IExtension
Public Sub ShowWindow() _
Implements Common.IExtension.ShowWindow
End Sub
End Class

你也可以使用任意字符串来确定输出,但是最普遍的扩展是通过一个接口协议来检索。ExportMetadata属性会包含主机能够检索的额外扩展信息,而不需要真正地展示基本对象,这样可以让我们控制示例并保护性能。

设计方案时,将接口设置为由主机和所有扩展组件单独引用。不要在主机和扩展之间建立直接的引用。所有的组件都需要引用 System.ComponentModel.Composition.dll。编译的扩展要放在方便的位置。你可以在属性属性对话框中指定建立的位置。

主机要管理CompositionContainer。CompositionContainer接通幕后的输入与输出,而且它必须了解所能获取的输出。创建一个容器项目级别的变量以清理OnExit。对容器Dispose方法调用会处理所有执行IDisposable的部件:

Protected Overrides Sub OnExit( _
ByVal e As System.Windows.ExitEventArgs)
MyBase.OnExit(e)
If mContainer IsNot Nothing Then
mContainer.Dispose()
End If
End Sub

 

覆盖OnStartup方法会在应用程序启动时让你准备容器:

Protected Overrides Sub OnStartup( _
ByVal e As StartupEventArgs)
MyBase.OnStartup(e)
If Compose() Then
MainWindow.Show()
Else
Shutdown()
End If
End Sub
构成方法才是真正做准备工作的方法:
Private Function Compose() As Boolean
Dim cat As New AggregateCatalog

总目录允许你对若干目录进行统筹管理。如果一套目录在总目录中同时出现,所有符合这一套目录的条目都会被找到。目录中的不同类型也可以获取,包括 DirectoryCatalog,这个类型在所有指定目录中加载了所有组件。笔者建议将扩展的位置作为应用设定的一部分加入其中以实现更大的配置。你还可以添加当前组件:

Dim extLocation = My.Settings.ExtensionLocation
cat.Catalogs.Add(New DirectoryCatalog(extLocation))
cat.Catalogs.Add(New AssemblyCatalog( _
Me.GetType.Assembly))
mContainer = New CompositionContainer(cat)

从这一点讲容器已经处于待命状态只是还没有请求发出。当你调用Compose方法的时候,一个构建批处理会让你指定条目以评估Import请求。任何稍后被Import 请求实例化的对象将会被额外的Import请求评估。许多情况下,首先对Compose的调用是唯一需要演示的调用。因为Compose演示了组成部分,如果组成规则没有得到贯彻这一演示会失败,因此Try/Catch锁定提供了报告:

Dim batch = New Hosting.CompositionBatch()
batch.AddPart(Me)
Try
mContainer.Compose(batch)
Catch ex As CompositionException
MessageBox.Show(ex.ToString())
Return False
End Try
Return True
End Function

应用程序的主窗口在域中使用Import属性。满足这一请求并创建域值,主窗口自身需通过MEF来提供——MEF会对任何明确添加到批处理以及任何通过另一Import实例化的Import属性进行评估。你可以用Overloads来替换MainWindows方法:

_

About D8

  • ©2014 织梦吧(d8) DedeCMS学习交流平台
  • 唯一网址 www.DedeCMS8.com 网站地图
  • 联系我们 1170734538@qq.com ,  QQ