/* -*-c++-*- */ /* osgEarth - Geospatial SDK for OpenSceneGraph * Copyright 2008-2013 Pelican Mapping * http://osgearth.org * * osgEarth is free software; you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with this program. If not, see */ #ifndef OSGEARTH_EXTENSION_H #define OSGEARTH_EXTENSION_H 1 #include #include #include #include #include #include #include #include #define META_OE_Extension(NS, CLASS, SLUG) \ META_Object(NS, CLASS); \ CLASS (const CLASS & rhs, const osg::CopyOp& op) { } \ virtual const char* getConfigKey() const { return #SLUG ; } namespace osgEarth { /** * An Extension is an object that can be loaded on demand (from a plugin) * and can have multiple object-specific interfaces. Its main function is * to enable activation and configuration of a plugin feature from an * osgEarth .earth file. * * For example, the pattern for declaring an Extension that connects to a * MapNode looks like: * * public MyExtension : public Extension, * public ExtensionInterface * * You can implement more than one interface. This one would connect to a * MapNode and to a UI Control: * * public MyExtension : public Extension, * public ExtensionInterface, * public ExtensionInterface * * You can register an Extension so that one can activate and configure it * from a .earth file. Use the registration macro: * * REGISTER_OSGEARTH_EXTENSION( osgearth_extension, ExtentionClassName ); * * Where the string "extension" in osgearth_extension is the key string * that will appear in the earth file under the element. */ class OSGEARTH_EXPORT Extension : public osg::Object // header-only { public: META_OE_Extension(osgEarth, Extension, extension); /** * Sets DB options that this extension should use when doing IO operations. */ virtual void setDBOptions(const osgDB::Options* readOptions) { } /** * Gets the configuration options that can be used to re-configure * this Extension. Necessary for serialization. */ virtual const ConfigOptions& getConfigOptions() const; /** * Convenience function for casting the extension to another one of its * interfaces. */ template T* as() { return dynamic_cast(this); } template const T* as() const { return dynamic_cast(this); } protected: Extension(); protected: virtual ~Extension() { } public: /** * Attempts to create an instance of an named extension. */ static Extension* create(const std::string& name, const ConfigOptions& options); /** * Fetch configuration options from a plugin loader */ static const ConfigOptions& getConfigOptions(const osgDB::Options*); private: ConfigOptions _defaultOptions; }; /** * This template lets you create object-specific interfaces in an extension. */ template class ExtensionInterface { public: /** * Connects the extension to an object. */ virtual bool connect(T* object) =0; /** * Disconnects the extension from an object. This should be the * same object used to call connect(). */ virtual bool disconnect(T* object) =0; /** * Cast a base extension to this interface, or return NULL * if the extenstion doesn't implemenent this inteface. */ static ExtensionInterface* get(Extension* e) { return dynamic_cast< ExtensionInterface* >(e); } }; } // namespace osgEarth #define REGISTER_OSGEARTH_EXTENSION(PLUGINNAME, CLASS) \ extern "C" void osgdb_##PLUGINNAME(void) {} \ static osgEarth::RegisterPluginLoader< osgEarth::PluginLoader > g_proxy_##CLASS_##PLUGINNAME( #PLUGINNAME ); #endif