问一个有难度点的问题,高手开来 http://www.csdn.net/Develop/Read_Article.asp?Id=31749 解决方案 » 免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货 偶们正在做这种东东所有的插件 从 IPluginSDK 继承 ,在 IPluginSDK 中定义 PerformAction(IPluginContext) 继承,IPluginContext提供插件的上下文对象。利用反射建立插件的实例 然后直接调用实例的PerformAction()方法。道理就是这样的。 IPluginSDK 里面同时定义一 PluginName的属性 来标示插件。在系统启动的时候 根据配置文件加载插件列表。在系统需要用到插件的时候 ,根据PluginName检索到插件对象的dll名字。呵呵。偶的发言结束。 偶不是高手。 http://blog.csdn.net/happyjun2000/archive/2004/09/03/93365.aspx网上还是有点资料的:) public void Initialize(MainForm mainForm) { sMainForm = mainForm; string searchPath = Application.StartupPath + "\\Modules"; if (!Directory.Exists(searchPath)) { throw new Exception("模块所在的目录不存在"); } string[] dlls = Directory.GetFiles(searchPath, "*.dll"); foreach(string dll in dlls) { if(CheckIngore(dll)) continue; LoadOnedll(dll, typeof(BusinessEntityAttribute), "CG_SMART_CLIENT"); } searchPath = Application.StartupPath + "\\Seeks"; if (!Directory.Exists(searchPath)) { throw new Exception("模块所在的目录不存在"); } dlls = Directory.GetFiles(searchPath, "*.dll"); foreach(string dll in dlls) { if(CheckIngore(dll)) continue; LoadOneSeekDll(dll, typeof(SeekAttribute), "CG_SEEK"); } sAppGloblal.Seeks = seeks; }private void LoadOnedll(string dll, Type typeAttr, string tableName) { Assembly assembly = Assembly.LoadFrom(dll); Type[] clientType = assembly.GetTypes(); foreach (Type type in clientType) { Attribute attribute = Attribute.GetCustomAttribute(type, typeAttr); if (attribute != null) { IRegister register = attribute as IRegister; string name = string.Empty; if (register != null) { name = register.RegisterName; if( registerDs.Tables[tableName].Rows.Find(name) != null) { throw new Exception(string.Format("重复加载 {0}", name)); } } DataRow row = registerDs.Tables[tableName].NewRow(); row.BeginEdit(); row["CS_REGISTER_NAME"] = name; row["CS_ASSEMBLY"] = assembly.GetName().ToString(); row["CS_TYPE"] = type; row["CS_DEVELOPER"] = register.DeveloperName; row["CS_DESCRIPTION"] = register.Description; row["CS_CREATE_DATE"] = register.CreateDate; row.EndEdit(); registerDs.Tables[tableName].Rows.Add(row); modules.Add(name, new ClassItem(name, type, assembly, attribute)); } } } 这个利用custom attribute的特性。 自己定义一个attribute public class BusinessEntityAttribute : EntityAttribute { /// <summary> /// 构造函数 /// </summary> /// <param name="registerName">业务实体在系统中的注册名</param> public BusinessEntityAttribute(string registerName) : base(registerName) { } } 它就会吃进你指定目录下面的dll, 每一个dll中具有BusinessEntityAttribute 属性的类型都很被加载进那个 datatable, 在后面再利用Activator.CreateInstance(fClassType); 楼主可以去查查 msdn magazine 02年 第7期 http://msdn.microsoft.com/msdnmag/issues/02/07/CuttingEdge/default.aspx 这个题目比较大,没有做过倒是用过一款软件支持VB程序外接的~~~只好谈谈原理了首先,你的系统必须要有定义好的执行接口、模块之间数据传递必须可以重新定义、模块的执行顺序也必须可以重新定义。其次,技术上的支持。.NET可以支持动态编译Microsoft.CSharp命名空间下有几个支持代码编译的类---CodeDom模型System.Reflection命名空间下有些类提供程序集动态加载及相关操作还有,如果允许用户更改方法的话建议之间提供.cs文件的插件,这样更加灵活~~~希望能对你有所帮助~~~ 建议楼主参考SharpDeveloper这个开源项目。我记的这个项目中是提供了插件的接口的。也完全是用C#实现的,完全开放源码。另外开发这个项目的三人还为此项目写了本书,好像是叫C#项目开发全程剖析,讲了整个项目的开发过程。希望有所帮助。 我原来的程序提供了vsa脚本的运行,发现在vsa脚本里语言错误无法找到,所以客户提出要求改成plugin形式,看了这么多回帖,有写思路了,在这里多谢各位了,如果我研究出来了,我会写成一个专题给大家,大家互相学习嘛。 c#使用正则,表达式是或关系,怎么获取起作用的匹配项? 关于string str = null的问题 数据传输与存储问题(100分) sql2005数据库安装问题 如何将两个字节的16进制数转换成小数 c# socket 传输文件 checkboxlist到数据库? 请教一个线程监控的问题 怎么将Office组件加到C#中进行开发(100分) 紧急求助,谁能发几个NET2003中的文件给我 我的新作 用base怎么调用抽象类的构造函数啊?
呵呵。偶的发言结束。 偶不是高手。
网上还是有点资料的:)
{
sMainForm = mainForm;
string searchPath = Application.StartupPath + "\\Modules";
if (!Directory.Exists(searchPath))
{
throw new Exception("模块所在的目录不存在");
}
string[] dlls = Directory.GetFiles(searchPath, "*.dll");
foreach(string dll in dlls)
{
if(CheckIngore(dll))
continue;
LoadOnedll(dll, typeof(BusinessEntityAttribute), "CG_SMART_CLIENT"); } searchPath = Application.StartupPath + "\\Seeks";
if (!Directory.Exists(searchPath))
{
throw new Exception("模块所在的目录不存在");
}
dlls = Directory.GetFiles(searchPath, "*.dll");
foreach(string dll in dlls)
{
if(CheckIngore(dll))
continue;
LoadOneSeekDll(dll, typeof(SeekAttribute), "CG_SEEK");
}
sAppGloblal.Seeks = seeks;
}private void LoadOnedll(string dll, Type typeAttr, string tableName)
{
Assembly assembly = Assembly.LoadFrom(dll);
Type[] clientType = assembly.GetTypes();
foreach (Type type in clientType)
{
Attribute attribute = Attribute.GetCustomAttribute(type, typeAttr);
if (attribute != null)
{ IRegister register = attribute as IRegister;
string name = string.Empty;
if (register != null)
{
name = register.RegisterName; if( registerDs.Tables[tableName].Rows.Find(name) != null)
{
throw new Exception(string.Format("重复加载 {0}", name));
}
}
DataRow row = registerDs.Tables[tableName].NewRow();
row.BeginEdit();
row["CS_REGISTER_NAME"] = name;
row["CS_ASSEMBLY"] = assembly.GetName().ToString();
row["CS_TYPE"] = type;
row["CS_DEVELOPER"] = register.DeveloperName;
row["CS_DESCRIPTION"] = register.Description;
row["CS_CREATE_DATE"] = register.CreateDate;
row.EndEdit();
registerDs.Tables[tableName].Rows.Add(row); modules.Add(name, new ClassItem(name, type, assembly, attribute));
} }
}
这个利用custom attribute的特性。 自己定义一个attribute
public class BusinessEntityAttribute : EntityAttribute
{
/// <summary>
/// 构造函数
/// </summary>
/// <param name="registerName">业务实体在系统中的注册名</param>
public BusinessEntityAttribute(string registerName) : base(registerName)
{
}
}
其次,技术上的支持。.NET可以支持动态编译Microsoft.CSharp命名空间下有几个支持代码编译的类---CodeDom模型
System.Reflection命名空间下有些类提供程序集动态加载及相关操作
还有,如果允许用户更改方法的话建议之间提供.cs文件的插件,这样更加灵活~~~希望能对你有所帮助~~~