]> git.tdb.fi Git - libs/gl.git/commitdiff
Add a Tag class to identify passes
authorMikko Rasa <tdb@tdb.fi>
Sun, 4 Nov 2007 22:11:27 +0000 (22:11 +0000)
committerMikko Rasa <tdb@tdb.fi>
Sun, 4 Nov 2007 22:11:27 +0000 (22:11 +0000)
Refactor the Renderable and Object interfaces a bit

source/object.cpp
source/object.h
source/objectinstance.cpp
source/objectinstance.h
source/renderable.h
source/scene.cpp
source/scene.h
source/tag.cpp [new file with mode: 0644]
source/tag.h [new file with mode: 0644]

index dba9774e7531fa0f7549f56341ed08d19646a6be..3ba2d64c378862ea435f6d371cc4e5ec122a5579 100644 (file)
@@ -26,56 +26,41 @@ Object::Object():
        meshes(1, static_cast<Mesh *>(0)),
        material(0)
 {
-       normal_pass=&passes[""];
+       normal_pass=&passes[0];
 }
 
 Object::~Object()
 {
-       for(map<string, ObjectPass>::iterator i=passes.begin(); i!=passes.end(); ++i)
+       for(map<unsigned, ObjectPass>::iterator i=passes.begin(); i!=passes.end(); ++i)
                delete i->second.shdata;
 }
 
-bool Object::has_pass(const string &pn) const
+bool Object::has_pass(const Tag &tag) const
 {
-       return passes.count(pn);
+       return passes.count(tag.id);
 }
 
-const ObjectPass &Object::get_pass(const string &pn) const
+const ObjectPass &Object::get_pass(const Tag &tag) const
 {
-       map<string, ObjectPass>::const_iterator i=passes.find(pn);
+       map<unsigned, ObjectPass>::const_iterator i=passes.find(tag.id);
        if(i==passes.end())
                throw KeyError("Unknown pass");
        return i->second;
 }
 
-void Object::render() const
+void Object::render(const Tag &tag) const
 {
-       render(*normal_pass, 0);
+       render(get_pass(tag), 0);
 }
 
-void Object::render(const ObjectInstance &inst) const
+void Object::render(const ObjectInstance &inst, const Tag &tag) const
 {
-       render(*normal_pass, &inst);
+       render(get_pass(tag), &inst);
 }
 
-void Object::render(const string &pn) const
+void Object::render(const list<const ObjectInstance *> &insts, const Tag &tag) const
 {
-       render(get_pass(pn), 0);
-}
-
-void Object::render(const string &pn, const ObjectInstance &inst) const
-{
-       render(get_pass(pn), &inst);
-}
-
-void Object::render(const list<const ObjectInstance *> &insts) const
-{
-       render(*normal_pass, insts);
-}
-
-void Object::render(const string &pn, const list<const ObjectInstance *> &insts) const
-{
-       render(get_pass(pn), insts);
+       render(get_pass(tag), insts);
 }
 
 void Object::setup_render(const ObjectPass &pass) const
@@ -163,7 +148,7 @@ Object::Loader::Loader(Object &o, Collection &c):
 
 Object::Loader::~Loader()
 {
-       for(map<string, ObjectPass>::iterator i=obj.passes.begin(); i!=obj.passes.end(); ++i)
+       for(map<unsigned, ObjectPass>::iterator i=obj.passes.begin(); i!=obj.passes.end(); ++i)
                if(i->second.shdata)
                {
                        for(unsigned j=0; j<textures.size(); ++j)
@@ -193,11 +178,12 @@ void Object::Loader::mesh(const string &n)
 
 void Object::Loader::pass(const string &n)
 {
-       if(obj.passes.count(n))
+       unsigned id=Tag(n).id;
+       if(obj.passes.count(id))
                throw KeyError("Duplicate pass name");
        ObjectPass p;
        load_sub(p, coll);
-       obj.passes[n]=p;
+       obj.passes[id]=p;
 }
 
 void Object::Loader::shader(const string &n)
index f0940652992692bfce462258cf0d4a72e58b48ec..0b808983099e08ffba4caf01da9ad943b3966f0f 100644 (file)
@@ -35,7 +35,7 @@ class Object: public Renderable
 private:
        std::vector<Mesh *> meshes;
        std::vector<Texture *> textures;
-       std::map<std::string, ObjectPass> passes;
+       std::map<unsigned, ObjectPass> passes;
        Material *material;
        ObjectPass *normal_pass;
 
@@ -69,25 +69,28 @@ public:
        Object();
        ~Object();
 
-       virtual bool has_pass(const std::string &) const;
-       const ObjectPass &get_pass(const std::string &) const;
+       virtual bool has_pass(const Tag &) const;
+       const ObjectPass &get_pass(const Tag &) const;
 
        /**
-       Renders the object.  If an ObjectInstance is provided, its hook functions
-       are called.
+       Renders the object.  A tag can be provided to render a non-default pass.
        */
-       virtual void render() const;
-       virtual void render(const ObjectInstance &) const;
-       virtual void render(const std::string &) const;
-       virtual void render(const std::string &, const ObjectInstance &) const;
+       virtual void render(const Tag &tag=Tag()) const;
 
        /**
-       Renders multiple instances of the object in one go.  This may be a
-       performance improvement, as the object-specific render setup only has to be
-       done once.
+       Renders the object with an instance.  The instance's hook functions are
+       called before and after drawing the mesh.  A tag may also be given to render
+       a non-default pass.
        */
-       void render(const std::list<const ObjectInstance *> &) const;
-       void render(const std::string &, const std::list<const ObjectInstance *> &) const;
+       virtual void render(const ObjectInstance &, const Tag &tag=Tag()) const;
+
+       /**
+       Renders multiple instances of the object in one go.  This may improve
+       performance, as the object-specific render setup only has to be done once.
+       Each instance's hook functions will be called before and after drawing the
+       mesh.
+       */
+       void render(const std::list<const ObjectInstance *> &, const Tag &tag=Tag()) const;
 private:
        void setup_render(const ObjectPass &) const;
        void finish_render(const ObjectPass &) const;
index 10dae3926c05374d07df95e9cd58d7184eb23853..7552cc937f54f30b6ffb9c654f8db8bb3d9e525d 100644 (file)
@@ -18,19 +18,14 @@ ObjectInstance::ObjectInstance(const Object &obj):
        object(obj)
 { }
 
-bool ObjectInstance::has_pass(const string &pn) const
+bool ObjectInstance::has_pass(const Tag &tag) const
 {
-       return object.has_pass(pn);
+       return object.has_pass(tag);
 }
 
-void ObjectInstance::render() const
+void ObjectInstance::render(const Tag &tag) const
 {
-       object.render(*this);
-}
-
-void ObjectInstance::render(const string &pn) const
-{
-       object.render(pn, *this);
+       object.render(*this, tag);
 }
 
 } // namespace GL
index 459c2da3523b23ff84e2cd510e2cde05d0c5a154..12e0d7fb561de95018c3ca6811bfab28cba4de75 100644 (file)
@@ -34,10 +34,9 @@ public:
 
        const Object &get_object() const { return object; }
 
-       virtual bool has_pass(const std::string &) const;
+       virtual bool has_pass(const Tag &tag) const;
 
-       virtual void render() const;
-       virtual void render(const std::string &) const;
+       virtual void render(const Tag &tag=Tag()) const;
 
        /**
        Hook function, called from Object just before rendering the mesh.
index b9b6b080e363150616dc809072217dffda23395e..00b8b9012d32d927c2ac1506484db86aa63ba834 100644 (file)
@@ -9,6 +9,7 @@ Distributed under the LGPL
 #define MSP_GL_RENDERABLE_H_
 
 #include <string>
+#include "tag.h"
 
 namespace Msp {
 namespace GL {
@@ -16,10 +17,9 @@ namespace GL {
 class Renderable
 {
 public:
-       virtual bool has_pass(const std::string &pn) const =0;
+       virtual bool has_pass(const Tag &tag) const =0;
 
-       virtual void render() const =0;
-       virtual void render(const std::string &pn) const =0;
+       virtual void render(const Tag &tag=Tag()) const =0;
 };
 
 } // namespace Msp
index 2ef2ea786cbe0428ee087f52ca8cd5f0e64410b1..20399daff01256e35de5bc87dedeec852dd49131 100644 (file)
@@ -22,17 +22,11 @@ void Scene::remove(const Renderable &r)
        renderables.erase(&r);
 }
 
-void Scene::render() const
+void Scene::render(const Tag &tag) const
 {
        for(set<const Renderable *>::const_iterator i=renderables.begin(); i!=renderables.end(); ++i)
-               (*i)->render();
-}
-
-void Scene::render(const string &pn) const
-{
-       for(set<const Renderable *>::const_iterator i=renderables.begin(); i!=renderables.end(); ++i)
-               if((*i)->has_pass(pn))
-                       (*i)->render(pn);
+               if((*i)->has_pass(tag))
+                       (*i)->render(tag);
 }
 
 } // namespace GL
index f4e128105f75535d8398f06267924cfb50f8568e..6bfad812e517ecc45216216ed2aa0a37c50e3789 100644 (file)
@@ -23,9 +23,8 @@ public:
        void add(const Renderable &);
        void remove(const Renderable &);
 
-       virtual bool has_pass(const std::string &) const { return true; }
-       virtual void render() const;
-       virtual void render(const std::string &) const;
+       virtual bool has_pass(const Tag &) const { return true; }
+       virtual void render(const Tag &tag=Tag()) const;
 };
 
 } // namespace GL
diff --git a/source/tag.cpp b/source/tag.cpp
new file mode 100644 (file)
index 0000000..c8041e0
--- /dev/null
@@ -0,0 +1,21 @@
+#include "tag.h"
+
+namespace Msp {
+namespace GL {
+
+Tag::Tag(const char *s):
+       id(0)
+{
+       for(const char *i=s; *i; ++i)
+               id=id*id+*i;
+}
+
+Tag::Tag(const std::string &s):
+       id(0)
+{
+       for(std::string::const_iterator i=s.begin(); i!=s.end(); ++i)
+               id=id*id+*i;
+}
+
+} // namespace GL
+} // namespace Msp
diff --git a/source/tag.h b/source/tag.h
new file mode 100644 (file)
index 0000000..87d4af6
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef MSP_GL_TAG_H_
+#define MSP_GL_TAG_H_
+
+#include <string>
+
+namespace Msp {
+namespace GL {
+
+struct Tag
+{
+       unsigned id;
+
+       Tag(): id(0) { }
+       Tag(const char *);
+       Tag(const std::string &s);
+};
+
+} // namespace GL
+} // namespace Msp
+
+#endif