wie programmiert man plugins?



  • Ich habe die oben genannte Frage. Ich will etwas progammieren,
    dass dateien bearbeiten usw. kann und wollte wissen wie ich plugins,
    die ich auch selber schreibe einbinden kann
    und das menü dementsprechen erweitern kann
    ähnlich wie bei Paint.Net

    LG XBert



  • Plugin für was?



  • Moin,
    Ich glaub er will wissen, wie er ein Plugin-System in seinem eigenen Programm implementiert. Warscheinlich ohne irgentwelche Scriptsprachen zu benutzen. Das interessiert mich auch schon länger, wie man das ordentlich hinbekommt.

    MFG



  • Achso, hatte die Frage andersrum verstanden.

    Nagut, das ist eigentlich recht einfach. Und zwar musst du erst Spezifikationen für Plugins festlegen. Es ist recht gebräuchlich, dass Plugins als DLLs kompiliert werden müssen und bestimmte Funktion daraus exportiert werden müssen.
    Du lädst dann also alle DLLs aus einem Ordner mit LoadLibrary, suchst dir mit GetProcAddress die entsprechenden Funktionen raus und rufst sie auf.
    Ich würds ungefähr so machen:

    Hauptprogramm, lädt alle Plugin-DLLs, PseudoCode.

    class Plugin
    {
    public:
        Plugin( path )
        {
            dll_handle = LoadLibrary( path )
            func_ptr = GetProcAddress( dll_handle, "GetPluginName" )
            if func_ptr == NULL
                fehler!
        }
    
        getPluginName()
        {
            return func_ptr();
        }
    
    private:
        dll_handle
        func_ptr
    }
    
    vector<Plugin> plugins
    
    void loadPlugins( path )
    {
        for all dll-files in path
            plugins += Plugin( dll_path )
    }
    

    Pseudo-Code von Plugin-DLL:

    export string GetPluginName()
    {
        return "MeinName"
    }
    


  • Normalerweise programmiert man sich für eine Plugin-Schnittstelle ein Interface. Du definierst eine abstrakte Basisklasse, von der dann die jeweiligen Plugin-Klassen abgeleitet werden, und deren Methoden überschreiben.

    Durch Polymorphie kannst du dann von Deinem Programm aus auf die Methoden der fremden Klasse zugreifen. Dem Plugin-Hersteller muss lediglich bekannt sein, welche Methoden vorgegeben sind. Wenn Du mehr Interesse zu dem Thema hast, kann ich Dir morgen einen ganz simplen Beispiel dazu schreiben.



  • @mikey, wie werden dann die Plugins geladen? Oder kann man mittlerweile Klassen in einer DLL unterbringen? Oder was verwendet man sonst für eine Technik?



  • Selbstverständlich kann man Klassen in einer DLL unterbringen.



  • Mit welcher Programmiersprache programmierst du diese?
    Vielleicht hat jemand ein Beispiel für die Programmiersprache parat liegen.



  • Badestrand schrieb:

    Oder kann man mittlerweile Klassen in einer DLL unterbringen?

    Das geht schon seit 10 Jahren, nur verliert man die Compilierunabhängigkeit.

    Badestrand schrieb:

    Oder was verwendet man sonst für eine Technik?

    COM, .NET, Corba

    Fände ich bei einer OO-Schnittstelle inzwischen geläufiger als DLLs (Stichwort: komponentenbasierte Programmierung).



  • Marc++us schrieb:

    Badestrand schrieb:

    Oder kann man mittlerweile Klassen in einer DLL unterbringen?

    Das geht schon seit 10 Jahren, nur verliert man die Compilierunabhängigkeit.

    Was bei Plugins ja schon ein recht großer Nachteil ist. Aber na gut, dass es geht ist schon recht cool (wenn auch keine große Kunst, wenn's Compiler-spezifisch ist).

    Marc++us schrieb:

    Badestrand schrieb:

    Oder was verwendet man sonst für eine Technik?

    COM, .NET, Corba

    Fände ich bei einer OO-Schnittstelle inzwischen geläufiger als DLLs (Stichwort: komponentenbasierte Programmierung).

    Ups, dann bin ich wohl auf einem ziemlich alten Stand 😞 Gibt's da denn eine Art quasi-Standard oder kocht jeder sein eigenes Süppchen?



  • ok vielleicht war die frage etwas zu ungenau.
    mein Programm enthält eine Dateiliste die dann je nach Dateityp
    mit dem entsprechenden plugin (zb ein jpg-viewer für jpg-dateien) geöffnet werden und auch graphisch sichtbar sein sollten.
    Das mit den dll's habe ich mir fast gedacht,
    aber wie weiß ich welche datei mit welchem plugin geöffnet werden soll und welche funktionen der dll aufzurufen sind.

    @mikey: für ein Beispiel wäre ich sehr dankbar (c++ wenn möglich)

    Mfg XBert



  • Badestrand schrieb:

    Ups, dann bin ich wohl auf einem ziemlich alten Stand 😞 Gibt's da denn eine Art quasi-Standard oder kocht jeder sein eigenes Süppchen?

    Kommt drauf an was du für Anforderungen hast, primär kann man zwischen Plattformunabhängigkeit und Sprachunabhängigkeit wählen, je nach Kombination der Beiden kannst du dich dann an verschiedenen Komponenten-"architekturen" (o. Spezifikationen) orientieren. Marc++us erwähnte ja schon ein paar, dazu kommen noch DCOM, JavaBeans, Enterprise JavaBeans und Webservices. Und einen "Quasi-Standard" gibt es IMHO nicht.



  • XBert schrieb:

    aber wie weiß ich welche datei mit welchem plugin geöffnet werden soll und welche funktionen der dll aufzurufen sind.

    In dem die DLLs in einem bestimmten Verzeichnis liegen? Dann einfach das Verzeichnis durchgehen. Oder in dem der User in eine Konfigdatei Einträge macht, wo die DLLs liegen und heißen?

    Und wie man die Funktionen anspricht, ist ja auch einfach: die Plugins MÜSSEN bestimmte Funktionen implementieren, die du vorgibst und dann einfach aufrufst. Stichwort: abstrakte Klassen bzw. pure virtual Memberfunctions.

    Hier gilt es halt abstraktes Denken anzukurbeln. 😉 Für OO-Programmierer sollte das einfach sein.



  • ok ich denke ich hab es soweit kapiert.
    ich dachte es muss von mir keine bestimmte funktion vorgegeben sein.
    und das mit dem dateityp der geöffnet werden soll, dabei werde ich vermutlich eine funktion verlangen wie diese:

    String __fastcall getAssociatedFileType(void){
       return "jpg;jpeg;";
    }
    

    also gut danke
    XBert



  • XBert schrieb:

    mein Programm enthält eine Dateiliste die dann je nach Dateityp
    mit dem entsprechenden plugin (zb ein jpg-viewer für jpg-dateien) geöffnet werden und auch graphisch sichtbar sein sollten.
    Das mit den dll's habe ich mir fast gedacht,
    aber wie weiß ich welche datei mit welchem plugin geöffnet werden soll und welche funktionen der dll aufzurufen sind.

    Das schreit geradezu nach einem Factory-basierten Aufbau.

    Für einen dem deinigen sehr ähnlichen Anwendungsfall (Dateierweiterungen und Ports in PVComm) habe ich mir ein kleines Plug-in- und Factory-Framework geschrieben, mit dem es möglich ist, solchen Code recht komfortabel über verschiedene DLLs zu verteilen. Du kannst dir ja mal den Quelltext ansehen.



  • lol@noob frage. das kommt wohl immer drauf an was das jew. program für ne schnittstelle zur verfügung stellt.



  • Bei den Fragen die du stellst, glauch ich nicht, dass du in der Lage bist das zu machen, was du vor hast.



  • XBert schrieb:

    @mikey: für ein Beispiel wäre ich sehr dankbar (c++ wenn möglich)

    Ein ganz minimalistisches Beispiel zur Prinzipverdeutlichung:

    #include <iostream> 
    #include <vector>
    
    /* ********** Klassenbeschreibungen ************
     * PluginInterface stellt die abstrakte Basisklasse dar, die jedem Plugin
     * bekannt sein sollte, um davon zu erben, und die entsprechenden Methoden
     * zu überladen.
     * 
     * PluginClass stellt die Klasse des Plugins dar, welche vom Interface 
     * abgeleitet wird, und die gewünschten Methoden redefiniert.
    
     * Hauptprogramm verwaltet alle Plugins, und gibt die angeforderten Instanzen zurück
     */
    
    class PluginInterface 
    { 
    public: 
    	virtual void ShowText() = 0; 
    }; 
    
    // Klasse des Plugins, welche sich anmelden möchte
    class PluginClass : public PluginInterface 
    { 
    public: 
        void ShowText() { std::cout << "Eigener Text aus dem Plugin!" << std::endl; } 
    }; 
    
    class Hauptprogramm
    {
    	std::vector<PluginInterface*> PluginHandles;
    
    public:
    	inline void AddNewPlugin(PluginInterface* plugin) { 
    		PluginHandles.push_back(plugin); 
    	}
    
    	inline PluginInterface* GetPluginHandle(unsigned short id) { 
    		return PluginHandles.at(id); 
    	}
    };
    
    int main()
    {
    	Hauptprogramm proggi;
    	PluginClass* plugin = new PluginClass;
    
    	proggi.AddNewPlugin(plugin);
    	proggi.GetPluginHandle(0)->ShowText();
    	delete plugin;
    }
    


  • Bei den Fragen die du stellst, glauch ich nicht, dass du in der Lage bist das zu machen, was du vor hast.

    Das kann schon sein aber wer nicht wagt,der nicht gewinnt.

    @mikey: danke für das Beispiel. ich werds mir zu Gemüte führen und versuchen es umzusetzen.

    Mfg XBert


Anmelden zum Antworten