|
Trouver une ressource
Vous ne trouvez pas de réponse à votre problème ? Alors posez la question dans le forum. Souvenez-vous qu'il n'y a jamais de question bête, mais rester dans l'ignorance parce que l'on n'ose pas poser une question, ça c'est une erreur !
CRÉATION DYNAMIQUE D'OBJETS
Information sur la source
Description
Ce code sert à lire dans un répertoire l'ensemble des DLL et à les ajouter si elles correspondent à une interface ou dérivent d'un type donné. J'utilise pour cela la reflexion. Ceci peut permettre de créer des plugins. La solution est composée de 3 projets, un executable qui contient le code de recherche des DLL, une DLL qui contient de type de référence (référencé dans l'exe) et une DLL qui contient les types dérivés (inconnue de l'exe). Une propriété statique de la classe de base peut servir de clef, sinon, c'est le nom de la classe qui aura cette fonction.
Source
- class Loader<BaseClass>
- {
- private Dictionary<string, Type> creatable;
- private Type BaseType;
- private string KeyElement;
- private string defaultElement;
-
- #region constructeurs
-
- /// <summary>
- /// Créé un chargeur de classe
- /// </summary>
- public Loader() : this("") { ;}
-
- /// <summary>
- /// Créé un chargeur de classes
- /// </summary>
- /// <param name="KeyElement">Element servant de clef</param>
- public Loader(string KeyElement)
- {
- this.BaseType = typeof(BaseClass);
- this.KeyElement = KeyElement;
- creatable = new Dictionary<string,Type>();
- }
-
- #endregion
-
- #region gestion des types
- /// <summary>
- /// Ajoute toutes les classes contenues dans toutes les assemblies d'un répertoire
- /// </summary>
- /// <param name="Path">Chemin Contenant les assemblies à charger</param>
- public void AddFolder(string Path) {
- //Charge les fichiers contenus dans le répertoire
- DirectoryInfo directory = new DirectoryInfo(Path);
- foreach (FileInfo file in directory.GetFiles("*.dll"))
- {
- AddAssembly(file.FullName);
- }
- }
-
- /// <summary>
- /// Ajoute toutes les classes contenues dans une assembly
- /// </summary>
- /// <param name="Path"></param>
- public void AddAssembly(string Path)
- {
- //Charge l'assembly
- Assembly assembly = Assembly.Load(AssemblyName.GetAssemblyName(Path)); ;
- //Récupère tous les type contenus
- Type[] types = assembly.GetTypes();
- foreach (Type type in types)
- {
- AddType(type);
- }
- }
-
- /// <summary>
- /// Ajoute un type
- /// </summary>
- /// <param name="type">Type à ajouter</param>
- private void AddType(Type type)
- {
- //Vérifie que le type dérive bien de la classe de base
- if (!IsBasedOn(type,BaseType)) return;
- //Récupère la valeur clef (nom de la classe si le nom est null)
- string key;
- if (string.IsNullOrEmpty(KeyElement)) {
- key = type.FullName;
- } else {
- key = type.InvokeMember(KeyElement, BindingFlags.InvokeMethod | BindingFlags.FlattenHierarchy | BindingFlags.GetProperty | BindingFlags.Static | BindingFlags.Public, null, null, null).ToString();
- }
- //inscrit la classe dans la liste
- creatable[key] = type;
- }
-
- /// <summary>
- /// Ajoute un type
- /// </summary>
- /// <param name="Path">Chemin de l'assembly contenant la classe</param>
- /// <param name="ClassName">Nom de la classe</param>
- private void AddType(string Path, string ClassName)
- {
- //Charge l'assembly
- Assembly assembly = Assembly.Load(AssemblyName.GetAssemblyName(Path));
- //charge le type particulier
- Type type = assembly.GetType(ClassName);
- //Ajoute le type
- AddType(type);
- }
-
- /// <summary>
- /// Retire un type de la liste
- /// </summary>
- /// <param name="Id">Clef du type à enlever</param>
- public void RemoveType(string Id)
- {
- creatable.Remove(Id);
- }
- #endregion
-
- #region divers
- /// <summary>
- /// Défini une classe par défaut si la classe recherchée n'existe pas
- /// </summary>
- public string DefaultElement
- {
- get { return defaultElement; }
- set { defaultElement = value; }
- }
-
- /// <summary>
- /// Vérifie si une classe est basée ou dérivée d'un type particulier
- /// </summary>
- /// <param name="TestType">Type à tester</param>
- /// <param name="BaseType">Référence</param>
- /// <returns></returns>
- private bool IsBasedOn(Type TestType, Type BaseType) {
- if (TestType.IsSubclassOf(BaseType)) return true;
- if (TestType.FullName == BaseType.FullName) return true;
- if (Type.Equals(TestType, typeof(System.Object))) return false;
- return IsBasedOn(TestType.BaseType, BaseType);
- }
-
- #endregion
-
- #region creation de types
- /// <summary>
- /// Créé une instance de l'élément demandé, s'il n'existe pas, créé une instance de l'élément par défaut.
- /// </summary>
- /// <param name="Id">Identifiant de l'élément à créer</param>
- /// <param name="parameters">Paramètres du constructeur</param>
- /// <returns>Objet de la classe de base</returns>
- public BaseClass Create(string Id, params object[] parameters)
- {
- object Obj;
- try {
- Obj = Activator.CreateInstance(creatable[Id], parameters);
- } catch {
- try {
- Obj = Activator.CreateInstance(creatable[defaultElement], parameters);
- } catch {
- throw new System.Reflection.ReflectionTypeLoadException(null, null, "Impossible de créer l'objet, la clef n'existe pas");
- }
- }
- return (BaseClass)Obj;
- }
-
- #endregion
- }
class Loader<BaseClass>
{
private Dictionary<string, Type> creatable;
private Type BaseType;
private string KeyElement;
private string defaultElement;
#region constructeurs
/// <summary>
/// Créé un chargeur de classe
/// </summary>
public Loader() : this("") { ;}
/// <summary>
/// Créé un chargeur de classes
/// </summary>
/// <param name="KeyElement">Element servant de clef</param>
public Loader(string KeyElement)
{
this.BaseType = typeof(BaseClass);
this.KeyElement = KeyElement;
creatable = new Dictionary<string,Type>();
}
#endregion
#region gestion des types
/// <summary>
/// Ajoute toutes les classes contenues dans toutes les assemblies d'un répertoire
/// </summary>
/// <param name="Path">Chemin Contenant les assemblies à charger</param>
public void AddFolder(string Path) {
//Charge les fichiers contenus dans le répertoire
DirectoryInfo directory = new DirectoryInfo(Path);
foreach (FileInfo file in directory.GetFiles("*.dll"))
{
AddAssembly(file.FullName);
}
}
/// <summary>
/// Ajoute toutes les classes contenues dans une assembly
/// </summary>
/// <param name="Path"></param>
public void AddAssembly(string Path)
{
//Charge l'assembly
Assembly assembly = Assembly.Load(AssemblyName.GetAssemblyName(Path)); ;
//Récupère tous les type contenus
Type[] types = assembly.GetTypes();
foreach (Type type in types)
{
AddType(type);
}
}
/// <summary>
/// Ajoute un type
/// </summary>
/// <param name="type">Type à ajouter</param>
private void AddType(Type type)
{
//Vérifie que le type dérive bien de la classe de base
if (!IsBasedOn(type,BaseType)) return;
//Récupère la valeur clef (nom de la classe si le nom est null)
string key;
if (string.IsNullOrEmpty(KeyElement)) {
key = type.FullName;
} else {
key = type.InvokeMember(KeyElement, BindingFlags.InvokeMethod | BindingFlags.FlattenHierarchy | BindingFlags.GetProperty | BindingFlags.Static | BindingFlags.Public, null, null, null).ToString();
}
//inscrit la classe dans la liste
creatable[key] = type;
}
/// <summary>
/// Ajoute un type
/// </summary>
/// <param name="Path">Chemin de l'assembly contenant la classe</param>
/// <param name="ClassName">Nom de la classe</param>
private void AddType(string Path, string ClassName)
{
//Charge l'assembly
Assembly assembly = Assembly.Load(AssemblyName.GetAssemblyName(Path));
//charge le type particulier
Type type = assembly.GetType(ClassName);
//Ajoute le type
AddType(type);
}
/// <summary>
/// Retire un type de la liste
/// </summary>
/// <param name="Id">Clef du type à enlever</param>
public void RemoveType(string Id)
{
creatable.Remove(Id);
}
#endregion
#region divers
/// <summary>
/// Défini une classe par défaut si la classe recherchée n'existe pas
/// </summary>
public string DefaultElement
{
get { return defaultElement; }
set { defaultElement = value; }
}
/// <summary>
/// Vérifie si une classe est basée ou dérivée d'un type particulier
/// </summary>
/// <param name="TestType">Type à tester</param>
/// <param name="BaseType">Référence</param>
/// <returns></returns>
private bool IsBasedOn(Type TestType, Type BaseType) {
if (TestType.IsSubclassOf(BaseType)) return true;
if (TestType.FullName == BaseType.FullName) return true;
if (Type.Equals(TestType, typeof(System.Object))) return false;
return IsBasedOn(TestType.BaseType, BaseType);
}
#endregion
#region creation de types
/// <summary>
/// Créé une instance de l'élément demandé, s'il n'existe pas, créé une instance de l'élément par défaut.
/// </summary>
/// <param name="Id">Identifiant de l'élément à créer</param>
/// <param name="parameters">Paramètres du constructeur</param>
/// <returns>Objet de la classe de base</returns>
public BaseClass Create(string Id, params object[] parameters)
{
object Obj;
try {
Obj = Activator.CreateInstance(creatable[Id], parameters);
} catch {
try {
Obj = Activator.CreateInstance(creatable[defaultElement], parameters);
} catch {
throw new System.Reflection.ReflectionTypeLoadException(null, null, "Impossible de créer l'objet, la clef n'existe pas");
}
}
return (BaseClass)Obj;
}
#endregion
}
Historique
- 20 février 2007 07:46:37 :
- Prise en compte des remarques de bidou
- 20 février 2007 15:53:21 :
- Correction d'erreur
Sources du même auteur
Sources de la même categorie
Sources en rapport avec celle ci
Commentaires et avis
Discussions en rapport avec ce code source dans le forum
Declaration dynamique d'une classe [ par Barz ]
Comment par code peut-on executer une méthode d'une classe en dynamique, c'est à dire en ayant que une chaine correspondant au nom de la classe et une
litse de fichiers dynamique [ par denistheisen ]
Bonjour, Je suis a la recherche d'un javascript qui me permettrait de generer une liste dymanique de fichiers se trouvant dans un de mes repertoires e
Création d'un tableau dynamique HTML par le code... [ par pchanet ]
Bonjour à tous,Je suis en train de développer la gestion d'une table HTML (type <table>...</table>) en dynamique à partir de la page de co
Génération dynamique de windows.form en C# [ par Thanos_the_yopper ]
Bonjour,je suis en train de faire une appli qui, en fonction du contenu d'un fichier XML construit dynamiquement une fenetre windows avec des champs d
Objet dynamique .net. [ par jonguerre ]
Bonjour,Petite question je crée 2 objets Panel (panel1,panel2);panel1 = new System.Windows.Forms.Panel();panel2 = new System.Windows.Forms.Panel();J'a
Tableau dynamique [ par redpooka ]
Comment faire un tableau à 2 dimension dynamique ?Avec les collections arraylist, on peut faire un mais c'est juste avec une dimension.tableau du styl
Faire une zone de texte dynamique [ par typhoonx ]
Bonjour,Je suis en train de programmer une application de compression (dll dévelopée en C) et interface C#.Je voudrais faire une zone de texte dans la
site Dynamique [ par Gina78 ]
Bonjour,Je voudrais juste savoir les premières étapes pour creer un site DynamiqueMerci
générer un contrôle ( bouton) dynamique en c# [ par poelvo ]
Je voudrais créer des boutons à partir d'une liste d'objet d'une base de données, je n'aurai donc jamais le même nombre de boutons. Je ne sais donc pa
Nom dynamique de fichier [ par Sunnyprog ]
Sunnyprogfont=GeorgiaBonjour tt le monde !je voudrais savoir comment faire pour nommer un fichier de telle manière qu'il ait pour nom le contenu d'une
|
Téléchargements
Logiciels à télécharger sur le même thème :
|