上篇文章《发布一个免费漂亮的仿Outlook风格、支持换肤的通用界面框架》提供了一个漂亮的Outlook风格、支持换肤的通用界面框架。现在,我们先来通过源码学习如何开发一个简单的界面框架,后面我们再发布源码介绍如何开发Outlook风格、支持换肤的界面框架。点击以下链接下载该示例框架 简单界面框架源码下载。
1 简单界面框架概述
1.1 界面框架插件概述
我们先来看一下要创建的这个界面框架,如下图所示。这个界面框架是一个上下型布局风格,上部分是菜单,下部分是多标签页的内容区域。菜单由其它插件来提供,并且点击菜单时在内容区域显示其它插件注册的窗体或者用户控件。
下图演示了其它插件如何通过配置将界面元素注册到这个界面框架。在下图,DemoPlugin这个插件定义了一个Extension扩展节点,其对应扩展点为UIShell.Applications,并且底下定义了Application和Menu节点。当DemoPlugin插件被OSGi.NET内核安装后,它就将这个扩展信息注册到内核;接着界面框架就可以获取到相应的扩展信息,并在界面上创建了对应的菜单,并且在点击菜单时,将插件提供的窗体显示在内容区域里。
1.2 先尝试一下这个界面框架
下面我们先来尝试一下这个界面插件,你可以访问http://www.iopenworks.com/Products/ProductDetails/Introduction?proID=21 来查看一下这个界面框架的详细信息。
1.2.1 下载安装iOpenWorksSDK
进入开放工厂官方网站http://www.iopenworks.com,下载插件框架安装。
1.2.2 创建项目,下载该插件
运行VS 2008(支持VS2005/2008/2010,以2008为例),然后新建一个iOpenWorks主程序。
创建完成后,按F5,运行这个项目,并在插件中心中下载这个简单的界面框架插件。
下载安装完成后,点击“重启系统”按钮,你发现已经安装了这个界面框架插件了。
它已经包含了一个系统管理的菜单,这是因为系统管理菜单已经定义了一个如下的扩展信息,该格式的扩展会注册到OSGi.NET并被界面框架获取,然后创建相应的界面元素。
<Application Title= " 系统管理 " ToolTip= " 系统管理 " Icon= " UIShell.WinFormAppCenterPlugin.Resources.shell.png ">
<Menu Text= " 插件中心 " ToolTip= " 插件中心 " Icon= " UIShell.WinFormAppCenterPlugin.Resources.shell.png " Class= " UIShell.WinFormAppCenterPlugin.AppCenterUserControl "/>
<Menu Text= " 插件管理 " ToolTip= " 插件管理 " Icon= " UIShell.WinFormAppCenterPlugin.Resources.shell.png " Class= " UIShell.WinFormAppCenterPlugin.BundleManagementUserControl "/>
</Application>
</Extension>
接下来,我们可以添加一个已有的项目,把刚才下载的界面框架的源码添加到当前项目。
下面我们来通过源码学习一下如何来构建这样的界面框架插件了。
2 构建一个简单界面框架
2.1 创建扩展模型
这个界面框架通过OSGi.NET的扩展点-扩展机制实现了界面的扩展,允许其它插件通过定义扩展的方式将界面元素注册到该界面框架。这个框架接受的扩展配置如下所示。扩展点名称为UIShell.Applications,底下是Application和Menu定义。Application对应于界面菜单的根节点,Menu表示这个插件的所有菜单配置,支持嵌套方式。每个Menu可以定义一个Class属性,表示点击这个菜单时,在内容区域显示的窗体或者用户控件全名称。
2.2 创建扩展模型对象
当我们定义后界面框架接受的扩展信息的格式后,我们需要定义相应的扩展对象了。你可以查看源码的ExtensionModel目录下的3个文件。WinShellApplication和WinShellMenu对应Extension信息里面的Application和Menu XML节点配置,WinShellApplicationContainer是WinShellApplication对象容器。
WinShellApplicationContainer是一个单例的对象,它用于将Extension对象转换成WinShellApplication,并为插件维护所有WinShellApplication对象。这个类提供了如下四个接口:
(1)AddApplicationForExtension(Extension):将Extension转换成WinShellApplication,并添加到缓存,然后返回该对象
(2)RemoveApplicationForExtension(Extension):删除Extension对应的WinShellApplication对象。
(3)GetWinShellApplication(IBundle):获取一个插件注册的扩展信息对应的WinShellApplication对象。
(4)GetTopWinShellMenus(IBundle):获取一个插件注册的扩展信息对应的一级菜单列表。
WinShellApplication类对应扩展的Application XML节点,其Title、ToolTip、Icon属性对应XML相应属性,Bundle表示定义这个节点的插件,Menus表示子菜单集合。
WinShellMenu类对应扩展的Menu XML,其Text、ToolTip、Icon属性对应相应XML属性,ClassName对应Class属性,Application表示所属的WinShellApplication对象,Parent表示父菜单对象,Children表示子菜单对象列表。
建立扩展模型后,我们接着要来创建一个主界面了。
2.3 创建主界面
双击MainForm.cs打开主界面设计器。主界面为上下布局,上部分是一个MenuStrip,下部分是一个TabControl。
下面我们将通过OSGi.NET的扩展机制,将其它插件注册的扩展信息转换成这个主界面的菜单项。
2.4 处理扩展点,将扩展信息转换成界面元素
选择MainFormExtensionHandler.cs文件,按F7查看这个文件的源码。该文件获取OSGi.NET扩展信息并监听扩展变更事件,然后将扩展转换成主界面的界面元素。
首先,我们先看一下如何获取扩展信息并监听事件。代码如下,在HandleExtension方法中,我们通过BundleContext插件上下文的GetExtensions来获取界面框架定义的扩展点的所有已有扩展信息,然后通过ApplicationContainer将扩展转换成WinShellApplication对象,并为其创建相应菜单,接着监听扩展变更事件。
以下代码是扩展变更事件处理,当插件启动时,其扩展信息注册到OSGi.NET内核,当插件卸载时,其扩展信息会被卸载掉,因此,就触发这个事件。在这里,当扩展信息新增时,我们需要为其创建菜单项;反之,需要删除菜单项和已经显示的内容。
下面我们看一下为WinShellApplication创建相应界面元素的代码,这里我们利用该对象创建了一个顶层菜单项和所有子菜单项。
以下是移除界面元素的源码。
有关源码更多的细节,你可以自己浏览一下,如果有更多问题可以加入OSGi.NET插件仓库QQ交流群:121369588。