Fix an issue where a (cached) shader program could be used from multiple
[movit] / effect_util.cpp
1 #include <epoxy/gl.h>
2 #include <Eigen/Core>
3 #include <stddef.h>
4 #include <string>
5 #include "util.h"
6
7 using namespace std;
8
9 namespace movit {
10
11 GLint get_uniform_location(GLuint glsl_program_num, const string &prefix, const string &key)
12 {
13         string name = prefix + "_" + key;
14         return glGetUniformLocation(glsl_program_num, name.c_str());
15 }
16
17 void set_uniform_int(GLuint glsl_program_num, const string &prefix, const string &key, int value)
18 {
19         GLint location = get_uniform_location(glsl_program_num, prefix, key);
20         if (location == -1) {
21                 return;
22         }
23         check_error();
24         glUniform1i(location, value);
25         check_error();
26 }
27
28 void set_uniform_float(GLuint glsl_program_num, const string &prefix, const string &key, float value)
29 {
30         GLint location = get_uniform_location(glsl_program_num, prefix, key);
31         if (location == -1) {
32                 return;
33         }
34         check_error();
35         glUniform1f(location, value);
36         check_error();
37 }
38
39 void set_uniform_vec2(GLuint glsl_program_num, const string &prefix, const string &key, const float *values)
40 {
41         GLint location = get_uniform_location(glsl_program_num, prefix, key);
42         if (location == -1) {
43                 return;
44         }
45         check_error();
46         glUniform2fv(location, 1, values);
47         check_error();
48 }
49
50 void set_uniform_vec3(GLuint glsl_program_num, const string &prefix, const string &key, const float *values)
51 {
52         GLint location = get_uniform_location(glsl_program_num, prefix, key);
53         if (location == -1) {
54                 return;
55         }
56         check_error();
57         glUniform3fv(location, 1, values);
58         check_error();
59 }
60
61 void set_uniform_vec4(GLuint glsl_program_num, const string &prefix, const string &key, const float *values)
62 {
63         GLint location = get_uniform_location(glsl_program_num, prefix, key);
64         if (location == -1) {
65                 return;
66         }
67         check_error();
68         glUniform4fv(location, 1, values);
69         check_error();
70 }
71
72 void set_uniform_vec2_array(GLuint glsl_program_num, const string &prefix, const string &key, const float *values, size_t num_values)
73 {
74         GLint location = get_uniform_location(glsl_program_num, prefix, key);
75         if (location == -1) {
76                 return;
77         }
78         check_error();
79         glUniform2fv(location, num_values, values);
80         check_error();
81 }
82
83 void set_uniform_vec4_array(GLuint glsl_program_num, const string &prefix, const string &key, const float *values, size_t num_values)
84 {
85         GLint location = get_uniform_location(glsl_program_num, prefix, key);
86         if (location == -1) {
87                 return;
88         }
89         check_error();
90         glUniform4fv(location, num_values, values);
91         check_error();
92 }
93
94 void set_uniform_mat3(GLuint glsl_program_num, const string &prefix, const string &key, const Eigen::Matrix3d& matrix)
95 {
96         GLint location = get_uniform_location(glsl_program_num, prefix, key);
97         if (location == -1) {
98                 return;
99         }
100         check_error();
101
102         // Convert to float (GLSL has no double matrices).
103         float matrixf[9];
104         for (unsigned y = 0; y < 3; ++y) {
105                 for (unsigned x = 0; x < 3; ++x) {
106                         matrixf[y + x * 3] = matrix(y, x);
107                 }
108         }
109
110         glUniformMatrix3fv(location, 1, GL_FALSE, matrixf);
111         check_error();
112 }
113
114 }  // namespace movit