Imported Upstream version 1.64.0
[platform/upstream/boost.git] / boost / qvm / gen / mat_operations4.hpp
1 //Copyright (c) 2008-2016 Emil Dotchevski and Reverge Studios, Inc.\r
2 \r
3 //Distributed under the Boost Software License, Version 1.0. (See accompanying\r
4 //file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)\r
5 \r
6 #ifndef BOOST_QVM_B3124DC843BB8BA61F35A7D938251F\r
7 #define BOOST_QVM_B3124DC843BB8BA61F35A7D938251F\r
8 \r
9 //This file was generated by a program. Do not edit manually.\r
10 \r
11 #include <boost/qvm/assert.hpp>\r
12 #include <boost/qvm/deduce_mat.hpp>\r
13 #include <boost/qvm/deduce_vec.hpp>\r
14 #include <boost/qvm/enable_if.hpp>\r
15 #include <boost/qvm/error.hpp>\r
16 #include <boost/qvm/inline.hpp>\r
17 #include <boost/qvm/mat_traits.hpp>\r
18 #include <boost/qvm/quat_traits.hpp>\r
19 #include <boost/qvm/scalar_traits.hpp>\r
20 #include <boost/qvm/throw_exception.hpp>\r
21 \r
22 namespace\r
23 boost\r
24     {\r
25     namespace\r
26     qvm\r
27         {\r
28         template <class A,class B>\r
29         BOOST_QVM_INLINE_OPERATIONS\r
30         typename lazy_enable_if_c<\r
31             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
32             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
33             deduce_mat2<A,B,4,4> >::type\r
34         operator+( A const & a, B const & b )\r
35             {\r
36             typedef typename deduce_mat2<A,B,4,4>::type R;\r
37             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==4);\r
38             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==4);\r
39             R r;\r
40             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)+mat_traits<B>::template read_element<0,0>(b);\r
41             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)+mat_traits<B>::template read_element<0,1>(b);\r
42             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)+mat_traits<B>::template read_element<0,2>(b);\r
43             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)+mat_traits<B>::template read_element<0,3>(b);\r
44             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)+mat_traits<B>::template read_element<1,0>(b);\r
45             mat_traits<R>::template write_element<1,1>(r)=mat_traits<A>::template read_element<1,1>(a)+mat_traits<B>::template read_element<1,1>(b);\r
46             mat_traits<R>::template write_element<1,2>(r)=mat_traits<A>::template read_element<1,2>(a)+mat_traits<B>::template read_element<1,2>(b);\r
47             mat_traits<R>::template write_element<1,3>(r)=mat_traits<A>::template read_element<1,3>(a)+mat_traits<B>::template read_element<1,3>(b);\r
48             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)+mat_traits<B>::template read_element<2,0>(b);\r
49             mat_traits<R>::template write_element<2,1>(r)=mat_traits<A>::template read_element<2,1>(a)+mat_traits<B>::template read_element<2,1>(b);\r
50             mat_traits<R>::template write_element<2,2>(r)=mat_traits<A>::template read_element<2,2>(a)+mat_traits<B>::template read_element<2,2>(b);\r
51             mat_traits<R>::template write_element<2,3>(r)=mat_traits<A>::template read_element<2,3>(a)+mat_traits<B>::template read_element<2,3>(b);\r
52             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)+mat_traits<B>::template read_element<3,0>(b);\r
53             mat_traits<R>::template write_element<3,1>(r)=mat_traits<A>::template read_element<3,1>(a)+mat_traits<B>::template read_element<3,1>(b);\r
54             mat_traits<R>::template write_element<3,2>(r)=mat_traits<A>::template read_element<3,2>(a)+mat_traits<B>::template read_element<3,2>(b);\r
55             mat_traits<R>::template write_element<3,3>(r)=mat_traits<A>::template read_element<3,3>(a)+mat_traits<B>::template read_element<3,3>(b);\r
56             return r;\r
57             }\r
58 \r
59         namespace\r
60         sfinae\r
61             {\r
62             using ::boost::qvm::operator+;\r
63             }\r
64 \r
65         namespace\r
66         qvm_detail\r
67             {\r
68             template <int R,int C>\r
69             struct plus_mm_defined;\r
70 \r
71             template <>\r
72             struct\r
73             plus_mm_defined<4,4>\r
74                 {\r
75                 static bool const value=true;\r
76                 };\r
77             }\r
78 \r
79         template <class A,class B>\r
80         BOOST_QVM_INLINE_OPERATIONS\r
81         typename lazy_enable_if_c<\r
82             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
83             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
84             deduce_mat2<A,B,4,1> >::type\r
85         operator+( A const & a, B const & b )\r
86             {\r
87             typedef typename deduce_mat2<A,B,4,1>::type R;\r
88             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==4);\r
89             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==1);\r
90             R r;\r
91             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)+mat_traits<B>::template read_element<0,0>(b);\r
92             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)+mat_traits<B>::template read_element<1,0>(b);\r
93             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)+mat_traits<B>::template read_element<2,0>(b);\r
94             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)+mat_traits<B>::template read_element<3,0>(b);\r
95             return r;\r
96             }\r
97 \r
98         namespace\r
99         sfinae\r
100             {\r
101             using ::boost::qvm::operator+;\r
102             }\r
103 \r
104         namespace\r
105         qvm_detail\r
106             {\r
107             template <int R,int C>\r
108             struct plus_mm_defined;\r
109 \r
110             template <>\r
111             struct\r
112             plus_mm_defined<4,1>\r
113                 {\r
114                 static bool const value=true;\r
115                 };\r
116             }\r
117 \r
118         template <class A,class B>\r
119         BOOST_QVM_INLINE_OPERATIONS\r
120         typename lazy_enable_if_c<\r
121             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
122             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
123             deduce_mat2<A,B,1,4> >::type\r
124         operator+( A const & a, B const & b )\r
125             {\r
126             typedef typename deduce_mat2<A,B,1,4>::type R;\r
127             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==1);\r
128             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==4);\r
129             R r;\r
130             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)+mat_traits<B>::template read_element<0,0>(b);\r
131             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)+mat_traits<B>::template read_element<0,1>(b);\r
132             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)+mat_traits<B>::template read_element<0,2>(b);\r
133             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)+mat_traits<B>::template read_element<0,3>(b);\r
134             return r;\r
135             }\r
136 \r
137         namespace\r
138         sfinae\r
139             {\r
140             using ::boost::qvm::operator+;\r
141             }\r
142 \r
143         namespace\r
144         qvm_detail\r
145             {\r
146             template <int R,int C>\r
147             struct plus_mm_defined;\r
148 \r
149             template <>\r
150             struct\r
151             plus_mm_defined<1,4>\r
152                 {\r
153                 static bool const value=true;\r
154                 };\r
155             }\r
156 \r
157         template <class A,class B>\r
158         BOOST_QVM_INLINE_OPERATIONS\r
159         typename lazy_enable_if_c<\r
160             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
161             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
162             deduce_mat2<A,B,4,4> >::type\r
163         operator-( A const & a, B const & b )\r
164             {\r
165             typedef typename deduce_mat2<A,B,4,4>::type R;\r
166             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==4);\r
167             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==4);\r
168             R r;\r
169             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)-mat_traits<B>::template read_element<0,0>(b);\r
170             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)-mat_traits<B>::template read_element<0,1>(b);\r
171             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)-mat_traits<B>::template read_element<0,2>(b);\r
172             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)-mat_traits<B>::template read_element<0,3>(b);\r
173             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)-mat_traits<B>::template read_element<1,0>(b);\r
174             mat_traits<R>::template write_element<1,1>(r)=mat_traits<A>::template read_element<1,1>(a)-mat_traits<B>::template read_element<1,1>(b);\r
175             mat_traits<R>::template write_element<1,2>(r)=mat_traits<A>::template read_element<1,2>(a)-mat_traits<B>::template read_element<1,2>(b);\r
176             mat_traits<R>::template write_element<1,3>(r)=mat_traits<A>::template read_element<1,3>(a)-mat_traits<B>::template read_element<1,3>(b);\r
177             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)-mat_traits<B>::template read_element<2,0>(b);\r
178             mat_traits<R>::template write_element<2,1>(r)=mat_traits<A>::template read_element<2,1>(a)-mat_traits<B>::template read_element<2,1>(b);\r
179             mat_traits<R>::template write_element<2,2>(r)=mat_traits<A>::template read_element<2,2>(a)-mat_traits<B>::template read_element<2,2>(b);\r
180             mat_traits<R>::template write_element<2,3>(r)=mat_traits<A>::template read_element<2,3>(a)-mat_traits<B>::template read_element<2,3>(b);\r
181             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)-mat_traits<B>::template read_element<3,0>(b);\r
182             mat_traits<R>::template write_element<3,1>(r)=mat_traits<A>::template read_element<3,1>(a)-mat_traits<B>::template read_element<3,1>(b);\r
183             mat_traits<R>::template write_element<3,2>(r)=mat_traits<A>::template read_element<3,2>(a)-mat_traits<B>::template read_element<3,2>(b);\r
184             mat_traits<R>::template write_element<3,3>(r)=mat_traits<A>::template read_element<3,3>(a)-mat_traits<B>::template read_element<3,3>(b);\r
185             return r;\r
186             }\r
187 \r
188         namespace\r
189         sfinae\r
190             {\r
191             using ::boost::qvm::operator-;\r
192             }\r
193 \r
194         namespace\r
195         qvm_detail\r
196             {\r
197             template <int R,int C>\r
198             struct minus_mm_defined;\r
199 \r
200             template <>\r
201             struct\r
202             minus_mm_defined<4,4>\r
203                 {\r
204                 static bool const value=true;\r
205                 };\r
206             }\r
207 \r
208         template <class A,class B>\r
209         BOOST_QVM_INLINE_OPERATIONS\r
210         typename lazy_enable_if_c<\r
211             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
212             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
213             deduce_mat2<A,B,4,1> >::type\r
214         operator-( A const & a, B const & b )\r
215             {\r
216             typedef typename deduce_mat2<A,B,4,1>::type R;\r
217             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==4);\r
218             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==1);\r
219             R r;\r
220             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)-mat_traits<B>::template read_element<0,0>(b);\r
221             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)-mat_traits<B>::template read_element<1,0>(b);\r
222             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)-mat_traits<B>::template read_element<2,0>(b);\r
223             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)-mat_traits<B>::template read_element<3,0>(b);\r
224             return r;\r
225             }\r
226 \r
227         namespace\r
228         sfinae\r
229             {\r
230             using ::boost::qvm::operator-;\r
231             }\r
232 \r
233         namespace\r
234         qvm_detail\r
235             {\r
236             template <int R,int C>\r
237             struct minus_mm_defined;\r
238 \r
239             template <>\r
240             struct\r
241             minus_mm_defined<4,1>\r
242                 {\r
243                 static bool const value=true;\r
244                 };\r
245             }\r
246 \r
247         template <class A,class B>\r
248         BOOST_QVM_INLINE_OPERATIONS\r
249         typename lazy_enable_if_c<\r
250             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
251             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
252             deduce_mat2<A,B,1,4> >::type\r
253         operator-( A const & a, B const & b )\r
254             {\r
255             typedef typename deduce_mat2<A,B,1,4>::type R;\r
256             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==1);\r
257             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==4);\r
258             R r;\r
259             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)-mat_traits<B>::template read_element<0,0>(b);\r
260             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)-mat_traits<B>::template read_element<0,1>(b);\r
261             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)-mat_traits<B>::template read_element<0,2>(b);\r
262             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)-mat_traits<B>::template read_element<0,3>(b);\r
263             return r;\r
264             }\r
265 \r
266         namespace\r
267         sfinae\r
268             {\r
269             using ::boost::qvm::operator-;\r
270             }\r
271 \r
272         namespace\r
273         qvm_detail\r
274             {\r
275             template <int R,int C>\r
276             struct minus_mm_defined;\r
277 \r
278             template <>\r
279             struct\r
280             minus_mm_defined<1,4>\r
281                 {\r
282                 static bool const value=true;\r
283                 };\r
284             }\r
285 \r
286         template <class A,class B>\r
287         BOOST_QVM_INLINE_OPERATIONS\r
288         typename enable_if_c<\r
289             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
290             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
291             A &>::type\r
292         operator+=( A & a, B const & b )\r
293             {\r
294             mat_traits<A>::template write_element<0,0>(a)+=mat_traits<B>::template read_element<0,0>(b);\r
295             mat_traits<A>::template write_element<0,1>(a)+=mat_traits<B>::template read_element<0,1>(b);\r
296             mat_traits<A>::template write_element<0,2>(a)+=mat_traits<B>::template read_element<0,2>(b);\r
297             mat_traits<A>::template write_element<0,3>(a)+=mat_traits<B>::template read_element<0,3>(b);\r
298             mat_traits<A>::template write_element<1,0>(a)+=mat_traits<B>::template read_element<1,0>(b);\r
299             mat_traits<A>::template write_element<1,1>(a)+=mat_traits<B>::template read_element<1,1>(b);\r
300             mat_traits<A>::template write_element<1,2>(a)+=mat_traits<B>::template read_element<1,2>(b);\r
301             mat_traits<A>::template write_element<1,3>(a)+=mat_traits<B>::template read_element<1,3>(b);\r
302             mat_traits<A>::template write_element<2,0>(a)+=mat_traits<B>::template read_element<2,0>(b);\r
303             mat_traits<A>::template write_element<2,1>(a)+=mat_traits<B>::template read_element<2,1>(b);\r
304             mat_traits<A>::template write_element<2,2>(a)+=mat_traits<B>::template read_element<2,2>(b);\r
305             mat_traits<A>::template write_element<2,3>(a)+=mat_traits<B>::template read_element<2,3>(b);\r
306             mat_traits<A>::template write_element<3,0>(a)+=mat_traits<B>::template read_element<3,0>(b);\r
307             mat_traits<A>::template write_element<3,1>(a)+=mat_traits<B>::template read_element<3,1>(b);\r
308             mat_traits<A>::template write_element<3,2>(a)+=mat_traits<B>::template read_element<3,2>(b);\r
309             mat_traits<A>::template write_element<3,3>(a)+=mat_traits<B>::template read_element<3,3>(b);\r
310             return a;\r
311             }\r
312 \r
313         namespace\r
314         sfinae\r
315             {\r
316             using ::boost::qvm::operator+=;\r
317             }\r
318 \r
319         namespace\r
320         qvm_detail\r
321             {\r
322             template <int R,int C>\r
323             struct plus_eq_mm_defined;\r
324 \r
325             template <>\r
326             struct\r
327             plus_eq_mm_defined<4,4>\r
328                 {\r
329                 static bool const value=true;\r
330                 };\r
331             }\r
332 \r
333         template <class A,class B>\r
334         BOOST_QVM_INLINE_OPERATIONS\r
335         typename enable_if_c<\r
336             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
337             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
338             A &>::type\r
339         operator+=( A & a, B const & b )\r
340             {\r
341             mat_traits<A>::template write_element<0,0>(a)+=mat_traits<B>::template read_element<0,0>(b);\r
342             mat_traits<A>::template write_element<1,0>(a)+=mat_traits<B>::template read_element<1,0>(b);\r
343             mat_traits<A>::template write_element<2,0>(a)+=mat_traits<B>::template read_element<2,0>(b);\r
344             mat_traits<A>::template write_element<3,0>(a)+=mat_traits<B>::template read_element<3,0>(b);\r
345             return a;\r
346             }\r
347 \r
348         namespace\r
349         sfinae\r
350             {\r
351             using ::boost::qvm::operator+=;\r
352             }\r
353 \r
354         namespace\r
355         qvm_detail\r
356             {\r
357             template <int R,int C>\r
358             struct plus_eq_mm_defined;\r
359 \r
360             template <>\r
361             struct\r
362             plus_eq_mm_defined<4,1>\r
363                 {\r
364                 static bool const value=true;\r
365                 };\r
366             }\r
367 \r
368         template <class A,class B>\r
369         BOOST_QVM_INLINE_OPERATIONS\r
370         typename enable_if_c<\r
371             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
372             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
373             A &>::type\r
374         operator+=( A & a, B const & b )\r
375             {\r
376             mat_traits<A>::template write_element<0,0>(a)+=mat_traits<B>::template read_element<0,0>(b);\r
377             mat_traits<A>::template write_element<0,1>(a)+=mat_traits<B>::template read_element<0,1>(b);\r
378             mat_traits<A>::template write_element<0,2>(a)+=mat_traits<B>::template read_element<0,2>(b);\r
379             mat_traits<A>::template write_element<0,3>(a)+=mat_traits<B>::template read_element<0,3>(b);\r
380             return a;\r
381             }\r
382 \r
383         namespace\r
384         sfinae\r
385             {\r
386             using ::boost::qvm::operator+=;\r
387             }\r
388 \r
389         namespace\r
390         qvm_detail\r
391             {\r
392             template <int R,int C>\r
393             struct plus_eq_mm_defined;\r
394 \r
395             template <>\r
396             struct\r
397             plus_eq_mm_defined<1,4>\r
398                 {\r
399                 static bool const value=true;\r
400                 };\r
401             }\r
402 \r
403         template <class A,class B>\r
404         BOOST_QVM_INLINE_OPERATIONS\r
405         typename enable_if_c<\r
406             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
407             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
408             A &>::type\r
409         operator-=( A & a, B const & b )\r
410             {\r
411             mat_traits<A>::template write_element<0,0>(a)-=mat_traits<B>::template read_element<0,0>(b);\r
412             mat_traits<A>::template write_element<0,1>(a)-=mat_traits<B>::template read_element<0,1>(b);\r
413             mat_traits<A>::template write_element<0,2>(a)-=mat_traits<B>::template read_element<0,2>(b);\r
414             mat_traits<A>::template write_element<0,3>(a)-=mat_traits<B>::template read_element<0,3>(b);\r
415             mat_traits<A>::template write_element<1,0>(a)-=mat_traits<B>::template read_element<1,0>(b);\r
416             mat_traits<A>::template write_element<1,1>(a)-=mat_traits<B>::template read_element<1,1>(b);\r
417             mat_traits<A>::template write_element<1,2>(a)-=mat_traits<B>::template read_element<1,2>(b);\r
418             mat_traits<A>::template write_element<1,3>(a)-=mat_traits<B>::template read_element<1,3>(b);\r
419             mat_traits<A>::template write_element<2,0>(a)-=mat_traits<B>::template read_element<2,0>(b);\r
420             mat_traits<A>::template write_element<2,1>(a)-=mat_traits<B>::template read_element<2,1>(b);\r
421             mat_traits<A>::template write_element<2,2>(a)-=mat_traits<B>::template read_element<2,2>(b);\r
422             mat_traits<A>::template write_element<2,3>(a)-=mat_traits<B>::template read_element<2,3>(b);\r
423             mat_traits<A>::template write_element<3,0>(a)-=mat_traits<B>::template read_element<3,0>(b);\r
424             mat_traits<A>::template write_element<3,1>(a)-=mat_traits<B>::template read_element<3,1>(b);\r
425             mat_traits<A>::template write_element<3,2>(a)-=mat_traits<B>::template read_element<3,2>(b);\r
426             mat_traits<A>::template write_element<3,3>(a)-=mat_traits<B>::template read_element<3,3>(b);\r
427             return a;\r
428             }\r
429 \r
430         namespace\r
431         sfinae\r
432             {\r
433             using ::boost::qvm::operator-=;\r
434             }\r
435 \r
436         namespace\r
437         qvm_detail\r
438             {\r
439             template <int R,int C>\r
440             struct minus_eq_mm_defined;\r
441 \r
442             template <>\r
443             struct\r
444             minus_eq_mm_defined<4,4>\r
445                 {\r
446                 static bool const value=true;\r
447                 };\r
448             }\r
449 \r
450         template <class A,class B>\r
451         BOOST_QVM_INLINE_OPERATIONS\r
452         typename enable_if_c<\r
453             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
454             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
455             A &>::type\r
456         operator-=( A & a, B const & b )\r
457             {\r
458             mat_traits<A>::template write_element<0,0>(a)-=mat_traits<B>::template read_element<0,0>(b);\r
459             mat_traits<A>::template write_element<1,0>(a)-=mat_traits<B>::template read_element<1,0>(b);\r
460             mat_traits<A>::template write_element<2,0>(a)-=mat_traits<B>::template read_element<2,0>(b);\r
461             mat_traits<A>::template write_element<3,0>(a)-=mat_traits<B>::template read_element<3,0>(b);\r
462             return a;\r
463             }\r
464 \r
465         namespace\r
466         sfinae\r
467             {\r
468             using ::boost::qvm::operator-=;\r
469             }\r
470 \r
471         namespace\r
472         qvm_detail\r
473             {\r
474             template <int R,int C>\r
475             struct minus_eq_mm_defined;\r
476 \r
477             template <>\r
478             struct\r
479             minus_eq_mm_defined<4,1>\r
480                 {\r
481                 static bool const value=true;\r
482                 };\r
483             }\r
484 \r
485         template <class A,class B>\r
486         BOOST_QVM_INLINE_OPERATIONS\r
487         typename enable_if_c<\r
488             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
489             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
490             A &>::type\r
491         operator-=( A & a, B const & b )\r
492             {\r
493             mat_traits<A>::template write_element<0,0>(a)-=mat_traits<B>::template read_element<0,0>(b);\r
494             mat_traits<A>::template write_element<0,1>(a)-=mat_traits<B>::template read_element<0,1>(b);\r
495             mat_traits<A>::template write_element<0,2>(a)-=mat_traits<B>::template read_element<0,2>(b);\r
496             mat_traits<A>::template write_element<0,3>(a)-=mat_traits<B>::template read_element<0,3>(b);\r
497             return a;\r
498             }\r
499 \r
500         namespace\r
501         sfinae\r
502             {\r
503             using ::boost::qvm::operator-=;\r
504             }\r
505 \r
506         namespace\r
507         qvm_detail\r
508             {\r
509             template <int R,int C>\r
510             struct minus_eq_mm_defined;\r
511 \r
512             template <>\r
513             struct\r
514             minus_eq_mm_defined<1,4>\r
515                 {\r
516                 static bool const value=true;\r
517                 };\r
518             }\r
519 \r
520         template <class A,class B>\r
521         BOOST_QVM_INLINE_OPERATIONS\r
522         typename lazy_enable_if_c<\r
523             mat_traits<A>::rows==4 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
524             deduce_mat<A> >::type\r
525         operator*( A const & a, B b )\r
526             {\r
527             typedef typename deduce_mat<A>::type R;\r
528             R r;\r
529             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)*b;\r
530             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)*b;\r
531             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)*b;\r
532             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)*b;\r
533             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)*b;\r
534             mat_traits<R>::template write_element<1,1>(r)=mat_traits<A>::template read_element<1,1>(a)*b;\r
535             mat_traits<R>::template write_element<1,2>(r)=mat_traits<A>::template read_element<1,2>(a)*b;\r
536             mat_traits<R>::template write_element<1,3>(r)=mat_traits<A>::template read_element<1,3>(a)*b;\r
537             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)*b;\r
538             mat_traits<R>::template write_element<2,1>(r)=mat_traits<A>::template read_element<2,1>(a)*b;\r
539             mat_traits<R>::template write_element<2,2>(r)=mat_traits<A>::template read_element<2,2>(a)*b;\r
540             mat_traits<R>::template write_element<2,3>(r)=mat_traits<A>::template read_element<2,3>(a)*b;\r
541             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)*b;\r
542             mat_traits<R>::template write_element<3,1>(r)=mat_traits<A>::template read_element<3,1>(a)*b;\r
543             mat_traits<R>::template write_element<3,2>(r)=mat_traits<A>::template read_element<3,2>(a)*b;\r
544             mat_traits<R>::template write_element<3,3>(r)=mat_traits<A>::template read_element<3,3>(a)*b;\r
545             return r;\r
546             }\r
547 \r
548         namespace\r
549         sfinae\r
550             {\r
551             using ::boost::qvm::operator*;\r
552             }\r
553 \r
554         namespace\r
555         qvm_detail\r
556             {\r
557             template <int R,int C>\r
558             struct mul_ms_defined;\r
559 \r
560             template <>\r
561             struct\r
562             mul_ms_defined<4,4>\r
563                 {\r
564                 static bool const value=true;\r
565                 };\r
566             }\r
567 \r
568         template <class A,class B>\r
569         BOOST_QVM_INLINE_OPERATIONS\r
570         typename lazy_enable_if_c<\r
571             is_scalar<A>::value && mat_traits<B>::rows==4 && mat_traits<B>::cols==4,\r
572             deduce_mat<B> >::type\r
573         operator*( A a, B const & b )\r
574             {\r
575             typedef typename deduce_mat<B>::type R;\r
576             R r;\r
577             mat_traits<R>::template write_element<0,0>(r)=a*mat_traits<B>::template read_element<0,0>(b);\r
578             mat_traits<R>::template write_element<0,1>(r)=a*mat_traits<B>::template read_element<0,1>(b);\r
579             mat_traits<R>::template write_element<0,2>(r)=a*mat_traits<B>::template read_element<0,2>(b);\r
580             mat_traits<R>::template write_element<0,3>(r)=a*mat_traits<B>::template read_element<0,3>(b);\r
581             mat_traits<R>::template write_element<1,0>(r)=a*mat_traits<B>::template read_element<1,0>(b);\r
582             mat_traits<R>::template write_element<1,1>(r)=a*mat_traits<B>::template read_element<1,1>(b);\r
583             mat_traits<R>::template write_element<1,2>(r)=a*mat_traits<B>::template read_element<1,2>(b);\r
584             mat_traits<R>::template write_element<1,3>(r)=a*mat_traits<B>::template read_element<1,3>(b);\r
585             mat_traits<R>::template write_element<2,0>(r)=a*mat_traits<B>::template read_element<2,0>(b);\r
586             mat_traits<R>::template write_element<2,1>(r)=a*mat_traits<B>::template read_element<2,1>(b);\r
587             mat_traits<R>::template write_element<2,2>(r)=a*mat_traits<B>::template read_element<2,2>(b);\r
588             mat_traits<R>::template write_element<2,3>(r)=a*mat_traits<B>::template read_element<2,3>(b);\r
589             mat_traits<R>::template write_element<3,0>(r)=a*mat_traits<B>::template read_element<3,0>(b);\r
590             mat_traits<R>::template write_element<3,1>(r)=a*mat_traits<B>::template read_element<3,1>(b);\r
591             mat_traits<R>::template write_element<3,2>(r)=a*mat_traits<B>::template read_element<3,2>(b);\r
592             mat_traits<R>::template write_element<3,3>(r)=a*mat_traits<B>::template read_element<3,3>(b);\r
593             return r;\r
594             }\r
595 \r
596         namespace\r
597         sfinae\r
598             {\r
599             using ::boost::qvm::operator*;\r
600             }\r
601 \r
602         namespace\r
603         qvm_detail\r
604             {\r
605             template <int R,int C>\r
606             struct mul_sm_defined;\r
607 \r
608             template <>\r
609             struct\r
610             mul_sm_defined<4,4>\r
611                 {\r
612                 static bool const value=true;\r
613                 };\r
614             }\r
615 \r
616         template <class A,class B>\r
617         BOOST_QVM_INLINE_OPERATIONS\r
618         typename lazy_enable_if_c<\r
619             mat_traits<A>::rows==4 && mat_traits<A>::cols==1 && is_scalar<B>::value,\r
620             deduce_mat<A> >::type\r
621         operator*( A const & a, B b )\r
622             {\r
623             typedef typename deduce_mat<A>::type R;\r
624             R r;\r
625             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)*b;\r
626             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)*b;\r
627             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)*b;\r
628             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)*b;\r
629             return r;\r
630             }\r
631 \r
632         namespace\r
633         sfinae\r
634             {\r
635             using ::boost::qvm::operator*;\r
636             }\r
637 \r
638         namespace\r
639         qvm_detail\r
640             {\r
641             template <int R,int C>\r
642             struct mul_ms_defined;\r
643 \r
644             template <>\r
645             struct\r
646             mul_ms_defined<4,1>\r
647                 {\r
648                 static bool const value=true;\r
649                 };\r
650             }\r
651 \r
652         template <class A,class B>\r
653         BOOST_QVM_INLINE_OPERATIONS\r
654         typename lazy_enable_if_c<\r
655             is_scalar<A>::value && mat_traits<B>::rows==4 && mat_traits<B>::cols==1,\r
656             deduce_mat<B> >::type\r
657         operator*( A a, B const & b )\r
658             {\r
659             typedef typename deduce_mat<B>::type R;\r
660             R r;\r
661             mat_traits<R>::template write_element<0,0>(r)=a*mat_traits<B>::template read_element<0,0>(b);\r
662             mat_traits<R>::template write_element<1,0>(r)=a*mat_traits<B>::template read_element<1,0>(b);\r
663             mat_traits<R>::template write_element<2,0>(r)=a*mat_traits<B>::template read_element<2,0>(b);\r
664             mat_traits<R>::template write_element<3,0>(r)=a*mat_traits<B>::template read_element<3,0>(b);\r
665             return r;\r
666             }\r
667 \r
668         namespace\r
669         sfinae\r
670             {\r
671             using ::boost::qvm::operator*;\r
672             }\r
673 \r
674         namespace\r
675         qvm_detail\r
676             {\r
677             template <int R,int C>\r
678             struct mul_sm_defined;\r
679 \r
680             template <>\r
681             struct\r
682             mul_sm_defined<4,1>\r
683                 {\r
684                 static bool const value=true;\r
685                 };\r
686             }\r
687 \r
688         template <class A,class B>\r
689         BOOST_QVM_INLINE_OPERATIONS\r
690         typename lazy_enable_if_c<\r
691             mat_traits<A>::rows==1 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
692             deduce_mat<A> >::type\r
693         operator*( A const & a, B b )\r
694             {\r
695             typedef typename deduce_mat<A>::type R;\r
696             R r;\r
697             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)*b;\r
698             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)*b;\r
699             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)*b;\r
700             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)*b;\r
701             return r;\r
702             }\r
703 \r
704         namespace\r
705         sfinae\r
706             {\r
707             using ::boost::qvm::operator*;\r
708             }\r
709 \r
710         namespace\r
711         qvm_detail\r
712             {\r
713             template <int R,int C>\r
714             struct mul_ms_defined;\r
715 \r
716             template <>\r
717             struct\r
718             mul_ms_defined<1,4>\r
719                 {\r
720                 static bool const value=true;\r
721                 };\r
722             }\r
723 \r
724         template <class A,class B>\r
725         BOOST_QVM_INLINE_OPERATIONS\r
726         typename lazy_enable_if_c<\r
727             is_scalar<A>::value && mat_traits<B>::rows==1 && mat_traits<B>::cols==4,\r
728             deduce_mat<B> >::type\r
729         operator*( A a, B const & b )\r
730             {\r
731             typedef typename deduce_mat<B>::type R;\r
732             R r;\r
733             mat_traits<R>::template write_element<0,0>(r)=a*mat_traits<B>::template read_element<0,0>(b);\r
734             mat_traits<R>::template write_element<0,1>(r)=a*mat_traits<B>::template read_element<0,1>(b);\r
735             mat_traits<R>::template write_element<0,2>(r)=a*mat_traits<B>::template read_element<0,2>(b);\r
736             mat_traits<R>::template write_element<0,3>(r)=a*mat_traits<B>::template read_element<0,3>(b);\r
737             return r;\r
738             }\r
739 \r
740         namespace\r
741         sfinae\r
742             {\r
743             using ::boost::qvm::operator*;\r
744             }\r
745 \r
746         namespace\r
747         qvm_detail\r
748             {\r
749             template <int R,int C>\r
750             struct mul_sm_defined;\r
751 \r
752             template <>\r
753             struct\r
754             mul_sm_defined<1,4>\r
755                 {\r
756                 static bool const value=true;\r
757                 };\r
758             }\r
759 \r
760         template <class A,class B>\r
761         BOOST_QVM_INLINE_OPERATIONS\r
762         typename enable_if_c<\r
763             mat_traits<A>::rows==4 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
764             A &>::type\r
765         operator*=( A & a, B b )\r
766             {\r
767             mat_traits<A>::template write_element<0,0>(a)*=b;\r
768             mat_traits<A>::template write_element<0,1>(a)*=b;\r
769             mat_traits<A>::template write_element<0,2>(a)*=b;\r
770             mat_traits<A>::template write_element<0,3>(a)*=b;\r
771             mat_traits<A>::template write_element<1,0>(a)*=b;\r
772             mat_traits<A>::template write_element<1,1>(a)*=b;\r
773             mat_traits<A>::template write_element<1,2>(a)*=b;\r
774             mat_traits<A>::template write_element<1,3>(a)*=b;\r
775             mat_traits<A>::template write_element<2,0>(a)*=b;\r
776             mat_traits<A>::template write_element<2,1>(a)*=b;\r
777             mat_traits<A>::template write_element<2,2>(a)*=b;\r
778             mat_traits<A>::template write_element<2,3>(a)*=b;\r
779             mat_traits<A>::template write_element<3,0>(a)*=b;\r
780             mat_traits<A>::template write_element<3,1>(a)*=b;\r
781             mat_traits<A>::template write_element<3,2>(a)*=b;\r
782             mat_traits<A>::template write_element<3,3>(a)*=b;\r
783             return a;\r
784             }\r
785 \r
786         namespace\r
787         sfinae\r
788             {\r
789             using ::boost::qvm::operator*=;\r
790             }\r
791 \r
792         namespace\r
793         qvm_detail\r
794             {\r
795             template <int R,int C>\r
796             struct mul_eq_ms_defined;\r
797 \r
798             template <>\r
799             struct\r
800             mul_eq_ms_defined<4,4>\r
801                 {\r
802                 static bool const value=true;\r
803                 };\r
804             }\r
805 \r
806         template <class A,class B>\r
807         BOOST_QVM_INLINE_OPERATIONS\r
808         typename enable_if_c<\r
809             mat_traits<A>::rows==4 && mat_traits<A>::cols==1 && is_scalar<B>::value,\r
810             A &>::type\r
811         operator*=( A & a, B b )\r
812             {\r
813             mat_traits<A>::template write_element<0,0>(a)*=b;\r
814             mat_traits<A>::template write_element<1,0>(a)*=b;\r
815             mat_traits<A>::template write_element<2,0>(a)*=b;\r
816             mat_traits<A>::template write_element<3,0>(a)*=b;\r
817             return a;\r
818             }\r
819 \r
820         namespace\r
821         sfinae\r
822             {\r
823             using ::boost::qvm::operator*=;\r
824             }\r
825 \r
826         namespace\r
827         qvm_detail\r
828             {\r
829             template <int R,int C>\r
830             struct mul_eq_ms_defined;\r
831 \r
832             template <>\r
833             struct\r
834             mul_eq_ms_defined<4,1>\r
835                 {\r
836                 static bool const value=true;\r
837                 };\r
838             }\r
839 \r
840         template <class A,class B>\r
841         BOOST_QVM_INLINE_OPERATIONS\r
842         typename enable_if_c<\r
843             mat_traits<A>::rows==1 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
844             A &>::type\r
845         operator*=( A & a, B b )\r
846             {\r
847             mat_traits<A>::template write_element<0,0>(a)*=b;\r
848             mat_traits<A>::template write_element<0,1>(a)*=b;\r
849             mat_traits<A>::template write_element<0,2>(a)*=b;\r
850             mat_traits<A>::template write_element<0,3>(a)*=b;\r
851             return a;\r
852             }\r
853 \r
854         namespace\r
855         sfinae\r
856             {\r
857             using ::boost::qvm::operator*=;\r
858             }\r
859 \r
860         namespace\r
861         qvm_detail\r
862             {\r
863             template <int R,int C>\r
864             struct mul_eq_ms_defined;\r
865 \r
866             template <>\r
867             struct\r
868             mul_eq_ms_defined<1,4>\r
869                 {\r
870                 static bool const value=true;\r
871                 };\r
872             }\r
873 \r
874         template <class A,class B>\r
875         BOOST_QVM_INLINE_OPERATIONS\r
876         typename lazy_enable_if_c<\r
877             mat_traits<A>::rows==4 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
878             deduce_mat<A> >::type\r
879         operator/( A const & a, B b )\r
880             {\r
881             typedef typename deduce_mat<A>::type R;\r
882             R r;\r
883             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)/b;\r
884             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)/b;\r
885             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)/b;\r
886             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)/b;\r
887             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)/b;\r
888             mat_traits<R>::template write_element<1,1>(r)=mat_traits<A>::template read_element<1,1>(a)/b;\r
889             mat_traits<R>::template write_element<1,2>(r)=mat_traits<A>::template read_element<1,2>(a)/b;\r
890             mat_traits<R>::template write_element<1,3>(r)=mat_traits<A>::template read_element<1,3>(a)/b;\r
891             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)/b;\r
892             mat_traits<R>::template write_element<2,1>(r)=mat_traits<A>::template read_element<2,1>(a)/b;\r
893             mat_traits<R>::template write_element<2,2>(r)=mat_traits<A>::template read_element<2,2>(a)/b;\r
894             mat_traits<R>::template write_element<2,3>(r)=mat_traits<A>::template read_element<2,3>(a)/b;\r
895             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)/b;\r
896             mat_traits<R>::template write_element<3,1>(r)=mat_traits<A>::template read_element<3,1>(a)/b;\r
897             mat_traits<R>::template write_element<3,2>(r)=mat_traits<A>::template read_element<3,2>(a)/b;\r
898             mat_traits<R>::template write_element<3,3>(r)=mat_traits<A>::template read_element<3,3>(a)/b;\r
899             return r;\r
900             }\r
901 \r
902         namespace\r
903         sfinae\r
904             {\r
905             using ::boost::qvm::operator/;\r
906             }\r
907 \r
908         namespace\r
909         qvm_detail\r
910             {\r
911             template <int R,int C>\r
912             struct div_ms_defined;\r
913 \r
914             template <>\r
915             struct\r
916             div_ms_defined<4,4>\r
917                 {\r
918                 static bool const value=true;\r
919                 };\r
920             }\r
921 \r
922         template <class A,class B>\r
923         BOOST_QVM_INLINE_OPERATIONS\r
924         typename lazy_enable_if_c<\r
925             is_scalar<A>::value && mat_traits<B>::rows==4 && mat_traits<B>::cols==4,\r
926             deduce_mat<B> >::type\r
927         operator/( A a, B const & b )\r
928             {\r
929             typedef typename deduce_mat<B>::type R;\r
930             R r;\r
931             mat_traits<R>::template write_element<0,0>(r)=a/mat_traits<B>::template read_element<0,0>(b);\r
932             mat_traits<R>::template write_element<0,1>(r)=a/mat_traits<B>::template read_element<0,1>(b);\r
933             mat_traits<R>::template write_element<0,2>(r)=a/mat_traits<B>::template read_element<0,2>(b);\r
934             mat_traits<R>::template write_element<0,3>(r)=a/mat_traits<B>::template read_element<0,3>(b);\r
935             mat_traits<R>::template write_element<1,0>(r)=a/mat_traits<B>::template read_element<1,0>(b);\r
936             mat_traits<R>::template write_element<1,1>(r)=a/mat_traits<B>::template read_element<1,1>(b);\r
937             mat_traits<R>::template write_element<1,2>(r)=a/mat_traits<B>::template read_element<1,2>(b);\r
938             mat_traits<R>::template write_element<1,3>(r)=a/mat_traits<B>::template read_element<1,3>(b);\r
939             mat_traits<R>::template write_element<2,0>(r)=a/mat_traits<B>::template read_element<2,0>(b);\r
940             mat_traits<R>::template write_element<2,1>(r)=a/mat_traits<B>::template read_element<2,1>(b);\r
941             mat_traits<R>::template write_element<2,2>(r)=a/mat_traits<B>::template read_element<2,2>(b);\r
942             mat_traits<R>::template write_element<2,3>(r)=a/mat_traits<B>::template read_element<2,3>(b);\r
943             mat_traits<R>::template write_element<3,0>(r)=a/mat_traits<B>::template read_element<3,0>(b);\r
944             mat_traits<R>::template write_element<3,1>(r)=a/mat_traits<B>::template read_element<3,1>(b);\r
945             mat_traits<R>::template write_element<3,2>(r)=a/mat_traits<B>::template read_element<3,2>(b);\r
946             mat_traits<R>::template write_element<3,3>(r)=a/mat_traits<B>::template read_element<3,3>(b);\r
947             return r;\r
948             }\r
949 \r
950         namespace\r
951         sfinae\r
952             {\r
953             using ::boost::qvm::operator/;\r
954             }\r
955 \r
956         namespace\r
957         qvm_detail\r
958             {\r
959             template <int R,int C>\r
960             struct div_sm_defined;\r
961 \r
962             template <>\r
963             struct\r
964             div_sm_defined<4,4>\r
965                 {\r
966                 static bool const value=true;\r
967                 };\r
968             }\r
969 \r
970         template <class A,class B>\r
971         BOOST_QVM_INLINE_OPERATIONS\r
972         typename lazy_enable_if_c<\r
973             mat_traits<A>::rows==4 && mat_traits<A>::cols==1 && is_scalar<B>::value,\r
974             deduce_mat<A> >::type\r
975         operator/( A const & a, B b )\r
976             {\r
977             typedef typename deduce_mat<A>::type R;\r
978             R r;\r
979             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)/b;\r
980             mat_traits<R>::template write_element<1,0>(r)=mat_traits<A>::template read_element<1,0>(a)/b;\r
981             mat_traits<R>::template write_element<2,0>(r)=mat_traits<A>::template read_element<2,0>(a)/b;\r
982             mat_traits<R>::template write_element<3,0>(r)=mat_traits<A>::template read_element<3,0>(a)/b;\r
983             return r;\r
984             }\r
985 \r
986         namespace\r
987         sfinae\r
988             {\r
989             using ::boost::qvm::operator/;\r
990             }\r
991 \r
992         namespace\r
993         qvm_detail\r
994             {\r
995             template <int R,int C>\r
996             struct div_ms_defined;\r
997 \r
998             template <>\r
999             struct\r
1000             div_ms_defined<4,1>\r
1001                 {\r
1002                 static bool const value=true;\r
1003                 };\r
1004             }\r
1005 \r
1006         template <class A,class B>\r
1007         BOOST_QVM_INLINE_OPERATIONS\r
1008         typename lazy_enable_if_c<\r
1009             is_scalar<A>::value && mat_traits<B>::rows==4 && mat_traits<B>::cols==1,\r
1010             deduce_mat<B> >::type\r
1011         operator/( A a, B const & b )\r
1012             {\r
1013             typedef typename deduce_mat<B>::type R;\r
1014             R r;\r
1015             mat_traits<R>::template write_element<0,0>(r)=a/mat_traits<B>::template read_element<0,0>(b);\r
1016             mat_traits<R>::template write_element<1,0>(r)=a/mat_traits<B>::template read_element<1,0>(b);\r
1017             mat_traits<R>::template write_element<2,0>(r)=a/mat_traits<B>::template read_element<2,0>(b);\r
1018             mat_traits<R>::template write_element<3,0>(r)=a/mat_traits<B>::template read_element<3,0>(b);\r
1019             return r;\r
1020             }\r
1021 \r
1022         namespace\r
1023         sfinae\r
1024             {\r
1025             using ::boost::qvm::operator/;\r
1026             }\r
1027 \r
1028         namespace\r
1029         qvm_detail\r
1030             {\r
1031             template <int R,int C>\r
1032             struct div_sm_defined;\r
1033 \r
1034             template <>\r
1035             struct\r
1036             div_sm_defined<4,1>\r
1037                 {\r
1038                 static bool const value=true;\r
1039                 };\r
1040             }\r
1041 \r
1042         template <class A,class B>\r
1043         BOOST_QVM_INLINE_OPERATIONS\r
1044         typename lazy_enable_if_c<\r
1045             mat_traits<A>::rows==1 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
1046             deduce_mat<A> >::type\r
1047         operator/( A const & a, B b )\r
1048             {\r
1049             typedef typename deduce_mat<A>::type R;\r
1050             R r;\r
1051             mat_traits<R>::template write_element<0,0>(r)=mat_traits<A>::template read_element<0,0>(a)/b;\r
1052             mat_traits<R>::template write_element<0,1>(r)=mat_traits<A>::template read_element<0,1>(a)/b;\r
1053             mat_traits<R>::template write_element<0,2>(r)=mat_traits<A>::template read_element<0,2>(a)/b;\r
1054             mat_traits<R>::template write_element<0,3>(r)=mat_traits<A>::template read_element<0,3>(a)/b;\r
1055             return r;\r
1056             }\r
1057 \r
1058         namespace\r
1059         sfinae\r
1060             {\r
1061             using ::boost::qvm::operator/;\r
1062             }\r
1063 \r
1064         namespace\r
1065         qvm_detail\r
1066             {\r
1067             template <int R,int C>\r
1068             struct div_ms_defined;\r
1069 \r
1070             template <>\r
1071             struct\r
1072             div_ms_defined<1,4>\r
1073                 {\r
1074                 static bool const value=true;\r
1075                 };\r
1076             }\r
1077 \r
1078         template <class A,class B>\r
1079         BOOST_QVM_INLINE_OPERATIONS\r
1080         typename enable_if_c<\r
1081             mat_traits<A>::rows==4 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
1082             A &>::type\r
1083         operator/=( A & a, B b )\r
1084             {\r
1085             mat_traits<A>::template write_element<0,0>(a)/=b;\r
1086             mat_traits<A>::template write_element<0,1>(a)/=b;\r
1087             mat_traits<A>::template write_element<0,2>(a)/=b;\r
1088             mat_traits<A>::template write_element<0,3>(a)/=b;\r
1089             mat_traits<A>::template write_element<1,0>(a)/=b;\r
1090             mat_traits<A>::template write_element<1,1>(a)/=b;\r
1091             mat_traits<A>::template write_element<1,2>(a)/=b;\r
1092             mat_traits<A>::template write_element<1,3>(a)/=b;\r
1093             mat_traits<A>::template write_element<2,0>(a)/=b;\r
1094             mat_traits<A>::template write_element<2,1>(a)/=b;\r
1095             mat_traits<A>::template write_element<2,2>(a)/=b;\r
1096             mat_traits<A>::template write_element<2,3>(a)/=b;\r
1097             mat_traits<A>::template write_element<3,0>(a)/=b;\r
1098             mat_traits<A>::template write_element<3,1>(a)/=b;\r
1099             mat_traits<A>::template write_element<3,2>(a)/=b;\r
1100             mat_traits<A>::template write_element<3,3>(a)/=b;\r
1101             return a;\r
1102             }\r
1103 \r
1104         namespace\r
1105         sfinae\r
1106             {\r
1107             using ::boost::qvm::operator/=;\r
1108             }\r
1109 \r
1110         namespace\r
1111         qvm_detail\r
1112             {\r
1113             template <int R,int C>\r
1114             struct div_eq_ms_defined;\r
1115 \r
1116             template <>\r
1117             struct\r
1118             div_eq_ms_defined<4,4>\r
1119                 {\r
1120                 static bool const value=true;\r
1121                 };\r
1122             }\r
1123 \r
1124         template <class A,class B>\r
1125         BOOST_QVM_INLINE_OPERATIONS\r
1126         typename enable_if_c<\r
1127             mat_traits<A>::rows==4 && mat_traits<A>::cols==1 && is_scalar<B>::value,\r
1128             A &>::type\r
1129         operator/=( A & a, B b )\r
1130             {\r
1131             mat_traits<A>::template write_element<0,0>(a)/=b;\r
1132             mat_traits<A>::template write_element<1,0>(a)/=b;\r
1133             mat_traits<A>::template write_element<2,0>(a)/=b;\r
1134             mat_traits<A>::template write_element<3,0>(a)/=b;\r
1135             return a;\r
1136             }\r
1137 \r
1138         namespace\r
1139         sfinae\r
1140             {\r
1141             using ::boost::qvm::operator/=;\r
1142             }\r
1143 \r
1144         namespace\r
1145         qvm_detail\r
1146             {\r
1147             template <int R,int C>\r
1148             struct div_eq_ms_defined;\r
1149 \r
1150             template <>\r
1151             struct\r
1152             div_eq_ms_defined<4,1>\r
1153                 {\r
1154                 static bool const value=true;\r
1155                 };\r
1156             }\r
1157 \r
1158         template <class A,class B>\r
1159         BOOST_QVM_INLINE_OPERATIONS\r
1160         typename enable_if_c<\r
1161             mat_traits<A>::rows==1 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
1162             A &>::type\r
1163         operator/=( A & a, B b )\r
1164             {\r
1165             mat_traits<A>::template write_element<0,0>(a)/=b;\r
1166             mat_traits<A>::template write_element<0,1>(a)/=b;\r
1167             mat_traits<A>::template write_element<0,2>(a)/=b;\r
1168             mat_traits<A>::template write_element<0,3>(a)/=b;\r
1169             return a;\r
1170             }\r
1171 \r
1172         namespace\r
1173         sfinae\r
1174             {\r
1175             using ::boost::qvm::operator/=;\r
1176             }\r
1177 \r
1178         namespace\r
1179         qvm_detail\r
1180             {\r
1181             template <int R,int C>\r
1182             struct div_eq_ms_defined;\r
1183 \r
1184             template <>\r
1185             struct\r
1186             div_eq_ms_defined<1,4>\r
1187                 {\r
1188                 static bool const value=true;\r
1189                 };\r
1190             }\r
1191 \r
1192         template <class A,class B>\r
1193         BOOST_QVM_INLINE_OPERATIONS\r
1194         typename enable_if_c<\r
1195             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1196             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1197             A &>::type\r
1198         assign( A & a, B const & b )\r
1199             {\r
1200             mat_traits<A>::template write_element<0,0>(a)=mat_traits<B>::template read_element<0,0>(b);\r
1201             mat_traits<A>::template write_element<0,1>(a)=mat_traits<B>::template read_element<0,1>(b);\r
1202             mat_traits<A>::template write_element<0,2>(a)=mat_traits<B>::template read_element<0,2>(b);\r
1203             mat_traits<A>::template write_element<0,3>(a)=mat_traits<B>::template read_element<0,3>(b);\r
1204             mat_traits<A>::template write_element<1,0>(a)=mat_traits<B>::template read_element<1,0>(b);\r
1205             mat_traits<A>::template write_element<1,1>(a)=mat_traits<B>::template read_element<1,1>(b);\r
1206             mat_traits<A>::template write_element<1,2>(a)=mat_traits<B>::template read_element<1,2>(b);\r
1207             mat_traits<A>::template write_element<1,3>(a)=mat_traits<B>::template read_element<1,3>(b);\r
1208             mat_traits<A>::template write_element<2,0>(a)=mat_traits<B>::template read_element<2,0>(b);\r
1209             mat_traits<A>::template write_element<2,1>(a)=mat_traits<B>::template read_element<2,1>(b);\r
1210             mat_traits<A>::template write_element<2,2>(a)=mat_traits<B>::template read_element<2,2>(b);\r
1211             mat_traits<A>::template write_element<2,3>(a)=mat_traits<B>::template read_element<2,3>(b);\r
1212             mat_traits<A>::template write_element<3,0>(a)=mat_traits<B>::template read_element<3,0>(b);\r
1213             mat_traits<A>::template write_element<3,1>(a)=mat_traits<B>::template read_element<3,1>(b);\r
1214             mat_traits<A>::template write_element<3,2>(a)=mat_traits<B>::template read_element<3,2>(b);\r
1215             mat_traits<A>::template write_element<3,3>(a)=mat_traits<B>::template read_element<3,3>(b);\r
1216             return a;\r
1217             }\r
1218 \r
1219         namespace\r
1220         sfinae\r
1221             {\r
1222             using ::boost::qvm::assign;\r
1223             }\r
1224 \r
1225         namespace\r
1226         qvm_detail\r
1227             {\r
1228             template <int R,int C>\r
1229             struct assign_mm_defined;\r
1230 \r
1231             template <>\r
1232             struct\r
1233             assign_mm_defined<4,4>\r
1234                 {\r
1235                 static bool const value=true;\r
1236                 };\r
1237             }\r
1238 \r
1239         template <class A,class B>\r
1240         BOOST_QVM_INLINE_OPERATIONS\r
1241         typename enable_if_c<\r
1242             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1243             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
1244             A &>::type\r
1245         assign( A & a, B const & b )\r
1246             {\r
1247             mat_traits<A>::template write_element<0,0>(a)=mat_traits<B>::template read_element<0,0>(b);\r
1248             mat_traits<A>::template write_element<1,0>(a)=mat_traits<B>::template read_element<1,0>(b);\r
1249             mat_traits<A>::template write_element<2,0>(a)=mat_traits<B>::template read_element<2,0>(b);\r
1250             mat_traits<A>::template write_element<3,0>(a)=mat_traits<B>::template read_element<3,0>(b);\r
1251             return a;\r
1252             }\r
1253 \r
1254         namespace\r
1255         sfinae\r
1256             {\r
1257             using ::boost::qvm::assign;\r
1258             }\r
1259 \r
1260         namespace\r
1261         qvm_detail\r
1262             {\r
1263             template <int R,int C>\r
1264             struct assign_mm_defined;\r
1265 \r
1266             template <>\r
1267             struct\r
1268             assign_mm_defined<4,1>\r
1269                 {\r
1270                 static bool const value=true;\r
1271                 };\r
1272             }\r
1273 \r
1274         template <class A,class B>\r
1275         BOOST_QVM_INLINE_OPERATIONS\r
1276         typename enable_if_c<\r
1277             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
1278             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1279             A &>::type\r
1280         assign( A & a, B const & b )\r
1281             {\r
1282             mat_traits<A>::template write_element<0,0>(a)=mat_traits<B>::template read_element<0,0>(b);\r
1283             mat_traits<A>::template write_element<0,1>(a)=mat_traits<B>::template read_element<0,1>(b);\r
1284             mat_traits<A>::template write_element<0,2>(a)=mat_traits<B>::template read_element<0,2>(b);\r
1285             mat_traits<A>::template write_element<0,3>(a)=mat_traits<B>::template read_element<0,3>(b);\r
1286             return a;\r
1287             }\r
1288 \r
1289         namespace\r
1290         sfinae\r
1291             {\r
1292             using ::boost::qvm::assign;\r
1293             }\r
1294 \r
1295         namespace\r
1296         qvm_detail\r
1297             {\r
1298             template <int R,int C>\r
1299             struct assign_mm_defined;\r
1300 \r
1301             template <>\r
1302             struct\r
1303             assign_mm_defined<1,4>\r
1304                 {\r
1305                 static bool const value=true;\r
1306                 };\r
1307             }\r
1308 \r
1309         template <class R,class A>\r
1310         BOOST_QVM_INLINE_OPERATIONS\r
1311         typename enable_if_c<\r
1312             mat_traits<R>::rows==4 && mat_traits<A>::rows==4 &&\r
1313             mat_traits<R>::cols==4 && mat_traits<A>::cols==4,\r
1314             R>::type\r
1315         convert_to( A const & a )\r
1316             {\r
1317             R r;\r
1318             mat_traits<R>::template write_element<0,0>(r) = mat_traits<A>::template read_element<0,0>(a);\r
1319             mat_traits<R>::template write_element<0,1>(r) = mat_traits<A>::template read_element<0,1>(a);\r
1320             mat_traits<R>::template write_element<0,2>(r) = mat_traits<A>::template read_element<0,2>(a);\r
1321             mat_traits<R>::template write_element<0,3>(r) = mat_traits<A>::template read_element<0,3>(a);\r
1322             mat_traits<R>::template write_element<1,0>(r) = mat_traits<A>::template read_element<1,0>(a);\r
1323             mat_traits<R>::template write_element<1,1>(r) = mat_traits<A>::template read_element<1,1>(a);\r
1324             mat_traits<R>::template write_element<1,2>(r) = mat_traits<A>::template read_element<1,2>(a);\r
1325             mat_traits<R>::template write_element<1,3>(r) = mat_traits<A>::template read_element<1,3>(a);\r
1326             mat_traits<R>::template write_element<2,0>(r) = mat_traits<A>::template read_element<2,0>(a);\r
1327             mat_traits<R>::template write_element<2,1>(r) = mat_traits<A>::template read_element<2,1>(a);\r
1328             mat_traits<R>::template write_element<2,2>(r) = mat_traits<A>::template read_element<2,2>(a);\r
1329             mat_traits<R>::template write_element<2,3>(r) = mat_traits<A>::template read_element<2,3>(a);\r
1330             mat_traits<R>::template write_element<3,0>(r) = mat_traits<A>::template read_element<3,0>(a);\r
1331             mat_traits<R>::template write_element<3,1>(r) = mat_traits<A>::template read_element<3,1>(a);\r
1332             mat_traits<R>::template write_element<3,2>(r) = mat_traits<A>::template read_element<3,2>(a);\r
1333             mat_traits<R>::template write_element<3,3>(r) = mat_traits<A>::template read_element<3,3>(a);\r
1334             return r;\r
1335             }\r
1336 \r
1337         template <class R,class A>\r
1338         BOOST_QVM_INLINE\r
1339         typename enable_if_c<\r
1340             is_mat<R>::value && is_quat<A>::value &&\r
1341             mat_traits<R>::rows==4 && mat_traits<R>::cols==4,\r
1342             R>::type\r
1343         convert_to( A const & q )\r
1344             {\r
1345             typedef typename mat_traits<R>::scalar_type T;\r
1346             T const a=quat_traits<A>::template read_element<0>(q);\r
1347             T const b=quat_traits<A>::template read_element<1>(q);\r
1348             T const c=quat_traits<A>::template read_element<2>(q);\r
1349             T const d=quat_traits<A>::template read_element<3>(q);\r
1350             T const bb = b*b;\r
1351             T const cc = c*c;\r
1352             T const dd = d*d;\r
1353             T const bc = b*c;\r
1354             T const bd = b*d;\r
1355             T const cd = c*d;\r
1356             T const ab = a*b;\r
1357             T const ac = a*c;\r
1358             T const ad = a*d;\r
1359             T const zero = scalar_traits<T>::value(0);\r
1360             T const one = scalar_traits<T>::value(1);\r
1361             T const two = one+one;\r
1362             R r;\r
1363             mat_traits<R>::template write_element<0,0>(r) = one - two*(cc+dd);\r
1364             mat_traits<R>::template write_element<0,1>(r) = two*(bc-ad);\r
1365             mat_traits<R>::template write_element<0,2>(r) = two*(bd+ac);\r
1366             mat_traits<R>::template write_element<0,3>(r) = zero;\r
1367             mat_traits<R>::template write_element<1,0>(r) = two*(bc+ad);\r
1368             mat_traits<R>::template write_element<1,1>(r) = one - two*(bb+dd);\r
1369             mat_traits<R>::template write_element<1,2>(r) = two*(cd-ab);\r
1370             mat_traits<R>::template write_element<1,3>(r) = zero;\r
1371             mat_traits<R>::template write_element<2,0>(r) = two*(bd-ac);\r
1372             mat_traits<R>::template write_element<2,1>(r) = two*(cd+ab);\r
1373             mat_traits<R>::template write_element<2,2>(r) = one - two*(bb+cc);\r
1374             mat_traits<R>::template write_element<2,3>(r) = zero;\r
1375             mat_traits<R>::template write_element<3,0>(r) = zero;\r
1376             mat_traits<R>::template write_element<3,1>(r) = zero;\r
1377             mat_traits<R>::template write_element<3,2>(r) = zero;\r
1378             mat_traits<R>::template write_element<3,3>(r) = one;\r
1379             return r;\r
1380             }\r
1381 \r
1382         namespace\r
1383         sfinae\r
1384             {\r
1385             using ::boost::qvm::convert_to;\r
1386             }\r
1387 \r
1388         namespace\r
1389         qvm_detail\r
1390             {\r
1391             template <int R,int C>\r
1392             struct convert_to_m_defined;\r
1393 \r
1394             template <>\r
1395             struct\r
1396             convert_to_m_defined<4,4>\r
1397                 {\r
1398                 static bool const value=true;\r
1399                 };\r
1400             }\r
1401 \r
1402         template <class R,class A>\r
1403         BOOST_QVM_INLINE_OPERATIONS\r
1404         typename enable_if_c<\r
1405             mat_traits<R>::rows==4 && mat_traits<A>::rows==4 &&\r
1406             mat_traits<R>::cols==1 && mat_traits<A>::cols==1,\r
1407             R>::type\r
1408         convert_to( A const & a )\r
1409             {\r
1410             R r;\r
1411             mat_traits<R>::template write_element<0,0>(r) = mat_traits<A>::template read_element<0,0>(a);\r
1412             mat_traits<R>::template write_element<1,0>(r) = mat_traits<A>::template read_element<1,0>(a);\r
1413             mat_traits<R>::template write_element<2,0>(r) = mat_traits<A>::template read_element<2,0>(a);\r
1414             mat_traits<R>::template write_element<3,0>(r) = mat_traits<A>::template read_element<3,0>(a);\r
1415             return r;\r
1416             }\r
1417 \r
1418         namespace\r
1419         sfinae\r
1420             {\r
1421             using ::boost::qvm::convert_to;\r
1422             }\r
1423 \r
1424         namespace\r
1425         qvm_detail\r
1426             {\r
1427             template <int R,int C>\r
1428             struct convert_to_m_defined;\r
1429 \r
1430             template <>\r
1431             struct\r
1432             convert_to_m_defined<4,1>\r
1433                 {\r
1434                 static bool const value=true;\r
1435                 };\r
1436             }\r
1437 \r
1438         template <class R,class A>\r
1439         BOOST_QVM_INLINE_OPERATIONS\r
1440         typename enable_if_c<\r
1441             mat_traits<R>::rows==1 && mat_traits<A>::rows==1 &&\r
1442             mat_traits<R>::cols==4 && mat_traits<A>::cols==4,\r
1443             R>::type\r
1444         convert_to( A const & a )\r
1445             {\r
1446             R r;\r
1447             mat_traits<R>::template write_element<0,0>(r) = mat_traits<A>::template read_element<0,0>(a);\r
1448             mat_traits<R>::template write_element<0,1>(r) = mat_traits<A>::template read_element<0,1>(a);\r
1449             mat_traits<R>::template write_element<0,2>(r) = mat_traits<A>::template read_element<0,2>(a);\r
1450             mat_traits<R>::template write_element<0,3>(r) = mat_traits<A>::template read_element<0,3>(a);\r
1451             return r;\r
1452             }\r
1453 \r
1454         namespace\r
1455         sfinae\r
1456             {\r
1457             using ::boost::qvm::convert_to;\r
1458             }\r
1459 \r
1460         namespace\r
1461         qvm_detail\r
1462             {\r
1463             template <int R,int C>\r
1464             struct convert_to_m_defined;\r
1465 \r
1466             template <>\r
1467             struct\r
1468             convert_to_m_defined<1,4>\r
1469                 {\r
1470                 static bool const value=true;\r
1471                 };\r
1472             }\r
1473 \r
1474         template <class A,class B>\r
1475         BOOST_QVM_INLINE_OPERATIONS\r
1476         typename enable_if_c<\r
1477             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1478             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1479             bool>::type\r
1480         operator==( A const & a, B const & b )\r
1481             {\r
1482             return\r
1483                 mat_traits<A>::template read_element<0,0>(a)==mat_traits<B>::template read_element<0,0>(b) &&\r
1484                 mat_traits<A>::template read_element<0,1>(a)==mat_traits<B>::template read_element<0,1>(b) &&\r
1485                 mat_traits<A>::template read_element<0,2>(a)==mat_traits<B>::template read_element<0,2>(b) &&\r
1486                 mat_traits<A>::template read_element<0,3>(a)==mat_traits<B>::template read_element<0,3>(b) &&\r
1487                 mat_traits<A>::template read_element<1,0>(a)==mat_traits<B>::template read_element<1,0>(b) &&\r
1488                 mat_traits<A>::template read_element<1,1>(a)==mat_traits<B>::template read_element<1,1>(b) &&\r
1489                 mat_traits<A>::template read_element<1,2>(a)==mat_traits<B>::template read_element<1,2>(b) &&\r
1490                 mat_traits<A>::template read_element<1,3>(a)==mat_traits<B>::template read_element<1,3>(b) &&\r
1491                 mat_traits<A>::template read_element<2,0>(a)==mat_traits<B>::template read_element<2,0>(b) &&\r
1492                 mat_traits<A>::template read_element<2,1>(a)==mat_traits<B>::template read_element<2,1>(b) &&\r
1493                 mat_traits<A>::template read_element<2,2>(a)==mat_traits<B>::template read_element<2,2>(b) &&\r
1494                 mat_traits<A>::template read_element<2,3>(a)==mat_traits<B>::template read_element<2,3>(b) &&\r
1495                 mat_traits<A>::template read_element<3,0>(a)==mat_traits<B>::template read_element<3,0>(b) &&\r
1496                 mat_traits<A>::template read_element<3,1>(a)==mat_traits<B>::template read_element<3,1>(b) &&\r
1497                 mat_traits<A>::template read_element<3,2>(a)==mat_traits<B>::template read_element<3,2>(b) &&\r
1498                 mat_traits<A>::template read_element<3,3>(a)==mat_traits<B>::template read_element<3,3>(b);\r
1499             }\r
1500 \r
1501         namespace\r
1502         sfinae\r
1503             {\r
1504             using ::boost::qvm::operator==;\r
1505             }\r
1506 \r
1507         namespace\r
1508         qvm_detail\r
1509             {\r
1510             template <int R,int C>\r
1511             struct eq_mm_defined;\r
1512 \r
1513             template <>\r
1514             struct\r
1515             eq_mm_defined<4,4>\r
1516                 {\r
1517                 static bool const value=true;\r
1518                 };\r
1519             }\r
1520 \r
1521         template <class A,class B>\r
1522         BOOST_QVM_INLINE_OPERATIONS\r
1523         typename enable_if_c<\r
1524             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1525             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
1526             bool>::type\r
1527         operator==( A const & a, B const & b )\r
1528             {\r
1529             return\r
1530                 mat_traits<A>::template read_element<0,0>(a)==mat_traits<B>::template read_element<0,0>(b) &&\r
1531                 mat_traits<A>::template read_element<1,0>(a)==mat_traits<B>::template read_element<1,0>(b) &&\r
1532                 mat_traits<A>::template read_element<2,0>(a)==mat_traits<B>::template read_element<2,0>(b) &&\r
1533                 mat_traits<A>::template read_element<3,0>(a)==mat_traits<B>::template read_element<3,0>(b);\r
1534             }\r
1535 \r
1536         namespace\r
1537         sfinae\r
1538             {\r
1539             using ::boost::qvm::operator==;\r
1540             }\r
1541 \r
1542         namespace\r
1543         qvm_detail\r
1544             {\r
1545             template <int R,int C>\r
1546             struct eq_mm_defined;\r
1547 \r
1548             template <>\r
1549             struct\r
1550             eq_mm_defined<4,1>\r
1551                 {\r
1552                 static bool const value=true;\r
1553                 };\r
1554             }\r
1555 \r
1556         template <class A,class B>\r
1557         BOOST_QVM_INLINE_OPERATIONS\r
1558         typename enable_if_c<\r
1559             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
1560             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1561             bool>::type\r
1562         operator==( A const & a, B const & b )\r
1563             {\r
1564             return\r
1565                 mat_traits<A>::template read_element<0,0>(a)==mat_traits<B>::template read_element<0,0>(b) &&\r
1566                 mat_traits<A>::template read_element<0,1>(a)==mat_traits<B>::template read_element<0,1>(b) &&\r
1567                 mat_traits<A>::template read_element<0,2>(a)==mat_traits<B>::template read_element<0,2>(b) &&\r
1568                 mat_traits<A>::template read_element<0,3>(a)==mat_traits<B>::template read_element<0,3>(b);\r
1569             }\r
1570 \r
1571         namespace\r
1572         sfinae\r
1573             {\r
1574             using ::boost::qvm::operator==;\r
1575             }\r
1576 \r
1577         namespace\r
1578         qvm_detail\r
1579             {\r
1580             template <int R,int C>\r
1581             struct eq_mm_defined;\r
1582 \r
1583             template <>\r
1584             struct\r
1585             eq_mm_defined<1,4>\r
1586                 {\r
1587                 static bool const value=true;\r
1588                 };\r
1589             }\r
1590 \r
1591         template <class A,class B>\r
1592         BOOST_QVM_INLINE_OPERATIONS\r
1593         typename enable_if_c<\r
1594             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1595             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1596             bool>::type\r
1597         operator!=( A const & a, B const & b )\r
1598             {\r
1599             return\r
1600                 !(mat_traits<A>::template read_element<0,0>(a)==mat_traits<B>::template read_element<0,0>(b)) ||\r
1601                 !(mat_traits<A>::template read_element<0,1>(a)==mat_traits<B>::template read_element<0,1>(b)) ||\r
1602                 !(mat_traits<A>::template read_element<0,2>(a)==mat_traits<B>::template read_element<0,2>(b)) ||\r
1603                 !(mat_traits<A>::template read_element<0,3>(a)==mat_traits<B>::template read_element<0,3>(b)) ||\r
1604                 !(mat_traits<A>::template read_element<1,0>(a)==mat_traits<B>::template read_element<1,0>(b)) ||\r
1605                 !(mat_traits<A>::template read_element<1,1>(a)==mat_traits<B>::template read_element<1,1>(b)) ||\r
1606                 !(mat_traits<A>::template read_element<1,2>(a)==mat_traits<B>::template read_element<1,2>(b)) ||\r
1607                 !(mat_traits<A>::template read_element<1,3>(a)==mat_traits<B>::template read_element<1,3>(b)) ||\r
1608                 !(mat_traits<A>::template read_element<2,0>(a)==mat_traits<B>::template read_element<2,0>(b)) ||\r
1609                 !(mat_traits<A>::template read_element<2,1>(a)==mat_traits<B>::template read_element<2,1>(b)) ||\r
1610                 !(mat_traits<A>::template read_element<2,2>(a)==mat_traits<B>::template read_element<2,2>(b)) ||\r
1611                 !(mat_traits<A>::template read_element<2,3>(a)==mat_traits<B>::template read_element<2,3>(b)) ||\r
1612                 !(mat_traits<A>::template read_element<3,0>(a)==mat_traits<B>::template read_element<3,0>(b)) ||\r
1613                 !(mat_traits<A>::template read_element<3,1>(a)==mat_traits<B>::template read_element<3,1>(b)) ||\r
1614                 !(mat_traits<A>::template read_element<3,2>(a)==mat_traits<B>::template read_element<3,2>(b)) ||\r
1615                 !(mat_traits<A>::template read_element<3,3>(a)==mat_traits<B>::template read_element<3,3>(b));\r
1616             }\r
1617 \r
1618         namespace\r
1619         sfinae\r
1620             {\r
1621             using ::boost::qvm::operator!=;\r
1622             }\r
1623 \r
1624         namespace\r
1625         qvm_detail\r
1626             {\r
1627             template <int R,int C>\r
1628             struct neq_mm_defined;\r
1629 \r
1630             template <>\r
1631             struct\r
1632             neq_mm_defined<4,4>\r
1633                 {\r
1634                 static bool const value=true;\r
1635                 };\r
1636             }\r
1637 \r
1638         template <class A,class B>\r
1639         BOOST_QVM_INLINE_OPERATIONS\r
1640         typename enable_if_c<\r
1641             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1642             mat_traits<A>::cols==1 && mat_traits<B>::cols==1,\r
1643             bool>::type\r
1644         operator!=( A const & a, B const & b )\r
1645             {\r
1646             return\r
1647                 !(mat_traits<A>::template read_element<0,0>(a)==mat_traits<B>::template read_element<0,0>(b)) ||\r
1648                 !(mat_traits<A>::template read_element<1,0>(a)==mat_traits<B>::template read_element<1,0>(b)) ||\r
1649                 !(mat_traits<A>::template read_element<2,0>(a)==mat_traits<B>::template read_element<2,0>(b)) ||\r
1650                 !(mat_traits<A>::template read_element<3,0>(a)==mat_traits<B>::template read_element<3,0>(b));\r
1651             }\r
1652 \r
1653         namespace\r
1654         sfinae\r
1655             {\r
1656             using ::boost::qvm::operator!=;\r
1657             }\r
1658 \r
1659         namespace\r
1660         qvm_detail\r
1661             {\r
1662             template <int R,int C>\r
1663             struct neq_mm_defined;\r
1664 \r
1665             template <>\r
1666             struct\r
1667             neq_mm_defined<4,1>\r
1668                 {\r
1669                 static bool const value=true;\r
1670                 };\r
1671             }\r
1672 \r
1673         template <class A,class B>\r
1674         BOOST_QVM_INLINE_OPERATIONS\r
1675         typename enable_if_c<\r
1676             mat_traits<A>::rows==1 && mat_traits<B>::rows==1 &&\r
1677             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1678             bool>::type\r
1679         operator!=( A const & a, B const & b )\r
1680             {\r
1681             return\r
1682                 !(mat_traits<A>::template read_element<0,0>(a)==mat_traits<B>::template read_element<0,0>(b)) ||\r
1683                 !(mat_traits<A>::template read_element<0,1>(a)==mat_traits<B>::template read_element<0,1>(b)) ||\r
1684                 !(mat_traits<A>::template read_element<0,2>(a)==mat_traits<B>::template read_element<0,2>(b)) ||\r
1685                 !(mat_traits<A>::template read_element<0,3>(a)==mat_traits<B>::template read_element<0,3>(b));\r
1686             }\r
1687 \r
1688         namespace\r
1689         sfinae\r
1690             {\r
1691             using ::boost::qvm::operator!=;\r
1692             }\r
1693 \r
1694         namespace\r
1695         qvm_detail\r
1696             {\r
1697             template <int R,int C>\r
1698             struct neq_mm_defined;\r
1699 \r
1700             template <>\r
1701             struct\r
1702             neq_mm_defined<1,4>\r
1703                 {\r
1704                 static bool const value=true;\r
1705                 };\r
1706             }\r
1707 \r
1708         template <class A>\r
1709         BOOST_QVM_INLINE_OPERATIONS\r
1710         typename lazy_enable_if_c<\r
1711             mat_traits<A>::rows==4 && mat_traits<A>::cols==4,\r
1712             deduce_mat<A> >::type\r
1713         operator-( A const & a )\r
1714             {\r
1715             typedef typename deduce_mat<A>::type R;\r
1716             R r;\r
1717             mat_traits<R>::template write_element<0,0>(r)=-mat_traits<A>::template read_element<0,0>(a);\r
1718             mat_traits<R>::template write_element<0,1>(r)=-mat_traits<A>::template read_element<0,1>(a);\r
1719             mat_traits<R>::template write_element<0,2>(r)=-mat_traits<A>::template read_element<0,2>(a);\r
1720             mat_traits<R>::template write_element<0,3>(r)=-mat_traits<A>::template read_element<0,3>(a);\r
1721             mat_traits<R>::template write_element<1,0>(r)=-mat_traits<A>::template read_element<1,0>(a);\r
1722             mat_traits<R>::template write_element<1,1>(r)=-mat_traits<A>::template read_element<1,1>(a);\r
1723             mat_traits<R>::template write_element<1,2>(r)=-mat_traits<A>::template read_element<1,2>(a);\r
1724             mat_traits<R>::template write_element<1,3>(r)=-mat_traits<A>::template read_element<1,3>(a);\r
1725             mat_traits<R>::template write_element<2,0>(r)=-mat_traits<A>::template read_element<2,0>(a);\r
1726             mat_traits<R>::template write_element<2,1>(r)=-mat_traits<A>::template read_element<2,1>(a);\r
1727             mat_traits<R>::template write_element<2,2>(r)=-mat_traits<A>::template read_element<2,2>(a);\r
1728             mat_traits<R>::template write_element<2,3>(r)=-mat_traits<A>::template read_element<2,3>(a);\r
1729             mat_traits<R>::template write_element<3,0>(r)=-mat_traits<A>::template read_element<3,0>(a);\r
1730             mat_traits<R>::template write_element<3,1>(r)=-mat_traits<A>::template read_element<3,1>(a);\r
1731             mat_traits<R>::template write_element<3,2>(r)=-mat_traits<A>::template read_element<3,2>(a);\r
1732             mat_traits<R>::template write_element<3,3>(r)=-mat_traits<A>::template read_element<3,3>(a);\r
1733             return r;\r
1734             }\r
1735 \r
1736         namespace\r
1737         sfinae\r
1738             {\r
1739             using ::boost::qvm::operator-;\r
1740             }\r
1741 \r
1742         namespace\r
1743         qvm_detail\r
1744             {\r
1745             template <int R,int C>\r
1746             struct minus_m_defined;\r
1747 \r
1748             template <>\r
1749             struct\r
1750             minus_m_defined<4,4>\r
1751                 {\r
1752                 static bool const value=true;\r
1753                 };\r
1754             }\r
1755 \r
1756         template <class A>\r
1757         BOOST_QVM_INLINE_OPERATIONS\r
1758         typename lazy_enable_if_c<\r
1759             mat_traits<A>::rows==4 && mat_traits<A>::cols==1,\r
1760             deduce_mat<A> >::type\r
1761         operator-( A const & a )\r
1762             {\r
1763             typedef typename deduce_mat<A>::type R;\r
1764             R r;\r
1765             mat_traits<R>::template write_element<0,0>(r)=-mat_traits<A>::template read_element<0,0>(a);\r
1766             mat_traits<R>::template write_element<1,0>(r)=-mat_traits<A>::template read_element<1,0>(a);\r
1767             mat_traits<R>::template write_element<2,0>(r)=-mat_traits<A>::template read_element<2,0>(a);\r
1768             mat_traits<R>::template write_element<3,0>(r)=-mat_traits<A>::template read_element<3,0>(a);\r
1769             return r;\r
1770             }\r
1771 \r
1772         namespace\r
1773         sfinae\r
1774             {\r
1775             using ::boost::qvm::operator-;\r
1776             }\r
1777 \r
1778         namespace\r
1779         qvm_detail\r
1780             {\r
1781             template <int R,int C>\r
1782             struct minus_m_defined;\r
1783 \r
1784             template <>\r
1785             struct\r
1786             minus_m_defined<4,1>\r
1787                 {\r
1788                 static bool const value=true;\r
1789                 };\r
1790             }\r
1791 \r
1792         template <class A>\r
1793         BOOST_QVM_INLINE_OPERATIONS\r
1794         typename lazy_enable_if_c<\r
1795             mat_traits<A>::rows==1 && mat_traits<A>::cols==4,\r
1796             deduce_mat<A> >::type\r
1797         operator-( A const & a )\r
1798             {\r
1799             typedef typename deduce_mat<A>::type R;\r
1800             R r;\r
1801             mat_traits<R>::template write_element<0,0>(r)=-mat_traits<A>::template read_element<0,0>(a);\r
1802             mat_traits<R>::template write_element<0,1>(r)=-mat_traits<A>::template read_element<0,1>(a);\r
1803             mat_traits<R>::template write_element<0,2>(r)=-mat_traits<A>::template read_element<0,2>(a);\r
1804             mat_traits<R>::template write_element<0,3>(r)=-mat_traits<A>::template read_element<0,3>(a);\r
1805             return r;\r
1806             }\r
1807 \r
1808         namespace\r
1809         sfinae\r
1810             {\r
1811             using ::boost::qvm::operator-;\r
1812             }\r
1813 \r
1814         namespace\r
1815         qvm_detail\r
1816             {\r
1817             template <int R,int C>\r
1818             struct minus_m_defined;\r
1819 \r
1820             template <>\r
1821             struct\r
1822             minus_m_defined<1,4>\r
1823                 {\r
1824                 static bool const value=true;\r
1825                 };\r
1826             }\r
1827 \r
1828         template <class A>\r
1829         BOOST_QVM_INLINE_OPERATIONS\r
1830         typename enable_if_c<\r
1831             mat_traits<A>::rows==4 && mat_traits<A>::cols==4,\r
1832             typename mat_traits<A>::scalar_type>::type\r
1833         determinant( A const & a )\r
1834             {\r
1835             typedef typename mat_traits<A>::scalar_type T;\r
1836             T const a00=mat_traits<A>::template read_element<0,0>(a);\r
1837             T const a01=mat_traits<A>::template read_element<0,1>(a);\r
1838             T const a02=mat_traits<A>::template read_element<0,2>(a);\r
1839             T const a03=mat_traits<A>::template read_element<0,3>(a);\r
1840             T const a10=mat_traits<A>::template read_element<1,0>(a);\r
1841             T const a11=mat_traits<A>::template read_element<1,1>(a);\r
1842             T const a12=mat_traits<A>::template read_element<1,2>(a);\r
1843             T const a13=mat_traits<A>::template read_element<1,3>(a);\r
1844             T const a20=mat_traits<A>::template read_element<2,0>(a);\r
1845             T const a21=mat_traits<A>::template read_element<2,1>(a);\r
1846             T const a22=mat_traits<A>::template read_element<2,2>(a);\r
1847             T const a23=mat_traits<A>::template read_element<2,3>(a);\r
1848             T const a30=mat_traits<A>::template read_element<3,0>(a);\r
1849             T const a31=mat_traits<A>::template read_element<3,1>(a);\r
1850             T const a32=mat_traits<A>::template read_element<3,2>(a);\r
1851             T const a33=mat_traits<A>::template read_element<3,3>(a);\r
1852             T det=(a00*(a11*(a22*a33-a23*a32)-a12*(a21*a33-a23*a31)+a13*(a21*a32-a22*a31))-a01*(a10*(a22*a33-a23*a32)-a12*(a20*a33-a23*a30)+a13*(a20*a32-a22*a30))+a02*(a10*(a21*a33-a23*a31)-a11*(a20*a33-a23*a30)+a13*(a20*a31-a21*a30))-a03*(a10*(a21*a32-a22*a31)-a11*(a20*a32-a22*a30)+a12*(a20*a31-a21*a30)));\r
1853             return det;\r
1854             }\r
1855 \r
1856         namespace\r
1857         sfinae\r
1858             {\r
1859             using ::boost::qvm::determinant;\r
1860             }\r
1861 \r
1862         namespace\r
1863         qvm_detail\r
1864             {\r
1865             template <int D>\r
1866             struct determinant_defined;\r
1867 \r
1868             template <>\r
1869             struct\r
1870             determinant_defined<4>\r
1871                 {\r
1872                 static bool const value=true;\r
1873                 };\r
1874             }\r
1875 \r
1876         template <class A,class B>\r
1877         BOOST_QVM_INLINE_OPERATIONS\r
1878         typename lazy_enable_if_c<\r
1879             mat_traits<A>::rows==4 && mat_traits<A>::cols==4 && is_scalar<B>::value,\r
1880             deduce_mat<A> >::type\r
1881         inverse( A const & a, B det )\r
1882             {\r
1883             typedef typename mat_traits<A>::scalar_type T;\r
1884             BOOST_QVM_ASSERT(det!=scalar_traits<B>::value(0));\r
1885             T const a00=mat_traits<A>::template read_element<0,0>(a);\r
1886             T const a01=mat_traits<A>::template read_element<0,1>(a);\r
1887             T const a02=mat_traits<A>::template read_element<0,2>(a);\r
1888             T const a03=mat_traits<A>::template read_element<0,3>(a);\r
1889             T const a10=mat_traits<A>::template read_element<1,0>(a);\r
1890             T const a11=mat_traits<A>::template read_element<1,1>(a);\r
1891             T const a12=mat_traits<A>::template read_element<1,2>(a);\r
1892             T const a13=mat_traits<A>::template read_element<1,3>(a);\r
1893             T const a20=mat_traits<A>::template read_element<2,0>(a);\r
1894             T const a21=mat_traits<A>::template read_element<2,1>(a);\r
1895             T const a22=mat_traits<A>::template read_element<2,2>(a);\r
1896             T const a23=mat_traits<A>::template read_element<2,3>(a);\r
1897             T const a30=mat_traits<A>::template read_element<3,0>(a);\r
1898             T const a31=mat_traits<A>::template read_element<3,1>(a);\r
1899             T const a32=mat_traits<A>::template read_element<3,2>(a);\r
1900             T const a33=mat_traits<A>::template read_element<3,3>(a);\r
1901             T const f=scalar_traits<T>::value(1)/det;\r
1902             typedef typename deduce_mat<A>::type R;\r
1903             R r;\r
1904             mat_traits<R>::template write_element<0,0>(r)= f*(a11*(a22*a33-a23*a32)-a12*(a21*a33-a23*a31)+a13*(a21*a32-a22*a31));\r
1905             mat_traits<R>::template write_element<0,1>(r)=-f*(a01*(a22*a33-a23*a32)-a02*(a21*a33-a23*a31)+a03*(a21*a32-a22*a31));\r
1906             mat_traits<R>::template write_element<0,2>(r)= f*(a01*(a12*a33-a13*a32)-a02*(a11*a33-a13*a31)+a03*(a11*a32-a12*a31));\r
1907             mat_traits<R>::template write_element<0,3>(r)=-f*(a01*(a12*a23-a13*a22)-a02*(a11*a23-a13*a21)+a03*(a11*a22-a12*a21));\r
1908             mat_traits<R>::template write_element<1,0>(r)=-f*(a10*(a22*a33-a23*a32)-a12*(a20*a33-a23*a30)+a13*(a20*a32-a22*a30));\r
1909             mat_traits<R>::template write_element<1,1>(r)= f*(a00*(a22*a33-a23*a32)-a02*(a20*a33-a23*a30)+a03*(a20*a32-a22*a30));\r
1910             mat_traits<R>::template write_element<1,2>(r)=-f*(a00*(a12*a33-a13*a32)-a02*(a10*a33-a13*a30)+a03*(a10*a32-a12*a30));\r
1911             mat_traits<R>::template write_element<1,3>(r)= f*(a00*(a12*a23-a13*a22)-a02*(a10*a23-a13*a20)+a03*(a10*a22-a12*a20));\r
1912             mat_traits<R>::template write_element<2,0>(r)= f*(a10*(a21*a33-a23*a31)-a11*(a20*a33-a23*a30)+a13*(a20*a31-a21*a30));\r
1913             mat_traits<R>::template write_element<2,1>(r)=-f*(a00*(a21*a33-a23*a31)-a01*(a20*a33-a23*a30)+a03*(a20*a31-a21*a30));\r
1914             mat_traits<R>::template write_element<2,2>(r)= f*(a00*(a11*a33-a13*a31)-a01*(a10*a33-a13*a30)+a03*(a10*a31-a11*a30));\r
1915             mat_traits<R>::template write_element<2,3>(r)=-f*(a00*(a11*a23-a13*a21)-a01*(a10*a23-a13*a20)+a03*(a10*a21-a11*a20));\r
1916             mat_traits<R>::template write_element<3,0>(r)=-f*(a10*(a21*a32-a22*a31)-a11*(a20*a32-a22*a30)+a12*(a20*a31-a21*a30));\r
1917             mat_traits<R>::template write_element<3,1>(r)= f*(a00*(a21*a32-a22*a31)-a01*(a20*a32-a22*a30)+a02*(a20*a31-a21*a30));\r
1918             mat_traits<R>::template write_element<3,2>(r)=-f*(a00*(a11*a32-a12*a31)-a01*(a10*a32-a12*a30)+a02*(a10*a31-a11*a30));\r
1919             mat_traits<R>::template write_element<3,3>(r)= f*(a00*(a11*a22-a12*a21)-a01*(a10*a22-a12*a20)+a02*(a10*a21-a11*a20));\r
1920             return r;\r
1921             }\r
1922 \r
1923         template <class A>\r
1924         BOOST_QVM_INLINE_OPERATIONS\r
1925         typename lazy_enable_if_c<\r
1926             mat_traits<A>::rows==4 && mat_traits<A>::cols==4,\r
1927             deduce_mat<A> >::type\r
1928         inverse( A const & a )\r
1929             {\r
1930             typedef typename mat_traits<A>::scalar_type T;\r
1931             T det=determinant(a);\r
1932             if( det==scalar_traits<T>::value(0) )\r
1933                 BOOST_QVM_THROW_EXCEPTION(zero_determinant_error());\r
1934             return inverse(a,det);\r
1935             }\r
1936 \r
1937         namespace\r
1938         sfinae\r
1939             {\r
1940             using ::boost::qvm::inverse;\r
1941             }\r
1942 \r
1943         namespace\r
1944         qvm_detail\r
1945             {\r
1946             template <int D>\r
1947             struct inverse_m_defined;\r
1948 \r
1949             template <>\r
1950             struct\r
1951             inverse_m_defined<4>\r
1952                 {\r
1953                 static bool const value=true;\r
1954                 };\r
1955             }\r
1956 \r
1957         template <class A,class B>\r
1958         BOOST_QVM_INLINE_OPERATIONS\r
1959         typename lazy_enable_if_c<\r
1960             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
1961             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
1962             deduce_mat2<A,B,4,4> >::type\r
1963         operator*( A const & a, B const & b )\r
1964             {\r
1965             typedef typename mat_traits<A>::scalar_type Ta;\r
1966             typedef typename mat_traits<B>::scalar_type Tb;\r
1967             Ta const a00 = mat_traits<A>::template read_element<0,0>(a);\r
1968             Ta const a01 = mat_traits<A>::template read_element<0,1>(a);\r
1969             Ta const a02 = mat_traits<A>::template read_element<0,2>(a);\r
1970             Ta const a03 = mat_traits<A>::template read_element<0,3>(a);\r
1971             Ta const a10 = mat_traits<A>::template read_element<1,0>(a);\r
1972             Ta const a11 = mat_traits<A>::template read_element<1,1>(a);\r
1973             Ta const a12 = mat_traits<A>::template read_element<1,2>(a);\r
1974             Ta const a13 = mat_traits<A>::template read_element<1,3>(a);\r
1975             Ta const a20 = mat_traits<A>::template read_element<2,0>(a);\r
1976             Ta const a21 = mat_traits<A>::template read_element<2,1>(a);\r
1977             Ta const a22 = mat_traits<A>::template read_element<2,2>(a);\r
1978             Ta const a23 = mat_traits<A>::template read_element<2,3>(a);\r
1979             Ta const a30 = mat_traits<A>::template read_element<3,0>(a);\r
1980             Ta const a31 = mat_traits<A>::template read_element<3,1>(a);\r
1981             Ta const a32 = mat_traits<A>::template read_element<3,2>(a);\r
1982             Ta const a33 = mat_traits<A>::template read_element<3,3>(a);\r
1983             Tb const b00 = mat_traits<B>::template read_element<0,0>(b);\r
1984             Tb const b01 = mat_traits<B>::template read_element<0,1>(b);\r
1985             Tb const b02 = mat_traits<B>::template read_element<0,2>(b);\r
1986             Tb const b03 = mat_traits<B>::template read_element<0,3>(b);\r
1987             Tb const b10 = mat_traits<B>::template read_element<1,0>(b);\r
1988             Tb const b11 = mat_traits<B>::template read_element<1,1>(b);\r
1989             Tb const b12 = mat_traits<B>::template read_element<1,2>(b);\r
1990             Tb const b13 = mat_traits<B>::template read_element<1,3>(b);\r
1991             Tb const b20 = mat_traits<B>::template read_element<2,0>(b);\r
1992             Tb const b21 = mat_traits<B>::template read_element<2,1>(b);\r
1993             Tb const b22 = mat_traits<B>::template read_element<2,2>(b);\r
1994             Tb const b23 = mat_traits<B>::template read_element<2,3>(b);\r
1995             Tb const b30 = mat_traits<B>::template read_element<3,0>(b);\r
1996             Tb const b31 = mat_traits<B>::template read_element<3,1>(b);\r
1997             Tb const b32 = mat_traits<B>::template read_element<3,2>(b);\r
1998             Tb const b33 = mat_traits<B>::template read_element<3,3>(b);\r
1999             typedef typename deduce_mat2<A,B,4,4>::type R;\r
2000             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==4);\r
2001             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==4);\r
2002             R r;\r
2003             mat_traits<R>::template write_element<0,0>(r)=a00*b00+a01*b10+a02*b20+a03*b30;\r
2004             mat_traits<R>::template write_element<0,1>(r)=a00*b01+a01*b11+a02*b21+a03*b31;\r
2005             mat_traits<R>::template write_element<0,2>(r)=a00*b02+a01*b12+a02*b22+a03*b32;\r
2006             mat_traits<R>::template write_element<0,3>(r)=a00*b03+a01*b13+a02*b23+a03*b33;\r
2007             mat_traits<R>::template write_element<1,0>(r)=a10*b00+a11*b10+a12*b20+a13*b30;\r
2008             mat_traits<R>::template write_element<1,1>(r)=a10*b01+a11*b11+a12*b21+a13*b31;\r
2009             mat_traits<R>::template write_element<1,2>(r)=a10*b02+a11*b12+a12*b22+a13*b32;\r
2010             mat_traits<R>::template write_element<1,3>(r)=a10*b03+a11*b13+a12*b23+a13*b33;\r
2011             mat_traits<R>::template write_element<2,0>(r)=a20*b00+a21*b10+a22*b20+a23*b30;\r
2012             mat_traits<R>::template write_element<2,1>(r)=a20*b01+a21*b11+a22*b21+a23*b31;\r
2013             mat_traits<R>::template write_element<2,2>(r)=a20*b02+a21*b12+a22*b22+a23*b32;\r
2014             mat_traits<R>::template write_element<2,3>(r)=a20*b03+a21*b13+a22*b23+a23*b33;\r
2015             mat_traits<R>::template write_element<3,0>(r)=a30*b00+a31*b10+a32*b20+a33*b30;\r
2016             mat_traits<R>::template write_element<3,1>(r)=a30*b01+a31*b11+a32*b21+a33*b31;\r
2017             mat_traits<R>::template write_element<3,2>(r)=a30*b02+a31*b12+a32*b22+a33*b32;\r
2018             mat_traits<R>::template write_element<3,3>(r)=a30*b03+a31*b13+a32*b23+a33*b33;\r
2019             return r;\r
2020             }\r
2021 \r
2022         namespace\r
2023         sfinae\r
2024             {\r
2025             using ::boost::qvm::operator*;\r
2026             }\r
2027 \r
2028         namespace\r
2029         qvm_detail\r
2030             {\r
2031             template <int R,int CR,int C>\r
2032             struct mul_mm_defined;\r
2033 \r
2034             template <>\r
2035             struct\r
2036             mul_mm_defined<4,4,4>\r
2037                 {\r
2038                 static bool const value=true;\r
2039                 };\r
2040             }\r
2041 \r
2042         template <class A,class B>\r
2043         BOOST_QVM_INLINE_OPERATIONS\r
2044         typename enable_if_c<\r
2045             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
2046             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
2047             A &>::type\r
2048         operator*=( A & a, B const & b )\r
2049             {\r
2050             typedef typename mat_traits<A>::scalar_type Ta;\r
2051             typedef typename mat_traits<B>::scalar_type Tb;\r
2052             Ta const a00 = mat_traits<A>::template read_element<0,0>(a);\r
2053             Ta const a01 = mat_traits<A>::template read_element<0,1>(a);\r
2054             Ta const a02 = mat_traits<A>::template read_element<0,2>(a);\r
2055             Ta const a03 = mat_traits<A>::template read_element<0,3>(a);\r
2056             Ta const a10 = mat_traits<A>::template read_element<1,0>(a);\r
2057             Ta const a11 = mat_traits<A>::template read_element<1,1>(a);\r
2058             Ta const a12 = mat_traits<A>::template read_element<1,2>(a);\r
2059             Ta const a13 = mat_traits<A>::template read_element<1,3>(a);\r
2060             Ta const a20 = mat_traits<A>::template read_element<2,0>(a);\r
2061             Ta const a21 = mat_traits<A>::template read_element<2,1>(a);\r
2062             Ta const a22 = mat_traits<A>::template read_element<2,2>(a);\r
2063             Ta const a23 = mat_traits<A>::template read_element<2,3>(a);\r
2064             Ta const a30 = mat_traits<A>::template read_element<3,0>(a);\r
2065             Ta const a31 = mat_traits<A>::template read_element<3,1>(a);\r
2066             Ta const a32 = mat_traits<A>::template read_element<3,2>(a);\r
2067             Ta const a33 = mat_traits<A>::template read_element<3,3>(a);\r
2068             Tb const b00 = mat_traits<B>::template read_element<0,0>(b);\r
2069             Tb const b01 = mat_traits<B>::template read_element<0,1>(b);\r
2070             Tb const b02 = mat_traits<B>::template read_element<0,2>(b);\r
2071             Tb const b03 = mat_traits<B>::template read_element<0,3>(b);\r
2072             Tb const b10 = mat_traits<B>::template read_element<1,0>(b);\r
2073             Tb const b11 = mat_traits<B>::template read_element<1,1>(b);\r
2074             Tb const b12 = mat_traits<B>::template read_element<1,2>(b);\r
2075             Tb const b13 = mat_traits<B>::template read_element<1,3>(b);\r
2076             Tb const b20 = mat_traits<B>::template read_element<2,0>(b);\r
2077             Tb const b21 = mat_traits<B>::template read_element<2,1>(b);\r
2078             Tb const b22 = mat_traits<B>::template read_element<2,2>(b);\r
2079             Tb const b23 = mat_traits<B>::template read_element<2,3>(b);\r
2080             Tb const b30 = mat_traits<B>::template read_element<3,0>(b);\r
2081             Tb const b31 = mat_traits<B>::template read_element<3,1>(b);\r
2082             Tb const b32 = mat_traits<B>::template read_element<3,2>(b);\r
2083             Tb const b33 = mat_traits<B>::template read_element<3,3>(b);\r
2084             mat_traits<A>::template write_element<0,0>(a)=a00*b00+a01*b10+a02*b20+a03*b30;\r
2085             mat_traits<A>::template write_element<0,1>(a)=a00*b01+a01*b11+a02*b21+a03*b31;\r
2086             mat_traits<A>::template write_element<0,2>(a)=a00*b02+a01*b12+a02*b22+a03*b32;\r
2087             mat_traits<A>::template write_element<0,3>(a)=a00*b03+a01*b13+a02*b23+a03*b33;\r
2088             mat_traits<A>::template write_element<1,0>(a)=a10*b00+a11*b10+a12*b20+a13*b30;\r
2089             mat_traits<A>::template write_element<1,1>(a)=a10*b01+a11*b11+a12*b21+a13*b31;\r
2090             mat_traits<A>::template write_element<1,2>(a)=a10*b02+a11*b12+a12*b22+a13*b32;\r
2091             mat_traits<A>::template write_element<1,3>(a)=a10*b03+a11*b13+a12*b23+a13*b33;\r
2092             mat_traits<A>::template write_element<2,0>(a)=a20*b00+a21*b10+a22*b20+a23*b30;\r
2093             mat_traits<A>::template write_element<2,1>(a)=a20*b01+a21*b11+a22*b21+a23*b31;\r
2094             mat_traits<A>::template write_element<2,2>(a)=a20*b02+a21*b12+a22*b22+a23*b32;\r
2095             mat_traits<A>::template write_element<2,3>(a)=a20*b03+a21*b13+a22*b23+a23*b33;\r
2096             mat_traits<A>::template write_element<3,0>(a)=a30*b00+a31*b10+a32*b20+a33*b30;\r
2097             mat_traits<A>::template write_element<3,1>(a)=a30*b01+a31*b11+a32*b21+a33*b31;\r
2098             mat_traits<A>::template write_element<3,2>(a)=a30*b02+a31*b12+a32*b22+a33*b32;\r
2099             mat_traits<A>::template write_element<3,3>(a)=a30*b03+a31*b13+a32*b23+a33*b33;\r
2100             return a;\r
2101             }\r
2102 \r
2103         namespace\r
2104         sfinae\r
2105             {\r
2106             using ::boost::qvm::operator*=;\r
2107             }\r
2108 \r
2109         namespace\r
2110         qvm_detail\r
2111             {\r
2112             template <int D>\r
2113             struct mul_eq_mm_defined;\r
2114 \r
2115             template <>\r
2116             struct\r
2117             mul_eq_mm_defined<4>\r
2118                 {\r
2119                 static bool const value=true;\r
2120                 };\r
2121             }\r
2122 \r
2123         template <class A,class B>\r
2124         BOOST_QVM_INLINE_OPERATIONS\r
2125         typename lazy_enable_if_c<\r
2126             mat_traits<A>::rows==4 && mat_traits<B>::rows==4 &&\r
2127             mat_traits<A>::cols==4 && mat_traits<B>::cols==1,\r
2128             deduce_mat2<A,B,4,1> >::type\r
2129         operator*( A const & a, B const & b )\r
2130             {\r
2131             typedef typename mat_traits<A>::scalar_type Ta;\r
2132             typedef typename mat_traits<B>::scalar_type Tb;\r
2133             Ta const a00 = mat_traits<A>::template read_element<0,0>(a);\r
2134             Ta const a01 = mat_traits<A>::template read_element<0,1>(a);\r
2135             Ta const a02 = mat_traits<A>::template read_element<0,2>(a);\r
2136             Ta const a03 = mat_traits<A>::template read_element<0,3>(a);\r
2137             Ta const a10 = mat_traits<A>::template read_element<1,0>(a);\r
2138             Ta const a11 = mat_traits<A>::template read_element<1,1>(a);\r
2139             Ta const a12 = mat_traits<A>::template read_element<1,2>(a);\r
2140             Ta const a13 = mat_traits<A>::template read_element<1,3>(a);\r
2141             Ta const a20 = mat_traits<A>::template read_element<2,0>(a);\r
2142             Ta const a21 = mat_traits<A>::template read_element<2,1>(a);\r
2143             Ta const a22 = mat_traits<A>::template read_element<2,2>(a);\r
2144             Ta const a23 = mat_traits<A>::template read_element<2,3>(a);\r
2145             Ta const a30 = mat_traits<A>::template read_element<3,0>(a);\r
2146             Ta const a31 = mat_traits<A>::template read_element<3,1>(a);\r
2147             Ta const a32 = mat_traits<A>::template read_element<3,2>(a);\r
2148             Ta const a33 = mat_traits<A>::template read_element<3,3>(a);\r
2149             Tb const b00 = mat_traits<B>::template read_element<0,0>(b);\r
2150             Tb const b10 = mat_traits<B>::template read_element<1,0>(b);\r
2151             Tb const b20 = mat_traits<B>::template read_element<2,0>(b);\r
2152             Tb const b30 = mat_traits<B>::template read_element<3,0>(b);\r
2153             typedef typename deduce_mat2<A,B,4,1>::type R;\r
2154             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==4);\r
2155             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==1);\r
2156             R r;\r
2157             mat_traits<R>::template write_element<0,0>(r)=a00*b00+a01*b10+a02*b20+a03*b30;\r
2158             mat_traits<R>::template write_element<1,0>(r)=a10*b00+a11*b10+a12*b20+a13*b30;\r
2159             mat_traits<R>::template write_element<2,0>(r)=a20*b00+a21*b10+a22*b20+a23*b30;\r
2160             mat_traits<R>::template write_element<3,0>(r)=a30*b00+a31*b10+a32*b20+a33*b30;\r
2161             return r;\r
2162             }\r
2163 \r
2164         namespace\r
2165         sfinae\r
2166             {\r
2167             using ::boost::qvm::operator*;\r
2168             }\r
2169 \r
2170         namespace\r
2171         qvm_detail\r
2172             {\r
2173             template <int R,int CR,int C>\r
2174             struct mul_mm_defined;\r
2175 \r
2176             template <>\r
2177             struct\r
2178             mul_mm_defined<4,4,1>\r
2179                 {\r
2180                 static bool const value=true;\r
2181                 };\r
2182             }\r
2183 \r
2184         template <class A,class B>\r
2185         BOOST_QVM_INLINE_OPERATIONS\r
2186         typename lazy_enable_if_c<\r
2187             mat_traits<A>::rows==1 && mat_traits<B>::rows==4 &&\r
2188             mat_traits<A>::cols==4 && mat_traits<B>::cols==4,\r
2189             deduce_mat2<A,B,1,4> >::type\r
2190         operator*( A const & a, B const & b )\r
2191             {\r
2192             typedef typename mat_traits<A>::scalar_type Ta;\r
2193             typedef typename mat_traits<B>::scalar_type Tb;\r
2194             Ta const a00 = mat_traits<A>::template read_element<0,0>(a);\r
2195             Ta const a01 = mat_traits<A>::template read_element<0,1>(a);\r
2196             Ta const a02 = mat_traits<A>::template read_element<0,2>(a);\r
2197             Ta const a03 = mat_traits<A>::template read_element<0,3>(a);\r
2198             Tb const b00 = mat_traits<B>::template read_element<0,0>(b);\r
2199             Tb const b01 = mat_traits<B>::template read_element<0,1>(b);\r
2200             Tb const b02 = mat_traits<B>::template read_element<0,2>(b);\r
2201             Tb const b03 = mat_traits<B>::template read_element<0,3>(b);\r
2202             Tb const b10 = mat_traits<B>::template read_element<1,0>(b);\r
2203             Tb const b11 = mat_traits<B>::template read_element<1,1>(b);\r
2204             Tb const b12 = mat_traits<B>::template read_element<1,2>(b);\r
2205             Tb const b13 = mat_traits<B>::template read_element<1,3>(b);\r
2206             Tb const b20 = mat_traits<B>::template read_element<2,0>(b);\r
2207             Tb const b21 = mat_traits<B>::template read_element<2,1>(b);\r
2208             Tb const b22 = mat_traits<B>::template read_element<2,2>(b);\r
2209             Tb const b23 = mat_traits<B>::template read_element<2,3>(b);\r
2210             Tb const b30 = mat_traits<B>::template read_element<3,0>(b);\r
2211             Tb const b31 = mat_traits<B>::template read_element<3,1>(b);\r
2212             Tb const b32 = mat_traits<B>::template read_element<3,2>(b);\r
2213             Tb const b33 = mat_traits<B>::template read_element<3,3>(b);\r
2214             typedef typename deduce_mat2<A,B,1,4>::type R;\r
2215             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::rows==1);\r
2216             BOOST_QVM_STATIC_ASSERT(mat_traits<R>::cols==4);\r
2217             R r;\r
2218             mat_traits<R>::template write_element<0,0>(r)=a00*b00+a01*b10+a02*b20+a03*b30;\r
2219             mat_traits<R>::template write_element<0,1>(r)=a00*b01+a01*b11+a02*b21+a03*b31;\r
2220             mat_traits<R>::template write_element<0,2>(r)=a00*b02+a01*b12+a02*b22+a03*b32;\r
2221             mat_traits<R>::template write_element<0,3>(r)=a00*b03+a01*b13+a02*b23+a03*b33;\r
2222             return r;\r
2223             }\r
2224 \r
2225         namespace\r
2226         sfinae\r
2227             {\r
2228             using ::boost::qvm::operator*;\r
2229             }\r
2230 \r
2231         namespace\r
2232         qvm_detail\r
2233             {\r
2234             template <int R,int CR,int C>\r
2235             struct mul_mm_defined;\r
2236 \r
2237             template <>\r
2238             struct\r
2239             mul_mm_defined<1,4,4>\r
2240                 {\r
2241                 static bool const value=true;\r
2242                 };\r
2243             }\r
2244 \r
2245         }\r
2246     }\r
2247 \r
2248 #endif\r