]> git.mxchange.org Git - simgear.git/commitdiff
getStateAttribute utility function
authorTim Moore <timoore@redhat.com>
Tue, 8 Sep 2009 10:53:33 +0000 (12:53 +0200)
committerTim Moore <timoore@redhat.com>
Fri, 13 Nov 2009 21:41:11 +0000 (22:41 +0100)
This provides a concise, typesafe way to get attributes from osg::StateSet.

Also, blew away BackRefInserter.

simgear/scene/material/Effect.cxx
simgear/structure/OSGUtils.hxx

index 5562c63b2f0d6b1cacd3441d80c6dc80bb121443..eba40dd74d10634e445e5cac9ad5aee12c4bbb96 100644 (file)
@@ -881,9 +881,7 @@ bool makeParametersFromStateSet(SGPropertyNode* paramRoot, const StateSet* ss)
     SGPropertyNode* matNode = paramRoot->getChild("material", 0, true);
     Vec4f ambVal, difVal, specVal, emisVal;
     float shininess = 0.0f;
-    const Material* mat
-        = static_cast<const Material*>(ss->getAttribute(StateAttribute
-                                                        ::MATERIAL));
+    const Material* mat = getStateAttribute<Material>(ss);
     if (mat) {
         ambVal = mat->getAmbient(Material::FRONT_AND_BACK);
         difVal = mat->getDiffuse(Material::FRONT_AND_BACK);
@@ -897,9 +895,7 @@ bool makeParametersFromStateSet(SGPropertyNode* paramRoot, const StateSet* ss)
     matNode->getChild("emissive", 0, true)->setValue(toVec4d(toSG(emisVal)));
     matNode->getChild("shininess", 0, true)->setValue(shininess);
     matNode->getChild("color-mode", 0, true)->setStringValue("diffuse");
-    const ShadeModel* sm
-        = static_cast<const ShadeModel*>(ss->getAttribute(StateAttribute
-                                                          ::SHADEMODEL));
+    const ShadeModel* sm = getStateAttribute<ShadeModel>(ss);
     string shadeModelString("smooth");
     if (sm) {
         ShadeModel::Mode smMode = sm->getMode();
@@ -909,9 +905,7 @@ bool makeParametersFromStateSet(SGPropertyNode* paramRoot, const StateSet* ss)
     paramRoot->getChild("shade-model", 0, true)
         ->setStringValue(shadeModelString);
     string cullFaceString("off");
-    const CullFace* cullFace
-        = static_cast<const CullFace*>(ss->getAttribute(StateAttribute
-                                                        ::CULLFACE));
+    const CullFace* cullFace = getStateAttribute<CullFace>(ss);
     if (cullFace) {
         switch (cullFace->getMode()) {
         case CullFace::FRONT:
index 21c5d698bbce3b1bc00f643cfc49917dba6220b4..557339d0ae9d73039425ca3b630fc59130c36bea 100644 (file)
@@ -20,8 +20,9 @@
 #ifndef SIMGEAR_OSGUTILS_HXX
 #define SIMGEAR_OSGUTILS_HXX 1
 
-#include <boost/iterator/iterator_facade.hpp>
 #include <osg/CopyOp>
+#include <osg/StateAttribute>
+#include <osg/StateSet>
 
 namespace simgear
 {
@@ -99,59 +100,280 @@ T* clone_ref(const osg::ref_ptr<T>& object,
     return static_cast<T*>(object->clone(copyop));
 }
 
-template<typename Container>
-class BackRefInsertIterator
-    : public boost::iterator_facade<BackRefInsertIterator<Container>,
-                                    BackRefInsertIterator<Container>,
-                                    boost::incrementable_traversal_tag
-                                    >
+}
+
+namespace osg
 {
-public:
-    typedef typename Container::value_type::element_type* PtrType;
-    BackRefInsertIterator() : _container(0) {}
-    explicit BackRefInsertIterator(Container& container)
-        : _container(&container)
-    {
-    }
+class AlphaFunc;
+class BlendColor;
+class BlendEquation;
+class BlendFunc;
+class ClampColor;
+class ColorMask;
+class ColorMatrix;
+class CullFace;
+class Depth;
+class Fog;
+class FragmentProgram;
+class FrontFace;
+class LightModel;
+class LineStipple;
+class LineWidth;
+class LogicOp;
+class Material;
+class Multisample;
+class Point;
+class PointSprite;
+class PolygonMode;
+class PolygonOffset;
+class PolygonStipple;
+class Program;
+class Scissor;
+class ShadeModel;
+class Stencil;
+class StencilTwoSided;
+class TexEnv;
+class TexEnvCombine;
+class TexEnvFilter;
+class TexGen;
+class TexMat;
+class Texture1D;
+class Texture2D;
+class Texture2DArray;
+class Texture3D;
+class TextureCubeMap;
+class TextureRectangle;
+class VertexProgram;
+class Viewport;
+}
 
-    BackRefInsertIterator&
-    operator=(const PtrType ptr)
-    {
-        _container->push_back(ptr);
-        return *this;
-    }
-    
-private:
-    friend class boost::iterator_core_access;
+namespace simgear
+{
+namespace osgutils
+{
+using namespace osg;
 
-    void increment()
-    {
-    }
-    
-    BackRefInsertIterator& dereference()
-    {
-        return *this;
-    }
+template<StateAttribute::Type T>
+struct TypeHolder
+{
+    static const StateAttribute::Type type = T;
+};
 
-    BackRefInsertIterator& dereference() const
-    {
-        return const_cast<BackRefInsertIterator&>(*this);
-    }
+template<typename AT> struct AttributeType;
+template<typename AT> struct TexAttributeType;
 
-    bool equal(const BackRefInsertIterator& rhs)
-    {
-        return _container == rhs._container;
-    }
-    
-    Container* _container;
-};
+template<>
+struct AttributeType<AlphaFunc>
+    : public TypeHolder<StateAttribute::ALPHAFUNC>
+{};
+
+template<>
+struct AttributeType<BlendColor>
+    : public TypeHolder<StateAttribute::BLENDCOLOR>
+{};
+
+template<>
+struct AttributeType<BlendEquation>
+    : public TypeHolder<StateAttribute::BLENDEQUATION>
+{};
+
+template<>
+struct AttributeType<BlendFunc>
+    : public TypeHolder<StateAttribute::BLENDFUNC>
+{};
+
+template<>
+struct AttributeType<ClampColor>
+    : public TypeHolder<StateAttribute::CLAMPCOLOR>
+{};
+
+template<>
+struct AttributeType<ColorMask>
+    : public TypeHolder<StateAttribute::COLORMASK>
+{};
+
+template<>
+struct AttributeType<ColorMatrix>
+    : public TypeHolder<StateAttribute::COLORMATRIX>
+{};
+
+template<>
+struct AttributeType<CullFace>
+    : public TypeHolder<StateAttribute::CULLFACE>
+{};
+
+
+template<>
+struct AttributeType<osg::Depth> // Conflicts with Xlib
+    : public TypeHolder<StateAttribute::DEPTH>
+{};
+
+template<>
+struct AttributeType<Fog>
+    : public TypeHolder<StateAttribute::FOG>
+{};
+
+template<>
+struct AttributeType<FragmentProgram>
+    : public TypeHolder<StateAttribute::FRAGMENTPROGRAM>
+{};
 
+template<>
+struct AttributeType<FrontFace>
+    : public TypeHolder<StateAttribute::FRONTFACE>
+{};
 
-template<typename Container>
-inline BackRefInsertIterator<Container>
-backRefInsertIterator(Container& container)
+template<>
+struct AttributeType<LightModel>
+    : public TypeHolder<StateAttribute::LIGHTMODEL>
+{};
+
+template<>
+struct AttributeType<LineStipple>
+    : public TypeHolder<StateAttribute::LINESTIPPLE>
+{};
+
+template<>
+struct AttributeType<LineWidth>
+    : public TypeHolder<StateAttribute::LINEWIDTH>
+{};
+
+template<>
+struct AttributeType<LogicOp>
+    : public TypeHolder<StateAttribute::LOGICOP>
+{};
+
+template<>
+struct AttributeType<Material>
+    : public TypeHolder<StateAttribute::MATERIAL>
+{};
+
+template<>
+struct AttributeType<Multisample>
+    : public TypeHolder<StateAttribute::MULTISAMPLE>
+{};
+
+template<>
+struct AttributeType<Point>
+    : public TypeHolder<StateAttribute::POINT>
+{};
+
+template<>
+struct TexAttributeType<PointSprite>
+    : public TypeHolder<StateAttribute::POINTSPRITE>
+{};
+
+template<>
+struct AttributeType<PolygonMode>
+    : public TypeHolder<StateAttribute::POLYGONMODE>
+{};
+
+template<>
+struct AttributeType<PolygonOffset>
+    : public TypeHolder<StateAttribute::POLYGONOFFSET>
+{};
+
+template<>
+struct AttributeType<PolygonStipple>
+    : public TypeHolder<StateAttribute::POLYGONSTIPPLE>
+{};
+
+template<>
+struct AttributeType<Program>
+    : public TypeHolder<StateAttribute::PROGRAM>
+{};
+
+template<>
+struct AttributeType<Scissor>
+    : public TypeHolder<StateAttribute::SCISSOR>
+{};
+
+template<>
+struct AttributeType<ShadeModel>
+    : public TypeHolder<StateAttribute::SHADEMODEL>
+{};
+
+template<>
+struct AttributeType<Stencil>
+    : public TypeHolder<StateAttribute::STENCIL>
+{};
+
+template<>
+struct AttributeType<StencilTwoSided>
+    : public TypeHolder<StateAttribute::STENCIL>
+{};
+
+// TexEnvCombine is not a subclass of TexEnv, so we can't do a
+// typesafe access of the attribute.
+#if 0
+template<>
+struct TexAttributeType<TexEnv>
+    : public TypeHolder<StateAttribute::TEXENV>
+{};
+
+template<>
+struct TexAttributeType<TexEnvCombine>
+    : public TypeHolder<StateAttribute::TEXENV>
+{};
+#endif
+
+template<>
+struct TexAttributeType<TexEnvFilter>
+    : public TypeHolder<StateAttribute::TEXENVFILTER>
+{};
+
+template<>
+struct TexAttributeType<TexGen>
+    : public TypeHolder<StateAttribute::TEXGEN>
+{};
+
+template<>
+struct TexAttributeType<TexMat>
+    : public TypeHolder<StateAttribute::TEXMAT>
+{};
+
+template<>
+struct TexAttributeType<Texture>
+    : public TypeHolder<StateAttribute::TEXTURE>
+{};
+
+template<>
+struct AttributeType<VertexProgram>
+    : public TypeHolder<StateAttribute::VERTEXPROGRAM>
+{};
+
+template<>
+struct AttributeType<Viewport>
+    : public TypeHolder<StateAttribute::VIEWPORT>
+{};
+} // namespace osgutils
+
+template<typename AT>
+inline AT* getStateAttribute(osg::StateSet* ss)
 {
-    return BackRefInsertIterator<Container>(container);
+    return static_cast<AT*>(ss->getAttribute(osgutils::AttributeType<AT>::type));
 }
+
+template<typename AT>
+inline const AT* getStateAttribute(const osg::StateSet* ss)
+{
+    return static_cast<const AT*>(ss->getAttribute(osgutils::AttributeType<AT>::type));
+}
+
+template<typename AT>
+inline AT* getStateAttribute(unsigned int unit, osg::StateSet* ss)
+{
+    return static_cast<AT*>(ss->getTextureAttribute(unit, osgutils::TexAttributeType<AT>
+                                                    ::type));
 }
+
+template<typename AT>
+inline const AT* getStateAttribute(unsigned int unit, const osg::StateSet* ss)
+{
+    return static_cast<const AT*>(ss->getTextureAttribute(unit,
+                                                          osgutils::TexAttributeType<AT>
+                                                          ::type));
+}
+} // namespace simgear
+
 #endif