2 Copyright (c) 2006 - 2008 The Open Toolkit library.
4 Permission is hereby granted, free of charge, to any person obtaining a copy of
5 this software and associated documentation files (the "Software"), to deal in
6 the Software without restriction, including without limitation the rights to
7 use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
8 of the Software, and to permit persons to whom the Software is furnished to do
9 so, subject to the following conditions:
11 The above copyright notice and this permission notice shall be included in all
12 copies or substantial portions of the Software.
14 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
28 /// Represents a 2x3 matrix.
30 public struct Matrix2x3d : IEquatable<Matrix2x3d>
33 /// Top row of the matrix.
38 /// Bottom row of the matrix.
45 public static readonly Matrix2x3d Zero = new Matrix2x3d(Vector3d.Zero, Vector3d.Zero);
48 /// Constructs a new instance.
50 /// <param name="row0">Top row of the matrix.</param>
51 /// <param name="row1">Bottom row of the matrix.</param>
52 public Matrix2x3d(Vector3d row0, Vector3d row1)
59 /// Constructs a new instance
61 /// <param name="m00">First item of the first row of the matrix.</param>
62 /// <param name="m01">Second item of the first row of the matrix.</param>
63 /// <param name="m02">Third item of the first row of the matrix.</param>
64 /// <param name="m10">First item of the second row of the matrix.</param>
65 /// <param name="m11">Second item of the second row of the matrix.</param>
66 /// <param name="m12">Third item of the second row of the matrix.</param>
68 double m00, double m01, double m02,
69 double m10, double m11, double m12)
71 Row0 = new Vector3d(m00, m01, m02);
72 Row1 = new Vector3d(m10, m11, m12);
76 /// Gets or sets the first column of this matrix.
78 public Vector2d Column0
80 get { return new Vector2d(Row0.X, Row1.X); }
81 set { Row0.X = value.X; Row1.X = value.Y; }
85 /// Gets or sets the second column of this matrix.
87 public Vector2d Column1
89 get { return new Vector2d(Row0.Y, Row1.Y); }
90 set { Row0.Y = value.X; Row1.Y = value.Y; }
94 /// Gets or sets the third column of this matrix.
96 public Vector2d Column2
98 get { return new Vector2d(Row0.Z, Row1.Z); }
99 set { Row0.Z = value.X; Row1.Z = value.Y; }
103 /// Gets or sets the value at row 1, column 1 of this instance.
105 public double M11 { get { return Row0.X; } set { Row0.X = value; } }
108 /// Gets or sets the value at row 1, column 2 of this instance.
110 public double M12 { get { return Row0.Y; } set { Row0.Y = value; } }
113 /// Gets or sets the value at row 1, column 3 of this instance.
115 public double M13 { get { return Row0.Z; } set { Row0.Z = value; } }
118 /// Gets or sets the value at row 2, column 1 of this instance.
120 public double M21 { get { return Row1.X; } set { Row1.X = value; } }
123 /// Gets or sets the value at row 2, column 2 of this instance.
125 public double M22 { get { return Row1.Y; } set { Row1.Y = value; } }
128 /// Gets or sets the value at row 2, column 3 of this instance.
130 public double M23 { get { return Row1.Z; } set { Row1.Z = value; } }
133 /// Gets or sets the values along the main diagonal of the matrix.
135 public Vector2d Diagonal
139 return new Vector2d(Row0.X, Row1.Y);
149 /// Gets the trace of the matrix, the sum of the values along the diagonal.
151 public double Trace { get { return Row0.X + Row1.Y; } }
154 /// Gets or sets the value at a specified row and column.
156 public double this[int rowIndex, int columnIndex]
162 return Row0[columnIndex];
164 else if (rowIndex == 1)
166 return Row1[columnIndex];
168 throw new IndexOutOfRangeException("You tried to access this matrix at: (" + rowIndex + ", " + columnIndex + ")");
174 Row0[columnIndex] = value;
176 else if (rowIndex == 1)
178 Row1[columnIndex] = value;
182 throw new IndexOutOfRangeException("You tried to set this matrix at: (" + rowIndex + ", " + columnIndex + ")");
188 /// Builds a rotation matrix.
190 /// <param name="angle">The counter-clockwise angle in radians.</param>
191 /// <param name="result">The resulting Matrix2x3d instance.</param>
192 public static void CreateRotation(double angle, out Matrix2x3d result)
194 double cos = System.Math.Cos(angle);
195 double sin = System.Math.Sin(angle);
200 result.Row1.X = -sin;
206 /// Builds a rotation matrix.
208 /// <param name="angle">The counter-clockwise angle in radians.</param>
209 /// <returns>The resulting Matrix2x3d instance.</returns>
210 public static Matrix2x3d CreateRotation(double angle)
213 CreateRotation(angle, out result);
218 /// Creates a scale matrix.
220 /// <param name="scale">Single scale factor for the x, y, and z axes.</param>
221 /// <param name="result">A scale matrix.</param>
222 public static void CreateScale(double scale, out Matrix2x3d result)
224 result.Row0.X = scale;
228 result.Row1.Y = scale;
233 /// Creates a scale matrix.
235 /// <param name="scale">Single scale factor for the x and y axes.</param>
236 /// <returns>A scale matrix.</returns>
237 public static Matrix2x3d CreateScale(double scale)
240 CreateScale(scale, out result);
245 /// Creates a scale matrix.
247 /// <param name="scale">Scale factors for the x and y axes.</param>
248 /// <param name="result">A scale matrix.</param>
249 public static void CreateScale(Vector2d scale, out Matrix2x3d result)
251 result.Row0.X = scale.X;
255 result.Row1.Y = scale.Y;
260 /// Creates a scale matrix.
262 /// <param name="scale">Scale factors for the x and y axes.</param>
263 /// <returns>A scale matrix.</returns>
264 public static Matrix2x3d CreateScale(Vector2d scale)
267 CreateScale(scale, out result);
272 /// Creates a scale matrix.
274 /// <param name="x">Scale factor for the x axis.</param>
275 /// <param name="y">Scale factor for the y axis.</param>
276 /// <param name="result">A scale matrix.</param>
277 public static void CreateScale(double x, double y, out Matrix2x3d result)
288 /// Creates a scale matrix.
290 /// <param name="x">Scale factor for the x axis.</param>
291 /// <param name="y">Scale factor for the y axis.</param>
292 /// <returns>A scale matrix.</returns>
293 public static Matrix2x3d CreateScale(double x, double y)
296 CreateScale(x, y, out result);
301 /// Multiplies and instance by a scalar.
303 /// <param name="left">The left operand of the multiplication.</param>
304 /// <param name="right">The right operand of the multiplication.</param>
305 /// <param name="result">A new instance that is the result of the multiplication.</param>
306 public static void Mult(ref Matrix2x3d left, double right, out Matrix2x3d result)
308 result.Row0.X = left.Row0.X * right;
309 result.Row0.Y = left.Row0.Y * right;
310 result.Row0.Z = left.Row0.Z * right;
311 result.Row1.X = left.Row1.X * right;
312 result.Row1.Y = left.Row1.Y * right;
313 result.Row1.Z = left.Row1.Z * right;
317 /// Multiplies and instance by a scalar.
319 /// <param name="left">The left operand of the multiplication.</param>
320 /// <param name="right">The right operand of the multiplication.</param>
321 /// <returns>A new instance that is the result of the multiplication.</returns>
322 public static Matrix2x3d Mult(Matrix2x3d left, double right)
325 Mult(ref left, right, out result);
330 /// Multiplies two instances.
332 /// <param name="left">The left operand of the multiplication.</param>
333 /// <param name="right">The right operand of the multiplication.</param>
334 /// <param name="result">A new instance that is the result of the multiplication.</param>
335 public static void Mult(ref Matrix2x3d left, ref Matrix3x2 right, out Matrix2d result)
337 double lM11 = left.Row0.X, lM12 = left.Row0.Y, lM13 = left.Row0.Z,
338 lM21 = left.Row1.X, lM22 = left.Row1.Y, lM23 = left.Row1.Z,
339 rM11 = right.Row0.X, rM12 = right.Row0.Y,
340 rM21 = right.Row1.X, rM22 = right.Row1.Y,
341 rM31 = right.Row2.X, rM32 = right.Row2.Y;
343 result.Row0.X = ((lM11 * rM11) + (lM12 * rM21)) + (lM13 * rM31);
344 result.Row0.Y = ((lM11 * rM12) + (lM12 * rM22)) + (lM13 * rM32);
345 result.Row1.X = ((lM21 * rM11) + (lM22 * rM21)) + (lM23 * rM31);
346 result.Row1.Y = ((lM21 * rM12) + (lM22 * rM22)) + (lM23 * rM32);
350 /// Multiplies two instances.
352 /// <param name="left">The left operand of the multiplication.</param>
353 /// <param name="right">The right operand of the multiplication.</param>
354 /// <returns>A new instance that is the result of the multiplication.</returns>
355 public static Matrix2d Mult(Matrix2x3d left, Matrix3x2 right)
358 Mult(ref left, ref right, out result);
363 /// Multiplies two instances.
365 /// <param name="left">The left operand of the multiplication.</param>
366 /// <param name="right">The right operand of the multiplication.</param>
367 /// <param name="result">A new instance that is the result of the multiplication.</param>
368 public static void Mult(ref Matrix2x3d left, ref Matrix3 right, out Matrix2x3d result)
370 double lM11 = left.Row0.X, lM12 = left.Row0.Y, lM13 = left.Row0.Z,
371 lM21 = left.Row1.X, lM22 = left.Row1.Y, lM23 = left.Row1.Z,
372 rM11 = right.Row0.X, rM12 = right.Row0.Y, rM13 = right.Row0.Z,
373 rM21 = right.Row1.X, rM22 = right.Row1.Y, rM23 = right.Row1.Z,
374 rM31 = right.Row2.X, rm32 = right.Row2.Y, rM33 = right.Row2.Z;
376 result.Row0.X = ((lM11 * rM11) + (lM12 * rM21)) + (lM13 * rM31);
377 result.Row0.Y = ((lM11 * rM12) + (lM12 * rM22)) + (lM13 * rm32);
378 result.Row0.Z = ((lM11 * rM13) + (lM12 * rM23)) + (lM13 * rM33);
379 result.Row1.X = ((lM21 * rM11) + (lM22 * rM21)) + (lM23 * rM31);
380 result.Row1.Y = ((lM21 * rM12) + (lM22 * rM22)) + (lM23 * rm32);
381 result.Row1.Z = ((lM21 * rM13) + (lM22 * rM23)) + (lM23 * rM33);
385 /// Multiplies two instances.
387 /// <param name="left">The left operand of the multiplication.</param>
388 /// <param name="right">The right operand of the multiplication.</param>
389 /// <returns>A new instance that is the result of the multiplication.</returns>
390 public static Matrix2x3d Mult(Matrix2x3d left, Matrix3 right)
393 Mult(ref left, ref right, out result);
398 /// Multiplies two instances.
400 /// <param name="left">The left operand of the multiplication.</param>
401 /// <param name="right">The right operand of the multiplication.</param>
402 /// <param name="result">A new instance that is the result of the multiplication.</param>
403 public static void Mult(ref Matrix2x3d left, ref Matrix3x4 right, out Matrix2x4d result)
405 double lM11 = left.Row0.X, lM12 = left.Row0.Y, lM13 = left.Row0.Z,
406 lM21 = left.Row1.X, lM22 = left.Row1.Y, lM23 = left.Row1.Z,
407 rM11 = right.Row0.X, rM12 = right.Row0.Y, rM13 = right.Row0.Z, rM14 = right.Row0.W,
408 rM21 = right.Row1.X, rM22 = right.Row1.Y, rM23 = right.Row1.Z, rM24 = right.Row1.W,
409 rM31 = right.Row2.X, rm32 = right.Row2.Y, rM33 = right.Row2.Z, rM34 = right.Row2.W;
411 result.Row0.X = ((lM11 * rM11) + (lM12 * rM21)) + (lM13 * rM31);
412 result.Row0.Y = ((lM11 * rM12) + (lM12 * rM22)) + (lM13 * rm32);
413 result.Row0.Z = ((lM11 * rM13) + (lM12 * rM23)) + (lM13 * rM33);
414 result.Row0.W = ((lM11 * rM14) + (lM12 * rM24)) + (lM13 * rM34);
415 result.Row1.X = ((lM21 * rM11) + (lM22 * rM21)) + (lM23 * rM31);
416 result.Row1.Y = ((lM21 * rM12) + (lM22 * rM22)) + (lM23 * rm32);
417 result.Row1.Z = ((lM21 * rM13) + (lM22 * rM23)) + (lM23 * rM33);
418 result.Row1.W = ((lM21 * rM14) + (lM22 * rM24)) + (lM23 * rM34);
422 /// Multiplies two instances.
424 /// <param name="left">The left operand of the multiplication.</param>
425 /// <param name="right">The right operand of the multiplication.</param>
426 /// <returns>A new instance that is the result of the multiplication.</returns>
427 public static Matrix2x4d Mult(Matrix2x3d left, Matrix3x4 right)
430 Mult(ref left, ref right, out result);
435 /// Adds two instances.
437 /// <param name="left">The left operand of the addition.</param>
438 /// <param name="right">The right operand of the addition.</param>
439 /// <param name="result">A new instance that is the result of the addition.</param>
440 public static void Add(ref Matrix2x3d left, ref Matrix2x3d right, out Matrix2x3d result)
442 result.Row0.X = left.Row0.X + right.Row0.X;
443 result.Row0.Y = left.Row0.Y + right.Row0.Y;
444 result.Row0.Z = left.Row0.Z + right.Row0.Z;
445 result.Row1.X = left.Row1.X + right.Row1.X;
446 result.Row1.Y = left.Row1.Y + right.Row1.Y;
447 result.Row1.Z = left.Row1.Z + right.Row1.Z;
451 /// Adds two instances.
453 /// <param name="left">The left operand of the addition.</param>
454 /// <param name="right">The right operand of the addition.</param>
455 /// <returns>A new instance that is the result of the addition.</returns>
456 public static Matrix2x3d Add(Matrix2x3d left, Matrix2x3d right)
459 Add(ref left, ref right, out result);
464 /// Subtracts two instances.
466 /// <param name="left">The left operand of the subtraction.</param>
467 /// <param name="right">The right operand of the subtraction.</param>
468 /// <param name="result">A new instance that is the result of the subtraction.</param>
469 public static void Subtract(ref Matrix2x3d left, ref Matrix2x3d right, out Matrix2x3d result)
471 result.Row0.X = left.Row0.X - right.Row0.X;
472 result.Row0.Y = left.Row0.Y - right.Row0.Y;
473 result.Row0.Z = left.Row0.Z - right.Row0.Z;
474 result.Row1.X = left.Row1.X - right.Row1.X;
475 result.Row1.Y = left.Row1.Y - right.Row1.Y;
476 result.Row1.Z = left.Row1.Z - right.Row1.Z;
480 /// Subtracts two instances.
482 /// <param name="left">The left operand of the subtraction.</param>
483 /// <param name="right">The right operand of the subtraction.</param>
484 /// <returns>A new instance that is the result of the subtraction.</returns>
485 public static Matrix2x3d Subtract(Matrix2x3d left, Matrix2x3d right)
488 Subtract(ref left, ref right, out result);
493 /// Calculate the transpose of the given matrix.
495 /// <param name="mat">The matrix to transpose.</param>
496 /// <param name="result">The transpose of the given matrix.</param>
497 public static void Transpose(ref Matrix2x3d mat, out Matrix3x2d result)
499 result.Row0.X = mat.Row0.X;
500 result.Row0.Y = mat.Row1.X;
501 result.Row1.X = mat.Row0.Y;
502 result.Row1.Y = mat.Row1.Y;
503 result.Row2.X = mat.Row0.Z;
504 result.Row2.Y = mat.Row1.Z;
508 /// Calculate the transpose of the given matrix.
510 /// <param name="mat">The matrix to transpose.</param>
511 /// <returns>The transpose of the given matrix.</returns>
512 public static Matrix3x2d Transpose(Matrix2x3d mat)
515 Transpose(ref mat, out result);
520 /// Scalar multiplication.
522 /// <param name="left">left-hand operand</param>
523 /// <param name="right">right-hand operand</param>
524 /// <returns>A new Matrix2x3d which holds the result of the multiplication</returns>
525 public static Matrix2x3d operator *(double left, Matrix2x3d right)
527 return Mult(right, left);
531 /// Scalar multiplication.
533 /// <param name="left">left-hand operand</param>
534 /// <param name="right">right-hand operand</param>
535 /// <returns>A new Matrix2x3d which holds the result of the multiplication</returns>
536 public static Matrix2x3d operator *(Matrix2x3d left, double right)
538 return Mult(left, right);
542 /// Matrix multiplication
544 /// <param name="left">left-hand operand</param>
545 /// <param name="right">right-hand operand</param>
546 /// <returns>A new Matrix2d which holds the result of the multiplication</returns>
547 public static Matrix2d operator *(Matrix2x3d left, Matrix3x2 right)
549 return Mult(left, right);
553 /// Matrix multiplication
555 /// <param name="left">left-hand operand</param>
556 /// <param name="right">right-hand operand</param>
557 /// <returns>A new Matrix2x3d which holds the result of the multiplication</returns>
558 public static Matrix2x3d operator *(Matrix2x3d left, Matrix3 right)
560 return Mult(left, right);
564 /// Matrix multiplication
566 /// <param name="left">left-hand operand</param>
567 /// <param name="right">right-hand operand</param>
568 /// <returns>A new Matrix2x4d which holds the result of the multiplication</returns>
569 public static Matrix2x4d operator *(Matrix2x3d left, Matrix3x4 right)
571 return Mult(left, right);
577 /// <param name="left">left-hand operand</param>
578 /// <param name="right">right-hand operand</param>
579 /// <returns>A new Matrix2x3d which holds the result of the addition</returns>
580 public static Matrix2x3d operator +(Matrix2x3d left, Matrix2x3d right)
582 return Add(left, right);
586 /// Matrix subtraction
588 /// <param name="left">left-hand operand</param>
589 /// <param name="right">right-hand operand</param>
590 /// <returns>A new Matrix2x3d which holds the result of the subtraction</returns>
591 public static Matrix2x3d operator -(Matrix2x3d left, Matrix2x3d right)
593 return Subtract(left, right);
597 /// Compares two instances for equality.
599 /// <param name="left">The first instance.</param>
600 /// <param name="right">The second instance.</param>
601 /// <returns>True, if left equals right; false otherwise.</returns>
602 public static bool operator ==(Matrix2x3d left, Matrix2x3d right)
604 return left.Equals(right);
608 /// Compares two instances for inequality.
610 /// <param name="left">The first instance.</param>
611 /// <param name="right">The second instance.</param>
612 /// <returns>True, if left does not equal right; false otherwise.</returns>
613 public static bool operator !=(Matrix2x3d left, Matrix2x3d right)
615 return !left.Equals(right);
619 /// Returns a System.String that represents the current Matrix2x3d.
621 /// <returns>The string representation of the matrix.</returns>
622 public override string ToString()
624 return String.Format("{0}\n{1}", Row0, Row1);
628 /// Returns the hashcode for this instance.
630 /// <returns>A System.Int32 containing the unique hashcode for this instance.</returns>
631 public override int GetHashCode()
635 return (this.Row0.GetHashCode() * 397) ^ this.Row1.GetHashCode();
640 /// Indicates whether this instance and a specified object are equal.
642 /// <param name="obj">The object to compare tresult.</param>
643 /// <returns>True if the instances are equal; false otherwise.</returns>
644 public override bool Equals(object obj)
646 if (!(obj is Matrix2x3d))
651 return this.Equals((Matrix2x3d)obj);
655 /// Indicates whether the current matrix is equal to another matrix.
657 /// <param name="other">An matrix to compare with this matrix.</param>
658 /// <returns>true if the current matrix is equal to the matrix parameter; otherwise, false.</returns>
659 public bool Equals(Matrix2x3d other)
662 Row0 == other.Row0 &&