2011-10-27 11 views
0

私はアプリケーションのサポートプラグインの作成方法をチュートリアルに従いました。すべて正常に動作しているようですが、プラグインを使用すると、関数の呼び出しとメインアプリケーションの変数へのアクセスが可能になります。私はネットの使用量などを監視するhttpラッパークラスを持っている..メインアプリケーションのために。プラグインは、マザーアプリケーションからhttpラッパーを呼び出します。C#プラグイン:アクセスする母フォームと関数

どうすればこの問題を解決できますか?使用可能なすべての関数/変数を持つクラスを定義する必要がありますか?また、GUIを生成するためのプラグインが必要になりますので、ユーザーはいくつかの設定を行うことができます。

これは私がこれまでに得たものである:

主な用途:

namespace MainApplication 
{ 
    public partial class Form1 : Form 
    { 
     public Form1() 
     { 
      InitializeComponent(); 
     } 

     List<iPlugin> PLUGIN_LIST = new List<iPlugin>(); 

     public void LoadPlugins() 
     { 
      // load plugins.. 
     } 

     // how do I call this function from a plugin?! 
     public void HTTP() 
     { 
      // do some networking stuff.. 
     } 

     private void Form1_Load(object sender, EventArgs e) 
     { 
      LoadPlugins(); 
     } 


    } 
} 

プラグインインターフェイス:

namespace PluginInterface 
{ 
    public interface iPlugin 
    { 
     string GetPluginName(); 

     void callHTTP(); 

     void SerVar(string var); 
    } 
} 

プラグイン:

namespace MyPlugin 
{ 
    public class Main : iPlugin 
    { 
     string variable = ""; 

     public string GetPluginName() 
     { 
      return "MyPlugin"; 
     } 

     public void callHTTP(){ 
      MainApplication.HTTP(); // call HTTP in main application 
     } 

     public void SerVar(string var) 
     { 
      variable = var; 
     } 
    } 
} 

また、私がチュートリアルに従ったとき、プラグインインターフェイスは別のプロジェクトで、MainApplicationとmyPluginの両方で「参照として追加する」必要がありました。それは私のアプリケーションとプラグインがpluginInterface.dllに依存していることを意味しますか?それとも開発に必要なのでしょうか?ランタイムに依存している場合は、私のアプリケーションとプラグインの両方でどうやって定義すればいいのですか?余分なDLLを使う必要はありませんか?希望は意味がある、ありがとう!

EDIT:あなたが取ることができる完全なMainApplicationコード

public interface iPlugin 
{ 
    string GetPluginName(); 

    string GetInformation(); 

    void SerVar(string var); 
} 


namespace MainApplication 
{ 
    public partial class Form1 : Form 
    { 
     public Form1() 
     { 
      InitializeComponent(); 
     } 

     List<iPlugin> PLUGIN_LIST = new List<iPlugin>(); 

     public void LoadPlugins() 
     { 

      string path = Assembly.GetExecutingAssembly().GetModules()[0].FullyQualifiedName; 
      string pluginDir = Path.GetDirectoryName(path) + "\\Plugins"; 

      foreach (string s in Directory.GetFiles(pluginDir, "*.dll")) 
      { 
       // THIS LINE GIVES THE ERROR 
       Type[] pluginTypes = Assembly.LoadFile(s).GetTypes(); 

       foreach (Type t in pluginTypes) 
       { 
        if (t.ToString().Contains("Main")) 
        { 
         iPlugin plugin = Activator.CreateInstance(t) as iPlugin; 

         PLUGIN_LIST.Add(plugin); 
         break; 
        } 
       } 
      } 

     } 



     private void Form1_Load(object sender, EventArgs e) 
     { 
      LoadPlugins(); 
     } 

    } 
} 

答えて

0

一つのアプローチは、あなたが(IMother言うと呼ばれる)母アプリケーションから呼び出したいすべてのメソッドが含まれているインタフェースを定義することであり、マザーアプリケーションにこれを実装させる。

IPluginvoid SetMother(IMother mother)のような方法で更新し、各プラグインをロードするときにこのメソッドをプラグインで呼び出すことができます。そうすれば、各プラグインは最初からIMotherという参照を持ち、必要に応じてメソッドを呼び出すことができます。

plugininterface.dllの質問については、はい、MainApplicationとmyPluginの両方がそのdllに依存しています(開発に必要なだけではありません)。特別なdllを使用しないようにしたい場合(余分なDLLへの参照は一般的に問題ではありません)、プラグインインタフェースをMainApplicationと同じプロジェクトに配置します。あなたのレイアウトを理解しているかどうか分からないので、あなたの質問に答えられない場合は、あなたのプロジェクト/ソリューションの設定方法に関する詳細を追加してください。

EDIT BASED ONコメント:3つのプロジェクト
ためmyPlugin
つのプロジェクトのためのMainApplication
つのプロジェクトのための一つのプロジェクトが含まれてい
一つのソリューションファイル:

は、私はあなたのレイアウトは、次のようなものであると仮定プラグインインタフェース。

プラグインインターフェイスのコードファイルをMainApplicationプロジェクトに移動できます。そうすれば、MainApplicationは他のものに依存しなくなります。プラグインのインターフェイスプロジェクトから.csファイルを取り出し、それをMainApplicationに追加するだけです。次に、myPluginからMainApplicationを参照する必要がありますが、これは問題ありません。

+0

メインアプリケーションプロジェクトのプラグインインターフェイスは、私が考えるより意味をなさないでしょう。 –

+0

ありがとうcsm!アプリケーション自体が単一のexeになるため、おそらくできるだけ少ないdllを使用したいと思います。ユーザーがそれをダウンロードすると、アプリはすべてのプラグインをダウンロードしてdirに保存します。メインアプリケーションがpluginInterface.dllに依存している場合、それは機能しません。すべての作業を行うために何かに依存しない別のアプリケーションを使用する必要があります。これは実行したくありません。私が提供したコードを使ってメインアプリケーションとプラグインでpluginInterfaceを定義するにはどうすればいいですか?ありがとう! – user1015551

+0

ありがとう、私は今それを試してみよう! – user1015551

0

これは他の何も変わりません。プラグインにフォームへの参照を与えます。

.dll依存性については、はい。プラグインとアプリケーションの両方が依存します。しかし、これは悪いことではありません。実際には、非常に非常に良い。私は建築のそのビットをまったく変更しません。

0

新しいインターフェイスを作成して、たとえばIHostPluginを作成し、このインターフェイス経由でプラグインで使用するメインフォームのプロパティを公開する必要があります。メインフォームクラス、またはそれより優れたインターフェイスを、メインフォームにアクセスできるラッパークラスに実装します。このクラスをmarshalByrefにして、このホストインターフェイスをパラメータとして使用するプラグインのインターフェイス上に、プラグインにホストへの参照を持つメソッドを作成することによって、プラグインに渡します。

アプリドメイン間で型の不一致がないように、これらのインターフェイスを別々のdllに保持する必要があります。これをソリューションに入れてプロジェクトを参照することはできません。

+0

ありがとう! DLLをexeファイルにコンパイルすることは可能ですか? – user1015551

+0

良い考えではありません。各AppDomainで読み込んだすべてのアセンブリでインターフェイスを共有したい場合は、インスタンス化しようとするとタイプミスマッチが発生します。ちょうどdllへの参照を追加してください。 – Kell

関連する問題