]> git.mxchange.org Git - simgear.git/blobdiff - simgear/scene/model/model.cxx
Improved tile cache priority scheme.
[simgear.git] / simgear / scene / model / model.cxx
index b9d0d89e502574a07696a283a1e0f80b218d8311..648b670aaf7ee4ad3032b0fb8989464f52d20027 100644 (file)
@@ -18,6 +18,7 @@
 #include <osgDB/ReadFile>
 #include <osgDB/SharedStateManager>
 
+#include <simgear/math/SGMath.hxx>
 #include <simgear/scene/material/Effect.hxx>
 #include <simgear/scene/material/EffectGeode.hxx>
 #include <simgear/scene/util/SGSceneFeatures.hxx>
@@ -32,6 +33,7 @@
 #include <simgear/props/props_io.hxx>
 #include <simgear/props/condition.hxx>
 
+#include "SGReaderWriterXMLOptions.hxx"
 #include "model.hxx"
 
 using std::vector;
@@ -208,11 +210,11 @@ class MakeEffectVisitor : public SplicingVisitor
 public:
     typedef std::map<string, SGPropertyNode_ptr> EffectMap;
     using SplicingVisitor::apply;
-    MakeEffectVisitor(const osgDB::ReaderWriter::Options* options = 0)
+    MakeEffectVisitor(const SGReaderWriterXMLOptions* options = 0)
         : _options(options)
     {
     }
-    virtual void apply(osg::Node& node);
+    virtual void apply(osg::Group& node);
     virtual void apply(osg::Geode& geode);
     EffectMap& getEffectMap() { return _effectMap; }
     const EffectMap& getEffectMap() const { return _effectMap; }
@@ -224,10 +226,10 @@ public:
 protected:
     EffectMap _effectMap;
     SGPropertyNode_ptr _currentEffectParent;
-    osg::ref_ptr<const osgDB::ReaderWriter::Options> _options;
+    osg::ref_ptr<const SGReaderWriterXMLOptions> _options;
 };
 
-void MakeEffectVisitor::apply(osg::Node& node)
+void MakeEffectVisitor::apply(osg::Group& node)
 {
     SGPropertyNode_ptr savedEffectRoot;
     const string& nodeName = node.getName();
@@ -241,6 +243,10 @@ void MakeEffectVisitor::apply(osg::Node& node)
         }
     }
     SplicingVisitor::apply(node);
+    // If a new node was created, copy the user data too.
+    ref_ptr<SGSceneUserData> userData = SGSceneUserData::getSceneUserData(&node);
+    if (userData.valid() && _childStack.back().back().get() != &node)
+        _childStack.back().back()->setUserData(new SGSceneUserData(*userData));
     if (restoreEffect)
         _currentEffectParent = savedEffectRoot;
 }
@@ -258,15 +264,24 @@ void MakeEffectVisitor::apply(osg::Geode& geode)
     makeParametersFromStateSet(ssRoot, ss);
     SGPropertyNode_ptr effectRoot = new SGPropertyNode;
     effect::mergePropertyTrees(effectRoot, ssRoot, _currentEffectParent);
-    Effect* effect = makeEffect(effectRoot, true, _options);
+    Effect* effect = makeEffect(effectRoot, true, _options.get());
     EffectGeode* eg = dynamic_cast<EffectGeode*>(&geode);
     if (eg) {
         eg->setEffect(effect);
     } else {
         eg = new EffectGeode;
         eg->setEffect(effect);
-        for (int i = 0; i < geode.getNumDrawables(); ++i)
-            eg->addDrawable(geode.getDrawable(i));
+        ref_ptr<SGSceneUserData> userData = SGSceneUserData::getSceneUserData(&geode);
+        if (userData.valid())
+            eg->setUserData(new SGSceneUserData(*userData));
+        for (unsigned i = 0; i < geode.getNumDrawables(); ++i) {
+            osg::Drawable *drawable = geode.getDrawable(i);
+            eg->addDrawable(drawable);
+
+            // Generate tangent vectors etc if needed
+            osg::Geometry *geom = dynamic_cast<osg::Geometry*>(drawable);
+            if(geom) eg->runGenerators(geom);
+        }
     }
     pushResultNode(&geode, eg);
 
@@ -294,7 +309,7 @@ protected:
 
 ref_ptr<Node> instantiateEffects(osg::Node* modelGroup,
                                  PropertyList& effectProps,
-                                 const osgDB::ReaderWriter::Options* options)
+                                 const SGReaderWriterXMLOptions* options)
 {
     SGPropertyNode_ptr defaultEffectPropRoot;
     MakeEffectVisitor visitor(options);