1 // Copyright (C) 2008 - 2009 Tim Moore timoore@redhat.com
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Library General Public
5 // License as published by the Free Software Foundation; either
6 // version 2 of the License, or (at your option) any later version.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Library General Public License for more details.
13 // You should have received a copy of the GNU General Public License
14 // along with this program; if not, write to the Free Software
15 // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17 #ifndef SIMGEAR_EFFECT_HXX
18 #define SIMGEAR_EFFECT_HXX 1
22 #include <boost/tr1/unordered_map.hpp>
24 #include <boost/functional/hash.hpp>
27 #include <osg/observer_ptr>
28 #include <osgDB/ReaderWriter>
30 #include <simgear/props/props.hxx>
31 #include <simgear/scene/util/UpdateOnceCallback.hxx>
49 class SGReaderWriterOptions;
52 * Object to be initialized at some point after an effect -- and its
53 * containing effect geode -- are hooked into the scene graph. Some
54 * things, like manipulations of the global property tree, are are
55 * only safe in the update process.
57 class DeferredPropertyListener {
59 virtual void activate(SGPropertyNode* propRoot) {};
60 virtual ~DeferredPropertyListener() {};
63 class Effect : public osg::Object
66 META_Object(simgear,Effect)
68 Effect(const Effect& rhs,
69 const osg::CopyOp& copyop = osg::CopyOp::SHALLOW_COPY);
70 osg::StateSet* getDefaultStateSet();
72 // Define what needs to be generated for this effect
79 void setGenerator(Generator what, int where) { generator[what] = where; }
80 int getGenerator(Generator what) const; // Returns -1 if generator should not be used
81 std::map<Generator, int> generator; // What is generated into which attribute location
83 std::vector<osg::ref_ptr<Technique> > techniques;
84 SGPropertyNode_ptr root;
85 // Pointer to the parameters node, if it exists
86 SGPropertyNode_ptr parametersProp;
87 Technique* chooseTechnique(osg::RenderInfo* renderInfo);
88 virtual void resizeGLObjectBuffers(unsigned int maxSize);
89 virtual void releaseGLObjects(osg::State* state = 0) const;
91 * Build the techniques from the effect properties.
93 bool realizeTechniques(const SGReaderWriterOptions* options = 0);
94 void addDeferredPropertyListener(DeferredPropertyListener* listener);
95 // Callback that is added to the effect geode to initialize the
97 friend struct InitializeCallback;
98 struct InitializeCallback : public UpdateOnceCallback
100 void doUpdate(osg::Node* node, osg::NodeVisitor* nv);
103 std::string getName(){return _name;}
104 void setName(std::string name){_name = name;}
107 // Support for a cache of effects that inherit from this one, so
108 // Effect objects with the same parameters and techniques can be
113 Key(SGPropertyNode* unmerged_, const osgDB::FilePathList& paths_)
114 : unmerged(unmerged_), paths(paths_)
117 Key& operator=(const Key& rhs)
119 unmerged = rhs.unmerged;
123 SGPropertyNode_ptr unmerged;
124 osgDB::FilePathList paths;
127 bool operator()(const Key& lhs, const Key& rhs) const;
130 typedef std::tr1::unordered_map<Key, osg::observer_ptr<Effect>,
131 boost::hash<Key>, Key::EqualTo> Cache;
139 friend size_t hash_value(const Key& key);
140 friend Effect* makeEffect(SGPropertyNode* prop, bool realizeTechniques,
141 const SGReaderWriterOptions* options);
145 // Automatic support for boost hash function
146 size_t hash_value(const Effect::Key&);
149 Effect* makeEffect(const std::string& name,
150 bool realizeTechniques,
151 const SGReaderWriterOptions* options);
153 Effect* makeEffect(SGPropertyNode* prop,
154 bool realizeTechniques,
155 const SGReaderWriterOptions* options);
157 bool makeParametersFromStateSet(SGPropertyNode* paramRoot,
158 const osg::StateSet* ss);
160 void clearEffectCache();
165 * The function that implements effect property tree inheritance.
167 void mergePropertyTrees(SGPropertyNode* resultNode,
168 const SGPropertyNode* left,
169 const SGPropertyNode* right);