1namespace glm
2{
3	// -- Constructors --
4
5#	if GLM_CONFIG_DEFAULTED_FUNCTIONS == GLM_DISABLE
6		template<typename T, qualifier Q>
7		GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat()
8#			if GLM_CONFIG_CTOR_INIT == GLM_CTOR_INITIALIZER_LIST
9				: value{col_type(1, 0, 0), col_type(0, 1, 0)}
10#			endif
11		{
12#			if GLM_CONFIG_CTOR_INIT == GLM_CTOR_INITIALISATION
13				this->value[0] = col_type(1, 0, 0);
14				this->value[1] = col_type(0, 1, 0);
15#			endif
16		}
17#	endif
18
19	template<typename T, qualifier Q>
20	template<qualifier P>
21	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<2, 3, T, P> const& m)
22#		if GLM_HAS_INITIALIZER_LISTS
23			: value{m.value[0], m.value[1]}
24#		endif
25	{
26#		if !GLM_HAS_INITIALIZER_LISTS
27			this->value[0] = m.value[0];
28			this->value[1] = m.value[1];
29#		endif
30	}
31
32	template<typename T, qualifier Q>
33	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(T scalar)
34#		if GLM_HAS_INITIALIZER_LISTS
35			: value{col_type(scalar, 0, 0), col_type(0, scalar, 0)}
36#		endif
37	{
38#		if !GLM_HAS_INITIALIZER_LISTS
39			this->value[0] = col_type(scalar, 0, 0);
40			this->value[1] = col_type(0, scalar, 0);
41#		endif
42	}
43
44	template<typename T, qualifier Q>
45	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat
46	(
47		T x0, T y0, T z0,
48		T x1, T y1, T z1
49	)
50#		if GLM_HAS_INITIALIZER_LISTS
51			: value{col_type(x0, y0, z0), col_type(x1, y1, z1)}
52#		endif
53	{
54#		if !GLM_HAS_INITIALIZER_LISTS
55			this->value[0] = col_type(x0, y0, z0);
56			this->value[1] = col_type(x1, y1, z1);
57#		endif
58	}
59
60	template<typename T, qualifier Q>
61	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(col_type const& v0, col_type const& v1)
62#		if GLM_HAS_INITIALIZER_LISTS
63			: value{col_type(v0), col_type(v1)}
64#		endif
65	{
66#		if !GLM_HAS_INITIALIZER_LISTS
67			this->value[0] = col_type(v0);
68			this->value[1] = col_type(v1);
69#		endif
70	}
71
72	// -- Conversion constructors --
73
74	template<typename T, qualifier Q>
75	template<
76		typename X1, typename Y1, typename Z1,
77		typename X2, typename Y2, typename Z2>
78	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat
79	(
80		X1 x1, Y1 y1, Z1 z1,
81		X2 x2, Y2 y2, Z2 z2
82	)
83#		if GLM_HAS_INITIALIZER_LISTS
84			: value{col_type(x1, y1, z1), col_type(x2, y2, z2)}
85#		endif
86	{
87#		if !GLM_HAS_INITIALIZER_LISTS
88			this->value[0] = col_type(x1, y1, z1);
89			this->value[1] = col_type(x2, y2, z2);
90#		endif
91	}
92
93	template<typename T, qualifier Q>
94	template<typename V1, typename V2>
95	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(vec<3, V1, Q> const& v1, vec<3, V2, Q> const& v2)
96#		if GLM_HAS_INITIALIZER_LISTS
97			: value{col_type(v1), col_type(v2)}
98#		endif
99	{
100#		if !GLM_HAS_INITIALIZER_LISTS
101			this->value[0] = col_type(v1);
102			this->value[1] = col_type(v2);
103#		endif
104	}
105
106	// -- Matrix conversions --
107
108	template<typename T, qualifier Q>
109	template<typename U, qualifier P>
110	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<2, 3, U, P> const& m)
111#		if GLM_HAS_INITIALIZER_LISTS
112			: value{col_type(m[0]), col_type(m[1])}
113#		endif
114	{
115#		if !GLM_HAS_INITIALIZER_LISTS
116			this->value[0] = col_type(m[0]);
117			this->value[1] = col_type(m[1]);
118#		endif
119	}
120
121	template<typename T, qualifier Q>
122	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<2, 2, T, Q> const& m)
123#		if GLM_HAS_INITIALIZER_LISTS
124			: value{col_type(m[0], 0), col_type(m[1], 0)}
125#		endif
126	{
127#		if !GLM_HAS_INITIALIZER_LISTS
128			this->value[0] = col_type(m[0], 0);
129			this->value[1] = col_type(m[1], 0);
130#		endif
131	}
132
133	template<typename T, qualifier Q>
134	GLM_FUNC_QUALIFIER GLM_CONSTEXPR  mat<2, 3, T, Q>::mat(mat<3, 3, T, Q> const& m)
135#		if GLM_HAS_INITIALIZER_LISTS
136			: value{col_type(m[0]), col_type(m[1])}
137#		endif
138	{
139#		if !GLM_HAS_INITIALIZER_LISTS
140			this->value[0] = col_type(m[0]);
141			this->value[1] = col_type(m[1]);
142#		endif
143	}
144
145	template<typename T, qualifier Q>
146	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<4, 4, T, Q> const& m)
147#		if GLM_HAS_INITIALIZER_LISTS
148		: value{col_type(m[0]), col_type(m[1])}
149#		endif
150	{
151#		if !GLM_HAS_INITIALIZER_LISTS
152			this->value[0] = col_type(m[0]);
153			this->value[1] = col_type(m[1]);
154#		endif
155	}
156
157	template<typename T, qualifier Q>
158	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<2, 4, T, Q> const& m)
159#		if GLM_HAS_INITIALIZER_LISTS
160			: value{col_type(m[0]), col_type(m[1])}
161#		endif
162	{
163#		if !GLM_HAS_INITIALIZER_LISTS
164			this->value[0] = col_type(m[0]);
165			this->value[1] = col_type(m[1]);
166#		endif
167	}
168
169	template<typename T, qualifier Q>
170	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<3, 2, T, Q> const& m)
171#		if GLM_HAS_INITIALIZER_LISTS
172			: value{col_type(m[0], 0), col_type(m[1], 0)}
173#		endif
174	{
175#		if !GLM_HAS_INITIALIZER_LISTS
176			this->value[0] = col_type(m[0], 0);
177			this->value[1] = col_type(m[1], 0);
178#		endif
179	}
180
181	template<typename T, qualifier Q>
182	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<3, 4, T, Q> const& m)
183#		if GLM_HAS_INITIALIZER_LISTS
184			: value{col_type(m[0]), col_type(m[1])}
185#		endif
186	{
187#		if !GLM_HAS_INITIALIZER_LISTS
188			this->value[0] = col_type(m[0]);
189			this->value[1] = col_type(m[1]);
190#		endif
191	}
192
193	template<typename T, qualifier Q>
194	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<4, 2, T, Q> const& m)
195#		if GLM_HAS_INITIALIZER_LISTS
196			: value{col_type(m[0], 0), col_type(m[1], 0)}
197#		endif
198	{
199#		if !GLM_HAS_INITIALIZER_LISTS
200			this->value[0] = col_type(m[0], 0);
201			this->value[1] = col_type(m[1], 0);
202#		endif
203	}
204
205	template<typename T, qualifier Q>
206	GLM_FUNC_QUALIFIER GLM_CONSTEXPR mat<2, 3, T, Q>::mat(mat<4, 3, T, Q> const& m)
207#		if GLM_HAS_INITIALIZER_LISTS
208			: value{col_type(m[0]), col_type(m[1])}
209#		endif
210	{
211#		if !GLM_HAS_INITIALIZER_LISTS
212			this->value[0] = col_type(m[0]);
213			this->value[1] = col_type(m[1]);
214#		endif
215	}
216
217	// -- Accesses --
218
219	template<typename T, qualifier Q>
220	GLM_FUNC_QUALIFIER typename mat<2, 3, T, Q>::col_type & mat<2, 3, T, Q>::operator[](typename mat<2, 3, T, Q>::length_type i)
221	{
222		assert(i < this->length());
223		return this->value[i];
224	}
225
226	template<typename T, qualifier Q>
227	GLM_FUNC_QUALIFIER GLM_CONSTEXPR typename mat<2, 3, T, Q>::col_type const& mat<2, 3, T, Q>::operator[](typename mat<2, 3, T, Q>::length_type i) const
228	{
229		assert(i < this->length());
230		return this->value[i];
231	}
232
233	// -- Unary updatable operators --
234
235	template<typename T, qualifier Q>
236	template<typename U>
237	GLM_FUNC_QUALIFIER mat<2, 3, T, Q>& mat<2, 3, T, Q>::operator=(mat<2, 3, U, Q> const& m)
238	{
239		this->value[0] = m[0];
240		this->value[1] = m[1];
241		return *this;
242	}
243
244	template<typename T, qualifier Q>
245	template<typename U>
246	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> & mat<2, 3, T, Q>::operator+=(U s)
247	{
248		this->value[0] += s;
249		this->value[1] += s;
250		return *this;
251	}
252
253	template<typename T, qualifier Q>
254	template<typename U>
255	GLM_FUNC_QUALIFIER mat<2, 3, T, Q>& mat<2, 3, T, Q>::operator+=(mat<2, 3, U, Q> const& m)
256	{
257		this->value[0] += m[0];
258		this->value[1] += m[1];
259		return *this;
260	}
261
262	template<typename T, qualifier Q>
263	template<typename U>
264	GLM_FUNC_QUALIFIER mat<2, 3, T, Q>& mat<2, 3, T, Q>::operator-=(U s)
265	{
266		this->value[0] -= s;
267		this->value[1] -= s;
268		return *this;
269	}
270
271	template<typename T, qualifier Q>
272	template<typename U>
273	GLM_FUNC_QUALIFIER mat<2, 3, T, Q>& mat<2, 3, T, Q>::operator-=(mat<2, 3, U, Q> const& m)
274	{
275		this->value[0] -= m[0];
276		this->value[1] -= m[1];
277		return *this;
278	}
279
280	template<typename T, qualifier Q>
281	template<typename U>
282	GLM_FUNC_QUALIFIER mat<2, 3, T, Q>& mat<2, 3, T, Q>::operator*=(U s)
283	{
284		this->value[0] *= s;
285		this->value[1] *= s;
286		return *this;
287	}
288
289	template<typename T, qualifier Q>
290	template<typename U>
291	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> & mat<2, 3, T, Q>::operator/=(U s)
292	{
293		this->value[0] /= s;
294		this->value[1] /= s;
295		return *this;
296	}
297
298	// -- Increment and decrement operators --
299
300	template<typename T, qualifier Q>
301	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> & mat<2, 3, T, Q>::operator++()
302	{
303		++this->value[0];
304		++this->value[1];
305		return *this;
306	}
307
308	template<typename T, qualifier Q>
309	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> & mat<2, 3, T, Q>::operator--()
310	{
311		--this->value[0];
312		--this->value[1];
313		return *this;
314	}
315
316	template<typename T, qualifier Q>
317	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> mat<2, 3, T, Q>::operator++(int)
318	{
319		mat<2, 3, T, Q> Result(*this);
320		++*this;
321		return Result;
322	}
323
324	template<typename T, qualifier Q>
325	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> mat<2, 3, T, Q>::operator--(int)
326	{
327		mat<2, 3, T, Q> Result(*this);
328		--*this;
329		return Result;
330	}
331
332	// -- Unary arithmetic operators --
333
334	template<typename T, qualifier Q>
335	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator+(mat<2, 3, T, Q> const& m)
336	{
337		return m;
338	}
339
340	template<typename T, qualifier Q>
341	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator-(mat<2, 3, T, Q> const& m)
342	{
343		return mat<2, 3, T, Q>(
344			-m[0],
345			-m[1]);
346	}
347
348	// -- Binary arithmetic operators --
349
350	template<typename T, qualifier Q>
351	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator+(mat<2, 3, T, Q> const& m, T scalar)
352	{
353		return mat<2, 3, T, Q>(
354			m[0] + scalar,
355			m[1] + scalar);
356	}
357
358	template<typename T, qualifier Q>
359	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator+(mat<2, 3, T, Q> const& m1, mat<2, 3, T, Q> const& m2)
360	{
361		return mat<2, 3, T, Q>(
362			m1[0] + m2[0],
363			m1[1] + m2[1]);
364	}
365
366	template<typename T, qualifier Q>
367	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator-(mat<2, 3, T, Q> const& m, T scalar)
368	{
369		return mat<2, 3, T, Q>(
370			m[0] - scalar,
371			m[1] - scalar);
372	}
373
374	template<typename T, qualifier Q>
375	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator-(mat<2, 3, T, Q> const& m1, mat<2, 3, T, Q> const& m2)
376	{
377		return mat<2, 3, T, Q>(
378			m1[0] - m2[0],
379			m1[1] - m2[1]);
380	}
381
382	template<typename T, qualifier Q>
383	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator*(mat<2, 3, T, Q> const& m, T scalar)
384	{
385		return mat<2, 3, T, Q>(
386			m[0] * scalar,
387			m[1] * scalar);
388	}
389
390	template<typename T, qualifier Q>
391	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator*(T scalar, mat<2, 3, T, Q> const& m)
392	{
393		return mat<2, 3, T, Q>(
394			m[0] * scalar,
395			m[1] * scalar);
396	}
397
398	template<typename T, qualifier Q>
399	GLM_FUNC_QUALIFIER typename mat<2, 3, T, Q>::col_type operator*
400	(
401		mat<2, 3, T, Q> const& m,
402		typename mat<2, 3, T, Q>::row_type const& v)
403	{
404		return typename mat<2, 3, T, Q>::col_type(
405			m[0][0] * v.x + m[1][0] * v.y,
406			m[0][1] * v.x + m[1][1] * v.y,
407			m[0][2] * v.x + m[1][2] * v.y);
408	}
409
410	template<typename T, qualifier Q>
411	GLM_FUNC_QUALIFIER typename mat<2, 3, T, Q>::row_type operator*
412	(
413		typename mat<2, 3, T, Q>::col_type const& v,
414		mat<2, 3, T, Q> const& m)
415	{
416		return typename mat<2, 3, T, Q>::row_type(
417			v.x * m[0][0] + v.y * m[0][1] + v.z * m[0][2],
418			v.x * m[1][0] + v.y * m[1][1] + v.z * m[1][2]);
419	}
420
421	template<typename T, qualifier Q>
422	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator*(mat<2, 3, T, Q> const& m1, mat<2, 2, T, Q> const& m2)
423	{
424		return mat<2, 3, T, Q>(
425			m1[0][0] * m2[0][0] + m1[1][0] * m2[0][1],
426			m1[0][1] * m2[0][0] + m1[1][1] * m2[0][1],
427			m1[0][2] * m2[0][0] + m1[1][2] * m2[0][1],
428			m1[0][0] * m2[1][0] + m1[1][0] * m2[1][1],
429			m1[0][1] * m2[1][0] + m1[1][1] * m2[1][1],
430			m1[0][2] * m2[1][0] + m1[1][2] * m2[1][1]);
431	}
432
433	template<typename T, qualifier Q>
434	GLM_FUNC_QUALIFIER mat<3, 3, T, Q> operator*(mat<2, 3, T, Q> const& m1, mat<3, 2, T, Q> const& m2)
435	{
436		T SrcA00 = m1[0][0];
437		T SrcA01 = m1[0][1];
438		T SrcA02 = m1[0][2];
439		T SrcA10 = m1[1][0];
440		T SrcA11 = m1[1][1];
441		T SrcA12 = m1[1][2];
442
443		T SrcB00 = m2[0][0];
444		T SrcB01 = m2[0][1];
445		T SrcB10 = m2[1][0];
446		T SrcB11 = m2[1][1];
447		T SrcB20 = m2[2][0];
448		T SrcB21 = m2[2][1];
449
450		mat<3, 3, T, Q> Result;
451		Result[0][0] = SrcA00 * SrcB00 + SrcA10 * SrcB01;
452		Result[0][1] = SrcA01 * SrcB00 + SrcA11 * SrcB01;
453		Result[0][2] = SrcA02 * SrcB00 + SrcA12 * SrcB01;
454		Result[1][0] = SrcA00 * SrcB10 + SrcA10 * SrcB11;
455		Result[1][1] = SrcA01 * SrcB10 + SrcA11 * SrcB11;
456		Result[1][2] = SrcA02 * SrcB10 + SrcA12 * SrcB11;
457		Result[2][0] = SrcA00 * SrcB20 + SrcA10 * SrcB21;
458		Result[2][1] = SrcA01 * SrcB20 + SrcA11 * SrcB21;
459		Result[2][2] = SrcA02 * SrcB20 + SrcA12 * SrcB21;
460		return Result;
461	}
462
463	template<typename T, qualifier Q>
464	GLM_FUNC_QUALIFIER mat<4, 3, T, Q> operator*(mat<2, 3, T, Q> const& m1, mat<4, 2, T, Q> const& m2)
465	{
466		return mat<4, 3, T, Q>(
467			m1[0][0] * m2[0][0] + m1[1][0] * m2[0][1],
468			m1[0][1] * m2[0][0] + m1[1][1] * m2[0][1],
469			m1[0][2] * m2[0][0] + m1[1][2] * m2[0][1],
470			m1[0][0] * m2[1][0] + m1[1][0] * m2[1][1],
471			m1[0][1] * m2[1][0] + m1[1][1] * m2[1][1],
472			m1[0][2] * m2[1][0] + m1[1][2] * m2[1][1],
473			m1[0][0] * m2[2][0] + m1[1][0] * m2[2][1],
474			m1[0][1] * m2[2][0] + m1[1][1] * m2[2][1],
475			m1[0][2] * m2[2][0] + m1[1][2] * m2[2][1],
476			m1[0][0] * m2[3][0] + m1[1][0] * m2[3][1],
477			m1[0][1] * m2[3][0] + m1[1][1] * m2[3][1],
478			m1[0][2] * m2[3][0] + m1[1][2] * m2[3][1]);
479	}
480
481	template<typename T, qualifier Q>
482	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator/(mat<2, 3, T, Q> const& m, T scalar)
483	{
484		return mat<2, 3, T, Q>(
485			m[0] / scalar,
486			m[1] / scalar);
487	}
488
489	template<typename T, qualifier Q>
490	GLM_FUNC_QUALIFIER mat<2, 3, T, Q> operator/(T scalar, mat<2, 3, T, Q> const& m)
491	{
492		return mat<2, 3, T, Q>(
493			scalar / m[0],
494			scalar / m[1]);
495	}
496
497	// -- Boolean operators --
498
499	template<typename T, qualifier Q>
500	GLM_FUNC_QUALIFIER bool operator==(mat<2, 3, T, Q> const& m1, mat<2, 3, T, Q> const& m2)
501	{
502		return (m1[0] == m2[0]) && (m1[1] == m2[1]);
503	}
504
505	template<typename T, qualifier Q>
506	GLM_FUNC_QUALIFIER bool operator!=(mat<2, 3, T, Q> const& m1, mat<2, 3, T, Q> const& m2)
507	{
508		return (m1[0] != m2[0]) || (m1[1] != m2[1]);
509	}
510} //namespace glm
511