source: nanovis/tags/1.1.1/vrmath/Matrix4x4f.cpp @ 4833

Last change on this file since 4833 was 3492, checked in by ldelgass, 11 years ago

Fix camera reset for nanovis. Includes refactoring of vector/matrix classes
in nanovis to consolidate into vrmath library. Also add preliminary canonical
view control to clients for testing.

File size: 33.4 KB
Line 
1/* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2/*
3 * Copyright (c) 2004-2013  HUBzero Foundation, LLC
4 *
5 * Author: Insoo Woo <iwoo@purdue.edu>
6 * Author: Leif Delgass <ldelgass@purdue.edu>
7 */
8
9#include <vrmath/Vector3f.h>
10#include <vrmath/Rotation.h>
11#include <vrmath/Matrix4x4f.h>
12
13using namespace vrmath;
14
15void Matrix4x4f::makeIdentity()
16{
17    _data[1] = _data[2] = _data[3] = _data[4] =
18        _data[6] = _data[7] = _data[8] = _data[9] =
19        _data[11] = _data[12] = _data[13] = _data[14] = 0.0f;
20    _data[0] = _data[5] = _data[10] = _data[15] = 1.0f;
21}
22
23void Matrix4x4f::makeTranslation(const Vector3f& translation)
24{
25    _data[1] = _data[2] = _data[3] = _data[4] =
26        _data[6] = _data[7] = _data[8] = _data[9] =
27        _data[11] = 0.0f;
28    _data[0] = _data[5] = _data[10] = _data[15] = 1.0f;
29    _data[12] = translation.x;
30    _data[13] = translation.y;
31    _data[14] = translation.z;
32}
33
34void Matrix4x4f::makeTranslation(float x, float y, float z)
35{
36    _data[1] = _data[2] = _data[3] = _data[4] =
37        _data[6] = _data[7] = _data[8] = _data[9] =
38        _data[11] = 0.0f;
39    _data[0] = _data[5] = _data[10] = _data[15] = 1.0f;
40    _data[12] = x;
41    _data[13] = y;
42    _data[14] = z;
43}
44
45void Matrix4x4f::makeRotation(const Rotation& rotation)
46{
47    if (rotation.getAngle() == 0.0 ||
48        (rotation.getX() == 0.0 &&
49         rotation.getY() == 0.0 &&
50         rotation.getZ() == 0.0)) {
51        makeIdentity();
52        return;
53    }
54
55    double xAxis = rotation.getX();
56    double yAxis = rotation.getY();
57    double zAxis = rotation.getZ();
58    double invLen = 1.0 / sqrt(xAxis * xAxis + yAxis * yAxis + zAxis * zAxis);
59    double cosine = cos(rotation.getAngle());
60    double sine = sin(rotation.getAngle());
61
62    xAxis *= invLen;
63    yAxis *= invLen;
64    zAxis *= invLen;
65
66    double oneMinusCosine = 1.0 - cosine;
67
68    _data[3] = _data[7] = _data[11] = _data[12] = _data[13] = _data[14] = 0.0f;
69    _data[15] = 1.0f;
70
71    _data[0] = float(xAxis * xAxis * oneMinusCosine + cosine);
72    _data[1] = float(yAxis * xAxis * oneMinusCosine + zAxis * sine);
73    _data[2] = float(xAxis * zAxis * oneMinusCosine - yAxis * sine);
74
75    _data[4] = float(xAxis * yAxis * oneMinusCosine - zAxis * sine);
76    _data[5] = float(yAxis * yAxis * oneMinusCosine + cosine);
77    _data[6] = float(yAxis * zAxis * oneMinusCosine + xAxis * sine);
78
79    _data[8] = float(xAxis * zAxis * oneMinusCosine + yAxis * sine);
80    _data[9] = float(yAxis * zAxis * oneMinusCosine - xAxis * sine);
81    _data[10] = float(zAxis * zAxis * oneMinusCosine + cosine);
82}
83
84void Matrix4x4f::makeRotation(double xAxis, double yAxis, double zAxis, double angle)
85{
86    if (angle == 0.0 ||
87        (xAxis == 0.0 &&
88         yAxis == 0.0 &&
89         zAxis == 0.0)) {
90        makeIdentity();
91        return;
92    }
93
94    double invLen = 1.0 / sqrt((double)xAxis * xAxis + (double)yAxis * yAxis + (double)zAxis * zAxis);
95    double cosine = cos(angle);
96    double sine = sin(angle);
97
98    xAxis *= invLen;
99    yAxis *= invLen;
100    zAxis *= invLen;
101
102    double oneMinusCosine = 1.0 - cosine;
103
104    _data[3] = _data[7] = _data[11] = _data[12] = _data[13] = _data[14] = 0.0f;
105    _data[15] = 1.0f;
106
107    _data[0] = float(xAxis * xAxis * oneMinusCosine + cosine);
108    _data[1] = float(yAxis * xAxis * oneMinusCosine + zAxis * sine);
109    _data[2] = float(xAxis * zAxis * oneMinusCosine - yAxis * sine);
110
111    _data[4] = float(xAxis * yAxis * oneMinusCosine - zAxis * sine);
112    _data[5] = float(yAxis * yAxis * oneMinusCosine + cosine);
113    _data[6] = float(yAxis * zAxis * oneMinusCosine + xAxis * sine);
114
115    _data[8] = float(xAxis * zAxis * oneMinusCosine + yAxis * sine);
116    _data[9] = float(yAxis * zAxis * oneMinusCosine - xAxis * sine);
117    _data[10] = float(zAxis * zAxis * oneMinusCosine + cosine);
118}
119
120void Matrix4x4f::makeScale(const Vector3f& scale)
121{
122    _data[1] = _data[2] = _data[3] = _data[4] =
123        _data[6] = _data[7] = _data[8] = _data[9] =
124        _data[11] = 0.0f;
125
126    _data[0] = scale.x;
127    _data[5] = scale.y;
128    _data[10] = scale.z;
129
130    _data[15] = 1.0f;
131    _data[12] = _data[13] = _data[14] = 0.0f;
132}
133
134void Matrix4x4f::makeScale(float x, float y, float z)
135{
136    _data[1] = _data[2] = _data[3] = _data[4] =
137        _data[6] = _data[7] = _data[8] = _data[9] =
138        _data[11] = 0.0f;
139
140    _data[0] = x;
141    _data[5] = y;
142    _data[10] = z;
143
144    _data[15] = 1.0f;
145    _data[12] = _data[13] = _data[14] = 0.0f;
146}
147
148Vector4f
149Matrix4x4f::transform(const Vector4f& v) const
150{
151    Vector4f ret;
152    ret.x = _data[0] * v.x + _data[4] * v.y + _data[8] * v.z  + _data[12] * v.w;
153    ret.y = _data[1] * v.x + _data[5] * v.y + _data[9] * v.z  + _data[13] * v.w;
154    ret.z = _data[2] * v.x + _data[6] * v.y + _data[10] * v.z + _data[14] * v.w;
155    ret.w = _data[3] * v.x + _data[7] * v.y + _data[11] * v.z + _data[15] * v.w;
156    return ret;
157}
158
159Vector3f
160Matrix4x4f::transformVec(const Vector3f& v) const
161{
162    Vector3f ret;
163    ret.x = _data[0] * v.x + _data[4] * v.y + _data[8] * v.z;
164    ret.y = _data[1] * v.x + _data[5] * v.y + _data[9] * v.z;
165    ret.z = _data[2] * v.x + _data[6] * v.y + _data[10] * v.z;
166    return ret;
167}
168
169Vector4f
170Matrix4x4f::preMultiplyRowVector(const Vector4f& v) const
171{
172    Vector4f ret;
173    ret.x = (_data[0]  * v.x) + (_data[1]  * v.y) + (_data[2]  * v.z) + (_data[3]  * v.w);
174    ret.y = (_data[4]  * v.x) + (_data[5]  * v.y) + (_data[6]  * v.z) + (_data[7]  * v.w);
175    ret.z = (_data[8]  * v.x) + (_data[9]  * v.y) + (_data[10] * v.z) + (_data[11] * v.w);
176    ret.w = (_data[12] * v.x) + (_data[13] * v.y) + (_data[14] * v.z) + (_data[15] * v.w);
177    return ret;
178}
179
180void Matrix4x4f::multiply(const Matrix4x4f& m1)
181{
182    float mat[16];
183    const float *mat1 = m1._data;
184
185    // 1 row
186    mat[0] = float(_data[0] * mat1[0] + _data[4] * mat1[1] +
187                   _data[8] * mat1[2] + _data[12] * mat1[3]);
188    mat[4] = float(_data[0] * mat1[4] + _data[4] * mat1[5] +
189                   _data[8] * mat1[6] + _data[12] * mat1[7]);
190    mat[8] = float(_data[0] * mat1[8] + _data[4] * mat1[9] +
191                   _data[8] * mat1[10] + _data[12] * mat1[11]);
192    mat[12] = float(_data[0] * mat1[12] + _data[4] * mat1[13] +
193                    _data[8] * mat1[14] + _data[12] * mat1[15]);
194
195    // 2 row
196    mat[1] = float(_data[1] * mat1[0] + _data[5] * mat1[1] +
197                   _data[9] * mat1[2] + _data[13] * mat1[3]);
198    mat[5] = float(_data[1] * mat1[4] + _data[5] * mat1[5] +
199                   _data[9] * mat1[6] + _data[13] * mat1[7]);
200    mat[9] = float(_data[1] * mat1[8] + _data[5] * mat1[9] +
201                   _data[9] * mat1[10] + _data[13] * mat1[11]);
202    mat[13] = float(_data[1] * mat1[12] + _data[5] * mat1[13] +
203                    _data[9] * mat1[14] + _data[13] * mat1[15]);
204
205    // 3 row
206    mat[2] = float(_data[2] * mat1[0] + _data[6] * mat1[1] +
207                   _data[10] * mat1[2] + _data[14] * mat1[3]);
208
209    mat[6] = float(_data[2] * mat1[4] + _data[6] * mat1[5] +
210                   _data[10] * mat1[6] + _data[14] * mat1[7]);
211    mat[10] = float(_data[2] * mat1[8] + _data[6] * mat1[9] +
212                    _data[10] * mat1[10] + _data[14] * mat1[11]);
213    mat[14] = float(_data[2] * mat1[12] + _data[6] * mat1[13] +
214                    _data[10] * mat1[14] + _data[14] * mat1[15]);
215
216    // 4 row
217    mat[3] = float(_data[3] * mat1[0] + _data[7] * mat1[1] +
218                   _data[11] * mat1[2] + _data[15] * mat1[3]);
219    mat[7] = float(_data[3] * mat1[4] + _data[7] * mat1[5] +
220                   _data[11] * mat1[6] + _data[15] * mat1[7]);
221    mat[11] = float(_data[3] * mat1[8] + _data[7] * mat1[9] +
222                    _data[11] * mat1[10] + _data[15] * mat1[11]);
223    mat[15] = float(_data[3] * mat1[12] + _data[7] * mat1[13] +
224                    _data[11] * mat1[14] + _data[15] * mat1[15]);
225
226    // set matrix
227    set(mat);
228}
229
230void Matrix4x4f::multiply(const Matrix4x4f& m1, const Matrix4x4f& m2)
231{
232    float mat[16];
233    const float *mat1 = m1._data;
234    const float *mat2 = m2._data;
235
236    // 1 row
237    mat[0] = float(mat1[0] * mat2[0] + mat1[4] * mat2[1] +
238                   mat1[8] * mat2[2] + mat1[12] * mat2[3]);
239    mat[4] = float(mat1[0] * mat2[4] + mat1[4] * mat2[5] +
240                   mat1[8] * mat2[6] + mat1[12] * mat2[7]);
241    mat[8] = float(mat1[0] * mat2[8] + mat1[4] * mat2[9] +
242                   mat1[8] * mat2[10] + mat1[12] * mat2[11]);
243    mat[12] = float(mat1[0] * mat2[12] + mat1[4] * mat2[13] +
244                    mat1[8] * mat2[14] + mat1[12] * mat2[15]);
245
246    // 2 row
247    mat[1] = float(mat1[1] * mat2[0] + mat1[5] * mat2[1] +
248                   mat1[9] * mat2[2] + mat1[13] * mat2[3]);
249    mat[5] = float(mat1[1] * mat2[4] + mat1[5] * mat2[5] +
250                   mat1[9] * mat2[6] + mat1[13] * mat2[7]);
251    mat[9] = float(mat1[1] * mat2[8] + mat1[5] * mat2[9] +
252                   mat1[9] * mat2[10] + mat1[13] * mat2[11]);
253    mat[13] = float(mat1[1] * mat2[12] + mat1[5] * mat2[13] +
254                    mat1[9] * mat2[14] + mat1[13] * mat2[15]);
255
256    // 3 row
257    mat[2] = float(mat1[2] * mat2[0] + mat1[6] * mat2[1] +
258                   mat1[10] * mat2[2] + mat1[14] * mat2[3]);
259    mat[6] = float(mat1[2] * mat2[4] + mat1[6] * mat2[5] +
260                   mat1[10] * mat2[6] + mat1[14] * mat2[7]);
261    mat[10] = float(mat1[2] * mat2[8] + mat1[6] * mat2[9] +
262                    mat1[10] * mat2[10] + mat1[14] * mat2[11]);
263    mat[14] = float(mat1[2] * mat2[12] + mat1[6] * mat2[13] +
264                    mat1[10] * mat2[14] + mat1[14] * mat2[15]);
265
266    // 4 row
267    mat[3] = float(mat1[3] * mat2[0] + mat1[7] * mat2[1] +
268                   mat1[11] * mat2[2] + mat1[15] * mat2[3]);
269    mat[7] = float(mat1[3] * mat2[4] + mat1[7] * mat2[5] +
270                   mat1[11] * mat2[6] + mat1[15] * mat2[7]);
271    mat[11] = float(mat1[3] * mat2[8] + mat1[7] * mat2[9] +
272                    mat1[11] * mat2[10] + mat1[15] * mat2[11]);
273    mat[15] = float(mat1[3] * mat2[12] + mat1[7] * mat2[13] +
274                    mat1[11] * mat2[14] + mat1[15] * mat2[15]);
275
276    // set matrix
277    set(mat);
278}
279
280void Matrix4x4f::multiplyFast(const Matrix4x4f& m1, const Matrix4x4f& m2)
281{
282    const float *mat1 = m1._data;
283    const float *mat2 = m2._data;
284
285    // 1 row
286    _data[0] = float(mat1[0] * mat2[0] + mat1[4] * mat2[1] +
287                     mat1[8] * mat2[2] + mat1[12] * mat2[3]);
288    _data[4] = float(mat1[0] * mat2[4] + mat1[4] * mat2[5] +
289                     mat1[8] * mat2[6] + mat1[12] * mat2[7]);
290    _data[8] = float(mat1[0] * mat2[8] + mat1[4] * mat2[9] +
291                     mat1[8] * mat2[10] + mat1[12] * mat2[11]);
292    _data[12] = float(mat1[0] * mat2[12] + mat1[4] * mat2[13] +
293                      mat1[8] * mat2[14] + mat1[12] * mat2[15]);
294
295    // 2 row
296    _data[1] = float(mat1[1] * mat2[0] + mat1[5] * mat2[1] +
297                     mat1[9] * mat2[2] + mat1[13] * mat2[3]);
298    _data[5] = float(mat1[1] * mat2[4] + mat1[5] * mat2[5] +
299                     mat1[9] * mat2[6] + mat1[13] * mat2[7]);
300    _data[9] = float(mat1[1] * mat2[8] + mat1[5] * mat2[9] +
301                     mat1[9] * mat2[10] + mat1[13] * mat2[11]);
302    _data[13] = float(mat1[1] * mat2[12] + mat1[5] * mat2[13] +
303                      mat1[9] * mat2[14] + mat1[13] * mat2[15]);
304
305    // 3 row
306    _data[2] = float(mat1[2] * mat2[0] + mat1[6] * mat2[1] +
307                     mat1[10] * mat2[2] + mat1[14] * mat2[3]);
308    _data[6] = float(mat1[2] * mat2[4] + mat1[6] * mat2[5] +
309                     mat1[10] * mat2[6] + mat1[14] * mat2[7]);
310    _data[10] = float(mat1[2] * mat2[8] + mat1[6] * mat2[9] +
311                      mat1[10] * mat2[10] + mat1[14] * mat2[11]);
312    _data[14] = float(mat1[2] * mat2[12] + mat1[6] * mat2[13] +
313                      mat1[10] * mat2[14] + mat1[14] * mat2[15]);
314
315    // 4 row
316    _data[3] = float(mat1[3] * mat2[0] + mat1[7] * mat2[1] +
317                     mat1[11] * mat2[2] + mat1[15] * mat2[3]);
318    _data[7] = float(mat1[3] * mat2[4] + mat1[7] * mat2[5] +
319                     mat1[11] * mat2[6] + mat1[15] * mat2[7]);
320    _data[11] = float(mat1[3] * mat2[8] + mat1[7] * mat2[9] +
321                      mat1[11] * mat2[10] + mat1[15] * mat2[11]);
322    _data[15] = float(mat1[3] * mat2[12] + mat1[7] * mat2[13] +
323                      mat1[11] * mat2[14] + mat1[15] * mat2[15]);
324}
325
326void Matrix4x4f::getRotation(Rotation& rotation)
327{
328    double c = (_data[0] + _data[5] + _data[10] - 1.0) * 0.5;
329
330    rotation.setAxis(_data[6] - _data[9], _data[8] - _data[2], _data[1] - _data[4]);
331
332    double len = sqrt(rotation.getX() * rotation.getX() +
333                      rotation.getY() * rotation.getY() +
334                      rotation.getZ() * rotation.getZ());
335
336    double s = 0.5 * len;
337
338    rotation.setAngle(atan2(s, c));
339
340    if (rotation.getX() == 0.0 &&
341        rotation.getY() == 0.0 &&
342        rotation.getZ() == 0.0) {
343        rotation.set(0, 1, 0, 0);
344    } else {
345        len = 1.0 / len;
346        rotation.setAxis(rotation.getX() * len,
347                         rotation.getY() * len,
348                         rotation.getZ() * len);
349    }
350}
351
352void Matrix4x4f::invert()
353{
354    float det =
355        _data[12] * _data[9] * _data[6] * _data[3]-
356        _data[8] * _data[13] * _data[6] * _data[3]-
357        _data[12] * _data[5] * _data[10] * _data[3]+
358        _data[4] * _data[13] * _data[10] * _data[3]+
359        _data[8] * _data[5] * _data[14] * _data[3]-
360        _data[4] * _data[9] * _data[14] * _data[3]-
361        _data[12] * _data[9] * _data[2] * _data[7]+
362        _data[8] * _data[13] * _data[2] * _data[7]+
363        _data[12] * _data[1] * _data[10] * _data[7]-
364        _data[0] * _data[13] * _data[10] * _data[7]-
365        _data[8] * _data[1] * _data[14] * _data[7]+
366        _data[0] * _data[9] * _data[14] * _data[7]+
367        _data[12] * _data[5] * _data[2] * _data[11]-
368        _data[4] * _data[13] * _data[2] * _data[11]-
369        _data[12] * _data[1] * _data[6] * _data[11]+
370        _data[0] * _data[13] * _data[6] * _data[11]+
371        _data[4] * _data[1] * _data[14] * _data[11]-
372        _data[0] * _data[5] * _data[14] * _data[11]-
373        _data[8] * _data[5] * _data[2] * _data[15]+
374        _data[4] * _data[9] * _data[2] * _data[15]+
375        _data[8] * _data[1] * _data[6] * _data[15]-
376        _data[0] * _data[9] * _data[6] * _data[15]-
377        _data[4] * _data[1] * _data[10] * _data[15]+
378        _data[0] * _data[5] * _data[10] * _data[15];
379
380    if ( det == 0.0f ) return;
381    det = 1 / det;
382
383    float mat[16];
384
385    mat[0] = (_data[9]*_data[14]*_data[7] -
386              _data[13]*_data[10]*_data[7] +
387              _data[13]*_data[6]*_data[11] -
388              _data[5]*_data[14]*_data[11] -
389              _data[9]*_data[6]*_data[15] +
390              _data[5]*_data[10]*_data[15]) * det;
391
392    mat[4] = (_data[12]*_data[10]*_data[7] -
393              _data[8]*_data[14]*_data[7] -
394              _data[12]*_data[6]*_data[11] +
395              _data[4]*_data[14]*_data[11] +
396              _data[8]*_data[6]*_data[15] -
397              _data[4]*_data[10]*_data[15]) * det;
398
399    mat[8] = (_data[8]*_data[13]*_data[7] -
400              _data[12]*_data[9]*_data[7] +
401              _data[12]*_data[5]*_data[11] -
402              _data[4]*_data[13]*_data[11] -
403              _data[8]*_data[5]*_data[15] +
404              _data[4]*_data[9]*_data[15]) * det;
405
406    mat[12] = (_data[12]*_data[9]*_data[6] -
407               _data[8]*_data[13]*_data[6] -
408               _data[12]*_data[5]*_data[10] +
409               _data[4]*_data[13]*_data[10] +
410               _data[8]*_data[5]*_data[14] -
411               _data[4]*_data[9]*_data[14]) * det;
412
413    mat[1] = (_data[13]*_data[10]*_data[3] -
414              _data[9]*_data[14]*_data[3] -
415              _data[13]*_data[2]*_data[11] +
416              _data[1]*_data[14]*_data[11] +
417              _data[9]*_data[2]*_data[15] -
418              _data[1]*_data[10]*_data[15]) * det;
419
420    mat[5] = (_data[8]*_data[14]*_data[3] -
421              _data[12]*_data[10]*_data[3] +
422              _data[12]*_data[2]*_data[11] -
423              _data[0]*_data[14]*_data[11] -
424              _data[8]*_data[2]*_data[15] +
425              _data[0]*_data[10]*_data[15]) * det;
426
427    mat[9] = (_data[12]*_data[9]*_data[3] -
428              _data[8]*_data[13]*_data[3] -
429              _data[12]*_data[1]*_data[11] +
430              _data[0]*_data[13]*_data[11] +
431              _data[8]*_data[1]*_data[15] -
432              _data[0]*_data[9]*_data[15]) * det;
433
434    mat[13] = (_data[8]*_data[13]*_data[2] -
435               _data[12]*_data[9]*_data[2] +
436               _data[12]*_data[1]*_data[10] -
437               _data[0]*_data[13]*_data[10] -
438               _data[8]*_data[1]*_data[14] +
439               _data[0]*_data[9]*_data[14]) * det;
440
441    mat[2] = (_data[5]*_data[14]*_data[3] -
442              _data[13]*_data[6]*_data[3] +
443              _data[13]*_data[2]*_data[7] -
444              _data[1]*_data[14]*_data[7] -
445              _data[5]*_data[2]*_data[15] +
446              _data[1]*_data[6]*_data[15]) * det;
447
448    mat[6] = (_data[12]*_data[6]*_data[3] -
449              _data[4]*_data[14]*_data[3] -
450              _data[12]*_data[2]*_data[7] +
451              _data[0]*_data[14]*_data[7] +
452              _data[4]*_data[2]*_data[15] -
453              _data[0]*_data[6]*_data[15]) * det;
454
455    mat[10] = (_data[4]*_data[13]*_data[3] -
456               _data[12]*_data[5]*_data[3] +
457               _data[12]*_data[1]*_data[7] -
458               _data[0]*_data[13]*_data[7] -
459               _data[4]*_data[1]*_data[15] +
460               _data[0]*_data[5]*_data[15]) * det;
461
462    mat[14] = (_data[12]*_data[5]*_data[2] -
463               _data[4]*_data[13]*_data[2] -
464               _data[12]*_data[1]*_data[6] +
465               _data[0]*_data[13]*_data[6] +
466               _data[4]*_data[1]*_data[14] -
467               _data[0]*_data[5]*_data[14]) * det;
468
469    mat[3] = (_data[9]*_data[6]*_data[3] -
470              _data[5]*_data[10]*_data[3] -
471              _data[9]*_data[2]*_data[7] +
472              _data[1]*_data[10]*_data[7] +
473              _data[5]*_data[2]*_data[11] -
474              _data[1]*_data[6]*_data[11]) * det;
475
476    mat[7] = (_data[4]*_data[10]*_data[3] -
477              _data[8]*_data[6]*_data[3] +
478              _data[8]*_data[2]*_data[7] -
479              _data[0]*_data[10]*_data[7] -
480              _data[4]*_data[2]*_data[11] +
481              _data[0]*_data[6]*_data[11]) * det;
482
483    mat[11] = (_data[8]*_data[5]*_data[3] -
484               _data[4]*_data[9]*_data[3] -
485               _data[8]*_data[1]*_data[7] +
486               _data[0]*_data[9]*_data[7] +
487               _data[4]*_data[1]*_data[11] -
488               _data[0]*_data[5]*_data[11]) * det;
489
490    mat[15] = (_data[4]*_data[9]*_data[2] -
491               _data[8]*_data[5]*_data[2] +
492               _data[8]*_data[1]*_data[6] -
493               _data[0]*_data[9]*_data[6] -
494               _data[4]*_data[1]*_data[10] +
495               _data[0]*_data[5]*_data[10]) * det;
496
497    set(mat);
498}
499
500void Matrix4x4f::invert(const Matrix4x4f& mat)
501{
502    float *data = (float *)mat._data;
503
504    float det =
505        data[12] * data[9] * data[6] * data[3]-
506        data[8] * data[13] * data[6] * data[3]-
507        data[12] * data[5] * data[10] * data[3]+
508        data[4] * data[13] * data[10] * data[3]+
509        data[8] * data[5] * data[14] * data[3]-
510        data[4] * data[9] * data[14] * data[3]-
511        data[12] * data[9] * data[2] * data[7]+
512        data[8] * data[13] * data[2] * data[7]+
513        data[12] * data[1] * data[10] * data[7]-
514        data[0] * data[13] * data[10] * data[7]-
515        data[8] * data[1] * data[14] * data[7]+
516        data[0] * data[9] * data[14] * data[7]+
517        data[12] * data[5] * data[2] * data[11]-
518        data[4] * data[13] * data[2] * data[11]-
519        data[12] * data[1] * data[6] * data[11]+
520        data[0] * data[13] * data[6] * data[11]+
521        data[4] * data[1] * data[14] * data[11]-
522        data[0] * data[5] * data[14] * data[11]-
523        data[8] * data[5] * data[2] * data[15]+
524        data[4] * data[9] * data[2] * data[15]+
525        data[8] * data[1] * data[6] * data[15]-
526        data[0] * data[9] * data[6] * data[15]-
527        data[4] * data[1] * data[10] * data[15]+
528        data[0] * data[5] * data[10] * data[15];
529
530    if ( det == 0.0f ) return;
531    det = 1 / det;
532
533    float dstData[16];
534
535    dstData[0] = (data[9]*data[14]*data[7] -
536                  data[13]*data[10]*data[7] +
537                  data[13]*data[6]*data[11] -
538                  data[5]*data[14]*data[11] -
539                  data[9]*data[6]*data[15] +
540                  data[5]*data[10]*data[15]) * det;
541
542    dstData[4] = (data[12]*data[10]*data[7] -
543                  data[8]*data[14]*data[7] -
544                  data[12]*data[6]*data[11] +
545                  data[4]*data[14]*data[11] +
546                  data[8]*data[6]*data[15] -
547                  data[4]*data[10]*data[15]) * det;
548
549    dstData[8] = (data[8]*data[13]*data[7] -
550                  data[12]*data[9]*data[7] +
551                  data[12]*data[5]*data[11] -
552                  data[4]*data[13]*data[11] -
553                  data[8]*data[5]*data[15] +
554                  data[4]*data[9]*data[15]) * det;
555
556    dstData[12] = (data[12]*data[9]*data[6] -
557                   data[8]*data[13]*data[6] -
558                   data[12]*data[5]*data[10] +
559                   data[4]*data[13]*data[10] +
560                   data[8]*data[5]*data[14] -
561                   data[4]*data[9]*data[14]) * det;
562
563    dstData[1] = (data[13]*data[10]*data[3] -
564                  data[9]*data[14]*data[3] -
565                  data[13]*data[2]*data[11] +
566                  data[1]*data[14]*data[11] +
567                  data[9]*data[2]*data[15] -
568                  data[1]*data[10]*data[15]) * det;
569
570    dstData[5] = (data[8]*data[14]*data[3] -
571                  data[12]*data[10]*data[3] +
572                  data[12]*data[2]*data[11] -
573                  data[0]*data[14]*data[11] -
574                  data[8]*data[2]*data[15] +
575                  data[0]*data[10]*data[15]) * det;
576
577    dstData[9] = (data[12]*data[9]*data[3] -
578                  data[8]*data[13]*data[3] -
579                  data[12]*data[1]*data[11] +
580                  data[0]*data[13]*data[11] +
581                  data[8]*data[1]*data[15] -
582                  data[0]*data[9]*data[15]) * det;
583
584    dstData[13] = (data[8]*data[13]*data[2] -
585                   data[12]*data[9]*data[2] +
586                   data[12]*data[1]*data[10] -
587                   data[0]*data[13]*data[10] -
588                   data[8]*data[1]*data[14] +
589                   data[0]*data[9]*data[14]) * det;
590
591    dstData[2] = (data[5]*data[14]*data[3] -
592                  data[13]*data[6]*data[3] +
593                  data[13]*data[2]*data[7] -
594                  data[1]*data[14]*data[7] -
595                  data[5]*data[2]*data[15] +
596                  data[1]*data[6]*data[15]) * det;
597
598    dstData[6] = (data[12]*data[6]*data[3] -
599                  data[4]*data[14]*data[3] -
600                  data[12]*data[2]*data[7] +
601                  data[0]*data[14]*data[7] +
602                  data[4]*data[2]*data[15] -
603                  data[0]*data[6]*data[15]) * det;
604
605    dstData[10] = (data[4]*data[13]*data[3] -
606                   data[12]*data[5]*data[3] +
607                   data[12]*data[1]*data[7] -
608                   data[0]*data[13]*data[7] -
609                   data[4]*data[1]*data[15] +
610                   data[0]*data[5]*data[15]) * det;
611
612    dstData[14] = (data[12]*data[5]*data[2] -
613                   data[4]*data[13]*data[2] -
614                   data[12]*data[1]*data[6] +
615                   data[0]*data[13]*data[6] +
616                   data[4]*data[1]*data[14] -
617                   data[0]*data[5]*data[14]) * det;
618
619    dstData[3] = (data[9]*data[6]*data[3] -
620                  data[5]*data[10]*data[3] -
621                  data[9]*data[2]*data[7] +
622                  data[1]*data[10]*data[7] +
623                  data[5]*data[2]*data[11] -
624                  data[1]*data[6]*data[11]) * det;
625
626    dstData[7] = (data[4]*data[10]*data[3] -
627                  data[8]*data[6]*data[3] +
628                  data[8]*data[2]*data[7] -
629                  data[0]*data[10]*data[7] -
630                  data[4]*data[2]*data[11] +
631                  data[0]*data[6]*data[11]) * det;
632
633    dstData[11] = (data[8]*data[5]*data[3] -
634                   data[4]*data[9]*data[3] -
635                   data[8]*data[1]*data[7] +
636                   data[0]*data[9]*data[7] +
637                   data[4]*data[1]*data[11] -
638                   data[0]*data[5]*data[11]) * det;
639
640    dstData[15] = (data[4]*data[9]*data[2] -
641                   data[8]*data[5]*data[2] +
642                   data[8]*data[1]*data[6] -
643                   data[0]*data[9]*data[6] -
644                   data[4]*data[1]*data[10] +
645                   data[0]*data[5]*data[10]) * det;
646
647    set(dstData);
648}
649
650void Matrix4x4f::invertFast(const Matrix4x4f& mat)
651{
652    float *srcData = (float *)mat._data;
653
654    float det =
655        srcData[12] * srcData[9] * srcData[6] * srcData[3]-
656        srcData[8] * srcData[13] * srcData[6] * srcData[3]-
657        srcData[12] * srcData[5] * srcData[10] * srcData[3]+
658        srcData[4] * srcData[13] * srcData[10] * srcData[3]+
659        srcData[8] * srcData[5] * srcData[14] * srcData[3]-
660        srcData[4] * srcData[9] * srcData[14] * srcData[3]-
661        srcData[12] * srcData[9] * srcData[2] * srcData[7]+
662        srcData[8] * srcData[13] * srcData[2] * srcData[7]+
663        srcData[12] * srcData[1] * srcData[10] * srcData[7]-
664        srcData[0] * srcData[13] * srcData[10] * srcData[7]-
665        srcData[8] * srcData[1] * srcData[14] * srcData[7]+
666        srcData[0] * srcData[9] * srcData[14] * srcData[7]+
667        srcData[12] * srcData[5] * srcData[2] * srcData[11]-
668        srcData[4] * srcData[13] * srcData[2] * srcData[11]-
669        srcData[12] * srcData[1] * srcData[6] * srcData[11]+
670        srcData[0] * srcData[13] * srcData[6] * srcData[11]+
671        srcData[4] * srcData[1] * srcData[14] * srcData[11]-
672        srcData[0] * srcData[5] * srcData[14] * srcData[11]-
673        srcData[8] * srcData[5] * srcData[2] * srcData[15]+
674        srcData[4] * srcData[9] * srcData[2] * srcData[15]+
675        srcData[8] * srcData[1] * srcData[6] * srcData[15]-
676        srcData[0] * srcData[9] * srcData[6] * srcData[15]-
677        srcData[4] * srcData[1] * srcData[10] * srcData[15]+
678        srcData[0] * srcData[5] * srcData[10] * srcData[15];
679
680    if ( det == 0.0f ) return;
681    det = 1 / det;
682
683    _data[0] = (srcData[9]*srcData[14]*srcData[7] -
684                srcData[13]*srcData[10]*srcData[7] +
685                srcData[13]*srcData[6]*srcData[11] -
686                srcData[5]*srcData[14]*srcData[11] -
687                srcData[9]*srcData[6]*srcData[15] +
688                srcData[5]*srcData[10]*srcData[15]) * det;
689
690    _data[4] = (srcData[12]*srcData[10]*srcData[7] -
691                srcData[8]*srcData[14]*srcData[7] -
692                srcData[12]*srcData[6]*srcData[11] +
693                srcData[4]*srcData[14]*srcData[11] +
694                srcData[8]*srcData[6]*srcData[15] -
695                srcData[4]*srcData[10]*srcData[15]) * det;
696
697    _data[8] = (srcData[8]*srcData[13]*srcData[7] -
698                srcData[12]*srcData[9]*srcData[7] +
699                srcData[12]*srcData[5]*srcData[11] -
700                srcData[4]*srcData[13]*srcData[11] -
701                srcData[8]*srcData[5]*srcData[15] +
702                srcData[4]*srcData[9]*srcData[15]) * det;
703
704    _data[12] = (srcData[12]*srcData[9]*srcData[6] -
705                 srcData[8]*srcData[13]*srcData[6] -
706                 srcData[12]*srcData[5]*srcData[10] +
707                 srcData[4]*srcData[13]*srcData[10] +
708                 srcData[8]*srcData[5]*srcData[14] -
709                 srcData[4]*srcData[9]*srcData[14]) * det;
710
711    _data[1] = (srcData[13]*srcData[10]*srcData[3] -
712                srcData[9]*srcData[14]*srcData[3] -
713                srcData[13]*srcData[2]*srcData[11] +
714                srcData[1]*srcData[14]*srcData[11] +
715                srcData[9]*srcData[2]*srcData[15] -
716                srcData[1]*srcData[10]*srcData[15]) * det;
717
718    _data[5] = (srcData[8]*srcData[14]*srcData[3] -
719                srcData[12]*srcData[10]*srcData[3] +
720                srcData[12]*srcData[2]*srcData[11] -
721                srcData[0]*srcData[14]*srcData[11] -
722                srcData[8]*srcData[2]*srcData[15] +
723                srcData[0]*srcData[10]*srcData[15]) * det;
724
725    _data[9] = (srcData[12]*srcData[9]*srcData[3] -
726                srcData[8]*srcData[13]*srcData[3] -
727                srcData[12]*srcData[1]*srcData[11] +
728                srcData[0]*srcData[13]*srcData[11] +
729                srcData[8]*srcData[1]*srcData[15] -
730                srcData[0]*srcData[9]*srcData[15]) * det;
731
732    _data[13] = (srcData[8]*srcData[13]*srcData[2] -
733                 srcData[12]*srcData[9]*srcData[2] +
734                 srcData[12]*srcData[1]*srcData[10] -
735                 srcData[0]*srcData[13]*srcData[10] -
736                 srcData[8]*srcData[1]*srcData[14] +
737                 srcData[0]*srcData[9]*srcData[14]) * det;
738
739    _data[2] = (srcData[5]*srcData[14]*srcData[3] -
740                srcData[13]*srcData[6]*srcData[3] +
741                srcData[13]*srcData[2]*srcData[7] -
742                srcData[1]*srcData[14]*srcData[7] -
743                srcData[5]*srcData[2]*srcData[15] +
744                srcData[1]*srcData[6]*srcData[15]) * det;
745
746    _data[6] = (srcData[12]*srcData[6]*srcData[3] -
747                srcData[4]*srcData[14]*srcData[3] -
748                srcData[12]*srcData[2]*srcData[7] +
749                srcData[0]*srcData[14]*srcData[7] +
750                srcData[4]*srcData[2]*srcData[15] -
751                srcData[0]*srcData[6]*srcData[15]) * det;
752
753    _data[10] = (srcData[4]*srcData[13]*srcData[3] -
754                 srcData[12]*srcData[5]*srcData[3] +
755                 srcData[12]*srcData[1]*srcData[7] -
756                 srcData[0]*srcData[13]*srcData[7] -
757                 srcData[4]*srcData[1]*srcData[15] +
758                 srcData[0]*srcData[5]*srcData[15]) * det;
759
760    _data[14] = (srcData[12]*srcData[5]*srcData[2] -
761                 srcData[4]*srcData[13]*srcData[2] -
762                 srcData[12]*srcData[1]*srcData[6] +
763                 srcData[0]*srcData[13]*srcData[6] +
764                 srcData[4]*srcData[1]*srcData[14] -
765                 srcData[0]*srcData[5]*srcData[14]) * det;
766
767    _data[3] = (srcData[9]*srcData[6]*srcData[3] -
768                srcData[5]*srcData[10]*srcData[3] -
769                srcData[9]*srcData[2]*srcData[7] +
770                srcData[1]*srcData[10]*srcData[7] +
771                srcData[5]*srcData[2]*srcData[11] -
772                srcData[1]*srcData[6]*srcData[11]) * det;
773
774    _data[7] = (srcData[4]*srcData[10]*srcData[3] -
775                srcData[8]*srcData[6]*srcData[3] +
776                srcData[8]*srcData[2]*srcData[7] -
777                srcData[0]*srcData[10]*srcData[7] -
778                srcData[4]*srcData[2]*srcData[11] +
779                srcData[0]*srcData[6]*srcData[11]) * det;
780
781    _data[11] = (srcData[8]*srcData[5]*srcData[3] -
782                 srcData[4]*srcData[9]*srcData[3] -
783                 srcData[8]*srcData[1]*srcData[7] +
784                 srcData[0]*srcData[9]*srcData[7] +
785                 srcData[4]*srcData[1]*srcData[11] -
786                 srcData[0]*srcData[5]*srcData[11]) * det;
787
788    _data[15] = (srcData[4]*srcData[9]*srcData[2] -
789                 srcData[8]*srcData[5]*srcData[2] +
790                 srcData[8]*srcData[1]*srcData[6] -
791                 srcData[0]*srcData[9]*srcData[6] -
792                 srcData[4]*srcData[1]*srcData[10] +
793                 srcData[0]*srcData[5]*srcData[10]) * det;
794}
795
796void Matrix4x4f::transpose()
797{
798    float m[16];
799
800    m[0] = _data[0];
801    m[1] = _data[4];
802    m[2] = _data[8];
803    m[3] = _data[12];
804
805    m[4] = _data[1];
806    m[5] = _data[5];
807    m[6] = _data[9];
808    m[7] = _data[13];
809
810    m[8] = _data[2];
811    m[9] = _data[6];
812    m[10] = _data[10];
813    m[11] = _data[14];
814
815    m[12] = _data[3];
816    m[13] = _data[7];
817    m[14] = _data[11];
818    m[15] = _data[15];
819
820    set(m);
821}
822
823void Matrix4x4f::transposeFast(const Matrix4x4f& mat)
824{
825    _data[0] = mat._data[0];
826    _data[1] = mat._data[4];
827    _data[2] = mat._data[8];
828    _data[3] = mat._data[12];
829
830    _data[4] = mat._data[1];
831    _data[5] = mat._data[5];
832    _data[6] = mat._data[9];
833    _data[7] = mat._data[13];
834
835    _data[8] = mat._data[2];
836    _data[9] = mat._data[6];
837    _data[10] = mat._data[10];
838    _data[11] = mat._data[14];
839
840    _data[12] = mat._data[3];
841    _data[13] = mat._data[7];
842    _data[14] = mat._data[11];
843    _data[15] = mat._data[15];
844}
845
846void Matrix4x4f::transpose(const Matrix4x4f& mat)
847{
848    float m[16];
849
850    m[0] = mat._data[0];
851    m[1] = mat._data[4];
852    m[2] = mat._data[8];
853    m[3] = mat._data[12];
854
855    m[4] = mat._data[1];
856    m[5] = mat._data[5];
857    m[6] = mat._data[9];
858    m[7] = mat._data[13];
859
860    m[8] = mat._data[2];
861    m[9] = mat._data[6];
862    m[10] = mat._data[10];
863    m[11] = mat._data[14];
864
865    m[12] = mat._data[3];
866    m[13] = mat._data[7];
867    m[14] = mat._data[11];
868    m[15] = mat._data[15];
869
870    set(m);
871}
872
873void Matrix4x4f::setDouble(double *m)
874{
875    for (int i = 0; i < 16; ++i) {
876        _data[i] = (float)m[i];
877    }
878}
879
880void Matrix4x4f::multiply(const Matrix4x4f& mat1, const Vector3f& position)
881{
882    Matrix4x4f mat;
883    mat.makeTranslation(position);
884    multiply(mat1, mat);
885}
886
887void Matrix4x4f::multiply(const Matrix4x4f& mat1, const Rotation& rotation)
888{
889    Matrix4x4f mat;
890    mat.makeRotation(rotation);
891    multiply(mat1, mat);
892}
893
894void Matrix4x4f::multiply(const Vector3f& position, const Matrix4x4f& mat1)
895{
896    Matrix4x4f mat;
897    mat.makeTranslation(position);
898    multiply(mat, mat1);
899}
900
901void Matrix4x4f::multiply(const Rotation& rotation, const Matrix4x4f& mat1)
902{
903    Matrix4x4f mat;
904    mat.makeRotation(rotation);
905    multiply(mat, mat1);
906}
907
908void Matrix4x4f::makeVecRotVec(const Vector3f& vec1, const Vector3f& vec2)
909{
910    Vector3f axis = cross(vec1, vec2);
911
912    float angle = atan2(axis.length(), vec1.dot(vec2));
913    axis = axis.normalize();
914    makeRotation(axis.x, axis.y, axis.z, angle);
915}
916
917void Matrix4x4f::multiplyScale(const Matrix4x4f& mat1, const Vector3f& scale)
918{
919    Matrix4x4f mat;
920    mat.makeScale(scale);
921    multiply(mat1, mat);
922}
923
924void Matrix4x4f::multiplyScale(const Vector3f& scale, const Matrix4x4f& mat1)
925{
926    Matrix4x4f mat;
927    mat.makeScale(scale);
928    multiply(mat, mat1);
929}
Note: See TracBrowser for help on using the repository browser.