日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Delta3d插件机制

發布時間:2024/8/23 编程问答 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Delta3d插件机制 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

Delta3d插件機制主要通過以下兩個類實現:

class MainWindow;/**Abstract interface class for STAGE plugins*/class Plugin{public:virtual ~Plugin() {} /** Is called after instantiation */virtual void Create() {}/** Is called before destruction */virtual void Destroy() {}};/** A plugin factory is used by the plugin manager to identify availableplugins and instantiate them.*/class PluginFactory{public:PluginFactory(): mIsSystemPlugin(false){}virtual ~PluginFactory() {}/** construct the plugin and return a pointer to it */virtual Plugin* Create(MainWindow* mw) = 0;/** delete the plugin */virtual void Destroy() = 0;/** get the name of the plugin */virtual std::string GetName() = 0;/** get a description of the plugin */virtual std::string GetDescription() = 0;/** fill list with names of all plugins this plugin depends on.WARNING: circular dependencies are not handled andwill cause a crash!*/virtual void GetDependencies(std::list<std::string>&) {};/** get the version of STAGE that the plugin is compiled against Only plugins compiled against the current version of STAGE are started*/virtual std::string GetExpectedSTAGEVersion() { // should be replaced by SVN to give version numberreturn "$Revision$"; }/** Should plugin be started autmatically? */bool IsSystemPlugin() { return mIsSystemPlugin; }protected:// set this to true if plugin should always be startedbool mIsSystemPlugin;}; class MainWindow;class DT_EDITQT_EXPORT PluginManager : public QObject{Q_OBJECTpublic:PluginManager(MainWindow* mw);typedef std::map<std::string,PluginFactory*> PluginFactoryMap;typedef std::map<std::string, Plugin*> ActivePluginMap;/** load all libraries in dir and check for plugin factories */void LoadPluginsInDir(const std::string& path);/** start all plugins that are saved as active in the config file */void StartPluginsInConfigFile();/*** write the list of active plugins to config file so * they can be started next time*/void StoreActivePluginsToConfigFile();/** get names of all plugins */void GetAvailablePlugins(std::list<std::string>& toFill) const;/** get names of all currently instantiated plugins */void GetActivePlugins(std::list<std::string>& toFill) const;/** is there a factory for a plugin with this name? */bool FactoryExists(const std::string& name);/** Get PluginFactory for Plugin with this name.* @throw dtUtil::Exception if no PluginFactory exists with that Plugin name* @param name The name of the Plugin/PluginFactory to get*/PluginFactory* GetPluginFactory(const std::string& name);/** is this plugin currently running? */bool IsInstantiated(const std::string& name);/** is this plugin a system plugin? */bool IsSystemPlugin(const std::string& name);/** return instance of plugin or NULL if not active */Plugin* GetPlugin(const std::string& name);/** returns all dependencies for a given plugin */std::list<std::string> GetPluginDependencies(const std::string& name);public slots:/** instantiate plugin with given name @param name Name of plugin to start@param storeToConfig Store list of active plugins to config file?*/void StartPlugin(const std::string& name, bool storeToConfig = true);/** stop and remove plugin with given name @param name Name of plugin to stop@param storeToConfig Store list of active plugins to config file?*/void StopPlugin(const std::string& name, bool storeToConfig = true);private:/** load plugin factory from library given by path */PluginFactory* LoadPluginFactory(const std::string& baseLibName);/** map from plugin name -> plugin factory */PluginFactoryMap mFactories;/** map from plugin name -> plugin instance */ActivePluginMap mActivePlugins;/** give plugins acces to GUI */MainWindow* mMainWindow;}; 實現文件如下:
PluginManager::PluginManager(MainWindow* mw): mMainWindow(mw){}/** load all dlls in dir and check for plugin factories */void PluginManager::LoadPluginsInDir(const std::string& path){// find out library extension for this system// take care of debug/release library stuff on windows#if defined(_MSC_VER) || defined(__CYGWIN__) || defined(__MINGW32__) || defined( __BCPLUSPLUS__) || defined( __MWERKS__)std::string libExtension = ".dll";#elsestd::string libExtension = ".so";#endif// get libs from directoryFileExtensionList ext;ext.push_back(libExtension);DirectoryContents files;try{files = FileUtils::GetInstance().DirGetFiles(path, ext);}catch (const dtUtil::Exception& e){//in case the path is bogusDTUNREFERENCED_PARAMETER(e);}if (!files.empty()){//add the path to the list of paths to search for libraries.LibrarySharingManager::GetInstance().AddToSearchPath(path);}// for each library in dirDirectoryContents::const_iterator i;for(i = files.begin(); i != files.end(); ++i){std::string fileName = *i;try{// load the plugin libraryconst std::string basePluginName = LibrarySharingManager::GetPlatformIndependentLibraryName(fileName);PluginFactory* factory = LoadPluginFactory(basePluginName);std::string name = factory->GetName();// check if a plugin with this name already existsif(mActivePlugins.find(name) != mActivePlugins.end()){std::ostringstream msg;msg << "Unable to load plugin " << name <<": A plugin with that name was already loaded!";throw Exception(msg.str(), __FILE__, __LINE__);}// insert factory into factory listmFactories[name] = factory;// factory exists, but plugin is not instantiated yetmActivePlugins[name] = NULL;// start system plugins immediatelyif(factory->IsSystemPlugin()){StartPlugin(name, false);}}catch(Exception& e){LOG_ERROR("Can't load plugin " + (*i) + " because " + e.ToString());}}}PluginFactory* PluginManager::LoadPluginFactory(const std::string& baseLibName){// use library sharing manager to do the actual library loadingLibrarySharingManager& lsm = LibrarySharingManager::GetInstance();dtCore::RefPtr<LibrarySharingManager::LibraryHandle> libHandle;try{libHandle = lsm.LoadSharedLibrary(baseLibName, true);}catch (const Exception&){std::ostringstream msg;msg << "Unable to load plugin " << baseLibName;throw Exception(msg.str(), __FILE__, __LINE__);}LibrarySharingManager::LibraryHandle::SYMBOL_ADDRESS createFn;createFn = libHandle->FindSymbol("CreatePluginFactory");//Make sure the plugin actually implemented these functions and they//have been exported.if (!createFn){std::ostringstream msg;msg << "Plugin " << baseLibName << " does not contain symbol 'CreatePluginFactory'";throw Exception(msg.str(), __FILE__, __LINE__);}// typedef for function pointer to get factory from librarytypedef PluginFactory* (*CreatePluginFactoryFn)();// instantiate factoryCreatePluginFactoryFn fn = (CreatePluginFactoryFn) createFn;PluginFactory* factory = fn();// check if the library was compiled against this revision of STAGEif(factory->GetExpectedSTAGEVersion() != "$Revision$"){std::ostringstream msg;msg << "Can't load plugin " << baseLibName << ": Built against wrong version";throw Exception(msg.str(), __FILE__, __LINE__);}else{return factory;}}/** get the list of plugins to start from config file and start them */void PluginManager::StartPluginsInConfigFile(){dtEditQt::EditorSettings settings;settings.beginGroup(EditorSettings::ACTIVE_PLUGINS);std::string activated =settings.value(EditorSettings::ACTIVE_PLUGINS).toString().toStdString();settings.endGroup();if(activated == ""){return;}// split config string by slashesstd::vector<std::string> tokens;StringTokenizer<IsSlash>::tokenize(tokens, activated);// for each tokenstd::vector<std::string>::iterator iter;for(iter = tokens.begin(); iter != tokens.end(); ++iter){std::string name = *iter;//if the plugin can be started and was not yet startedif(FactoryExists(name) && !IsInstantiated(name)){// start it!StartPlugin(name, false);}}}/*** write the list of active plugins to config file so* they can be started next time*/void PluginManager::StoreActivePluginsToConfigFile(){// create string with names of active plugins separated by slashstd::ostringstream os;std::list<std::string> plugins;GetActivePlugins(plugins);for(std::list<std::string>::iterator i = plugins.begin(); i != plugins.end(); ++i){// system plugins are always started, so no need to include themif(!IsSystemPlugin(*i)){os << *i << "/";}}dtEditQt::EditorSettings settings;settings.beginGroup(EditorSettings::ACTIVE_PLUGINS);settings.setValue(EditorSettings::ACTIVE_PLUGINS, os.str().c_str());settings.endGroup();}PluginFactory* PluginManager::GetPluginFactory(const std::string& name){PluginFactoryMap::iterator i = mFactories.find(name);if(i == mFactories.end()){throw Exception("Plugin not found with name " + name , __FILE__, __LINE__);}return i->second;}bool PluginManager::FactoryExists(const std::string& name){return (mFactories.find(name) != mFactories.end());}void PluginManager::GetAvailablePlugins(std::list<std::string>& toFill) const{PluginFactoryMap::const_iterator iter;for(iter = mFactories.begin(); iter != mFactories.end(); ++iter){PluginFactory* factory = (*iter).second;toFill.push_back(factory->GetName());}}void PluginManager::GetActivePlugins(std::list<std::string>& toFill) const{ActivePluginMap::const_iterator iter;for(iter = mActivePlugins.begin(); iter != mActivePlugins.end(); ++iter){if((*iter).second != NULL){toFill.push_back((*iter).first);}}}std::list<std::string> PluginManager::GetPluginDependencies(const std::string& name){std::list<std::string> deps;PluginFactory* factory = GetPluginFactory(name);if (factory){factory->GetDependencies(deps);}return deps;}void PluginManager::StartPlugin(const std::string& name, bool storeToConfig){LOG_ALWAYS("Starting plugin " + name);PluginFactory* factory = GetPluginFactory(name);// start all plugins this plugin depends onstd::list<std::string> deps;factory->GetDependencies(deps);while(!deps.empty()){std::string dependency = deps.front();deps.pop_front();// check if dependency can be fulfilledif(!FactoryExists(dependency)){std::ostringstream os;os << "Cannot start plugin " << name << ": It depends on plugin ";os << dependency << " which was not found.";QMessageBox::critical(mMainWindow, "Error", os.str().c_str(), "Ok");return;}// only start dependency if it is not running nowif(!IsInstantiated(dependency)){StartPlugin(dependency, false);}}// use factory to create the pluginmActivePlugins[name] = factory->Create(mMainWindow);// call Create() callback of pluginmActivePlugins[name]->Create();}void PluginManager::StopPlugin(const std::string& name, bool storeToConfig){// first check if plugin is actually runningif(!IsInstantiated(name)){return;}// Check if any other plugins depend on this one, and stop them as well.std::list<std::string> activePlugins;GetActivePlugins(activePlugins);while(!activePlugins.empty()){std::string plugin = activePlugins.front();activePlugins.pop_front();PluginFactory* factory = GetPluginFactory(plugin);// start all plugins this plugin depends onstd::list<std::string> deps;factory->GetDependencies(deps);while(!deps.empty()){std::string dependency = deps.front();deps.pop_front();// If the active plugin depends on this plugin, then we need to stop that one too.if (dependency == name){StopPlugin(plugin);break;}}}LOG_ALWAYS("Stopping plugin " + name);Plugin* plugin = GetPlugin(name);// call Destroy() callback of pluginplugin->Destroy();// tell factory to delete the pluginGetPluginFactory(name)->Destroy();// erase plugin from list of active pluginsmActivePlugins.erase(mActivePlugins.find(name));}bool PluginManager::IsInstantiated(const std::string& name){// all plugin names are in mActivePlugins, but names of non-active plugins// are mapped to NULLreturn mActivePlugins[name] != NULL;}/** is the plugin a system plugin? */bool PluginManager::IsSystemPlugin(const std::string& name){return GetPluginFactory(name)->IsSystemPlugin();}Plugin* PluginManager::GetPlugin(const std::string& name){// first check if plugin exists. return NULL if it doesn'tActivePluginMap::iterator i = mActivePlugins.find(name);if(i == mActivePlugins.end()){return NULL;}return i->second;}

通過繼承自抽象類Plugin實現自定義的插件,同時繼承自PluginFactory重寫主要函數實現自定義插件工廠(負責插件的生成),可以方便的對UI進行擴展;

/** construct the plugin and return a pointer to it */virtual Plugin* Create(MainWindow* mw) = 0;/** delete the plugin */virtual void Destroy() = 0;/** get the name of the plugin */virtual std::string GetName() = 0;/** get a description of the plugin */virtual std::string GetDescription() = 0;


自定義插件實現如下:

class XX_EXPORT CustomPlugin : public Plugin { public :void Create(){};void Destroy(){}; }; public XX_EXPORT CustomPluginFactory :public PluginFactory {public : Plugin* Create(MainWindow* mw) { mPlugin = new CustomPlugin(mv);return mPlugin; }void Destory() {delete mPlugin; }private:Plugin* mPlugin; };

在Dll中導出全局函數:

extern "C" XX_EXPORT PluginFactory* CreatePluginFactory() {return new PluginFactory(); }



總結

以上是生活随笔為你收集整理的Delta3d插件机制的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。