openMSX
gl_vec.cc
Go to the documentation of this file.
1 #include "catch.hpp"
2 #include "gl_vec.hh"
3 
4 using namespace gl;
5 
6 // Test approximations.
7 template<typename T>
8 bool approxEq(T x, T y)
9 {
10  return std::abs(x - y) < T(1.0e-5);
11 }
12 template<int N, typename T>
13 bool approxEq(const vecN<N, T>& x, const vecN<N, T>&y)
14 {
15  return length2(x - y) < T(1.0e-4);
16 }
17 
18 
19 TEST_CASE("gl_vec: rsqrt")
20 {
21  CHECK(rsqrt(16.0f) == 0.25f);
22  CHECK(rsqrt(16.0 ) == 0.25 );
23 }
24 
25 TEST_CASE("gl_vec: radians, degrees")
26 {
27  CHECK(approxEq(radians( 0.0), 0.0 ));
28  CHECK(approxEq(radians( 90.0), M_PI / 2));
29  CHECK(approxEq(radians(180.0), M_PI ));
30  CHECK(approxEq(degrees(0.0 ), 0.0));
31  CHECK(approxEq(degrees(M_PI / 2), 90.0));
32  CHECK(approxEq(degrees(M_PI ), 180.0));
33 }
34 
35 // It's useful to test both integer and float variants because the
36 // former are implemented in plain C++ and (only) the latter have SSE
37 // optimizations.
38 
39 TEST_CASE("gl_vec: constructors")
40 {
41  SECTION("default constructor") {
42  vec2 v2;
43  CHECK(v2[0] == 0);
44  CHECK(v2[1] == 0);
45  ivec2 i2;
46  CHECK(i2[0] == 0);
47  CHECK(i2[1] == 0);
48 
49  vec3 v3;
50  CHECK(v3[0] == 0);
51  CHECK(v3[1] == 0);
52  CHECK(v3[2] == 0);
53  ivec3 i3;
54  CHECK(i3[0] == 0);
55  CHECK(i3[1] == 0);
56  CHECK(i3[2] == 0);
57 
58  vec4 v4;
59  CHECK(v4[0] == 0);
60  CHECK(v4[1] == 0);
61  CHECK(v4[2] == 0);
62  CHECK(v4[3] == 0);
63  ivec4 i4;
64  CHECK(i4[0] == 0);
65  CHECK(i4[1] == 0);
66  CHECK(i4[2] == 0);
67  CHECK(i4[3] == 0);
68  }
69  SECTION("broadcast constructor") {
70  vec2 v2(2);
71  CHECK(v2[0] == 2);
72  CHECK(v2[1] == 2);
73  ivec2 i2(2);
74  CHECK(i2[0] == 2);
75  CHECK(i2[1] == 2);
76 
77  vec3 v3(3);
78  CHECK(v3[0] == 3);
79  CHECK(v3[1] == 3);
80  CHECK(v3[2] == 3);
81  ivec3 i3(3);
82  CHECK(i3[0] == 3);
83  CHECK(i3[1] == 3);
84  CHECK(i3[2] == 3);
85 
86  vec4 v4(4);
87  CHECK(v4[0] == 4);
88  CHECK(v4[1] == 4);
89  CHECK(v4[2] == 4);
90  CHECK(v4[3] == 4);
91  ivec4 i4(4);
92  CHECK(i4[0] == 4);
93  CHECK(i4[1] == 4);
94  CHECK(i4[2] == 4);
95  CHECK(i4[3] == 4);
96  }
97  SECTION("per-element constructor") {
98  vec2 v2(2, 3);
99  CHECK(v2[0] == 2);
100  CHECK(v2[1] == 3);
101  ivec2 i2(2, 3);
102  CHECK(i2[0] == 2);
103  CHECK(i2[1] == 3);
104 
105  vec3 v3(3, 4, 5);
106  CHECK(v3[0] == 3);
107  CHECK(v3[1] == 4);
108  CHECK(v3[2] == 5);
109  ivec3 i3(3, 4, 5);
110  CHECK(i3[0] == 3);
111  CHECK(i3[1] == 4);
112  CHECK(i3[2] == 5);
113 
114  vec4 v4(4, 5, 6, 7);
115  CHECK(v4[0] == 4);
116  CHECK(v4[1] == 5);
117  CHECK(v4[2] == 6);
118  CHECK(v4[3] == 7);
119  ivec4 i4(4, 5, 6, 7);
120  CHECK(i4[0] == 4);
121  CHECK(i4[1] == 5);
122  CHECK(i4[2] == 6);
123  CHECK(i4[3] == 7);
124  }
125  SECTION("construct from smaller vectors/scalar") {
126  vec3 v3(3, vec2(4, 5));
127  CHECK(v3[0] == 3);
128  CHECK(v3[1] == 4);
129  CHECK(v3[2] == 5);
130  ivec3 i3(ivec2(4, 5), 3);
131  CHECK(i3[0] == 4);
132  CHECK(i3[1] == 5);
133  CHECK(i3[2] == 3);
134 
135  vec4 v4(4, vec3(5, 6, 7));
136  CHECK(v4[0] == 4);
137  CHECK(v4[1] == 5);
138  CHECK(v4[2] == 6);
139  CHECK(v4[3] == 7);
140  ivec4 i4(ivec3(5, 6, 7), 4);
141  CHECK(i4[0] == 5);
142  CHECK(i4[1] == 6);
143  CHECK(i4[2] == 7);
144  CHECK(i4[3] == 4);
145 
146  vec4 w4(vec2(5, 6), vec2(7, 8));
147  CHECK(w4[0] == 5);
148  CHECK(w4[1] == 6);
149  CHECK(w4[2] == 7);
150  CHECK(w4[3] == 8);
151  ivec4 j4(ivec2(5, 6), ivec2(7, 8));
152  CHECK(j4[0] == 5);
153  CHECK(j4[1] == 6);
154  CHECK(j4[2] == 7);
155  CHECK(j4[3] == 8);
156 
157  #if 0
158  // Not implemeneted yet (also not yet needed).
159  vec4 x4(1, vec2(3, 5), 7);
160  CHECK(x4[0] == 1);
161  CHECK(x4[1] == 3);
162  CHECK(x4[2] == 5);
163  CHECK(x4[3] == 7);
164  ivec4 k4(2, ivec2(4, 6), 8);
165  CHECK(k4[0] == 2);
166  CHECK(k4[1] == 4);
167  CHECK(k4[2] == 6);
168  CHECK(k4[3] == 8);
169  #endif
170 
171  #if 0
172  // Ok, compile error:
173  // static assertion failed: wrong vector length in constructor
174  ivec3 wrong1(3, ivec3(4, 5, 6));
175  ivec4 wrong2(3, ivec2(4, 5));
176  ivec4 wrong3(ivec2(4, 5), ivec3(8, 9));
177  #endif
178  }
179 }
180 
181 TEST_CASE("gl_vec: modify elements")
182 {
183  vec2 v2;
184  v2[0] = 5;
185  CHECK(v2[0] == 5);
186  CHECK(v2[1] == 0);
187  v2[1] = 7;
188  CHECK(v2[0] == 5);
189  CHECK(v2[1] == 7);
190  ivec2 i2;
191  i2[0] = 5;
192  CHECK(i2[0] == 5);
193  CHECK(i2[1] == 0);
194  i2[1] = 7;
195  CHECK(i2[0] == 5);
196  CHECK(i2[1] == 7);
197 
198  vec3 v3(1);
199  v3[1] = 2;
200  CHECK(v3[0] == 1);
201  CHECK(v3[1] == 2);
202  CHECK(v3[2] == 1);
203  ivec3 i3(1);
204  i3[1] = 2;
205  CHECK(i3[0] == 1);
206  CHECK(i3[1] == 2);
207  CHECK(i3[2] == 1);
208 
209  vec4 v4(1, 2, 3, 4);
210  v4[0] = 9; v4[2] = 8;
211  CHECK(v4[0] == 9);
212  CHECK(v4[1] == 2);
213  CHECK(v4[2] == 8);
214  CHECK(v4[3] == 4);
215  ivec4 i4(1, 2, 3, 4);
216  i4[0] = 9; i4[2] = 8;
217  CHECK(i4[0] == 9);
218  CHECK(i4[1] == 2);
219  CHECK(i4[2] == 8);
220  CHECK(i4[3] == 4);
221 }
222 
223 TEST_CASE("gl_vec: (in)equality")
224 {
225  CHECK( vec2(1, 2) == vec2(1, 2));
226  CHECK( vec2(1, 2) != vec2(1, 4));
227  CHECK( vec2(1, 2) != vec2(3, 2));
228  CHECK( vec2(1, 2) != vec2(3, 4));
229  CHECK(ivec2(1, 2) == ivec2(1, 2));
230  CHECK(ivec2(1, 2) != ivec2(1, 4));
231  CHECK(ivec2(1, 2) != ivec2(3, 2));
232  CHECK(ivec2(1, 2) != ivec2(3, 4));
233 
234  CHECK( vec3(1, 2, 3) == vec3(1, 2, 3));
235  CHECK( vec3(1, 2, 3) != vec3(1, 2, 4));
236  CHECK(ivec3(1, 2, 3) == ivec3(1, 2, 3));
237  CHECK(ivec3(1, 2, 3) != ivec3(1, 2, 4));
238 
239  CHECK( vec4(1, 2, 3, 4) == vec4(1, 2, 3, 4));
240  CHECK( vec4(1, 2, 3, 4) != vec4(1, 2, 4, 4));
241  CHECK(ivec4(1, 2, 3, 4) == ivec4(1, 2, 3, 4));
242  CHECK(ivec4(1, 2, 3, 4) != ivec4(1, 2, 4, 4));
243 }
244 
245 TEST_CASE("gl_vec: copy constructor, assignment")
246 {
247  vec2 v2(2, 3);
248  vec2 w2(v2);
249  CHECK(v2 == w2);
250  v2[0] = 9; w2 = v2;
251  CHECK(v2 == w2);
252 
253  ivec2 i2(2, 3);
254  ivec2 j2(i2);
255  CHECK(i2 == j2);
256  i2[1] = 9; j2 = i2;
257  CHECK(i2 == j2);
258 
259  vec3 v3(3, 4, 5);
260  vec3 w3(v3);
261  CHECK(v3 == w3);
262  v3[2] = 8; w3 = v3;
263  CHECK(v3 == w3);
264 
265  ivec3 i3(3, 4, 5);
266  ivec3 j3(i3);
267  CHECK(i3 == j3);
268  i3[1] = 8; j3 = i3;
269  CHECK(i3 == j3);
270 
271  vec4 v4(4, 5, 6, 7);
272  vec4 w4(v4);
273  CHECK(v4 == w4);
274  v3[3] = 0; w4 = v4;
275  CHECK(v4 == w4);
276 
277  ivec4 i4(4, 5, 6, 7);
278  ivec4 j4(i4);
279  CHECK(i4 == j4);
280  i3[0] = 1; j4 = i4;
281  CHECK(i4 == j4);
282 }
283 
284 TEST_CASE("gl_vec: construct from larger vector")
285 {
286  vec4 v4(1, 2, 3, 4);
287  vec3 v3(7, 8, 9);
288  CHECK(vec3(v4) == vec3(1, 2, 3));
289  CHECK(vec2(v4) == vec2(1, 2));
290  CHECK(vec2(v3) == vec2(7, 8));
291 
292  ivec4 i4(1, 2, 3, 4);
293  ivec3 i3(7, 8, 9);
294  CHECK(ivec3(i4) == ivec3(1, 2, 3));
295  CHECK(ivec2(i4) == ivec2(1, 2));
296  CHECK(ivec2(i3) == ivec2(7, 8));
297 }
298 
299 // From here on I'll skip tests on vec2 and ivec2.
300 // Vectors of dimension 2 and 3 are handled by the same C++ code, so
301 // if there's a bug it should show up in both types.
302 
303 TEST_CASE("gl_vec: vector add")
304 {
305  vec3 v3(1, 2, 3); vec4 v4(1, 2, 3, 4);
306  ivec3 i3(1, 2, 3); ivec4 i4(1, 2, 3, 4);
307  CHECK((v3 + vec3(4, 5, 6)) == vec3(5, 7, 9));
308  CHECK((i3 + ivec3(4, 5, 6)) == ivec3(5, 7, 9));
309  CHECK((v4 + vec4(4, 5, 6, 7)) == vec4(5, 7, 9, 11));
310  CHECK((i4 + ivec4(4, 5, 6, 7)) == ivec4(5, 7, 9, 11));
311 
312  v3 += vec3(2, 3, 4);
313  i3 += ivec3(2, 3, 4);
314  v4 += vec4(2, 3, 4, 5);
315  i4 += ivec4(2, 3, 4, 5);
316  CHECK(v3 == vec3(3, 5, 7));
317  CHECK(i3 == ivec3(3, 5, 7));
318  CHECK(v4 == vec4(3, 5, 7, 9));
319  CHECK(i4 == ivec4(3, 5, 7, 9));
320 }
321 
322 TEST_CASE("gl_vec: vector subtract")
323 {
324  vec3 v3(1, 2, 3); vec4 v4(1, 2, 3, 4);
325  ivec3 i3(1, 2, 3); ivec4 i4(1, 2, 3, 4);
326  CHECK((v3 - vec3(4, 3, 2)) == vec3(-3, -1, 1));
327  CHECK((i3 - ivec3(4, 3, 2)) == ivec3(-3, -1, 1));
328  CHECK((v4 - vec4(4, 3, 2, 1)) == vec4(-3, -1, 1, 3));
329  CHECK((i4 - ivec4(4, 3, 2, 1)) == ivec4(-3, -1, 1, 3));
330 
331  v3 -= vec3(2, 4, 6);
332  i3 -= ivec3(2, 4, 6);
333  v4 -= vec4(2, 4, 6, 8);
334  i4 -= ivec4(2, 4, 6, 8);
335  CHECK(v3 == vec3(-1, -2, -3));
336  CHECK(i3 == ivec3(-1, -2, -3));
337  CHECK(v4 == vec4(-1, -2, -3, -4));
338  CHECK(i4 == ivec4(-1, -2, -3, -4));
339 }
340 
341 TEST_CASE("gl_vec: vector negate")
342 {
343  CHECK((- vec3(4, -3, 2)) == vec3(-4, 3, -2));
344  CHECK((-ivec3(4, -3, 2)) == ivec3(-4, 3, -2));
345  CHECK((- vec4(4, -3, 2, -1)) == vec4(-4, 3, -2, 1));
346  CHECK((-ivec4(4, -3, 2, -1)) == ivec4(-4, 3, -2, 1));
347 }
348 
349 TEST_CASE("gl_vec: component-wise vector multiplication")
350 {
351  vec3 v3(0, 2, -3); vec4 v4(0, 2, -3, 4);
352  ivec3 i3(0, 2, -3); ivec4 i4(0, 2, -3, 4);
353  // scalar * vector
354  CHECK((2.0f * v3) == vec3(0, 4, -6));
355  CHECK((2 * i3) == ivec3(0, 4, -6));
356  CHECK((2.0f * v4) == vec4(0, 4, -6, 8));
357  CHECK((2 * i4) == ivec4(0, 4, -6, 8));
358  // vector * scalar
359  CHECK((v3 * 2.0f) == vec3(0, 4, -6));
360  CHECK((i3 * 2 ) == ivec3(0, 4, -6));
361  CHECK((v4 * 2.0f) == vec4(0, 4, -6, 8));
362  CHECK((i4 * 2 ) == ivec4(0, 4, -6, 8));
363  // vector * vector
364  vec3 w3(-1, 2, -3); vec4 w4(-1, 2, -3, -4);
365  ivec3 j3(-1, 2, -3); ivec4 j4(-1, 2, -3, -4);
366  CHECK((v3 * w3) == vec3(0, 4, 9));
367  CHECK((i3 * j3) == ivec3(0, 4, 9));
368  CHECK((v4 * w4) == vec4(0, 4, 9, -16));
369  CHECK((i4 * j4) == ivec4(0, 4, 9, -16));
370  // *= scalar
371  v3 *= 2.0f; CHECK(v3 == vec3(0, 4, -6));
372  i3 *= 2; CHECK(i3 == ivec3(0, 4, -6));
373  v4 *= 2.0f; CHECK(v4 == vec4(0, 4, -6, 8));
374  i4 *= 2; CHECK(i4 == ivec4(0, 4, -6, 8));
375  // *= vector
376  v3 *= w3; CHECK(v3 == vec3(0, 8, 18));
377  i3 *= j3; CHECK(i3 == ivec3(0, 8, 18));
378  v4 *= w4; CHECK(v4 == vec4(0, 8, 18, -32));
379  i4 *= j4; CHECK(i4 == ivec4(0, 8, 18, -32));
380 }
381 
382 TEST_CASE("gl_vec: reciprocal (only floating point)")
383 {
384  CHECK(approxEq(recip(vec3(4, 2, 0.5)), vec3(0.25, 0.5, 2)));
385  CHECK(approxEq(recip(vec4(4, 2, 0.5, 1)), vec4(0.25, 0.5, 2, 1)));
386 }
387 
388 TEST_CASE("gl_vec: component-wise division (only floating point)")
389 {
390  vec3 v3( 0, 1, -4);
391  vec3 w3(-1, -2, 2);
392  CHECK((v3 / 2.0f) == vec3( 0, 0.5f, -2));
393  CHECK((6.0f / w3) == vec3(-6, -3, 3));
394  CHECK((v3 / w3) == vec3( 0, -0.5f, -2));
395 
396  vec4 v4( 2, 1, -4, -3);
397  vec4 w4(-1, 2, 2, -6);
398  CHECK(approxEq((v4 / -2.0f), vec4(-1, -0.5f, 2, 1.5f)));
399  CHECK(approxEq((6.0f / w4), vec4(-6, 3, 3, -1)));
400  CHECK(approxEq((v4 / w4), vec4(-2, 0.5f, -2, 0.5f)));
401 }
402 
403 TEST_CASE("gl_vec: component-wise min/max")
404 {
405  CHECK(min( vec3(2, 3, 4), vec3(1, -5, 7)) == vec3(1, -5, 4));
406  CHECK(min(ivec3(2, 3, 4), ivec3(1, -5, 7)) == ivec3(1, -5, 4));
407  CHECK(min( vec4(1, -2, 5, -7), vec4(0, 2, -4, -3)) == vec4(0, -2, -4, -7));
408  CHECK(min(ivec4(1, -2, 5, -7), ivec4(0, 2, -4, -3)) == ivec4(0, -2, -4, -7));
409 
410  CHECK(max( vec3(2, 3, 4), vec3(1, -5, 7)) == vec3(2, 3, 7));
411  CHECK(max(ivec3(2, 3, 4), ivec3(1, -5, 7)) == ivec3(2, 3, 7));
412  CHECK(max( vec4(1, -2, 5, -7), vec4(0, 2, -4, -3)) == vec4(1, 2, 5, -3));
413  CHECK(max(ivec4(1, -2, 5, -7), ivec4(0, 2, -4, -3)) == ivec4(1, 2, 5, -3));
414 }
415 
416 TEST_CASE("gl_vec: minimum component within a vector")
417 {
418  CHECK(min_component( vec3(1, 5, -7.2f)) == -7.2f);
419  CHECK(min_component(ivec3(3, 2, 4)) == 2);
420  CHECK(min_component( vec4(-1, 2, 5.2f, 0)) == -1);
421  CHECK(min_component(ivec4(1, -2, 5, -7)) == -7);
422 }
423 
424 TEST_CASE("gl_vec: clamp") {
425  CHECK(clamp( vec3(2, 3, 4), vec3(0, 4, -4), vec3(4, 7, 0)) == vec3(2, 4, 0));
426  CHECK(clamp(ivec3(2, 3, 4), ivec3(0, 4, -4), ivec3(4, 7, 0)) == ivec3(2, 4, 0));
427  CHECK(clamp( vec4(4, 2, 7, 1), vec4(0, 3, 2, 1), vec4(4, 6, 8, 3)) == vec4(4, 3, 7, 1));
428  CHECK(clamp(ivec4(4, 2, 7, 1), ivec4(0, 3, 2, 1), ivec4(4, 6, 8, 3)) == ivec4(4, 3, 7, 1));
429 
430  CHECK(clamp( vec3(2, 3, 4), 1.0f, 3.0f) == vec3(2, 3, 3));
431  CHECK(clamp(ivec3(2, 3, 4), 1, 3 ) == ivec3(2, 3, 3));
432  CHECK(clamp( vec4(4, 2, 7, 1), 2.0f, 6.0f) == vec4(4, 2, 6, 2));
433  CHECK(clamp(ivec4(4, 2, 7, 1), 2, 6 ) == ivec4(4, 2, 6, 2));
434 }
435 
436 TEST_CASE("gl_vec: sum of vector components")
437 {
438  CHECK(sum( vec3(4, -3, 2)) == 3.0f);
439  CHECK(sum(ivec3(4, -3, 2)) == 3 );
440  CHECK(sum( vec4(4, -3, 2, -1)) == 2.0f);
441  CHECK(sum(ivec4(4, -3, 2, -1)) == 2 );
442 
443  CHECK(sum_broadcast(vec3(4, -3, 2)) == vec3(3.0f));
444  CHECK(sum_broadcast(vec4(4, -3, 2, -1)) == vec4(2.0f));
445 }
446 
447 TEST_CASE("gl_vec: dot product")
448 {
449  CHECK(dot( vec3(4, -3, 2), vec3(-1, 3, 2) ) == -9.0f);
450  CHECK(dot(ivec3(4, -3, 2), ivec3(-1, 3, 2) ) == -9 );
451  CHECK(dot( vec4(4, -3, 2, -1), vec4(-1, 3, 2, -2)) == -7.0f);
452  CHECK(dot(ivec4(4, -3, 2, -1), ivec4(-1, 3, 2, -2)) == -7 );
453 
454  CHECK(dot_broadcast(vec3(4, -3, 2), vec3(-1, 3, 2) ) == vec3(-9.0f));
455  CHECK(dot_broadcast(vec4(4, -3, 2, -1), vec4(-1, 3, 2, -2)) == vec4(-7.0f));
456 }
457 
458 TEST_CASE("gl_vec: cross product (only for vectors of length 3)")
459 {
460  CHECK(cross( vec3(4, -3, 2), vec3(-1, 3, 2)) == vec3(-12, -10, 9));
461  CHECK(cross(ivec3(4, -3, 2), ivec3(-1, 3, 2)) == ivec3(-12, -10, 9));
462 }
463 
464 TEST_CASE("gl_vec: vector length squared (2-norm squared)")
465 {
466  CHECK(length2( vec3(4, -3, 2 )) == 29.0f);
467  CHECK(length2(ivec3(4, -3, 2 )) == 29 );
468  CHECK(length2( vec4(4, -3, 2, -1)) == 30.0f);
469  CHECK(length2(ivec4(4, -3, 2, -1)) == 30 );
470 }
471 TEST_CASE("gl_vec: vector length (2-norm), (only floating point)")
472 {
473  CHECK(length(vec3(4, -3, 2 )) == sqrtf(29.0f));
474  CHECK(length(vec4(4, -3, 2, -1)) == sqrtf(30.0f));
475 }
476 
477 TEST_CASE("gl_vec: vector normalization, only floating point")
478 {
479  CHECK(normalize(vec3( 0, 4, -3 )) == vec3( 0.0f, 0.8f, -0.6f));
480  CHECK(normalize(vec4(-4, 0, 0, 3)) == vec4(-0.8f, 0.0f, 0.0f, 0.6f));
481 }
482 
483 TEST_CASE("gl_vec: round")
484 {
485  CHECK(round(vec3( 1.1f, 2.6f, -3.8f)) == ivec3( 1, 3, -4));
486  CHECK(round(vec4(-1.1f, 2.4f, 3.8f, -4.6f)) == ivec4(-1, 2, 4, -5));
487  // round integers, nop
488  CHECK(round(ivec4(1, -2, 3, -4)) == ivec4(1, -2, 3, -4));
489 }
490 
491 TEST_CASE("gl_vec: trunc")
492 {
493  CHECK(trunc(vec3( 1.1f, 2.5f, -3.8f)) == ivec3( 1, 2, -3));
494  CHECK(trunc(vec4(-1.1f, 2.5f, 3.8f, -4.5f)) == ivec4(-1, 2, 3, -4));
495  // trunc integers, nop
496  CHECK(trunc(ivec4(1, -2, 3, -4)) == ivec4(1, -2, 3, -4));
497 }
498 
499 
500 #if 0
501 
502 // The following functions are not part of the actual test. They get compiled,
503 // but never executed. I used them to (manually) inspect the quality of the
504 // generated code. Mostly only for vec4, because the code was only optimized
505 // for that type.
506 
507 void test_constr(vec4& z)
508 {
509  z = vec4();
510 }
511 void test_constr(float x, vec4& z)
512 {
513  z = vec4(x);
514 }
515 void test_constr(float a, float b, float c, float d, vec4& z)
516 {
517  z = vec4(a, b, c, d);
518 }
519 
520 void test_change0(float x, vec4& z)
521 {
522  z[0] = x;
523 }
524 void test_change2(float x, vec4& z)
525 {
526  z[2] = x;
527 }
528 
529 void test_extract0(const vec4& x, float& z)
530 {
531  z = x[0];
532 }
533 void test_extract2(const vec4& x, float& z)
534 {
535  z = x[2];
536 }
537 
538 bool test_equal(const vec4& x, const vec4& y)
539 {
540  return x == y;
541 }
542 bool test_not_equal(const vec4& x, const vec4& y)
543 {
544  return x != y;
545 }
546 
547 void test_add(const vec4& x, const vec4& y, vec4& z)
548 {
549  z = x + y;
550 }
551 void test_add(vec4& x, const vec4& y)
552 {
553  x += y;
554 }
555 
556 void test_negate(const vec4& x, vec4& y)
557 {
558  y = -x;
559 }
560 
561 void test_mul(const vec4& x, const vec4& y, vec4& z)
562 {
563  z = x * y;
564 }
565 void test_mul(float x, const vec4& y, vec4& z)
566 {
567  z = x * y;
568 }
569 
570 void test_div(const vec4& x, const vec4& y, vec4& z)
571 {
572  z = x / y;
573 }
574 void test_div(float x, const vec4& y, vec4& z)
575 {
576  z = x / y;
577 }
578 void test_div(const vec4& x, float y, vec4& z)
579 {
580  z = x / y;
581 }
582 
583 void test_sum(const vec4& x, float& y)
584 {
585  y = sum(x);
586 }
587 void test_sum_broadcast(const vec4& x, vec4& y)
588 {
589  y = sum_broadcast(x);
590 }
591 
592 void test_dot(const vec4& x, const vec4& y, float& z)
593 {
594  z = dot(x, y);
595 }
596 void test_dot_broadcast(const vec4& x, const vec4& y, vec4& z)
597 {
598  z = dot_broadcast(x, y);
599 }
600 
601 void test_length2(const vec4& x, float& y)
602 {
603  y = length2(x);
604 }
605 
606 void test_length(const vec4& x, float& y)
607 {
608  y = length(x);
609 }
610 
611 void test_normalize(const vec4& x, vec4& y)
612 {
613  y = normalize(x);
614 }
615 
616 void test_recip(const vec4& x, vec4& y)
617 {
618  y = recip(x);
619 }
620 
621 
622 void test_constr(vec3& z)
623 {
624  z = vec3();
625 }
626 void test_constr(float x, vec3& z)
627 {
628  z = vec3(x);
629 }
630 void test_constr(float a, float b, float c, vec3& z)
631 {
632  z = vec3(a, b, c);
633 }
634 void test_constr(vec4 x, vec3& y)
635 {
636  y = vec3(x);
637 }
638 
639 void test_change0(float x, vec3& z)
640 {
641  z[0] = x;
642 }
643 void test_change2(float x, vec3& z)
644 {
645  z[2] = x;
646 }
647 
648 void test_extract0(const vec3& x, float& z)
649 {
650  z = x[0];
651 }
652 void test_extract2(const vec3& x, float& z)
653 {
654  z = x[2];
655 }
656 
657 bool test_equal(const vec3& x, const vec3& y)
658 {
659  return x == y;
660 }
661 bool test_not_equal(const vec3& x, const vec3& y)
662 {
663  return x != y;
664 }
665 
666 void test_add(const vec3& x, const vec3& y, vec3& z)
667 {
668  z = x + y;
669 }
670 void test_add(vec3& x, const vec3& y)
671 {
672  x += y;
673 }
674 
675 void test_negate(const vec3& x, vec3& y)
676 {
677  y = -x;
678 }
679 
680 void test_mul(const vec3& x, const vec3& y, vec3& z)
681 {
682  z = x * y;
683 }
684 void test_mul(float x, const vec3& y, vec3& z)
685 {
686  z = x * y;
687 }
688 
689 void test_div(const vec3& x, const vec3& y, vec3& z)
690 {
691  z = x / y;
692 }
693 void test_div(float x, const vec3& y, vec3& z)
694 {
695  z = x / y;
696 }
697 void test_div(const vec3& x, float y, vec3& z)
698 {
699  z = x / y;
700 }
701 
702 void test_min(const vec3& x, const vec3& y, vec3& z)
703 {
704  z = min(x, y);
705 }
706 
707 void test_min(const vec4& x, const vec4& y, vec4& z)
708 {
709  z = min(x, y);
710 }
711 
712 void test_clamp(const vec3& x, const vec3& y, const vec3& z, vec3& w)
713 {
714  w = clamp(x, y, z);
715 }
716 
717 void test_clamp(const vec4& x, const vec4& y, const vec4& z, vec4& w)
718 {
719  w = clamp(x, y, z);
720 }
721 
722 void test_clamp(const vec3& x, float y, float z, vec3& w)
723 {
724  w = clamp(x, y, z);
725 }
726 
727 void test_clamp(const vec4& x, float y, float z, vec4& w)
728 {
729  w = clamp(x, y, z);
730 }
731 
732 void test_clamp(const vec4& x, vec4& y)
733 {
734  y = clamp(x, 0.0f, 1.0f);
735 }
736 
737 void test_sum(const vec3& x, float& y)
738 {
739  y = sum(x);
740 }
741 
742 void test_dot(const vec3& x, const vec3& y, float& z)
743 {
744  z = dot(x, y);
745 }
746 
747 void test_length2(const vec3& x, float& y)
748 {
749  y = length2(x);
750 }
751 
752 void test_length(const vec3& x, float& y)
753 {
754  y = length(x);
755 }
756 
757 void test_normalize(const vec3& x, vec3& y)
758 {
759  y = normalize(x);
760 }
761 
762 void test_round(const vec4& x, ivec4& y)
763 {
764  y = round(x);
765 }
766 void test_trunc(const vec4& x, ivec4& y)
767 {
768  y = trunc(x);
769 }
770 
771 #endif
vecN< 4, int > ivec4
Definition: gl_vec.hh:144
T min_component(const vecN< N, T > &x)
Definition: gl_vec.hh:278
T length(const vecN< N, T > &x)
Definition: gl_vec.hh:343
float rsqrt(float x)
Definition: gl_vec.hh:150
T length2(const vecN< N, T > &x)
Definition: gl_vec.hh:336
vec4 v4(2, 1, -4, -3)
vecN< N, T > min(const vecN< N, T > &x, const vecN< N, T > &y)
Definition: gl_vec.hh:269
imat3 j3(ivec3(1, 2, 3), ivec3(4, 5, 6), ivec3(7, 0, 9))
#define M_PI
Definition: Math.hh:26
vecN< N, int > trunc(const vecN< N, T > &x)
Definition: gl_vec.hh:378
vecN< N, T > normalize(const vecN< N, T > &x)
Definition: gl_vec.hh:350
T degrees(T r)
Definition: gl_vec.hh:164
T radians(T d)
Definition: gl_vec.hh:160
vecN< N, T > max(const vecN< N, T > &x, const vecN< N, T > &y)
Definition: gl_vec.hh:287
T sum(const vecN< N, T > &x)
Definition: gl_vec.hh:310
vecN< 3, T > cross(const vecN< 3, T > &x, const vecN< 3, T > &y)
Definition: gl_vec.hh:357
vecN< 3, int > ivec3
Definition: gl_vec.hh:143
vecN< N, T > recip(const vecN< N, T > &x)
Definition: gl_vec.hh:239
vecN< N, int > round(const vecN< N, T > &x)
Definition: gl_vec.hh:366
vecN< 4, float > vec4
Definition: gl_vec.hh:141
imat4 k4(ivec4(1, 2, 3, 4), ivec4(3, 4, 0, 6), ivec4(5, 6, 7, 8), ivec4(7, 8, 9, 0))
vecN< 2, int > ivec2
Definition: gl_vec.hh:142
T dot(const vecN< N, T > &x, const vecN< N, T > &y)
Definition: gl_vec.hh:324
imat3 i3(ivec3(1, 2, 3), ivec3(4, 5, 6), ivec3(7, 8, 9))
bool approxEq(T x, T y)
Definition: gl_vec.cc:8
vecN< N, T > clamp(const vecN< N, T > &x, const vecN< N, T > &minVal, const vecN< N, T > &maxVal)
Definition: gl_vec.hh:296
vec3 w3(-1, -2, 2)
vecN< N, T > dot_broadcast(const vecN< N, T > &x, const vecN< N, T > &y)
Definition: gl_vec.hh:329
vecN< 3, float > vec3
Definition: gl_vec.hh:140
CHECK(vec2(1, 2) !=vec2(1, 4))
imat4 j4(ivec4(1, 0, 3, 4), ivec4(3, 4, 5, 6), ivec4(5, 6, 7, 8), ivec4(7, 8, 9, 0))
vecN< 2, float > vec2
Definition: gl_vec.hh:139
TEST_CASE("gl_vec: rsqrt")
Definition: gl_vec.cc:19
Definition: gl_mat.hh:24
imat4 i4(ivec4(1, 2, 3, 4), ivec4(3, 4, 5, 6), ivec4(5, 6, 7, 8), ivec4(7, 8, 9, 0))
vecN< N, T > sum_broadcast(const vecN< N, T > &x)
Definition: gl_vec.hh:317
vec4 w4(-1, 2, 2, -6)