Merge pull request #62 from udhos/master

Add setRotationMatrix().
diff --git a/lib/src/vector_math/opengl.dart b/lib/src/vector_math/opengl.dart
index 451f258..7489f84 100644
--- a/lib/src/vector_math/opengl.dart
+++ b/lib/src/vector_math/opengl.dart
@@ -21,6 +21,53 @@
 part of vector_math;
 
 /**
+ * Constructs a rotation matrix in [rotationMatrix].
+ *
+ * Sets [rotationMatrix] to a rotation matrix built from
+ * [forwardDirection] and [upDirection]. The right direction is
+ * constructed to be orthogonal to [forwardDirection] and
+ * [upDirection].
+ *
+ * [forwardDirection] specifies the direction of the forward vector.
+ * [upDirection] specifies the direction of the up vector.
+ *
+ * Use case is to build the per-model rotation matrix from vectors
+ * [forwardDirection] and [upDirection]. See sample code below for
+ * a context.
+ * 
+ * class Model {
+ * 
+ *   Vector3 _center = new Vector3.zero();        // per-model translation
+ *   Vector3 _scale = new Vector3(1.0, 1.0, 1.0); // per-model scaling
+ *   Matrix4 _rotation = new Matrix4.identity();  // per-model rotation
+ *   Matrix4 _MV = new Matrix4.identity();        // per-model model-view
+ * 
+ *   void updateModelViewUniform(RenderingContext gl, UniformLocation u_MV,
+ *       Vector3 camPosition, camFocusPosition, camUpDirection) {
+ * 
+ *     // V = View (inverse of camera)
+ *     // T = Translation
+ *     // R = Rotation
+ *     // S = Scaling
+ *     setViewMatrix(_MV, camPosition, camFocusPosition, camUpDirection); // MV = V
+ *     _MV.translate(_center); // MV = V*T
+ *     _MV.multiply(_rotation); // MV = V*T*R <-- _rotation is updated with setRotationMatrix(_rotation, forward, up);
+ *     _MV.scale(_scale); // MV = V*T*R*S
+ * 
+ *     gl.uniformMatrix4fv(u_MV, false, _MV.storage);
+ *   }
+ * 
+ * }
+ */
+void setRotationMatrix(Matrix4 rotationMatrix, Vector3 forwardDirection, upDirection) {
+  Vector3 right = forwardDirection.cross(upDirection).normalize();
+  rotationMatrix.setValues(forwardDirection[0], upDirection[0], right[0], 0.0,
+    forwardDirection[1], upDirection[1], right[1], 0.0,
+	forwardDirection[2], upDirection[2], right[2], 0.0,
+	0.0, 0.0, 0.0, 1.0);
+}
+
+/**
  * Constructs an OpenGL view matrix in [viewMatrix].
  *
  * [cameraPosition] specifies the position of the camera.
diff --git a/pubspec.yaml b/pubspec.yaml
index 8334724..4e1aa9a 100644
--- a/pubspec.yaml
+++ b/pubspec.yaml
@@ -1,5 +1,5 @@
 name: vector_math
-version: 1.4.3
+version: 1.4.4
 author: John McCutchan <john@johnmccutchan.com>
 description: A Vector Math library for 2D and 3D applications.
 homepage: https://github.com/johnmccutchan/vector_math
diff --git a/test/test_opengl_matrix.dart b/test/test_opengl_matrix.dart
index 78f7eed..f99828b 100644
--- a/test/test_opengl_matrix.dart
+++ b/test/test_opengl_matrix.dart
@@ -68,10 +68,26 @@
     relativeTest(ortho.getColumn(3), new Vector4(-(r + l) / (r - l), -(t + b) / (t - b), -(f + n) / (f - n), 1.0));
   }
 
+  void testRotationFromForwardUp() {
+    final Matrix4 rotation = new Matrix4.zero();
+    final Vector3 forward = new Vector3(1.0, 0.0, 0.0);
+    final Vector3 up = new Vector3(0.0, 1.0, 0.0);
+
+    setRotationMatrix(rotation, forward, up);    
+
+    final Vector3 right = new Vector3(0.0, 0.0, 1.0);
+
+    relativeTest(rotation, new Matrix4(forward[0], up[0], right[0], 0.0,
+        forward[1], up[1], right[1], 0.0,
+	forward[2], up[2], right[2], 0.0,
+	0.0, 0.0, 0.0, 1.0));
+  }
+
   void run() {
     test('LookAt', testLookAt);
     test('Unproject', testUnproject);
     test('Frustum', testFrustumMatrix);
     test('Orthographic', testOrthographicMatrix);
+    test('RotationFromForwardUp', testRotationFromForwardUp);
   }
 }