Ich versuche, ein Plugin-System zu schreiben, um einige Erweiterbarkeit zu einer Anwendung von mir zu geben, damit jemand ein Plugin für die Anwendung schreiben kann, ohne den Code der Hauptanwendung zu berühren (und das Risiko etwas zu brechen).Schreiben C# Plugin-System
Ich habe die Basis „IPlugin“ Schnittstelle geschrieben (atm, noch nichts implementiert)
Hier ist, wie ich bin Laden:
public static void Load()
{
// rawr: http://www.codeproject.com/KB/cs/c__plugin_architecture.aspx
String[] pluginFiles = Directory.GetFiles(Plugins.PluginsDirectory, "*.dll");
foreach (var plugin in pluginFiles)
{
Type objType = null;
try
{
//Assembly.GetExecutingAssembly().GetName().Name
MessageBox.Show(Directory.GetCurrentDirectory());
Assembly asm = Assembly.Load(plugin);
if (asm != null)
{
objType = asm.GetType(asm.FullName);
if (objType != null)
{
if (typeof(IPlugin).IsAssignableFrom(objType))
{
MessageBox.Show(Directory.GetCurrentDirectory());
IPlugin ipi = (IPlugin)Activator.CreateInstance(objType);
ipi.Host = Plugins.m_PluginsHost;
ipi.Assembly = asm;
}
}
}
}
catch (Exception e)
{
MessageBox.Show(e.ToString(), "Unhandled Exception! (Please Report!)", System.Windows.Forms.MessageBoxButtons.OK, System.Windows.Forms.MessageBoxIcon.Information);
}
}
}
Ein Freund zu helfen versucht, aber ich wirklich Ich habe nicht verstanden, was falsch war.
Die Ordnerstruktur für Plugins ist die folgende:
\
\ Plugins \
Alle Plugins eine DLL namens "Lab.Core.dll" in der [root] Verzeichnis verweisen und es ist nicht im Plugins-Verzeichnis vorhanden, da doppelte Referenzen geladen werden.
Das Plugin-System wird von Lab.Core.dll geladen, die auch von meiner ausführbaren Datei referenziert wird. Geben Sie "IPlugin" in Lab.Core.dll ein. Lab.Core.dll ist, genau wie genannt, der Kern meiner Anwendung.
EDIT:
Frage: Warum/Was die Ausnahme ist, ich bin immer und wie könnte ich mich über die Festsetzung es?
FINAL EDIT:
Ok, so habe ich beschlossen, es neu zu schreiben, nachdem irgend Quellcode sucht ein Freund für einen TF2 Regler geschrieben.
Hier ist, was ich habe und es funktioniert:
public class TestPlugin : IPlugin {
#region Constructor
public TestPlugin() {
//
}
#endregion
#region IPlugin Members
public String Name {
get {
return "Test Plugin";
}
}
public String Version {
get {
return "1.0.0";
}
}
public String Author {
get {
return "Zack";
}
}
public Boolean OnLoad() {
MessageBox.Show("Loaded!");
return true;
}
public Boolean OnAllLoaded() {
MessageBox.Show("All loaded!");
return true;
}
#endregion
}
public static void Load(String file) {
if (!File.Exists(file) || !file.EndsWith(".dll", true, null))
return;
Assembly asm = null;
try {
asm = Assembly.LoadFile(file);
} catch (Exception) {
// unable to load
return;
}
Type pluginInfo = null;
try {
Type[] types = asm.GetTypes();
Assembly core = AppDomain.CurrentDomain.GetAssemblies().Single(x => x.GetName().Name.Equals("Lab.Core"));
Type type = core.GetType("Lab.Core.IPlugin");
foreach (var t in types)
if (type.IsAssignableFrom((Type)t)) {
pluginInfo = t;
break;
}
if (pluginInfo != null) {
Object o = Activator.CreateInstance(pluginInfo);
IPlugin plugin = (IPlugin)o;
Plugins.Register(plugin);
}
} catch (Exception) {
}
}
public static void LoadAll() {
String[] files = Directory.GetFiles("./Plugins/", "*.dll");
foreach (var s in files)
Load(Path.Combine(Environment.CurrentDirectory, s));
for (Int32 i = 0; i < Plugins.List.Count; ++i) {
IPlugin p = Plugins.List.ElementAt(i);
try {
if (!p.OnAllLoaded()) {
Plugins.List.RemoveAt(i);
--i;
}
} catch (Exception) {
Plugins.List.RemoveAt(i);
--i;
}
}
}
Ich nehme zur Kenntnis, dass Sie nicht wirklich eine Frage gestellt, haben Sie gerade beschrieben, was Sie zu tun versuchen. Können Sie Ihre Frage in Form einer Frage formulieren? –
Err. Entschuldigung, ich habe aufgelegt, um zu erklären, was ich mache, aber habe die Frage vergessen. : x Ich werde diesen Schnitt machen. – Zack
Bitte posten Sie die vollständige Ausnahme, die Sie erhalten haben, komplett mit Stack-Trace und allen inneren Ausnahmen. Veröffentlichen Sie die Ergebnisse von ex.ToString(). –