]> git.tdb.fi Git - libs/gl.git/blobdiff - source/builders/sequencetemplate.cpp
Support effects and subordinate sequences inside sequence templates
[libs/gl.git] / source / builders / sequencetemplate.cpp
index 83c4b7671f75234b42125b30509dff9e1bde2371..999d2ae7693baaeea5e0c37229dd54d5b84f5a75 100644 (file)
@@ -1,52 +1,61 @@
 #include <msp/core/maputils.h>
 #include <msp/datafile/collection.h>
+#include <msp/strings/format.h>
 #include "ambientocclusion.h"
 #include "blend.h"
 #include "bloom.h"
 #include "colorcurve.h"
+#include "environmentmap.h"
 #include "lighting.h"
 #include "object.h"
 #include "resources.h"
 #include "scene.h"
 #include "sequencetemplate.h"
+#include "shadowmap.h"
+#include "sky.h"
 
 using namespace std;
 
 namespace Msp {
 namespace GL {
 
-SequenceTemplate::SequenceTemplate():
-       hdr(false),
-       alpha(false),
-       required_multisample(0),
-       max_multisample(0),
-       clear_enabled(false)
-{ }
-
 SequenceTemplate::~SequenceTemplate()
 {
+       for(const Renderable &r: renderables)
+               delete r.effect_template;
        for(const PostProcessor &p: postprocessors)
                delete p.postprocessor_template;
 }
 
-
-SequenceTemplate::PostProcessorRegistry &SequenceTemplate::get_postprocessor_registry()
+template<>
+SequenceTemplate::TemplateRegistry<GL::PostProcessor> &SequenceTemplate::get_registry<GL::PostProcessor>()
 {
-       static PostProcessorRegistry registry;
+       static TemplateRegistry<GL::PostProcessor> registry;
        static bool initialized = false;
        if(!initialized)
        {
-               registry.register_type<AmbientOcclusion>("ambient_occlusion");
-               registry.register_type<Bloom>("bloom");
-               registry.register_type<ColorCurve>("colorcurve");
+               registry.register_type<AmbientOcclusion::Template>("ambient_occlusion");
+               registry.register_type<Bloom::Template>("bloom");
+               registry.register_type<ColorCurve::Template>("colorcurve");
                initialized = true;
        }
        return registry;
 }
 
-
-SequenceTemplate::Step::~Step()
-{ }
+template<>
+SequenceTemplate::TemplateRegistry<Effect> &SequenceTemplate::get_registry<Effect>()
+{
+       static TemplateRegistry<Effect> registry;
+       static bool initialized = false;
+       if(!initialized)
+       {
+               registry.register_type<EnvironmentMap::Template>("environment_map");
+               registry.register_type<ShadowMap::Template>("shadow_map");
+               registry.register_type<Sky::Template>("sky");
+               initialized = true;
+       }
+       return registry;
+}
 
 
 SequenceTemplate::PostProcessor::PostProcessor(GL::PostProcessor::Template *ppt):
@@ -54,36 +63,45 @@ SequenceTemplate::PostProcessor::PostProcessor(GL::PostProcessor::Template *ppt)
 { }
 
 
-SequenceTemplate::PostProcLoader::PostProcLoader()
+DataFile::Loader::ActionMap SequenceTemplate::Loader::shared_actions;
+
+SequenceTemplate::Loader::Loader(SequenceTemplate &t, Collection &c):
+       CollectionObjectLoader<SequenceTemplate>(t, &c)
 {
-       get_postprocessor_registry().invoke_all(*this);
+       set_actions(shared_actions);
 }
 
-
-SequenceTemplate::Loader::Loader(SequenceTemplate &t, Collection &c):
-       DataFile::CollectionObjectLoader<SequenceTemplate, Resources>(t, &c)
+void SequenceTemplate::Loader::init_actions()
 {
        add("hdr", &SequenceTemplate::hdr);
        add("alpha", &SequenceTemplate::alpha);
        add("clear", &Loader::clear);
+       add("effect", &Loader::effect);
        add("multisample", &Loader::multisample);
        add("multisample", &Loader::multisample_range);
        add("postprocessor", &Loader::postprocessor);
+       add("postprocessor", &Loader::postprocessor_with_slot);
+       add("renderable", &Loader::renderable);
+       add("renderable", &Loader::renderable_with_default);
+       add("sequence", &Loader::sequence);
        add("step", &Loader::step);
-       add("step", &Loader::step_with_slot);
-
-       // Deprecated
-       add("pass", &Loader::step_with_slot);
 }
 
-void SequenceTemplate::Loader::postprocessor_loaded()
+void SequenceTemplate::Loader::clear()
 {
-       obj.postprocessors.push_back(get_postprocessor_template());
+       ClearLoader ldr(obj);
+       load_sub_with(ldr);
+       obj.clear_enabled = true;
 }
 
-void SequenceTemplate::Loader::clear()
+void SequenceTemplate::Loader::effect(const string &slot)
 {
-       obj.clear_enabled = true;
+       TemplateLoader<Effect> ldr(get_collection());
+       load_sub_with(ldr);
+       Renderable rend;
+       rend.slot_name = slot;
+       rend.effect_template = ldr.get_object();
+       obj.renderables.push_back(rend);
 }
 
 void SequenceTemplate::Loader::multisample(unsigned samples)
@@ -98,61 +116,123 @@ void SequenceTemplate::Loader::multisample_range(unsigned req, unsigned max)
        obj.max_multisample = max;
 }
 
-void SequenceTemplate::Loader::postprocessor(const string &slot)
+void SequenceTemplate::Loader::postprocessor()
 {
-       PostProcLoader ldr;
+       postprocessor_with_slot(string());
+}
+
+void SequenceTemplate::Loader::postprocessor_with_slot(const string &slot)
+{
+       TemplateLoader<GL::PostProcessor> ldr(get_collection());
        load_sub_with(ldr);
        PostProcessor pp;
-       pp.postprocessor_template = ldr.get_postprocessor_template();
+       pp.postprocessor_template = ldr.get_object();
        pp.slot_name = slot;
        obj.postprocessors.push_back(pp);
 }
 
-void SequenceTemplate::Loader::step(const string &tag)
+void SequenceTemplate::Loader::renderable(const string &slot)
 {
-       step_with_slot(tag, string());
+       Renderable rend;
+       rend.slot_name = slot;
+       obj.renderables.push_back(rend);
 }
 
-void SequenceTemplate::Loader::step_with_slot(const string &tag, const string &rend)
+void SequenceTemplate::Loader::renderable_with_default(const string &slot, const string &name)
+{
+       Renderable rend;
+       rend.renderable = &get_collection().get<GL::Renderable>(name);
+       rend.slot_name = slot;
+       obj.renderables.push_back(rend);
+}
+
+void SequenceTemplate::Loader::sequence(const string &slot, const string &name)
+{
+       Renderable rend;
+       rend.sequence_template = &get_collection().get<SequenceTemplate>(name);
+       rend.slot_name = slot;
+       SequenceLoader ldr(rend);
+       load_sub_with(ldr);
+       obj.renderables.push_back(rend);
+}
+
+void SequenceTemplate::Loader::step(const string &tag, const string &rend)
 {
        Step stp;
        stp.tag = tag;
-       stp.slot_name = rend;
-       if(coll)
-       {
-               Step::Loader ldr(stp, *coll);
-               ldr.set_inline_base_name(format("%s/%d.step", get_source(), obj.steps.size()));
-               load_sub_with(ldr);
-       }
-       else
-               load_sub(stp);
+       stp.renderable_name = rend;
+       Step::Loader ldr(stp, get_collection());
+       ldr.set_inline_base_name(format("%s/%d.step", get_source(), obj.steps.size()));
+       load_sub_with(ldr);
 
        obj.steps.push_back(stp);
 }
 
 
-SequenceTemplate::Step::Loader::Loader(Step &p):
-       DataFile::CollectionObjectLoader<Step>(p, 0)
+DataFile::Loader::ActionMap SequenceTemplate::ClearLoader::shared_actions;
+
+SequenceTemplate::ClearLoader::ClearLoader(SequenceTemplate &t):
+       ObjectLoader<SequenceTemplate>(t)
 {
-       init();
+       set_actions(shared_actions);
 }
 
+void SequenceTemplate::ClearLoader::init_actions()
+{
+       add("color", &ClearLoader::color);
+       add("depth", &ClearLoader::depth);
+       add("stencil", &ClearLoader::stencil);
+}
+
+void SequenceTemplate::ClearLoader::color(float r, float g, float b, float a)
+{
+       obj.clear_colors.push_back(Color(r, g, b, a));
+}
+
+void SequenceTemplate::ClearLoader::depth(float d)
+{
+       obj.clear_depth = d;
+}
+
+void SequenceTemplate::ClearLoader::stencil(int s)
+{
+       obj.clear_stencil = s;
+}
+
+
+DataFile::Loader::ActionMap SequenceTemplate::SequenceLoader::shared_actions;
+
+SequenceTemplate::SequenceLoader::SequenceLoader(Renderable &r):
+       ObjectLoader<Renderable>(r)
+{
+       set_actions(shared_actions);
+}
+
+void SequenceTemplate::SequenceLoader::init_actions()
+{
+       add("renderable", &SequenceLoader::renderable);
+}
+
+void SequenceTemplate::SequenceLoader::renderable(const string &slot, const string &name)
+{
+       obj.sequence_renderables[slot] = name;
+}
+
+
+DataFile::Loader::ActionMap SequenceTemplate::Step::Loader::shared_actions;
+
 SequenceTemplate::Step::Loader::Loader(Step &p, Collection &c):
        DataFile::CollectionObjectLoader<Step>(p, &c)
 {
-       init();
+       set_actions(shared_actions);
 }
 
-void SequenceTemplate::Step::Loader::init()
+void SequenceTemplate::Step::Loader::init_actions()
 {
-       add("blend", &Loader::blend);
-       add("blend", &Loader::blend_factors);
        add("depth_test", &Loader::depth_test);
        add("depth_test", &Loader::depth_compare);
        add("lighting", &Loader::lighting);
        add("lighting", &Loader::lighting_inline);
-       add("object", &Loader::object);
-       add("scene", &Loader::scene);
        add("stencil_test", &Loader::stencil_test);
 }
 
@@ -161,16 +241,6 @@ void SequenceTemplate::Step::Loader::set_inline_base_name(const string &n)
        inline_base_name = n;
 }
 
-void SequenceTemplate::Step::Loader::blend()
-{
-       load_sub(obj.blend);
-}
-
-void SequenceTemplate::Step::Loader::blend_factors(BlendFactor src, BlendFactor dest)
-{
-       obj.blend = Blend(src, dest);
-}
-
 void SequenceTemplate::Step::Loader::depth_test()
 {
        load_sub(obj.depth_test);
@@ -184,7 +254,7 @@ void SequenceTemplate::Step::Loader::depth_compare(Predicate c)
 void SequenceTemplate::Step::Loader::lighting_inline()
 {
        RefPtr<Lighting> lightn = new Lighting;
-       load_sub(*lightn);
+       load_sub(*lightn, get_collection());
        get_collection().add(inline_base_name+".lightn", lightn.get());
        obj.lighting = lightn.release();
 }
@@ -194,16 +264,6 @@ void SequenceTemplate::Step::Loader::lighting(const string &name)
        obj.lighting = &get_collection().get<Lighting>(name);
 }
 
-void SequenceTemplate::Step::Loader::object(const string &name)
-{
-       obj.default_renderable = &get_collection().get<GL::Object>(name);
-}
-
-void SequenceTemplate::Step::Loader::scene(const string &name)
-{
-       obj.default_renderable = &get_collection().get<Scene>(name);
-}
-
 void SequenceTemplate::Step::Loader::stencil_test()
 {
        load_sub(obj.stencil_test);