pluginProgramming.docu 8.92 KB
 Jan Möbius committed Feb 22, 2011 1 /** \page pluginProgramming Plugin Programming  Mike Kremer committed Apr 22, 2009 2  *  Jan Möbius committed Oct 23, 2009 3  *  Mike Kremer committed Apr 22, 2009 4 5  * \section quickref Quick references: * - \ref plugin_sec  Jan Möbius committed Feb 14, 2012 6  * - \ref plugin_startup  Mike Kremer committed Apr 22, 2009 7 8 9 10  * - \ref plugin_prog_sec * - \ref geometryData * \section tuts Tutorials * - \ref ex1  Mike Kremer committed Sep 29, 2009 11  * - \ref ex1c  Mike Kremer committed Apr 22, 2009 12 13  * - \ref ex2 * - \ref ex3  Jan Möbius committed Mar 17, 2011 14  * - \ref tutorial_thread  Mike Kremer committed Apr 22, 2009 15 16 17  * * \section plugin_sec Plugin Basics *  Jan Möbius committed Feb 25, 2011 18  * As mentioned above OpenFlipper is a plugin based system. It uses the QT plugin implementation to  Mike Kremer committed Apr 22, 2009 19 20 21  * load and unload plugins at runtime. Every algorithm should be added as one of these plugins. * * The plugins have to be created as .so (or under windows : .dll) files which should be symlinked or  Jan Möbius committed Feb 25, 2011 22 23 24  * copied to the Plugin sub folder. The cmake build system automatically places the plugins in the right folders * on all supported platforms. The Plugins are then loaded on startup of the core application * (they may also be loaded at runtime later).  Jan Möbius committed Feb 14, 2012 25 26 27 28 29 30 31 32 33 34  * * \section plugin_startup OpenFlipper Startup and Plugin Initialization * The plugins are initialized as shown in the following flow diagram: * * \image html OpenFlipperStartup.png * * OpenFlipper first starts its core system. Therefore it loads the settings, parses command line options and initializes * the QT library. Afterwards the object and scenegraph management are initialized. The next step creates the core * user interface and the logging system. Now the plugins are loaded in the following way: * -# All the plugins are loaded into memory.  Jan Möbius committed Feb 14, 2012 35  * -# For each plugin, the interfaces get connected and afterwards the BaseInterface::initializePlugin() function is called.  Jan Möbius committed Feb 14, 2012 36  * (Here you can setup your internal variables). After execution of this slot your plugin should be fully functional. Only gui  Jan Möbius committed Feb 14, 2012 37  * elements may be uninitialized and should be created in BaseInterface::pluginsInitialized().  Jan Möbius committed Feb 14, 2012 38 39 40 41 42 43 44 45 46  * -# For each plugin the BaseInterface::pluginsInitialized() function is called. Here you can setup your gui elements and start * sending signals to the core. * -# For each plugin the INIInterface::loadIniFileOptions() slot is called (if the interface is implemented). This slot can be used to load * additional options from INI files. (DEPRECATED! Use the OpenFlipperSettings() class instead) * *\note - Do not create objects via addEmpty or load objects during OpenFlipper startup, as the rendering system is not ready yet! *\note - The ini interface is deprecated for loading or storing plugin options. Please use OpenFlipperSettings() instead. * * Afterwards the plugin initialization is complete and the core sets up the final gui.  Mike Kremer committed Apr 22, 2009 47  *  Jan Möbius committed Feb 25, 2011 48  * \section plugin_prog_sec Plugin Programming  Mike Kremer committed Apr 22, 2009 49  * The interface between the core and the plugins is managed via simple interfaces based on the signal/slot  Jan Möbius committed Feb 25, 2011 50 51 52  * metaphor of QT. Your plugins have to be derived from these interfaces. You don't have to implement * all functions or signals of the interfaces you include. The BaseInterface has to be included in every * plugin. See the \ref baseInterfacePage "BaseInterface Documentation" for details.  Mike Kremer committed Apr 22, 2009 53  *  Jan Möbius committed Feb 25, 2011 54  * Unimplemented functions will be left unconnected from the core and won't have any impact on the applications  Mike Kremer committed Apr 22, 2009 55  * speed or stability. As stated above, every plugin has to be derived from the BaseInterface. This is the  Jan Möbius committed Feb 25, 2011 56 57 58 59  * basic factory which makes the core aware of the plugin. The BaseInterface::name() and the * BaseInterface::description() of the plugin is exported via the BaseInterface. The initialization of each * plugin is done via this interface too. * See \ref baseInterfacePluginInitialization for an overview of OpenFlipper's startup and initialization calls.  Mike Kremer committed Apr 22, 2009 60  *  Jan Möbius committed Feb 25, 2011 61  * After this interface of the plugin is successfully processed all other interfaces will be initialized  Jan Möbius committed Feb 25, 2011 62 63  * and connected to the core. For details about the individual interfaces see the * \ref interfaces "Plugin Interfaces Documentation".  Mike Kremer committed Apr 22, 2009 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95  * * \section geometryData Handling geometry data within a plugin * * \subsection addingAndRemovingGeometry Adding and removing mesh objects in OpenFlipper * * If you want to load geometry data from a file or simply add objects to the scene * from within a plugin, it has to implement the \ref LoadSavePlugin. * * LoadSaveInterface::load( QString _file, DataType _type, int& _id) tries to * load file with file name _file of type _type, _id contains the new created * object's id or -1 if loading failed. OpenFlipper will then create all * the necessary scene graph nodes such that the developer generally does * not need to know in detail how to create and add the required nodes to the scene. * * Otherwise if a file has been loaded externally, slot * * LoadSaveInterface::openedFile (int _id) is called. * * When removing objects from the scene, the plugin simply has to emit signal * * LoadSaveInterface::deleteObject(int _id) * * or * * LoadSaveInterface::deleteAllObjects() in order to clear the scene. * * \subsection pluginFunctions OpenFlipper's plugin functions * * As a plugin in most cases operates on geometry data, developers might want to know how to gain access to mesh data * from within a plugin. In our tutorial \ref ex2 we roughly mentioned that the communication between OpenFlipper * and it's plugins is accomplished through either one of the provided \ref interfaces or the \ref PluginFunctions. *  Jan Möbius committed Jan 27, 2012 96 97  * For example iterating over all objects is managed via the ObjectIterator. *  Mike Kremer committed Apr 22, 2009 98 99 100 101  * * for ( PluginFunctions::ObjectIterator o_it(PluginFunctions::SOURCE_OBJECTS);
 Jan Möbius committed Jan 27, 2012 102 103  * * See \ref OpenFlipperIterators for details.  Mike Kremer committed Apr 22, 2009 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126  * * Possible restrictions are \c ALL_OBJECTS (to iterate over all objects in the scene), \c TARGET_OBJECTS (objects * that were marked as target) and \c SOURCE_OBJECTS. * * Another way to get handles to scene objects is to use the functions \c PluginFunctions::getObject() or * PluginFunctions::getPickedObject(). These functions provide a pointer to either a \ref BaseObjectData * or \ref BaseObject object. As in \ref ex2 one can easily test the type of an object by calling * * \c o_it->dataType(DATA_TYPE) * * where \c o_it is an object iterator and \c DATA_TYPE is one of the data types specified in \ref OpenFlipper/common/Types.hh. * \c o_it->dataType(DATA_TRIANGLE_MESH) for example will return true if the object is a triangle mesh. * * The mesh data itself can be obtained by calling the appropriate handle plugin function. For example if we consider * a triangle mesh, we get a handle to the mesh itself by calling * * TriMesh* mesh = PluginFunctions::triMesh(*o_it); * * where \c o_it once again is our object iterator. See \ref PluginFunctions for a complete overview. * * \subsection updatingObjects Updating objects * * Once your plugin has manipulated object data we have to inform OpenFlipper's core about the changes.  Mike Kremer committed Mar 10, 2010 127  * When doing this, OpenFlipper distinguishes between five basic types of changes:  Mike Kremer committed Apr 22, 2009 128  *  Mike Kremer committed Mar 10, 2010 129 130 131 132 133  * - Object selections * - Visibility * - Geometry * - Topology * - Selections (Vertices, Edges, Faces)  Mike Kremer committed Apr 22, 2009 134 135 136 137  * * When changing geometry, OpenFlipper's core will be forced to redraw the object that has been * changed by emitting signal *  Mike Kremer committed Mar 10, 2010 138  * \ref BaseInterface::updatedObject(int _id, UpdateType _type)  Mike Kremer committed Apr 22, 2009 139  *  Mike Kremer committed Mar 10, 2010 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158  * where \c _id is the object's id and _type is the type of changes that have been made. * Note: UpdateType offers the following values * * - UPDATE_ALL * - UPDATE_OBJECT_SELECTION * - UPDATE_VISIBILITY * - UPDATE_GEOMETRY * - UPDATE_TOPOLOGY * - UPDATE_SELECTION (ALL THREE KINDS) * - UPDATE_SELECTION_VERTICES * - UPDATE_SELECTION_EDGES * - UPDATE_SELECTION_FACES * - UPDATE_UNUSED * * If the second parameter of this signal is not specified, it will fall back * to the default value UPDATE_ALL for compatibility reasons which actually updates * each of the types. Unless it is really necessary this should generally be avoided * since it consumes a lot of computation time. *  Mike Kremer committed Mar 10, 2010 159 160 161 162  * Additionally, when overriding the slot BaseInterface::slotObjectUpdated(int, const UpdateType), * a plugin receives the updated object's id (first parameter) and the type * of changes (second parameter). *  Mike Kremer committed Mar 10, 2010 163  * See \ref BaseInterface for more information.  Mike Kremer committed Apr 22, 2009 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185  * * When changing object properties it won't be necessary to redraw the scene * since it can be expensive in computation power. In this case, one should emit * * \ref BaseInterface::objectPropertiesChanged(int _id) * * where \c _id once again is the object's id. * * If a plugin changed an object's visibility (hide, show), it should emit * * \ref BaseInterface::visibilityChanged(int _id) * * for the core to update the visibility state of object with identifier \c _id. * * Last, when changing an object's selection, it * will be updated by emitting * * \ref BaseInterface::objectSelectionChanged(int _id) * * where \c _id as in the examples above is the object's identifier. * * Also see \ref BaseInterface.  Jan Möbius committed Oct 23, 2009 186  *  Jan Möbius committed Jan 27, 2012 187 188 189 190 191  * \section pluginProgramming_related_pages Related pages * - \subpage pluginExamples * - \subpage OpenFlipperIterators * - \subpage interfaces * - \subpage adding_empty_objects  Mike Kremer committed Apr 22, 2009 192  */