]> git.mxchange.org Git - simgear.git/blobdiff - simgear/scene/material/Effect.cxx
Work around apparent OSG 3.2.0 normal binding bug.
[simgear.git] / simgear / scene / material / Effect.cxx
index 70f8e8fe49509e5c199aab64405ccfa8a77ae8bb..17b02a65a8e878e6d0d1cbb788cae66d860cf34c 100644 (file)
@@ -24,6 +24,7 @@
 #include "Technique.hxx"
 #include "Pass.hxx"
 #include "TextureBuilder.hxx"
+#include "parseBlendFunc.hxx"
 
 #include <algorithm>
 #include <functional>
@@ -453,58 +454,16 @@ struct BlendBuilder : public PassAttributeBuilder
             pass->setMode(GL_BLEND, StateAttribute::OFF);
             return;
         }
-        const SGPropertyNode* psource
-            = getEffectPropertyChild(effect, prop, "source");
-        const SGPropertyNode* pdestination
-            = getEffectPropertyChild(effect, prop, "destination");
-        const SGPropertyNode* psourceRGB
-            = getEffectPropertyChild(effect, prop, "source-rgb");
-        const SGPropertyNode* psourceAlpha
-            = getEffectPropertyChild(effect, prop, "source-alpha");
-        const SGPropertyNode* pdestRGB
-            = getEffectPropertyChild(effect, prop, "destination-rgb");
-        const SGPropertyNode* pdestAlpha
-            = getEffectPropertyChild(effect, prop, "destination-alpha");
-        BlendFunc::BlendFuncMode sourceMode = BlendFunc::ONE;
-        BlendFunc::BlendFuncMode destMode = BlendFunc::ZERO;
-        if (psource)
-            findAttr(blendFuncModes, psource, sourceMode);
-        if (pdestination)
-            findAttr(blendFuncModes, pdestination, destMode);
-        if (psource && pdestination
-            && !(psourceRGB || psourceAlpha || pdestRGB || pdestAlpha)
-            && sourceMode == BlendFunc::SRC_ALPHA
-            && destMode == BlendFunc::ONE_MINUS_SRC_ALPHA) {
-            pass->setAttributeAndModes(StateAttributeFactory::instance()
-                                       ->getStandardBlendFunc());
-            return;
-        }
-        BlendFunc* blendFunc = new BlendFunc;
-        if (psource)
-            blendFunc->setSource(sourceMode);
-        if (pdestination)
-            blendFunc->setDestination(destMode);
-        if (psourceRGB) {
-            BlendFunc::BlendFuncMode sourceRGBMode;
-            findAttr(blendFuncModes, psourceRGB, sourceRGBMode);
-            blendFunc->setSourceRGB(sourceRGBMode);
-        }
-        if (pdestRGB) {
-            BlendFunc::BlendFuncMode destRGBMode;
-            findAttr(blendFuncModes, pdestRGB, destRGBMode);
-            blendFunc->setDestinationRGB(destRGBMode);
-        }
-        if (psourceAlpha) {
-            BlendFunc::BlendFuncMode sourceAlphaMode;
-            findAttr(blendFuncModes, psourceAlpha, sourceAlphaMode);
-            blendFunc->setSourceAlpha(sourceAlphaMode);
-        }
-        if (pdestAlpha) {
-            BlendFunc::BlendFuncMode destAlphaMode;
-            findAttr(blendFuncModes, pdestAlpha, destAlphaMode);
-            blendFunc->setDestinationAlpha(destAlphaMode);
-        }
-        pass->setAttributeAndModes(blendFunc);
+
+        parseBlendFunc(
+          pass,
+          getEffectPropertyChild(effect, prop, "source"),
+          getEffectPropertyChild(effect, prop, "destination"),
+          getEffectPropertyChild(effect, prop, "source-rgb"),
+          getEffectPropertyChild(effect, prop, "destination-rgb"),
+          getEffectPropertyChild(effect, prop, "source-alpha"),
+          getEffectPropertyChild(effect, prop, "destination-alpha")
+        );
     }
 };
 
@@ -1399,14 +1358,25 @@ template<typename T>
 class PropertyExpression : public SGExpression<T>
 {
 public:
-    PropertyExpression(SGPropertyNode* pnode) : _pnode(pnode) {}
+    PropertyExpression(SGPropertyNode* pnode) : _pnode(pnode), _listener(NULL) {}
+    
+    ~PropertyExpression()
+    {
+        delete _listener;
+    }
     
     void eval(T& value, const expression::Binding*) const
     {
         value = _pnode->getValue<T>();
     }
+    
+    void setListener(SGPropertyChangeListener* l)
+    {
+        _listener = l;
+    }
 protected:
     SGPropertyNode_ptr _pnode;
+    SGPropertyChangeListener* _listener;
 };
 
 class EffectPropertyListener : public SGPropertyChangeListener
@@ -1419,6 +1389,9 @@ public:
         if (_tniq.valid())
             _tniq->refreshValidity();
     }
+    
+    virtual ~EffectPropertyListener() { }
+    
 protected:
     osg::observer_ptr<Technique> _tniq;
 };
@@ -1432,9 +1405,12 @@ Expression* propertyExpressionParser(const SGPropertyNode* exp,
     PropertyExpression<T>* pexp = new PropertyExpression<T>(pnode);
     TechniquePredParser* predParser
         = dynamic_cast<TechniquePredParser*>(parser);
-    if (predParser)
-        pnode->addChangeListener(new EffectPropertyListener(predParser
-                                                            ->getTechnique()));
+    if (predParser) {
+        EffectPropertyListener* l = new EffectPropertyListener(predParser
+                                                               ->getTechnique());
+        pexp->setListener(l);
+        pnode->addChangeListener(l);
+    }
     return pexp;
 }