]> git.sesse.net Git - movit/blob - effect_chain.h
Typo fix.
[movit] / effect_chain.h
1 #ifndef _EFFECT_CHAIN_H
2 #define _EFFECT_CHAIN_H 1
3
4 #include <set>
5 #include <vector>
6
7 #include "effect.h"
8 #include "effect_id.h"
9 #include "image_format.h"
10 #include "input.h"
11
12 class EffectChain {
13 public:
14         EffectChain(unsigned width, unsigned height);
15
16         // User API:
17         // input, effects, output, finalize need to come in that specific order.
18
19         Input *add_input(const ImageFormat &format);
20
21         // The returned pointer is owned by EffectChain.
22         Effect *add_effect(EffectId effect) {
23                 return add_effect(effect, last_added_effect());
24         }
25         Effect *add_effect(EffectId effect, Effect *input) {
26                 std::vector<Effect *> inputs;
27                 inputs.push_back(input);
28                 return add_effect(effect, inputs);
29         }
30         Effect *add_effect(EffectId effect, Effect *input1, Effect *input2) {
31                 std::vector<Effect *> inputs;
32                 inputs.push_back(input1);
33                 inputs.push_back(input2);
34                 return add_effect(effect, inputs);
35         }
36         Effect *add_effect(EffectId effect, const std::vector<Effect *> &inputs);
37
38         // Similar to add_effect, but:
39         //
40         //  * Does not insert any normalizing effects.
41         //  * Does not ask the effect to insert itself, so it won't work
42         //    with meta-effects.
43         //
44         // We should really separate out these two “sides” of Effect in the
45         // type system soon.
46         void add_effect_raw(Effect *effect, const std::vector<Effect *> &inputs);
47
48         void add_output(const ImageFormat &format);
49         void finalize();
50
51         //void render(unsigned char *src, unsigned char *dst);
52         void render_to_screen();
53
54         Effect *last_added_effect() {
55                 if (effects.empty()) {
56                         return NULL;
57                 } else {
58                         return effects.back();
59                 }       
60         }
61
62 private:
63         struct Phase {
64                 GLint glsl_program_num;
65                 bool input_needs_mipmaps;
66                 std::vector<Effect *> inputs;
67                 std::vector<Effect *> effects;  // In order.
68         };
69
70         Effect *normalize_to_linear_gamma(Effect *input);
71         Effect *normalize_to_srgb(Effect *input);
72
73         void draw_vertex(float x, float y, const std::vector<Effect *> &inputs);
74
75         // Create a GLSL program computing the given effects in order.
76         Phase compile_glsl_program(const std::vector<Effect *> &inputs, const std::vector<Effect *> &effects);
77
78         // Create all GLSL programs needed to compute the given effect, and all outputs
79         // that depends on it (whenever possible).
80         void construct_glsl_programs(Effect *start, std::set<Effect *> *completed_effects);
81
82         unsigned width, height;
83         ImageFormat input_format, output_format;
84         std::vector<Effect *> effects, unexpanded_effects;
85         std::map<Effect *, std::string> effect_ids;
86         std::map<Effect *, GLuint> effect_output_textures;
87         std::map<Effect *, std::vector<Effect *> > outgoing_links;
88         std::map<Effect *, std::vector<Effect *> > incoming_links;
89
90         GLuint fbo;
91         std::vector<Phase> phases;
92
93         GLenum format, bytes_per_pixel;
94         bool finalized;
95
96         // Used during the building of the effect chain.
97         std::map<Effect *, ColorSpace> output_color_space;
98         std::map<Effect *, GammaCurve> output_gamma_curve;      
99 };
100
101
102 #endif // !defined(_EFFECT_CHAIN_H)