33 #ifndef __VMML__MATRIX__HPP__ 34 #define __VMML__MATRIX__HPP__ 36 #include <vmmlib/enable_if.hpp> 37 #include <vmmlib/types.hpp> 51 template<
size_t R,
size_t C,
typename T >
class Matrix 64 Matrix(
const T* begin,
const T* end );
70 explicit Matrix(
const std::vector< T >&
data );
84 typename enable_if< R == S+1 && C == S+1 && S == 3 >::type* = 0 );
93 typename enable_if< R == S+1 && C == S+1 && S == 3 >::type* = 0 );
104 bool equals(
const Matrix& other,
105 T tolerance = std::numeric_limits< T >::epsilon( ))
const;
117 #ifdef VMMLIB_USE_CXX03 118 template<
size_t O,
size_t P >
119 typename enable_if< R == C && O == P && R == O >::type*
121 template<
size_t O,
size_t P,
122 typename =
typename enable_if< R == C && O == P && R == O >::type >
128 Matrix
operator+(
const Matrix& other )
const;
131 Matrix
operator-(
const Matrix& other )
const;
149 T&
operator()(
size_t rowIndex,
size_t colIndex );
152 T
operator()(
size_t rowIndex,
size_t colIndex )
const;
158 template<
size_t O,
size_t P >
160 typename enable_if< O <= R && P <= C >::type* = 0 )
const;
175 template<
size_t P,
size_t Q >
183 void operator=(
const std::vector< T >& data );
201 vector< C-1, T > getTranslation()
const;
213 typename enable_if< R == S+1 && C == S+1 && S == 3 >::type* = 0 )
const;
223 template<
size_t O,
size_t P >
227 template<
size_t O,
size_t P >
228 typename enable_if< O == P && R == C && O == R && R >= 2 >::type*
232 template<
size_t O,
size_t P >
238 template<
typename TT >
240 typename enable_if< R == C && R == 4, TT >::type* = 0 );
242 template<
typename TT >
244 typename enable_if< R == C && R == 4, TT >::type* = 0 );
246 template<
typename TT >
248 typename enable_if< R == C && R == 4, TT >::type* = 0 );
250 template<
typename TT >
252 typename enable_if< R == C && R == 4, TT >::type* = 0 );
254 template<
typename TT >
256 typename enable_if< R == C && R == 4, TT >::type* = 0 );
258 template<
typename TT >
260 typename enable_if< R == C && R == 4, TT >::type* = 0 );
262 template<
typename TT >
264 typename enable_if< R == C && R == 4, TT >::type* = 0 );
266 template<
typename TT >
268 typename enable_if< R == C && R == 4, TT >::type* = 0 );
271 friend std::ostream& operator << ( std::ostream& os,
274 const std::ios::fmtflags flags = os.flags();
275 const int prec = os.precision();
277 os.setf( std::ios::right, std::ios::adjustfield );
280 for(
size_t rowIndex = 0; rowIndex < R; ++rowIndex )
283 for(
size_t colIndex = 0; colIndex < C; ++colIndex )
284 os << std::setw(10) << matrix( rowIndex, colIndex ) <<
" ";
285 os <<
"|" << std::endl;
287 os.precision( prec );
296 #include <vmmlib/quaternion.hpp> 297 #include <vmmlib/vector.hpp> 303 template<
typename T >
306 return matrix_.
array[ 0 ];
309 template<
typename T >
312 return matrix_( 0, 0 ) * matrix_( 1, 1 ) - matrix_( 0, 1 ) * matrix_( 1, 0);
315 template<
typename T >
318 return m_( 0,0 ) * ( m_( 1,1 ) * m_( 2,2 ) - m_( 1,2 ) * m_( 2,1 )) +
319 m_( 0,1 ) * ( m_( 1,2 ) * m_( 2,0 ) - m_( 1,0 ) * m_( 2,2 )) +
320 m_( 0,2 ) * ( m_( 1,0 ) * m_( 2,1 ) - m_( 1,1 ) * m_( 2,0 ));
323 template<
typename T >
326 return m( 0, 3 ) * m( 1, 2 ) * m( 2, 1 ) * m( 3, 0 )
327 - m( 0, 2 ) * m( 1, 3 ) * m( 2, 1 ) * m( 3, 0 )
328 - m( 0, 3 ) * m( 1, 1 ) * m( 2, 2 ) * m( 3, 0 )
329 + m( 0, 1 ) * m( 1, 3 ) * m( 2, 2 ) * m( 3, 0 )
330 + m( 0, 2 ) * m( 1, 1 ) * m( 2, 3 ) * m( 3, 0 )
331 - m( 0, 1 ) * m( 1, 2 ) * m( 2, 3 ) * m( 3, 0 )
332 - m( 0, 3 ) * m( 1, 2 ) * m( 2, 0 ) * m( 3, 1 )
333 + m( 0, 2 ) * m( 1, 3 ) * m( 2, 0 ) * m( 3, 1 )
334 + m( 0, 3 ) * m( 1, 0 ) * m( 2, 2 ) * m( 3, 1 )
335 - m( 0, 0 ) * m( 1, 3 ) * m( 2, 2 ) * m( 3, 1 )
336 - m( 0, 2 ) * m( 1, 0 ) * m( 2, 3 ) * m( 3, 1 )
337 + m( 0, 0 ) * m( 1, 2 ) * m( 2, 3 ) * m( 3, 1 )
338 + m( 0, 3 ) * m( 1, 1 ) * m( 2, 0 ) * m( 3, 2 )
339 - m( 0, 1 ) * m( 1, 3 ) * m( 2, 0 ) * m( 3, 2 )
340 - m( 0, 3 ) * m( 1, 0 ) * m( 2, 1 ) * m( 3, 2 )
341 + m( 0, 0 ) * m( 1, 3 ) * m( 2, 1 ) * m( 3, 2 )
342 + m( 0, 1 ) * m( 1, 0 ) * m( 2, 3 ) * m( 3, 2 )
343 - m( 0, 0 ) * m( 1, 1 ) * m( 2, 3 ) * m( 3, 2 )
344 - m( 0, 2 ) * m( 1, 1 ) * m( 2, 0 ) * m( 3, 3 )
345 + m( 0, 1 ) * m( 1, 2 ) * m( 2, 0 ) * m( 3, 3 )
346 + m( 0, 2 ) * m( 1, 0 ) * m( 2, 1 ) * m( 3, 3 )
347 - m( 0, 0 ) * m( 1, 2 ) * m( 2, 1 ) * m( 3, 3 )
348 - m( 0, 1 ) * m( 1, 0 ) * m( 2, 2 ) * m( 3, 3 )
349 + m( 0, 0 ) * m( 1, 1 ) * m( 2, 2 ) * m( 3, 3 );
352 template<
typename T >
358 template<
typename T >
361 const T det = computeDeterminant( m_ );
362 if( std::abs( det ) < std::numeric_limits< T >::epsilon( ))
364 std::vector< T >( 4, std::numeric_limits< T >::quiet_NaN( )));
367 m_.getAdjugate( inverse );
368 const T detinv = 1 / det;
369 inverse( 0, 0 ) *= detinv;
370 inverse( 0, 1 ) *= detinv;
371 inverse( 1, 0 ) *= detinv;
372 inverse( 1, 1 ) *= detinv;
376 template<
typename T >
382 inverse( 0, 0 ) = m_( 1, 1 ) * m_( 2, 2 ) - m_( 1, 2 ) * m_( 2, 1 );
383 inverse( 0, 1 ) = m_( 0, 2 ) * m_( 2, 1 ) - m_( 0, 1 ) * m_( 2, 2 );
384 inverse( 0, 2 ) = m_( 0, 1 ) * m_( 1, 2 ) - m_( 0, 2 ) * m_( 1, 1 );
385 inverse( 1, 0 ) = m_( 1, 2 ) * m_( 2, 0 ) - m_( 1, 0 ) * m_( 2, 2 );
386 inverse( 1, 1 ) = m_( 0, 0 ) * m_( 2, 2 ) - m_( 0, 2 ) * m_( 2, 0 );
387 inverse( 1, 2 ) = m_( 0, 2 ) * m_( 1, 0 ) - m_( 0, 0 ) * m_( 1, 2 );
388 inverse( 2, 0 ) = m_( 1, 0 ) * m_( 2, 1 ) - m_( 1, 1 ) * m_( 2, 0 );
389 inverse( 2, 1 ) = m_( 0, 1 ) * m_( 2, 0 ) - m_( 0, 0 ) * m_( 2, 1 );
390 inverse( 2, 2 ) = m_( 0, 0 ) * m_( 1, 1 ) - m_( 0, 1 ) * m_( 1, 0 );
392 const T determinant = m_( 0, 0 ) * inverse( 0, 0 ) +
393 m_( 0, 1 ) * inverse( 1, 0 ) +
394 m_( 0, 2 ) * inverse( 2, 0 );
396 if ( std::abs( determinant ) <= std::numeric_limits< T >::epsilon( ))
398 std::vector< T >( 9, std::numeric_limits< T >::quiet_NaN( )));
400 const T detinv =
static_cast< T
>( 1.0 ) / determinant;
402 inverse( 0, 0 ) *= detinv;
403 inverse( 0, 1 ) *= detinv;
404 inverse( 0, 2 ) *= detinv;
405 inverse( 1, 0 ) *= detinv;
406 inverse( 1, 1 ) *= detinv;
407 inverse( 1, 2 ) *= detinv;
408 inverse( 2, 0 ) *= detinv;
409 inverse( 2, 1 ) *= detinv;
410 inverse( 2, 2 ) *= detinv;
414 template<
typename T >
421 const T t1[6] = { array[ 2] * array[ 7] - array[ 6] * array[ 3],
422 array[ 2] * array[11] - array[10] * array[ 3],
423 array[ 2] * array[15] - array[14] * array[ 3],
424 array[ 6] * array[11] - array[10] * array[ 7],
425 array[ 6] * array[15] - array[14] * array[ 7],
426 array[10] * array[15] - array[14] * array[11] };
430 inv.
array[0] = array[ 5] * t1[5] - array[ 9] * t1[4] + array[13] * t1[3];
431 inv.
array[1] = array[ 9] * t1[2] - array[13] * t1[1] - array[ 1] * t1[5];
432 inv.
array[2] = array[13] * t1[0] - array[ 5] * t1[2] + array[ 1] * t1[4];
433 inv.
array[3] = array[ 5] * t1[1] - array[ 1] * t1[3] - array[ 9] * t1[0];
434 inv.
array[4] = array[ 8] * t1[4] - array[ 4] * t1[5] - array[12] * t1[3];
435 inv.
array[5] = array[ 0] * t1[5] - array[ 8] * t1[2] + array[12] * t1[1];
436 inv.
array[6] = array[ 4] * t1[2] - array[12] * t1[0] - array[ 0] * t1[4];
437 inv.
array[7] = array[ 0] * t1[3] - array[ 4] * t1[1] + array[ 8] * t1[0];
440 const T t2[6] = { array[ 0] * array[ 5] - array[ 4] * array[ 1],
441 array[ 0] * array[ 9] - array[ 8] * array[ 1],
442 array[ 0] * array[13] - array[12] * array[ 1],
443 array[ 4] * array[ 9] - array[ 8] * array[ 5],
444 array[ 4] * array[13] - array[12] * array[ 5],
445 array[ 8] * array[13] - array[12] * array[ 9] };
448 inv.
array[8] = array[ 7] * t2[5] - array[11] * t2[4] + array[15] * t2[3];
449 inv.
array[9] = array[11] * t2[2] - array[15] * t2[1] - array[ 3] * t2[5];
450 inv.
array[10] = array[15] * t2[0] - array[ 7] * t2[2] + array[ 3] * t2[4];
451 inv.
array[11] = array[ 7] * t2[1] - array[ 3] * t2[3] - array[11] * t2[0];
452 inv.
array[12] = array[10] * t2[4] - array[ 6] * t2[5] - array[14] * t2[3];
453 inv.
array[13] = array[ 2] * t2[5] - array[10] * t2[2] + array[14] * t2[1];
454 inv.
array[14] = array[ 6] * t2[2] - array[14] * t2[0] - array[ 2] * t2[4];
455 inv.
array[15] = array[ 2] * t2[3] - array[ 6] * t2[1] + array[10] * t2[0];
458 const T determinant = array[0] * inv.
array[0] + array[4] * inv.
array[1] +
459 array[8] * inv.
array[2] + array[12] * inv.
array[3];
462 const T detinv = T( 1 ) / determinant;
463 for(
size_t i = 0; i != 16; ++i )
464 inv.
array[i] *= detinv;
468 template<
size_t R,
size_t C,
typename T >
471 throw std::runtime_error(
"Can't compute inverse of this matrix" );
475 template<
size_t R,
size_t C,
typename T >
inline 479 for(
size_t row = 0; row< R; ++row )
480 for(
size_t col = 0; col < C; ++col )
481 transposed( col, row ) = matrix( row, col );
486 template<
size_t R,
size_t C,
typename T >
491 for(
size_t i = 0; i < R; ++i )
495 template<
size_t R,
size_t C,
typename T >
499 const T* to = std::min( end_, begin_ + R * C );
500 ::memcpy(
array, begin_, (to - begin_) *
sizeof( T ));
503 template<
size_t R,
size_t C,
typename T >
509 template<
size_t R,
size_t C,
typename T >
510 template<
size_t P,
size_t Q >
516 template<
size_t R,
size_t C,
typename T >
template<
size_t O >
519 typename enable_if< R == O+1 && C == O+1 && O == 3 >::type* )
522 setTranslation( translation );
529 template<
size_t R,
size_t C,
typename T >
template<
size_t S >
533 typename enable_if< R == S+1 && C == S+1 && S == 3 >::type* )
540 (*this)( 0, 0 ) = s.x();
541 (*this)( 0, 1 ) = s.y();
542 (*this)( 0, 2 ) = s.z();
543 (*this)( 1, 0 ) = u.x();
544 (*this)( 1, 1 ) = u.y();
545 (*this)( 1, 2 ) = u.z();
546 (*this)( 2, 0 ) = -f.x();
547 (*this)( 2, 1 ) = -f.y();
548 (*this)( 2, 2 ) = -f.z();
549 (*this)( 0, 3 ) = -vmml::dot( s, eye );
550 (*this)( 1, 3 ) = -vmml::dot( u, eye );
551 (*this)( 2, 3 ) = vmml::dot( f, eye );
555 template<
size_t R,
size_t C,
typename T >
inline 558 if ( rowIndex >= R || colIndex >= C )
559 throw std::runtime_error(
"matrix( row, column ) index out of bounds" );
560 return array[ colIndex * R + rowIndex ];
563 template<
size_t R,
size_t C,
typename T >
inline 566 if ( rowIndex >= R || colIndex >= C )
567 throw std::runtime_error(
"matrix( row, column ) index out of bounds" );
568 return array[ colIndex * R + rowIndex ];
571 template<
size_t R,
size_t C,
typename T >
574 for(
size_t i = 0; i < R * C; ++i )
580 template<
size_t R,
size_t C,
typename T >
586 template<
size_t R,
size_t C,
typename T >
588 const T tolerance )
const 590 for(
size_t i = 0; i < R * C; ++i )
591 if( std::abs(
array[ i ] - other.
array[ i ]) > tolerance )
599 ::memcpy(
array, source.
array, R * C *
sizeof( T ));
603 template<
size_t R,
size_t C,
typename T >
template<
size_t P,
size_t Q >
607 const size_t minL = std::min( P, R );
608 const size_t minC = std::min( Q, C );
610 for (
size_t i = 0 ; i < minL ; ++i )
611 for (
size_t j = 0 ; j < minC ; ++j )
612 (*
this)( i, j ) = source( i, j );
613 for (
size_t i = minL ; i< R ; ++i )
614 for (
size_t j = minC ; j < C ; ++j )
619 template<
size_t R,
size_t C,
typename T >
622 const size_t to = std::min( R * C, values.size( ));
623 ::memcpy(
array, values.data(), to *
sizeof( T ));
627 ::memset(
array + to, 0, (R * C - to) *
sizeof( T ));
629 ::bzero(
array + to, (R * C - to) *
sizeof( T ));
634 template<
size_t R,
size_t C,
typename T >
template<
size_t P >
644 for(
size_t rowIndex = 0; rowIndex< R; ++rowIndex )
646 for(
size_t colIndex = 0; colIndex < C; ++colIndex )
648 T& component = (*this)( rowIndex, colIndex );
649 component =
static_cast< T
>( 0.0 );
650 for(
size_t p = 0; p < P; p++)
651 component += left( rowIndex, p ) * right( p, colIndex );
657 template<
size_t R,
size_t C,
typename T >
template<
size_t P >
662 return result.
multiply( *
this, other );
665 #ifdef VMMLIB_USE_CXX03 666 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P >
667 typename enable_if< R == C && O == P && R == O >::type*
669 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P,
typename >
676 #ifdef VMMLIB_USE_CXX03 683 template<
size_t R,
size_t C,
typename T >
689 for(
size_t i = 0; i< R; ++i )
692 for(
size_t j = 0; j < C; ++j )
693 tmp += (*
this)( i, j ) * vec( j );
699 template<
size_t R,
size_t C,
typename T >
inline 703 for(
size_t i = 0; i< R * C; ++i )
708 template<
size_t R,
size_t C,
typename T >
712 throw std::runtime_error(
"getColumn() - index out of bounds." );
714 ::memcpy( &column.
array[0], &
array[ R * index ], R *
sizeof( T ));
718 template<
size_t R,
size_t C,
typename T >
722 throw std::runtime_error(
"setColumn() - index out of bounds." );
723 memcpy(
array + R * index, column.
array, R *
sizeof( T ) );
726 template<
size_t R,
size_t C,
typename T >
730 throw std::runtime_error(
"getRow() - index out of bounds." );
733 for(
size_t colIndex = 0; colIndex < C; ++colIndex )
734 row( colIndex ) = (*this)( index, colIndex );
738 template<
size_t R,
size_t C,
typename T >
742 throw std::runtime_error(
"setRow() - index out of bounds." );
744 for(
size_t colIndex = 0; colIndex < C; ++colIndex )
745 (*
this)( rowIndex, colIndex ) = row( colIndex );
748 template<
size_t R,
size_t C,
typename T >
inline 757 template<
size_t R,
size_t C,
typename T >
760 for(
size_t i = 0; i < R * C; ++i )
764 template<
size_t R,
size_t C,
typename T >
inline 773 template<
size_t R,
size_t C,
typename T >
776 for(
size_t i = 0; i < R * C; ++i )
780 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P >
783 typename enable_if< O <= R && P <= C >::type* )
const 786 if ( O + rowOffset > R || P + colOffset > C )
787 throw std::runtime_error(
"index out of bounds." );
789 for(
size_t row = 0; row < O; ++row )
790 for(
size_t col = 0; col < P; ++col )
791 result( row, col ) = (*this)( rowOffset + row, colOffset + col );
796 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P >
799 size_t rowOffset,
size_t colOffset )
801 for(
size_t row = 0; row < O; ++row )
802 for(
size_t col = 0; col < P; ++col )
803 (*
this)( rowOffset + row, colOffset + col ) = sub_matrix( row, col);
807 template<
size_t R,
size_t C,
typename T >
810 return computeInverse( *
this );
813 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P >
822 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P >
823 typename enable_if< O == P && R == C && O == R && R >= 2 >::type*
826 Matrix< R-1, C-1, T > minor_;
828 const size_t _negate = 1u;
829 for(
size_t rowIndex = 0; rowIndex< R; ++rowIndex )
830 for(
size_t colIndex = 0; colIndex < C; ++colIndex )
831 if ( ( rowIndex + colIndex ) & _negate )
832 cofactors( rowIndex, colIndex ) = -getMinor( minor_, rowIndex, colIndex );
834 cofactors( rowIndex, colIndex ) = getMinor( minor_, rowIndex, colIndex );
839 template<
size_t R,
size_t C,
typename T >
template<
size_t O,
size_t P >
844 size_t rowOffset = 0;
845 size_t colOffset = 0;
846 for(
size_t rowIndex = 0; rowIndex< R; ++rowIndex )
848 if ( rowIndex == row_to_cut )
852 for(
size_t colIndex = 0; colIndex < R; ++colIndex )
854 if ( colIndex == col_to_cut )
857 minor_( rowIndex + rowOffset, colIndex + colOffset )
858 = (*this)( rowIndex, colIndex );
863 return computeDeterminant( minor_ );
866 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
868 typename enable_if< R == C && R == 4, TT >::type* )
870 const T angle =
static_cast< T
>( angle_ );
871 const T sine = std::sin( angle );
872 const T cosine = std::cos( angle );
876 tmp =
array[ 4 ] * cosine +
array[ 8 ] * sine;
880 tmp =
array[ 5 ] * cosine +
array[ 9 ] * sine;
884 tmp =
array[ 6 ] * cosine +
array[ 10 ] * sine;
888 tmp =
array[ 7 ] * cosine +
array[ 11 ] * sine;
895 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
897 typename enable_if< R == C && R == 4, TT >::type* )
899 const T angle =
static_cast< T
>( angle_ );
900 const T sine = std::sin( angle );
901 const T cosine = std::cos( angle );
905 tmp =
array[ 0 ] * cosine -
array[ 8 ] * sine;
909 tmp =
array[ 1 ] * cosine -
array[ 9 ] * sine;
913 tmp =
array[ 2 ] * cosine -
array[ 10 ] * sine;
917 tmp =
array[ 3 ] * cosine -
array[ 11 ] * sine;
924 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
926 typename enable_if< R == C && R == 4, TT >::type* )
928 const T angle =
static_cast< T
>( angle_ );
929 const T sine = std::sin( angle );
930 const T cosine = std::cos( angle );
934 tmp =
array[ 0 ] * cosine +
array[ 4 ] * sine;
938 tmp =
array[ 1 ] * cosine +
array[ 5 ] * sine;
942 tmp =
array[ 2 ] * cosine +
array[ 6 ] * sine;
946 tmp =
array[ 3 ] * cosine +
array[ 7 ] * sine;
953 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
955 typename enable_if< R == C && R == 4, TT >::type* )
957 const T angle =
static_cast< T
>( angle_ );
958 const T sine = std::sin( angle );
959 const T cosine = std::cos( angle );
965 array[ 2 ] = tmp * -sine +
array[ 2 ] * cosine;
969 array[ 6 ] = tmp * -sine +
array[ 6 ] * cosine;
973 array[ 10 ] = tmp * -sine +
array[ 10 ] * cosine;
977 array[ 14 ] = tmp * -sine +
array[ 14 ] * cosine;
982 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
984 typename enable_if< R == C && R == 4, TT >::type* )
986 const T angle =
static_cast< T
>( angle_ );
987 const T sine = std::sin( angle );
988 const T cosine = std::cos( angle );
994 array[ 2 ] = tmp * sine +
array[ 2 ] * cosine;
998 array[ 6 ] = tmp * sine +
array[ 6 ] * cosine;
1002 array[ 10 ] = tmp * sine +
array[ 10 ] * cosine;
1006 array[ 14 ] = tmp * sine +
array[ 14 ] * cosine;
1011 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
1013 typename enable_if< R == C && R == 4, TT >::type* )
1015 const T angle =
static_cast< T
>( angle_ );
1016 const T sine = std::sin( angle );
1017 const T cosine = std::cos( angle );
1023 array[ 1 ] = tmp * -sine +
array[ 1 ] * cosine;
1027 array[ 5 ] = tmp * -sine +
array[ 5 ] * cosine;
1031 array[ 9 ] = tmp * -sine +
array[ 9 ] * cosine;
1035 array[ 13 ] = tmp * -sine +
array[ 13 ] * cosine;
1040 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
inline 1042 typename enable_if< R == C && R == 4, TT >::type* )
1044 array[0] *= scale_[ 0 ];
1045 array[1] *= scale_[ 0 ];
1046 array[2] *= scale_[ 0 ];
1047 array[3] *= scale_[ 0 ];
1048 array[4] *= scale_[ 1 ];
1049 array[5] *= scale_[ 1 ];
1050 array[6] *= scale_[ 1 ];
1051 array[7] *= scale_[ 1 ];
1052 array[8] *= scale_[ 2 ];
1053 array[9] *= scale_[ 2 ];
1054 array[10] *= scale_[ 2 ];
1055 array[11] *= scale_[ 2 ];
1060 template<
size_t R,
size_t C,
typename T >
template<
typename TT >
inline 1063 typename enable_if< R == C && R == 4, TT >::type* )
1065 array[12] *=
static_cast< T
>( scale_[0] );
1066 array[13] *=
static_cast< T
>( scale_[1] );
1067 array[14] *=
static_cast< T
>( scale_[2] );
1075 for(
size_t i = 0; i < C-1; ++i )
1076 array[ i + R * (C - 1) ] = trans[ i ];
1080 template<
size_t R,
size_t C,
typename T >
inline 1084 for(
size_t i = 0; i < C-1; ++i )
1085 result[ i ] =
array[ i + R * (C - 1) ];
1089 template<
size_t R,
size_t C,
typename T >
template<
size_t S >
1092 typename enable_if< R == S+1 && C == S+1 && S == 3 >::type* )
const 1101 lookAt = eye + lookAt;
Matrix< R, P, T > operator*(const Matrix< C, P, T > &other) const
Matrix operator+(const Matrix &other) const
Element-wise addition of two matrices.
enable_if< O<=R &&P<=C >::type *setSubMatrix(const Matrix< O, P, T > &sub_matrix, size_t rowOffset, size_t colOffset);const Matrix &operator=(const Matrix< R, C, T > &source_);template< size_t P, size_t Q > const Matrix &operator=(const Matrix< P, Q, T > &source_);void operator=(const std::vector< T > &data);Matrix< R, C, T > operator-() const ;vector< R, T > getColumn(size_t columnIndex) const ;void setColumn(size_t index, const vector< R, T > &column);vector< C, T > getRow(size_t index) const ;void setRow(size_t index, const vector< C, T > &row);vector< C-1, T > getTranslation() const ;Matrix< R, C, T > &setTranslation(const vector< C-1, T > &t);template< size_t S > void getLookAt(vector< S, T > &eye, vector< S, T > &lookAt, vector< S, T > &up, typename enable_if< R==S+1 &&C==S+1 &&S==3 >::type *=0) const ;Matrix< R, C, T > inverse() const ;template< size_t O, size_t P > typename enable_if< O==P &&R==C &&O==R &&R >=2 >::type *getAdjugate(Matrix< O, P, T > &adjugate) const ;template< size_t O, size_t P > typename enable_if< O==P &&R==C &&O==R &&R >=2 >::type * getCofactors(Matrix< O, P, T > &cofactors) const
Set the sub matrix of size OxP at the given start indices.
bool operator==(const Matrix &other) const
Matrix< R, C, T > & operator*=(const Matrix< O, P, T > &right)
Multiply two square matrices.
Matrix()
Construct a zero-initialized matrix.
T array[R *C]
column by column storage
Matrix operator-(const Matrix &other) const
Element-wise substraction of two matrices.
bool equals(const Matrix &other, T tolerance=std::numeric_limits< T >::epsilon()) const
heavily inspired by boost::enable_if http://www.boost.org, file: boost/utility/enable_if.hpp, Copyright 2003 Jaakko Järvi, Jeremiah Willcock, Andrew Lumsdaine
void operator-=(const Matrix &other)
Element-wise substraction of two matrices.
T & operator()(size_t rowIndex, size_t colIndex)
Matrix< C, R, T > transpose(const Matrix< R, C, T > &matrix)
Matrix< 3, 3, T > getRotationMatrix() const
bool operator!=(const Matrix &other) const
Matrix< O, P, T > getSubMatrix(size_t rowOffset, size_t colOffset, typename enable_if< O<=R &&P<=C >::type *=0) const
Matrix< R, C, T > & multiply(const Matrix< R, P, T > &left, const Matrix< P, C, T > &right)
Set this to the product of the two matrices (left_RxP * right_PxC)
void operator+=(const Matrix &other)
Element-wise addition of two matrices.
Matrix with R rows and C columns of element type T.