5#include <initializer_list>
21template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
32 fmat(std::initializer_list<T> components) :
fvec<T,N*M>((
cgv::type::uint32_type)components.
size(), components.
begin()) {}
40 for (j = 0; j < std::min(m, M); ++j) {
42 for (i = 0; i < std::min(n, N); ++i)
43 (*
this)(i, j) = a[column_major ? j * n + i : i * m + j];
45 (*
this)(i, j) = (i == j) ? T(1) : T(0);
49 (*
this)(i, j) = (i == j) ? T(1) : T(0);
56 (*
this)(i, j) = (T)a[column_major ? j * n + i : i * m + j];
62 template <
typename T1,
typename T2>
64 for(
unsigned i = 0; i < N; i++)
65 for(
unsigned j = 0; j < M; j++)
66 (*
this)(i,j) = (T)(v(i)*
w(j));
69 constexpr static unsigned nrows() {
return N; }
71 constexpr static unsigned ncols() {
return M; }
75 base_type::operator = (m);
87 assert(i < N && j < M);
88 return base_type::v[j*N+i];
92 assert(i < N && j < M);
93 return base_type::v[j*N+i];
114 template <
typename S>
117 template <
typename S>
120 template <
typename S>
123 template <
typename S>
126 template <
typename S>
131 for(
unsigned i = 0; i < N; i++)
132 for(
unsigned j = 0; j < N;j++)
133 for(
unsigned k = 0; k < N; k++)
139 template <
typename S, cgv::type::u
int32_type L>
143 for(
unsigned i = 0; i < N; i++)
144 for(
unsigned j = 0; j < L;j++)
145 for(
unsigned k = 0; k < M; k++)
152 template <
typename S>
155 static_assert(N == M,
"Number of rows and columns must be equal");
156 static const auto vzero =
fvec<T, N-1>(0);
158 for (
unsigned i=0; i<N; i++)
162 for (
unsigned j=0; j<N-1; j++)
163 for (
unsigned i=0; i<N; i++)
164 r(i,j) = dot_dir(rows[i], m2.
col(j));
166 for (
unsigned i=0; i<N; i++)
167 r(i,N-1) = dot_pos(rows[i], vzero);
172 template <
typename S>
175 for(
unsigned i = 0; i < N; i++)
176 r(i) = dot(
row(i),v);
180 template <
typename S>
183 for(
unsigned i = 0; i < N; i++)
184 r(i) = dot_pos(
row(i), v);
188 template <
typename S>
191 for(
unsigned i = 0; i < N; i++)
192 r(i) = dot_dir(
row(i), v);
199 for(
unsigned j = 0; j < M; j++)
205 for(
unsigned j = 0; j < M;j++)
206 operator()(i,j)=v(j);
210 return reinterpret_cast<fvec<T,N>*
>(
this)[j];
214 return reinterpret_cast<const fvec<T,N>*
>(
this)[j];
218 reinterpret_cast<fvec<T,N>*
>(
this)[j] = v;
225 for(
unsigned i = 0; i < N;i++)
233 for(
unsigned i = 1; i < N; i++)
234 for(
unsigned j = 0; j < i; j++)
235 std::swap(
operator()(i,j),
operator()(j,i));
243 for(
unsigned i = 0; i < M && i < N; ++i)
249#define CGV_MATH_FMAT_DECLARED
256template <
typename T, cgv::type::u
int32_type N>
257fmat<T, N, N> inverse(
const fmat<T, N, N>& m) =
delete;
261fmat<T, 2, 2> inverse(
const fmat<T, 2, 2>& m)
264 T t4 = T(1) / (-m(0, 0) * m(1, 1) + m(0, 1) * m(1, 0));
265 im(0, 0) = -m(1, 1) * t4;
266 im(1, 0) = +m(1, 0) * t4;
267 im(0, 1) = +m(0, 1) * t4;
268 im(1, 1) = -m(0, 0) * t4;
275fmat<T, 3, 3> inverse(
const fmat<T, 3, 3>& m)
278 +m(0, 0) * (m(1, 1) * m(2, 2) - m(1, 2) * m(2, 1))
279 - m(0, 1) * (m(1, 0) * m(2, 2) - m(1, 2) * m(2, 0))
280 + m(0, 2) * (m(1, 0) * m(2, 1) - m(1, 1) * m(2, 0)));
283 im(0, 0) = +(m(1, 1) * m(2, 2) - m(1, 2) * m(2, 1)) * inv_det;
284 im(0, 1) = -(m(0, 1) * m(2, 2) - m(0, 2) * m(2, 1)) * inv_det;
285 im(0, 2) = +(m(0, 1) * m(1, 2) - m(0, 2) * m(1, 1)) * inv_det;
286 im(1, 0) = -(m(1, 0) * m(2, 2) - m(1, 2) * m(2, 0)) * inv_det;
287 im(1, 1) = +(m(0, 0) * m(2, 2) - m(0, 2) * m(2, 0)) * inv_det;
288 im(1, 2) = -(m(0, 0) * m(1, 2) - m(0, 2) * m(1, 0)) * inv_det;
289 im(2, 0) = +(m(1, 0) * m(2, 1) - m(1, 1) * m(2, 0)) * inv_det;
290 im(2, 1) = -(m(0, 0) * m(2, 1) - m(0, 1) * m(2, 0)) * inv_det;
291 im(2, 2) = +(m(0, 0) * m(1, 1) - m(0, 1) * m(1, 0)) * inv_det;
297fmat<T, 4, 4> inverse(
const fmat<T, 4, 4>& m)
299 T coef00 = m(2, 2) * m(3, 3) - m(2, 3) * m(3, 2);
300 T coef02 = m(2, 1) * m(3, 3) - m(2, 3) * m(3, 1);
301 T coef03 = m(2, 1) * m(3, 2) - m(2, 2) * m(3, 1);
303 T coef04 = m(1, 2) * m(3, 3) - m(1, 3) * m(3, 2);
304 T coef06 = m(1, 1) * m(3, 3) - m(1, 3) * m(3, 1);
305 T coef07 = m(1, 1) * m(3, 2) - m(1, 2) * m(3, 1);
307 T coef08 = m(1, 2) * m(2, 3) - m(1, 3) * m(2, 2);
308 T coef10 = m(1, 1) * m(2, 3) - m(1, 3) * m(2, 1);
309 T coef11 = m(1, 1) * m(2, 2) - m(1, 2) * m(2, 1);
311 T coef12 = m(0, 2) * m(3, 3) - m(0, 3) * m(3, 2);
312 T coef14 = m(0, 1) * m(3, 3) - m(0, 3) * m(3, 1);
313 T coef15 = m(0, 1) * m(3, 2) - m(0, 2) * m(3, 1);
315 T coef16 = m(0, 2) * m(2, 3) - m(0, 3) * m(2, 2);
316 T coef18 = m(0, 1) * m(2, 3) - m(0, 3) * m(2, 1);
317 T coef19 = m(0, 1) * m(2, 2) - m(0, 2) * m(2, 1);
319 T coef20 = m(0, 2) * m(1, 3) - m(0, 3) * m(1, 2);
320 T coef22 = m(0, 1) * m(1, 3) - m(0, 3) * m(1, 1);
321 T coef23 = m(0, 1) * m(1, 2) - m(0, 2) * m(1, 1);
323 fvec<T, 4> fac0(coef00, coef00, coef02, coef03);
324 fvec<T, 4> fac1(coef04, coef04, coef06, coef07);
325 fvec<T, 4> fac2(coef08, coef08, coef10, coef11);
326 fvec<T, 4> fac3(coef12, coef12, coef14, coef15);
327 fvec<T, 4> fac4(coef16, coef16, coef18, coef19);
328 fvec<T, 4> fac5(coef20, coef20, coef22, coef23);
330 fvec<T, 4> vec0(m(0, 1), m(0, 0), m(0, 0), m(0, 0));
331 fvec<T, 4> vec1(m(1, 1), m(1, 0), m(1, 0), m(1, 0));
332 fvec<T, 4>
vec2(m(2, 1), m(2, 0), m(2, 0), m(2, 0));
333 fvec<T, 4>
vec3(m(3, 1), m(3, 0), m(3, 0), m(3, 0));
335 fvec<T, 4> inv0(vec1 * fac0 -
vec2 * fac1 + vec3 * fac2);
336 fvec<T, 4> inv1(vec0 * fac0 -
vec2 * fac3 + vec3 * fac4);
337 fvec<T, 4> inv2(vec0 * fac1 - vec1 * fac3 + vec3 * fac5);
338 fvec<T, 4> inv3(vec0 * fac2 - vec1 * fac4 +
vec2 * fac5);
340 fvec<T, 4> sign_a(+(T)1, -(T)1, +(T)1, -(T)1);
341 fvec<T, 4> sign_b(-(T)1, +(T)1, -(T)1, +(T)1);
344 im.set_col(0, inv0 * sign_a);
345 im.set_col(1, inv1 * sign_b);
346 im.set_col(2, inv2 * sign_a);
347 im.set_col(3, inv3 * sign_b);
348 fvec<T, 4> row0(im(0, 0), im(1, 0), im(2, 0), im(3, 0));
349 fvec<T, 4> dot0(m.row(0) * row0);
350 T dot1 = (dot0[0] + dot0[1]) + (dot0[2] + dot0[3]);
351 T inv_det = (T)1 / dot1;
356template <
typename T, cgv::type::u
int32_type N>
357fmat<T,N,N> transpose(
const fmat<T,N,N>& m)
365template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
366fmat<T,N,M> operator * (
const T& s,
const fmat<T,N,M>& m)
372template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
373fvec<T, M> operator * (
const fvec<T, N>& v_row,
const fmat<T, N, M>& m)
376 for (
unsigned i = 0; i < M; i++)
377 r_row(i) = dot(m.col(i), v_row);
382template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
383std::ostream&
operator<<(std::ostream& out,
const fmat<T,N,M>& m)
385 for (
unsigned i=0;i<N;++i) {
386 for(
unsigned j =0;j < M-1;++j)
387 out << m(i,j) <<
" ";
396template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
397std::istream& operator>>(std::istream& in, fmat<T,N,M>& m)
399 for (
unsigned i=0;i<m.nrows();++i)
400 for(
unsigned j =0;j < m.ncols();++j)
406template <
typename T, cgv::type::u
int32_type N,
typename S, cgv::type::u
int32_type M>
407fmat<T, N, M> dyad(
const fvec<T,N>& v,
const fvec<S,M>& w)
410 for (
unsigned i = 0; i < N; i++)
411 for (
unsigned j = 0; j < M; j++)
412 m(i, j) = v(i)*(T)w(j);
418T det(
const fmat<T, 2, 2>& m) {
419 return m(0, 0) * m(1, 1) - m(0, 1) * m(1, 0);
424T det(
const fmat<T, 3, 3>& m) {
425 T a = m(0, 0) * m(1, 1) * m(2, 2) + m(0, 1) * m(1, 2) * m(2, 0) + m(0, 2) * m(1, 0) * m(2, 1);
426 T b = -m(2, 0) * m(1, 1) * m(0, 2) - m(2, 1) * m(1, 2) * m(0, 0) - m(2, 2) * m(1, 0) * m(0, 1);
431template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
432const fmat<T, N, M> lerp(
const fmat<T, N, M>& m1,
const fmat<T, N, M>& m2, T t)
435 for(
unsigned i = 0; i < N; i++)
436 for(
unsigned j = 0; j < M; j++)
437 m(i, j) = ((T)1 - t)*m1(i, j) + t * m2(i, j);
442template <
typename T, cgv::type::u
int32_type N, cgv::type::u
int32_type M>
443const fmat<T, N, M> lerp(
const fmat<T, N, M>& m1,
const fmat<T, N, M>& m2, fmat<T, N, M> t)
446 for(
unsigned i = 0; i < N; i++)
447 for(
unsigned j = 0; j < M; j++)
448 m(i, j) = ((T)1 - t(i, j))*m1(i, j) + t(i, j)*m2(i, j);
complete implementation of method actions that only call one method when entering a node
matrix of fixed size dimensions
const fmat< T, N, M > operator-(const fmat< S, N, M > m2) const
matrix subtraction
const fmat< T, N, L > operator*(const fmat< S, M, L > &m2) const
multiplication with a ncols x M matrix m2
const fvec< T, N > & col(unsigned j) const
read-only reference a column of the matrix as a vector
fmat(const fvec< T1, N > &v, const fvec< T2, M > &w)
construct from outer product of vector v and w
fmat()
standard constructor
const fvec< S, N > mul_dir(const fvec< S, M-1 > &v) const
multiplication with M-1 dimensional direction vector which will be implicitly homogenized
fmat(cgv::type::uint32_type n, cgv::type::uint32_type m, const S *a, bool column_major=true)
creates a matrix from an array a of given dimensions but different type - by default in column major ...
fmat(std::initializer_list< T > components)
construct from individual components using list-initialization syntax
static constexpr unsigned ncols()
number of columns
fmat(std::initializer_list< fvec< T, N > > cols)
construct from column vectors using list-initialization syntax
fmat(const T &c)
construct a matrix with all elements set to c
fvec< T, N > & col(unsigned j)
reference a column of the matrix as a vector
fvec< T, N *M > base_type
base type is a vector with sufficent number of elements
const fmat< T, N, M > operator/(const T &s) const
division by a scalar
const fmat< T, N, M > operator+(const fmat< S, N, M > m2) const
matrix addition
void set_col(unsigned j, const fvec< T, N > &v)
set column j of the matrix to vector v
fmat< T, N, M > & operator+=(const T &s)
in place addition by a scalar
const fmat< T, N, M > operator-() const
negation operator
fvec< T, M > row(unsigned i) const
extract a row from the matrix as a vector, this takes time linear in the number of columns
static constexpr unsigned nrows()
number of rows
T frobenius_norm() const
returns the frobenius norm of matrix m
this_type operator*(const T &s) const
scalar multiplication
const fmat< T, N, M > operator*=(const fmat< S, N, N > &m2)
in place matrix multiplication with a ncols x ncols matrix m2
fmat< T, N, M > this_type
base type is a vector with sufficent number of elements
const fmat< T, N, M > operator+(const T &s)
componentwise addition of a scalar
const fmat< T, N, N > mul_h(const fmat< S, N-1, N-1 > &m2) const
multiplication with (N-1)x(N-1) matrix, assuming the first operand represents an affine or perspectiv...
fmat< T, N, M > & operator=(const fmat< S, N, M > &m)
assignment of a matrix with a different element type
void transpose()
transpose matrix
fmat(cgv::type::uint32_type n, cgv::type::uint32_type m, const T *a, bool column_major=true)
creates a matrix from an array a of given dimensions - by default in column major format - and fills ...
void set_row(unsigned i, const fvec< T, M > &v)
set row i of the matrix to vector v
T trace() const
returns the trace
const fvec< S, N > mul_pos(const fvec< S, M-1 > &v) const
multiplication with M-1 dimensional position vector which will be implicitly homogenized
bool is_square() const
returns true if matrix is a square matrix
fmat< T, N, M > & operator-=(const T &s)
in place substraction of a scalar
void identity()
set identity matrix
fmat(const fmat< S, N, M > &m)
copy constructor for matrix with different element type
T & operator()(unsigned i, unsigned j)
access to the element in the ith row in column j
fmat< T, N, M > & operator/=(const T &s)
in place division by a scalar
A vector with zero based index.
fvec< T, N > & operator*=(const T &s)
in place multiplication with s
fvec< T, N > & operator-=(const T &s)
in place subtraction by scalar s
fvec< T, N > & operator/=(const T &s)
in place division by scalar s
iterator begin()
return an iterator to the first component of *this
T length() const
length of the vector L2-Norm
fvec< T, N > & operator+=(const T &s)
in place addition of a scalar s
T & w()
return fourth component
static cgv::type::uint32_type size()
return number of components
cgv::math::fmat< double, 3, 3 > dmat3
declare type of 3x3 matrices
cgv::math::fmat< float, 3, 3 > mat3
declare type of 3x3 matrices
cgv::math::fmat< double, 4, 4 > dmat4
declare type of 4x4 matrices
cgv::math::fmat< float, 2, 2 > mat2
declare type of 2x2 matrices
cgv::math::fvec< float, 2 > vec2
declare type of 2d single precision floating point vectors
cgv::math::fmat< double, 2, 2 > dmat2
declare type of 2x2 matrices
cgv::math::fvec< float, 3 > vec3
declare type of 3d single precision floating point vectors
cgv::math::fmat< double, 3, 4 > dmat3x4
declare type of 3x4 matrices which are often used to store a pose
cgv::math::fmat< float, 4, 4 > mat4
declare type of 4x4 matrices
cgv::math::fmat< float, 3, 4 > mat3x4
declare type of 3x4 matrices which are often used to store a pose
std::ostream & operator<<(std::ostream &os, const vr_device_info &di)
stream out operator for device infos