| 
									
										
										
										
											2015-05-24 06:55:12 +02:00
										 |  |  | // Copyright 2008 Dolphin Emulator Project
 | 
					
						
							| 
									
										
										
										
											2015-05-18 01:08:10 +02:00
										 |  |  | // Licensed under GPLv2+
 | 
					
						
							| 
									
										
										
										
											2013-04-17 23:09:55 -04:00
										 |  |  | // Refer to the license.txt file included.
 | 
					
						
							| 
									
										
										
										
											2008-12-08 04:46:09 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-02-10 13:54:46 -05:00
										 |  |  | #pragma once
 | 
					
						
							| 
									
										
										
										
											2008-12-08 04:46:09 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-09-11 23:43:17 -04:00
										 |  |  | #include <algorithm>
 | 
					
						
							| 
									
										
										
										
											2014-02-20 04:11:52 +01:00
										 |  |  | #include <cstdlib>
 | 
					
						
							| 
									
										
										
										
											2009-07-12 21:58:32 +00:00
										 |  |  | #include <vector>
 | 
					
						
							| 
									
										
										
										
											2014-02-17 05:18:15 -05:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-09-07 20:06:58 -05:00
										 |  |  | #include "Common/CommonTypes.h"
 | 
					
						
							| 
									
										
										
										
											2009-07-12 21:58:32 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | namespace MathUtil | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2016-04-03 19:08:47 -04:00
										 |  |  | 
 | 
					
						
							|  |  |  | template <typename T> | 
					
						
							|  |  |  | constexpr T SNANConstant() | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | 	return std::numeric_limits<T>::signaling_NaN(); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #ifdef _MSC_VER
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // MSVC needs a workaround, because its std::numeric_limits<double>::signaling_NaN()
 | 
					
						
							|  |  |  | // will use __builtin_nans, which is improperly handled by the compiler and generates
 | 
					
						
							|  |  |  | // a bad constant. Here we go back to the version MSVC used before the builtin.
 | 
					
						
							|  |  |  | // TODO: Remove this and use numeric_limits directly whenever this bug is fixed.
 | 
					
						
							|  |  |  | template <> | 
					
						
							|  |  |  | constexpr double SNANConstant() | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | 	return (_CSTD _Snan._Double); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | template <> | 
					
						
							|  |  |  | constexpr float SNANConstant() | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | 	return (_CSTD _Snan._Float); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | #endif
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-02-04 20:43:07 -05:00
										 |  |  | template<class T> | 
					
						
							| 
									
										
										
										
											2015-09-11 23:43:17 -04:00
										 |  |  | constexpr T Clamp(const T val, const T& min, const T& max) | 
					
						
							| 
									
										
										
										
											2014-02-04 20:43:07 -05:00
										 |  |  | { | 
					
						
							| 
									
										
										
										
											2015-09-11 23:43:17 -04:00
										 |  |  | 	return std::max(min, std::min(max, val)); | 
					
						
							| 
									
										
										
										
											2014-07-15 00:42:33 +12:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-09-12 00:22:48 -04:00
										 |  |  | constexpr bool IsPow2(u32 imm) | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | 	return (imm & (imm - 1)) == 0; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | // The most significant bit of the fraction is an is-quiet bit on all architectures we care about.
 | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  | static const u64 DOUBLE_SIGN = 0x8000000000000000ULL, | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  |                  DOUBLE_EXP  = 0x7FF0000000000000ULL, | 
					
						
							|  |  |  |                  DOUBLE_FRAC = 0x000FFFFFFFFFFFFFULL, | 
					
						
							|  |  |  |                  DOUBLE_ZERO = 0x0000000000000000ULL, | 
					
						
							|  |  |  |                  DOUBLE_QBIT = 0x0008000000000000ULL; | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-05-25 18:14:29 +00:00
										 |  |  | static const u32 FLOAT_SIGN = 0x80000000, | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  |                  FLOAT_EXP  = 0x7F800000, | 
					
						
							|  |  |  |                  FLOAT_FRAC = 0x007FFFFF, | 
					
						
							|  |  |  |                  FLOAT_ZERO = 0x00000000; | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  | union IntDouble { | 
					
						
							|  |  |  | 	double d; | 
					
						
							|  |  |  | 	u64 i; | 
					
						
							| 
									
										
										
										
											2014-03-23 10:24:06 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	explicit IntDouble(u64 _i) : i(_i) {} | 
					
						
							|  |  |  | 	explicit IntDouble(double _d) : d(_d) {} | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | }; | 
					
						
							|  |  |  | union IntFloat { | 
					
						
							|  |  |  | 	float f; | 
					
						
							|  |  |  | 	u32 i; | 
					
						
							| 
									
										
										
										
											2014-03-23 10:24:06 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	explicit IntFloat(u32 _i) : i(_i) {} | 
					
						
							|  |  |  | 	explicit IntFloat(float _f) : f(_f) {} | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | }; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | inline bool IsQNAN(double d) | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2014-03-23 10:24:06 +01:00
										 |  |  | 	IntDouble x(d); | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | 	return ((x.i & DOUBLE_EXP) == DOUBLE_EXP) && | 
					
						
							|  |  |  | 	       ((x.i & DOUBLE_QBIT) == DOUBLE_QBIT); | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | inline bool IsSNAN(double d) | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2014-03-23 10:24:06 +01:00
										 |  |  | 	IntDouble x(d); | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | 	return ((x.i & DOUBLE_EXP) == DOUBLE_EXP) && | 
					
						
							|  |  |  | 	       ((x.i & DOUBLE_FRAC) != DOUBLE_ZERO) && | 
					
						
							|  |  |  | 	       ((x.i & DOUBLE_QBIT) == DOUBLE_ZERO); | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | inline float FlushToZero(float f) | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2014-03-23 10:24:06 +01:00
										 |  |  | 	IntFloat x(f); | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 	if ((x.i & FLOAT_EXP) == 0) | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | 	{ | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 		x.i &= FLOAT_SIGN;  // turn into signed zero
 | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 	return x.f; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-10-24 22:05:53 +02:00
										 |  |  | inline double FlushToZero(double d) | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | { | 
					
						
							| 
									
										
										
										
											2014-03-23 10:24:06 +01:00
										 |  |  | 	IntDouble x(d); | 
					
						
							| 
									
										
										
										
											2013-10-24 22:05:53 +02:00
										 |  |  | 	if ((x.i & DOUBLE_EXP) == 0) | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | 	{ | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 		x.i &= DOUBLE_SIGN;  // turn into signed zero
 | 
					
						
							| 
									
										
										
										
											2014-03-09 19:34:58 +01:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 	return x.d; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-06-14 11:30:33 +00:00
										 |  |  | enum PPCFpClass | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | 	PPC_FPCLASS_QNAN = 0x11, | 
					
						
							|  |  |  | 	PPC_FPCLASS_NINF = 0x9, | 
					
						
							|  |  |  | 	PPC_FPCLASS_NN   = 0x8, | 
					
						
							|  |  |  | 	PPC_FPCLASS_ND   = 0x18, | 
					
						
							|  |  |  | 	PPC_FPCLASS_NZ   = 0x12, | 
					
						
							|  |  |  | 	PPC_FPCLASS_PZ   = 0x2, | 
					
						
							|  |  |  | 	PPC_FPCLASS_PD   = 0x14, | 
					
						
							|  |  |  | 	PPC_FPCLASS_PN   = 0x4, | 
					
						
							|  |  |  | 	PPC_FPCLASS_PINF = 0x5, | 
					
						
							|  |  |  | }; | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-06-14 11:30:33 +00:00
										 |  |  | // Uses PowerPC conventions for the return value, so it can be easily
 | 
					
						
							|  |  |  | // used directly in CPU emulation.
 | 
					
						
							| 
									
										
										
										
											2011-05-25 18:14:29 +00:00
										 |  |  | u32 ClassifyDouble(double dvalue); | 
					
						
							| 
									
										
										
										
											2009-06-15 21:10:11 +00:00
										 |  |  | // More efficient float version.
 | 
					
						
							| 
									
										
										
										
											2011-05-25 18:14:29 +00:00
										 |  |  | u32 ClassifyFloat(float fvalue); | 
					
						
							| 
									
										
										
										
											2009-06-14 11:30:33 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-09-02 20:50:03 -07:00
										 |  |  | extern const int frsqrte_expected_base[]; | 
					
						
							|  |  |  | extern const int frsqrte_expected_dec[]; | 
					
						
							| 
									
										
										
										
											2014-09-03 12:11:02 -07:00
										 |  |  | extern const int fres_expected_base[]; | 
					
						
							|  |  |  | extern const int fres_expected_dec[]; | 
					
						
							| 
									
										
										
										
											2014-09-02 20:50:03 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-09-03 12:11:02 -07:00
										 |  |  | // PowerPC approximation algorithms
 | 
					
						
							| 
									
										
										
										
											2014-09-02 20:50:03 -07:00
										 |  |  | double ApproximateReciprocalSquareRoot(double val); | 
					
						
							| 
									
										
										
										
											2014-09-03 12:11:02 -07:00
										 |  |  | double ApproximateReciprocal(double val); | 
					
						
							| 
									
										
										
										
											2014-09-02 20:50:03 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | template<class T> | 
					
						
							|  |  |  | struct Rectangle | 
					
						
							|  |  |  | { | 
					
						
							| 
									
										
										
										
											2015-10-20 20:11:25 -04:00
										 |  |  | 	T left{}; | 
					
						
							|  |  |  | 	T top{}; | 
					
						
							|  |  |  | 	T right{}; | 
					
						
							|  |  |  | 	T bottom{}; | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-10-20 20:24:11 -04:00
										 |  |  | 	constexpr Rectangle() = default; | 
					
						
							| 
									
										
										
										
											2011-03-08 07:39:36 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-10-20 20:24:11 -04:00
										 |  |  | 	constexpr Rectangle(T theLeft, T theTop, T theRight, T theBottom) | 
					
						
							| 
									
										
										
										
											2011-03-08 07:39:36 +00:00
										 |  |  | 		: left(theLeft), top(theTop), right(theRight), bottom(theBottom) | 
					
						
							| 
									
										
										
										
											2015-10-20 20:24:11 -04:00
										 |  |  | 	{} | 
					
						
							| 
									
										
										
										
											2013-10-29 01:23:17 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2015-10-20 20:24:11 -04:00
										 |  |  | 	constexpr bool operator==(const Rectangle& r) const | 
					
						
							|  |  |  | 	{ | 
					
						
							|  |  |  | 		return left == r.left && top == r.top && right == r.right && bottom == r.bottom; | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2011-03-08 07:39:36 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | 	T GetWidth() const { return abs(right - left); } | 
					
						
							|  |  |  | 	T GetHeight() const { return abs(bottom - top); } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// If the rectangle is in a coordinate system with a lower-left origin, use
 | 
					
						
							|  |  |  | 	// this Clamp.
 | 
					
						
							|  |  |  | 	void ClampLL(T x1, T y1, T x2, T y2) | 
					
						
							|  |  |  | 	{ | 
					
						
							| 
									
										
										
										
											2015-09-11 23:43:17 -04:00
										 |  |  | 		left   = Clamp(left, x1, x2); | 
					
						
							|  |  |  | 		right  = Clamp(right, x1, x2); | 
					
						
							|  |  |  | 		top    = Clamp(top, y2, y1); | 
					
						
							|  |  |  | 		bottom = Clamp(bottom, y2, y1); | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-03-08 07:39:36 +00:00
										 |  |  | 	// If the rectangle is in a coordinate system with an upper-left origin,
 | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | 	// use this Clamp.
 | 
					
						
							| 
									
										
										
										
											2013-10-29 01:23:17 -04:00
										 |  |  | 	void ClampUL(T x1, T y1, T x2, T y2) | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | 	{ | 
					
						
							| 
									
										
										
										
											2015-09-11 23:43:17 -04:00
										 |  |  | 		left   = Clamp(left, x1, x2); | 
					
						
							|  |  |  | 		right  = Clamp(right, x1, x2); | 
					
						
							|  |  |  | 		top    = Clamp(top, y1, y2); | 
					
						
							|  |  |  | 		bottom = Clamp(bottom, y1, y2); | 
					
						
							| 
									
										
										
										
											2009-07-15 00:51:24 +00:00
										 |  |  | 	} | 
					
						
							|  |  |  | }; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-06-14 11:30:33 +00:00
										 |  |  | }  // namespace MathUtil
 | 
					
						
							| 
									
										
										
										
											2009-06-14 10:59:06 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-07-28 07:40:18 +00:00
										 |  |  | float MathFloatVectorSum(const std::vector<float>&); | 
					
						
							| 
									
										
										
										
											2008-12-08 04:46:09 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-02-09 18:29:13 -05:00
										 |  |  | #define ROUND_UP(x, a)   (((x) + (a) - 1) & ~((a) - 1))
 | 
					
						
							|  |  |  | #define ROUND_DOWN(x, a) ((x) & ~((a) - 1))
 | 
					
						
							| 
									
										
										
										
											2009-02-22 00:40:52 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-03-05 15:48:57 -06:00
										 |  |  | // Rounds down. 0 -> undefined
 | 
					
						
							| 
									
										
										
										
											2014-08-24 11:03:07 -07:00
										 |  |  | inline int IntLog2(u64 val) | 
					
						
							| 
									
										
										
										
											2013-03-05 03:12:17 -06:00
										 |  |  | { | 
					
						
							| 
									
										
										
										
											2013-03-05 15:48:57 -06:00
										 |  |  | #if defined(__GNUC__)
 | 
					
						
							|  |  |  | 	return 63 - __builtin_clzll(val); | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2014-09-03 13:04:48 -04:00
										 |  |  | #elif defined(_MSC_VER)
 | 
					
						
							| 
									
										
										
										
											2013-03-05 15:48:57 -06:00
										 |  |  | 	unsigned long result = -1; | 
					
						
							|  |  |  | 	_BitScanReverse64(&result, val); | 
					
						
							| 
									
										
										
										
											2013-03-05 03:12:17 -06:00
										 |  |  | 	return result; | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-03-05 03:12:17 -06:00
										 |  |  | #else
 | 
					
						
							| 
									
										
										
										
											2014-02-24 10:20:53 +01:00
										 |  |  | 	int result = -1; | 
					
						
							| 
									
										
										
										
											2013-03-05 03:12:17 -06:00
										 |  |  | 	while (val != 0) | 
					
						
							|  |  |  | 	{ | 
					
						
							|  |  |  | 		val >>= 1; | 
					
						
							|  |  |  | 		++result; | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	return result; | 
					
						
							|  |  |  | #endif
 | 
					
						
							|  |  |  | } | 
					
						
							| 
									
										
										
										
											2009-06-14 11:30:33 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  | // Tiny matrix/vector library.
 | 
					
						
							| 
									
										
										
										
											2011-02-14 02:18:03 +00:00
										 |  |  | // Used for things like Free-Look in the gfx backend.
 | 
					
						
							| 
									
										
										
										
											2009-06-14 11:30:33 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | class Matrix33 | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | public: | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void LoadIdentity(Matrix33& mtx); | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 	// set mtx to be a rotation matrix around the x axis
 | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void RotateX(Matrix33& mtx, float rad); | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 	// set mtx to be a rotation matrix around the y axis
 | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void RotateY(Matrix33& mtx, float rad); | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 	// set result = a x b
 | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void Multiply(const Matrix33& a, const Matrix33& b, Matrix33& result); | 
					
						
							|  |  |  | 	static void Multiply(const Matrix33& a, const float vec[3], float result[3]); | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 	float data[9]; | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | }; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class Matrix44 | 
					
						
							|  |  |  | { | 
					
						
							|  |  |  | public: | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void LoadIdentity(Matrix44& mtx); | 
					
						
							|  |  |  | 	static void LoadMatrix33(Matrix44& mtx, const Matrix33& m33); | 
					
						
							|  |  |  | 	static void Set(Matrix44& mtx, const float mtxArray[16]); | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void Translate(Matrix44& mtx, const float vec[3]); | 
					
						
							|  |  |  | 	static void Shear(Matrix44& mtx, const float a, const float b = 0); | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2016-01-21 21:27:56 +01:00
										 |  |  | 	static void Multiply(const Matrix44& a, const Matrix44& b, Matrix44& result); | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2013-03-19 21:51:12 -04:00
										 |  |  | 	float data[16]; | 
					
						
							| 
									
										
										
										
											2009-04-19 10:10:45 +00:00
										 |  |  | }; |