PageRenderTime 87ms CodeModel.GetById 26ms app.highlight 55ms RepoModel.GetById 1ms app.codeStats 0ms

/indra/llmath/tests/llquaternion_test.cpp

https://bitbucket.org/lindenlab/viewer-beta/
C++ | 660 lines | 514 code | 88 blank | 58 comment | 98 complexity | 39847776b6792ec481a8574a776224ed MD5 | raw file
  1/** 
  2 * @file llquaternion_test.cpp
  3 * @author Adroit
  4 * @date 2007-03
  5 * @brief Test cases of llquaternion.h
  6 *
  7 * $LicenseInfo:firstyear=2007&license=viewerlgpl$
  8 * Second Life Viewer Source Code
  9 * Copyright (C) 2010, Linden Research, Inc.
 10 * 
 11 * This library is free software; you can redistribute it and/or
 12 * modify it under the terms of the GNU Lesser General Public
 13 * License as published by the Free Software Foundation;
 14 * version 2.1 of the License only.
 15 * 
 16 * This library is distributed in the hope that it will be useful,
 17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 19 * Lesser General Public License for more details.
 20 * 
 21 * You should have received a copy of the GNU Lesser General Public
 22 * License along with this library; if not, write to the Free Software
 23 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 24 * 
 25 * Linden Research, Inc., 945 Battery Street, San Francisco, CA  94111  USA
 26 * $/LicenseInfo$
 27 */
 28
 29#include "linden_common.h"
 30#include "../test/lltut.h"
 31
 32#include "../v4math.h"
 33#include "../v3math.h"
 34#include "../v3dmath.h"
 35#include "../m4math.h"
 36#include "../m3math.h"
 37#include "../llquaternion.h"
 38
 39namespace tut
 40{
 41	struct llquat_test
 42	{
 43	};
 44	typedef test_group<llquat_test> llquat_test_t;
 45	typedef llquat_test_t::object llquat_test_object_t;
 46	tut::llquat_test_t tut_llquat_test("LLQuaternion");
 47
 48	//test case for LLQuaternion::LLQuaternion(void) fn.
 49	template<> template<>
 50	void llquat_test_object_t::test<1>()
 51	{
 52		LLQuaternion llquat;
 53		ensure("LLQuaternion::LLQuaternion() failed", 0.f == llquat.mQ[0] &&
 54		 									0.f == llquat.mQ[1] &&
 55		 									0.f == llquat.mQ[2] &&
 56											1.f == llquat.mQ[3]);
 57	}
 58
 59	//test case for explicit LLQuaternion(const LLMatrix4 &mat) fn.
 60	template<> template<>
 61	void llquat_test_object_t::test<2>()
 62	{
 63		LLMatrix4 llmat;
 64		LLVector4 vector1(2.0f, 1.0f, 3.0f, 6.0f);
 65		LLVector4 vector2(5.0f, 6.0f, 0.0f, 1.0f);
 66		LLVector4 vector3(2.0f, 1.0f, 2.0f, 9.0f);
 67		LLVector4 vector4(3.0f, 8.0f, 1.0f, 5.0f);
 68
 69		llmat.initRows(vector1, vector2, vector3, vector4);
 70		ensure("explicit LLQuaternion(const LLMatrix4 &mat) failed", 2.0f == llmat.mMatrix[0][0] &&
 71										 	1.0f == llmat.mMatrix[0][1] &&
 72											3.0f == llmat.mMatrix[0][2] &&
 73											6.0f == llmat.mMatrix[0][3] &&
 74											5.0f == llmat.mMatrix[1][0] &&
 75											6.0f == llmat.mMatrix[1][1] &&
 76											0.0f == llmat.mMatrix[1][2] &&
 77											1.0f == llmat.mMatrix[1][3] &&
 78											2.0f == llmat.mMatrix[2][0] &&
 79											1.0f == llmat.mMatrix[2][1] &&
 80											2.0f == llmat.mMatrix[2][2] &&
 81											9.0f == llmat.mMatrix[2][3] &&
 82											3.0f == llmat.mMatrix[3][0] &&
 83											8.0f == llmat.mMatrix[3][1] &&
 84											1.0f == llmat.mMatrix[3][2] &&
 85											5.0f == llmat.mMatrix[3][3]);
 86	}
 87	
 88	template<> template<>
 89	void llquat_test_object_t::test<3>()
 90	{
 91		LLMatrix3 llmat;
 92
 93		LLVector3 vect1(3.4028234660000000f , 234.56f, 4234.442234f);
 94		LLVector3 vect2(741.434f, 23.00034f, 6567.223423f);
 95		LLVector3 vect3(566.003034f, 12.98705f, 234.764423f);
 96		llmat.setRows(vect1, vect2, vect3);
 97
 98		ensure("LLMatrix3::setRows fn failed.", 3.4028234660000000f == llmat.mMatrix[0][0] &&
 99										234.56f == llmat.mMatrix[0][1] &&
100										4234.442234f == llmat.mMatrix[0][2] &&
101										741.434f == llmat.mMatrix[1][0] &&
102										23.00034f == llmat.mMatrix[1][1] &&
103										6567.223423f == llmat.mMatrix[1][2] &&
104										566.003034f == llmat.mMatrix[2][0] &&
105										12.98705f == llmat.mMatrix[2][1] &&
106										234.764423f == llmat.mMatrix[2][2]);		
107	}
108
109	//test case for LLQuaternion(F32 x, F32 y, F32 z, F32 w), setQuatInit() and normQuat() fns.
110	template<> template<>
111	void llquat_test_object_t::test<4>()
112	{
113		F32 x_val = 3.0f;
114		F32 y_val = 2.0f;
115		F32 z_val = 6.0f;
116		F32 w_val = 1.0f;
117		
118		LLQuaternion res_quat;
119		res_quat.setQuatInit(x_val, y_val, z_val, w_val);
120		res_quat.normQuat();
121				
122		ensure("LLQuaternion::normQuat() fn failed", 
123							is_approx_equal(0.42426407f, res_quat.mQ[0]) &&
124							is_approx_equal(0.28284273f, res_quat.mQ[1]) &&
125							is_approx_equal(0.84852815f, res_quat.mQ[2]) &&
126							is_approx_equal(0.14142136f, res_quat.mQ[3]));
127		
128		x_val = 0.0f;
129		y_val = 0.0f;
130		z_val = 0.0f;
131		w_val = 0.0f;
132
133		res_quat.setQuatInit(x_val, y_val, z_val, w_val);
134		res_quat.normQuat();
135
136		ensure("LLQuaternion::normQuat() fn. failed.", 
137							is_approx_equal(0.0f, res_quat.mQ[0]) &&
138							is_approx_equal(0.0f, res_quat.mQ[1]) &&
139							is_approx_equal(0.0f, res_quat.mQ[2]) &&
140							is_approx_equal(1.0f, res_quat.mQ[3]));
141
142
143		ensure("LLQuaternion::normQuat() fn. failed.", 
144							is_approx_equal(0.0f, res_quat.mQ[0]) &&
145							is_approx_equal(0.0f, res_quat.mQ[1]) &&
146							is_approx_equal(0.0f, res_quat.mQ[2]) &&
147							is_approx_equal(1.0f, res_quat.mQ[3]));
148	}
149
150	//test case for conjQuat() and transQuat() fns.
151	template<> template<>
152	void llquat_test_object_t::test<5>()
153	{
154		F32 x_val = 3.0f;
155		F32 y_val = 2.0f;
156		F32 z_val = 6.0f;
157		F32 w_val = 1.0f;
158		
159		LLQuaternion res_quat;
160		LLQuaternion result, result1;
161		result1 = result = res_quat.setQuatInit(x_val, y_val, z_val, w_val);
162				
163		result.conjQuat();
164		result1.transQuat();
165
166		ensure("LLQuaternion::conjQuat and LLQuaternion::transQuat failed ", 
167								is_approx_equal(result1.mQ[0], result.mQ[0]) &&
168								is_approx_equal(result1.mQ[1], result.mQ[1]) &&
169								is_approx_equal(result1.mQ[2], result.mQ[2]));		
170
171	}
172
173	//test case for dot(const LLQuaternion &a, const LLQuaternion &b) fn.
174	template<> template<>
175	void llquat_test_object_t::test<6>()
176	{
177		LLQuaternion quat1(3.0f, 2.0f, 6.0f, 0.0f), quat2(1.0f, 1.0f, 1.0f, 1.0f);
178		ensure("1. The two values are different", llround(12.000000f, 2) == llround(dot(quat1, quat2), 2));
179
180		LLQuaternion quat0(3.0f, 9.334f, 34.5f, 23.0f), quat(34.5f, 23.23f, 2.0f, 45.5f);
181		ensure("2. The two values are different", llround(1435.828807f, 2) == llround(dot(quat0, quat), 2));
182	}
183
184	//test case for LLQuaternion &LLQuaternion::constrain(F32 radians) fn.
185	template<> template<>
186	void llquat_test_object_t::test<7>()
187	{
188		F32 radian = 60.0f;
189		LLQuaternion quat(3.0f, 2.0f, 6.0f, 0.0f);
190		LLQuaternion quat1;
191		quat1 = quat.constrain(radian);
192		ensure("1. LLQuaternion::constrain(F32 radians) failed", 
193									is_approx_equal_fraction(-0.423442f, quat1.mQ[0], 8) &&
194									is_approx_equal_fraction(-0.282295f, quat1.mQ[1], 8) &&
195									is_approx_equal_fraction(-0.846884f, quat1.mQ[2], 8) &&				
196									is_approx_equal_fraction(0.154251f, quat1.mQ[3], 8));				
197											
198
199		radian = 30.0f;
200		LLQuaternion quat0(37.50f, 12.0f, 86.023f, 40.32f);
201		quat1 = quat0.constrain(radian);
202	
203		ensure("2. LLQuaternion::constrain(F32 radians) failed", 
204									is_approx_equal_fraction(37.500000f, quat1.mQ[0], 8) &&
205									is_approx_equal_fraction(12.0000f, quat1.mQ[1], 8) &&
206									is_approx_equal_fraction(86.0230f, quat1.mQ[2], 8) &&				
207									is_approx_equal_fraction(40.320000f, quat1.mQ[3], 8));				
208	}
209
210	template<> template<>
211	void llquat_test_object_t::test<8>()
212	{
213		F32 value1 = 15.0f;
214		LLQuaternion quat1(1.0f, 2.0f, 4.0f, 1.0f);
215		LLQuaternion quat2(4.0f, 3.0f, 6.5f, 9.7f);
216		LLQuaternion res_lerp, res_slerp, res_nlerp;
217		
218		//test case for lerp(F32 t, const LLQuaternion &q) fn. 
219		res_lerp = lerp(value1, quat1);
220		ensure("1. LLQuaternion lerp(F32 t, const LLQuaternion &q) failed", 
221										is_approx_equal_fraction(0.181355f, res_lerp.mQ[0], 16) &&
222										is_approx_equal_fraction(0.362711f, res_lerp.mQ[1], 16) &&
223										is_approx_equal_fraction(0.725423f, res_lerp.mQ[2], 16) &&				
224										is_approx_equal_fraction(0.556158f, res_lerp.mQ[3], 16));				
225
226		//test case for lerp(F32 t, const LLQuaternion &p, const LLQuaternion &q) fn.
227		res_lerp = lerp(value1, quat1, quat2);
228		ensure("2. LLQuaternion lerp(F32 t, const LLQuaternion &p, const LLQuaternion &q) failed",
229										is_approx_equal_fraction(0.314306f, res_lerp.mQ[0], 16) &&
230										is_approx_equal_fraction(0.116156f, res_lerp.mQ[1], 16) &&
231										is_approx_equal_fraction(0.283559f, res_lerp.mQ[2], 16) &&				
232										is_approx_equal_fraction(0.898506f, res_lerp.mQ[3], 16));				
233
234		//test case for slerp( F32 u, const LLQuaternion &a, const LLQuaternion &b ) fn.
235		res_slerp = slerp(value1, quat1, quat2);
236		ensure("3. LLQuaternion slerp( F32 u, const LLQuaternion &a, const LLQuaternion &b) failed", 
237										is_approx_equal_fraction(46.000f, res_slerp.mQ[0], 16) &&
238										is_approx_equal_fraction(17.00f, res_slerp.mQ[1], 16) &&
239										is_approx_equal_fraction(41.5f, res_slerp.mQ[2], 16) &&				
240										is_approx_equal_fraction(131.5f, res_slerp.mQ[3], 16));				
241
242		//test case for nlerp(F32 t, const LLQuaternion &a, const LLQuaternion &b) fn.
243		res_nlerp = nlerp(value1, quat1, quat2);
244		ensure("4. LLQuaternion nlerp(F32 t, const LLQuaternion &a, const LLQuaternion &b) failed",  
245										is_approx_equal_fraction(0.314306f, res_nlerp.mQ[0], 16) &&
246										is_approx_equal_fraction(0.116157f, res_nlerp.mQ[1], 16) &&
247										is_approx_equal_fraction(0.283559f, res_nlerp.mQ[2], 16) &&				
248										is_approx_equal_fraction(0.898506f, res_nlerp.mQ[3], 16));				
249
250		//test case for nlerp(F32 t, const LLQuaternion &q) fn.
251		res_slerp = slerp(value1, quat1);
252		ensure("5. LLQuaternion slerp(F32 t, const LLQuaternion &q) failed", 
253										is_approx_equal_fraction(1.0f, res_slerp.mQ[0], 16) &&
254										is_approx_equal_fraction(2.0f, res_slerp.mQ[1], 16) &&
255										is_approx_equal_fraction(4.0000f, res_slerp.mQ[2], 16) &&				
256										is_approx_equal_fraction(1.000f, res_slerp.mQ[3], 16));				
257										
258		LLQuaternion quat3(2.0f, 1.0f, 5.5f, 10.5f);
259		LLQuaternion res_nlerp1;
260		value1 = 100.0f;
261		res_nlerp1 = nlerp(value1, quat3);
262		ensure("6. LLQuaternion nlerp(F32 t, const LLQuaternion &q)  failed", 
263										is_approx_equal_fraction(0.268245f, res_nlerp1.mQ[0], 16) &&										is_approx_equal_fraction(0.134122f, res_nlerp1.mQ[1], 2) &&
264										is_approx_equal_fraction(0.737673f, res_nlerp1.mQ[2], 16) &&				
265										is_approx_equal_fraction(0.604892f, res_nlerp1.mQ[3], 16));				
266
267		//test case for lerp(F32 t, const LLQuaternion &q) fn. 
268		res_lerp = lerp(value1, quat2);
269		ensure("7. LLQuaternion lerp(F32 t, const LLQuaternion &q) failed", 
270										is_approx_equal_fraction(0.404867f, res_lerp.mQ[0], 16) &&
271										is_approx_equal_fraction(0.303650f, res_lerp.mQ[1], 16) &&
272										is_approx_equal_fraction(0.657909f, res_lerp.mQ[2], 16) &&				
273										is_approx_equal_fraction(0.557704f, res_lerp.mQ[3], 16));				
274		
275	}
276
277	template<> template<>
278	void llquat_test_object_t::test<9>()
279	{
280		//test case for LLQuaternion operator*(const LLQuaternion &a, const LLQuaternion &b) fn
281		LLQuaternion quat1(1.0f, 2.5f, 3.5f, 5.5f);
282		LLQuaternion quat2(4.0f, 3.0f, 5.0f, 1.0f);
283		LLQuaternion result = quat1 *  quat2;
284		ensure("1. LLQuaternion Operator* failed", (21.0f == result.mQ[0]) &&
285											(10.0f == result.mQ[1]) &&
286											(38.0f == result.mQ[2]) && 
287											(-23.5f == result.mQ[3]));
288
289		LLQuaternion quat3(2341.340f, 2352.345f, 233.25f, 7645.5f);
290		LLQuaternion quat4(674.067f, 893.0897f, 578.0f, 231.0f);
291		result = quat3 * quat4;
292		ensure("2. LLQuaternion Operator* failed", (4543086.5f == result.mQ[0]) &&
293											(8567578.0f == result.mQ[1]) &&
294											(3967591.25f == result.mQ[2]) &&
295											is_approx_equal(-2047783.25f, result.mQ[3]));
296
297		//inline LLQuaternion operator+(const LLQuaternion &a, const LLQuaternion &b)fn.		
298		result = quat1 + quat2;
299		ensure("3. LLQuaternion operator+ failed", (5.0f == result.mQ[0]) &&
300											(5.5f == result.mQ[1]) &&
301											(8.5f == result.mQ[2]) &&
302											(6.5f == result.mQ[3]));
303
304		result = quat3 + quat4;
305		ensure(
306			"4. LLQuaternion operator+ failed",
307			is_approx_equal(3015.407227f, result.mQ[0]) &&
308			is_approx_equal(3245.434570f, result.mQ[1]) &&
309			(811.25f == result.mQ[2]) &&
310			(7876.5f == result.mQ[3]));
311
312		//inline LLQuaternion operator-(const LLQuaternion &a, const LLQuaternion &b) fn
313		result = quat1 - quat2;
314		ensure(
315			"5. LLQuaternion operator-(const LLQuaternion &a, const LLQuaternion &b) failed", 
316			(-3.0f == result.mQ[0]) &&
317			(-0.5f == result.mQ[1]) &&
318			(-1.5f == result.mQ[2]) &&
319			(4.5f == result.mQ[3]));
320
321		result = quat3 - quat4;
322		ensure(
323			"6. LLQuaternion operator-(const LLQuaternion &a, const LLQuaternion &b) failed", 
324			is_approx_equal(1667.273071f, result.mQ[0]) &&
325			is_approx_equal(1459.255249f, result.mQ[1]) &&
326			(-344.75f == result.mQ[2]) &&
327			(7414.50f == result.mQ[3]));
328	}
329
330	//test case for LLVector4 operator*(const LLVector4 &a, const LLQuaternion &rot) fn.
331	template<> template<>
332	void llquat_test_object_t::test<10>()
333	{
334		LLVector4 vect(12.0f, 5.0f, 60.0f, 75.1f);
335		LLQuaternion quat(2323.034f, 23.5f, 673.23f, 57667.5f);
336		LLVector4 result = vect * quat;
337		ensure(
338			"1. LLVector4 operator*(const LLVector4 &a, const LLQuaternion &rot) failed", 
339			is_approx_equal(39928406016.0f, result.mV[0]) &&
340			// gcc on x86 actually gives us more precision than we were expecting, verified with -ffloat-store - we forgive this
341			(1457802240.0f >= result.mV[1]) && // gcc+x86+linux
342			(1457800960.0f <= result.mV[1]) && // elsewhere
343			is_approx_equal(200580612096.0f, result.mV[2]) &&
344			(75.099998f == result.mV[3]));
345
346		LLVector4 vect1(22.0f, 45.0f, 40.0f, 78.1f);
347		LLQuaternion quat1(2.034f, 45.5f, 37.23f, 7.5f);
348		result = vect1 * quat1;
349		ensure(
350			"2. LLVector4 operator*(const LLVector4 &a, const LLQuaternion &rot) failed", 
351			is_approx_equal(-58153.5390f, result.mV[0]) &&
352			(183787.8125f == result.mV[1]) &&
353			(116864.164063f == result.mV[2]) &&
354			(78.099998f == result.mV[3]));
355	}
356
357	//test case for LLVector3 operator*(const LLVector3 &a, const LLQuaternion &rot) fn.
358	template<> template<>
359	void llquat_test_object_t::test<11>()
360	{
361		LLVector3 vect(12.0f, 5.0f, 60.0f);
362		LLQuaternion quat(23.5f, 6.5f, 3.23f, 56.5f);
363		LLVector3 result = vect * quat;
364		ensure(
365			"1. LLVector3 operator*(const LLVector3 &a, const LLQuaternion &rot) failed", 
366			is_approx_equal(97182.953125f,result.mV[0]) &&
367			is_approx_equal(-135405.640625f, result.mV[1]) &&
368			is_approx_equal(162986.140f, result.mV[2]));
369
370		LLVector3 vect1(5.0f, 40.0f, 78.1f);
371		LLQuaternion quat1(2.034f, 45.5f, 37.23f, 7.5f);
372		result = vect1 * quat1;
373		ensure(
374			"2. LLVector3 operator*(const LLVector3 &a, const LLQuaternion &rot) failed", 
375			is_approx_equal(33217.703f, result.mV[0]) &&
376			is_approx_equal(295383.8125f, result.mV[1]) &&
377			is_approx_equal(84718.140f, result.mV[2]));
378	}
379
380	//test case for LLVector3d operator*(const LLVector3d &a, const LLQuaternion &rot) fn.
381	template<> template<>
382	void llquat_test_object_t::test<12>()
383	{
384		LLVector3d vect(-2.0f, 5.0f, -6.0f);
385		LLQuaternion quat(-3.5f, 4.5f, 3.5f, 6.5f);
386		LLVector3d result = vect * quat;
387		ensure(
388			"1. LLVector3d operator*(const LLVector3d &a, const LLQuaternion &rot) failed ", 
389			(-633.0f == result.mdV[0]) &&
390			(-300.0f == result.mdV[1]) &&
391			(-36.0f == result.mdV[2]));
392
393		LLVector3d vect1(5.0f, -4.5f, 8.21f);
394		LLQuaternion quat1(2.0f, 4.5f, -7.2f, 9.5f);
395		result = vect1 * quat1;
396		ensure(
397			"2. LLVector3d operator*(const LLVector3d &a, const LLQuaternion &rot) failed", 
398			is_approx_equal_fraction(-120.29f, (F32) result.mdV[0], 8) &&
399			is_approx_equal_fraction(-1683.958f, (F32) result.mdV[1], 8) &&
400			is_approx_equal_fraction(516.56f, (F32) result.mdV[2], 8));
401
402		LLVector3d vect2(2.0f, 3.5f, 1.1f);
403		LLQuaternion quat2(1.0f, 4.0f, 2.0f, 5.0f);
404		result = vect2 * quat2;
405		ensure(
406			"3. LLVector3d operator*(const LLVector3d &a, const LLQuaternion &rot) failed", 
407			is_approx_equal_fraction(18.400001f, (F32) result.mdV[0], 8) &&
408			is_approx_equal_fraction(188.6f, (F32) result.mdV[1], 8) &&
409			is_approx_equal_fraction(32.20f, (F32) result.mdV[2], 8));
410	}
411
412	//test case for inline LLQuaternion operator-(const LLQuaternion &a) fn.
413	template<> template<>
414	void llquat_test_object_t::test<13>()
415	{
416		LLQuaternion quat(23.5f, 34.5f, 16723.4f, 324.7f);
417		LLQuaternion result = -quat;
418		ensure(
419			"1. LLQuaternion operator-(const LLQuaternion &a) failed", 
420			(-23.5f == result.mQ[0]) &&
421			(-34.5f == result.mQ[1]) &&
422			(-16723.4f == result.mQ[2]) &&
423			(-324.7f == result.mQ[3]));
424
425		LLQuaternion quat1(-3.5f, -34.5f, -16.4f, -154.7f);
426		result = -quat1;
427		ensure(
428			"2. LLQuaternion operator-(const LLQuaternion &a) failed.", 
429			(3.5f == result.mQ[0]) &&
430			(34.5f == result.mQ[1]) &&
431			(16.4f == result.mQ[2]) &&
432			(154.7f == result.mQ[3]));
433	}
434
435	//test case for inline LLQuaternion operator*(F32 a, const LLQuaternion &q) and
436	//inline LLQuaternion operator*(F32 a, const LLQuaternion &q) fns.
437	template<> template<>
438	void llquat_test_object_t::test<14>()
439	{
440		LLQuaternion quat_value(9.0f, 8.0f, 7.0f, 6.0f);
441		F32 a =3.5f;
442		LLQuaternion result = a * quat_value;
443		LLQuaternion result1 = quat_value * a;
444
445		ensure(
446			"1. LLQuaternion operator* failed",
447			(result.mQ[0] == result1.mQ[0]) &&
448			(result.mQ[1] == result1.mQ[1]) &&
449			(result.mQ[2] == result1.mQ[2]) &&
450			(result.mQ[3] == result1.mQ[3]));
451
452
453		LLQuaternion quat_val(9454.0f, 43568.3450f, 456343247.0343f, 2346.03434f);
454		a =-3324.3445f;
455		result = a * quat_val;
456		result1 = quat_val * a;
457
458		ensure(
459			"2. LLQuaternion operator* failed",
460			(result.mQ[0] == result1.mQ[0]) &&
461			(result.mQ[1] == result1.mQ[1]) &&
462			(result.mQ[2] == result1.mQ[2]) &&
463			(result.mQ[3] == result1.mQ[3]));
464	}
465	
466	template<> template<>
467	void llquat_test_object_t::test<15>()
468	{
469		// test cases for inline LLQuaternion operator~(const LLQuaternion &a)
470		LLQuaternion quat_val(2323.634f, -43535.4f, 3455.88f, -32232.45f);
471		LLQuaternion result = ~quat_val;
472		ensure(
473			"1. LLQuaternion operator~(const LLQuaternion &a) failed ", 
474			(-2323.634f == result.mQ[0]) &&
475			(43535.4f == result.mQ[1]) &&
476			(-3455.88f == result.mQ[2]) &&
477			(-32232.45f == result.mQ[3]));
478
479		//test case for inline bool LLQuaternion::operator==(const LLQuaternion &b) const
480		LLQuaternion quat_val1(2323.634f, -43535.4f, 3455.88f, -32232.45f);
481		LLQuaternion quat_val2(2323.634f, -43535.4f, 3455.88f, -32232.45f);
482		ensure(
483			"2. LLQuaternion::operator==(const LLQuaternion &b) failed",
484			quat_val1 == quat_val2);
485	}
486	
487	template<> template<>
488	void llquat_test_object_t::test<16>()
489	{
490		//test case for inline bool LLQuaternion::operator!=(const LLQuaternion &b) const
491		LLQuaternion quat_val1(2323.634f, -43535.4f, 3455.88f, -32232.45f);
492		LLQuaternion quat_val2(0, -43535.4f, 3455.88f, -32232.45f);
493		ensure("LLQuaternion::operator!=(const LLQuaternion &b) failed", quat_val1 != quat_val2);
494	}
495
496	template<> template<>
497	void llquat_test_object_t::test<17>()
498	{
499		//test case for LLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order)
500		F32 x = 2.0f;
501		F32 y = 1.0f;
502		F32 z = 3.0f;
503		
504		LLQuaternion result = mayaQ(x, y, z, LLQuaternion::XYZ);
505		ensure(
506			"1. LLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order) failed for XYZ",
507			is_approx_equal_fraction(0.0172174f, result.mQ[0], 16) &&
508			is_approx_equal_fraction(0.009179f, result.mQ[1], 16) &&
509			is_approx_equal_fraction(0.026020f, result.mQ[2], 16) &&
510			is_approx_equal_fraction(0.999471f, result.mQ[3], 16));
511
512		LLQuaternion result1 = mayaQ(x, y, z, LLQuaternion::YZX);
513		ensure(
514			"2. LLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order) failed for XYZ",
515			is_approx_equal_fraction(0.017217f, result1.mQ[0], 16) &&
516			is_approx_equal_fraction(0.008265f, result1.mQ[1], 16) &&
517			is_approx_equal_fraction(0.026324f, result1.mQ[2], 16) &&
518			is_approx_equal_fraction(0.999471f, result1.mQ[3], 16));
519		
520		LLQuaternion result2 = mayaQ(x, y, z, LLQuaternion::ZXY);
521		ensure(
522			"3. LLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order) failed for ZXY", 
523			is_approx_equal_fraction(0.017674f, result2.mQ[0], 16) &&
524			is_approx_equal_fraction(0.008265f, result2.mQ[1], 16) &&
525			is_approx_equal_fraction(0.026020f, result2.mQ[2], 16) &&
526			is_approx_equal_fraction(0.999471f, result2.mQ[3], 16));
527											
528		LLQuaternion result3 = mayaQ(x, y, z, LLQuaternion::XZY);
529		ensure(
530			"4. TLLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order) failed for XZY", 
531			is_approx_equal_fraction(0.017674f, result3.mQ[0], 16) &&
532			is_approx_equal_fraction(0.009179f, result3.mQ[1], 16) &&
533			is_approx_equal_fraction(0.026020f, result3.mQ[2], 16) &&
534			is_approx_equal_fraction(0.999463f, result3.mQ[3], 16));
535											
536		LLQuaternion result4 = mayaQ(x, y, z, LLQuaternion::YXZ);
537		ensure(
538			"5. LLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order) failed for YXZ", 
539			is_approx_equal_fraction(0.017217f, result4.mQ[0], 16) &&
540			is_approx_equal_fraction(0.009179f, result4.mQ[1], 16) &&
541			is_approx_equal_fraction(0.026324f, result4.mQ[2], 16) &&
542			is_approx_equal_fraction(0.999463f, result4.mQ[3], 16));
543											
544		LLQuaternion result5 = mayaQ(x, y, z, LLQuaternion::ZYX);
545		ensure(
546			"6. LLQuaternion mayaQ(F32 xRot, F32 yRot, F32 zRot, LLQuaternion::Order order) failed for ZYX", 
547			is_approx_equal_fraction(0.017674f, result5.mQ[0], 16) &&
548			is_approx_equal_fraction(0.008265f, result5.mQ[1], 16) &&
549			is_approx_equal_fraction(0.026324f, result5.mQ[2], 16) &&
550			is_approx_equal_fraction(0.999463f, result5.mQ[3], 16));
551	}
552
553	template<> template<>
554	void llquat_test_object_t::test<18>()
555	{
556		// test case for friend std::ostream& operator<<(std::ostream &s, const LLQuaternion &a) fn
557		LLQuaternion a(1.0f, 1.0f, 1.0f, 1.0f); 
558		std::ostringstream result_value;
559		result_value << a;
560		ensure_equals("1. Operator << failed", result_value.str(), "{ 1, 1, 1, 1 }");
561
562		LLQuaternion b(-31.034f, 231.2340f, 3451.344320f, -341.0f); 
563		std::ostringstream result_value1;
564		result_value1 << b;
565		ensure_equals("2. Operator << failed", result_value1.str(), "{ -31.034, 231.234, 3451.34, -341 }");
566
567		LLQuaternion c(1.0f, 2.2f, 3.3f, 4.4f); 
568		result_value << c;
569		ensure_equals("3. Operator << failed", result_value.str(), "{ 1, 1, 1, 1 }{ 1, 2.2, 3.3, 4.4 }");
570
571	}
572	
573	template<> template<>
574	void llquat_test_object_t::test<19>()
575	{
576		//test case for const char *OrderToString( const LLQuaternion::Order order ) fn
577		const char* result = OrderToString(LLQuaternion::XYZ);
578		ensure("1. OrderToString failed for XYZ",  (0 == strcmp("XYZ", result)));
579		
580		result = OrderToString(LLQuaternion::YZX);
581		ensure("2. OrderToString failed for YZX",  (0 == strcmp("YZX", result)));
582		
583		result = OrderToString(LLQuaternion::ZXY);
584		ensure(
585			"3. OrderToString failed for ZXY",
586			(0 == strcmp("ZXY", result)) &&
587			(0 != strcmp("XYZ", result)) &&
588			(0 != strcmp("YXZ", result)) &&
589			(0 != strcmp("ZYX", result)) &&
590			(0 != strcmp("XYZ", result)));
591
592		result = OrderToString(LLQuaternion::XZY);
593		ensure("4. OrderToString failed for XZY",  (0 == strcmp("XZY", result)));
594
595		result = OrderToString(LLQuaternion::ZYX);
596		ensure("5. OrderToString failed for ZYX",  (0 == strcmp("ZYX", result)));
597
598		result = OrderToString(LLQuaternion::YXZ);
599		ensure("6.OrderToString failed for YXZ",  (0 == strcmp("YXZ", result)));
600	}
601
602	template<> template<>
603	void llquat_test_object_t::test<20>()
604	{
605		//test case for LLQuaternion::Order StringToOrder( const char *str ) fn
606		int result = StringToOrder("XYZ");
607		ensure("1. LLQuaternion::Order StringToOrder(const char *str ) failed for XYZ", 0 == result);
608
609		result = StringToOrder("YZX");
610		ensure("2. LLQuaternion::Order StringToOrder(const char *str) failed for YZX", 1 == result);
611
612		result = StringToOrder("ZXY");
613		ensure("3. LLQuaternion::Order StringToOrder(const char *str) failed for ZXY", 2 == result);
614		
615		result = StringToOrder("XZY");
616		ensure("4. LLQuaternion::Order StringToOrder(const char *str) failed for XZY", 3 == result);
617
618		result = StringToOrder("YXZ");
619		ensure("5. LLQuaternion::Order StringToOrder(const char *str) failed for YXZ", 4 == result);
620	
621		result = StringToOrder("ZYX");
622		ensure("6. LLQuaternion::Order StringToOrder(const char *str) failed for  ZYX", 5 == result);	
623
624	}
625
626	template<> template<>
627	void llquat_test_object_t::test<21>()
628	{
629		//void LLQuaternion::getAngleAxis(F32* angle, LLVector3 &vec) const fn
630		F32 angle_value = 90.0f;
631		LLVector3 vect(12.0f, 4.0f, 1.0f);
632		LLQuaternion llquat(angle_value, vect);
633		llquat.getAngleAxis(&angle_value, vect); 
634		ensure(
635			"LLQuaternion::getAngleAxis(F32* angle, LLVector3 &vec) failed", 
636			is_approx_equal_fraction(2.035406f, angle_value, 16) &&
637			is_approx_equal_fraction(0.315244f, vect.mV[1], 16) &&
638			is_approx_equal_fraction(0.078811f, vect.mV[2], 16) &&
639			is_approx_equal_fraction(0.945733f, vect.mV[0], 16));
640	}
641
642	template<> template<>
643	void llquat_test_object_t::test<22>()
644	{
645		//test case for void LLQuaternion::getEulerAngles(F32 *roll, F32 *pitch, F32 *yaw) const fn
646		F32 roll = -12.0f;
647		F32 pitch = -22.43f;
648		F32 yaw = 11.0f;
649
650		LLQuaternion llquat;
651		llquat.getEulerAngles(&roll, &pitch, &yaw);
652		ensure(
653			"LLQuaternion::getEulerAngles(F32 *roll, F32 *pitch, F32 *yaw) failed",
654			is_approx_equal(0.000f, llquat.mQ[0]) &&
655			is_approx_equal(0.000f, llquat.mQ[1]) &&
656			is_approx_equal(0.000f, llquat.mQ[2]) &&
657			is_approx_equal(1.000f, llquat.mQ[3]));
658	}
659
660}