]> git.tdb.fi Git - libs/gl.git/blob - source/builders/sequencetemplate.h
bf1e8be185e086efc6b3597139f827630e672536
[libs/gl.git] / source / builders / sequencetemplate.h
1 #ifndef SEQUENCETEMPLATE_H_
2 #define SEQUENCETEMPLATE_H_
3
4 #include <string>
5 #include <vector>
6 #include <msp/core/typeregistry.h>
7 #include <msp/datafile/objectloader.h>
8 #include "blend.h"
9 #include "depthtest.h"
10 #include "postprocessor.h"
11 #include "resources.h"
12 #include "stenciltest.h"
13
14 namespace Msp {
15 namespace GL {
16
17 class Lighting;
18 class Renderable;
19
20 class SequenceTemplate
21 {
22 private:
23         class PostProcLoader: virtual public DataFile::Loader
24         {
25         private:
26                 template<typename T>
27                 struct AddPostProc
28                 {
29                         void operator()(const std::string &kw, PostProcLoader &ldr) const { ldr.add(kw, &PostProcLoader::postprocessor<T>); }
30                 };
31
32         protected:
33                 RefPtr<PostProcessor::Template> postproc;
34
35         public:
36                 PostProcLoader();
37
38                 PostProcessor::Template *get_postprocessor_template() { return postproc.release(); }
39
40         protected:
41                 virtual void postprocessor_loaded() { }
42
43         private:
44                 template<typename T>
45                 void postprocessor();
46
47                 friend class SequenceTemplate;
48         };
49
50 public:
51         class Loader: public DataFile::CollectionObjectLoader<SequenceTemplate, Resources>, public PostProcLoader
52         {
53         public:
54                 Loader(SequenceTemplate &, Collection &);
55
56                 virtual void postprocessor_loaded();
57                 void clear();
58                 void multisample(unsigned);
59                 void multisample_range(unsigned, unsigned);
60                 void postprocessor(const std::string &);
61                 void step(const std::string &);
62                 void step_with_slot(const std::string &, const std::string &);
63         };
64
65         struct Step
66         {
67                 class Loader: public DataFile::CollectionObjectLoader<Step>
68                 {
69                 private:
70                         std::string inline_base_name;
71
72                 public:
73                         Loader(Step &s): Loader(s, 0) { }
74                         Loader(Step &s, Collection &c): Loader(s, &c) { }
75                 private:
76                         Loader(Step &, Collection *);
77                         void init();
78
79                 public:
80                         void set_inline_base_name(const std::string &);
81
82                 private:
83                         void blend();
84                         void blend_factors(BlendFactor, BlendFactor);
85                         void depth_test();
86                         void depth_compare(Predicate);
87                         void lighting(const std::string &);
88                         void lighting_inline();
89                         void object(const std::string &);
90                         void scene(const std::string &);
91                         void stencil_test();
92                 };
93
94                 std::string tag;
95                 const Lighting *lighting;
96                 DepthTest depth_test;
97                 StencilTest stencil_test;
98                 Blend blend;
99                 std::string slot_name;
100                 Renderable *default_renderable;
101
102                 ~Step();
103         };
104
105         struct PostProcessor
106         {
107                 GL::PostProcessor::Template *postprocessor_template;
108                 std::string slot_name;
109
110                 PostProcessor(GL::PostProcessor::Template * = 0);
111         };
112
113 private:
114         class ClearLoader: public DataFile::ObjectLoader<SequenceTemplate>
115         {
116         public:
117                 ClearLoader(SequenceTemplate &);
118
119         private:
120                 void color(float, float, float, float);
121                 void depth(float);
122                 void stencil(int);
123         };
124
125         typedef TypeRegistry<PostProcLoader::AddPostProc, PostProcLoader &> PostProcessorRegistry;
126
127         bool hdr;
128         bool alpha;
129         unsigned required_multisample;
130         unsigned max_multisample;
131         std::vector<Step> steps;
132         std::vector<PostProcessor> postprocessors;
133         bool clear_enabled;
134         std::vector<Color> clear_colors;
135         float clear_depth;
136         int clear_stencil;
137
138 public:
139         SequenceTemplate();
140         ~SequenceTemplate();
141
142         bool get_hdr() const { return hdr; }
143         bool get_alpha() const { return alpha; }
144         unsigned get_required_multisample() const { return required_multisample; }
145         unsigned get_maximum_multisample() const { return max_multisample; }
146         const std::vector<Step> &get_steps() const { return steps; }
147         const std::vector<PostProcessor> &get_postprocessors() const { return postprocessors; }
148         bool is_clear_enabled() const { return clear_enabled; }
149         const std::vector<Color> &get_clear_colors() const { return clear_colors; }
150         float get_clear_depth() const { return clear_depth; }
151         int get_clear_stencil() const { return clear_stencil; }
152
153         template<typename T>
154         static void register_postprocessor(const std::string &);
155 private:
156         static PostProcessorRegistry &get_postprocessor_registry();
157 };
158
159 template<typename T>
160 void SequenceTemplate::register_postprocessor(const std::string &kw)
161 {
162         get_postprocessor_registry().register_type<T>(kw);
163 }
164
165 template<typename T>
166 void SequenceTemplate::PostProcLoader::postprocessor()
167 {
168         if(postproc)
169                 throw std::logic_error("Only one postprocessor allowed per slot");
170         RefPtr<typename T::Template> pp = new typename T::Template;
171         load_sub(*pp);
172         postproc = pp;
173         pp = 0;
174         postprocessor_loaded();
175 }
176
177 } // namespace GL
178 } // namespace Msp
179
180 #endif