简要说明:可扩展程序包括三个部分,第一部分是个接口程序,包含IAppFunctionality接口,所有扩展都要实现该接口,第二部分是扩展,实现IAppFunctionality,第三部分是主程序,它检测与它同级目录下是否有plugins文件夹,如果没有,就创建,如果有,查找该目录下所有实现IAppFunctionality接口的程序集,并更新菜单。
未添加扩展(即plugins下无dll程序)的运行情况
![未安装插件 未安装插件的效果](http://blog.faya.me/wp-content/uploads/2011/05/%E6%9C%AA%E5%AE%89%E8%A3%85%E6%8F%92%E4%BB%B6.png)
安装插件之后
![安装了插件 安装了插件后菜单发生了变化](http://blog.faya.me/wp-content/uploads/2011/05/%E5%AE%89%E8%A3%85%E4%BA%86%E6%8F%92%E4%BB%B6.png)
点击Plugin1和Plugin2:
![安装插件2 %E6%9C%AA%E5%AE%89%E8%A3%85%E6%8F%92%E4%BB%B62.png](http://blog.faya.me/wp-content/uploads/2011/05/%E6%9C%AA%E5%AE%89%E8%A3%85%E6%8F%92%E4%BB%B62.png)
![安装插件3 %E6%9C%AA%E5%AE%89%E8%A3%85%E6%8F%92%E4%BB%B63.png](http://blog.faya.me/wp-content/uploads/2011/05/%E6%9C%AA%E5%AE%89%E8%A3%85%E6%8F%92%E4%BB%B63.png)
程序源码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
| //AuthorInfoAttribute.cs
using System;
namespace PluginBase
{
public interface IAppFunctionality
{
void ShowInfo();
}
[AttributeUsage(AttributeTargets.Class)]
public class AuthorInfoAttribute : System.Attribute
{
public string Email { get; set; }
public string Name { get; set; }
}
} |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| //Plugin1.cs
using System.Windows.Forms;
using PluginBase;
namespace Plugin1
{
[AuthorInfoAttribute(Name="liulixiang", Email="liulixiang1988@gmail.com")]
public class Plugin1: IAppFunctionality
{
public void ShowInfo()
{
MessageBox.Show("Hello world, 你懂的。");
}
}
} |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| //Plugin2.cs
using System.Windows.Forms;
using PluginBase;
namespace Plugin2
{
[AuthorInfoAttribute(Name="liulixiang", Email="liulixiang1988@gmail.com")]
public class Plugin2:IAppFunctionality
{
public void ShowInfo()
{
MessageBox.Show("打酱油~~~");
}
}
} |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
| //MainApp.cs
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Windows.Forms;
using PluginBase;
namespace MyExtendableApp
{
public partial class MainApp : Form
{
private string pluginDir = "plugins\\";
private List<PluginBase.IAppFunctionality> apps = new List<PluginBase.IAppFunctionality>();
public MainApp()
{
InitializeComponent();
LoadPlugins();
}
private void LoadPlugins()
{
if (!Directory.Exists(pluginDir))
{
// 如果扩展程序文件夹不存在,就创建它
Directory.CreateDirectory(pluginDir);
}
try
{
var plugins = from plugin in Directory.EnumerateFiles(pluginDir, "*.dll")
select plugin;
foreach (string plugin in plugins)
{
Assembly thePluginAsm = null;
thePluginAsm = Assembly.LoadFrom(plugin);
//获取所有实现扩展接口的程序集
var theClassTypes = from t in thePluginAsm.GetTypes()
where t.IsClass && (t.GetInterface("IAppFunctionality") != null)
select t;
//调用接口方法
foreach (Type t in theClassTypes)
{
IAppFunctionality itfApp = (IAppFunctionality)thePluginAsm.CreateInstance(t.FullName, true);
apps.Add(itfApp);
ToolStripMenuItem menuItem = new ToolStripMenuItem(t.Name);
menuItem.Click += new System.EventHandler(delegate(object o, EventArgs e)
{
itfApp.ShowInfo();
});
menuStrip1.Items.Add(menuItem);
// itfApp.ShowInfo();
}
}
}
catch (System.Exception ex)
{
MessageBox.Show(ex.Message);
}
}
}
} |