fix the spelling in whole piglit
[piglit.git] / tests / spec / nv_texture_env_combine4 / combine.c
blob9a5c03fc7fb7c3dd3081c67a1bcf7142f5df92d1
1 /*
2 * Copyright (C) 1999 Allen Akin All Rights Reserved.
4 * Permission is hereby granted, free of charge, to any person
5 * obtaining a copy of this software and associated documentation
6 * files (the "Software"), to deal in the Software without
7 * restriction, including without limitation the rights to use,
8 * copy, modify, merge, publish, distribute, sublicense, and/or
9 * sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following
11 * conditions:
13 * The above copyright notice and this permission notice shall be
14 * included in all copies or substantial portions of the
15 * Software.
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY
18 * KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
19 * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
20 * PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ALLEN AKIN BE
21 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
23 * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
24 * DEALINGS IN THE SOFTWARE.
28 /**
29 * @file combine.c: Test GL_NV_texture_env_combine4
30 * Author: Brian Paul (brianp@valinux.com) January 2009
32 * Generate some random combiner state and colors, compute the expected
33 * color, then render with the combiner state and compare the results.
34 * Only one texture unit is tested and not all possible combiner terms
35 * are exercised.
38 #include "piglit-util-gl.h"
40 PIGLIT_GL_TEST_CONFIG_BEGIN
42 config.supports_gl_compat_version = 13;
43 config.window_visual = PIGLIT_GL_VISUAL_RGB;
44 config.khr_no_error_support = PIGLIT_NO_ERRORS;
46 PIGLIT_GL_TEST_CONFIG_END
48 #ifdef _WIN32
49 #define SRAND(x) srand(x)
50 #define DRAND() ((float)rand() / RAND_MAX)
51 #else
52 #define SRAND(x) srand48(x)
53 #define DRAND() drand48()
54 #endif
56 #define NUM_TESTS 200
58 struct combine_state {
59 GLenum combine_mode;
60 GLenum source[4];
61 GLenum operand_rgb[4];
62 GLenum operand_a[4];
63 float primary_color[4];
64 float constant_color[4];
65 float texture_color[4];
68 /* generate random combiner state */
69 static void
70 generate_state(struct combine_state *state)
72 if (DRAND() > 0.5f)
73 state->combine_mode = GL_ADD;
74 else
75 state->combine_mode = GL_ADD_SIGNED_EXT;
77 for (int i = 0; i < 4; i++) {
78 int src = (int)(DRAND() * 4.0);
79 switch (src) {
80 case 0:
81 state->source[i] = GL_ZERO;
82 break;
83 case 1:
84 state->source[i] = GL_TEXTURE;
85 break;
86 case 2:
87 state->source[i] = GL_CONSTANT_EXT;
88 break;
89 default:
90 state->source[i] = GL_PRIMARY_COLOR_EXT;
91 break;
94 if (DRAND() > 0.5f) {
95 state->operand_rgb[i] = GL_SRC_COLOR;
96 state->operand_a[i] = GL_SRC_ALPHA;
97 } else {
98 state->operand_rgb[i] = GL_ONE_MINUS_SRC_COLOR;
99 state->operand_a[i] = GL_ONE_MINUS_SRC_ALPHA;
103 state->primary_color[0] = DRAND();
104 state->primary_color[1] = DRAND();
105 state->primary_color[2] = DRAND();
106 state->primary_color[3] = DRAND();
108 state->constant_color[0] = DRAND();
109 state->constant_color[1] = DRAND();
110 state->constant_color[2] = DRAND();
111 state->constant_color[3] = DRAND();
113 state->texture_color[0] = DRAND();
114 state->texture_color[1] = DRAND();
115 state->texture_color[2] = DRAND();
116 state->texture_color[3] = DRAND();
119 /* compute expected final color */
120 static void
121 evaluate_state(const struct combine_state state, float result[4])
123 float arg[4][4];
125 /* setup terms */
126 for (int i = 0; i < 4; i++) {
127 switch (state.source[i]) {
128 case GL_ZERO:
129 arg[i][0] = arg[i][1] = arg[i][2] = arg[i][3] = 0.0f;
130 break;
131 case GL_PRIMARY_COLOR_EXT:
132 arg[i][0] = state.primary_color[0];
133 arg[i][1] = state.primary_color[1];
134 arg[i][2] = state.primary_color[2];
135 arg[i][3] = state.primary_color[3];
136 break;
137 case GL_CONSTANT_EXT:
138 arg[i][0] = state.constant_color[0];
139 arg[i][1] = state.constant_color[1];
140 arg[i][2] = state.constant_color[2];
141 arg[i][3] = state.constant_color[3];
142 break;
143 case GL_TEXTURE:
144 arg[i][0] = state.texture_color[0];
145 arg[i][1] = state.texture_color[1];
146 arg[i][2] = state.texture_color[2];
147 arg[i][3] = state.texture_color[3];
148 break;
149 default:
150 assert(0);
153 switch (state.operand_rgb[i]) {
154 case GL_SRC_COLOR:
155 /* nop */
156 break;
157 case GL_ONE_MINUS_SRC_COLOR:
158 arg[i][0] = 1.0f - arg[i][0];
159 arg[i][1] = 1.0f - arg[i][1];
160 arg[i][2] = 1.0f - arg[i][2];
161 arg[i][3] = 1.0f - arg[i][3];
162 break;
163 default:
164 assert(0);
168 /* combine terms, loop over color channels */
169 for (int i = 0; i < 4; i++) {
170 result[i] = arg[0][i] * arg[1][i] + arg[2][i] * arg[3][i];
171 if (state.combine_mode == GL_ADD_SIGNED_EXT)
172 result[i] -= 0.5f;
173 if (result[i] < 0.0f)
174 result[i] = 0.0f;
175 else if (result[i] > 1.0f)
176 result[i] = 1.0f;
180 /* render quad with given combiner state and compare resulting color
181 * return false if GL error is detected or comparison fails, true otherwise.
183 static bool
184 render_state(const struct combine_state state, const float expected[4])
186 if (!piglit_check_gl_error(GL_NO_ERROR))
187 return false;
189 glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE4_NV);
191 glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, state.combine_mode);
192 glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, state.combine_mode);
194 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB, state.source[0]);
195 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, state.source[0]);
196 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB, state.source[1]);
197 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_ALPHA, state.source[1]);
198 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_RGB, state.source[2]);
199 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_ALPHA, state.source[2]);
200 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE3_RGB_NV, state.source[3]);
201 glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE3_ALPHA_NV, state.source[3]);
203 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB, state.operand_rgb[0]);
204 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, state.operand_a[0]);
205 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB, state.operand_rgb[1]);
206 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_ALPHA, state.operand_a[1]);
207 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_RGB, state.operand_rgb[2]);
208 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_ALPHA, state.operand_a[2]);
209 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND3_RGB_NV, state.operand_rgb[3]);
210 glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND3_ALPHA_NV, state.operand_a[3]);
212 glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR,
213 state.constant_color);
215 if (!piglit_check_gl_error(GL_NO_ERROR))
216 return false;
218 glEnable(GL_TEXTURE_2D);
219 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
220 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
222 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 1, 1, 0, GL_RGBA, GL_FLOAT,
223 state.texture_color);
225 glColor4fv(state.primary_color);
227 glClear(GL_COLOR_BUFFER_BIT);
228 piglit_draw_rect_tex(-1, -1, 2, 2, 0, 0, 1, 1);
230 return piglit_probe_pixel_rgb(piglit_width / 2, piglit_height / 2,
231 expected);
234 enum piglit_result
235 piglit_display(void)
237 for (int i = 0; i < NUM_TESTS; i++) {
238 struct combine_state state;
239 float expected[4];
241 generate_state(&state);
243 evaluate_state(state, expected);
245 if (!render_state(state, expected))
246 return PIGLIT_FAIL;
249 return PIGLIT_PASS;
252 void
253 piglit_init(int argc, char **argv)
255 piglit_require_extension("GL_NV_texture_env_combine4");
256 SRAND(42); /* init random number generator */