source: projectionDesigner/trunk/projdesigner/include/gmtl/Xforms.h @ 287

Last change on this file since 287 was 4, checked in by Torben Dannhauer, 15 years ago
File size: 22.9 KB
Line 
1/************************************************************** ggt-head beg
2 *
3 * GGT: Generic Graphics Toolkit
4 *
5 * Original Authors:
6 *   Allen Bierbaum
7 *
8 * -----------------------------------------------------------------
9 * File:          Xforms.h,v
10 * Date modified: 2004/11/12 01:34:49
11 * Version:       1.34
12 * -----------------------------------------------------------------
13 *
14 *********************************************************** ggt-head end */
15/*************************************************************** ggt-cpr beg
16*
17* GGT: The Generic Graphics Toolkit
18* Copyright (C) 2001,2002 Allen Bierbaum
19*
20* This library is free software; you can redistribute it and/or
21* modify it under the terms of the GNU Lesser General Public
22* License as published by the Free Software Foundation; either
23* version 2.1 of the License, or (at your option) any later version.
24*
25* This library is distributed in the hope that it will be useful,
26* but WITHOUT ANY WARRANTY; without even the implied warranty of
27* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
28* Lesser General Public License for more details.
29*
30* You should have received a copy of the GNU Lesser General Public
31* License along with this library; if not, write to the Free Software
32* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
33*
34 ************************************************************ ggt-cpr end */
35#ifndef _GMTL_XFORMS_H_
36#define _GMTL_XFORMS_H_
37
38#include <gmtl/Point.h>
39#include <gmtl/Vec.h>
40#include <gmtl/Matrix.h>
41#include <gmtl/MatrixOps.h>
42#include <gmtl/Quat.h>
43#include <gmtl/QuatOps.h>
44#include <gmtl/Ray.h>
45#include <gmtl/LineSeg.h>
46#include <gmtl/Util/StaticAssert.h>
47
48namespace gmtl
49{
50   /** @ingroup Transforms
51    *  @name Vector Transform (Quaternion)
52    *  @{
53    */
54   
55   /** transform a vector by a rotation quaternion.
56    * @pre give a vector, and a rotation quaternion (by definition, a rotation quaternion is normalized).
57    * @param result     The vector to write the result into
58    * @param rot        The quaternion
59    * @param vector     The original vector to transform
60    * @post v' = q P(v) q*  (where result is v', rot is q, and vector is v.  q* is conj(q), and P(v) is pure quaternion made from v)
61    * @see game programming gems #1 p199
62    * @see shoemake siggraph notes
63    * @notes for the implementation, inv and conj should both work for the "q*" in "Rv = q P(v) q*"
64    *        but conj is actually faster so we usually choose that.
65    * @notes also note, that if the input quat wasn't normalized (and thus isn't a rotation quat),
66    *        then this might not give the correct result, since conj and invert is only equiv when normalized...
67    */
68   template <typename DATA_TYPE>
69   inline VecBase<DATA_TYPE, 3>& xform( VecBase<DATA_TYPE, 3>& result, const Quat<DATA_TYPE>& rot, const VecBase<DATA_TYPE, 3>& vector )
70   {
71      // check preconditions...
72      gmtlASSERT( Math::isEqual( length( rot ), (DATA_TYPE)1.0, (DATA_TYPE)0.0001 ) && "must pass a rotation quaternion to xform(result,quat,vec) - by definition, a rotation quaternion is normalized).  if you need non-rotation quaternion support, let us know." );
73
74      // easiest to write and understand (slowest too)
75      //return result_vec = makeVec( rot * makePure( vector ) * makeConj( rot ) );
76
77      // completely hand expanded
78      // (faster by 28% in gcc 2.96 debug mode.)
79      // (faster by 35% in gcc 2.96 opt3 mode (78% for doubles))
80      Quat<DATA_TYPE> rot_conj( -rot[Xelt], -rot[Yelt], -rot[Zelt], rot[Welt] );
81      Quat<DATA_TYPE> pure( vector[0], vector[1], vector[2], (DATA_TYPE)0.0 );
82      Quat<DATA_TYPE> temp(
83         pure[Welt]*rot_conj[Xelt] + pure[Xelt]*rot_conj[Welt] + pure[Yelt]*rot_conj[Zelt] - pure[Zelt]*rot_conj[Yelt],
84         pure[Welt]*rot_conj[Yelt] + pure[Yelt]*rot_conj[Welt] + pure[Zelt]*rot_conj[Xelt] - pure[Xelt]*rot_conj[Zelt],
85         pure[Welt]*rot_conj[Zelt] + pure[Zelt]*rot_conj[Welt] + pure[Xelt]*rot_conj[Yelt] - pure[Yelt]*rot_conj[Xelt],
86         pure[Welt]*rot_conj[Welt] - pure[Xelt]*rot_conj[Xelt] - pure[Yelt]*rot_conj[Yelt] - pure[Zelt]*rot_conj[Zelt] );
87
88      result.set(
89         rot[Welt]*temp[Xelt] + rot[Xelt]*temp[Welt] + rot[Yelt]*temp[Zelt] - rot[Zelt]*temp[Yelt],
90         rot[Welt]*temp[Yelt] + rot[Yelt]*temp[Welt] + rot[Zelt]*temp[Xelt] - rot[Xelt]*temp[Zelt],
91         rot[Welt]*temp[Zelt] + rot[Zelt]*temp[Welt] + rot[Xelt]*temp[Yelt] - rot[Yelt]*temp[Xelt] );
92      return result;
93   }
94
95   /** transform a vector by a rotation quaternion.
96    * @pre give a vector, and a rotation quaternion (by definition, a rotation quaternion is normalized).
97    * @param rot        The quaternion
98    * @param vector     The original vector to transform
99    * @return  the resulting vector transformed by the quaternion
100    * @post v' = q P(v) q*  (where result is v', rot is q, and vector is v.  q* is conj(q), and P(v) is pure quaternion made from v)
101    */
102   template <typename DATA_TYPE>
103   inline VecBase<DATA_TYPE, 3> operator*( const Quat<DATA_TYPE>& rot, const VecBase<DATA_TYPE, 3>& vector )
104   {
105      VecBase<DATA_TYPE, 3> temporary;
106      return xform( temporary, rot, vector );
107   }
108
109
110   /** transform a vector by a rotation quaternion.
111    * @pre give a vector, and a rotation quaternion (by definition, a rotation quaternion is normalized).
112    * @param rot        The quaternion
113    * @param vector     The original vector to transform
114    * @post v' = q P(v) q*  (where result is v', rot is q, and vector is v.  q* is conj(q), and P(v) is pure quaternion made from v)
115    */   
116   template <typename DATA_TYPE>
117   inline VecBase<DATA_TYPE, 3> operator*=(VecBase<DATA_TYPE, 3>& vector, const Quat<DATA_TYPE>& rot)
118   {
119      VecBase<DATA_TYPE, 3> temporary = vector;
120      return xform( vector, rot, temporary);
121   }
122
123
124   /** @} */
125
126   /** @ingroup Transforms
127    *  @name Vector Transform (Matrix)
128    *  @{
129    */
130
131   /** xform a vector by a matrix.
132    *  Transforms a vector with a matrix, uses multiplication of [m x k] matrix by a [k x 1] matrix (the later also known as a Vector...).
133    *  @param result        the vector to write the result in
134    *  @param matrix        the transform matrix
135    *  @param vector        the original vector
136    *  @post This results in a rotational xform of the vector (assumes you know what you are doing -
137    *  i.e. that you know that the last component of a vector by definition is 0.0, and changing
138    *  this might make the xform different than what you may expect).
139    *  @post returns a point same size as the matrix rows...  (v[r][1] = m[r][k] * v[k][1])
140    */
141   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
142   inline Vec<DATA_TYPE, COLS>& xform( Vec<DATA_TYPE, COLS>& result, const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Vec<DATA_TYPE, COLS>& vector )
143   {
144      // do a standard [m x k] by [k x n] matrix multiplication (where n == 0).
145
146      // reset vec to zero...
147      result = Vec<DATA_TYPE, COLS>();
148
149      for (unsigned iRow = 0; iRow < ROWS; ++iRow)
150      for (unsigned iCol = 0; iCol < COLS; ++iCol)
151         result[iRow] += matrix( iRow, iCol ) * vector[iCol];
152
153      return result;
154   }
155
156
157   /** matrix * vector xform.
158    *  multiplication of [m x k] matrix by a [k x 1] matrix (also known as a Vector...).
159    *  @param matrix    the transform matrix
160    *  @param vector    the original vector
161    *  @return  the vector transformed by the matrix
162    *  @post This results in a full matrix xform of the vector (assumes you know what you are doing -
163    *  i.e. that you know that the last component of a vector by definition is 0.0, and changing
164    *  this might make the xform different that what you may expect).
165    *  @post returns a vec same size as the matrix rows...  (v[r][1] = m[r][k] * v[k][1])
166    */
167   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
168   inline Vec<DATA_TYPE, COLS> operator*( const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Vec<DATA_TYPE, COLS>& vector )
169   {
170      // do a standard [m x k] by [k x n] matrix multiplication (where n == 0).
171      Vec<DATA_TYPE, COLS> temporary;
172      return xform( temporary, matrix, vector );
173   }
174
175
176
177
178   /** partially transform a partially specified vector by a matrix, assumes last elt of vector is 0 (the 0 makes it only partially transformed).
179    *  Transforms a vector with a matrix, uses multiplication of [m x k] matrix by a [k-1 x 1] matrix (also known as a Vector [with w == 0 for vectors by definition] ).
180    *  @param result        the vector to write the result in
181    *  @param matrix        the transform matrix
182    *  @param vector        the original vector
183    *  @post the [k-1 x 1] vector you pass in is treated as a [vector, 0.0]
184    *  @post This ends up being a partial xform using only the rotation from the matrix (vector xformed result is untranslated).
185    */
186   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS, unsigned VEC_SIZE>
187   inline Vec<DATA_TYPE, VEC_SIZE>& xform( Vec<DATA_TYPE, VEC_SIZE >& result, const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Vec<DATA_TYPE, VEC_SIZE >& vector )
188   {
189      GMTL_STATIC_ASSERT( VEC_SIZE == COLS - 1, Vec_of_wrong_size_for_xform );
190      // do a standard [m x k] by [k x n] matrix multiplication (where n == 0).
191
192      // copy the point to the correct size.
193      Vec<DATA_TYPE, COLS> temp_vector, temp_result;
194      for (unsigned x = 0; x < VEC_SIZE; ++x)
195         temp_vector[x] = vector[x];
196      temp_vector[COLS-1] = (DATA_TYPE)0.0; // by definition of a vector, set the last unspecified elt to 0.0
197
198      // transform it.
199      xform<DATA_TYPE, ROWS, COLS>( temp_result, matrix, temp_vector );
200
201      // convert result back to vec<DATA_TYPE, VEC_SIZE>
202      // some matrices will make the W param large even if this is a true vector,
203      // we'll need to redistribute it to the other elts if W param is non-zero
204      if (Math::isEqual( temp_result[VEC_SIZE], (DATA_TYPE)0, (DATA_TYPE)0.0001 ) == false)
205      {
206         DATA_TYPE w_coord_div = DATA_TYPE( 1.0 ) / temp_result[VEC_SIZE];
207         for (unsigned x = 0; x < VEC_SIZE; ++x)
208            result[x] = temp_result[x] * w_coord_div;
209      }
210      else
211      {
212         for (unsigned x = 0; x < VEC_SIZE; ++x)
213            result[x] = temp_result[x];
214      }
215
216      return result;
217   }
218
219   /** matrix * partial vector, assumes last elt of vector is 0 (partial transform).
220    *  @param matrix        the transform matrix
221    *  @param vector        the original vector
222    *  @return  the vector transformed by the matrix
223    *  multiplication of [m x k] matrix by a [k-1 x 1] matrix (also known as a Vector [with w == 0 for vectors by definition] ).
224    *  @post the [k-1 x 1] vector you pass in is treated as a [vector, 0.0]
225    *  @post This ends up being a partial xform using only the rotation from the matrix (vector xformed result is untranslated).
226    */
227   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS, unsigned COLS_MINUS_ONE>
228   inline Vec<DATA_TYPE, COLS_MINUS_ONE> operator*( const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Vec<DATA_TYPE, COLS_MINUS_ONE>& vector )
229   {
230      Vec<DATA_TYPE, COLS_MINUS_ONE> temporary;
231      return xform( temporary, matrix, vector );
232   }
233
234   /** @} */
235
236   /** @ingroup Transforms
237    *  @name Point Transform (Matrix)
238    *  @{
239    */
240
241
242   /** transform point by a matrix.
243    *  multiplication of [m x k] matrix by a [k x 1] matrix (also known as a Point...).
244    *  @param result        the point to write the result in
245    *  @param matrix        the transform matrix
246    *  @param point         the original point
247    *  @post This results in a full matrix xform of the point.
248    *  @post returns a point same size as the matrix rows...  (p[r][1] = m[r][k] * p[k][1])
249    */
250   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
251   inline Point<DATA_TYPE, COLS>& xform( Point<DATA_TYPE, COLS>& result, const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Point<DATA_TYPE, COLS>& point )
252   {
253      // do a standard [m x k] by [k x n] matrix multiplication (n == 1).
254
255      // reset point to zero...
256      result = Point<DATA_TYPE, COLS>();
257
258      for (unsigned iRow = 0; iRow < ROWS; ++iRow)
259      for (unsigned iCol = 0; iCol < COLS; ++iCol)
260         result[iRow] += matrix( iRow, iCol ) * point[iCol];
261
262      return result;
263   }
264
265   /** matrix * point.
266    *  multiplication of [m x k] matrix by a [k x 1] matrix (also known as a Point...).
267    *  @param matrix        the transform matrix
268    *  @param point         the original point
269    *  @return  the point transformed by the matrix
270    *  @post This results in a full matrix xform of the point.
271    *  @post returns a point same size as the matrix rows...  (p[r][1] = m[r][k] * p[k][1])
272    */
273   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
274   inline Point<DATA_TYPE, COLS> operator*( const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Point<DATA_TYPE, COLS>& point )
275   {
276      Point<DATA_TYPE, COLS> temporary;
277      return xform( temporary, matrix, point );
278   }
279
280
281
282
283   /** transform a partially specified point by a matrix, assumes last elt of point is 1.
284    *  Transforms a point with a matrix, uses multiplication of [m x k] matrix by a [k-1 x 1] matrix (also known as a Point [with w == 1 for points by definition] ).
285    *  @param result        the point to write the result in
286    *  @param matrix        the transform matrix
287    *  @param point         the original point
288    *  @post the [k-1 x 1] point you pass in is treated as [point, 1.0]
289    *  @post This results in a full matrix xform of the point.
290    * @todo we need a PointOps.h operator*=(scalar) function
291    */
292   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS, unsigned PNT_SIZE>
293   inline Point<DATA_TYPE, PNT_SIZE>& xform( Point<DATA_TYPE, PNT_SIZE>& result, const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Point<DATA_TYPE, PNT_SIZE>& point )
294   {
295      //gmtlSERT( PNT_SIZE == COLS - 1 && "The precondition of this method is that the vector size must be one less than the number of columns in the matrix.  eg. if Mat<n,k>, then Vec<k-1>." );
296      GMTL_STATIC_ASSERT( PNT_SIZE == COLS-1, Point_not_of_size_mat_col_minus_1_as_required_for_xform);
297
298      // copy the point to the correct size.
299      Point<DATA_TYPE, PNT_SIZE+1> temp_point, temp_result;
300      for (unsigned x = 0; x < PNT_SIZE; ++x)
301         temp_point[x] = point[x];
302      temp_point[PNT_SIZE] = (DATA_TYPE)1.0; // by definition of a point, set the last unspecified elt to 1.0
303
304      // transform it.
305      xform<DATA_TYPE, ROWS, COLS>( temp_result, matrix, temp_point );
306
307      // convert result back to pnt<DATA_TYPE, PNT_SIZE>
308      // some matrices will make the W param large even if this is a true vector,
309      // we'll need to redistribute it to the other elts if W param is non-zero
310      if (Math::isEqual( temp_result[PNT_SIZE], (DATA_TYPE)0, (DATA_TYPE)0.0001 ) == false)
311      {
312         DATA_TYPE w_coord_div = DATA_TYPE( 1.0 ) / temp_result[PNT_SIZE];
313         for (unsigned x = 0; x < PNT_SIZE; ++x)
314            result[x] = temp_result[x] * w_coord_div;
315      }
316      else
317      {
318         for (unsigned x = 0; x < PNT_SIZE; ++x)
319            result[x] = temp_result[x];
320      }
321
322      return result;
323   }
324
325   /** matrix * partially specified point.
326    *  multiplication of [m x k] matrix by a [k-1 x 1] matrix (also known as a Point [with w == 1 for points by definition] ).
327    *  @param matrix        the transform matrix
328    *  @param point         the original point
329    *  @return  the point transformed by the matrix
330    *  @post the [k-1 x 1] vector you pass in is treated as a [point, 1.0]
331    *  @post This results in a full matrix xform of the point.
332    */
333   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS, unsigned COLS_MINUS_ONE>
334   inline Point<DATA_TYPE, COLS_MINUS_ONE> operator*( const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Point<DATA_TYPE, COLS_MINUS_ONE>& point )
335   {
336      Point<DATA_TYPE, COLS_MINUS_ONE> temporary;
337      return xform( temporary, matrix, point );
338   }
339
340   /** point * a matrix
341    *  multiplication of [m x k] matrix by a [k x 1] matrix (also known as a Point [with w == 1 for points by definition] ).
342    *  @param matrix        the transform matrix
343    *  @param point         the original point
344    *  @return  the point transformed by the matrix
345    *  @post This results in a full matrix xform of the point.
346    */
347   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
348   inline Point<DATA_TYPE, COLS> operator*( const Point<DATA_TYPE, COLS>& point, const Matrix<DATA_TYPE, ROWS, COLS>& matrix )
349   {
350      Point<DATA_TYPE, COLS> temporary;
351      return xform( temporary, matrix, point );
352   }
353
354
355   /** point *= a matrix
356    *  multiplication of [m x k] matrix by a [k x 1] matrix (also known as a Point [with w == 1 for points by definition] ).
357    *  @param matrix        the transform matrix
358    *  @param point         the original point
359    *  @return  the point transformed by the matrix
360    *  @post This results in a full matrix xform of the point.
361    */
362   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
363   inline Point<DATA_TYPE, COLS> operator*=(Point<DATA_TYPE, COLS>& point, const Matrix<DATA_TYPE, ROWS, COLS>& matrix)
364   {
365      Point<DATA_TYPE, COLS> temporary = point;
366      return xform( point, matrix, temporary);
367   }
368
369   /** partial point *= a matrix
370    *  multiplication of [m x k] matrix by a [k-1 x 1] matrix (also known as a Point [with w == 1 for points by definition] ).
371    *  @param matrix        the transform matrix
372    *  @param point         the original point
373    *  @return  the point transformed by the matrix
374    *  @post the [k-1 x 1] vector you pass in is treated as a [point, 1.0]
375    *  @post This results in a full matrix xform of the point.
376    */
377   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS, unsigned COLS_MINUS_ONE>
378   inline Point<DATA_TYPE, COLS_MINUS_ONE>& operator*=( Point<DATA_TYPE, COLS_MINUS_ONE>& point, const Matrix<DATA_TYPE, ROWS, COLS>& matrix )
379   {
380      Point<DATA_TYPE, COLS_MINUS_ONE> temporary = point;
381      return xform( point, matrix, temporary);
382   }
383
384
385   /** @} */
386
387   /** transform ray by a matrix.
388    *  multiplication of [m x k] matrix by two [k x 1] matrices (also known as a ray...).
389    *  @param result        the ray to write the result in
390    *  @param matrix        the transform matrix
391    *  @param ray           the original ray
392    *  @post This results in a full matrix xform of the ray.
393    *  @post returns a ray same size as the matrix rows...  (p[r][1] = m[r][k] * p[k][1])
394    */
395   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
396   inline Ray<DATA_TYPE>& xform( Ray<DATA_TYPE>& result, const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Ray<DATA_TYPE>& ray )
397   {
398      gmtl::Point<DATA_TYPE, 3> pos;
399      gmtl::Vec<DATA_TYPE, 3> dir;
400      result.setOrigin( xform( pos, matrix, ray.getOrigin() ) );
401      result.setDir( xform( dir, matrix, ray.getDir() ) );
402      return result;
403   }
404
405   /** ray * a matrix
406    *  multiplication of [m x k] matrix by a ray.
407    *  @param matrix        the transform matrix
408    *  @param ray           the original ray
409    *  @return  the ray transformed by the matrix
410    *  @post This results in a full matrix xform of the ray.
411    */
412   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
413   inline Ray<DATA_TYPE> operator*( const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const Ray<DATA_TYPE>& ray )
414   {
415      Ray<DATA_TYPE> temporary;
416      return xform( temporary, matrix, ray );
417   }
418
419
420   /** ray *= a matrix
421    *  multiplication of [m x k] matrix by a ray.
422    *  @param matrix        the transform matrix
423    *  @param ray           the original ray
424    *  @return  the ray transformed by the matrix
425    *  @post This results in a full matrix xform of the ray.
426    */
427   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
428   inline Ray<DATA_TYPE>& operator*=( Ray<DATA_TYPE>& ray, const Matrix<DATA_TYPE, ROWS, COLS>& matrix )
429   {
430      Ray<DATA_TYPE> temporary = ray;
431      return xform( ray, matrix, temporary);
432   }
433
434   /** transform seg by a matrix.
435    *  multiplication of [m x k] matrix by two [k x 1] matrices (also known as a seg...).
436    *  @param result        the seg to write the result in
437    *  @param matrix        the transform matrix
438    *  @param seg           the original seg
439    *  @post This results in a full matrix xform of the seg.
440    *  @post returns a seg same size as the matrix rows...  (p[r][1] = m[r][k] * p[k][1])
441    */
442   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
443   inline LineSeg<DATA_TYPE>& xform( LineSeg<DATA_TYPE>& result, const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const LineSeg<DATA_TYPE>& seg )
444   {
445      gmtl::Point<DATA_TYPE, 3> pos;
446      gmtl::Vec<DATA_TYPE, 3> dir;
447      result.setOrigin( xform( pos, matrix, seg.getOrigin() ) );
448      result.setDir( xform( dir, matrix, seg.getDir() ) );
449      return result;
450   }
451
452   /** seg * a matrix
453    *  multiplication of [m x k] matrix by a seg.
454    *  @param matrix        the transform matrix
455    *  @param seg         the original ray
456    *  @return  the seg transformed by the matrix
457    *  @post This results in a full matrix xform of the seg.
458    */
459   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
460   inline LineSeg<DATA_TYPE> operator*( const Matrix<DATA_TYPE, ROWS, COLS>& matrix, const LineSeg<DATA_TYPE>& seg )
461   {
462      LineSeg<DATA_TYPE> temporary;
463      return xform( temporary, matrix, seg );
464   }
465
466
467   /** seg *= a matrix
468    *  multiplication of [m x k] matrix by a seg.
469    *  @param matrix        the transform matrix
470    *  @param seg         the original point
471    *  @return  the point transformed by the matrix
472    *  @post This results in a full matrix xform of the point.
473    */
474   template <typename DATA_TYPE, unsigned ROWS, unsigned COLS>
475   inline LineSeg<DATA_TYPE>& operator*=( LineSeg<DATA_TYPE>& seg, const Matrix<DATA_TYPE, ROWS, COLS>& matrix )
476   {
477      LineSeg<DATA_TYPE> temporary = seg;
478      return xform( seg, matrix, temporary);
479   }
480
481
482
483
484   // old xform stuff...
485/*
486// XXX: Assuming that there is no projective portion to the matrix or homogeneous coord
487// NOTE: It is a vec, so we don't deal with the translation
488Vec3 operator*(const Matrix& mat, const Vec3& vec)
489{
490
491   Vec3 ret_vec;
492   for(int iRow=0;iRow<3;iRow++)
493   {
494      ret_vec[iRow] = (vec[0]* (mat[0][iRow]))
495                    + (vec[1]* (mat[1][iRow]))
496                    + (vec[2]* (mat[2][iRow]));
497   }
498   return ret_vec;
499}
500
501// XXX: Assuming no projective or homogeneous coord to the mat
502Point3 operator*(const Matrix& mat, const Point3& point)
503{
504   Point3 ret_pt;
505   for(int iRow=0;iRow<3;iRow++)
506   {
507      ret_pt[iRow] = (point[0]* (mat[0][iRow]))
508                   + (point[1]* (mat[1][iRow]))
509                   + (point[2]* (mat[2][iRow]))
510                   + (mat[3][iRow]);
511   }
512   return ret_pt;
513}
514
515// Xform an OOB by a matrix
516// NOTE: This will NOT work if the matrix has shear or scale
517OOBox operator*(const Matrix& mat, const OOBox& box)
518{
519   OOBox ret_box;
520
521   ret_box.center() = mat * box.center();
522
523   ret_box.axis(0) = mat * ret_box.axis(0);
524   ret_box.axis(1) = mat * ret_box.axis(1);
525   ret_box.axis(2) = mat * ret_box.axis(2);
526
527   ret_box.halfLen(0) = box.halfLen(0);
528   ret_box.halfLen(1) = box.halfLen(1);
529   ret_box.halfLen(2) = box.halfLen(2);
530
531   return ret_box;
532}
533*/
534
535};
536
537#endif
Note: See TracBrowser for help on using the repository browser.