How to create a pluggable GUI and DLLs in c#
Asked Answered
G

2

5

Not sure the exact terms to use here, so any help would be appreciated.

To be the most simplistic, I have a forms application. When I load "form.exe", the form has one control, a menu. This menu has one menuitem, "Exit". What I would like, is when the Form is loading, be able to pass in arguments to this forms app that specify DLLs that could add specialized methods, controls, etc.

Now when I load "form.exe add_plugable.dll", my menu has another menuitem, "Add". When I load "form.exe add_plugable.dll remove_pluggable.dll", menu has 3 items "Exit", "Add", and "Remove".

Hope this makes sense. What do I need to include in the Forms application and how do I create my DLLs? I am aware I need a common interface, but dont know exactly how to accomplish this with namespaces and interfaces and abstract classes.

Thanks!

Gloriane answered 5/10, 2012 at 17:15 Comment(0)
D
6

I would recommend looking into the Managed Extensibility Framework. It was designed for this exact type of scenario.

For example, it is what Visual Studio uses for its extensibility, so add ins can be dynamically discovered and plugged in at runtime.

Desjardins answered 5/10, 2012 at 17:16 Comment(3)
This probably will be my solution when I upgrade to VS 2010. However im currently on 2008 and using .Net 3.5.Gloriane
@Gloriane Grab it from the CodePlex site. Works perfectly in .NET 3.5: mef.codeplex.com/releases/view/40606Desjardins
I actually found this tutorial too (added for reference): c-sharpcorner.com/uploadfile/rmcochran/…Gloriane
I
6

You can use a pre-written framework, but if you are looking for a "bare bones" solution, try this:

  1. Create an interface (or set of interfaces, if you prefer) that contains all methods that the forms app will call, e.g. IPlugin. Put the interface(s) in a separate class library.
  2. In each plugin DLL, create a public class that implements IPlugin.
  3. In the forms app, decide what plugins to load and when to call them. This logic is entirely up to you.

Load a plugin like this, then call the interface members to accomplish what you want. You could read the plugin file and class names from app.config, a database, or calculate them via a naming convention, according to your requirements.

var pluginAssembly = Assembly.Load(pluginFileName);
var plugin = (IPlugin) pluginAssembly.CreateInstance(pluginClassName);

These methods have several overloads allowing more control over the process. For example, you can load the plugin assembly using an AssemblyName rather than a simple string. When instantiating the class, you can specify binding flags and a set of parameter values to pass to the class's constructor.

Input answered 5/10, 2012 at 17:49 Comment(4)
Great piece of help. Wish I could vote this up more than once.Danny
One question. Does this allow me to be able to simply drop a new DLL (containing a class that implements IPlugin) into the application directory and let my application automatically discover this upon next load? Since new plug-in DLLs will be added to the directory later, I'll not have a value for pluginClassName parameter that you mentioned above. How to work around this? And how to know if a particular DLL contains a class that implements IPlugin?Danny
Assembly.Load will only discover your DLL when it is first called, so you can drop them into the directory at any time before attempting to load them. Once loaded, an assembly will be cached in memory for the lifetime of the AppDomain. To refresh the cache, recycle the AppDomain.Input
To discover plugin classes without knowing their names in advance requires you to write the appropriate logic yourself. For example, you could use reflection to find all public classes in the assembly that implement the plugin interface.Input

© 2022 - 2024 — McMap. All rights reserved.