소스 검색

Merge pull request #10650 from TristanVALCKE/UnitTesting

Prepares return of unit tests
Mr.doob 8 년 전
부모
커밋
6d096f8c83
100개의 변경된 파일1353개의 추가작업 그리고 7815개의 파일을 삭제
  1. 2 0
      package.json
  2. 248 0
      test/Three.Unit.js
  3. 40 0
      test/rollup.unit.config.js
  4. 0 41
      test/unit/cameras/OrthographicCamera.js
  5. 0 117
      test/unit/core/BufferAttribute.js
  6. 0 76
      test/unit/core/EventDispatcher.js
  7. 0 29
      test/unit/core/InstancedBufferAttribute.js
  8. 0 53
      test/unit/core/InstancedBufferGeometry.js
  9. 0 46
      test/unit/core/InterleavedBuffer.js
  10. 0 102
      test/unit/core/Object3D.js
  11. 10 10
      test/unit/editor/TestAddObjectCommandAndRemoveObjectCommand.js
  12. 8 8
      test/unit/editor/TestAddScriptCommand.js
  13. 5 5
      test/unit/editor/TestMassUndoAndRedo.js
  14. 13 13
      test/unit/editor/TestMoveObjectCommand.js
  15. 14 14
      test/unit/editor/TestMultiCmdsCommand.js
  16. 18 18
      test/unit/editor/TestNegativeCases.js
  17. 31 31
      test/unit/editor/TestNestedDoUndoRedo.js
  18. 7 7
      test/unit/editor/TestRemoveScriptCommand.js
  19. 4 4
      test/unit/editor/TestSerialization.js
  20. 5 5
      test/unit/editor/TestSetColorCommand.js
  21. 20 20
      test/unit/editor/TestSetGeometryCommand.js
  22. 8 8
      test/unit/editor/TestSetGeometryValueCommand.js
  23. 5 5
      test/unit/editor/TestSetMaterialColorCommand.js
  24. 5 5
      test/unit/editor/TestSetMaterialCommand.js
  25. 5 5
      test/unit/editor/TestSetMaterialMapCommand.js
  26. 5 5
      test/unit/editor/TestSetMaterialValueCommand.js
  27. 11 11
      test/unit/editor/TestSetPositionCommand.js
  28. 11 11
      test/unit/editor/TestSetRotationCommand.js
  29. 11 11
      test/unit/editor/TestSetScaleCommand.js
  30. 6 6
      test/unit/editor/TestSetSceneCommand.js
  31. 8 8
      test/unit/editor/TestSetScriptValueCommand.js
  32. 5 5
      test/unit/editor/TestSetUuidCommand.js
  33. 7 7
      test/unit/editor/TestSetValueCommand.js
  34. 0 87
      test/unit/extras/ImageUtils.test.js
  35. 0 246
      test/unit/math/Box2.js
  36. 0 313
      test/unit/math/Box3.js
  37. 0 280
      test/unit/math/Color.js
  38. 0 156
      test/unit/math/Frustum.js
  39. 0 69
      test/unit/math/Line3.js
  40. 0 35
      test/unit/math/Math.js
  41. 0 212
      test/unit/math/Matrix3.js
  42. 0 197
      test/unit/math/Plane.js
  43. 0 112
      test/unit/math/Sphere.js
  44. 0 191
      test/unit/math/Triangle.js
  45. 0 262
      test/unit/math/Vector2.js
  46. 0 379
      test/unit/math/Vector3.js
  47. 0 318
      test/unit/math/Vector4.js
  48. 0 291
      test/unit/qunit-1.18.0.css
  49. 0 3829
      test/unit/qunit-1.18.0.js
  50. 4 4
      test/unit/qunit-utils.js
  51. 34 0
      test/unit/src/animation/AnimationAction.js
  52. 6 0
      test/unit/src/animation/AnimationClip.js
  53. 6 0
      test/unit/src/animation/AnimationMixer.js
  54. 9 9
      test/unit/src/animation/AnimationObjectGroup.js
  55. 6 0
      test/unit/src/animation/AnimationUtils.js
  56. 6 0
      test/unit/src/animation/KeyframeTrack.js
  57. 6 0
      test/unit/src/animation/KeyframeTrackConstructor.js
  58. 6 0
      test/unit/src/animation/KeyframeTrackPrototype.js
  59. 6 0
      test/unit/src/animation/PropertyBinding.js
  60. 6 0
      test/unit/src/animation/PropertyMixer.js
  61. 6 0
      test/unit/src/animation/tracks/BooleanKeyframeTrack.js
  62. 6 0
      test/unit/src/animation/tracks/ColorKeyframeTrack.js
  63. 6 0
      test/unit/src/animation/tracks/NumberKeyframeTrack.js
  64. 6 0
      test/unit/src/animation/tracks/QuaternionKeyframeTrack.js
  65. 6 0
      test/unit/src/animation/tracks/StringKeyframeTrack.js
  66. 6 0
      test/unit/src/animation/tracks/VectorKeyFrameTrack.js
  67. 6 0
      test/unit/src/audio/Audio.js
  68. 6 0
      test/unit/src/audio/AudioAnalyser.js
  69. 6 0
      test/unit/src/audio/AudioContext.js
  70. 6 0
      test/unit/src/audio/AudioListener.js
  71. 6 0
      test/unit/src/audio/PositionalAudio.js
  72. 6 6
      test/unit/src/cameras/Camera.js
  73. 6 0
      test/unit/src/cameras/CubeCamera.js
  74. 41 0
      test/unit/src/cameras/OrthographicCamera.js
  75. 10 10
      test/unit/src/cameras/PerspectiveCamera.js
  76. 6 0
      test/unit/src/cameras/StereoCamera.js
  77. 6 0
      test/unit/src/constants.js
  78. 117 0
      test/unit/src/core/BufferAttribute.js
  79. 54 54
      test/unit/src/core/BufferGeometry.js
  80. 5 5
      test/unit/src/core/Clock.js
  81. 6 0
      test/unit/src/core/DirectGeometry.js
  82. 76 0
      test/unit/src/core/EventDispatcher.js
  83. 17 17
      test/unit/src/core/Face3.js
  84. 21 22
      test/unit/src/core/Geometry.js
  85. 29 0
      test/unit/src/core/InstancedBufferAttribute.js
  86. 53 0
      test/unit/src/core/InstancedBufferGeometry.js
  87. 5 5
      test/unit/src/core/InstancedInterleavedBuffer.js
  88. 46 0
      test/unit/src/core/InterleavedBuffer.js
  89. 6 6
      test/unit/src/core/InterleavedBufferAttribute.js
  90. 6 0
      test/unit/src/core/Layers.js
  91. 102 0
      test/unit/src/core/Object3D.js
  92. 14 14
      test/unit/src/core/Raycaster.js
  93. 6 0
      test/unit/src/core/Uniform.js
  94. 6 0
      test/unit/src/extras/SceneUtils.js
  95. 6 0
      test/unit/src/extras/ShapeUtils.js
  96. 6 0
      test/unit/src/extras/core/Curve.js
  97. 6 0
      test/unit/src/extras/core/CurvePath.js
  98. 6 0
      test/unit/src/extras/core/Font.js
  99. 6 0
      test/unit/src/extras/core/Interpolations.js
  100. 6 0
      test/unit/src/extras/core/Path.js

+ 2 - 0
package.json

@@ -28,6 +28,7 @@
   },
   "scripts": {
     "build": "rollup -c",
+    "build-test": "rollup -c test/rollup.unit.config.js",
     "build-uglify": "rollup -c && uglifyjs build/three.js -cm --preamble \"// threejs.org/license\" > build/three.min.js",
     "build-closure": "rollup -c && java -jar utils/build/compiler/closure-compiler-v20160713.jar --warning_level=VERBOSE --jscomp_off=globalThis --jscomp_off=checkTypes --externs utils/build/externs.js --language_in=ECMASCRIPT5_STRICT --js build/three.js --js_output_file build/three.min.js",
     "dev": "rollup -c -w",
@@ -49,6 +50,7 @@
   "devDependencies": {
     "eslint": "^3.10.1",
     "eslint-config-mdcs": "^4.2.2",
+    "qunitjs": "^2.1.1",
     "rollup": "^0.36.3",
     "rollup-watch": "^2.5.0",
     "uglify-js": "^2.6.0"

+ 248 - 0
test/Three.Unit.js

@@ -0,0 +1,248 @@
+
+//src
+import '../src/polyfills.js';
+export * from '../src/constants.js';
+export * from '../src/Three.Legacy.js';
+
+//src/animation
+export { AnimationAction } from '../src/animation/AnimationAction.js';
+export { AnimationClip } from '../src/animation/AnimationClip.js';
+export { AnimationMixer } from '../src/animation/AnimationMixer.js';
+export { AnimationObjectGroup } from '../src/animation/AnimationObjectGroup.js';
+export { AnimationUtils } from '../src/animation/AnimationUtils.js';
+export { KeyframeTrack } from '../src/animation/KeyframeTrack.js';
+export { KeyframeTrackConstructor } from '../src/animation/KeyframeTrackConstructor.js';
+export { KeyframeTrackPrototype } from '../src/animation/KeyframeTrackPrototype.js';
+export { PropertyBinding } from '../src/animation/PropertyBinding.js';
+export { PropertyMixer } from '../src/animation/PropertyMixer.js';
+
+//src/animation/tracks
+export { BooleanKeyframeTrack } from '../src/animation/tracks/BooleanKeyframeTrack.js';
+export { ColorKeyframeTrack } from '../src/animation/tracks/ColorKeyframeTrack.js';
+export { NumberKeyframeTrack } from '../src/animation/tracks/NumberKeyframeTrack.js';
+export { QuaternionKeyframeTrack } from '../src/animation/tracks/QuaternionKeyframeTrack.js';
+export { StringKeyframeTrack } from '../src/animation/tracks/StringKeyframeTrack.js';
+export { VectorKeyframeTrack } from '../src/animation/tracks/VectorKeyframeTrack.js';
+
+
+//src/audio
+export { Audio } from '../src/audio/Audio.js';
+export { AudioAnalyser } from '../src/audio/AudioAnalyser.js';
+export { AudioContext } from '../src/audio/AudioContext.js';
+export { AudioListener } from '../src/audio/AudioListener.js';
+export { PositionalAudio } from '../src/audio/PositionalAudio.js';
+
+
+//src/cameras
+export { Camera } from '../src/cameras/Camera.js';
+export { CubeCamera } from '../src/cameras/CubeCamera.js';
+export { OrthographicCamera } from '../src/cameras/OrthographicCamera.js';
+export { PerspectiveCamera } from '../src/cameras/PerspectiveCamera.js';
+export { StereoCamera } from '../src/cameras/StereoCamera.js';
+
+
+//src/core
+export * from '../src/core/BufferAttribute.js';
+export { BufferGeometry } from '../src/core/BufferGeometry.js';
+export { Clock } from '../src/core/Clock.js';
+export { DirectGeometry } from '../src/core/DirectGeometry.js';
+export { EventDispatcher } from '../src/core/EventDispatcher.js';
+export { Face3 } from '../src/core/Face3.js';
+export { GeometryIdCount, Geometry } from '../src/core/Geometry.js';
+export { InstancedBufferAttribute } from '../src/core/InstancedBufferAttribute.js';
+export { InstancedBufferGeometry } from '../src/core/InstancedBufferGeometry.js';
+export { InstancedInterleavedBuffer } from '../src/core/InstancedInterleavedBuffer.js';
+export { InterleavedBuffer } from '../src/core/InterleavedBuffer.js';
+export { InterleavedBufferAttribute } from '../src/core/InterleavedBufferAttribute.js';
+export { Layers } from '../src/core/Layers.js';
+export { Object3D } from '../src/core/Object3D.js';
+export { Raycaster } from '../src/core/Raycaster.js';
+export { Uniform } from '../src/core/Uniform.js';
+
+
+//src/extras
+export { SceneUtils } from '../src/extras/SceneUtils.js';
+export { ShapeUtils } from '../src/extras/ShapeUtils.js';
+
+//src/extras/core
+export { Curve } from '../src/extras/core/Curve.js';
+export { CurvePath } from '../src/extras/core/CurvePath.js';
+export { Font } from '../src/extras/core/Font.js';
+export * from '../src/extras/core/Interpolations.js';
+export { Path } from '../src/extras/core/Path.js';
+export { PathPrototype } from '../src/extras/core/PathPrototype.js';
+export { Shape } from '../src/extras/core/Shape.js';
+export { ShapePath } from '../src/extras/core/ShapePath.js';
+
+//src/extras/curves
+export { ArcCurve } from '../src/extras/curves/ArcCurve.js';
+export { CatmullRomCurve3 } from '../src/extras/curves/CatmullRomCurve3.js';
+export { CubicBezierCurve } from '../src/extras/curves/CubicBezierCurve.js';
+export { CubicBezierCurve3 } from '../src/extras/curves/CubicBezierCurve3.js';
+export { EllipseCurve } from '../src/extras/curves/EllipseCurve.js';
+export { LineCurve } from '../src/extras/curves/LineCurve.js';
+export { LineCurve3 } from '../src/extras/curves/LineCurve3.js';
+export { QuadraticBezierCurve } from '../src/extras/curves/QuadraticBezierCurve.js';
+export { QuadraticBezierCurve3 } from '../src/extras/curves/QuadraticBezierCurve3.js';
+export { SplineCurve } from '../src/extras/curves/SplineCurve.js';
+
+//src/extras/objects
+export { ImmediateRenderObject } from '../src/extras/objects/ImmediateRenderObject.js';
+export { MorphBlendMesh } from '../src/extras/objects/MorphBlendMesh.js';
+
+
+//src/geometries
+export * from '../src/geometries/Geometries.js';
+
+
+//src/helpers
+export { ArrowHelper } from '../src/helpers/ArrowHelper.js';
+export { AxisHelper } from '../src/helpers/AxisHelper.js';
+export { BoxHelper } from '../src/helpers/BoxHelper.js';
+export { CameraHelper } from '../src/helpers/CameraHelper.js';
+export { DirectionalLightHelper } from '../src/helpers/DirectionalLightHelper.js';
+export { FaceNormalsHelper } from '../src/helpers/FaceNormalsHelper.js';
+export { GridHelper } from '../src/helpers/GridHelper.js';
+export { HemisphereLightHelper } from '../src/helpers/HemisphereLightHelper.js';
+export { PointLightHelper } from '../src/helpers/PointLightHelper.js';
+export { PolarGridHelper } from '../src/helpers/PolarGridHelper.js';
+export { RectAreaLightHelper } from '../src/helpers/RectAreaLightHelper.js';
+export { SkeletonHelper } from '../src/helpers/SkeletonHelper.js';
+export { SpotLightHelper } from '../src/helpers/SpotLightHelper.js';
+export { VertexNormalsHelper } from '../src/helpers/VertexNormalsHelper.js';
+
+
+//src/lights
+export { AmbientLight } from '../src/lights/AmbientLight.js';
+export { DirectionalLight } from '../src/lights/DirectionalLight.js';
+export { DirectionalLightShadow } from '../src/lights/DirectionalLightShadow.js';
+export { HemisphereLight } from '../src/lights/HemisphereLight.js';
+export { Light } from '../src/lights/Light.js';
+export { LightShadow } from '../src/lights/LightShadow.js';
+export { PointLight } from '../src/lights/PointLight.js';
+export { RectAreaLight } from '../src/lights/RectAreaLight.js';
+//export { RectAreaLightShadow } from '../src/lights/RectAreaLightShadow.js'; //Todo (tristan): Need to be fixed !
+export { SpotLight } from '../src/lights/SpotLight.js';
+export { SpotLightShadow } from '../src/lights/SpotLightShadow.js';
+
+
+//src/loaders
+export { AnimationLoader } from '../src/loaders/AnimationLoader.js';
+export { AudioLoader } from '../src/loaders/AudioLoader.js';
+export { BufferGeometryLoader } from '../src/loaders/BufferGeometryLoader.js';
+export { Cache } from '../src/loaders/Cache.js';
+export { CompressedTextureLoader } from '../src/loaders/CompressedTextureLoader.js';
+export { CubeTextureLoader } from '../src/loaders/CubeTextureLoader.js';
+export { DataTextureLoader } from '../src/loaders/DataTextureLoader.js';
+export { DefaultLoadingManager, LoadingManager } from '../src/loaders/LoadingManager.js';
+export { FileLoader } from '../src/loaders/FileLoader.js';
+export { FontLoader } from '../src/loaders/FontLoader.js';
+export { ImageLoader } from '../src/loaders/ImageLoader.js';
+export { JSONLoader } from '../src/loaders/JSONLoader.js';
+export { Loader } from '../src/loaders/Loader.js';
+export { MaterialLoader } from '../src/loaders/MaterialLoader.js';
+export { ObjectLoader } from '../src/loaders/ObjectLoader.js';
+export { TextureLoader } from '../src/loaders/TextureLoader.js';
+
+
+//src/materials
+export * from '../src/materials/Materials.js';
+
+
+//src/math
+export { _Math as Math } from '../src/math/Math.js';
+export { Box2 } from '../src/math/Box2.js';
+export { Box3 } from '../src/math/Box3.js';
+export { Color } from '../src/math/Color.js';
+export { Cylindrical } from '../src/math/Cylindrical.js';
+export { Euler } from '../src/math/Euler.js';
+export { Frustum } from '../src/math/Frustum.js';
+export { Interpolant } from '../src/math/Interpolant.js';
+export { Line3 } from '../src/math/Line3.js';
+export { Matrix3 } from '../src/math/Matrix3.js';
+export { Matrix4 } from '../src/math/Matrix4.js';
+export { Plane } from '../src/math/Plane.js';
+export { Quaternion } from '../src/math/Quaternion.js';
+export { Ray } from '../src/math/Ray.js';
+export { Sphere } from '../src/math/Sphere.js';
+export { Spherical } from '../src/math/Spherical.js';
+export { Triangle } from '../src/math/Triangle.js';
+export { Vector2 } from '../src/math/Vector2.js';
+export { Vector3 } from '../src/math/Vector3.js';
+export { Vector4 } from '../src/math/Vector4.js';
+
+//src/math/interpolants
+export { CubicInterpolant } from '../src/math/interpolants/CubicInterpolant.js';
+export { DiscreteInterpolant } from '../src/math/interpolants/DiscreteInterpolant.js';
+export { LinearInterpolant } from '../src/math/interpolants/LinearInterpolant.js';
+export { QuaternionLinearInterpolant } from '../src/math/interpolants/QuaternionLinearInterpolant.js';
+
+
+//src/objects
+export { Bone } from '../src/objects/Bone.js';
+export { Group } from '../src/objects/Group.js';
+export { LensFlare } from '../src/objects/LensFlare.js';
+export { Line } from '../src/objects/Line.js';
+export { LineSegments } from '../src/objects/LineSegments.js';
+export { LOD } from '../src/objects/LOD.js';
+export { Mesh } from '../src/objects/Mesh.js';
+export { Points } from '../src/objects/Points.js';
+export { Skeleton } from '../src/objects/Skeleton.js';
+export { SkinnedMesh } from '../src/objects/SkinnedMesh.js';
+export { Sprite } from '../src/objects/Sprite.js';
+
+
+//src/renderers
+export { WebGL2Renderer } from '../src/renderers/WebGL2Renderer.js';
+export { WebGLRenderer } from '../src/renderers/WebGLRenderer.js';
+export { WebGLRenderTarget } from '../src/renderers/WebGLRenderTarget.js';
+export { WebGLRenderTargetCube } from '../src/renderers/WebGLRenderTargetCube.js';
+
+//src/renderers/shaders
+export { ShaderChunk } from '../src/renderers/shaders/ShaderChunk.js';
+export { ShaderLib } from '../src/renderers/shaders/ShaderLib.js';
+export { UniformsLib } from '../src/renderers/shaders/UniformsLib.js';
+export { UniformsUtils } from '../src/renderers/shaders/UniformsUtils.js';
+
+//src/renderers/webgl
+export { WebGLBufferRenderer } from '../src/renderers/webgl/WebGLBufferRenderer.js';
+export { WebGLCapabilities } from '../src/renderers/webgl/WebGLCapabilities.js';
+export { WebGLClipping } from '../src/renderers/webgl/WebGLClipping.js';
+export { WebGLExtensions } from '../src/renderers/webgl/WebGLExtensions.js';
+export { WebGLGeometries } from '../src/renderers/webgl/WebGLGeometries.js';
+export { WebGLIndexedBufferRenderer } from '../src/renderers/webgl/WebGLIndexedBufferRenderer.js';
+export { WebGLLights } from '../src/renderers/webgl/WebGLLights.js';
+export { WebGLObjects } from '../src/renderers/webgl/WebGLObjects.js';
+export { WebGLProgram } from '../src/renderers/webgl/WebGLProgram.js';
+export { WebGLProperties } from '../src/renderers/webgl/WebGLProperties.js';
+export { WebGLShader } from '../src/renderers/webgl/WebGLShader.js';
+export { WebGLShadowMap } from '../src/renderers/webgl/WebGLShadowMap.js';
+export { WebGLState } from '../src/renderers/webgl/WebGLState.js';
+export { WebGLTextures } from '../src/renderers/webgl/WebGLTextures.js';
+export { WebGLUniforms } from '../src/renderers/webgl/WebGLUniforms.js';
+
+//src/renderers/webgl/plugins
+export { LensFlarePlugin } from '../src/renderers/webgl/plugins/LensFlarePlugin.js';
+export { SpritePlugin } from '../src/renderers/webgl/plugins/SpritePlugin.js';
+
+
+//src/scenes
+export { Fog } from '../src/scenes/Fog.js';
+export { FogExp2 } from '../src/scenes/FogExp2.js';
+export { Scene } from '../src/scenes/Scene.js';
+
+
+//src/textures
+export { CanvasTexture } from '../src/textures/CanvasTexture.js';
+export { CompressedTexture } from '../src/textures/CompressedTexture.js';
+export { CubeTexture } from '../src/textures/CubeTexture.js';
+export { DataTexture } from '../src/textures/DataTexture.js';
+export { DepthTexture } from '../src/textures/DepthTexture.js';
+export { Texture } from '../src/textures/Texture.js';
+export { VideoTexture } from '../src/textures/VideoTexture.js';
+
+
+
+
+
+

+ 40 - 0
test/rollup.unit.config.js

@@ -0,0 +1,40 @@
+function glsl() {
+
+	return {
+
+		transform( code, id ) {
+
+			if ( /\.glsl$/.test( id ) === false ) return;
+
+			var transformedCode = 'export default ' + JSON.stringify(
+				code
+					.replace( /[ \t]*\/\/.*\n/g, '' )
+					.replace( /[ \t]*\/\*[\s\S]*?\*\//g, '' )
+					.replace( /\n{2,}/g, '\n' )
+			) + ';';
+			return {
+				code: transformedCode,
+				map: { mappings: '' }
+			};
+
+		}
+
+	};
+
+}
+
+export default {
+	entry: 'test/Three.Unit.js',
+	indent: '\t',
+	plugins: [
+		glsl()
+	],
+	// sourceMap: true,
+	targets: [
+		{
+			format: 'umd',
+			moduleName: 'THREE',
+			dest: 'test/unit/three.unit.js'
+		}
+	]
+};

+ 0 - 41
test/unit/cameras/OrthographicCamera.js

@@ -1,41 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "OrthographicCamera" );
-
-test( "updateProjectionMatrix", function() {
-	var left = -1, right = 1, top = 1, bottom = -1, near = 1, far = 3;
-	var cam = new THREE.OrthographicCamera(left, right, top, bottom, near, far);
-
-	// updateProjectionMatrix is called in contructor
-	var pMatrix = cam.projectionMatrix.elements;
-
-	// orthographic projection is given my the 4x4 Matrix
-	// 2/r-l		0			 0		-(l+r/r-l)
-	//   0		2/t-b		 0		-(t+b/t-b)
-	//   0			0		-2/f-n	-(f+n/f-n)
-	//   0			0			 0				1
-
-	ok( pMatrix[0] === 2 / ( right - left ), "m[0,0] === 2 / (r - l)" );
-	ok( pMatrix[5] === 2 / ( top - bottom ), "m[1,1] === 2 / (t - b)" );
-	ok( pMatrix[10] === -2 / ( far - near ), "m[2,2] === -2 / (f - n)" );
-	ok( pMatrix[12] === - ( ( right + left ) / ( right - left ) ), "m[3,0] === -(r+l/r-l)" );
-	ok( pMatrix[13] === - ( ( top + bottom ) / ( top - bottom ) ), "m[3,1] === -(t+b/b-t)" );
-	ok( pMatrix[14] === - ( ( far + near ) / ( far - near ) ), "m[3,2] === -(f+n/f-n)" );
-});
-
-test( "clone", function() {
-	var left = -1.5, right = 1.5, top = 1, bottom = -1, near = 0.1, far = 42;
-	var cam = new THREE.OrthographicCamera(left, right, top, bottom, near, far);
-
-	var clonedCam = cam.clone();
-
-	ok( cam.left === clonedCam.left , "left is equal" );
-	ok( cam.right === clonedCam.right , "right is equal" );
-	ok( cam.top === clonedCam.top , "top is equal" );
-	ok( cam.bottom === clonedCam.bottom , "bottom is equal" );
-	ok( cam.near === clonedCam.near , "near is equal" );
-	ok( cam.far === clonedCam.far , "far is equal" );
-	ok( cam.zoom === clonedCam.zoom , "zoom is equal" );
-});

+ 0 - 117
test/unit/core/BufferAttribute.js

@@ -1,117 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "BufferAttribute" );
-
-test( "count", function() {
-	ok(
-		new THREE.BufferAttribute( new Float32Array( [1, 2, 3, 4, 5, 6] ), 3 ).count === 2,
-		'count is equal to the number of chunks'
-	);
-});
-
-test( "copy", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array( [1, 2, 3, 4, 5, 6] ), 3 );
-	attr.setDynamic( true );
-	attr.needsUpdate = true;
-
-	var attrCopy = new THREE.BufferAttribute().copy( attr );
-
-	ok( attr.count === attrCopy.count, 'count is equal' );
-	ok( attr.itemSize === attrCopy.itemSize, 'itemSize is equal' );
-	ok( attr.dynamic === attrCopy.dynamic, 'dynamic is equal' );
-	ok( attr.array.length === attrCopy.array.length, 'array length is equal' );
-	ok( attr.version === 1 && attrCopy.version === 0, 'version is not copied which is good' );
-});
-
-test( "copyAt", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array( [1, 2, 3, 4, 5, 6, 7, 8, 9] ), 3 );
-	var attr2 = new THREE.BufferAttribute( new Float32Array(9), 3 );
-
-	attr2.copyAt( 1, attr, 2 );
-	attr2.copyAt( 0, attr, 1 );
-	attr2.copyAt( 2, attr, 0 );
-
-	var i = attr.array;
-	var i2 = attr2.array; // should be [4, 5, 6, 7, 8, 9, 1, 2, 3]
-
-	ok( i2[0] === i[3] && i2[1] === i[4] && i2[2] === i[5], 'chunck copied to correct place' );
-	ok( i2[3] === i[6] && i2[4] === i[7] && i2[5] === i[8], 'chunck copied to correct place' );
-	ok( i2[6] === i[0] && i2[7] === i[1] && i2[8] === i[2], 'chunck copied to correct place' );
-});
-
-test( "copyColorsArray", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array(6), 3 );
-
-	attr.copyColorsArray( [
-		new THREE.Color( 0, 0.5, 1 ),
-		new THREE.Color( 0.25, 1, 0 )
-	]);
-
-	var i = attr.array;
-	ok( i[0] === 0 && i[1] === 0.5 && i[2] === 1, 'first color was copied correctly' );
-	ok( i[3] === 0.25 && i[4] === 1 && i[5] === 0, 'second color was copied correctly' );
-});
-
-test( "copyIndicesArray", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array(6), 3 );
-
-	attr.copyIndicesArray( [
-		{a: 1, b: 2, c: 3},
-		{a: 4, b: 5, c: 6}
-	]);
-
-	var i = attr.array;
-	ok( i[0] === 1 && i[1] === 2 && i[2] === 3, 'first indices were copied correctly' );
-	ok( i[3] === 4 && i[4] === 5 && i[5] === 6, 'second indices were copied correctly' );
-});
-
-test( "copyVector2sArray", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array(4), 2 );
-
-	attr.copyVector2sArray( [
-		new THREE.Vector2(1, 2),
-		new THREE.Vector2(4, 5)
-	]);
-
-	var i = attr.array;
-	ok( i[0] === 1 && i[1] === 2, 'first vector was copied correctly' );
-	ok( i[2] === 4 && i[3] === 5, 'second vector was copied correctly' );
-});
-
-test( "copyVector3sArray", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array(6), 2 );
-
-	attr.copyVector3sArray( [
-		new THREE.Vector3(1, 2, 3),
-		new THREE.Vector3(10, 20, 30)
-	]);
-
-	var i = attr.array;
-	ok( i[0] === 1 && i[1] === 2 && i[2] === 3, 'first vector was copied correctly' );
-	ok( i[3] === 10 && i[4] === 20 && i[5] === 30, 'second vector was copied correctly' );
-});
-
-test( "copyVector4sArray", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array(8), 2 );
-
-	attr.copyVector4sArray( [
-		new THREE.Vector4(1, 2, 3, 4),
-		new THREE.Vector4(10, 20, 30, 40)
-	]);
-
-	var i = attr.array;
-	ok( i[0] === 1 && i[1] === 2 && i[2] === 3 && i[3] === 4, 'first vector was copied correctly' );
-	ok( i[4] === 10 && i[5] === 20 && i[6] === 30 && i[7] === 40, 'second vector was copied correctly' );
-});
-
-test( "clone", function() {
-	var attr = new THREE.BufferAttribute( new Float32Array([1, 2, 3, 4, 0.12, -12]), 2 );
-	var attrCopy = attr.clone();
-
-	ok( attr.array.length === attrCopy.array.length, 'attribute was cloned' );
-	for ( var i = 0; i < attr.array.length; i++ ) {
-		ok( attr.array[i] === attrCopy.array[i], 'array item is equal' );
-	}
-});

+ 0 - 76
test/unit/core/EventDispatcher.js

@@ -1,76 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "EventDispatcher" );
-
-test( "addEventListener", function() {
-	var eventDispatcher = new THREE.EventDispatcher();
-
-	var listener = {};
-	eventDispatcher.addEventListener( 'anyType', listener );
-
-	ok( eventDispatcher._listeners.anyType.length === 1, "listener with unknown type was added" );
-	ok( eventDispatcher._listeners.anyType[0] === listener, "listener with unknown type was added" );
-
-	eventDispatcher.addEventListener( 'anyType', listener );
-
-	ok( eventDispatcher._listeners.anyType.length === 1, "can't add one listener twice to same type" );
-	ok( eventDispatcher._listeners.anyType[0] === listener, "listener is still there" );
-});
-
-test( "hasEventListener", function() {
-	var eventDispatcher = new THREE.EventDispatcher();
-
-	var listener = {};
-	eventDispatcher.addEventListener( 'anyType', listener );
-
-	ok( eventDispatcher.hasEventListener( 'anyType', listener ), "listener was found" );
-	ok( !eventDispatcher.hasEventListener( 'anotherType', listener ), "listener was not found which is good" );
-});
-
-test( "removeEventListener", function() {
-	var eventDispatcher = new THREE.EventDispatcher();
-
-	var listener = {};
-
-	ok ( eventDispatcher._listeners === undefined, "there are no listeners by default" );
-
-	eventDispatcher.addEventListener( 'anyType', listener );
-	ok ( Object.keys( eventDispatcher._listeners ).length === 1 &&
-		eventDispatcher._listeners.anyType.length === 1, "if a listener was added, there is a new key" );
-
-	eventDispatcher.removeEventListener( 'anyType', listener );
-	ok ( eventDispatcher._listeners.anyType.length === 0, "listener was deleted" );
-
-	eventDispatcher.removeEventListener( 'unknownType', listener );
-	ok ( eventDispatcher._listeners.unknownType === undefined, "unknown types will be ignored" );
-
-	eventDispatcher.removeEventListener( 'anyType', undefined );
-	ok ( eventDispatcher._listeners.anyType.length === 0, "undefined listeners are ignored" );
-});
-
-test( "dispatchEvent", function() {
-	var eventDispatcher = new THREE.EventDispatcher();
-
-	var callCount = 0;
-	var listener = function() { callCount++; };
-
-	eventDispatcher.addEventListener( 'anyType', listener );
-	ok( callCount === 0, "no event, no call" );
-
-	eventDispatcher.dispatchEvent( { type: 'anyType' } );
-	ok( callCount === 1, "one event, one call" );
-
-	eventDispatcher.dispatchEvent( { type: 'anyType' } );
-	ok( callCount === 2, "two events, two calls" );
-});
-
-
-
-
-
-
-
-
-//

+ 0 - 29
test/unit/core/InstancedBufferAttribute.js

@@ -1,29 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "InstancedBufferAttribute" );
-
-test( "can be created", function() {
-	var instance = new THREE.InstancedBufferAttribute(new Float32Array(10), 2);
-	ok( instance.meshPerAttribute === 1, "ok" );
-
-	instance = new THREE.InstancedBufferAttribute(new Float32Array(10), 2, 123);
-	ok( instance.meshPerAttribute === 123, "ok" );
-
-});
-
-test( "copy", function() {
-	var array = new Float32Array( [1, 2, 3, 7, 8, 9] );
-	var instance = new THREE.InstancedBufferAttribute( array, 2, 123 );
-	var copiedInstance = instance.copy( instance );
-
-	ok( copiedInstance instanceof THREE.InstancedBufferAttribute, "the clone has the correct type" );
-	ok( copiedInstance.itemSize === 2, "itemSize was copied" );
-	ok( copiedInstance.meshPerAttribute === 123, "meshPerAttribute was copied" );
-
-	for (var i = 0; i < array.length; i++) {
-		ok( copiedInstance.array[i] === array[i], "array was copied" );
-	}
-
-});

+ 0 - 53
test/unit/core/InstancedBufferGeometry.js

@@ -1,53 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "InstancedBufferGeometry" );
-
-function createClonableMock() {
-	return {
-		callCount: 0,
-
-		clone: function() {
-			this.callCount++;
-
-			return this;
-		}
-	}
-}
-
-test( "copy", function() {
-	var instanceMock1 = {};
-	var instanceMock2 = {};
-	var indexMock = createClonableMock();
-	var defaultAttribute1 = new THREE.BufferAttribute([1]);
-	var defaultAttribute2 = new THREE.BufferAttribute([2]);
-
-	var instance = new THREE.InstancedBufferGeometry();
-
-	instance.addGroup( 0, 10, instanceMock1 );
-	instance.addGroup( 10, 5, instanceMock2 );
-	instance.setIndex( indexMock );
-	instance.addAttribute( 'defaultAttribute1', defaultAttribute1 );
-	instance.addAttribute( 'defaultAttribute2', defaultAttribute2 );
-
-	var copiedInstance = instance.copy( instance );
-
-	ok( copiedInstance instanceof THREE.InstancedBufferGeometry, "the clone has the correct type" );
-
-	ok( copiedInstance.index === indexMock, "index was copied" );
-	ok( copiedInstance.index.callCount === 1, "index.clone was called once" );
-
-	ok( copiedInstance.attributes['defaultAttribute1'] instanceof THREE.BufferAttribute, "attribute was created" );
-	// the given attribute mock was passed to the array property of the created buffer attribute
-	ok( copiedInstance.attributes['defaultAttribute1'].array[0] === defaultAttribute1.array, "attribute was copied" );
-	ok( copiedInstance.attributes['defaultAttribute2'].array[0] === defaultAttribute2.array, "attribute was copied" );
-
-	ok( copiedInstance.groups[0].start === 0, "group was copied" );
-	ok( copiedInstance.groups[0].count === 10, "group was copied" );
-	ok( copiedInstance.groups[0].instances === instanceMock1, "group was copied" );
-
-	ok( copiedInstance.groups[1].start === 10, "group was copied" );
-	ok( copiedInstance.groups[1].count === 5, "group was copied" );
-	ok( copiedInstance.groups[1].instances === instanceMock2, "group was copied" );
-});

+ 0 - 46
test/unit/core/InterleavedBuffer.js

@@ -1,46 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "InterleavedBuffer" );
-
-function checkInstanceAgainstCopy( instance, copiedInstance ) {
-	ok( copiedInstance instanceof THREE.InterleavedBuffer, "the clone has the correct type" );
-
-	for ( var i = 0; i < instance.array.length; i++ ) {
-		ok( copiedInstance.array[i] === instance.array[i], "array was copied" );
-	}
-
-	ok( copiedInstance.stride === instance.stride, "stride was copied" );
-	ok( copiedInstance.dynamic === true, "dynamic was copied" );
-}
-
-test( "length and count", function() {
-	var instance = new THREE.InterleavedBuffer( new Float32Array( [1, 2, 3, 7, 8 ,9] ), 3 );
-
-	ok( instance.length === 6, "length is calculated via array length" );
-	ok( instance.count === 2, "count is calculated via array length / stride" );
-});
-
-test( "copy", function() {
-	var array = new Float32Array( [1, 2, 3, 7, 8 ,9] );
-	var instance = new THREE.InterleavedBuffer( array, 3 );
-	instance.setDynamic( true );
-
-	checkInstanceAgainstCopy(instance, instance.copy( instance ) );
-});
-
-test( "clone", function() {
-	var array = new Float32Array( [1, 2, 3, 7, 8 ,9] );
-	var instance = new THREE.InterleavedBuffer( array, 3 );
-	instance.setDynamic( true );
-
-	checkInstanceAgainstCopy( instance, instance.clone() );
-});
-
-test( "set", function() {
-	var instance = new THREE.InterleavedBuffer( new Float32Array( [1, 2, 3, 7, 8 ,9] ), 3 );
-
-	instance.set( [0, -1] );
-	ok( instance.array[0] === 0 && instance.array[1] === -1, "replace at first by default" );
-});

+ 0 - 102
test/unit/core/Object3D.js

@@ -1,102 +0,0 @@
-/**
- * @author simonThiele / https://github.com/simonThiele
- */
-
-module( "Object3D" );
-
-var RadToDeg = 180 / Math.PI;
-
-test( "rotateX", function() {
-	var obj = new THREE.Object3D();
-
-	var angleInRad = 1.562;
-	obj.rotateX(angleInRad);
-
-	// should calculate the correct rotation on x
-	checkIfFloatsAreEqual(obj.rotation.x, angleInRad);
-});
-
-test( "rotateY", function() {
-	var obj = new THREE.Object3D();
-
-	var angleInRad = -0.346;
-	obj.rotateY(angleInRad);
-
-	// should calculate the correct rotation on y
-	checkIfFloatsAreEqual(obj.rotation.y, angleInRad);
-});
-
-test( "rotateZ", function() {
-	var obj = new THREE.Object3D();
-
-	var angleInRad = 1;
-	obj.rotateZ(angleInRad);
-
-	// should calculate the correct rotation on y
-	checkIfFloatsAreEqual(obj.rotation.z, angleInRad);
-});
-
-test( "translateOnAxis", function() {
-	var obj = new THREE.Object3D();
-
-	// get a reference object for comparing
-	var reference = {x: 1, y: 1.23, z: -4.56};
-	obj.translateOnAxis(new THREE.Vector3(1, 0, 0), 1);
-	obj.translateOnAxis(new THREE.Vector3(0, 1, 0), 1.23);
-	obj.translateOnAxis(new THREE.Vector3(0, 0, 1), -4.56);
-
-	checkIfPropsAreEqual(reference, obj.position);
-});
-
-test( "translateX", function() {
-	var obj = new THREE.Object3D();
-	obj.translateX(1.234);
-
-	ok( obj.position.x === 1.234 , "x is equal" );
-});
-
-test( "translateY", function() {
-	var obj = new THREE.Object3D();
-	obj.translateY(1.234);
-
-	ok( obj.position.y === 1.234 , "y is equal" );
-});
-
-test( "translateZ", function() {
-	var obj = new THREE.Object3D();
-	obj.translateZ(1.234);
-
-	ok( obj.position.z === 1.234 , "z is equal" );
-});
-
-test( "lookAt", function() {
-	var obj = new THREE.Object3D();
-	obj.lookAt(new THREE.Vector3(0, -1, 1));
-
-	ok( obj.rotation.x * RadToDeg === 45 , "x is equal" );
-});
-
-test( "getWorldRotation", function() {
-	var obj = new THREE.Object3D();
-
-	obj.lookAt(new THREE.Vector3(0, -1, 1));
-	ok( obj.getWorldRotation().x * RadToDeg === 45 , "x is equal" );
-
-	obj.lookAt(new THREE.Vector3(1, 0, 0));
-	ok( obj.getWorldRotation().y * RadToDeg === 90 , "y is equal" );
-});
-
-function checkIfPropsAreEqual(reference, obj) {
-	ok( obj.x === reference.x , "x is equal" );
-	ok( obj.y === reference.y , "y is equal!" );
-	ok( obj.z === reference.z , "z is equal!" );
-}
-
-// since float equal checking is a mess in js, one solution is to cut off
-// decimal places
-function checkIfFloatsAreEqual(f1, f2) {
-	var f1Rounded = ((f1 * 1000) | 0) / 1000;
-	var f2Rounded = ((f2 * 1000) | 0) / 1000;
-
-	ok( f1Rounded === f2Rounded, "passed" );
-}

+ 10 - 10
test/unit/editor/TestAddObjectCommandAndRemoveObjectCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "AddObjectCommandAndRemoveObjectCommand" );
+QUnit.module( "AddObjectCommandAndRemoveObjectCommand" );
 
-test( "Test AddObjectCommand and RemoveObjectCommand (Undo and Redo)", function() {
+QUnit.test( "Test AddObjectCommand and RemoveObjectCommand (Undo and Redo)", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -23,15 +23,15 @@ test( "Test AddObjectCommand and RemoveObjectCommand (Undo and Redo)", function(
 		cmd.updatable = false;
 
 		editor.execute( cmd );
-		ok( editor.scene.children.length == 1, "OK, adding '" + object.type + "' was successful " );
+		assert.ok( editor.scene.children.length == 1, "OK, adding '" + object.type + "' was successful " );
 
 		editor.undo();
-		ok( editor.scene.children.length == 0, "OK, adding '" + object.type + "' is undone (was removed)" );
+		assert.ok( editor.scene.children.length == 0, "OK, adding '" + object.type + "' is undone (was removed)" );
 
 		editor.redo();
-		ok( editor.scene.children[ 0 ].name == object.name, "OK, removed '" + object.type + "' was added again (redo)" );
+		assert.ok( editor.scene.children[ 0 ].name == object.name, "OK, removed '" + object.type + "' was added again (redo)" );
 
-		ok( editor.selected == object, "OK, focus was set on recovered object after Add-Redo" );
+		assert.ok( editor.selected == object, "OK, focus was set on recovered object after Add-Redo" );
 
 
 		// Test Remove
@@ -39,15 +39,15 @@ test( "Test AddObjectCommand and RemoveObjectCommand (Undo and Redo)", function(
 		cmd.updatable = false;
 
 		editor.execute( cmd );
-		ok( editor.scene.children.length == 0, "OK, removing object was successful" );
+		assert.ok( editor.scene.children.length == 0, "OK, removing object was successful" );
 
 		editor.undo();
-		ok( editor.scene.children[ 0 ].name == object.name, "OK, removed object was added again (undo)" );
+		assert.ok( editor.scene.children[ 0 ].name == object.name, "OK, removed object was added again (undo)" );
 
-		ok( editor.selected == object, "OK, focus was set on recovered object after Delete-Undo" );
+		assert.ok( editor.selected == object, "OK, focus was set on recovered object after Delete-Undo" );
 
 		editor.redo();
-		ok( editor.scene.children.length == 0, "OK, object was removed again (redo)" );
+		assert.ok( editor.scene.children.length == 0, "OK, object was removed again (redo)" );
 
 
 	} );

+ 8 - 8
test/unit/editor/TestAddScriptCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "AddScriptCommand" );
+QUnit.module( "AddScriptCommand" );
 
-test( "Test AddScriptCommand (Undo and Redo)", function() {
+QUnit.test( "Test AddScriptCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 
@@ -24,7 +24,7 @@ test( "Test AddScriptCommand (Undo and Redo)", function() {
 		editor.execute( new AddObjectCommand( item ) );
 
 	} );
-	ok( editor.scene.children.length == 2, "OK, the box and the sphere have been added" );
+	assert.ok( editor.scene.children.length == 2, "OK, the box and the sphere have been added" );
 
 	// add scripts to the objects
 	for ( var i = 0; i < scripts.length; i ++ ) {
@@ -36,24 +36,24 @@ test( "Test AddScriptCommand (Undo and Redo)", function() {
 	}
 
 	var scriptsKeys = Object.keys( editor.scripts );
-	ok( getScriptCount( editor ) == scripts.length, "OK, correct number of scripts have been added" );
+	assert.ok( getScriptCount( editor ) == scripts.length, "OK, correct number of scripts have been added" );
 
 	for ( var i = 0; i < objects.length; i ++ ) {
 
-		ok( objects[ i ].uuid == scriptsKeys[ i ], "OK, script key #" + i + " matches the object's UUID" );
+		assert.ok( objects[ i ].uuid == scriptsKeys[ i ], "OK, script key #" + i + " matches the object's UUID" );
 
 	}
 
 	editor.undo();
-	ok( getScriptCount( editor ) == scripts.length - 1, "OK, one script has been removed by undo" );
+	assert.ok( getScriptCount( editor ) == scripts.length - 1, "OK, one script has been removed by undo" );
 
 	editor.redo();
-	ok( getScriptCount( editor ) == scripts.length, "OK, one script has been added again by redo" );
+	assert.ok( getScriptCount( editor ) == scripts.length, "OK, one script has been added again by redo" );
 
 
 	for ( var i = 0; i < scriptsKeys.length; i ++ ) {
 
-		ok( editor.scripts[ scriptsKeys[ i ] ][ 0 ] == scripts[ i ], "OK, script #" + i + " is still assigned correctly" );
+		assert.ok( editor.scripts[ scriptsKeys[ i ] ][ 0 ] == scripts[ i ], "OK, script #" + i + " is still assigned correctly" );
 
 	}
 

+ 5 - 5
test/unit/editor/TestMassUndoAndRedo.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "MassUndoAndRedo" );
+QUnit.module( "MassUndoAndRedo" );
 
-test( "MassUndoAndRedo (stress test)", function() {
+QUnit.test( "MassUndoAndRedo (stress test)", function( assert ) {
 
 	var editor = new Editor();
 
@@ -24,7 +24,7 @@ test( "MassUndoAndRedo (stress test)", function() {
 
 	}
 
-	ok( editor.scene.children.lenght = MAX_OBJECTS,
+	assert.ok( editor.scene.children.lenght = MAX_OBJECTS,
 		"OK, " + MAX_OBJECTS + " objects have been added" );
 
 	// remove all objects
@@ -37,7 +37,7 @@ test( "MassUndoAndRedo (stress test)", function() {
 	}
 
 
-	ok( editor.scene.children.length == 0,
+	assert.ok( editor.scene.children.length == 0,
 		"OK, all objects have been removed by undos" );
 
 
@@ -49,7 +49,7 @@ test( "MassUndoAndRedo (stress test)", function() {
 
 	}
 
-	ok( editor.scene.children.lenght = MAX_OBJECTS,
+	assert.ok( editor.scene.children.lenght = MAX_OBJECTS,
 		"OK, " + MAX_OBJECTS + " objects have been added again by redos" );
 
 } );

+ 13 - 13
test/unit/editor/TestMoveObjectCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "MoveObjectCommand" );
+QUnit.module( "MoveObjectCommand" );
 
-test( "Test MoveObjectCommand (Undo and Redo)", function() {
+QUnit.test( "Test MoveObjectCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 
@@ -19,24 +19,24 @@ test( "Test MoveObjectCommand (Undo and Redo)", function() {
 	editor.execute( new AddObjectCommand( lukeSkywalker ) );
 
 
-	ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is 'Scene' " );
-	ok( lukeSkywalker.parent.name   == "Scene", "OK, Luke's parent is 'Scene' " );
+	assert.ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is 'Scene' " );
+	assert.ok( lukeSkywalker.parent.name   == "Scene", "OK, Luke's parent is 'Scene' " );
 
 	// Tell Luke, Anakin is his father
 	editor.execute( new MoveObjectCommand( lukeSkywalker, anakinSkywalker ) );
 
-	ok( true === true, "(Luke has been told who his father is)" );
-	ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is still 'Scene' " );
-	ok( lukeSkywalker.parent.name   == anakinsName, "OK, Luke's parent is '" + anakinsName + "' " );
+	assert.ok( true === true, "(Luke has been told who his father is)" );
+	assert.ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is still 'Scene' " );
+	assert.ok( lukeSkywalker.parent.name   == anakinsName, "OK, Luke's parent is '" + anakinsName + "' " );
 
 	editor.undo();
-	ok( true === true, "(Statement undone)" );
-	ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is still 'Scene' " );
-	ok( lukeSkywalker.parent.name   == "Scene", "OK, Luke's parent is 'Scene' again " );
+	assert.ok( true === true, "(Statement undone)" );
+	assert.ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is still 'Scene' " );
+	assert.ok( lukeSkywalker.parent.name   == "Scene", "OK, Luke's parent is 'Scene' again " );
 
 	editor.redo();
-	ok( true === true, "(Statement redone)" );
-	ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is still 'Scene' " );
-	ok( lukeSkywalker.parent.name   == anakinsName, "OK, Luke's parent is '" + anakinsName + "' again " );
+	assert.ok( true === true, "(Statement redone)" );
+	assert.ok( anakinSkywalker.parent.name == "Scene", "OK, Anakin's parent is still 'Scene' " );
+	assert.ok( lukeSkywalker.parent.name   == anakinsName, "OK, Luke's parent is '" + anakinsName + "' again " );
 
 } );

+ 14 - 14
test/unit/editor/TestMultiCmdsCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "MultiCmdsCommand" );
+QUnit.module( "MultiCmdsCommand" );
 
-test( "Test MultiCmdsCommand (Undo and Redo)", function() {
+QUnit.test( "Test MultiCmdsCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 	var box = aBox( 'Multi Command Box' );
@@ -60,21 +60,21 @@ test( "Test MultiCmdsCommand (Undo and Redo)", function() {
 
 
 	// test one modified value for each command
-	ok( box.geometry.parameters.widthSegments == 7, "OK, widthSegments has been modified accordingly after two multi executes (expected: 7, actual: " + box.geometry.parameters.widthSegments + ")" );
-	ok( box.position.y == 5, "OK, y position has been modified accordingly after two multi executes (expected: 5, actual: " + box.position.y + ")" );
-	ok( box.rotation.x == 0.4, "OK, x rotation has been modified accordingly after two multi executes (expected: 0.4, actual: " + box.rotation.x + ") " );
-	ok( box.scale.z == 1.6, "OK, z scale has been modified accordingly after two multi executes (expected: 1.6, actual: " + box.scale.z + ")" );
+	assert.ok( box.geometry.parameters.widthSegments == 7, "OK, widthSegments has been modified accordingly after two multi executes (expected: 7, actual: " + box.geometry.parameters.widthSegments + ")" );
+	assert.ok( box.position.y == 5, "OK, y position has been modified accordingly after two multi executes (expected: 5, actual: " + box.position.y + ")" );
+	assert.ok( box.rotation.x == 0.4, "OK, x rotation has been modified accordingly after two multi executes (expected: 0.4, actual: " + box.rotation.x + ") " );
+	assert.ok( box.scale.z == 1.6, "OK, z scale has been modified accordingly after two multi executes (expected: 1.6, actual: " + box.scale.z + ")" );
 
 	editor.undo();
-	ok( box.geometry.parameters.widthSegments == 2, "OK, widthSegments has been modified accordingly after undo (expected: 2, actual: " + box.geometry.parameters.widthSegments + ")" );
-	ok( box.position.y == 2, "OK, y position has been modified accordingly after undo (expected: 2, actual: " + box.position.y + ")" );
-	ok( box.rotation.x == 0.1, "OK, x rotation has been modified accordingly after undo (expected: 0.1, actual: " + box.rotation.x + ")" );
-	ok( box.scale.z == 1.3, "OK, z scale has been modified accordingly after undo (expected: 1.3, actual: " + box.scale.z + ")" );
+	assert.ok( box.geometry.parameters.widthSegments == 2, "OK, widthSegments has been modified accordingly after undo (expected: 2, actual: " + box.geometry.parameters.widthSegments + ")" );
+	assert.ok( box.position.y == 2, "OK, y position has been modified accordingly after undo (expected: 2, actual: " + box.position.y + ")" );
+	assert.ok( box.rotation.x == 0.1, "OK, x rotation has been modified accordingly after undo (expected: 0.1, actual: " + box.rotation.x + ")" );
+	assert.ok( box.scale.z == 1.3, "OK, z scale has been modified accordingly after undo (expected: 1.3, actual: " + box.scale.z + ")" );
 
 	editor.redo();
-	ok( box.geometry.parameters.widthSegments == 7, "OK, widthSegments has been modified accordingly after two multi executes (expected: 7, actual: " + box.geometry.parameters.widthSegments + ")" );
-	ok( box.position.y == 5, "OK, y position has been modified accordingly after two multi executes (expected: 5, actual: " + box.position.y + ")" );
-	ok( box.rotation.x == 0.4, "OK, x rotation has been modified accordingly after two multi executes (expected: 0.4, actual: " + box.rotation.x + ") " );
-	ok( box.scale.z == 1.6, "OK, z scale has been modified accordingly after two multi executes (expected: 1.6, actual: " + box.scale.z + ")" );
+	assert.ok( box.geometry.parameters.widthSegments == 7, "OK, widthSegments has been modified accordingly after two multi executes (expected: 7, actual: " + box.geometry.parameters.widthSegments + ")" );
+	assert.ok( box.position.y == 5, "OK, y position has been modified accordingly after two multi executes (expected: 5, actual: " + box.position.y + ")" );
+	assert.ok( box.rotation.x == 0.4, "OK, x rotation has been modified accordingly after two multi executes (expected: 0.4, actual: " + box.rotation.x + ") " );
+	assert.ok( box.scale.z == 1.6, "OK, z scale has been modified accordingly after two multi executes (expected: 1.6, actual: " + box.scale.z + ")" );
 
 } );

+ 18 - 18
test/unit/editor/TestNegativeCases.js

@@ -3,21 +3,21 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "NegativeCases" );
+QUnit.module( "NegativeCases" );
 
-test( "Test unwanted situations ", function() {
+QUnit.test( "Test unwanted situations ", function( assert ) {
 
 	var editor = new Editor();
 
 	// illegal
 	editor.undo();
-	ok( editor.history.undos.length == 0, "OK, (illegal) undo did not affect the undo history" );
-	ok( editor.history.redos.length == 0, "OK, (illegal) undo did not affect the redo history" );
+	assert.ok( editor.history.undos.length == 0, "OK, (illegal) undo did not affect the undo history" );
+	assert.ok( editor.history.redos.length == 0, "OK, (illegal) undo did not affect the redo history" );
 
 	// illegal
 	editor.redo();
-	ok( editor.history.undos.length == 0, "OK, (illegal) redo did not affect the undo history" );
-	ok( editor.history.redos.length == 0, "OK, (illegal) redo did not affect the redo history" );
+	assert.ok( editor.history.undos.length == 0, "OK, (illegal) redo did not affect the undo history" );
+	assert.ok( editor.history.redos.length == 0, "OK, (illegal) redo did not affect the redo history" );
 
 
 	var box = aBox();
@@ -25,31 +25,31 @@ test( "Test unwanted situations ", function() {
 	cmd.updatable = false;
 	editor.execute( cmd );
 
-	ok( editor.history.undos.length == 1, "OK, execute changed undo history" );
-	ok( editor.history.redos.length == 0, "OK, execute did not change redo history" );
+	assert.ok( editor.history.undos.length == 1, "OK, execute changed undo history" );
+	assert.ok( editor.history.redos.length == 0, "OK, execute did not change redo history" );
 
 	// illegal
 	editor.redo();
-	ok( editor.history.undos.length == 1, "OK, (illegal) redo did not affect the undo history" );
-	ok( editor.history.redos.length == 0, "OK, (illegal) redo did not affect the redo history" );
+	assert.ok( editor.history.undos.length == 1, "OK, (illegal) redo did not affect the undo history" );
+	assert.ok( editor.history.redos.length == 0, "OK, (illegal) redo did not affect the redo history" );
 
 
 	editor.undo();
-	ok( editor.history.undos.length == 0, "OK, undo changed the undo history" );
-	ok( editor.history.redos.length == 1, "OK, undo changed the redo history" );
+	assert.ok( editor.history.undos.length == 0, "OK, undo changed the undo history" );
+	assert.ok( editor.history.redos.length == 1, "OK, undo changed the redo history" );
 
 	// illegal
 	editor.undo();
-	ok( editor.history.undos.length == 0, "OK, (illegal) undo did not affect the undo history" );
-	ok( editor.history.redos.length == 1, "OK, (illegal) undo did not affect the redo history" );
+	assert.ok( editor.history.undos.length == 0, "OK, (illegal) undo did not affect the undo history" );
+	assert.ok( editor.history.redos.length == 1, "OK, (illegal) undo did not affect the redo history" );
 
 	editor.redo();
-	ok( editor.history.undos.length == 1, "OK, redo changed the undo history" );
-	ok( editor.history.redos.length == 0, "OK, undo changed the redo history" );
+	assert.ok( editor.history.undos.length == 1, "OK, redo changed the undo history" );
+	assert.ok( editor.history.redos.length == 0, "OK, undo changed the redo history" );
 
 	// illegal
 	editor.redo();
-	ok( editor.history.undos.length == 1, "OK, (illegal) did not affect the undo history" );
-	ok( editor.history.redos.length == 0, "OK, (illegal) did not affect the redo history" );
+	assert.ok( editor.history.undos.length == 1, "OK, (illegal) did not affect the undo history" );
+	assert.ok( editor.history.redos.length == 0, "OK, (illegal) did not affect the redo history" );
 
 } );

+ 31 - 31
test/unit/editor/TestNestedDoUndoRedo.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "NestedDoUndoRedo" );
+QUnit.module( "NestedDoUndoRedo" );
 
-test( "Test nested Do's, Undo's and Redo's", function() {
+QUnit.test( "Test nested Do's, Undo's and Redo's", function( assert ) {
 
 	var editor = new Editor();
 
@@ -46,17 +46,17 @@ test( "Test nested Do's, Undo's and Redo's", function() {
 
 	/* full check */
 
-	ok( mesh.position.x ==   102, "OK, X position is correct " );
-	ok( mesh.position.y ==     3, "OK, Y position is correct " );
-	ok( mesh.position.z ==     4, "OK, Z position is correct " );
+	assert.ok( mesh.position.x ==   102, "OK, X position is correct " );
+	assert.ok( mesh.position.y ==     3, "OK, Y position is correct " );
+	assert.ok( mesh.position.z ==     4, "OK, Z position is correct " );
 
-	ok( mesh.rotation.x ==    12, "OK, X rotation is correct " );
-	ok( mesh.rotation.y ==  1013, "OK, Y rotation is correct " );
-	ok( mesh.rotation.z ==    14, "OK, Z rotation is correct " );
+	assert.ok( mesh.rotation.x ==    12, "OK, X rotation is correct " );
+	assert.ok( mesh.rotation.y ==  1013, "OK, Y rotation is correct " );
+	assert.ok( mesh.rotation.z ==    14, "OK, Z rotation is correct " );
 
-	ok( mesh.scale.x    ==    22, "OK, X scale is correct " );
-	ok( mesh.scale.y    ==    23, "OK, Y scale is correct " );
-	ok( mesh.scale.z    == 10024, "OK, Z scale is correct " );
+	assert.ok( mesh.scale.x    ==    22, "OK, X scale is correct " );
+	assert.ok( mesh.scale.y    ==    23, "OK, Y scale is correct " );
+	assert.ok( mesh.scale.z    == 10024, "OK, Z scale is correct " );
 
 
 	editor.undo();  // rescaling undone
@@ -65,44 +65,44 @@ test( "Test nested Do's, Undo's and Redo's", function() {
 
 	/* full check */
 
-	ok( mesh.position.x ==     2, "OK, X position is correct " );
-	ok( mesh.position.y ==     3, "OK, Y position is correct " );
-	ok( mesh.position.z ==     4, "OK, Z position is correct " );
+	assert.ok( mesh.position.x ==     2, "OK, X position is correct " );
+	assert.ok( mesh.position.y ==     3, "OK, Y position is correct " );
+	assert.ok( mesh.position.z ==     4, "OK, Z position is correct " );
 
-	ok( mesh.rotation.x ==    12, "OK, X rotation is correct " );
-	ok( mesh.rotation.y ==    13, "OK, Y rotation is correct " );
-	ok( mesh.rotation.z ==    14, "OK, Z rotation is correct " );
+	assert.ok( mesh.rotation.x ==    12, "OK, X rotation is correct " );
+	assert.ok( mesh.rotation.y ==    13, "OK, Y rotation is correct " );
+	assert.ok( mesh.rotation.z ==    14, "OK, Z rotation is correct " );
 
-	ok( mesh.scale.x    ==    22, "OK, X scale is correct " );
-	ok( mesh.scale.y    ==    23, "OK, Y scale is correct " );
-	ok( mesh.scale.z    ==    24, "OK, Z scale is correct " );
+	assert.ok( mesh.scale.x    ==    22, "OK, X scale is correct " );
+	assert.ok( mesh.scale.y    ==    23, "OK, Y scale is correct " );
+	assert.ok( mesh.scale.z    ==    24, "OK, Z scale is correct " );
 
 
 	editor.redo();  // translation redone
 	editor.redo();  // rotation redone
 
 	editor.execute( new RemoveObjectCommand( mesh ) );
-	ok( editor.scene.children.length == 0, "OK, object removal was successful" );
+	assert.ok( editor.scene.children.length == 0, "OK, object removal was successful" );
 
 	editor.undo();  // removal undone
-	ok( mesh.rotation.y ==    1013, "OK, Y rotation is correct " );
+	assert.ok( mesh.rotation.y ==    1013, "OK, Y rotation is correct " );
 
 
 	editor.undo();  // rotation undone (expected!)
 
 	/* full check */
 
-	ok( mesh.position.x ==   102, "OK, X position is correct " );
-	ok( mesh.position.y ==     3, "OK, Y position is correct " );
-	ok( mesh.position.z ==     4, "OK, Z position is correct " );
+	assert.ok( mesh.position.x ==   102, "OK, X position is correct " );
+	assert.ok( mesh.position.y ==     3, "OK, Y position is correct " );
+	assert.ok( mesh.position.z ==     4, "OK, Z position is correct " );
 
-	ok( mesh.rotation.x ==    12, "OK, X rotation is correct " );
-	ok( mesh.rotation.y ==    13, "OK, Y rotation is correct " );
-	ok( mesh.rotation.z ==    14, "OK, Z rotation is correct " );
+	assert.ok( mesh.rotation.x ==    12, "OK, X rotation is correct " );
+	assert.ok( mesh.rotation.y ==    13, "OK, Y rotation is correct " );
+	assert.ok( mesh.rotation.z ==    14, "OK, Z rotation is correct " );
 
-	ok( mesh.scale.x    ==    22, "OK, X scale is correct " );
-	ok( mesh.scale.y    ==    23, "OK, Y scale is correct " );
-	ok( mesh.scale.z    ==    24, "OK, Z scale is correct " );
+	assert.ok( mesh.scale.x    ==    22, "OK, X scale is correct " );
+	assert.ok( mesh.scale.y    ==    23, "OK, Y scale is correct " );
+	assert.ok( mesh.scale.z    ==    24, "OK, Z scale is correct " );
 
 
 } );

+ 7 - 7
test/unit/editor/TestRemoveScriptCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "RemoveScriptCommand" );
+QUnit.module( "RemoveScriptCommand" );
 
-test( "Test RemoveScriptCommand (Undo and Redo)", function() {
+QUnit.test( "Test RemoveScriptCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 
@@ -24,7 +24,7 @@ test( "Test RemoveScriptCommand (Undo and Redo)", function() {
 		editor.execute( new AddObjectCommand( item ) );
 
 	} );
-	ok( editor.scene.children.length == 2, "OK, the box and the sphere have been added" );
+	assert.ok( editor.scene.children.length == 2, "OK, the box and the sphere have been added" );
 
 	// add scripts to the objects
 	for ( var i = 0; i < scripts.length; i ++ ) {
@@ -42,23 +42,23 @@ test( "Test RemoveScriptCommand (Undo and Redo)", function() {
 		editor.execute( cmd );
 
 	}
-	ok( getScriptCount( editor ) == 0, "OK, all scripts have been removed" );
+	assert.ok( getScriptCount( editor ) == 0, "OK, all scripts have been removed" );
 
 	scripts.map( function() {
 
 		editor.undo();
 
 	} );
-	ok( getScriptCount( editor ) == scripts.length, "OK, all scripts have been added again by undo(s)" );
+	assert.ok( getScriptCount( editor ) == scripts.length, "OK, all scripts have been added again by undo(s)" );
 
 	var scriptsKeys = Object.keys( editor.scripts );
 	for ( var i = 0; i < scriptsKeys.length; i ++ ) {
 
-		ok( editor.scripts[ scriptsKeys[ i ] ][ 0 ] == scripts[ i ], "OK, script #" + i + " is still assigned correctly" );
+		assert.ok( editor.scripts[ scriptsKeys[ i ] ][ 0 ] == scripts[ i ], "OK, script #" + i + " is still assigned correctly" );
 
 	}
 
 	editor.redo();
-	ok( getScriptCount( editor ) == scripts.length - 1, "OK, one script has been removed again by redo" );
+	assert.ok( getScriptCount( editor ) == scripts.length - 1, "OK, one script has been removed again by redo" );
 
 } );

+ 4 - 4
test/unit/editor/TestSerialization.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "Serialization" );
+QUnit.module( "Serialization" );
 
-test( "Test Serialization", function( assert ) {
+QUnit.test( "Test Serialization", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -321,7 +321,7 @@ test( "Test Serialization", function( assert ) {
 
 			var history2 = JSON.stringify( editor.history.toJSON() );
 
-			ok( history == history2, "OK, forward serializing was successful for " + name );
+			assert.ok( history == history2, "OK, forward serializing was successful for " + name );
 
 			editor.clear();
 
@@ -346,7 +346,7 @@ test( "Test Serialization", function( assert ) {
 
 			var history2 = JSON.stringify( editor.history.toJSON() );
 
-			ok( history == history2, "OK, backward serializing was successful for " + name );
+			assert.ok( history == history2, "OK, backward serializing was successful for " + name );
 
 			editor.clear();
 

+ 5 - 5
test/unit/editor/TestSetColorCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetColorCommand" );
+QUnit.module( "SetColorCommand" );
 
-test( "Test SetColorCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetColorCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 	var pointLight = aPointlight( "The light Light" );
@@ -25,15 +25,15 @@ test( "Test SetColorCommand (Undo and Redo)", function() {
 
 	} );
 
-	ok( pointLight.color.getHex() == colors[ colors.length - 1 ],
+	assert.ok( pointLight.color.getHex() == colors[ colors.length - 1 ],
 		"OK, color has been set successfully (expected: '" + colors[ colors.length - 1 ] + "', actual: '" + pointLight.color.getHex() + "')" );
 
 	editor.undo();
-	ok( pointLight.color.getHex() == colors[ colors.length - 2 ],
+	assert.ok( pointLight.color.getHex() == colors[ colors.length - 2 ],
 		"OK, color has been set successfully after undo (expected: '" + colors[ colors.length - 2 ] + "', actual: '" + pointLight.color.getHex() + "')" );
 
 	editor.redo();
-	ok( pointLight.color.getHex() == colors[ colors.length - 1 ],
+	assert.ok( pointLight.color.getHex() == colors[ colors.length - 1 ],
 		"OK, color has been set successfully after redo (expected: '" + colors[ colors.length - 1 ] + "', actual: '" + pointLight.color.getHex() + "')" );
 
 

+ 20 - 20
test/unit/editor/TestSetGeometryCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetGeometryCommand" );
+QUnit.module( "SetGeometryCommand" );
 
-test( "Test SetGeometryCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetGeometryCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 
@@ -30,34 +30,34 @@ test( "Test SetGeometryCommand (Undo and Redo)", function() {
 		var actualParams = box.geometry.parameters;
 		var expectedParams = geometryParams[ i ].geometry.parameters;
 
-		ok( actualParams.width == expectedParams.width, "OK, box width matches the corresponding value from boxGeometry"  + ( i + 1 ) );
-		ok( actualParams.height == expectedParams.height, "OK, box height matches the corresponding value from boxGeometry" + ( i + 1 ) );
-		ok( actualParams.depth == expectedParams.depth, "OK, box depth matches the corresponding value from boxGeometry"  + ( i + 1 ) );
-		ok( actualParams.widthSegments == expectedParams.widthSegments, "OK, box widthSegments matches the corresponding value from boxGeometry"  + ( i + 1 ) );
-		ok( actualParams.heightSegments == expectedParams.heightSegments, "OK, box heightSegments matches the corresponding value from boxGeometry"  + ( i + 1 ) );
-		ok( actualParams.depthSegments == expectedParams.depthSegments, "OK, box depthSegments matches the corresponding value from boxGeometry"  + ( i + 1 ) );
+		assert.ok( actualParams.width == expectedParams.width, "OK, box width matches the corresponding value from boxGeometry"  + ( i + 1 ) );
+		assert.ok( actualParams.height == expectedParams.height, "OK, box height matches the corresponding value from boxGeometry" + ( i + 1 ) );
+		assert.ok( actualParams.depth == expectedParams.depth, "OK, box depth matches the corresponding value from boxGeometry"  + ( i + 1 ) );
+		assert.ok( actualParams.widthSegments == expectedParams.widthSegments, "OK, box widthSegments matches the corresponding value from boxGeometry"  + ( i + 1 ) );
+		assert.ok( actualParams.heightSegments == expectedParams.heightSegments, "OK, box heightSegments matches the corresponding value from boxGeometry"  + ( i + 1 ) );
+		assert.ok( actualParams.depthSegments == expectedParams.depthSegments, "OK, box depthSegments matches the corresponding value from boxGeometry"  + ( i + 1 ) );
 
 	}
 
 	editor.undo();
 	var actualParams = box.geometry.parameters;
 	var expectedParams = geometryParams[ 0 ].geometry.parameters;
-	ok( actualParams.width == expectedParams.width, "OK, box width matches the corresponding value from boxGeometry1 (after undo)" );
-	ok( actualParams.height == expectedParams.height, "OK, box height matches the corresponding value from boxGeometry1 (after undo)" );
-	ok( actualParams.depth == expectedParams.depth, "OK, box depth matches the corresponding value from boxGeometry1 (after undo)" );
-	ok( actualParams.widthSegments == expectedParams.widthSegments, "OK, box widthSegments matches the corresponding value from boxGeometry1 (after undo)" );
-	ok( actualParams.heightSegments == expectedParams.heightSegments, "OK, box heightSegments matches the corresponding value from boxGeometry1 (after undo)" );
-	ok( actualParams.depthSegments == expectedParams.depthSegments, "OK, box depthSegments matches the corresponding value from boxGeometry1 (after undo)" );
+	assert.ok( actualParams.width == expectedParams.width, "OK, box width matches the corresponding value from boxGeometry1 (after undo)" );
+	assert.ok( actualParams.height == expectedParams.height, "OK, box height matches the corresponding value from boxGeometry1 (after undo)" );
+	assert.ok( actualParams.depth == expectedParams.depth, "OK, box depth matches the corresponding value from boxGeometry1 (after undo)" );
+	assert.ok( actualParams.widthSegments == expectedParams.widthSegments, "OK, box widthSegments matches the corresponding value from boxGeometry1 (after undo)" );
+	assert.ok( actualParams.heightSegments == expectedParams.heightSegments, "OK, box heightSegments matches the corresponding value from boxGeometry1 (after undo)" );
+	assert.ok( actualParams.depthSegments == expectedParams.depthSegments, "OK, box depthSegments matches the corresponding value from boxGeometry1 (after undo)" );
 
 	editor.redo();
 	var actualParams = box.geometry.parameters;
 	var expectedParams = geometryParams[ 1 ].geometry.parameters;
-	ok( actualParams.width == expectedParams.width, "OK, box width matches the corresponding value from boxGeometry2 (after redo)" );
-	ok( actualParams.height == expectedParams.height, "OK, box height matches the corresponding value from boxGeometry2 (after redo)" );
-	ok( actualParams.depth == expectedParams.depth, "OK, box depth matches the corresponding value from boxGeometry2 (after redo)" );
-	ok( actualParams.widthSegments == expectedParams.widthSegments, "OK, box widthSegments matches the corresponding value from boxGeometry2 (after redo)" );
-	ok( actualParams.heightSegments == expectedParams.heightSegments, "OK, box heightSegments matches the corresponding value from boxGeometry2 (after redo)" );
-	ok( actualParams.depthSegments == expectedParams.depthSegments, "OK, box depthSegments matches the corresponding value from boxGeometry2 (after redo)" );
+	assert.ok( actualParams.width == expectedParams.width, "OK, box width matches the corresponding value from boxGeometry2 (after redo)" );
+	assert.ok( actualParams.height == expectedParams.height, "OK, box height matches the corresponding value from boxGeometry2 (after redo)" );
+	assert.ok( actualParams.depth == expectedParams.depth, "OK, box depth matches the corresponding value from boxGeometry2 (after redo)" );
+	assert.ok( actualParams.widthSegments == expectedParams.widthSegments, "OK, box widthSegments matches the corresponding value from boxGeometry2 (after redo)" );
+	assert.ok( actualParams.heightSegments == expectedParams.heightSegments, "OK, box heightSegments matches the corresponding value from boxGeometry2 (after redo)" );
+	assert.ok( actualParams.depthSegments == expectedParams.depthSegments, "OK, box depthSegments matches the corresponding value from boxGeometry2 (after redo)" );
 
 
 } );

+ 8 - 8
test/unit/editor/TestSetGeometryValueCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetGeometryValueCommand" );
+QUnit.module( "SetGeometryValueCommand" );
 
-test( "Test SetGeometryValueCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetGeometryValueCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 	var box = aBox( 'The Box' );
@@ -33,19 +33,19 @@ test( "Test SetGeometryValueCommand (Undo and Redo)", function() {
 
 	}
 
-	ok( box.geometry.name == testData[ 1 ].name, "OK, box.geometry.name is correct after executes" );
-	ok( box.geometry.uuid == testData[ 1 ].uuid, "OK, box.geometry.uuid is correct after executes" );
+	assert.ok( box.geometry.name == testData[ 1 ].name, "OK, box.geometry.name is correct after executes" );
+	assert.ok( box.geometry.uuid == testData[ 1 ].uuid, "OK, box.geometry.uuid is correct after executes" );
 
 	editor.undo();
 	editor.undo();
 
-	ok( box.geometry.name == testData[ 0 ].name, "OK, box.geometry.name is correct after undos" );
-	ok( box.geometry.uuid == testData[ 0 ].uuid, "OK, box.geometry.uuid is correct after undos" );
+	assert.ok( box.geometry.name == testData[ 0 ].name, "OK, box.geometry.name is correct after undos" );
+	assert.ok( box.geometry.uuid == testData[ 0 ].uuid, "OK, box.geometry.uuid is correct after undos" );
 
 	editor.redo();
 	editor.redo();
 
-	ok( box.geometry.name == testData[ 1 ].name, "OK, box.geometry.name is correct after executes" );
-	ok( box.geometry.uuid == testData[ 1 ].uuid, "OK, box.geometry.uuid is correct after executes" );
+	assert.ok( box.geometry.name == testData[ 1 ].name, "OK, box.geometry.name is correct after executes" );
+	assert.ok( box.geometry.uuid == testData[ 1 ].uuid, "OK, box.geometry.uuid is correct after executes" );
 
 } );

+ 5 - 5
test/unit/editor/TestSetMaterialColorCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetMaterialColorCommand" );
+QUnit.module( "SetMaterialColorCommand" );
 
-test( "Test for SetMaterialColorCommand (Undo and Redo)", function() {
+QUnit.test( "Test for SetMaterialColorCommand (Undo and Redo)", function( assert ) {
 
 	// Setup scene
 	var editor = new Editor();
@@ -31,13 +31,13 @@ test( "Test for SetMaterialColorCommand (Undo and Redo)", function() {
 
 		} );
 
-		ok( box.material[ attributeName ].getHex() == colors[ colors.length - 1 ], "OK, " + attributeName + " was set correctly to last color " );
+		assert.ok( box.material[ attributeName ].getHex() == colors[ colors.length - 1 ], "OK, " + attributeName + " was set correctly to last color " );
 
 		editor.undo();
-		ok( box.material[ attributeName ].getHex() == colors[ colors.length - 2 ], "OK, " + attributeName + " is set correctly to second to last color after undo" );
+		assert.ok( box.material[ attributeName ].getHex() == colors[ colors.length - 2 ], "OK, " + attributeName + " is set correctly to second to last color after undo" );
 
 		editor.redo();
-		ok( box.material[ attributeName ].getHex() == colors[ colors.length - 1 ], "OK, " + attributeName + " is set correctly to last color after redo" );
+		assert.ok( box.material[ attributeName ].getHex() == colors[ colors.length - 1 ], "OK, " + attributeName + " is set correctly to last color after redo" );
 
 
 	} );

+ 5 - 5
test/unit/editor/TestSetMaterialCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetMaterialCommand" );
+QUnit.module( "SetMaterialCommand" );
 
-test( "Test for SetMaterialCommand (Undo and Redo)", function() {
+QUnit.test( "Test for SetMaterialCommand (Undo and Redo)", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -38,7 +38,7 @@ test( "Test for SetMaterialCommand (Undo and Redo)", function() {
 	var i = materialClasses.length - 1;
 
 	// initial test
-	ok( box.material.type == materialClasses[ i ],
+	assert.ok( box.material.type == materialClasses[ i ],
 		"OK, initial material type was set correctly (expected: '" + materialClasses[ i ] + "', actual: '" + box.material.type + "')" );
 
 
@@ -48,7 +48,7 @@ test( "Test for SetMaterialCommand (Undo and Redo)", function() {
 
 		editor.undo();
 		-- i;
-		ok( box.material.type == materialClasses[ i ],
+		assert.ok( box.material.type == materialClasses[ i ],
 			"OK, material type was set correctly after undo (expected: '" + materialClasses[ i ] + "', actual: '" + box.material.type + "')" );
 
 	}
@@ -58,7 +58,7 @@ test( "Test for SetMaterialCommand (Undo and Redo)", function() {
 
 		editor.redo();
 		++ i;
-		ok( box.material.type == materialClasses[ i ],
+		assert.ok( box.material.type == materialClasses[ i ],
 			"OK, material type was set correctly after redo (expected: '" + materialClasses[ i ] + "', actual: '" + box.material.type + "')" );
 
 	}

+ 5 - 5
test/unit/editor/TestSetMaterialMapCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetMaterialMapCommand" );
+QUnit.module( "SetMaterialMapCommand" );
 
-test( "Test for SetMaterialMapCommand (Undo and Redo)", function() {
+QUnit.test( "Test for SetMaterialMapCommand (Undo and Redo)", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -54,15 +54,15 @@ test( "Test for SetMaterialMapCommand (Undo and Redo)", function() {
 		} );
 
 
-		ok( box.material[ mapName ].image.src == images[ images.length - 1 ].image.src,
+		assert.ok( box.material[ mapName ].image.src == images[ images.length - 1 ].image.src,
 			"OK, " + mapName + " set correctly " );
 
 		editor.undo();
-		ok( box.material[ mapName ].image.src == images[ images.length - 2 ].image.src,
+		assert.ok( box.material[ mapName ].image.src == images[ images.length - 2 ].image.src,
 			"OK, " + mapName + " set correctly after undo " );
 
 		editor.redo();
-		ok( box.material[ mapName ].image.src == images[ images.length - 1 ].image.src,
+		assert.ok( box.material[ mapName ].image.src == images[ images.length - 1 ].image.src,
 			"OK, " + mapName + " set correctly after redo" );
 
 	} );

+ 5 - 5
test/unit/editor/TestSetMaterialValueCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetMaterialValueCommand" );
+QUnit.module( "SetMaterialValueCommand" );
 
-test( "Test for SetMaterialValueCommand (Undo and Redo)", function() {
+QUnit.test( "Test for SetMaterialValueCommand (Undo and Redo)", function( assert ) {
 
 	// setup scene
 	var editor = new Editor();
@@ -46,15 +46,15 @@ test( "Test for SetMaterialValueCommand (Undo and Redo)", function() {
 		} );
 
 		var length = testData[ attributeName ].length;
-		ok( box.material[ attributeName ] == testData[ attributeName ][ length - 1 ],
+		assert.ok( box.material[ attributeName ] == testData[ attributeName ][ length - 1 ],
 			"OK, " + attributeName + " was set correctly to the last value (expected: '" + testData[ attributeName ][ length - 1 ] + "', actual: '" + box.material[ attributeName ] + "')" );
 
 		editor.undo();
-		ok( box.material[ attributeName ] == testData[ attributeName ][ length - 2 ],
+		assert.ok( box.material[ attributeName ] == testData[ attributeName ][ length - 2 ],
 			"OK, " + attributeName + " was set correctly to the second to the last value after undo (expected: '" + testData[ attributeName ][ length - 2 ] + "', actual: '" + box.material[ attributeName ] + "')" );
 
 		editor.redo();
-		ok( box.material[ attributeName ] == testData[ attributeName ][ length - 1 ],
+		assert.ok( box.material[ attributeName ] == testData[ attributeName ][ length - 1 ],
 			"OK, " + attributeName + " was set correctly to the last value again after redo (expected: '" + testData[ attributeName ][ length - 1 ] + "', actual: '" + box.material[ attributeName ] + "')" );
 
 	} );

+ 11 - 11
test/unit/editor/TestSetPositionCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetPositionCommand" );
+QUnit.module( "SetPositionCommand" );
 
-test( "Test SetPositionCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetPositionCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 	var box = aBox();
@@ -29,20 +29,20 @@ test( "Test SetPositionCommand (Undo and Redo)", function() {
 
 	} );
 
-	ok( box.position.x == positions[ positions.length - 1 ].x, "OK, changing X position was successful" );
-	ok( box.position.y == positions[ positions.length - 1 ].y, "OK, changing Y position was successful" );
-	ok( box.position.z == positions[ positions.length - 1 ].z, "OK, changing Z position was successful" );
+	assert.ok( box.position.x == positions[ positions.length - 1 ].x, "OK, changing X position was successful" );
+	assert.ok( box.position.y == positions[ positions.length - 1 ].y, "OK, changing Y position was successful" );
+	assert.ok( box.position.z == positions[ positions.length - 1 ].z, "OK, changing Z position was successful" );
 
 
 	editor.undo();
-	ok( box.position.x == positions[ positions.length - 2 ].x, "OK, changing X position was successful (after undo)" );
-	ok( box.position.y == positions[ positions.length - 2 ].y, "OK, changing Y position was successful (after undo)" );
-	ok( box.position.z == positions[ positions.length - 2 ].z, "OK, changing Z position was successful (after undo)" );
+	assert.ok( box.position.x == positions[ positions.length - 2 ].x, "OK, changing X position was successful (after undo)" );
+	assert.ok( box.position.y == positions[ positions.length - 2 ].y, "OK, changing Y position was successful (after undo)" );
+	assert.ok( box.position.z == positions[ positions.length - 2 ].z, "OK, changing Z position was successful (after undo)" );
 
 	editor.redo();
-	ok( box.position.x == positions[ positions.length - 1 ].x, "OK, changing X position was successful (after redo)" );
-	ok( box.position.y == positions[ positions.length - 1 ].y, "OK, changing Y position was successful (after redo)" );
-	ok( box.position.z == positions[ positions.length - 1 ].z, "OK, changing Z position was successful (after redo)" );
+	assert.ok( box.position.x == positions[ positions.length - 1 ].x, "OK, changing X position was successful (after redo)" );
+	assert.ok( box.position.y == positions[ positions.length - 1 ].y, "OK, changing Y position was successful (after redo)" );
+	assert.ok( box.position.z == positions[ positions.length - 1 ].z, "OK, changing Z position was successful (after redo)" );
 
 
 } );

+ 11 - 11
test/unit/editor/TestSetRotationCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetRotationCommand" );
+QUnit.module( "SetRotationCommand" );
 
-test( "Test SetRotationCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetRotationCommand (Undo and Redo)", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -32,19 +32,19 @@ test( "Test SetRotationCommand (Undo and Redo)", function() {
 	} );
 
 
-	ok( box.rotation.x == rotations[ rotations.length - 1 ].x, "OK, changing X rotation was successful" );
-	ok( box.rotation.y == rotations[ rotations.length - 1 ].y, "OK, changing Y rotation was successful" );
-	ok( box.rotation.z == rotations[ rotations.length - 1 ].z, "OK, changing Z rotation was successful" );
+	assert.ok( box.rotation.x == rotations[ rotations.length - 1 ].x, "OK, changing X rotation was successful" );
+	assert.ok( box.rotation.y == rotations[ rotations.length - 1 ].y, "OK, changing Y rotation was successful" );
+	assert.ok( box.rotation.z == rotations[ rotations.length - 1 ].z, "OK, changing Z rotation was successful" );
 
 	editor.undo();
-	ok( box.rotation.x == rotations[ rotations.length - 2 ].x, "OK, changing X rotation was successful (after undo)" );
-	ok( box.rotation.y == rotations[ rotations.length - 2 ].y, "OK, changing Y rotation was successful (after undo)" );
-	ok( box.rotation.z == rotations[ rotations.length - 2 ].z, "OK, changing Z rotation was successful (after undo)" );
+	assert.ok( box.rotation.x == rotations[ rotations.length - 2 ].x, "OK, changing X rotation was successful (after undo)" );
+	assert.ok( box.rotation.y == rotations[ rotations.length - 2 ].y, "OK, changing Y rotation was successful (after undo)" );
+	assert.ok( box.rotation.z == rotations[ rotations.length - 2 ].z, "OK, changing Z rotation was successful (after undo)" );
 
 	editor.redo();
-	ok( box.rotation.x == rotations[ rotations.length - 1 ].x, "OK, changing X rotation was successful (after redo)" );
-	ok( box.rotation.y == rotations[ rotations.length - 1 ].y, "OK, changing Y rotation was successful (after redo)" );
-	ok( box.rotation.z == rotations[ rotations.length - 1 ].z, "OK, changing Z rotation was successful (after redo)" );
+	assert.ok( box.rotation.x == rotations[ rotations.length - 1 ].x, "OK, changing X rotation was successful (after redo)" );
+	assert.ok( box.rotation.y == rotations[ rotations.length - 1 ].y, "OK, changing Y rotation was successful (after redo)" );
+	assert.ok( box.rotation.z == rotations[ rotations.length - 1 ].z, "OK, changing Z rotation was successful (after redo)" );
 
 
 

+ 11 - 11
test/unit/editor/TestSetScaleCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetScaleCommand" );
+QUnit.module( "SetScaleCommand" );
 
-test( "Test SetScaleCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetScaleCommand (Undo and Redo)", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -31,21 +31,21 @@ test( "Test SetScaleCommand (Undo and Redo)", function() {
 
 	} );
 
-	ok( box.scale.x == scales[ scales.length - 1 ].x, "OK, setting X scale value was successful" );
-	ok( box.scale.y == scales[ scales.length - 1 ].y, "OK, setting Y scale value was successful" );
-	ok( box.scale.z == scales[ scales.length - 1 ].z, "OK, setting Z scale value was successful" );
+	assert.ok( box.scale.x == scales[ scales.length - 1 ].x, "OK, setting X scale value was successful" );
+	assert.ok( box.scale.y == scales[ scales.length - 1 ].y, "OK, setting Y scale value was successful" );
+	assert.ok( box.scale.z == scales[ scales.length - 1 ].z, "OK, setting Z scale value was successful" );
 
 
 	editor.undo();
-	ok( box.scale.x == scales[ scales.length - 2 ].x, "OK, X scale is correct after undo" );
-	ok( box.scale.y == scales[ scales.length - 2 ].y, "OK, Y scale is correct after undo" );
-	ok( box.scale.z == scales[ scales.length - 2 ].z, "OK, Z scale is correct after undo" );
+	assert.ok( box.scale.x == scales[ scales.length - 2 ].x, "OK, X scale is correct after undo" );
+	assert.ok( box.scale.y == scales[ scales.length - 2 ].y, "OK, Y scale is correct after undo" );
+	assert.ok( box.scale.z == scales[ scales.length - 2 ].z, "OK, Z scale is correct after undo" );
 
 
 	editor.redo();
-	ok( box.scale.x == scales[ scales.length - 1 ].x, "OK, X scale is correct after redo" );
-	ok( box.scale.y == scales[ scales.length - 1 ].y, "OK, Y scale is correct after redo" );
-	ok( box.scale.z == scales[ scales.length - 1 ].z, "OK, Z scale is correct after redo" );
+	assert.ok( box.scale.x == scales[ scales.length - 1 ].x, "OK, X scale is correct after redo" );
+	assert.ok( box.scale.y == scales[ scales.length - 1 ].y, "OK, Y scale is correct after redo" );
+	assert.ok( box.scale.z == scales[ scales.length - 1 ].z, "OK, Z scale is correct after redo" );
 
 
 } );

+ 6 - 6
test/unit/editor/TestSetSceneCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "TestCmdSetScene" );
+QUnit.module( "TestCmdSetScene" );
 
-test( "Test for SetSceneCommand (Undo and Redo)", function() {
+QUnit.test( "Test for SetSceneCommand (Undo and Redo)", function( assert ) {
 
 	// setup
 	var editor = new Editor();
@@ -36,13 +36,13 @@ test( "Test for SetSceneCommand (Undo and Redo)", function() {
 	} );
 
 	// tests
-	ok( editor.scene.children.length = scenes.length,
+	assert.ok( editor.scene.children.length = scenes.length,
 		"OK, all scenes have been merged" );
 
 	var i = 0;
 	while ( i < editor.scene.children.length ) {
 
-		ok( editor.scene.children[ i ].name == scenes[ i ].obj.name,
+		assert.ok( editor.scene.children[ i ].name == scenes[ i ].obj.name,
 			"OK, editor.scene.children[ " + i + " ].name matches scenes[ " + i + " ].obj.name" );
 		i ++;
 
@@ -52,7 +52,7 @@ test( "Test for SetSceneCommand (Undo and Redo)", function() {
 	var i = 0;
 	while ( i < editor.scene.children.length ) {
 
-		ok( editor.scene.children[ i ].name == scenes[ i ].obj.name,
+		assert.ok( editor.scene.children[ i ].name == scenes[ i ].obj.name,
 			"OK, editor.scene.children[ " + i + " ].name matches scenes[ " + i + " ].obj.name after undo" );
 		i ++;
 
@@ -63,7 +63,7 @@ test( "Test for SetSceneCommand (Undo and Redo)", function() {
 	var i = 0;
 	while ( i < editor.scene.children.length ) {
 
-		ok( editor.scene.children[ i ].name == scenes[ i ].obj.name,
+		assert.ok( editor.scene.children[ i ].name == scenes[ i ].obj.name,
 			"OK, editor.scene.children[ " + i + " ].name matches scenes[ " + i + " ].obj.name after redo" );
 		i ++;
 

+ 8 - 8
test/unit/editor/TestSetScriptValueCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetScriptValueCommand" );
+QUnit.module( "SetScriptValueCommand" );
 
-test( "Test SetScriptValueCommand for source (Undo and Redo)", function() {
+QUnit.test( "Test SetScriptValueCommand for source (Undo and Redo)", function( assert ) {
 
 
 	// setup
@@ -41,15 +41,15 @@ test( "Test SetScriptValueCommand for source (Undo and Redo)", function() {
 	} );
 
 	var length = testSourceData.length;
-	ok( editor.scripts[ box.uuid ][ 0 ][ 'source' ] == testSourceData[ length - 1 ].source,
+	assert.ok( editor.scripts[ box.uuid ][ 0 ][ 'source' ] == testSourceData[ length - 1 ].source,
 		"OK, 'source' was set correctly to the last value (expected: '" + testSourceData[ length - 1 ].source + "', actual: '" + editor.scripts[ box.uuid ][ 0 ][ 'source' ] + "')" );
 
 	editor.undo();
-	ok( editor.scripts[ box.uuid ][ 0 ][ 'source' ] == testSourceData[ length - 2 ].source,
+	assert.ok( editor.scripts[ box.uuid ][ 0 ][ 'source' ] == testSourceData[ length - 2 ].source,
 		"OK, 'source' was set correctly to the second to the last value after undo (expected: '" + testSourceData[ length - 2 ].source + "', actual: '" + editor.scripts[ box.uuid ][ 0 ][ 'source' ] + "')" );
 
 	editor.redo();
-	ok( editor.scripts[ box.uuid ][ 0 ][ 'source' ] == testSourceData[ length - 1 ].source,
+	assert.ok( editor.scripts[ box.uuid ][ 0 ][ 'source' ] == testSourceData[ length - 1 ].source,
 		"OK, 'source' was set correctly to the last value again after redo (expected: '" + testSourceData[ length - 1 ].source + "', actual: '" + editor.scripts[ box.uuid ][ 0 ][ 'source' ]	 + "')" );
 
 
@@ -64,14 +64,14 @@ test( "Test SetScriptValueCommand for source (Undo and Redo)", function() {
 	} );
 
 	var scriptName = editor.scripts[ box.uuid ][ 0 ][ "name" ];
-	ok( scriptName == names[ names.length - 1 ], "OK, the script name corresponds to the last script name that was assigned" );
+	assert.ok( scriptName == names[ names.length - 1 ], "OK, the script name corresponds to the last script name that was assigned" );
 
 	editor.undo();
 	scriptName = editor.scripts[ box.uuid ][ 0 ][ "name" ];
-	ok( scriptName == names[ names.length - 2 ], "OK, the script name corresponds to the second last script name that was assigned" );
+	assert.ok( scriptName == names[ names.length - 2 ], "OK, the script name corresponds to the second last script name that was assigned" );
 
 	editor.redo();
 	scriptName = editor.scripts[ box.uuid ][ 0 ][ "name" ];
-	ok( scriptName == names[ names.length - 1 ], "OK, the script name corresponds to the last script name that was assigned, again" );
+	assert.ok( scriptName == names[ names.length - 1 ], "OK, the script name corresponds to the last script name that was assigned, again" );
 
 } );

+ 5 - 5
test/unit/editor/TestSetUuidCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetUuidCommand" );
+QUnit.module( "SetUuidCommand" );
 
-test( "Test SetUuidCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetUuidCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 	var object = aBox( 'UUID test box' );
@@ -22,15 +22,15 @@ test( "Test SetUuidCommand (Undo and Redo)", function() {
 
 	} );
 
-	ok( object.uuid == uuids[ uuids.length - 1 ],
+	assert.ok( object.uuid == uuids[ uuids.length - 1 ],
 		"OK, UUID on actual object matches last UUID in the test data array " );
 
 	editor.undo();
-	ok( object.uuid == uuids[ uuids.length - 2 ],
+	assert.ok( object.uuid == uuids[ uuids.length - 2 ],
 		"OK, UUID on actual object matches second to the last UUID in the test data array (after undo)" );
 
 	editor.redo();
-	ok( object.uuid == uuids[ uuids.length - 1 ],
+	assert.ok( object.uuid == uuids[ uuids.length - 1 ],
 		"OK, UUID on actual object matches last UUID in the test data array again (after redo) " );
 
 

+ 7 - 7
test/unit/editor/TestSetValueCommand.js

@@ -3,9 +3,9 @@
  * Developed as part of a project at University of Applied Sciences and Arts Northwestern Switzerland (www.fhnw.ch)
  */
 
-module( "SetValueCommand" );
+QUnit.module( "SetValueCommand" );
 
-test( "Test SetValueCommand (Undo and Redo)", function() {
+QUnit.test( "Test SetValueCommand (Undo and Redo)", function( assert ) {
 
 	var editor = new Editor();
 
@@ -20,7 +20,7 @@ test( "Test SetValueCommand (Undo and Redo)", function() {
 
 		editor.execute( new AddObjectCommand( object ) );
 
-		ok( 0 == 0, "Testing object of type '" + object.type + "'" );
+		assert.ok( 0 == 0, "Testing object of type '" + object.type + "'" );
 
 		[ 'name', 'fov', 'near', 'far', 'intensity', 'distance', 'angle', 'exponent', 'decay', 'visible', 'userData' ].map( function( item ) {
 
@@ -29,18 +29,18 @@ test( "Test SetValueCommand (Undo and Redo)", function() {
 				var cmd = new SetValueCommand( object, item, valueBefore );
 				cmd.updatable = false;
 				editor.execute( cmd );
-				ok( object[ item ] == valueBefore, " OK, the attribute '" + item + "' is correct after first execute (expected: '" + valueBefore + "', actual: '" + object[ item ] + "')" );
+				assert.ok( object[ item ] == valueBefore, " OK, the attribute '" + item + "' is correct after first execute (expected: '" + valueBefore + "', actual: '" + object[ item ] + "')" );
 
 				var cmd = new SetValueCommand( object, item, valueAfter );
 				cmd.updatable = false;
 				editor.execute( cmd );
-				ok( object[ item ] == valueAfter, " OK, the attribute '" + item + "' is correct after second execute (expected: '" + valueAfter + "', actual: '" + object[ item ] + "')" );
+				assert.ok( object[ item ] == valueAfter, " OK, the attribute '" + item + "' is correct after second execute (expected: '" + valueAfter + "', actual: '" + object[ item ] + "')" );
 
 				editor.undo();
-				ok( object[ item ] == valueBefore, " OK, the attribute '" + item + "' is correct after undo (expected: '" + valueBefore + "', actual: '" + object[ item ] + "')" );
+				assert.ok( object[ item ] == valueBefore, " OK, the attribute '" + item + "' is correct after undo (expected: '" + valueBefore + "', actual: '" + object[ item ] + "')" );
 
 				editor.redo();
-				ok( object[ item ] == valueAfter, " OK, the attribute '" + item + "' is correct after redo (expected: '" + valueAfter + "', actual: '" + object[ item ] + "')" );
+				assert.ok( object[ item ] == valueAfter, " OK, the attribute '" + item + "' is correct after redo (expected: '" + valueAfter + "', actual: '" + object[ item ] + "')" );
 
 			}
 

+ 0 - 87
test/unit/extras/ImageUtils.test.js

@@ -1,87 +0,0 @@
-QUnit.module( "ImageLoader", {
-
-	beforeEach: function() {
-
-		THREE.Cache.clear();
-
-	}
-
-});
-
-
-var good_url = '../../examples/textures/sprite.png';
-var bad_url = 'url_not_found';
-
-
-QUnit.test( "test load handler", function( assert ) {
-
-	var done = assert.async();
-
-  new THREE.TextureLoader().load(good_url, function ( tex ) {
-
-		assert.success( "load handler should be called" );
-		assert.ok( tex, "texture is defined" );
-		assert.ok( tex.image, "texture.image is defined" );
-		done();
-
-	}, undefined, function () {
-
-		assert.fail( "error handler should not be called" );
-		done();
-
-	});
-});
-
-
-QUnit.test( "test error handler", function( assert ) {
-
-	var done = assert.async();
-
-	new THREE.TextureLoader().load(bad_url, function () {
-
-		assert.fail( "load handler should not be called" );
-		done();
-
-	},
-
-	undefined,
-
-	function ( event ) {
-
-		assert.success( "error handler should be called" );
-		assert.ok( event.type === 'error', "should have error event" );
-
-		done();
-
-	});
-
-});
-
-
-QUnit.test( "test cached texture", function( assert ) {
-
-	var done = assert.async();
-
-	var rtex1 = new THREE.TextureLoader().load(good_url, function ( tex1 ) {
-
-		assert.ok( rtex1.image !== undefined, "texture 1 image is loaded" );
-		assert.equal( rtex1, tex1, "texture 1 callback is equal to return" );
-
-		var rtex2 = new THREE.TextureLoader().load(good_url, function ( tex2 ) {
-
-			assert.ok( rtex2 !== undefined, "cached callback is async" );
-			assert.ok( rtex2.image !== undefined, "texture 2 image is loaded" );
-			assert.equal( rtex2, tex2, "texture 2 callback is equal to return" );
-
-			done();
-
-		});
-
-		assert.ok( rtex2, "texture 2 return is defined" );
-
-	});
-
-	assert.ok( rtex1, "texture 1 return is defined" );
-	assert.ok( rtex1.image === undefined, "texture 1 image is not loaded" );
-
-});

+ 0 - 246
test/unit/math/Box2.js

@@ -1,246 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Box2" );
-
-test( "constructor", function() {
-	var a = new THREE.Box2();
-	ok( a.min.equals( posInf2 ), "Passed!" );
-	ok( a.max.equals( negInf2 ), "Passed!" );
-
-	a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	ok( a.min.equals( zero2 ), "Passed!" );
-	ok( a.max.equals( zero2 ), "Passed!" );
-
-	a = new THREE.Box2( zero2.clone(), one2.clone() );
-	ok( a.min.equals( zero2 ), "Passed!" );
-	ok( a.max.equals( one2 ), "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Box2( zero2.clone(), one2.clone() );
-	var b = new THREE.Box2().copy( a );
-	ok( b.min.equals( zero2 ), "Passed!" );
-	ok( b.max.equals( one2 ), "Passed!" );
-
-	// ensure that it is a true copy
-	a.min = zero2;
-	a.max = one2;
-	ok( b.min.equals( zero2 ), "Passed!" );
-	ok( b.max.equals( one2 ), "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Box2();
-
-	a.set( zero2, one2 );
-	ok( a.min.equals( zero2 ), "Passed!" );
-	ok( a.max.equals( one2 ), "Passed!" );
-});
-
-test( "setFromPoints", function() {
-	var a = new THREE.Box2();
-
-	a.setFromPoints( [ zero2, one2, two2 ] );
-	ok( a.min.equals( zero2 ), "Passed!" );
-	ok( a.max.equals( two2 ), "Passed!" );
-
-	a.setFromPoints( [ one2 ] );
-	ok( a.min.equals( one2 ), "Passed!" );
-	ok( a.max.equals( one2 ), "Passed!" );
-
-	a.setFromPoints( [] );
-	ok( a.isEmpty(), "Passed!" );
-});
-
-test( "empty/makeEmpty", function() {
-	var a = new THREE.Box2();
-
-	ok( a.isEmpty(), "Passed!" );
-
-	var a = new THREE.Box2( zero2.clone(), one2.clone() );
-	ok( ! a.isEmpty(), "Passed!" );
-
-	a.makeEmpty();
-	ok( a.isEmpty(), "Passed!" );
-});
-
-test( "getCenter", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-
-	ok( a.getCenter().equals( zero2 ), "Passed!" );
-
-	a = new THREE.Box2( zero2, one2 );
-	var midpoint = one2.clone().multiplyScalar( 0.5 );
-	ok( a.getCenter().equals( midpoint ), "Passed!" );
-});
-
-test( "getSize", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-
-	ok( a.getSize().equals( zero2 ), "Passed!" );
-
-	a = new THREE.Box2( zero2.clone(), one2.clone() );
-	ok( a.getSize().equals( one2 ), "Passed!" );
-});
-
-
-test( "expandByPoint", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-
-	a.expandByPoint( zero2 );
-	ok( a.getSize().equals( zero2 ), "Passed!" );
-
-	a.expandByPoint( one2 );
-	ok( a.getSize().equals( one2 ), "Passed!" );
-
-	a.expandByPoint( one2.clone().negate() );
-	ok( a.getSize().equals( one2.clone().multiplyScalar( 2 ) ), "Passed!" );
-	ok( a.getCenter().equals( zero2 ), "Passed!" );
-});
-
-test( "expandByVector", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-
-	a.expandByVector( zero2 );
-	ok( a.getSize().equals( zero2 ), "Passed!" );
-
-	a.expandByVector( one2 );
-	ok( a.getSize().equals( one2.clone().multiplyScalar( 2 ) ), "Passed!" );
-	ok( a.getCenter().equals( zero2 ), "Passed!" );
-});
-
-test( "expandByScalar", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-
-	a.expandByScalar( 0 );
-	ok( a.getSize().equals( zero2 ), "Passed!" );
-
-	a.expandByScalar( 1 );
-	ok( a.getSize().equals( one2.clone().multiplyScalar( 2 ) ), "Passed!" );
-	ok( a.getCenter().equals( zero2 ), "Passed!" );
-});
-
-test( "containsPoint", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-
-	ok( a.containsPoint( zero2 ), "Passed!" );
-	ok( ! a.containsPoint( one2 ), "Passed!" );
-
-	a.expandByScalar( 1 );
-	ok( a.containsPoint( zero2 ), "Passed!" );
-	ok( a.containsPoint( one2 ), "Passed!" );
-	ok( a.containsPoint( one2.clone().negate() ), "Passed!" );
-});
-
-test( "containsBox", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( zero2.clone(), one2.clone() );
-	var c = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.containsBox( a ), "Passed!" );
-	ok( ! a.containsBox( b ), "Passed!" );
-	ok( ! a.containsBox( c ), "Passed!" );
-
-	ok( b.containsBox( a ), "Passed!" );
-	ok( c.containsBox( a ), "Passed!" );
-	ok( ! b.containsBox( c ), "Passed!" );
-});
-
-test( "getParameter", function() {
-	var a = new THREE.Box2( zero2.clone(), one2.clone() );
-	var b = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.getParameter( new THREE.Vector2( 0, 0 ) ).equals( new THREE.Vector2( 0, 0 ) ), "Passed!" );
-	ok( a.getParameter( new THREE.Vector2( 1, 1 ) ).equals( new THREE.Vector2( 1, 1 ) ), "Passed!" );
-
-	ok( b.getParameter( new THREE.Vector2( -1, -1 ) ).equals( new THREE.Vector2( 0, 0 ) ), "Passed!" );
-	ok( b.getParameter( new THREE.Vector2( 0, 0 ) ).equals( new THREE.Vector2( 0.5, 0.5 ) ), "Passed!" );
-	ok( b.getParameter( new THREE.Vector2( 1, 1 ) ).equals( new THREE.Vector2( 1, 1 ) ), "Passed!" );
-});
-
-test( "clampPoint", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.clampPoint( new THREE.Vector2( 0, 0 ) ).equals( new THREE.Vector2( 0, 0 ) ), "Passed!" );
-	ok( a.clampPoint( new THREE.Vector2( 1, 1 ) ).equals( new THREE.Vector2( 0, 0 ) ), "Passed!" );
-	ok( a.clampPoint( new THREE.Vector2( -1, -1 ) ).equals( new THREE.Vector2( 0, 0 ) ), "Passed!" );
-
-	ok( b.clampPoint( new THREE.Vector2( 2, 2 ) ).equals( new THREE.Vector2( 1, 1 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector2( 1, 1 ) ).equals( new THREE.Vector2( 1, 1 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector2( 0, 0 ) ).equals( new THREE.Vector2( 0, 0 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector2( -1, -1 ) ).equals( new THREE.Vector2( -1, -1 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector2( -2, -2 ) ).equals( new THREE.Vector2( -1, -1 ) ), "Passed!" );
-});
-
-test( "distanceToPoint", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.distanceToPoint( new THREE.Vector2( 0, 0 ) ) == 0, "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector2( 1, 1 ) ) == Math.sqrt( 2 ), "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector2( -1, -1 ) ) == Math.sqrt( 2 ), "Passed!" );
-
-	ok( b.distanceToPoint( new THREE.Vector2( 2, 2 ) ) == Math.sqrt( 2 ), "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector2( 1, 1 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector2( 0, 0 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector2( -1, -1 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector2( -2, -2 ) ) == Math.sqrt( 2 ), "Passed!" );
-});
-
-test( "intersectsBox", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( zero2.clone(), one2.clone() );
-	var c = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.intersectsBox( a ), "Passed!" );
-	ok( a.intersectsBox( b ), "Passed!" );
-	ok( a.intersectsBox( c ), "Passed!" );
-
-	ok( b.intersectsBox( a ), "Passed!" );
-	ok( c.intersectsBox( a ), "Passed!" );
-	ok( b.intersectsBox( c ), "Passed!" );
-
-	b.translate( new THREE.Vector2( 2, 2 ) );
-	ok( ! a.intersectsBox( b ), "Passed!" );
-	ok( ! b.intersectsBox( a ), "Passed!" );
-	ok( ! b.intersectsBox( c ), "Passed!" );
-});
-
-test( "intersect", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( zero2.clone(), one2.clone() );
-	var c = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.clone().intersect( a ).equals( a ), "Passed!" );
-	ok( a.clone().intersect( b ).equals( a ), "Passed!" );
-	ok( b.clone().intersect( b ).equals( b ), "Passed!" );
-	ok( a.clone().intersect( c ).equals( a ), "Passed!" );
-	ok( b.clone().intersect( c ).equals( b ), "Passed!" );
-	ok( c.clone().intersect( c ).equals( c ), "Passed!" );
-});
-
-test( "union", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( zero2.clone(), one2.clone() );
-	var c = new THREE.Box2( one2.clone().negate(), one2.clone() );
-
-	ok( a.clone().union( a ).equals( a ), "Passed!" );
-	ok( a.clone().union( b ).equals( b ), "Passed!" );
-	ok( a.clone().union( c ).equals( c ), "Passed!" );
-	ok( b.clone().union( c ).equals( c ), "Passed!" );
-});
-
-test( "translate", function() {
-	var a = new THREE.Box2( zero2.clone(), zero2.clone() );
-	var b = new THREE.Box2( zero2.clone(), one2.clone() );
-	var c = new THREE.Box2( one2.clone().negate(), one2.clone() );
-	var d = new THREE.Box2( one2.clone().negate(), zero2.clone() );
-
-	ok( a.clone().translate( one2 ).equals( new THREE.Box2( one2, one2 ) ), "Passed!" );
-	ok( a.clone().translate( one2 ).translate( one2.clone().negate() ).equals( a ), "Passed!" );
-	ok( d.clone().translate( one2 ).equals( b ), "Passed!" );
-	ok( b.clone().translate( one2.clone().negate() ).equals( d ), "Passed!" );
-});

+ 0 - 313
test/unit/math/Box3.js

@@ -1,313 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Box3" );
-
-test( "constructor", function() {
-	var a = new THREE.Box3();
-	ok( a.min.equals( posInf3 ), "Passed!" );
-	ok( a.max.equals( negInf3 ), "Passed!" );
-
-	a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	ok( a.min.equals( zero3 ), "Passed!" );
-	ok( a.max.equals( zero3 ), "Passed!" );
-
-	a = new THREE.Box3( zero3.clone(), one3.clone() );
-	ok( a.min.equals( zero3 ), "Passed!" );
-	ok( a.max.equals( one3 ), "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Box3( zero3.clone(), one3.clone() );
-	var b = new THREE.Box3().copy( a );
-	ok( b.min.equals( zero3 ), "Passed!" );
-	ok( b.max.equals( one3 ), "Passed!" );
-
-	// ensure that it is a true copy
-	a.min = zero3;
-	a.max = one3;
-	ok( b.min.equals( zero3 ), "Passed!" );
-	ok( b.max.equals( one3 ), "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Box3();
-
-	a.set( zero3, one3 );
-	ok( a.min.equals( zero3 ), "Passed!" );
-	ok( a.max.equals( one3 ), "Passed!" );
-});
-
-test( "setFromPoints", function() {
-	var a = new THREE.Box3();
-
-	a.setFromPoints( [ zero3, one3, two3 ] );
-	ok( a.min.equals( zero3 ), "Passed!" );
-	ok( a.max.equals( two3 ), "Passed!" );
-
-	a.setFromPoints( [ one3 ] );
-	ok( a.min.equals( one3 ), "Passed!" );
-	ok( a.max.equals( one3 ), "Passed!" );
-
-	a.setFromPoints( [] );
-	ok( a.isEmpty(), "Passed!" );
-});
-
-test( "empty/makeEmpty", function() {
-	var a = new THREE.Box3();
-
-	ok( a.isEmpty(), "Passed!" );
-
-	var a = new THREE.Box3( zero3.clone(), one3.clone() );
-	ok( ! a.isEmpty(), "Passed!" );
-
-	a.makeEmpty();
-	ok( a.isEmpty(), "Passed!" );
-});
-
-test( "getCenter", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-
-	ok( a.getCenter().equals( zero3 ), "Passed!" );
-
-	a = new THREE.Box3( zero3.clone(), one3.clone() );
-	var midpoint = one3.clone().multiplyScalar( 0.5 );
-	ok( a.getCenter().equals( midpoint ), "Passed!" );
-});
-
-test( "getSize", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-
-	ok( a.getSize().equals( zero3 ), "Passed!" );
-
-	a = new THREE.Box3( zero3.clone(), one3.clone() );
-	ok( a.getSize().equals( one3 ), "Passed!" );
-});
-
-
-test( "expandByPoint", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-
-	a.expandByPoint( zero3 );
-	ok( a.getSize().equals( zero3 ), "Passed!" );
-
-	a.expandByPoint( one3 );
-	ok( a.getSize().equals( one3 ), "Passed!" );
-
-	a.expandByPoint( one3.clone().negate() );
-	ok( a.getSize().equals( one3.clone().multiplyScalar( 2 ) ), "Passed!" );
-	ok( a.getCenter().equals( zero3 ), "Passed!" );
-});
-
-test( "expandByVector", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-
-	a.expandByVector( zero3 );
-	ok( a.getSize().equals( zero3 ), "Passed!" );
-
-	a.expandByVector( one3 );
-	ok( a.getSize().equals( one3.clone().multiplyScalar( 2 ) ), "Passed!" );
-	ok( a.getCenter().equals( zero3 ), "Passed!" );
-});
-
-test( "expandByScalar", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-
-	a.expandByScalar( 0 );
-	ok( a.getSize().equals( zero3 ), "Passed!" );
-
-	a.expandByScalar( 1 );
-	ok( a.getSize().equals( one3.clone().multiplyScalar( 2 ) ), "Passed!" );
-	ok( a.getCenter().equals( zero3 ), "Passed!" );
-});
-
-test( "containsPoint", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-
-	ok( a.containsPoint( zero3 ), "Passed!" );
-	ok( ! a.containsPoint( one3 ), "Passed!" );
-
-	a.expandByScalar( 1 );
-	ok( a.containsPoint( zero3 ), "Passed!" );
-	ok( a.containsPoint( one3 ), "Passed!" );
-	ok( a.containsPoint( one3.clone().negate() ), "Passed!" );
-});
-
-test( "containsBox", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.containsBox( a ), "Passed!" );
-	ok( ! a.containsBox( b ), "Passed!" );
-	ok( ! a.containsBox( c ), "Passed!" );
-
-	ok( b.containsBox( a ), "Passed!" );
-	ok( c.containsBox( a ), "Passed!" );
-	ok( ! b.containsBox( c ), "Passed!" );
-});
-
-test( "getParameter", function() {
-	var a = new THREE.Box3( zero3.clone(), one3.clone() );
-	var b = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.getParameter( new THREE.Vector3( 0, 0, 0 ) ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( a.getParameter( new THREE.Vector3( 1, 1, 1 ) ).equals( new THREE.Vector3( 1, 1, 1 ) ), "Passed!" );
-
-	ok( b.getParameter( new THREE.Vector3( -1, -1, -1 ) ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( b.getParameter( new THREE.Vector3( 0, 0, 0 ) ).equals( new THREE.Vector3( 0.5, 0.5, 0.5 ) ), "Passed!" );
-	ok( b.getParameter( new THREE.Vector3( 1, 1, 1 ) ).equals( new THREE.Vector3( 1, 1, 1 ) ), "Passed!" );
-});
-
-test( "clampPoint", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.clampPoint( new THREE.Vector3( 0, 0, 0 ) ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( a.clampPoint( new THREE.Vector3( 1, 1, 1 ) ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( a.clampPoint( new THREE.Vector3( -1, -1, -1 ) ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	ok( b.clampPoint( new THREE.Vector3( 2, 2, 2 ) ).equals( new THREE.Vector3( 1, 1, 1 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector3( 1, 1, 1 ) ).equals( new THREE.Vector3( 1, 1, 1 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector3( 0, 0, 0 ) ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector3( -1, -1, -1 ) ).equals( new THREE.Vector3( -1, -1, -1 ) ), "Passed!" );
-	ok( b.clampPoint( new THREE.Vector3( -2, -2, -2 ) ).equals( new THREE.Vector3( -1, -1, -1 ) ), "Passed!" );
-});
-
-test( "distanceToPoint", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.distanceToPoint( new THREE.Vector3( 0, 0, 0 ) ) == 0, "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( 1, 1, 1 ) ) == Math.sqrt( 3 ), "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( -1, -1, -1 ) ) == Math.sqrt( 3 ), "Passed!" );
-
-	ok( b.distanceToPoint( new THREE.Vector3( 2, 2, 2 ) ) == Math.sqrt( 3 ), "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( 1, 1, 1 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( 0, 0, 0 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( -1, -1, -1 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( -2, -2, -2 ) ) == Math.sqrt( 3 ), "Passed!" );
-});
-
-test( "distanceToPoint", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.distanceToPoint( new THREE.Vector3( 0, 0, 0 ) ) == 0, "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( 1, 1, 1 ) ) == Math.sqrt( 3 ), "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( -1, -1, -1 ) ) == Math.sqrt( 3 ), "Passed!" );
-
-	ok( b.distanceToPoint( new THREE.Vector3( 2, 2, 2 ) ) == Math.sqrt( 3 ), "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( 1, 1, 1 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( 0, 0, 0 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( -1, -1, -1 ) ) == 0, "Passed!" );
-	ok( b.distanceToPoint( new THREE.Vector3( -2, -2, -2 ) ) == Math.sqrt( 3 ), "Passed!" );
-});
-
-test( "intersectsBox", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.intersectsBox( a ), "Passed!" );
-	ok( a.intersectsBox( b ), "Passed!" );
-	ok( a.intersectsBox( c ), "Passed!" );
-
-	ok( b.intersectsBox( a ), "Passed!" );
-	ok( c.intersectsBox( a ), "Passed!" );
-	ok( b.intersectsBox( c ), "Passed!" );
-
-	b.translate( new THREE.Vector3( 2, 2, 2 ) );
-	ok( ! a.intersectsBox( b ), "Passed!" );
-	ok( ! b.intersectsBox( a ), "Passed!" );
-	ok( ! b.intersectsBox( c ), "Passed!" );
-});
-
-test( "intersectsSphere", function() {
-	var a = new THREE.Box3( zero3.clone(), one3.clone() );
-	var b = new THREE.Sphere( zero3.clone(), 1 );
-
-	ok( a.intersectsSphere( b ) , "Passed!" );
-
-	b.translate( new THREE.Vector3( 2, 2, 2 ) );
-	ok( ! a.intersectsSphere( b ) , "Passed!" );
-});
-
-test( "intersectsPlane", function() {
-	var a = new THREE.Box3( zero3.clone(), one3.clone() );
-	var b = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), 1 );
-	var c = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), 1.25 );
-	var d = new THREE.Plane( new THREE.Vector3( 0, -1, 0 ), 1.25 );
-
-	ok( a.intersectsPlane( b ) , "Passed!" );
-	ok( ! a.intersectsPlane( c ) , "Passed!" );
-	ok( ! a.intersectsPlane( d ) , "Passed!" );
-});
-
-test( "getBoundingSphere", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.getBoundingSphere().equals( new THREE.Sphere( zero3, 0 ) ), "Passed!" );
-	ok( b.getBoundingSphere().equals( new THREE.Sphere( one3.clone().multiplyScalar( 0.5 ), Math.sqrt( 3 ) * 0.5 ) ), "Passed!" );
-	ok( c.getBoundingSphere().equals( new THREE.Sphere( zero3, Math.sqrt( 12 ) * 0.5 ) ), "Passed!" );
-});
-
-test( "intersect", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.clone().intersect( a ).equals( a ), "Passed!" );
-	ok( a.clone().intersect( b ).equals( a ), "Passed!" );
-	ok( b.clone().intersect( b ).equals( b ), "Passed!" );
-	ok( a.clone().intersect( c ).equals( a ), "Passed!" );
-	ok( b.clone().intersect( c ).equals( b ), "Passed!" );
-	ok( c.clone().intersect( c ).equals( c ), "Passed!" );
-});
-
-test( "union", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-
-	ok( a.clone().union( a ).equals( a ), "Passed!" );
-	ok( a.clone().union( b ).equals( b ), "Passed!" );
-	ok( a.clone().union( c ).equals( c ), "Passed!" );
-	ok( b.clone().union( c ).equals( c ), "Passed!" );
-});
-
-var compareBox = function ( a, b, threshold ) {
-	threshold = threshold || 0.0001;
-	return ( a.min.distanceTo( b.min ) < threshold &&
-	a.max.distanceTo( b.max ) < threshold );
-};
-
-test( "applyMatrix4", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-	var d = new THREE.Box3( one3.clone().negate(), zero3.clone() );
-
-	var m = new THREE.Matrix4().makeTranslation( 1, -2, 1 );
-	var t1 = new THREE.Vector3( 1, -2, 1 );
-
-	ok( compareBox( a.clone().applyMatrix4( m ), a.clone().translate( t1 ) ), "Passed!" );
-	ok( compareBox( b.clone().applyMatrix4( m ), b.clone().translate( t1 ) ), "Passed!" );
-	ok( compareBox( c.clone().applyMatrix4( m ), c.clone().translate( t1 ) ), "Passed!" );
-	ok( compareBox( d.clone().applyMatrix4( m ), d.clone().translate( t1 ) ), "Passed!" );
-});
-
-test( "translate", function() {
-	var a = new THREE.Box3( zero3.clone(), zero3.clone() );
-	var b = new THREE.Box3( zero3.clone(), one3.clone() );
-	var c = new THREE.Box3( one3.clone().negate(), one3.clone() );
-	var d = new THREE.Box3( one3.clone().negate(), zero3.clone() );
-
-	ok( a.clone().translate( one3 ).equals( new THREE.Box3( one3, one3 ) ), "Passed!" );
-	ok( a.clone().translate( one3 ).translate( one3.clone().negate() ).equals( a ), "Passed!" );
-	ok( d.clone().translate( one3 ).equals( b ), "Passed!" );
-	ok( b.clone().translate( one3.clone().negate() ).equals( d ), "Passed!" );
-});

+ 0 - 280
test/unit/math/Color.js

@@ -1,280 +0,0 @@
-module( "Color" );
-
-test( "constructor", function(){
-    var c = new THREE.Color();
-    ok( c.r, "Red: " + c.r );
-    ok( c.g, "Green: " + c.g );
-    ok( c.b, "Blue: " + c.b );
-});
-
-test( "rgb constructor", function(){
-    var c = new THREE.Color( 1, 1, 1 );
-    ok( c.r == 1, "Passed" );
-    ok( c.g == 1, "Passed" );
-    ok( c.b == 1, "Passed" );
-});
-
-test( "copyHex", function(){
-    var c = new THREE.Color();
-    var c2 = new THREE.Color(0xF5FFFA);
-    c.copy(c2);
-    ok(c.getHex() == c2.getHex(), "Hex c: " + c.getHex() + " Hex c2: " + c2.getHex());
-});
-
-test( "copyColorString", function(){
-    var c = new THREE.Color();
-    var c2 = new THREE.Color('ivory');
-    c.copy(c2);
-    ok(c.getHex() == c2.getHex(), "Hex c: " + c.getHex() + " Hex c2: " + c2.getHex());
-});
-
-test( "setRGB", function(){
-    var c = new THREE.Color();
-    c.setRGB(1, 0.2, 0.1);
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g == 0.2, "Green: " + c.g );
-    ok( c.b == 0.1, "Blue: " + c.b );
-});
-
-test( "copyGammaToLinear", function(){
-    var c = new THREE.Color();
-    var c2 = new THREE.Color();
-    c2.setRGB(0.3, 0.5, 0.9);
-    c.copyGammaToLinear(c2);
-    ok( c.r == 0.09, "Red c: " + c.r + " Red c2: " + c2.r);
-    ok( c.g == 0.25, "Green c: " + c.g + " Green c2: " + c2.g);
-    ok( c.b == 0.81, "Blue c: " + c.b + " Blue c2: " + c2.b);
-});
-
-test( "copyLinearToGamma", function(){
-    var c = new THREE.Color();
-    var c2 = new THREE.Color();
-    c2.setRGB(0.09, 0.25, 0.81);
-    c.copyLinearToGamma(c2);
-    ok( c.r == 0.3, "Red c: " + c.r + " Red c2: " + c2.r);
-    ok( c.g == 0.5, "Green c: " + c.g + " Green c2: " + c2.g);
-    ok( c.b == 0.9, "Blue c: " + c.b + " Blue c2: " + c2.b);
-});
-
-
-test( "convertGammaToLinear", function(){
-    var c = new THREE.Color();
-    c.setRGB(0.3, 0.5, 0.9);
-    c.convertGammaToLinear();
-    ok( c.r == 0.09, "Red: " + c.r );
-    ok( c.g == 0.25, "Green: " + c.g );
-    ok( c.b == 0.81, "Blue: " + c.b );
-});
-
-
-test( "convertLinearToGamma", function(){
-    var c = new THREE.Color();
-    c.setRGB(4, 9, 16);
-    c.convertLinearToGamma();
-    ok( c.r == 2, "Red: " + c.r );
-    ok( c.g == 3, "Green: " + c.g );
-    ok( c.b == 4, "Blue: " + c.b );
-});
-
-test("setWithNum", function(){
-    var c = new THREE.Color();
-    c.set(0xFF0000);
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-
-test( "setWithString", function(){
-    var c = new THREE.Color();
-    c.set('silver');
-    ok(c.getHex() == 0xC0C0C0, "Hex c: " + c.getHex());
-});
-
-
-test( "clone", function(){
-    var c = new THREE.Color('teal');
-    var c2 = c.clone();
-    ok(c2.getHex() == 0x008080, "Hex c2: " + c2.getHex());
-});
-
-test( "lerp", function(){
-    var c = new THREE.Color();
-    var c2 = new THREE.Color();
-    c.setRGB(0, 0, 0);
-    c.lerp(c2, 0.2);
-    ok( c.r == 0.2, "Red: " + c.r );
-    ok( c.g == 0.2, "Green: " + c.g );
-    ok( c.b == 0.2, "Blue: " + c.b );
-    
-});
-
-
-test( "setStyleRGBRed", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgb(255,0,0)');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleRGBARed", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgba(255,0,0,0.5)');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleRGBRedWithSpaces", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgb( 255 , 0,   0 )');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleRGBARedWithSpaces", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgba( 255,  0,  0  , 1 )');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleRGBPercent", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgb(100%,50%,10%)');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g == 0.5, "Green: " + c.g );
-    ok( c.b == 0.1, "Blue: " + c.b );
-});
-
-test( "setStyleRGBAPercent", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgba(100%,50%,10%, 0.5)');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g == 0.5, "Green: " + c.g );
-    ok( c.b == 0.1, "Blue: " + c.b );
-});
-
-test( "setStyleRGBPercentWithSpaces", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgb( 100% ,50%  , 10% )');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g == 0.5, "Green: " + c.g );
-    ok( c.b == 0.1, "Blue: " + c.b );
-});
-
-test( "setStyleRGBAPercentWithSpaces", function(){
-    var c = new THREE.Color();
-    c.setStyle('rgba( 100% ,50%  ,  10%, 0.5 )');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g == 0.5, "Green: " + c.g );
-    ok( c.b == 0.1, "Blue: " + c.b );
-});
-
-test( "setStyleHSLRed", function(){
-    var c = new THREE.Color();
-    c.setStyle('hsl(360,100%,50%)');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleHSLARed", function(){
-    var c = new THREE.Color();
-    c.setStyle('hsla(360,100%,50%,0.5)');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleHSLRedWithSpaces", function(){
-    var c = new THREE.Color();
-    c.setStyle('hsl(360,  100% , 50% )');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleHSLARedWithSpaces", function(){
-    var c = new THREE.Color();
-    c.setStyle('hsla( 360,  100% , 50%,  0.5 )');
-    ok( c.r == 1, "Red: " + c.r );
-    ok( c.g === 0, "Green: " + c.g );
-    ok( c.b === 0, "Blue: " + c.b );
-});
-
-test( "setStyleHexSkyBlue", function(){
-    var c = new THREE.Color();
-    c.setStyle('#87CEEB');
-    ok(c.getHex() == 0x87CEEB, "Hex c: " + c.getHex());
-});
-
-test( "setStyleHexSkyBlueMixed", function(){
-    var c = new THREE.Color();
-    c.setStyle('#87cEeB');
-    ok(c.getHex() == 0x87CEEB, "Hex c: " + c.getHex());
-});
-
-test( "setStyleHex2Olive", function(){
-    var c = new THREE.Color();
-    c.setStyle('#F00');
-    ok(c.getHex() == 0xFF0000, "Hex c: " + c.getHex());
-});
-
-test( "setStyleHex2OliveMixed", function(){
-    var c = new THREE.Color();
-    c.setStyle('#f00');
-    ok(c.getHex() == 0xFF0000, "Hex c: " + c.getHex());
-});
-
-test( "setStyleColorName", function(){
-    var c = new THREE.Color();
-    c.setStyle('powderblue');
-    ok(c.getHex() == 0xB0E0E6, "Hex c: " + c.getHex());
-});
-
-test( "getHex", function(){
-    var c = new THREE.Color('red');
-    var res = c.getHex();
-    ok( res == 0xFF0000, "Hex: " + res );
-});
-
-test( "setHex", function(){
-    var c = new THREE.Color();
-    c.setHex(0xFA8072);
-    ok( c.getHex() == 0xFA8072, "Hex: " + c.getHex());
-});
-
-test( "getHexString", function(){
-    var c = new THREE.Color('tomato');
-    var res = c.getHexString();
-    ok( res == 'ff6347', "Hex: " + res );
-});
-
-test( "getStyle", function(){
-    var c = new THREE.Color('plum');
-    var res = c.getStyle();
-    ok( res == 'rgb(221,160,221)', "style: " + res );
-});
-
-test( "getHSL", function () {
-    var c = new THREE.Color( 0x80ffff );
-    var hsl = c.getHSL();
-
-    ok( hsl.h == 0.5, "hue: " + hsl.h );
-    ok( hsl.s == 1.0, "saturation: " + hsl.s );
-    ok( (Math.round(parseFloat(hsl.l)*100)/100) == 0.75, "lightness: " + hsl.l );
-});
-
-test( "setHSL", function () {
-    var c = new THREE.Color();
-    c.setHSL(0.75, 1.0, 0.25);
-    var hsl = c.getHSL();
-
-    ok( hsl.h == 0.75, "hue: " + hsl.h );
-    ok( hsl.s == 1.00, "saturation: " + hsl.s );
-    ok( hsl.l == 0.25, "lightness: " + hsl.l );
-});

+ 0 - 156
test/unit/math/Frustum.js

@@ -1,156 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Frustum" );
-
-var unit3 = new THREE.Vector3( 1, 0, 0 );
-
-var planeEquals = function ( a, b, tolerance ) {
-
-	tolerance = tolerance || 0.0001;
-
-	if ( a.normal.distanceTo( b.normal ) > tolerance ) return false;
-	if ( Math.abs( a.constant - b.constant ) > tolerance ) return false;
-
-	return true;
-
-};
-
-test( "constructor", function() {
-	var a = new THREE.Frustum();
-
-	ok( a.planes !== undefined, "Passed!" );
-	ok( a.planes.length === 6, "Passed!" );
-
-	var pDefault = new THREE.Plane();
-	for( var i = 0; i < 6; i ++ ) {
-		ok( a.planes[i].equals( pDefault ), "Passed!" );
-	}
-
-	var p0 = new THREE.Plane( unit3, -1 );
-	var p1 = new THREE.Plane( unit3, 1 );
-	var p2 = new THREE.Plane( unit3, 2 );
-	var p3 = new THREE.Plane( unit3, 3 );
-	var p4 = new THREE.Plane( unit3, 4 );
-	var p5 = new THREE.Plane( unit3, 5 );
-
-	a = new THREE.Frustum( p0, p1, p2, p3, p4, p5 );
-	ok( a.planes[0].equals( p0 ), "Passed!" );
-	ok( a.planes[1].equals( p1 ), "Passed!" );
-	ok( a.planes[2].equals( p2 ), "Passed!" );
-	ok( a.planes[3].equals( p3 ), "Passed!" );
-	ok( a.planes[4].equals( p4 ), "Passed!" );
-	ok( a.planes[5].equals( p5 ), "Passed!" );
-});
-
-test( "copy", function() {
-
-	var p0 = new THREE.Plane( unit3, -1 );
-	var p1 = new THREE.Plane( unit3, 1 );
-	var p2 = new THREE.Plane( unit3, 2 );
-	var p3 = new THREE.Plane( unit3, 3 );
-	var p4 = new THREE.Plane( unit3, 4 );
-	var p5 = new THREE.Plane( unit3, 5 );
-
-	var b = new THREE.Frustum( p0, p1, p2, p3, p4, p5 );
-	var a = new THREE.Frustum().copy( b );
-	ok( a.planes[0].equals( p0 ), "Passed!" );
-	ok( a.planes[1].equals( p1 ), "Passed!" );
-	ok( a.planes[2].equals( p2 ), "Passed!" );
-	ok( a.planes[3].equals( p3 ), "Passed!" );
-	ok( a.planes[4].equals( p4 ), "Passed!" );
-	ok( a.planes[5].equals( p5 ), "Passed!" );
-
-	// ensure it is a true copy by modifying source
-	b.planes[0] = p1;
-	ok( a.planes[0].equals( p0 ), "Passed!" );
-});
-
-test( "setFromMatrix/makeOrthographic/containsPoint", function() {
-	var m = new THREE.Matrix4().makeOrthographic( -1, 1, -1, 1, 1, 100 );
-	var a = new THREE.Frustum().setFromMatrix( m );
-
-	ok( ! a.containsPoint( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 0, 0, -50 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 0, 0, -1.001 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( -1, -1, -1.001 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( -1.1, -1.1, -1.001 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 1, 1, -1.001 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( 1.1, 1.1, -1.001 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 0, 0, -100 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( -1, -1, -100 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( -1.1, -1.1, -100.1 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 1, 1, -100 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( 1.1, 1.1, -100.1 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( 0, 0, -101 ) ), "Passed!" );
-
-});
-
-test( "setFromMatrix/makePerspective/containsPoint", function() {
-	var m = new THREE.Matrix4().makePerspective( -1, 1, 1, -1, 1, 100 );
-	var a = new THREE.Frustum().setFromMatrix( m );
-
-	ok( ! a.containsPoint( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 0, 0, -50 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 0, 0, -1.001 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( -1, -1, -1.001 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( -1.1, -1.1, -1.001 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 1, 1, -1.001 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( 1.1, 1.1, -1.001 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 0, 0, -99.999 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( -99.999, -99.999, -99.999 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( -100.1, -100.1, -100.1 ) ), "Passed!" );
-	ok( a.containsPoint( new THREE.Vector3( 99.999, 99.999, -99.999 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( 100.1, 100.1, -100.1 ) ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( 0, 0, -101 ) ), "Passed!" );
-});
-
-test( "setFromMatrix/makePerspective/intersectsSphere", function() {
-	var m = new THREE.Matrix4().makePerspective( -1, 1, 1, -1, 1, 100 );
-	var a = new THREE.Frustum().setFromMatrix( m );
-
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, 0 ), 0 ) ), "Passed!" );
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, 0 ), 0.9 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, 0 ), 1.1 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, -50 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, -1.001 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( -1, -1, -1.001 ), 0 ) ), "Passed!" );
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( -1.1, -1.1, -1.001 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( -1.1, -1.1, -1.001 ), 0.5 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 1, 1, -1.001 ), 0 ) ), "Passed!" );
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 1.1, 1.1, -1.001 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 1.1, 1.1, -1.001 ), 0.5 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, -99.999 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( -99.999, -99.999, -99.999 ), 0 ) ), "Passed!" );
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( -100.1, -100.1, -100.1 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( -100.1, -100.1, -100.1 ), 0.5 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 99.999, 99.999, -99.999 ), 0 ) ), "Passed!" );
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 100.1, 100.1, -100.1 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 100.1, 100.1, -100.1 ), 0.2 ) ), "Passed!" );
-	ok( ! a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, -101 ), 0 ) ), "Passed!" );
-	ok( a.intersectsSphere( new THREE.Sphere( new THREE.Vector3( 0, 0, -101 ), 1.1 ) ), "Passed!" );
-});
-
-test( "clone", function() {
-
-	var p0 = new THREE.Plane( unit3, -1 );
-	var p1 = new THREE.Plane( unit3, 1 );
-	var p2 = new THREE.Plane( unit3, 2 );
-	var p3 = new THREE.Plane( unit3, 3 );
-	var p4 = new THREE.Plane( unit3, 4 );
-	var p5 = new THREE.Plane( unit3, 5 );
-
-	var b = new THREE.Frustum( p0, p1, p2, p3, p4, p5 );
-	var a = b.clone();
-	ok( a.planes[0].equals( p0 ), "Passed!" );
-	ok( a.planes[1].equals( p1 ), "Passed!" );
-	ok( a.planes[2].equals( p2 ), "Passed!" );
-	ok( a.planes[3].equals( p3 ), "Passed!" );
-	ok( a.planes[4].equals( p4 ), "Passed!" );
-	ok( a.planes[5].equals( p5 ), "Passed!" );
-
-	// ensure it is a true copy by modifying source
-	a.planes[0].copy( p1 );
-	ok( b.planes[0].equals( p0 ), "Passed!" );
-});

+ 0 - 69
test/unit/math/Line3.js

@@ -1,69 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Line3" );
-
-test( "constructor/equals", function() {
-	var a = new THREE.Line3();
-	ok( a.start.equals( zero3 ), "Passed!" );
-	ok( a.end.equals( zero3 ), "Passed!" );
-
-	a = new THREE.Line3( two3.clone(), one3.clone() );
-	ok( a.start.equals( two3 ), "Passed!" );
-	ok( a.end.equals( one3 ), "Passed!" );
-});
-
-test( "copy/equals", function() {
-	var a = new THREE.Line3( zero3.clone(), one3.clone() );
-	var b = new THREE.Line3().copy( a );
-	ok( b.start.equals( zero3 ), "Passed!" );
-	ok( b.end.equals( one3 ), "Passed!" );
-
-	// ensure that it is a true copy
-	a.start = zero3;
-	a.end = one3;
-	ok( b.start.equals( zero3 ), "Passed!" );
-	ok( b.end.equals( one3 ), "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Line3();
-
-	a.set( one3, one3 );
-	ok( a.start.equals( one3 ), "Passed!" );
-	ok( a.end.equals( one3 ), "Passed!" );
-});
-
-test( "at", function() {
-	var a = new THREE.Line3( one3.clone(), new THREE.Vector3( 1, 1, 2 ) );
-
-	ok( a.at( -1 ).distanceTo( new THREE.Vector3( 1, 1, 0 ) ) < 0.0001, "Passed!" );
-	ok( a.at( 0 ).distanceTo( one3.clone() ) < 0.0001, "Passed!" );
-	ok( a.at( 1 ).distanceTo( new THREE.Vector3( 1, 1, 2 ) ) < 0.0001, "Passed!" );
-	ok( a.at( 2 ).distanceTo( new THREE.Vector3( 1, 1, 3 ) ) < 0.0001, "Passed!" );
-});
-
-test( "closestPointToPoint/closestPointToPointParameter", function() {
-	var a = new THREE.Line3( one3.clone(), new THREE.Vector3( 1, 1, 2 ) );
-
-	// nearby the ray
-	ok( a.closestPointToPointParameter( zero3.clone(), true ) == 0, "Passed!" );
-	var b1 = a.closestPointToPoint( zero3.clone(), true );
-	ok( b1.distanceTo( new THREE.Vector3( 1, 1, 1 ) ) < 0.0001, "Passed!" );
-
-	// nearby the ray
-	ok( a.closestPointToPointParameter( zero3.clone(), false ) == -1, "Passed!" );
-	var b2 = a.closestPointToPoint( zero3.clone(), false );
-	ok( b2.distanceTo( new THREE.Vector3( 1, 1, 0 ) ) < 0.0001, "Passed!" );
-
-	// nearby the ray
-	ok( a.closestPointToPointParameter( new THREE.Vector3( 1, 1, 5 ), true ) == 1, "Passed!" );
-	var b = a.closestPointToPoint( new THREE.Vector3( 1, 1, 5 ), true );
-	ok( b.distanceTo( new THREE.Vector3( 1, 1, 2 ) ) < 0.0001, "Passed!" );
-
-	// exactly on the ray
-	ok( a.closestPointToPointParameter( one3.clone(), true ) == 0, "Passed!" );
-	var c = a.closestPointToPoint( one3.clone(), true );
-	ok( c.distanceTo( one3.clone() ) < 0.0001, "Passed!" );
-});

+ 0 - 35
test/unit/math/Math.js

@@ -1,35 +0,0 @@
-/**
- * @author humbletim / https://github.com/humbletim
- */
-
-module( "Math" );
-
-//https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/sign
-//http://people.mozilla.org/~jorendorff/es6-draft.html#sec-math.sign
-/* 
-20.2.2.29 Math.sign(x)
-
-Returns the sign of the x, indicating whether x is positive, negative or zero.
-
-If x is NaN, the result is NaN.
-If x is -0, the result is -0.
-If x is +0, the result is +0.
-If x is negative and not -0, the result is -1.
-If x is positive and not +0, the result is +1.
-*/
-
-test( "Math.sign/polyfill", function() {
-
-	ok( isNaN( Math.sign(NaN) ) , "If x is NaN<NaN>, the result is NaN.");
-	ok( isNaN( Math.sign(new THREE.Vector3()) ) , "If x is NaN<object>, the result is NaN.");
-	ok( isNaN( Math.sign() ) , "If x is NaN<undefined>, the result is NaN.");
-	ok( isNaN( Math.sign('--3') ) , "If x is NaN<'--3'>, the result is NaN.");
-	ok( Math.sign(-0) === -0 , "If x is -0, the result is -0.");
-	ok( Math.sign(+0) === +0 , "If x is +0, the result is +0.");
-	ok( Math.sign(-Infinity) === -1 , "If x is negative<-Infinity> and not -0, the result is -1.");
-	ok( Math.sign('-3') === -1 , "If x is negative<'-3'> and not -0, the result is -1.");
-	ok( Math.sign('-1e-10') === -1 , "If x is negative<'-1e-10'> and not -0, the result is -1.");
-	ok( Math.sign(+Infinity) === +1 , "If x is positive<+Infinity> and not +0, the result is +1.");
-	ok( Math.sign('+3') === +1 , "If x is positive<'+3'> and not +0, the result is +1.");
-
-});

+ 0 - 212
test/unit/math/Matrix3.js

@@ -1,212 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Matrix3" );
-
-var matrixEquals3 = function( a, b, tolerance ) {
-	tolerance = tolerance || 0.0001;
-	if( a.elements.length != b.elements.length ) {
-		return false;
-	}
-	for( var i = 0, il = a.elements.length; i < il; i ++ ) {
-		var delta = a.elements[i] - b.elements[i];
-		if( delta > tolerance ) {
-			return false;
-		}
-	}
-	return true;
-};
-
-
-var toMatrix4 = function( m3 ) {
-	var result = new THREE.Matrix4();
-	var re = result.elements;
-	var me = m3.elements;
-	re[0] = me[0];
-	re[1] = me[1];
-	re[2] = me[2];
-	re[4] = me[3];
-	re[5] = me[4];
-	re[6] = me[5];
-	re[8] = me[6];
-	re[9] = me[7];
-	re[10] = me[8];
-
-	return result;
-};
-
-test( "constructor", function() {
-	var a = new THREE.Matrix3();
-	ok( a.determinant() == 1, "Passed!" );
-
-	var b = new THREE.Matrix3().set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	ok( b.elements[0] == 0 );
-	ok( b.elements[1] == 3 );
-	ok( b.elements[2] == 6 );
-	ok( b.elements[3] == 1 );
-	ok( b.elements[4] == 4 );
-	ok( b.elements[5] == 7 );
-	ok( b.elements[6] == 2 );
-	ok( b.elements[7] == 5 );
-	ok( b.elements[8] == 8 );
-
-	ok( ! matrixEquals3( a, b ), "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Matrix3().set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	var b = new THREE.Matrix3().copy( a );
-
-	ok( matrixEquals3( a, b ), "Passed!" );
-
-	// ensure that it is a true copy
-	a.elements[0] = 2;
-	ok( ! matrixEquals3( a, b ), "Passed!" );
-});
-
-test( "set", function() {
-	var b = new THREE.Matrix3();
-	ok( b.determinant() == 1, "Passed!" );
-
-	b.set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	ok( b.elements[0] == 0 );
-	ok( b.elements[1] == 3 );
-	ok( b.elements[2] == 6 );
-	ok( b.elements[3] == 1 );
-	ok( b.elements[4] == 4 );
-	ok( b.elements[5] == 7 );
-	ok( b.elements[6] == 2 );
-	ok( b.elements[7] == 5 );
-	ok( b.elements[8] == 8 );
-});
-
-test( "identity", function() {
-	var b = new THREE.Matrix3().set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	ok( b.elements[0] == 0 );
-	ok( b.elements[1] == 3 );
-	ok( b.elements[2] == 6 );
-	ok( b.elements[3] == 1 );
-	ok( b.elements[4] == 4 );
-	ok( b.elements[5] == 7 );
-	ok( b.elements[6] == 2 );
-	ok( b.elements[7] == 5 );
-	ok( b.elements[8] == 8 );
-
-	var a = new THREE.Matrix3();
-	ok( ! matrixEquals3( a, b ), "Passed!" );
-
-	b.identity();
-	ok( matrixEquals3( a, b ), "Passed!" );
-});
-
-test( "multiplyScalar", function() {
-	var b = new THREE.Matrix3().set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	ok( b.elements[0] == 0 );
-	ok( b.elements[1] == 3 );
-	ok( b.elements[2] == 6 );
-	ok( b.elements[3] == 1 );
-	ok( b.elements[4] == 4 );
-	ok( b.elements[5] == 7 );
-	ok( b.elements[6] == 2 );
-	ok( b.elements[7] == 5 );
-	ok( b.elements[8] == 8 );
-
-	b.multiplyScalar( 2 );
-	ok( b.elements[0] == 0*2 );
-	ok( b.elements[1] == 3*2 );
-	ok( b.elements[2] == 6*2 );
-	ok( b.elements[3] == 1*2 );
-	ok( b.elements[4] == 4*2 );
-	ok( b.elements[5] == 7*2 );
-	ok( b.elements[6] == 2*2 );
-	ok( b.elements[7] == 5*2 );
-	ok( b.elements[8] == 8*2 );
-});
-
-
-test( "determinant", function() {
-	var a = new THREE.Matrix3();
-	ok( a.determinant() == 1, "Passed!" );
-
-	a.elements[0] = 2;
-	ok( a.determinant() == 2, "Passed!" );
-
-	a.elements[0] = 0;
-	ok( a.determinant() == 0, "Passed!" );
-
-	// calculated via http://www.euclideanspace.com/maths/algebra/matrix/functions/determinant/threeD/index.htm
-	a.set( 2, 3, 4, 5, 13, 7, 8, 9, 11 );
-	ok( a.determinant() == -73, "Passed!" );
-});
-
-
-test( "getInverse", function() {
-	var identity = new THREE.Matrix3();
-	var identity4 = new THREE.Matrix4();
-	var a = new THREE.Matrix3();
-	var b = new THREE.Matrix3().set( 0, 0, 0, 0, 0, 0, 0, 0, 0 );
-	var c = new THREE.Matrix3().set( 0, 0, 0, 0, 0, 0, 0, 0, 0 );
-
-	b.getInverse( a, false );
-	ok( matrixEquals3( a, identity ), "Passed!" );
-
-	try { 
-		b.getInverse( c, true );
-		ok( false, "Passed!" ); // should never get here.
-	}
-	catch( err ) {
-		ok( true, "Passed!" );
-	}
-
-	var testMatrices = [
-		new THREE.Matrix4().makeRotationX( 0.3 ),
-		new THREE.Matrix4().makeRotationX( -0.3 ),
-		new THREE.Matrix4().makeRotationY( 0.3 ),
-		new THREE.Matrix4().makeRotationY( -0.3 ),
-		new THREE.Matrix4().makeRotationZ( 0.3 ),
-		new THREE.Matrix4().makeRotationZ( -0.3 ),
-		new THREE.Matrix4().makeScale( 1, 2, 3 ),
-		new THREE.Matrix4().makeScale( 1/8, 1/2, 1/3 )
-		];
-
-	for( var i = 0, il = testMatrices.length; i < il; i ++ ) {
-		var m = testMatrices[i];
-
-		a.setFromMatrix4( m );
-		var mInverse3 = b.getInverse( a );
-
-		var mInverse = toMatrix4( mInverse3 );
-
-		// the determinant of the inverse should be the reciprocal
-		ok( Math.abs( a.determinant() * mInverse3.determinant() - 1 ) < 0.0001, "Passed!" );
-		ok( Math.abs( m.determinant() * mInverse.determinant() - 1 ) < 0.0001, "Passed!" );
-
-		var mProduct = new THREE.Matrix4().multiplyMatrices( m, mInverse );
-		ok( Math.abs( mProduct.determinant() - 1 ) < 0.0001, "Passed!" );
-		ok( matrixEquals3( mProduct, identity4 ), "Passed!" );
-	}
-});
-
-test( "transpose", function() {
-	var a = new THREE.Matrix3();
-	var b = a.clone().transpose();
-	ok( matrixEquals3( a, b ), "Passed!" );
-
-	b = new THREE.Matrix3().set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	var c = b.clone().transpose();
-	ok( ! matrixEquals3( b, c ), "Passed!" ); 
-	c.transpose();
-	ok( matrixEquals3( b, c ), "Passed!" ); 
-});
-
-test( "clone", function() {
-	var a = new THREE.Matrix3().set( 0, 1, 2, 3, 4, 5, 6, 7, 8 );
-	var b = a.clone();
-
-	ok( matrixEquals3( a, b ), "Passed!" );
-
-	// ensure that it is a true copy
-	a.elements[0] = 2;
-	ok( ! matrixEquals3( a, b ), "Passed!" );
-});

+ 0 - 197
test/unit/math/Plane.js

@@ -1,197 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Plane" );
-
-var comparePlane = function ( a, b, threshold ) {
-	threshold = threshold || 0.0001;
-	return ( a.normal.distanceTo( b.normal ) < threshold &&
-	Math.abs( a.constant - b.constant ) < threshold );
-};
-
-
-test( "constructor", function() {
-	var a = new THREE.Plane();
-	ok( a.normal.x == 1, "Passed!" );
-	ok( a.normal.y == 0, "Passed!" );
-	ok( a.normal.z == 0, "Passed!" );
-	ok( a.constant == 0, "Passed!" );
-
-	a = new THREE.Plane( one3.clone(), 0 );
-	ok( a.normal.x == 1, "Passed!" );
-	ok( a.normal.y == 1, "Passed!" );
-	ok( a.normal.z == 1, "Passed!" );
-	ok( a.constant == 0, "Passed!" );
-
-	a = new THREE.Plane( one3.clone(), 1 );
-	ok( a.normal.x == 1, "Passed!" );
-	ok( a.normal.y == 1, "Passed!" );
-	ok( a.normal.z == 1, "Passed!" );
-	ok( a.constant == 1, "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Plane( new THREE.Vector3( x, y, z ), w );
-	var b = new THREE.Plane().copy( a );
-	ok( b.normal.x == x, "Passed!" );
-	ok( b.normal.y == y, "Passed!" );
-	ok( b.normal.z == z, "Passed!" );
-	ok( b.constant == w, "Passed!" );
-
-	// ensure that it is a true copy
-	a.normal.x = 0;
-	a.normal.y = -1;
-	a.normal.z = -2;
-	a.constant = -3;
-	ok( b.normal.x == x, "Passed!" );
-	ok( b.normal.y == y, "Passed!" );
-	ok( b.normal.z == z, "Passed!" );
-	ok( b.constant == w, "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Plane();
-	ok( a.normal.x == 1, "Passed!" );
-	ok( a.normal.y == 0, "Passed!" );
-	ok( a.normal.z == 0, "Passed!" );
-	ok( a.constant == 0, "Passed!" );
-
-	var b = a.clone().set( new THREE.Vector3( x, y, z ), w );
-	ok( b.normal.x == x, "Passed!" );
-	ok( b.normal.y == y, "Passed!" );
-	ok( b.normal.z == z, "Passed!" );
-	ok( b.constant == w, "Passed!" );
-});
-
-test( "setComponents", function() {
-	var a = new THREE.Plane();
-	ok( a.normal.x == 1, "Passed!" );
-	ok( a.normal.y == 0, "Passed!" );
-	ok( a.normal.z == 0, "Passed!" );
-	ok( a.constant == 0, "Passed!" );
-
-	var b = a.clone().setComponents( x, y, z , w );
-	ok( b.normal.x == x, "Passed!" );
-	ok( b.normal.y == y, "Passed!" );
-	ok( b.normal.z == z, "Passed!" );
-	ok( b.constant == w, "Passed!" );
-});
-
-test( "setFromNormalAndCoplanarPoint", function() {
-	var normal = one3.clone().normalize();
-	var a = new THREE.Plane().setFromNormalAndCoplanarPoint( normal, zero3 );
-
-	ok( a.normal.equals( normal ), "Passed!" );
-	ok( a.constant == 0, "Passed!" );
-});
-
-test( "normalize", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 2, 0, 0 ), 2 );
-
-	a.normalize();
-	ok( a.normal.length() == 1, "Passed!" );
-	ok( a.normal.equals( new THREE.Vector3( 1, 0, 0 ) ), "Passed!" );
-	ok( a.constant == 1, "Passed!" );
-});
-
-test( "negate/distanceToPoint", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 2, 0, 0 ), -2 );
-
-	a.normalize();
-	ok( a.distanceToPoint( new THREE.Vector3( 4, 0, 0 ) ) === 3, "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( 1, 0, 0 ) ) === 0, "Passed!" );
-
-	a.negate();
-	ok( a.distanceToPoint( new THREE.Vector3( 4, 0, 0 ) ) === -3, "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( 1, 0, 0 ) ) === 0, "Passed!" );
-});
-
-test( "distanceToPoint", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 2, 0, 0 ), -2 );
-
-	a.normalize();
-	ok( a.distanceToPoint( a.projectPoint( zero3.clone() ) ) === 0, "Passed!" );
-	ok( a.distanceToPoint( new THREE.Vector3( 4, 0, 0 ) ) === 3, "Passed!" );
-});
-
-test( "distanceToSphere", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 0 );
-
-	var b = new THREE.Sphere( new THREE.Vector3( 2, 0, 0 ), 1 );
-
-	ok( a.distanceToSphere( b ) === 1, "Passed!" );
-
-	a.set( new THREE.Vector3( 1, 0, 0 ), 2 );
-	ok( a.distanceToSphere( b ) === 3, "Passed!" );
-	a.set( new THREE.Vector3( 1, 0, 0 ), -2 );
-	ok( a.distanceToSphere( b ) === -1, "Passed!" );
-});
-
-test( "isInterestionLine/intersectLine", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 0 );
-
-	var l1 = new THREE.Line3( new THREE.Vector3( -10, 0, 0 ), new THREE.Vector3( 10, 0, 0 ) );
-	ok( a.intersectsLine( l1 ), "Passed!" );
-	ok( a.intersectLine( l1 ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), -3 );
-
-	ok( a.intersectsLine( l1 ), "Passed!" );
-	ok( a.intersectLine( l1 ).equals( new THREE.Vector3( 3, 0, 0 ) ), "Passed!" );
-
-
-	a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), -11 );
-
-	ok( ! a.intersectsLine( l1 ), "Passed!" );
-	ok( a.intersectLine( l1 ) === undefined, "Passed!" );
-
-	a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 11 );
-
-	ok( ! a.intersectsLine( l1 ), "Passed!" );
-	ok( a.intersectLine( l1 ) === undefined, "Passed!" );
-
-});
-
-test( "projectPoint", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 0 );
-
-	ok( a.projectPoint( new THREE.Vector3( 10, 0, 0 ) ).equals( zero3 ), "Passed!" );
-	ok( a.projectPoint( new THREE.Vector3( -10, 0, 0 ) ).equals( zero3 ), "Passed!" );
-
-	a = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), -1 );
-	ok( a.projectPoint( new THREE.Vector3( 0, 0, 0 ) ).equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-	ok( a.projectPoint( new THREE.Vector3( 0, 1, 0 ) ).equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-
-});
-
-test( "orthoPoint", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 0 );
-
-	ok( a.orthoPoint( new THREE.Vector3( 10, 0, 0 ) ).equals( new THREE.Vector3( 10, 0, 0 ) ), "Passed!" );
-	ok( a.orthoPoint( new THREE.Vector3( -10, 0, 0 ) ).equals( new THREE.Vector3( -10, 0, 0 ) ), "Passed!" );
-});
-
-test( "coplanarPoint", function() {
-	var a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 0 );
-	ok( a.distanceToPoint( a.coplanarPoint() ) === 0, "Passed!" );
-
-	a = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), -1 );
-	ok( a.distanceToPoint( a.coplanarPoint() ) === 0, "Passed!" );
-});
-
-test( "applyMatrix4/translate", function() {
-
-	var a = new THREE.Plane( new THREE.Vector3( 1, 0, 0 ), 0 );
-
-	var m = new THREE.Matrix4();
-	m.makeRotationZ( Math.PI * 0.5 );
-
-	ok( comparePlane( a.clone().applyMatrix4( m ), new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), 0 ) ), "Passed!" );
-
-	a = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), -1 );
-	ok( comparePlane( a.clone().applyMatrix4( m ), new THREE.Plane( new THREE.Vector3( -1, 0, 0 ), -1 ) ), "Passed!" );
-
-	m.makeTranslation( 1, 1, 1 );
-	ok( comparePlane( a.clone().applyMatrix4( m ), a.clone().translate( new THREE.Vector3( 1, 1, 1 ) ) ), "Passed!" );
-});

+ 0 - 112
test/unit/math/Sphere.js

@@ -1,112 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Sphere" );
-
-test( "constructor", function() {
-	var a = new THREE.Sphere();
-	ok( a.center.equals( zero3 ), "Passed!" );
-	ok( a.radius == 0, "Passed!" );
-
-	a = new THREE.Sphere( one3.clone(), 1 );
-	ok( a.center.equals( one3 ), "Passed!" );
-	ok( a.radius == 1, "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-	var b = new THREE.Sphere().copy( a );
-
-	ok( b.center.equals( one3 ), "Passed!" );
-	ok( b.radius == 1, "Passed!" );
-
-	// ensure that it is a true copy
-	a.center = zero3;
-	a.radius = 0;
-	ok( b.center.equals( one3 ), "Passed!" );
-	ok( b.radius == 1, "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Sphere();
-	ok( a.center.equals( zero3 ), "Passed!" );
-	ok( a.radius == 0, "Passed!" );
-
-	a.set( one3, 1 );
-	ok( a.center.equals( one3 ), "Passed!" );
-	ok( a.radius == 1, "Passed!" );
-});
-
-test( "empty", function() {
-	var a = new THREE.Sphere();
-	ok( a.empty(), "Passed!" );
-
-	a.set( one3, 1 );
-	ok( ! a.empty(), "Passed!" );
-});
-
-test( "containsPoint", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-
-	ok( ! a.containsPoint( zero3 ), "Passed!" );
-	ok( a.containsPoint( one3 ), "Passed!" );
-});
-
-test( "distanceToPoint", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-
-	ok( ( a.distanceToPoint( zero3 ) - 0.7320 ) < 0.001, "Passed!" );
-	ok( a.distanceToPoint( one3 ) === -1, "Passed!" );
-});
-
-test( "intersectsSphere", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-	var b = new THREE.Sphere( zero3.clone(), 1 );
-	var c = new THREE.Sphere( zero3.clone(), 0.25 );
-
-	ok( a.intersectsSphere( b ) , "Passed!" );
-	ok( ! a.intersectsSphere( c ) , "Passed!" );
-});
-
-test( "intersectsPlane", function() {
-	var a = new THREE.Sphere( zero3.clone(), 1 );
-	var b = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), 1 );
-	var c = new THREE.Plane( new THREE.Vector3( 0, 1, 0 ), 1.25 );
-	var d = new THREE.Plane( new THREE.Vector3( 0, -1, 0 ), 1.25 );
-
-	ok( a.intersectsPlane( b ) , "Passed!" );
-	ok( ! a.intersectsPlane( c ) , "Passed!" );
-	ok( ! a.intersectsPlane( d ) , "Passed!" );
-});
-
-test( "clampPoint", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-
-	ok( a.clampPoint( new THREE.Vector3( 1, 1, 3 ) ).equals( new THREE.Vector3( 1, 1, 2 ) ), "Passed!" );
-	ok( a.clampPoint( new THREE.Vector3( 1, 1, -3 ) ).equals( new THREE.Vector3( 1, 1, 0 ) ), "Passed!" );
-});
-
-test( "getBoundingBox", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-
-	ok( a.getBoundingBox().equals( new THREE.Box3( zero3, two3 ) ), "Passed!" );
-
-	a.set( zero3, 0 );
-	ok( a.getBoundingBox().equals( new THREE.Box3( zero3, zero3 ) ), "Passed!" );
-});
-
-test( "applyMatrix4", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-
-	var m = new THREE.Matrix4().makeTranslation( 1, -2, 1 );
-
-	ok( a.clone().applyMatrix4( m ).getBoundingBox().equals( a.getBoundingBox().applyMatrix4( m ) ), "Passed!" );
-});
-
-test( "translate", function() {
-	var a = new THREE.Sphere( one3.clone(), 1 );
-
-	a.translate( one3.clone().negate() );
-	ok( a.center.equals( zero3 ), "Passed!" );
-});

+ 0 - 191
test/unit/math/Triangle.js

@@ -1,191 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Triangle" );
-
-test( "constructor", function() {
-	var a = new THREE.Triangle();
-	ok( a.a.equals( zero3 ), "Passed!" );
-	ok( a.b.equals( zero3 ), "Passed!" );
-	ok( a.c.equals( zero3 ), "Passed!" );
-
-	a = new THREE.Triangle( one3.clone().negate(), one3.clone(), two3.clone() );
-	ok( a.a.equals( one3.clone().negate() ), "Passed!" );
-	ok( a.b.equals( one3 ), "Passed!" );
-	ok( a.c.equals( two3 ), "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Triangle( one3.clone().negate(), one3.clone(), two3.clone() );
-	var b = new THREE.Triangle().copy( a );
-	ok( b.a.equals( one3.clone().negate() ), "Passed!" );
-	ok( b.b.equals( one3 ), "Passed!" );
-	ok( b.c.equals( two3 ), "Passed!" );
-
-	// ensure that it is a true copy
-	a.a = one3;
-	a.b = zero3;
-	a.c = zero3;
-	ok( b.a.equals( one3.clone().negate() ), "Passed!" );
-	ok( b.b.equals( one3 ), "Passed!" );
-	ok( b.c.equals( two3 ), "Passed!" );
-});
-
-test( "setFromPointsAndIndices", function() {
-	var a = new THREE.Triangle();
-
-	var points = [ one3, one3.clone().negate(), two3 ];
-	a.setFromPointsAndIndices( points, 1, 0, 2 );
-	ok( a.a.equals( one3.clone().negate() ), "Passed!" );
-	ok( a.b.equals( one3 ), "Passed!" );
-	ok( a.c.equals( two3 ), "Passed!" );
-
-});
-
-test( "set", function() {
-	var a = new THREE.Triangle();
-
-	a.set( one3.clone().negate(), one3, two3 );
-	ok( a.a.equals( one3.clone().negate() ), "Passed!" );
-	ok( a.b.equals( one3 ), "Passed!" );
-	ok( a.c.equals( two3 ), "Passed!" );
-
-});
-
-test( "area", function() {
-	var a = new THREE.Triangle();
-
-	ok( a.area() == 0, "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-	ok( a.area() == 0.5, "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 0, 0, 2 ) );
-	ok( a.area() == 2, "Passed!" );
-
-	// colinear triangle.
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 3, 0, 0 ) );
-	ok( a.area() == 0, "Passed!" );
-});
-
-test( "midpoint", function() {
-	var a = new THREE.Triangle();
-
-	ok( a.midpoint().equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-	ok( a.midpoint().equals( new THREE.Vector3( 1/3, 1/3, 0 ) ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 0, 0, 2 ) );
-	ok( a.midpoint().equals( new THREE.Vector3( 2/3, 0, 2/3 ) ), "Passed!" );
-});
-
-test( "normal", function() {
-	var a = new THREE.Triangle();
-
-	ok( a.normal().equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-	ok( a.normal().equals( new THREE.Vector3( 0, 0, 1 ) ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 0, 0, 2 ) );
-	ok( a.normal().equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-});
-
-test( "plane", function() {
-	var a = new THREE.Triangle();
-
-	// artificial normal is created in this case.
-	ok( a.plane().distanceToPoint( a.a ) == 0, "Passed!" );
-	ok( a.plane().distanceToPoint( a.b ) == 0, "Passed!" );
-	ok( a.plane().distanceToPoint( a.c ) == 0, "Passed!" );
-	ok( a.plane().normal.equals( a.normal() ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-	ok( a.plane().distanceToPoint( a.a ) == 0, "Passed!" );
-	ok( a.plane().distanceToPoint( a.b ) == 0, "Passed!" );
-	ok( a.plane().distanceToPoint( a.c ) == 0, "Passed!" );
-	ok( a.plane().normal.equals( a.normal() ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 0, 0, 2 ) );
-	ok( a.plane().distanceToPoint( a.a ) == 0, "Passed!" );
-	ok( a.plane().distanceToPoint( a.b ) == 0, "Passed!" );
-	ok( a.plane().distanceToPoint( a.c ) == 0, "Passed!" );
-	ok( a.plane().normal.clone().normalize().equals( a.normal() ), "Passed!" );
-});
-
-test( "barycoordFromPoint", function() {
-	var a = new THREE.Triangle();
-
-	var bad = new THREE.Vector3( -2, -1, -1 );
-
-	ok( a.barycoordFromPoint( a.a ).equals( bad ), "Passed!" );
-	ok( a.barycoordFromPoint( a.b ).equals( bad ), "Passed!" );
-	ok( a.barycoordFromPoint( a.c ).equals( bad ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-	ok( a.barycoordFromPoint( a.a ).equals( new THREE.Vector3( 1, 0, 0 ) ), "Passed!" );
-	ok( a.barycoordFromPoint( a.b ).equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-	ok( a.barycoordFromPoint( a.c ).equals( new THREE.Vector3( 0, 0, 1 ) ), "Passed!" );
-	ok( a.barycoordFromPoint( a.midpoint() ).distanceTo( new THREE.Vector3( 1/3, 1/3, 1/3 ) ) < 0.0001, "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 0, 0, 2 ) );
-	ok( a.barycoordFromPoint( a.a ).equals( new THREE.Vector3( 1, 0, 0 ) ), "Passed!" );
-	ok( a.barycoordFromPoint( a.b ).equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-	ok( a.barycoordFromPoint( a.c ).equals( new THREE.Vector3( 0, 0, 1 ) ), "Passed!" );
-	ok( a.barycoordFromPoint( a.midpoint() ).distanceTo( new THREE.Vector3( 1/3, 1/3, 1/3 ) ) < 0.0001, "Passed!" );
-});
-
-test( "containsPoint", function() {
-	var a = new THREE.Triangle();
-
-	ok( ! a.containsPoint( a.a ), "Passed!" );
-	ok( ! a.containsPoint( a.b ), "Passed!" );
-	ok( ! a.containsPoint( a.c ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-	ok( a.containsPoint( a.a ), "Passed!" );
-	ok( a.containsPoint( a.b ), "Passed!" );
-	ok( a.containsPoint( a.c ), "Passed!" );
-	ok( a.containsPoint( a.midpoint() ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( -1, -1, -1 ) ), "Passed!" );
-
-	a = new THREE.Triangle( new THREE.Vector3( 2, 0, 0 ), new THREE.Vector3( 0, 0, 0 ), new THREE.Vector3( 0, 0, 2 ) );
-	ok( a.containsPoint( a.a ), "Passed!" );
-	ok( a.containsPoint( a.b ), "Passed!" );
-	ok( a.containsPoint( a.c ), "Passed!" );
-	ok( a.containsPoint( a.midpoint() ), "Passed!" );
-	ok( ! a.containsPoint( new THREE.Vector3( -1, -1, -1 ) ), "Passed!" );
-});
-
-test( "closestPointToPoint", function() {
-
-	var a = new THREE.Triangle( new THREE.Vector3( -1, 0, 0 ), new THREE.Vector3( 1, 0, 0 ), new THREE.Vector3( 0, 1, 0 ) );
-
-	// point lies inside the triangle
-	var b0 = a.closestPointToPoint( new THREE.Vector3( 0, 0.5, 0 ) );
-	ok( b0.equals( new THREE.Vector3( 0, 0.5, 0 ) ), "Passed!" );
-
-	// point lies on a vertex
-	b0 = a.closestPointToPoint( a.a );
-	ok( b0.equals( a.a ), "Passed!" );
-	b0 = a.closestPointToPoint( a.b );
-	ok( b0.equals( a.b ), "Passed!" );
-	b0 = a.closestPointToPoint( a.c );
-	ok( b0.equals( a.c ), "Passed!" );
-
-	// point lies on an edge
-	b0 = a.closestPointToPoint( zero3.clone() );
-	ok( b0.equals( zero3.clone() ), "Passed!" );
-
-	// point lies outside the triangle
-	b0 = a.closestPointToPoint( new THREE.Vector3( -2, 0, 0 ) );
-	ok( b0.equals( new THREE.Vector3( -1, 0, 0 ) ), "Passed!" );
-	b0 = a.closestPointToPoint( new THREE.Vector3( 2, 0, 0 ) );
-	ok( b0.equals( new THREE.Vector3( 1, 0, 0 ) ), "Passed!" );
-	b0 = a.closestPointToPoint( new THREE.Vector3( 0, 2, 0 ) );
-	ok( b0.equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-	b0 = a.closestPointToPoint( new THREE.Vector3( 0, -2, 0 ) );
-	ok( b0.equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-});

+ 0 - 262
test/unit/math/Vector2.js

@@ -1,262 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Vector2" );
-
-test( "constructor", function() {
-	var a = new THREE.Vector2();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-
-	a = new THREE.Vector2( x, y );
-	ok( a.x === x, "Passed!" );
-	ok( a.y === y, "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Vector2( x, y );
-	var b = new THREE.Vector2().copy( a );
-	ok( b.x == x, "Passed!" );
-	ok( b.y == y, "Passed!" );
-
-	// ensure that it is a true copy
-	a.x = 0;
-	a.y = -1;
-	ok( b.x == x, "Passed!" );
-	ok( b.y == y, "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Vector2();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-
-	a.set( x, y );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-});
-
-test( "setX,setY", function() {
-	var a = new THREE.Vector2();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-
-	a.setX( x );
-	a.setY( y );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-});
-
-test( "setComponent,getComponent", function() {
-	var a = new THREE.Vector2();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-
-	a.setComponent( 0, 1 );
-	a.setComponent( 1, 2 );
-	ok( a.getComponent( 0 ) == 1, "Passed!" );
-	ok( a.getComponent( 1 ) == 2, "Passed!" );
-});
-
-test( "add", function() {
-	var a = new THREE.Vector2( x, y );
-	var b = new THREE.Vector2( -x, -y );
-
-	a.add( b );
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-
-	var c = new THREE.Vector2().addVectors( b, b );
-	ok( c.x == -2*x, "Passed!" );
-	ok( c.y == -2*y, "Passed!" );
-});
-
-test( "sub", function() {
-	var a = new THREE.Vector2( x, y );
-	var b = new THREE.Vector2( -x, -y );
-
-	a.sub( b );
-	ok( a.x == 2*x, "Passed!" );
-	ok( a.y == 2*y, "Passed!" );
-
-	var c = new THREE.Vector2().subVectors( a, a );
-	ok( c.x == 0, "Passed!" );
-	ok( c.y == 0, "Passed!" );
-});
-
-test( "multiply/divide", function() {
-	var a = new THREE.Vector2( x, y );
-	var b = new THREE.Vector2( -x, -y );
-
-	a.multiplyScalar( -2 );
-	ok( a.x == x*-2, "Passed!" );
-	ok( a.y == y*-2, "Passed!" );
-
-	b.multiplyScalar( -2 );
-	ok( b.x == 2*x, "Passed!" );
-	ok( b.y == 2*y, "Passed!" );
-
-	a.divideScalar( -2 );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-
-	b.divideScalar( -2 );
-	ok( b.x == -x, "Passed!" );
-	ok( b.y == -y, "Passed!" );
-});
-
-
-test( "min/max/clamp", function() {
-	var a = new THREE.Vector2( x, y );
-	var b = new THREE.Vector2( -x, -y );
-	var c = new THREE.Vector2();
-
-	c.copy( a ).min( b );
-	ok( c.x == -x, "Passed!" );
-	ok( c.y == -y, "Passed!" );
-
-	c.copy( a ).max( b );
-	ok( c.x == x, "Passed!" );
-	ok( c.y == y, "Passed!" );
-
-	c.set( -2*x, 2*y );
-	c.clamp( b, a );
-	ok( c.x == -x, "Passed!" );
-	ok( c.y == y, "Passed!" );
-
-	c.set(-2*x, 2*x);
-	c.clampScalar( -x, x );
-	equal( c.x, -x, "scalar clamp x" );
-	equal( c.y,  x, "scalar clamp y" );
-});
-
-test( "rounding", function() {
-	deepEqual( new THREE.Vector2( -0.1, 0.1 ).floor(), new THREE.Vector2( -1, 0 ), "floor .1" );
-	deepEqual( new THREE.Vector2( -0.5, 0.5 ).floor(), new THREE.Vector2( -1, 0 ), "floor .5" );
-	deepEqual( new THREE.Vector2( -0.9, 0.9 ).floor(), new THREE.Vector2( -1, 0 ), "floor .9" );
-
-	deepEqual( new THREE.Vector2( -0.1, 0.1 ).ceil(), new THREE.Vector2( 0, 1 ), "ceil .1" );
-	deepEqual( new THREE.Vector2( -0.5, 0.5 ).ceil(), new THREE.Vector2( 0, 1 ), "ceil .5" );
-	deepEqual( new THREE.Vector2( -0.9, 0.9 ).ceil(), new THREE.Vector2( 0, 1 ), "ceil .9" );
-
-	deepEqual( new THREE.Vector2( -0.1, 0.1 ).round(), new THREE.Vector2( 0, 0 ), "round .1" );
-	deepEqual( new THREE.Vector2( -0.5, 0.5 ).round(), new THREE.Vector2( 0, 1 ), "round .5" );
-	deepEqual( new THREE.Vector2( -0.9, 0.9 ).round(), new THREE.Vector2( -1, 1 ), "round .9" );
-
-	deepEqual( new THREE.Vector2( -0.1, 0.1 ).roundToZero(), new THREE.Vector2( 0, 0 ), "roundToZero .1" );
-	deepEqual( new THREE.Vector2( -0.5, 0.5 ).roundToZero(), new THREE.Vector2( 0, 0 ), "roundToZero .5" );
-	deepEqual( new THREE.Vector2( -0.9, 0.9 ).roundToZero(), new THREE.Vector2( 0, 0 ), "roundToZero .9" );
-	deepEqual( new THREE.Vector2( -1.1, 1.1 ).roundToZero(), new THREE.Vector2( -1, 1 ), "roundToZero 1.1" );
-	deepEqual( new THREE.Vector2( -1.5, 1.5 ).roundToZero(), new THREE.Vector2( -1, 1 ), "roundToZero 1.5" );
-	deepEqual( new THREE.Vector2( -1.9, 1.9 ).roundToZero(), new THREE.Vector2( -1, 1 ), "roundToZero 1.9" );
-});
-
-test( "negate", function() {
-	var a = new THREE.Vector2( x, y );
-
-	a.negate();
-	ok( a.x == -x, "Passed!" );
-	ok( a.y == -y, "Passed!" );
-});
-
-test( "dot", function() {
-	var a = new THREE.Vector2( x, y );
-	var b = new THREE.Vector2( -x, -y );
-	var c = new THREE.Vector2();
-
-	var result = a.dot( b );
-	ok( result == (-x*x-y*y), "Passed!" );
-
-	result = a.dot( c );
-	ok( result == 0, "Passed!" );
-});
-
-test( "length/lengthSq", function() {
-	var a = new THREE.Vector2( x, 0 );
-	var b = new THREE.Vector2( 0, -y );
-	var c = new THREE.Vector2();
-
-	ok( a.length() == x, "Passed!" );
-	ok( a.lengthSq() == x*x, "Passed!" );
-	ok( b.length() == y, "Passed!" );
-	ok( b.lengthSq() == y*y, "Passed!" );
-	ok( c.length() == 0, "Passed!" );
-	ok( c.lengthSq() == 0, "Passed!" );
-
-	a.set( x, y );
-	ok( a.length() == Math.sqrt( x*x + y*y ), "Passed!" );
-	ok( a.lengthSq() == ( x*x + y*y ), "Passed!" );
-});
-
-test( "normalize", function() {
-	var a = new THREE.Vector2( x, 0 );
-	var b = new THREE.Vector2( 0, -y );
-	var c = new THREE.Vector2();
-
-	a.normalize();
-	ok( a.length() == 1, "Passed!" );
-	ok( a.x == 1, "Passed!" );
-
-	b.normalize();
-	ok( b.length() == 1, "Passed!" );
-	ok( b.y == -1, "Passed!" );
-});
-
-test( "distanceTo/distanceToSquared", function() {
-	var a = new THREE.Vector2( x, 0 );
-	var b = new THREE.Vector2( 0, -y );
-	var c = new THREE.Vector2();
-
-	ok( a.distanceTo( c ) == x, "Passed!" );
-	ok( a.distanceToSquared( c ) == x*x, "Passed!" );
-
-	ok( b.distanceTo( c ) == y, "Passed!" );
-	ok( b.distanceToSquared( c ) == y*y, "Passed!" );
-});
-
-test( "setLength", function() {
-	var a = new THREE.Vector2( x, 0 );
-
-	ok( a.length() == x, "Passed!" );
-	a.setLength( y );
-	ok( a.length() == y, "Passed!" );
-
-	a = new THREE.Vector2( 0, 0 );
-	ok( a.length() == 0, "Passed!" );
-	a.setLength( y );
-	ok( a.length() == 0, "Passed!" );
-});
-
-test( "lerp/clone", function() {
-	var a = new THREE.Vector2( x, 0 );
-	var b = new THREE.Vector2( 0, -y );
-
-	ok( a.lerp( a, 0 ).equals( a.lerp( a, 0.5 ) ), "Passed!" );
-	ok( a.lerp( a, 0 ).equals( a.lerp( a, 1 ) ), "Passed!" );
-
-	ok( a.clone().lerp( b, 0 ).equals( a ), "Passed!" );
-
-	ok( a.clone().lerp( b, 0.5 ).x == x*0.5, "Passed!" );
-	ok( a.clone().lerp( b, 0.5 ).y == -y*0.5, "Passed!" );
-
-	ok( a.clone().lerp( b, 1 ).equals( b ), "Passed!" );
-});
-
-test( "equals", function() {
-	var a = new THREE.Vector2( x, 0 );
-	var b = new THREE.Vector2( 0, -y );
-
-	ok( a.x != b.x, "Passed!" );
-	ok( a.y != b.y, "Passed!" );
-
-	ok( ! a.equals( b ), "Passed!" );
-	ok( ! b.equals( a ), "Passed!" );
-
-	a.copy( b );
-	ok( a.x == b.x, "Passed!" );
-	ok( a.y == b.y, "Passed!" );
-
-	ok( a.equals( b ), "Passed!" );
-	ok( b.equals( a ), "Passed!" );
-});

+ 0 - 379
test/unit/math/Vector3.js

@@ -1,379 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Vector3" );
-
-test( "constructor", function() {
-	var a = new THREE.Vector3();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-
-	a = new THREE.Vector3( x, y, z );
-	ok( a.x === x, "Passed!" );
-	ok( a.y === y, "Passed!" );
-	ok( a.z === z, "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector3().copy( a );
-	ok( b.x == x, "Passed!" );
-	ok( b.y == y, "Passed!" );
-	ok( b.z == z, "Passed!" );
-
-	// ensure that it is a true copy
-	a.x = 0;
-	a.y = -1;
-	a.z = -2;
-	ok( b.x == x, "Passed!" );
-	ok( b.y == y, "Passed!" );
-	ok( b.z == z, "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Vector3();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-
-	a.set( x, y, z );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-	ok( a.z == z, "Passed!" );
-});
-
-test( "setX,setY,setZ", function() {
-	var a = new THREE.Vector3();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-
-	a.setX( x );
-	a.setY( y );
-	a.setZ( z );
-
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-	ok( a.z == z, "Passed!" );
-});
-
-test( "setComponent,getComponent", function() {
-	var a = new THREE.Vector3();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-
-	a.setComponent( 0, 1 );
-	a.setComponent( 1, 2 );
-	a.setComponent( 2, 3 );
-	ok( a.getComponent( 0 ) == 1, "Passed!" );
-	ok( a.getComponent( 1 ) == 2, "Passed!" );
-	ok( a.getComponent( 2 ) == 3, "Passed!" );
-});
-
-test( "add", function() {
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector3( -x, -y, -z );
-
-	a.add( b );
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-
-	var c = new THREE.Vector3().addVectors( b, b );
-	ok( c.x == -2*x, "Passed!" );
-	ok( c.y == -2*y, "Passed!" );
-	ok( c.z == -2*z, "Passed!" );
-});
-
-test( "sub", function() {
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector3( -x, -y, -z );
-
-	a.sub( b );
-	ok( a.x == 2*x, "Passed!" );
-	ok( a.y == 2*y, "Passed!" );
-	ok( a.z == 2*z, "Passed!" );
-
-	var c = new THREE.Vector3().subVectors( a, a );
-	ok( c.x == 0, "Passed!" );
-	ok( c.y == 0, "Passed!" );
-	ok( c.z == 0, "Passed!" );
-});
-
-test( "multiply/divide", function() {
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector3( -x, -y, -z );
-
-	a.multiplyScalar( -2 );
-	ok( a.x == x*-2, "Passed!" );
-	ok( a.y == y*-2, "Passed!" );
-	ok( a.z == z*-2, "Passed!" );
-
-	b.multiplyScalar( -2 );
-	ok( b.x == 2*x, "Passed!" );
-	ok( b.y == 2*y, "Passed!" );
-	ok( b.z == 2*z, "Passed!" );
-
-	a.divideScalar( -2 );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-	ok( a.z == z, "Passed!" );
-
-	b.divideScalar( -2 );
-	ok( b.x == -x, "Passed!" );
-	ok( b.y == -y, "Passed!" );
-	ok( b.z == -z, "Passed!" );
-});
-
-test( "min/max/clamp", function() {
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector3( -x, -y, -z );
-	var c = new THREE.Vector3();
-
-	c.copy( a ).min( b );
-	ok( c.x == -x, "Passed!" );
-	ok( c.y == -y, "Passed!" );
-	ok( c.z == -z, "Passed!" );
-
-	c.copy( a ).max( b );
-	ok( c.x == x, "Passed!" );
-	ok( c.y == y, "Passed!" );
-	ok( c.z == z, "Passed!" );
-
-	c.set( -2*x, 2*y, -2*z );
-	c.clamp( b, a );
-	ok( c.x == -x, "Passed!" );
-	ok( c.y == y, "Passed!" );
-	ok( c.z == -z, "Passed!" );
-});
-
-test( "negate", function() {
-	var a = new THREE.Vector3( x, y, z );
-
-	a.negate();
-	ok( a.x == -x, "Passed!" );
-	ok( a.y == -y, "Passed!" );
-	ok( a.z == -z, "Passed!" );
-});
-
-test( "dot", function() {
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector3( -x, -y, -z );
-	var c = new THREE.Vector3();
-
-	var result = a.dot( b );
-	ok( result == (-x*x-y*y-z*z), "Passed!" );
-
-	result = a.dot( c );
-	ok( result == 0, "Passed!" );
-});
-
-test( "length/lengthSq", function() {
-	var a = new THREE.Vector3( x, 0, 0 );
-	var b = new THREE.Vector3( 0, -y, 0 );
-	var c = new THREE.Vector3( 0, 0, z );
-	var d = new THREE.Vector3();
-
-	ok( a.length() == x, "Passed!" );
-	ok( a.lengthSq() == x*x, "Passed!" );
-	ok( b.length() == y, "Passed!" );
-	ok( b.lengthSq() == y*y, "Passed!" );
-	ok( c.length() == z, "Passed!" );
-	ok( c.lengthSq() == z*z, "Passed!" );
-	ok( d.length() == 0, "Passed!" );
-	ok( d.lengthSq() == 0, "Passed!" );
-
-	a.set( x, y, z );
-	ok( a.length() == Math.sqrt( x*x + y*y + z*z ), "Passed!" );
-	ok( a.lengthSq() == ( x*x + y*y + z*z ), "Passed!" );
-});
-
-test( "normalize", function() {
-	var a = new THREE.Vector3( x, 0, 0 );
-	var b = new THREE.Vector3( 0, -y, 0 );
-	var c = new THREE.Vector3( 0, 0, z );
-
-	a.normalize();
-	ok( a.length() == 1, "Passed!" );
-	ok( a.x == 1, "Passed!" );
-
-	b.normalize();
-	ok( b.length() == 1, "Passed!" );
-	ok( b.y == -1, "Passed!" );
-
-	c.normalize();
-	ok( c.length() == 1, "Passed!" );
-	ok( c.z == 1, "Passed!" );
-});
-
-test( "distanceTo/distanceToSquared", function() {
-	var a = new THREE.Vector3( x, 0, 0 );
-	var b = new THREE.Vector3( 0, -y, 0 );
-	var c = new THREE.Vector3( 0, 0, z );
-	var d = new THREE.Vector3();
-
-	ok( a.distanceTo( d ) == x, "Passed!" );
-	ok( a.distanceToSquared( d ) == x*x, "Passed!" );
-
-	ok( b.distanceTo( d ) == y, "Passed!" );
-	ok( b.distanceToSquared( d ) == y*y, "Passed!" );
-
-	ok( c.distanceTo( d ) == z, "Passed!" );
-	ok( c.distanceToSquared( d ) == z*z, "Passed!" );
-});
-
-test( "setLength", function() {
-	var a = new THREE.Vector3( x, 0, 0 );
-
-	ok( a.length() == x, "Passed!" );
-	a.setLength( y );
-	ok( a.length() == y, "Passed!" );
-
-	a = new THREE.Vector3( 0, 0, 0 );
-	ok( a.length() == 0, "Passed!" );
-	a.setLength( y );
-	ok( a.length() == 0, "Passed!" );
-
-});
-
-test( "projectOnVector", function() {
-	var a = new THREE.Vector3( 1, 0, 0 );
-	var b = new THREE.Vector3();
-	var normal = new THREE.Vector3( 10, 0, 0 );
-
-	ok( b.copy( a ).projectOnVector( normal ).equals( new THREE.Vector3( 1, 0, 0 ) ), "Passed!" );
-
-	a.set( 0, 1, 0 );
-	ok( b.copy( a ).projectOnVector( normal ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	a.set( 0, 0, -1 );
-	ok( b.copy( a ).projectOnVector( normal ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	a.set( -1, 0, 0 );
-	ok( b.copy( a ).projectOnVector( normal ).equals( new THREE.Vector3( -1, 0, 0 ) ), "Passed!" );
-
-});
-
-test( "projectOnPlane", function() {
-	var a = new THREE.Vector3( 1, 0, 0 );
-	var b = new THREE.Vector3();
-	var normal = new THREE.Vector3( 1, 0, 0 );
-
-	ok( b.copy( a ).projectOnPlane( normal ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-	a.set( 0, 1, 0 );
-	ok( b.copy( a ).projectOnPlane( normal ).equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-
-	a.set( 0, 0, -1 );
-	ok( b.copy( a ).projectOnPlane( normal ).equals( new THREE.Vector3( 0, 0, -1 ) ), "Passed!" );
-
-	a.set( -1, 0, 0 );
-	ok( b.copy( a ).projectOnPlane( normal ).equals( new THREE.Vector3( 0, 0, 0 ) ), "Passed!" );
-
-});
-
-test( "reflect", function() {
-	var a = new THREE.Vector3();
-	var normal = new THREE.Vector3( 0, 1, 0 );
-	var b = new THREE.Vector3();
-
-	a.set( 0, -1, 0 );
-	ok( b.copy( a ).reflect( normal ).equals( new THREE.Vector3( 0, 1, 0 ) ), "Passed!" );
-
-	a.set( 1, -1, 0 );
-	ok( b.copy( a ).reflect( normal ).equals( new THREE.Vector3( 1, 1, 0 ) ), "Passed!" );
-
-	a.set( 1, -1, 0 );
-	normal.set( 0, -1, 0 );
-	ok( b.copy( a ).reflect( normal ).equals( new THREE.Vector3( 1, 1, 0 ) ), "Passed!" );
-});
-
-test( "angleTo", function() {
-	var a = new THREE.Vector3( 0, -0.18851655680720186, 0.9820700116639124 );
-	var b = new THREE.Vector3( 0, 0.18851655680720186, -0.9820700116639124 );
-
-	equal( a.angleTo( a ), 0 );
-	equal( a.angleTo( b ), Math.PI );
-
-	var x = new THREE.Vector3( 1, 0, 0 );
-	var y = new THREE.Vector3( 0, 1, 0 );
-	var z = new THREE.Vector3( 0, 0, 1 );
-
-	equal( x.angleTo( y ), Math.PI / 2 );
-	equal( x.angleTo( z ), Math.PI / 2 );
-	equal( z.angleTo( x ), Math.PI / 2 );
-
-	ok( Math.abs( x.angleTo( new THREE.Vector3( 1, 1, 0 ) ) - ( Math.PI / 4 ) ) < 0.0000001 );
-});
-
-test( "lerp/clone", function() {
-	var a = new THREE.Vector3( x, 0, z );
-	var b = new THREE.Vector3( 0, -y, 0 );
-
-	ok( a.lerp( a, 0 ).equals( a.lerp( a, 0.5 ) ), "Passed!" );
-	ok( a.lerp( a, 0 ).equals( a.lerp( a, 1 ) ), "Passed!" );
-
-	ok( a.clone().lerp( b, 0 ).equals( a ), "Passed!" );
-
-	ok( a.clone().lerp( b, 0.5 ).x == x*0.5, "Passed!" );
-	ok( a.clone().lerp( b, 0.5 ).y == -y*0.5, "Passed!" );
-	ok( a.clone().lerp( b, 0.5 ).z == z*0.5, "Passed!" );
-
-	ok( a.clone().lerp( b, 1 ).equals( b ), "Passed!" );
-});
-
-test( "equals", function() {
-	var a = new THREE.Vector3( x, 0, z );
-	var b = new THREE.Vector3( 0, -y, 0 );
-
-	ok( a.x != b.x, "Passed!" );
-	ok( a.y != b.y, "Passed!" );
-	ok( a.z != b.z, "Passed!" );
-
-	ok( ! a.equals( b ), "Passed!" );
-	ok( ! b.equals( a ), "Passed!" );
-
-	a.copy( b );
-	ok( a.x == b.x, "Passed!" );
-	ok( a.y == b.y, "Passed!" );
-	ok( a.z == b.z, "Passed!" );
-
-	ok( a.equals( b ), "Passed!" );
-	ok( b.equals( a ), "Passed!" );
-});
-
-test( "applyMatrix4", function() {
-
-	var a = new THREE.Vector3( x, y, z );
-	var b = new THREE.Vector4( x, y, z, 1 );
-
-	var m = new THREE.Matrix4().makeRotationX( Math.PI );
-	a.applyMatrix4( m );
-	b.applyMatrix4( m );
-	ok( a.x == b.x / b.w, "Passed!" );
-	ok( a.y == b.y / b.w, "Passed!" );
-	ok( a.z == b.z / b.w, "Passed!" );
-
-	m = new THREE.Matrix4().makeTranslation( 3, 2, 1 );
-	a.applyMatrix4( m );
-	b.applyMatrix4( m );
-	ok( a.x == b.x / b.w, "Passed!" );
-	ok( a.y == b.y / b.w, "Passed!" );
-	ok( a.z == b.z / b.w, "Passed!" );
-
-	m = new THREE.Matrix4().set(
-		1, 0, 0, 0,
-		0, 1, 0, 0,
-		0, 0, 1, 0,
-		0, 0, 1, 0
-	);
-	a.applyMatrix4( m );
-	b.applyMatrix4( m );
-	ok( a.x == b.x / b.w, "Passed!" );
-	ok( a.y == b.y / b.w, "Passed!" );
-	ok( a.z == b.z / b.w, "Passed!" );
-
-});

+ 0 - 318
test/unit/math/Vector4.js

@@ -1,318 +0,0 @@
-/**
- * @author bhouston / http://exocortex.com
- */
-
-module( "Vector4" );
-
-test( "constructor", function() {
-	var a = new THREE.Vector4();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-	ok( a.w == 1, "Passed!" );
-
-	a = new THREE.Vector4( x, y, z, w );
-	ok( a.x === x, "Passed!" );
-	ok( a.y === y, "Passed!" );
-	ok( a.z === z, "Passed!" );
-	ok( a.w === w, "Passed!" );
-});
-
-test( "copy", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-	var b = new THREE.Vector4().copy( a );
-	ok( b.x == x, "Passed!" );
-	ok( b.y == y, "Passed!" );
-	ok( b.z == z, "Passed!" );
-	ok( b.w == w, "Passed!" );
-
-	// ensure that it is a true copy
-	a.x = 0;
-	a.y = -1;
-	a.z = -2;
-	a.w = -3;
-	ok( b.x == x, "Passed!" );
-	ok( b.y == y, "Passed!" );
-	ok( b.z == z, "Passed!" );
-	ok( b.w == w, "Passed!" );
-});
-
-test( "set", function() {
-	var a = new THREE.Vector4();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-	ok( a.w == 1, "Passed!" );
-
-	a.set( x, y, z, w );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-	ok( a.z == z, "Passed!" );
-	ok( a.w == w, "Passed!" );
-});
-
-test( "setX,setY,setZ,setW", function() {
-	var a = new THREE.Vector4();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-	ok( a.w == 1, "Passed!" );
-
-	a.setX( x );
-	a.setY( y );
-	a.setZ( z );
-	a.setW( w );
-
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-	ok( a.z == z, "Passed!" );
-	ok( a.w == w, "Passed!" );
-});
-
-test( "setComponent,getComponent", function() {
-	var a = new THREE.Vector4();
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-	ok( a.w == 1, "Passed!" );
-
-	a.setComponent( 0, 1 );
-	a.setComponent( 1, 2 );
-	a.setComponent( 2, 3 );
-	a.setComponent( 3, 4 );
-	ok( a.getComponent( 0 ) == 1, "Passed!" );
-	ok( a.getComponent( 1 ) == 2, "Passed!" );
-	ok( a.getComponent( 2 ) == 3, "Passed!" );
-	ok( a.getComponent( 3 ) == 4, "Passed!" );
-});
-
-test( "add", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-	var b = new THREE.Vector4( -x, -y, -z, -w );
-
-	a.add( b );
-	ok( a.x == 0, "Passed!" );
-	ok( a.y == 0, "Passed!" );
-	ok( a.z == 0, "Passed!" );
-	ok( a.w == 0, "Passed!" );
-
-	var c = new THREE.Vector4().addVectors( b, b );
-	ok( c.x == -2*x, "Passed!" );
-	ok( c.y == -2*y, "Passed!" );
-	ok( c.z == -2*z, "Passed!" );
-	ok( c.w == -2*w, "Passed!" );
-});
-
-test( "sub", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-	var b = new THREE.Vector4( -x, -y, -z, -w );
-
-	a.sub( b );
-	ok( a.x == 2*x, "Passed!" );
-	ok( a.y == 2*y, "Passed!" );
-	ok( a.z == 2*z, "Passed!" );
-	ok( a.w == 2*w, "Passed!" );
-
-	var c = new THREE.Vector4().subVectors( a, a );
-	ok( c.x == 0, "Passed!" );
-	ok( c.y == 0, "Passed!" );
-	ok( c.z == 0, "Passed!" );
-	ok( c.w == 0, "Passed!" );
-});
-
-test( "multiply/divide", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-	var b = new THREE.Vector4( -x, -y, -z, -w );
-
-	a.multiplyScalar( -2 );
-	ok( a.x == x*-2, "Passed!" );
-	ok( a.y == y*-2, "Passed!" );
-	ok( a.z == z*-2, "Passed!" );
-	ok( a.w == w*-2, "Passed!" );
-
-	b.multiplyScalar( -2 );
-	ok( b.x == 2*x, "Passed!" );
-	ok( b.y == 2*y, "Passed!" );	
-	ok( b.z == 2*z, "Passed!" );	
-	ok( b.w == 2*w, "Passed!" );	
-
-	a.divideScalar( -2 );
-	ok( a.x == x, "Passed!" );
-	ok( a.y == y, "Passed!" );
-	ok( a.z == z, "Passed!" );
-	ok( a.w == w, "Passed!" );
-
-	b.divideScalar( -2 );
-	ok( b.x == -x, "Passed!" );
-	ok( b.y == -y, "Passed!" );
-	ok( b.z == -z, "Passed!" );
-	ok( b.w == -w, "Passed!" );
-});
-
-test( "min/max/clamp", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-	var b = new THREE.Vector4( -x, -y, -z, -w );
-	var c = new THREE.Vector4();
-
-	c.copy( a ).min( b );
-	ok( c.x == -x, "Passed!" );
-	ok( c.y == -y, "Passed!" );
-	ok( c.z == -z, "Passed!" );
-	ok( c.w == -w, "Passed!" );
-
-	c.copy( a ).max( b );
-	ok( c.x == x, "Passed!" );
-	ok( c.y == y, "Passed!" );
-	ok( c.z == z, "Passed!" );
-	ok( c.w == w, "Passed!" );
-
-	c.set( -2*x, 2*y, -2*z, 2*w );
-	c.clamp( b, a );
-	ok( c.x == -x, "Passed!" );
-	ok( c.y == y, "Passed!" );
-	ok( c.z == -z, "Passed!" );
-	ok( c.w == w, "Passed!" );
-});
-
-test( "negate", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-
-	a.negate();
-	ok( a.x == -x, "Passed!" );
-	ok( a.y == -y, "Passed!" );
-	ok( a.z == -z, "Passed!" );
-	ok( a.w == -w, "Passed!" );
-});
-
-test( "dot", function() {
-	var a = new THREE.Vector4( x, y, z, w );
-	var b = new THREE.Vector4( -x, -y, -z, -w );
-	var c = new THREE.Vector4( 0, 0, 0, 0 );
-
-	var result = a.dot( b );
-	ok( result == (-x*x-y*y-z*z-w*w), "Passed!" );
-
-	result = a.dot( c );
-	ok( result == 0, "Passed!" );
-});
-
-test( "length/lengthSq", function() {
-	var a = new THREE.Vector4( x, 0, 0, 0 );
-	var b = new THREE.Vector4( 0, -y, 0, 0 );
-	var c = new THREE.Vector4( 0, 0, z, 0 );
-	var d = new THREE.Vector4( 0, 0, 0, w );
-	var e = new THREE.Vector4( 0, 0, 0, 0 );
-	
-	ok( a.length() == x, "Passed!" );
-	ok( a.lengthSq() == x*x, "Passed!" );
-	ok( b.length() == y, "Passed!" );
-	ok( b.lengthSq() == y*y, "Passed!" );
-	ok( c.length() == z, "Passed!" );
-	ok( c.lengthSq() == z*z, "Passed!" );
-	ok( d.length() == w, "Passed!" );
-	ok( d.lengthSq() == w*w, "Passed!" );
-	ok( e.length() == 0, "Passed!" );
-	ok( e.lengthSq() == 0, "Passed!" );
-
-	a.set( x, y, z, w );
-	ok( a.length() == Math.sqrt( x*x + y*y + z*z + w*w ), "Passed!" );
-	ok( a.lengthSq() == ( x*x + y*y + z*z + w*w ), "Passed!" );
-});
-
-test( "normalize", function() {
-	var a = new THREE.Vector4( x, 0, 0, 0 );
-	var b = new THREE.Vector4( 0, -y, 0, 0 );
-	var c = new THREE.Vector4( 0, 0, z, 0 );
-	var d = new THREE.Vector4( 0, 0, 0, -w );
-	
-	a.normalize();
-	ok( a.length() == 1, "Passed!" );
-	ok( a.x == 1, "Passed!" );
-
-	b.normalize();
-	ok( b.length() == 1, "Passed!" );
-	ok( b.y == -1, "Passed!" );
-
-	c.normalize();
-	ok( c.length() == 1, "Passed!" );
-	ok( c.z == 1, "Passed!" );
-
-	d.normalize();
-	ok( d.length() == 1, "Passed!" );
-	ok( d.w == -1, "Passed!" );
-});
-
-/*
-test( "distanceTo/distanceToSquared", function() {
-	var a = new THREE.Vector4( x, 0, 0, 0 );
-	var b = new THREE.Vector4( 0, -y, 0, 0 );
-	var c = new THREE.Vector4( 0, 0, z, 0 );
-	var d = new THREE.Vector4( 0, 0, 0, -w );
-	var e = new THREE.Vector4();
-	
-	ok( a.distanceTo( e ) == x, "Passed!" );
-	ok( a.distanceToSquared( e ) == x*x, "Passed!" );
-
-	ok( b.distanceTo( e ) == y, "Passed!" );
-	ok( b.distanceToSquared( e ) == y*y, "Passed!" );
-
-	ok( c.distanceTo( e ) == z, "Passed!" );
-	ok( c.distanceToSquared( e ) == z*z, "Passed!" );
-
-	ok( d.distanceTo( e ) == w, "Passed!" );
-	ok( d.distanceToSquared( e ) == w*w, "Passed!" );
-});
-*/
-
-
-test( "setLength", function() {
-	var a = new THREE.Vector4( x, 0, 0, 0 );
-
-	ok( a.length() == x, "Passed!" );
-	a.setLength( y );
-	ok( a.length() == y, "Passed!" );
-
-	a = new THREE.Vector4( 0, 0, 0, 0 );
-	ok( a.length() == 0, "Passed!" );
-	a.setLength( y );
-	ok( a.length() == 0, "Passed!" );
-});
-
-test( "lerp/clone", function() {
-	var a = new THREE.Vector4( x, 0, z, 0 );
-	var b = new THREE.Vector4( 0, -y, 0, -w );
-
-	ok( a.lerp( a, 0 ).equals( a.lerp( a, 0.5 ) ), "Passed!" );
-	ok( a.lerp( a, 0 ).equals( a.lerp( a, 1 ) ), "Passed!" );
-
-	ok( a.clone().lerp( b, 0 ).equals( a ), "Passed!" );
-
-	ok( a.clone().lerp( b, 0.5 ).x == x*0.5, "Passed!" );
-	ok( a.clone().lerp( b, 0.5 ).y == -y*0.5, "Passed!" );
-	ok( a.clone().lerp( b, 0.5 ).z == z*0.5, "Passed!" );
-	ok( a.clone().lerp( b, 0.5 ).w == -w*0.5, "Passed!" );
-
-	ok( a.clone().lerp( b, 1 ).equals( b ), "Passed!" );
-});
-
-test( "equals", function() {
-	var a = new THREE.Vector4( x, 0, z, 0 );
-	var b = new THREE.Vector4( 0, -y, 0, -w );
-
-	ok( a.x != b.x, "Passed!" );
-	ok( a.y != b.y, "Passed!" );
-	ok( a.z != b.z, "Passed!" );
-	ok( a.w != b.w, "Passed!" );
-
-	ok( ! a.equals( b ), "Passed!" );
-	ok( ! b.equals( a ), "Passed!" );
-
-	a.copy( b );
-	ok( a.x == b.x, "Passed!" );
-	ok( a.y == b.y, "Passed!" );
-	ok( a.z == b.z, "Passed!" );
-	ok( a.w == b.w, "Passed!" );
-
-	ok( a.equals( b ), "Passed!" );
-	ok( b.equals( a ), "Passed!" );
-});

+ 0 - 291
test/unit/qunit-1.18.0.css

@@ -1,291 +0,0 @@
-/*!
- * QUnit 1.18.0
- * http://qunitjs.com/
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license
- * http://jquery.org/license
- *
- * Date: 2015-04-03T10:23Z
- */
-
-/** Font Family and Sizes */
-
-#qunit-tests, #qunit-header, #qunit-banner, #qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult {
-	font-family: "Helvetica Neue Light", "HelveticaNeue-Light", "Helvetica Neue", Calibri, Helvetica, Arial, sans-serif;
-}
-
-#qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult, #qunit-tests li { font-size: small; }
-#qunit-tests { font-size: smaller; }
-
-
-/** Resets */
-
-#qunit-tests, #qunit-header, #qunit-banner, #qunit-userAgent, #qunit-testresult, #qunit-modulefilter {
-	margin: 0;
-	padding: 0;
-}
-
-
-/** Header */
-
-#qunit-header {
-	padding: 0.5em 0 0.5em 1em;
-
-	color: #8699A4;
-	background-color: #0D3349;
-
-	font-size: 1.5em;
-	line-height: 1em;
-	font-weight: 400;
-
-	border-radius: 5px 5px 0 0;
-}
-
-#qunit-header a {
-	text-decoration: none;
-	color: #C2CCD1;
-}
-
-#qunit-header a:hover,
-#qunit-header a:focus {
-	color: #FFF;
-}
-
-#qunit-testrunner-toolbar label {
-	display: inline-block;
-	padding: 0 0.5em 0 0.1em;
-}
-
-#qunit-banner {
-	height: 5px;
-}
-
-#qunit-testrunner-toolbar {
-	padding: 0.5em 1em 0.5em 1em;
-	color: #5E740B;
-	background-color: #EEE;
-	overflow: hidden;
-}
-
-#qunit-userAgent {
-	padding: 0.5em 1em 0.5em 1em;
-	background-color: #2B81AF;
-	color: #FFF;
-	text-shadow: rgba(0, 0, 0, 0.5) 2px 2px 1px;
-}
-
-#qunit-modulefilter-container {
-	float: right;
-	padding: 0.2em;
-}
-
-.qunit-url-config {
-	display: inline-block;
-	padding: 0.1em;
-}
-
-.qunit-filter {
-	display: block;
-	float: right;
-	margin-left: 1em;
-}
-
-/** Tests: Pass/Fail */
-
-#qunit-tests {
-	list-style-position: inside;
-}
-
-#qunit-tests li {
-	padding: 0.4em 1em 0.4em 1em;
-	border-bottom: 1px solid #FFF;
-	list-style-position: inside;
-}
-
-#qunit-tests > li {
-	display: none;
-}
-
-#qunit-tests li.running,
-#qunit-tests li.pass,
-#qunit-tests li.fail,
-#qunit-tests li.skipped {
-	display: list-item;
-}
-
-#qunit-tests.hidepass li.running,
-#qunit-tests.hidepass li.pass {
-	visibility: hidden;
-	position: absolute;
-	width:   0px;
-	height:  0px;
-	padding: 0;
-	border:  0;
-	margin:  0;
-}
-
-#qunit-tests li strong {
-	cursor: pointer;
-}
-
-#qunit-tests li.skipped strong {
-	cursor: default;
-}
-
-#qunit-tests li a {
-	padding: 0.5em;
-	color: #C2CCD1;
-	text-decoration: none;
-}
-
-#qunit-tests li p a {
-	padding: 0.25em;
-	color: #6B6464;
-}
-#qunit-tests li a:hover,
-#qunit-tests li a:focus {
-	color: #000;
-}
-
-#qunit-tests li .runtime {
-	float: right;
-	font-size: smaller;
-}
-
-.qunit-assert-list {
-	margin-top: 0.5em;
-	padding: 0.5em;
-
-	background-color: #FFF;
-
-	border-radius: 5px;
-}
-
-.qunit-collapsed {
-	display: none;
-}
-
-#qunit-tests table {
-	border-collapse: collapse;
-	margin-top: 0.2em;
-}
-
-#qunit-tests th {
-	text-align: right;
-	vertical-align: top;
-	padding: 0 0.5em 0 0;
-}
-
-#qunit-tests td {
-	vertical-align: top;
-}
-
-#qunit-tests pre {
-	margin: 0;
-	white-space: pre-wrap;
-	word-wrap: break-word;
-}
-
-#qunit-tests del {
-	background-color: #E0F2BE;
-	color: #374E0C;
-	text-decoration: none;
-}
-
-#qunit-tests ins {
-	background-color: #FFCACA;
-	color: #500;
-	text-decoration: none;
-}
-
-/*** Test Counts */
-
-#qunit-tests b.counts                       { color: #000; }
-#qunit-tests b.passed                       { color: #5E740B; }
-#qunit-tests b.failed                       { color: #710909; }
-
-#qunit-tests li li {
-	padding: 5px;
-	background-color: #FFF;
-	border-bottom: none;
-	list-style-position: inside;
-}
-
-/*** Passing Styles */
-
-#qunit-tests li li.pass {
-	color: #3C510C;
-	background-color: #FFF;
-	border-left: 10px solid #C6E746;
-}
-
-#qunit-tests .pass                          { color: #528CE0; background-color: #D2E0E6; }
-#qunit-tests .pass .test-name               { color: #366097; }
-
-#qunit-tests .pass .test-actual,
-#qunit-tests .pass .test-expected           { color: #999; }
-
-#qunit-banner.qunit-pass                    { background-color: #C6E746; }
-
-/*** Failing Styles */
-
-#qunit-tests li li.fail {
-	color: #710909;
-	background-color: #FFF;
-	border-left: 10px solid #EE5757;
-	white-space: pre;
-}
-
-#qunit-tests > li:last-child {
-	border-radius: 0 0 5px 5px;
-}
-
-#qunit-tests .fail                          { color: #000; background-color: #EE5757; }
-#qunit-tests .fail .test-name,
-#qunit-tests .fail .module-name             { color: #000; }
-
-#qunit-tests .fail .test-actual             { color: #EE5757; }
-#qunit-tests .fail .test-expected           { color: #008000; }
-
-#qunit-banner.qunit-fail                    { background-color: #EE5757; }
-
-/*** Skipped tests */
-
-#qunit-tests .skipped {
-	background-color: #EBECE9;
-}
-
-#qunit-tests .qunit-skipped-label {
-	background-color: #F4FF77;
-	display: inline-block;
-	font-style: normal;
-	color: #366097;
-	line-height: 1.8em;
-	padding: 0 0.5em;
-	margin: -0.4em 0.4em -0.4em 0;
-}
-
-/** Result */
-
-#qunit-testresult {
-	padding: 0.5em 1em 0.5em 1em;
-
-	color: #2B81AF;
-	background-color: #D2E0E6;
-
-	border-bottom: 1px solid #FFF;
-}
-#qunit-testresult .module-name {
-	font-weight: 700;
-}
-
-/** Fixture */
-
-#qunit-fixture {
-	position: absolute;
-	top: -10000px;
-	left: -10000px;
-	width: 1000px;
-	height: 1000px;
-}

+ 0 - 3829
test/unit/qunit-1.18.0.js

@@ -1,3829 +0,0 @@
-/*!
- * QUnit 1.18.0
- * http://qunitjs.com/
- *
- * Copyright jQuery Foundation and other contributors
- * Released under the MIT license
- * http://jquery.org/license
- *
- * Date: 2015-04-03T10:23Z
- */
-
-(function( window ) {
-
-var QUnit,
-	config,
-	onErrorFnPrev,
-	loggingCallbacks = {},
-	fileName = ( sourceFromStacktrace( 0 ) || "" ).replace( /(:\d+)+\)?/, "" ).replace( /.+\//, "" ),
-	toString = Object.prototype.toString,
-	hasOwn = Object.prototype.hasOwnProperty,
-	// Keep a local reference to Date (GH-283)
-	Date = window.Date,
-	now = Date.now || function() {
-		return new Date().getTime();
-	},
-	globalStartCalled = false,
-	runStarted = false,
-	setTimeout = window.setTimeout,
-	clearTimeout = window.clearTimeout,
-	defined = {
-		document: window.document !== undefined,
-		setTimeout: window.setTimeout !== undefined,
-		sessionStorage: (function() {
-			var x = "qunit-test-string";
-			try {
-				sessionStorage.setItem( x, x );
-				sessionStorage.removeItem( x );
-				return true;
-			} catch ( e ) {
-				return false;
-			}
-		}())
-	},
-	/**
-	 * Provides a normalized error string, correcting an issue
-	 * with IE 7 (and prior) where Error.prototype.toString is
-	 * not properly implemented
-	 *
-	 * Based on http://es5.github.com/#x15.11.4.4
-	 *
-	 * @param {String|Error} error
-	 * @return {String} error message
-	 */
-	errorString = function( error ) {
-		var name, message,
-			errorString = error.toString();
-		if ( errorString.substring( 0, 7 ) === "[object" ) {
-			name = error.name ? error.name.toString() : "Error";
-			message = error.message ? error.message.toString() : "";
-			if ( name && message ) {
-				return name + ": " + message;
-			} else if ( name ) {
-				return name;
-			} else if ( message ) {
-				return message;
-			} else {
-				return "Error";
-			}
-		} else {
-			return errorString;
-		}
-	},
-	/**
-	 * Makes a clone of an object using only Array or Object as base,
-	 * and copies over the own enumerable properties.
-	 *
-	 * @param {Object} obj
-	 * @return {Object} New object with only the own properties (recursively).
-	 */
-	objectValues = function( obj ) {
-		var key, val,
-			vals = QUnit.is( "array", obj ) ? [] : {};
-		for ( key in obj ) {
-			if ( hasOwn.call( obj, key ) ) {
-				val = obj[ key ];
-				vals[ key ] = val === Object( val ) ? objectValues( val ) : val;
-			}
-		}
-		return vals;
-	};
-
-QUnit = {};
-
-/**
- * Config object: Maintain internal state
- * Later exposed as QUnit.config
- * `config` initialized at top of scope
- */
-config = {
-	// The queue of tests to run
-	queue: [],
-
-	// block until document ready
-	blocking: true,
-
-	// by default, run previously failed tests first
-	// very useful in combination with "Hide passed tests" checked
-	reorder: true,
-
-	// by default, modify document.title when suite is done
-	altertitle: true,
-
-	// by default, scroll to top of the page when suite is done
-	scrolltop: true,
-
-	// when enabled, all tests must call expect()
-	requireExpects: false,
-
-	// depth up-to which object will be dumped
-	maxDepth: 0,
-
-	// add checkboxes that are persisted in the query-string
-	// when enabled, the id is set to `true` as a `QUnit.config` property
-	urlConfig: [
-		{
-			id: "hidepassed",
-			label: "Hide passed tests",
-			tooltip: "Only show tests and assertions that fail. Stored as query-strings."
-		},
-		{
-			id: "noglobals",
-			label: "Check for Globals",
-			tooltip: "Enabling this will test if any test introduces new properties on the " +
-				"`window` object. Stored as query-strings."
-		},
-		{
-			id: "notrycatch",
-			label: "No try-catch",
-			tooltip: "Enabling this will run tests outside of a try-catch block. Makes debugging " +
-				"exceptions in IE reasonable. Stored as query-strings."
-		}
-	],
-
-	// Set of all modules.
-	modules: [],
-
-	// The first unnamed module
-	currentModule: {
-		name: "",
-		tests: []
-	},
-
-	callbacks: {}
-};
-
-// Push a loose unnamed module to the modules collection
-config.modules.push( config.currentModule );
-
-// Initialize more QUnit.config and QUnit.urlParams
-(function() {
-	var i, current,
-		location = window.location || { search: "", protocol: "file:" },
-		params = location.search.slice( 1 ).split( "&" ),
-		length = params.length,
-		urlParams = {};
-
-	if ( params[ 0 ] ) {
-		for ( i = 0; i < length; i++ ) {
-			current = params[ i ].split( "=" );
-			current[ 0 ] = decodeURIComponent( current[ 0 ] );
-
-			// allow just a key to turn on a flag, e.g., test.html?noglobals
-			current[ 1 ] = current[ 1 ] ? decodeURIComponent( current[ 1 ] ) : true;
-			if ( urlParams[ current[ 0 ] ] ) {
-				urlParams[ current[ 0 ] ] = [].concat( urlParams[ current[ 0 ] ], current[ 1 ] );
-			} else {
-				urlParams[ current[ 0 ] ] = current[ 1 ];
-			}
-		}
-	}
-
-	if ( urlParams.filter === true ) {
-		delete urlParams.filter;
-	}
-
-	QUnit.urlParams = urlParams;
-
-	// String search anywhere in moduleName+testName
-	config.filter = urlParams.filter;
-
-	if ( urlParams.maxDepth ) {
-		config.maxDepth = parseInt( urlParams.maxDepth, 10 ) === -1 ?
-			Number.POSITIVE_INFINITY :
-			urlParams.maxDepth;
-	}
-
-	config.testId = [];
-	if ( urlParams.testId ) {
-
-		// Ensure that urlParams.testId is an array
-		urlParams.testId = decodeURIComponent( urlParams.testId ).split( "," );
-		for ( i = 0; i < urlParams.testId.length; i++ ) {
-			config.testId.push( urlParams.testId[ i ] );
-		}
-	}
-
-	// Figure out if we're running the tests from a server or not
-	QUnit.isLocal = location.protocol === "file:";
-
-	// Expose the current QUnit version
-	QUnit.version = "1.18.0";
-}());
-
-// Root QUnit object.
-// `QUnit` initialized at top of scope
-extend( QUnit, {
-
-	// call on start of module test to prepend name to all tests
-	module: function( name, testEnvironment ) {
-		var currentModule = {
-			name: name,
-			testEnvironment: testEnvironment,
-			tests: []
-		};
-
-		// DEPRECATED: handles setup/teardown functions,
-		// beforeEach and afterEach should be used instead
-		if ( testEnvironment && testEnvironment.setup ) {
-			testEnvironment.beforeEach = testEnvironment.setup;
-			delete testEnvironment.setup;
-		}
-		if ( testEnvironment && testEnvironment.teardown ) {
-			testEnvironment.afterEach = testEnvironment.teardown;
-			delete testEnvironment.teardown;
-		}
-
-		config.modules.push( currentModule );
-		config.currentModule = currentModule;
-	},
-
-	// DEPRECATED: QUnit.asyncTest() will be removed in QUnit 2.0.
-	asyncTest: function( testName, expected, callback ) {
-		if ( arguments.length === 2 ) {
-			callback = expected;
-			expected = null;
-		}
-
-		QUnit.test( testName, expected, callback, true );
-	},
-
-	test: function( testName, expected, callback, async ) {
-		var test;
-
-		if ( arguments.length === 2 ) {
-			callback = expected;
-			expected = null;
-		}
-
-		test = new Test({
-			testName: testName,
-			expected: expected,
-			async: async,
-			callback: callback
-		});
-
-		test.queue();
-	},
-
-	skip: function( testName ) {
-		var test = new Test({
-			testName: testName,
-			skip: true
-		});
-
-		test.queue();
-	},
-
-	// DEPRECATED: The functionality of QUnit.start() will be altered in QUnit 2.0.
-	// In QUnit 2.0, invoking it will ONLY affect the `QUnit.config.autostart` blocking behavior.
-	start: function( count ) {
-		var globalStartAlreadyCalled = globalStartCalled;
-
-		if ( !config.current ) {
-			globalStartCalled = true;
-
-			if ( runStarted ) {
-				throw new Error( "Called start() outside of a test context while already started" );
-			} else if ( globalStartAlreadyCalled || count > 1 ) {
-				throw new Error( "Called start() outside of a test context too many times" );
-			} else if ( config.autostart ) {
-				throw new Error( "Called start() outside of a test context when " +
-					"QUnit.config.autostart was true" );
-			} else if ( !config.pageLoaded ) {
-
-				// The page isn't completely loaded yet, so bail out and let `QUnit.load` handle it
-				config.autostart = true;
-				return;
-			}
-		} else {
-
-			// If a test is running, adjust its semaphore
-			config.current.semaphore -= count || 1;
-
-			// Don't start until equal number of stop-calls
-			if ( config.current.semaphore > 0 ) {
-				return;
-			}
-
-			// throw an Error if start is called more often than stop
-			if ( config.current.semaphore < 0 ) {
-				config.current.semaphore = 0;
-
-				QUnit.pushFailure(
-					"Called start() while already started (test's semaphore was 0 already)",
-					sourceFromStacktrace( 2 )
-				);
-				return;
-			}
-		}
-
-		resumeProcessing();
-	},
-
-	// DEPRECATED: QUnit.stop() will be removed in QUnit 2.0.
-	stop: function( count ) {
-
-		// If there isn't a test running, don't allow QUnit.stop() to be called
-		if ( !config.current ) {
-			throw new Error( "Called stop() outside of a test context" );
-		}
-
-		// If a test is running, adjust its semaphore
-		config.current.semaphore += count || 1;
-
-		pauseProcessing();
-	},
-
-	config: config,
-
-	// Safe object type checking
-	is: function( type, obj ) {
-		return QUnit.objectType( obj ) === type;
-	},
-
-	objectType: function( obj ) {
-		if ( typeof obj === "undefined" ) {
-			return "undefined";
-		}
-
-		// Consider: typeof null === object
-		if ( obj === null ) {
-			return "null";
-		}
-
-		var match = toString.call( obj ).match( /^\[object\s(.*)\]$/ ),
-			type = match && match[ 1 ] || "";
-
-		switch ( type ) {
-			case "Number":
-				if ( isNaN( obj ) ) {
-					return "nan";
-				}
-				return "number";
-			case "String":
-			case "Boolean":
-			case "Array":
-			case "Date":
-			case "RegExp":
-			case "Function":
-				return type.toLowerCase();
-		}
-		if ( typeof obj === "object" ) {
-			return "object";
-		}
-		return undefined;
-	},
-
-	extend: extend,
-
-	load: function() {
-		config.pageLoaded = true;
-
-		// Initialize the configuration options
-		extend( config, {
-			stats: { all: 0, bad: 0 },
-			moduleStats: { all: 0, bad: 0 },
-			started: 0,
-			updateRate: 1000,
-			autostart: true,
-			filter: ""
-		}, true );
-
-		config.blocking = false;
-
-		if ( config.autostart ) {
-			resumeProcessing();
-		}
-	}
-});
-
-// Register logging callbacks
-(function() {
-	var i, l, key,
-		callbacks = [ "begin", "done", "log", "testStart", "testDone",
-			"moduleStart", "moduleDone" ];
-
-	function registerLoggingCallback( key ) {
-		var loggingCallback = function( callback ) {
-			if ( QUnit.objectType( callback ) !== "function" ) {
-				throw new Error(
-					"QUnit logging methods require a callback function as their first parameters."
-				);
-			}
-
-			config.callbacks[ key ].push( callback );
-		};
-
-		// DEPRECATED: This will be removed on QUnit 2.0.0+
-		// Stores the registered functions allowing restoring
-		// at verifyLoggingCallbacks() if modified
-		loggingCallbacks[ key ] = loggingCallback;
-
-		return loggingCallback;
-	}
-
-	for ( i = 0, l = callbacks.length; i < l; i++ ) {
-		key = callbacks[ i ];
-
-		// Initialize key collection of logging callback
-		if ( QUnit.objectType( config.callbacks[ key ] ) === "undefined" ) {
-			config.callbacks[ key ] = [];
-		}
-
-		QUnit[ key ] = registerLoggingCallback( key );
-	}
-})();
-
-// `onErrorFnPrev` initialized at top of scope
-// Preserve other handlers
-onErrorFnPrev = window.onerror;
-
-// Cover uncaught exceptions
-// Returning true will suppress the default browser handler,
-// returning false will let it run.
-window.onerror = function( error, filePath, linerNr ) {
-	var ret = false;
-	if ( onErrorFnPrev ) {
-		ret = onErrorFnPrev( error, filePath, linerNr );
-	}
-
-	// Treat return value as window.onerror itself does,
-	// Only do our handling if not suppressed.
-	if ( ret !== true ) {
-		if ( QUnit.config.current ) {
-			if ( QUnit.config.current.ignoreGlobalErrors ) {
-				return true;
-			}
-			QUnit.pushFailure( error, filePath + ":" + linerNr );
-		} else {
-			QUnit.test( "global failure", extend(function() {
-				QUnit.pushFailure( error, filePath + ":" + linerNr );
-			}, { validTest: true } ) );
-		}
-		return false;
-	}
-
-	return ret;
-};
-
-function done() {
-	var runtime, passed;
-
-	config.autorun = true;
-
-	// Log the last module results
-	if ( config.previousModule ) {
-		runLoggingCallbacks( "moduleDone", {
-			name: config.previousModule.name,
-			tests: config.previousModule.tests,
-			failed: config.moduleStats.bad,
-			passed: config.moduleStats.all - config.moduleStats.bad,
-			total: config.moduleStats.all,
-			runtime: now() - config.moduleStats.started
-		});
-	}
-	delete config.previousModule;
-
-	runtime = now() - config.started;
-	passed = config.stats.all - config.stats.bad;
-
-	runLoggingCallbacks( "done", {
-		failed: config.stats.bad,
-		passed: passed,
-		total: config.stats.all,
-		runtime: runtime
-	});
-}
-
-// Doesn't support IE6 to IE9, it will return undefined on these browsers
-// See also https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Error/Stack
-function extractStacktrace( e, offset ) {
-	offset = offset === undefined ? 4 : offset;
-
-	var stack, include, i;
-
-	if ( e.stack ) {
-		stack = e.stack.split( "\n" );
-		if ( /^error$/i.test( stack[ 0 ] ) ) {
-			stack.shift();
-		}
-		if ( fileName ) {
-			include = [];
-			for ( i = offset; i < stack.length; i++ ) {
-				if ( stack[ i ].indexOf( fileName ) !== -1 ) {
-					break;
-				}
-				include.push( stack[ i ] );
-			}
-			if ( include.length ) {
-				return include.join( "\n" );
-			}
-		}
-		return stack[ offset ];
-
-	// Support: Safari <=6 only
-	} else if ( e.sourceURL ) {
-
-		// exclude useless self-reference for generated Error objects
-		if ( /qunit.js$/.test( e.sourceURL ) ) {
-			return;
-		}
-
-		// for actual exceptions, this is useful
-		return e.sourceURL + ":" + e.line;
-	}
-}
-
-function sourceFromStacktrace( offset ) {
-	var error = new Error();
-
-	// Support: Safari <=7 only, IE <=10 - 11 only
-	// Not all browsers generate the `stack` property for `new Error()`, see also #636
-	if ( !error.stack ) {
-		try {
-			throw error;
-		} catch ( err ) {
-			error = err;
-		}
-	}
-
-	return extractStacktrace( error, offset );
-}
-
-function synchronize( callback, last ) {
-	if ( QUnit.objectType( callback ) === "array" ) {
-		while ( callback.length ) {
-			synchronize( callback.shift() );
-		}
-		return;
-	}
-	config.queue.push( callback );
-
-	if ( config.autorun && !config.blocking ) {
-		process( last );
-	}
-}
-
-function process( last ) {
-	function next() {
-		process( last );
-	}
-	var start = now();
-	config.depth = ( config.depth || 0 ) + 1;
-
-	while ( config.queue.length && !config.blocking ) {
-		if ( !defined.setTimeout || config.updateRate <= 0 ||
-				( ( now() - start ) < config.updateRate ) ) {
-			if ( config.current ) {
-
-				// Reset async tracking for each phase of the Test lifecycle
-				config.current.usedAsync = false;
-			}
-			config.queue.shift()();
-		} else {
-			setTimeout( next, 13 );
-			break;
-		}
-	}
-	config.depth--;
-	if ( last && !config.blocking && !config.queue.length && config.depth === 0 ) {
-		done();
-	}
-}
-
-function begin() {
-	var i, l,
-		modulesLog = [];
-
-	// If the test run hasn't officially begun yet
-	if ( !config.started ) {
-
-		// Record the time of the test run's beginning
-		config.started = now();
-
-		verifyLoggingCallbacks();
-
-		// Delete the loose unnamed module if unused.
-		if ( config.modules[ 0 ].name === "" && config.modules[ 0 ].tests.length === 0 ) {
-			config.modules.shift();
-		}
-
-		// Avoid unnecessary information by not logging modules' test environments
-		for ( i = 0, l = config.modules.length; i < l; i++ ) {
-			modulesLog.push({
-				name: config.modules[ i ].name,
-				tests: config.modules[ i ].tests
-			});
-		}
-
-		// The test run is officially beginning now
-		runLoggingCallbacks( "begin", {
-			totalTests: Test.count,
-			modules: modulesLog
-		});
-	}
-
-	config.blocking = false;
-	process( true );
-}
-
-function resumeProcessing() {
-	runStarted = true;
-
-	// A slight delay to allow this iteration of the event loop to finish (more assertions, etc.)
-	if ( defined.setTimeout ) {
-		setTimeout(function() {
-			if ( config.current && config.current.semaphore > 0 ) {
-				return;
-			}
-			if ( config.timeout ) {
-				clearTimeout( config.timeout );
-			}
-
-			begin();
-		}, 13 );
-	} else {
-		begin();
-	}
-}
-
-function pauseProcessing() {
-	config.blocking = true;
-
-	if ( config.testTimeout && defined.setTimeout ) {
-		clearTimeout( config.timeout );
-		config.timeout = setTimeout(function() {
-			if ( config.current ) {
-				config.current.semaphore = 0;
-				QUnit.pushFailure( "Test timed out", sourceFromStacktrace( 2 ) );
-			} else {
-				throw new Error( "Test timed out" );
-			}
-			resumeProcessing();
-		}, config.testTimeout );
-	}
-}
-
-function saveGlobal() {
-	config.pollution = [];
-
-	if ( config.noglobals ) {
-		for ( var key in window ) {
-			if ( hasOwn.call( window, key ) ) {
-				// in Opera sometimes DOM element ids show up here, ignore them
-				if ( /^qunit-test-output/.test( key ) ) {
-					continue;
-				}
-				config.pollution.push( key );
-			}
-		}
-	}
-}
-
-function checkPollution() {
-	var newGlobals,
-		deletedGlobals,
-		old = config.pollution;
-
-	saveGlobal();
-
-	newGlobals = diff( config.pollution, old );
-	if ( newGlobals.length > 0 ) {
-		QUnit.pushFailure( "Introduced global variable(s): " + newGlobals.join( ", " ) );
-	}
-
-	deletedGlobals = diff( old, config.pollution );
-	if ( deletedGlobals.length > 0 ) {
-		QUnit.pushFailure( "Deleted global variable(s): " + deletedGlobals.join( ", " ) );
-	}
-}
-
-// returns a new Array with the elements that are in a but not in b
-function diff( a, b ) {
-	var i, j,
-		result = a.slice();
-
-	for ( i = 0; i < result.length; i++ ) {
-		for ( j = 0; j < b.length; j++ ) {
-			if ( result[ i ] === b[ j ] ) {
-				result.splice( i, 1 );
-				i--;
-				break;
-			}
-		}
-	}
-	return result;
-}
-
-function extend( a, b, undefOnly ) {
-	for ( var prop in b ) {
-		if ( hasOwn.call( b, prop ) ) {
-
-			// Avoid "Member not found" error in IE8 caused by messing with window.constructor
-			if ( !( prop === "constructor" && a === window ) ) {
-				if ( b[ prop ] === undefined ) {
-					delete a[ prop ];
-				} else if ( !( undefOnly && typeof a[ prop ] !== "undefined" ) ) {
-					a[ prop ] = b[ prop ];
-				}
-			}
-		}
-	}
-
-	return a;
-}
-
-function runLoggingCallbacks( key, args ) {
-	var i, l, callbacks;
-
-	callbacks = config.callbacks[ key ];
-	for ( i = 0, l = callbacks.length; i < l; i++ ) {
-		callbacks[ i ]( args );
-	}
-}
-
-// DEPRECATED: This will be removed on 2.0.0+
-// This function verifies if the loggingCallbacks were modified by the user
-// If so, it will restore it, assign the given callback and print a console warning
-function verifyLoggingCallbacks() {
-	var loggingCallback, userCallback;
-
-	for ( loggingCallback in loggingCallbacks ) {
-		if ( QUnit[ loggingCallback ] !== loggingCallbacks[ loggingCallback ] ) {
-
-			userCallback = QUnit[ loggingCallback ];
-
-			// Restore the callback function
-			QUnit[ loggingCallback ] = loggingCallbacks[ loggingCallback ];
-
-			// Assign the deprecated given callback
-			QUnit[ loggingCallback ]( userCallback );
-
-			if ( window.console && window.console.warn ) {
-				window.console.warn(
-					"QUnit." + loggingCallback + " was replaced with a new value.\n" +
-					"Please, check out the documentation on how to apply logging callbacks.\n" +
-					"Reference: http://api.qunitjs.com/category/callbacks/"
-				);
-			}
-		}
-	}
-}
-
-// from jquery.js
-function inArray( elem, array ) {
-	if ( array.indexOf ) {
-		return array.indexOf( elem );
-	}
-
-	for ( var i = 0, length = array.length; i < length; i++ ) {
-		if ( array[ i ] === elem ) {
-			return i;
-		}
-	}
-
-	return -1;
-}
-
-function Test( settings ) {
-	var i, l;
-
-	++Test.count;
-
-	extend( this, settings );
-	this.assertions = [];
-	this.semaphore = 0;
-	this.usedAsync = false;
-	this.module = config.currentModule;
-	this.stack = sourceFromStacktrace( 3 );
-
-	// Register unique strings
-	for ( i = 0, l = this.module.tests; i < l.length; i++ ) {
-		if ( this.module.tests[ i ].name === this.testName ) {
-			this.testName += " ";
-		}
-	}
-
-	this.testId = generateHash( this.module.name, this.testName );
-
-	this.module.tests.push({
-		name: this.testName,
-		testId: this.testId
-	});
-
-	if ( settings.skip ) {
-
-		// Skipped tests will fully ignore any sent callback
-		this.callback = function() {};
-		this.async = false;
-		this.expected = 0;
-	} else {
-		this.assert = new Assert( this );
-	}
-}
-
-Test.count = 0;
-
-Test.prototype = {
-	before: function() {
-		if (
-
-			// Emit moduleStart when we're switching from one module to another
-			this.module !== config.previousModule ||
-
-				// They could be equal (both undefined) but if the previousModule property doesn't
-				// yet exist it means this is the first test in a suite that isn't wrapped in a
-				// module, in which case we'll just emit a moduleStart event for 'undefined'.
-				// Without this, reporters can get testStart before moduleStart  which is a problem.
-				!hasOwn.call( config, "previousModule" )
-		) {
-			if ( hasOwn.call( config, "previousModule" ) ) {
-				runLoggingCallbacks( "moduleDone", {
-					name: config.previousModule.name,
-					tests: config.previousModule.tests,
-					failed: config.moduleStats.bad,
-					passed: config.moduleStats.all - config.moduleStats.bad,
-					total: config.moduleStats.all,
-					runtime: now() - config.moduleStats.started
-				});
-			}
-			config.previousModule = this.module;
-			config.moduleStats = { all: 0, bad: 0, started: now() };
-			runLoggingCallbacks( "moduleStart", {
-				name: this.module.name,
-				tests: this.module.tests
-			});
-		}
-
-		config.current = this;
-
-		this.testEnvironment = extend( {}, this.module.testEnvironment );
-		delete this.testEnvironment.beforeEach;
-		delete this.testEnvironment.afterEach;
-
-		this.started = now();
-		runLoggingCallbacks( "testStart", {
-			name: this.testName,
-			module: this.module.name,
-			testId: this.testId
-		});
-
-		if ( !config.pollution ) {
-			saveGlobal();
-		}
-	},
-
-	run: function() {
-		var promise;
-
-		config.current = this;
-
-		if ( this.async ) {
-			QUnit.stop();
-		}
-
-		this.callbackStarted = now();
-
-		if ( config.notrycatch ) {
-			promise = this.callback.call( this.testEnvironment, this.assert );
-			this.resolvePromise( promise );
-			return;
-		}
-
-		try {
-			promise = this.callback.call( this.testEnvironment, this.assert );
-			this.resolvePromise( promise );
-		} catch ( e ) {
-			this.pushFailure( "Died on test #" + ( this.assertions.length + 1 ) + " " +
-				this.stack + ": " + ( e.message || e ), extractStacktrace( e, 0 ) );
-
-			// else next test will carry the responsibility
-			saveGlobal();
-
-			// Restart the tests if they're blocking
-			if ( config.blocking ) {
-				QUnit.start();
-			}
-		}
-	},
-
-	after: function() {
-		checkPollution();
-	},
-
-	queueHook: function( hook, hookName ) {
-		var promise,
-			test = this;
-		return function runHook() {
-			config.current = test;
-			if ( config.notrycatch ) {
-				promise = hook.call( test.testEnvironment, test.assert );
-				test.resolvePromise( promise, hookName );
-				return;
-			}
-			try {
-				promise = hook.call( test.testEnvironment, test.assert );
-				test.resolvePromise( promise, hookName );
-			} catch ( error ) {
-				test.pushFailure( hookName + " failed on " + test.testName + ": " +
-					( error.message || error ), extractStacktrace( error, 0 ) );
-			}
-		};
-	},
-
-	// Currently only used for module level hooks, can be used to add global level ones
-	hooks: function( handler ) {
-		var hooks = [];
-
-		// Hooks are ignored on skipped tests
-		if ( this.skip ) {
-			return hooks;
-		}
-
-		if ( this.module.testEnvironment &&
-				QUnit.objectType( this.module.testEnvironment[ handler ] ) === "function" ) {
-			hooks.push( this.queueHook( this.module.testEnvironment[ handler ], handler ) );
-		}
-
-		return hooks;
-	},
-
-	finish: function() {
-		config.current = this;
-		if ( config.requireExpects && this.expected === null ) {
-			this.pushFailure( "Expected number of assertions to be defined, but expect() was " +
-				"not called.", this.stack );
-		} else if ( this.expected !== null && this.expected !== this.assertions.length ) {
-			this.pushFailure( "Expected " + this.expected + " assertions, but " +
-				this.assertions.length + " were run", this.stack );
-		} else if ( this.expected === null && !this.assertions.length ) {
-			this.pushFailure( "Expected at least one assertion, but none were run - call " +
-				"expect(0) to accept zero assertions.", this.stack );
-		}
-
-		var i,
-			bad = 0;
-
-		this.runtime = now() - this.started;
-		config.stats.all += this.assertions.length;
-		config.moduleStats.all += this.assertions.length;
-
-		for ( i = 0; i < this.assertions.length; i++ ) {
-			if ( !this.assertions[ i ].result ) {
-				bad++;
-				config.stats.bad++;
-				config.moduleStats.bad++;
-			}
-		}
-
-		runLoggingCallbacks( "testDone", {
-			name: this.testName,
-			module: this.module.name,
-			skipped: !!this.skip,
-			failed: bad,
-			passed: this.assertions.length - bad,
-			total: this.assertions.length,
-			runtime: this.runtime,
-
-			// HTML Reporter use
-			assertions: this.assertions,
-			testId: this.testId,
-
-			// DEPRECATED: this property will be removed in 2.0.0, use runtime instead
-			duration: this.runtime
-		});
-
-		// QUnit.reset() is deprecated and will be replaced for a new
-		// fixture reset function on QUnit 2.0/2.1.
-		// It's still called here for backwards compatibility handling
-		QUnit.reset();
-
-		config.current = undefined;
-	},
-
-	queue: function() {
-		var bad,
-			test = this;
-
-		if ( !this.valid() ) {
-			return;
-		}
-
-		function run() {
-
-			// each of these can by async
-			synchronize([
-				function() {
-					test.before();
-				},
-
-				test.hooks( "beforeEach" ),
-
-				function() {
-					test.run();
-				},
-
-				test.hooks( "afterEach" ).reverse(),
-
-				function() {
-					test.after();
-				},
-				function() {
-					test.finish();
-				}
-			]);
-		}
-
-		// `bad` initialized at top of scope
-		// defer when previous test run passed, if storage is available
-		bad = QUnit.config.reorder && defined.sessionStorage &&
-				+sessionStorage.getItem( "qunit-test-" + this.module.name + "-" + this.testName );
-
-		if ( bad ) {
-			run();
-		} else {
-			synchronize( run, true );
-		}
-	},
-
-	push: function( result, actual, expected, message ) {
-		var source,
-			details = {
-				module: this.module.name,
-				name: this.testName,
-				result: result,
-				message: message,
-				actual: actual,
-				expected: expected,
-				testId: this.testId,
-				runtime: now() - this.started
-			};
-
-		if ( !result ) {
-			source = sourceFromStacktrace();
-
-			if ( source ) {
-				details.source = source;
-			}
-		}
-
-		runLoggingCallbacks( "log", details );
-
-		this.assertions.push({
-			result: !!result,
-			message: message
-		});
-	},
-
-	pushFailure: function( message, source, actual ) {
-		if ( !this instanceof Test ) {
-			throw new Error( "pushFailure() assertion outside test context, was " +
-				sourceFromStacktrace( 2 ) );
-		}
-
-		var details = {
-				module: this.module.name,
-				name: this.testName,
-				result: false,
-				message: message || "error",
-				actual: actual || null,
-				testId: this.testId,
-				runtime: now() - this.started
-			};
-
-		if ( source ) {
-			details.source = source;
-		}
-
-		runLoggingCallbacks( "log", details );
-
-		this.assertions.push({
-			result: false,
-			message: message
-		});
-	},
-
-	resolvePromise: function( promise, phase ) {
-		var then, message,
-			test = this;
-		if ( promise != null ) {
-			then = promise.then;
-			if ( QUnit.objectType( then ) === "function" ) {
-				QUnit.stop();
-				then.call(
-					promise,
-					QUnit.start,
-					function( error ) {
-						message = "Promise rejected " +
-							( !phase ? "during" : phase.replace( /Each$/, "" ) ) +
-							" " + test.testName + ": " + ( error.message || error );
-						test.pushFailure( message, extractStacktrace( error, 0 ) );
-
-						// else next test will carry the responsibility
-						saveGlobal();
-
-						// Unblock
-						QUnit.start();
-					}
-				);
-			}
-		}
-	},
-
-	valid: function() {
-		var include,
-			filter = config.filter && config.filter.toLowerCase(),
-			module = QUnit.urlParams.module && QUnit.urlParams.module.toLowerCase(),
-			fullName = ( this.module.name + ": " + this.testName ).toLowerCase();
-
-		// Internally-generated tests are always valid
-		if ( this.callback && this.callback.validTest ) {
-			return true;
-		}
-
-		if ( config.testId.length > 0 && inArray( this.testId, config.testId ) < 0 ) {
-			return false;
-		}
-
-		if ( module && ( !this.module.name || this.module.name.toLowerCase() !== module ) ) {
-			return false;
-		}
-
-		if ( !filter ) {
-			return true;
-		}
-
-		include = filter.charAt( 0 ) !== "!";
-		if ( !include ) {
-			filter = filter.slice( 1 );
-		}
-
-		// If the filter matches, we need to honour include
-		if ( fullName.indexOf( filter ) !== -1 ) {
-			return include;
-		}
-
-		// Otherwise, do the opposite
-		return !include;
-	}
-
-};
-
-// Resets the test setup. Useful for tests that modify the DOM.
-/*
-DEPRECATED: Use multiple tests instead of resetting inside a test.
-Use testStart or testDone for custom cleanup.
-This method will throw an error in 2.0, and will be removed in 2.1
-*/
-QUnit.reset = function() {
-
-	// Return on non-browser environments
-	// This is necessary to not break on node tests
-	if ( typeof window === "undefined" ) {
-		return;
-	}
-
-	var fixture = defined.document && document.getElementById &&
-			document.getElementById( "qunit-fixture" );
-
-	if ( fixture ) {
-		fixture.innerHTML = config.fixture;
-	}
-};
-
-QUnit.pushFailure = function() {
-	if ( !QUnit.config.current ) {
-		throw new Error( "pushFailure() assertion outside test context, in " +
-			sourceFromStacktrace( 2 ) );
-	}
-
-	// Gets current test obj
-	var currentTest = QUnit.config.current;
-
-	return currentTest.pushFailure.apply( currentTest, arguments );
-};
-
-// Based on Java's String.hashCode, a simple but not
-// rigorously collision resistant hashing function
-function generateHash( module, testName ) {
-	var hex,
-		i = 0,
-		hash = 0,
-		str = module + "\x1C" + testName,
-		len = str.length;
-
-	for ( ; i < len; i++ ) {
-		hash  = ( ( hash << 5 ) - hash ) + str.charCodeAt( i );
-		hash |= 0;
-	}
-
-	// Convert the possibly negative integer hash code into an 8 character hex string, which isn't
-	// strictly necessary but increases user understanding that the id is a SHA-like hash
-	hex = ( 0x100000000 + hash ).toString( 16 );
-	if ( hex.length < 8 ) {
-		hex = "0000000" + hex;
-	}
-
-	return hex.slice( -8 );
-}
-
-function Assert( testContext ) {
-	this.test = testContext;
-}
-
-// Assert helpers
-QUnit.assert = Assert.prototype = {
-
-	// Specify the number of expected assertions to guarantee that failed test
-	// (no assertions are run at all) don't slip through.
-	expect: function( asserts ) {
-		if ( arguments.length === 1 ) {
-			this.test.expected = asserts;
-		} else {
-			return this.test.expected;
-		}
-	},
-
-	// Increment this Test's semaphore counter, then return a single-use function that
-	// decrements that counter a maximum of once.
-	async: function() {
-		var test = this.test,
-			popped = false;
-
-		test.semaphore += 1;
-		test.usedAsync = true;
-		pauseProcessing();
-
-		return function done() {
-			if ( !popped ) {
-				test.semaphore -= 1;
-				popped = true;
-				resumeProcessing();
-			} else {
-				test.pushFailure( "Called the callback returned from `assert.async` more than once",
-					sourceFromStacktrace( 2 ) );
-			}
-		};
-	},
-
-	// Exports test.push() to the user API
-	push: function( /* result, actual, expected, message */ ) {
-		var assert = this,
-			currentTest = ( assert instanceof Assert && assert.test ) || QUnit.config.current;
-
-		// Backwards compatibility fix.
-		// Allows the direct use of global exported assertions and QUnit.assert.*
-		// Although, it's use is not recommended as it can leak assertions
-		// to other tests from async tests, because we only get a reference to the current test,
-		// not exactly the test where assertion were intended to be called.
-		if ( !currentTest ) {
-			throw new Error( "assertion outside test context, in " + sourceFromStacktrace( 2 ) );
-		}
-
-		if ( currentTest.usedAsync === true && currentTest.semaphore === 0 ) {
-			currentTest.pushFailure( "Assertion after the final `assert.async` was resolved",
-				sourceFromStacktrace( 2 ) );
-
-			// Allow this assertion to continue running anyway...
-		}
-
-		if ( !( assert instanceof Assert ) ) {
-			assert = currentTest.assert;
-		}
-		return assert.test.push.apply( assert.test, arguments );
-	},
-
-	ok: function( result, message ) {
-		message = message || ( result ? "okay" : "failed, expected argument to be truthy, was: " +
-			QUnit.dump.parse( result ) );
-		this.push( !!result, result, true, message );
-	},
-
-	notOk: function( result, message ) {
-		message = message || ( !result ? "okay" : "failed, expected argument to be falsy, was: " +
-			QUnit.dump.parse( result ) );
-		this.push( !result, result, false, message );
-	},
-
-	equal: function( actual, expected, message ) {
-		/*jshint eqeqeq:false */
-		this.push( expected == actual, actual, expected, message );
-	},
-
-	notEqual: function( actual, expected, message ) {
-		/*jshint eqeqeq:false */
-		this.push( expected != actual, actual, expected, message );
-	},
-
-	propEqual: function( actual, expected, message ) {
-		actual = objectValues( actual );
-		expected = objectValues( expected );
-		this.push( QUnit.equiv( actual, expected ), actual, expected, message );
-	},
-
-	notPropEqual: function( actual, expected, message ) {
-		actual = objectValues( actual );
-		expected = objectValues( expected );
-		this.push( !QUnit.equiv( actual, expected ), actual, expected, message );
-	},
-
-	deepEqual: function( actual, expected, message ) {
-		this.push( QUnit.equiv( actual, expected ), actual, expected, message );
-	},
-
-	notDeepEqual: function( actual, expected, message ) {
-		this.push( !QUnit.equiv( actual, expected ), actual, expected, message );
-	},
-
-	strictEqual: function( actual, expected, message ) {
-		this.push( expected === actual, actual, expected, message );
-	},
-
-	notStrictEqual: function( actual, expected, message ) {
-		this.push( expected !== actual, actual, expected, message );
-	},
-
-	"throws": function( block, expected, message ) {
-		var actual, expectedType,
-			expectedOutput = expected,
-			ok = false,
-			currentTest = ( this instanceof Assert && this.test ) || QUnit.config.current;
-
-		// 'expected' is optional unless doing string comparison
-		if ( message == null && typeof expected === "string" ) {
-			message = expected;
-			expected = null;
-		}
-
-		currentTest.ignoreGlobalErrors = true;
-		try {
-			block.call( currentTest.testEnvironment );
-		} catch (e) {
-			actual = e;
-		}
-		currentTest.ignoreGlobalErrors = false;
-
-		if ( actual ) {
-			expectedType = QUnit.objectType( expected );
-
-			// we don't want to validate thrown error
-			if ( !expected ) {
-				ok = true;
-				expectedOutput = null;
-
-			// expected is a regexp
-			} else if ( expectedType === "regexp" ) {
-				ok = expected.test( errorString( actual ) );
-
-			// expected is a string
-			} else if ( expectedType === "string" ) {
-				ok = expected === errorString( actual );
-
-			// expected is a constructor, maybe an Error constructor
-			} else if ( expectedType === "function" && actual instanceof expected ) {
-				ok = true;
-
-			// expected is an Error object
-			} else if ( expectedType === "object" ) {
-				ok = actual instanceof expected.constructor &&
-					actual.name === expected.name &&
-					actual.message === expected.message;
-
-			// expected is a validation function which returns true if validation passed
-			} else if ( expectedType === "function" && expected.call( {}, actual ) === true ) {
-				expectedOutput = null;
-				ok = true;
-			}
-		}
-
-		currentTest.assert.push( ok, actual, expectedOutput, message );
-	}
-};
-
-// Provide an alternative to assert.throws(), for enviroments that consider throws a reserved word
-// Known to us are: Closure Compiler, Narwhal
-(function() {
-	/*jshint sub:true */
-	Assert.prototype.raises = Assert.prototype[ "throws" ];
-}());
-
-// Test for equality any JavaScript type.
-// Author: Philippe Rathé <[email protected]>
-QUnit.equiv = (function() {
-
-	// Call the o related callback with the given arguments.
-	function bindCallbacks( o, callbacks, args ) {
-		var prop = QUnit.objectType( o );
-		if ( prop ) {
-			if ( QUnit.objectType( callbacks[ prop ] ) === "function" ) {
-				return callbacks[ prop ].apply( callbacks, args );
-			} else {
-				return callbacks[ prop ]; // or undefined
-			}
-		}
-	}
-
-	// the real equiv function
-	var innerEquiv,
-
-		// stack to decide between skip/abort functions
-		callers = [],
-
-		// stack to avoiding loops from circular referencing
-		parents = [],
-		parentsB = [],
-
-		getProto = Object.getPrototypeOf || function( obj ) {
-			/* jshint camelcase: false, proto: true */
-			return obj.__proto__;
-		},
-		callbacks = (function() {
-
-			// for string, boolean, number and null
-			function useStrictEquality( b, a ) {
-
-				/*jshint eqeqeq:false */
-				if ( b instanceof a.constructor || a instanceof b.constructor ) {
-
-					// to catch short annotation VS 'new' annotation of a
-					// declaration
-					// e.g. var i = 1;
-					// var j = new Number(1);
-					return a == b;
-				} else {
-					return a === b;
-				}
-			}
-
-			return {
-				"string": useStrictEquality,
-				"boolean": useStrictEquality,
-				"number": useStrictEquality,
-				"null": useStrictEquality,
-				"undefined": useStrictEquality,
-
-				"nan": function( b ) {
-					return isNaN( b );
-				},
-
-				"date": function( b, a ) {
-					return QUnit.objectType( b ) === "date" && a.valueOf() === b.valueOf();
-				},
-
-				"regexp": function( b, a ) {
-					return QUnit.objectType( b ) === "regexp" &&
-
-						// the regex itself
-						a.source === b.source &&
-
-						// and its modifiers
-						a.global === b.global &&
-
-						// (gmi) ...
-						a.ignoreCase === b.ignoreCase &&
-						a.multiline === b.multiline &&
-						a.sticky === b.sticky;
-				},
-
-				// - skip when the property is a method of an instance (OOP)
-				// - abort otherwise,
-				// initial === would have catch identical references anyway
-				"function": function() {
-					var caller = callers[ callers.length - 1 ];
-					return caller !== Object && typeof caller !== "undefined";
-				},
-
-				"array": function( b, a ) {
-					var i, j, len, loop, aCircular, bCircular;
-
-					// b could be an object literal here
-					if ( QUnit.objectType( b ) !== "array" ) {
-						return false;
-					}
-
-					len = a.length;
-					if ( len !== b.length ) {
-						// safe and faster
-						return false;
-					}
-
-					// track reference to avoid circular references
-					parents.push( a );
-					parentsB.push( b );
-					for ( i = 0; i < len; i++ ) {
-						loop = false;
-						for ( j = 0; j < parents.length; j++ ) {
-							aCircular = parents[ j ] === a[ i ];
-							bCircular = parentsB[ j ] === b[ i ];
-							if ( aCircular || bCircular ) {
-								if ( a[ i ] === b[ i ] || aCircular && bCircular ) {
-									loop = true;
-								} else {
-									parents.pop();
-									parentsB.pop();
-									return false;
-								}
-							}
-						}
-						if ( !loop && !innerEquiv( a[ i ], b[ i ] ) ) {
-							parents.pop();
-							parentsB.pop();
-							return false;
-						}
-					}
-					parents.pop();
-					parentsB.pop();
-					return true;
-				},
-
-				"object": function( b, a ) {
-
-					/*jshint forin:false */
-					var i, j, loop, aCircular, bCircular,
-						// Default to true
-						eq = true,
-						aProperties = [],
-						bProperties = [];
-
-					// comparing constructors is more strict than using
-					// instanceof
-					if ( a.constructor !== b.constructor ) {
-
-						// Allow objects with no prototype to be equivalent to
-						// objects with Object as their constructor.
-						if ( !( ( getProto( a ) === null && getProto( b ) === Object.prototype ) ||
-							( getProto( b ) === null && getProto( a ) === Object.prototype ) ) ) {
-							return false;
-						}
-					}
-
-					// stack constructor before traversing properties
-					callers.push( a.constructor );
-
-					// track reference to avoid circular references
-					parents.push( a );
-					parentsB.push( b );
-
-					// be strict: don't ensure hasOwnProperty and go deep
-					for ( i in a ) {
-						loop = false;
-						for ( j = 0; j < parents.length; j++ ) {
-							aCircular = parents[ j ] === a[ i ];
-							bCircular = parentsB[ j ] === b[ i ];
-							if ( aCircular || bCircular ) {
-								if ( a[ i ] === b[ i ] || aCircular && bCircular ) {
-									loop = true;
-								} else {
-									eq = false;
-									break;
-								}
-							}
-						}
-						aProperties.push( i );
-						if ( !loop && !innerEquiv( a[ i ], b[ i ] ) ) {
-							eq = false;
-							break;
-						}
-					}
-
-					parents.pop();
-					parentsB.pop();
-					callers.pop(); // unstack, we are done
-
-					for ( i in b ) {
-						bProperties.push( i ); // collect b's properties
-					}
-
-					// Ensures identical properties name
-					return eq && innerEquiv( aProperties.sort(), bProperties.sort() );
-				}
-			};
-		}());
-
-	innerEquiv = function() { // can take multiple arguments
-		var args = [].slice.apply( arguments );
-		if ( args.length < 2 ) {
-			return true; // end transition
-		}
-
-		return ( (function( a, b ) {
-			if ( a === b ) {
-				return true; // catch the most you can
-			} else if ( a === null || b === null || typeof a === "undefined" ||
-					typeof b === "undefined" ||
-					QUnit.objectType( a ) !== QUnit.objectType( b ) ) {
-
-				// don't lose time with error prone cases
-				return false;
-			} else {
-				return bindCallbacks( a, callbacks, [ b, a ] );
-			}
-
-			// apply transition with (1..n) arguments
-		}( args[ 0 ], args[ 1 ] ) ) &&
-			innerEquiv.apply( this, args.splice( 1, args.length - 1 ) ) );
-	};
-
-	return innerEquiv;
-}());
-
-// Based on jsDump by Ariel Flesler
-// http://flesler.blogspot.com/2008/05/jsdump-pretty-dump-of-any-javascript.html
-QUnit.dump = (function() {
-	function quote( str ) {
-		return "\"" + str.toString().replace( /"/g, "\\\"" ) + "\"";
-	}
-	function literal( o ) {
-		return o + "";
-	}
-	function join( pre, arr, post ) {
-		var s = dump.separator(),
-			base = dump.indent(),
-			inner = dump.indent( 1 );
-		if ( arr.join ) {
-			arr = arr.join( "," + s + inner );
-		}
-		if ( !arr ) {
-			return pre + post;
-		}
-		return [ pre, inner + arr, base + post ].join( s );
-	}
-	function array( arr, stack ) {
-		var i = arr.length,
-			ret = new Array( i );
-
-		if ( dump.maxDepth && dump.depth > dump.maxDepth ) {
-			return "[object Array]";
-		}
-
-		this.up();
-		while ( i-- ) {
-			ret[ i ] = this.parse( arr[ i ], undefined, stack );
-		}
-		this.down();
-		return join( "[", ret, "]" );
-	}
-
-	var reName = /^function (\w+)/,
-		dump = {
-
-			// objType is used mostly internally, you can fix a (custom) type in advance
-			parse: function( obj, objType, stack ) {
-				stack = stack || [];
-				var res, parser, parserType,
-					inStack = inArray( obj, stack );
-
-				if ( inStack !== -1 ) {
-					return "recursion(" + ( inStack - stack.length ) + ")";
-				}
-
-				objType = objType || this.typeOf( obj  );
-				parser = this.parsers[ objType ];
-				parserType = typeof parser;
-
-				if ( parserType === "function" ) {
-					return;
-					stack.push( obj );
-					res = parser.call( this, obj, stack );
-					stack.pop();
-					return res;
-				}
-				return ( parserType === "string" ) ? parser : this.parsers.error;
-			},
-			typeOf: function( obj ) {
-				var type;
-				if ( obj === null ) {
-					type = "null";
-				} else if ( typeof obj === "undefined" ) {
-					type = "undefined";
-				} else if ( QUnit.is( "regexp", obj ) ) {
-					type = "regexp";
-				} else if ( QUnit.is( "date", obj ) ) {
-					type = "date";
-				} else if ( QUnit.is( "function", obj ) ) {
-					type = "function";
-				} else if ( obj.setInterval !== undefined &&
-						obj.document !== undefined &&
-						obj.nodeType === undefined ) {
-					type = "window";
-				} else if ( obj.nodeType === 9 ) {
-					type = "document";
-				} else if ( obj.nodeType ) {
-					type = "node";
-				} else if (
-
-					// native arrays
-					toString.call( obj ) === "[object Array]" ||
-
-					// NodeList objects
-					( typeof obj.length === "number" && obj.item !== undefined &&
-					( obj.length ? obj.item( 0 ) === obj[ 0 ] : ( obj.item( 0 ) === null &&
-					obj[ 0 ] === undefined ) ) )
-				) {
-					type = "array";
-				} else if ( obj.constructor === Error.prototype.constructor ) {
-					type = "error";
-				} else {
-					type = typeof obj;
-				}
-				return type;
-			},
-			separator: function() {
-				return this.multiline ? this.HTML ? "<br />" : "\n" : this.HTML ? "&#160;" : " ";
-			},
-			// extra can be a number, shortcut for increasing-calling-decreasing
-			indent: function( extra ) {
-				if ( !this.multiline ) {
-					return "";
-				}
-				var chr = this.indentChar;
-				if ( this.HTML ) {
-					chr = chr.replace( /\t/g, "   " ).replace( / /g, "&#160;" );
-				}
-				return new Array( this.depth + ( extra || 0 ) ).join( chr );
-			},
-			up: function( a ) {
-				this.depth += a || 1;
-			},
-			down: function( a ) {
-				this.depth -= a || 1;
-			},
-			setParser: function( name, parser ) {
-				this.parsers[ name ] = parser;
-			},
-			// The next 3 are exposed so you can use them
-			quote: quote,
-			literal: literal,
-			join: join,
-			//
-			depth: 1,
-			maxDepth: QUnit.config.maxDepth,
-
-			// This is the list of parsers, to modify them, use dump.setParser
-			parsers: {
-				window: "[Window]",
-				document: "[Document]",
-				error: function( error ) {
-					return "Error(\"" + error.message + "\")";
-				},
-				unknown: "[Unknown]",
-				"null": "null",
-				"undefined": "undefined",
-				"function": function( fn ) {
-					var ret = "function",
-
-						// functions never have name in IE
-						name = "name" in fn ? fn.name : ( reName.exec( fn ) || [] )[ 1 ];
-
-					if ( name ) {
-						ret += " " + name;
-					}
-					ret += "( ";
-
-					ret = [ ret, dump.parse( fn, "functionArgs" ), "){" ].join( "" );
-					return join( ret, dump.parse( fn, "functionCode" ), "}" );
-				},
-				array: array,
-				nodelist: array,
-				"arguments": array,
-				object: function( map, stack ) {
-					var keys, key, val, i, nonEnumerableProperties,
-						ret = [];
-
-					if ( dump.maxDepth && dump.depth > dump.maxDepth ) {
-						return "[object Object]";
-					}
-
-					dump.up();
-					keys = [];
-					for ( key in map ) {
-						keys.push( key );
-					}
-
-					// Some properties are not always enumerable on Error objects.
-					nonEnumerableProperties = [ "message", "name" ];
-					for ( i in nonEnumerableProperties ) {
-						key = nonEnumerableProperties[ i ];
-						if ( key in map && inArray( key, keys ) < 0 ) {
-							keys.push( key );
-						}
-					}
-					keys.sort();
-					for ( i = 0; i < keys.length; i++ ) {
-						key = keys[ i ];
-						val = map[ key ];
-						ret.push( dump.parse( key, "key" ) + ": " +
-							dump.parse( val, undefined, stack ) );
-					}
-					dump.down();
-					return join( "{", ret, "}" );
-				},
-				node: function( node ) {
-					var len, i, val,
-						open = dump.HTML ? "&lt;" : "<",
-						close = dump.HTML ? "&gt;" : ">",
-						tag = node.nodeName.toLowerCase(),
-						ret = open + tag,
-						attrs = node.attributes;
-
-					if ( attrs ) {
-						for ( i = 0, len = attrs.length; i < len; i++ ) {
-							val = attrs[ i ].nodeValue;
-
-							// IE6 includes all attributes in .attributes, even ones not explicitly
-							// set. Those have values like undefined, null, 0, false, "" or
-							// "inherit".
-							if ( val && val !== "inherit" ) {
-								ret += " " + attrs[ i ].nodeName + "=" +
-									dump.parse( val, "attribute" );
-							}
-						}
-					}
-					ret += close;
-
-					// Show content of TextNode or CDATASection
-					if ( node.nodeType === 3 || node.nodeType === 4 ) {
-						ret += node.nodeValue;
-					}
-
-					return ret + open + "/" + tag + close;
-				},
-
-				// function calls it internally, it's the arguments part of the function
-				functionArgs: function( fn ) {
-					var args,
-						l = fn.length;
-
-					if ( !l ) {
-						return "";
-					}
-
-					args = new Array( l );
-					while ( l-- ) {
-
-						// 97 is 'a'
-						args[ l ] = String.fromCharCode( 97 + l );
-					}
-					return " " + args.join( ", " ) + " ";
-				},
-				// object calls it internally, the key part of an item in a map
-				key: quote,
-				// function calls it internally, it's the content of the function
-				functionCode: "[code]",
-				// node calls it internally, it's an html attribute value
-				attribute: quote,
-				string: quote,
-				date: quote,
-				regexp: literal,
-				number: literal,
-				"boolean": literal
-			},
-			// if true, entities are escaped ( <, >, \t, space and \n )
-			HTML: false,
-			// indentation unit
-			indentChar: "  ",
-			// if true, items in a collection, are separated by a \n, else just a space.
-			multiline: true
-		};
-
-	return dump;
-}());
-
-// back compat
-QUnit.jsDump = QUnit.dump;
-
-// For browser, export only select globals
-if ( typeof window !== "undefined" ) {
-
-	// Deprecated
-	// Extend assert methods to QUnit and Global scope through Backwards compatibility
-	(function() {
-		var i,
-			assertions = Assert.prototype;
-
-		function applyCurrent( current ) {
-			return function() {
-				var assert = new Assert( QUnit.config.current );
-				current.apply( assert, arguments );
-			};
-		}
-
-		for ( i in assertions ) {
-			QUnit[ i ] = applyCurrent( assertions[ i ] );
-		}
-	})();
-
-	(function() {
-		var i, l,
-			keys = [
-				"test",
-				"module",
-				"expect",
-				"asyncTest",
-				"start",
-				"stop",
-				"ok",
-				"notOk",
-				"equal",
-				"notEqual",
-				"propEqual",
-				"notPropEqual",
-				"deepEqual",
-				"notDeepEqual",
-				"strictEqual",
-				"notStrictEqual",
-				"throws"
-			];
-
-		for ( i = 0, l = keys.length; i < l; i++ ) {
-			window[ keys[ i ] ] = QUnit[ keys[ i ] ];
-		}
-	})();
-
-	window.QUnit = QUnit;
-}
-
-// For nodejs
-if ( typeof module !== "undefined" && module && module.exports ) {
-	module.exports = QUnit;
-
-	// For consistency with CommonJS environments' exports
-	module.exports.QUnit = QUnit;
-}
-
-// For CommonJS with exports, but without module.exports, like Rhino
-if ( typeof exports !== "undefined" && exports ) {
-	exports.QUnit = QUnit;
-}
-
-if ( typeof define === "function" && define.amd ) {
-	define( function() {
-		return QUnit;
-	} );
-	QUnit.config.autostart = false;
-}
-
-// Get a reference to the global object, like window in browsers
-}( (function() {
-	return this;
-})() ));
-
-/*istanbul ignore next */
-// jscs:disable maximumLineLength
-/*
- * This file is a modified version of google-diff-match-patch's JavaScript implementation
- * (https://code.google.com/p/google-diff-match-patch/source/browse/trunk/javascript/diff_match_patch_uncompressed.js),
- * modifications are licensed as more fully set forth in LICENSE.txt.
- *
- * The original source of google-diff-match-patch is attributable and licensed as follows:
- *
- * Copyright 2006 Google Inc.
- * http://code.google.com/p/google-diff-match-patch/
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- * More Info:
- *  https://code.google.com/p/google-diff-match-patch/
- *
- * Usage: QUnit.diff(expected, actual)
- *
- * QUnit.diff( "the quick brown fox jumped over", "the quick fox jumps over" ) === "the  quick <del>brown </del> fox jump<ins>s</ins><del>ed</del over"
- */
-QUnit.diff = (function() {
-
-    function DiffMatchPatch() {
-
-        // Defaults.
-        // Redefine these in your program to override the defaults.
-
-        // Number of seconds to map a diff before giving up (0 for infinity).
-        this.DiffTimeout = 1.0;
-        // Cost of an empty edit operation in terms of edit characters.
-        this.DiffEditCost = 4;
-    }
-
-    //  DIFF FUNCTIONS
-
-    /**
-     * The data structure representing a diff is an array of tuples:
-     * [[DIFF_DELETE, 'Hello'], [DIFF_INSERT, 'Goodbye'], [DIFF_EQUAL, ' world.']]
-     * which means: delete 'Hello', add 'Goodbye' and keep ' world.'
-     */
-    var DIFF_DELETE = -1,
-		DIFF_INSERT = 1,
-		DIFF_EQUAL = 0;
-
-    /**
-     * Find the differences between two texts.  Simplifies the problem by stripping
-     * any common prefix or suffix off the texts before diffing.
-     * @param {string} text1 Old string to be diffed.
-     * @param {string} text2 New string to be diffed.
-     * @param {boolean=} optChecklines Optional speedup flag. If present and false,
-     *     then don't run a line-level diff first to identify the changed areas.
-     *     Defaults to true, which does a faster, slightly less optimal diff.
-     * @param {number} optDeadline Optional time when the diff should be complete
-     *     by.  Used internally for recursive calls.  Users should set DiffTimeout
-     *     instead.
-     * @return {!Array.<!DiffMatchPatch.Diff>} Array of diff tuples.
-     */
-    DiffMatchPatch.prototype.DiffMain = function( text1, text2, optChecklines, optDeadline ) {
-        var deadline, checklines, commonlength,
-			commonprefix, commonsuffix, diffs;
-        // Set a deadline by which time the diff must be complete.
-        if ( typeof optDeadline === "undefined" ) {
-            if ( this.DiffTimeout <= 0 ) {
-                optDeadline = Number.MAX_VALUE;
-            } else {
-                optDeadline = ( new Date() ).getTime() + this.DiffTimeout * 1000;
-            }
-        }
-        deadline = optDeadline;
-
-        // Check for null inputs.
-        if ( text1 === null || text2 === null ) {
-            throw new Error( "Null input. (DiffMain)" );
-        }
-
-        // Check for equality (speedup).
-        if ( text1 === text2 ) {
-            if ( text1 ) {
-                return [
-                    [ DIFF_EQUAL, text1 ]
-                ];
-            }
-            return [];
-        }
-
-        if ( typeof optChecklines === "undefined" ) {
-            optChecklines = true;
-        }
-
-        checklines = optChecklines;
-
-        // Trim off common prefix (speedup).
-        commonlength = this.diffCommonPrefix( text1, text2 );
-        commonprefix = text1.substring( 0, commonlength );
-        text1 = text1.substring( commonlength );
-        text2 = text2.substring( commonlength );
-
-        // Trim off common suffix (speedup).
-        /////////
-        commonlength = this.diffCommonSuffix( text1, text2 );
-        commonsuffix = text1.substring( text1.length - commonlength );
-        text1 = text1.substring( 0, text1.length - commonlength );
-        text2 = text2.substring( 0, text2.length - commonlength );
-
-        // Compute the diff on the middle block.
-        diffs = this.diffCompute( text1, text2, checklines, deadline );
-
-        // Restore the prefix and suffix.
-        if ( commonprefix ) {
-            diffs.unshift( [ DIFF_EQUAL, commonprefix ] );
-        }
-        if ( commonsuffix ) {
-            diffs.push( [ DIFF_EQUAL, commonsuffix ] );
-        }
-        this.diffCleanupMerge( diffs );
-        return diffs;
-    };
-
-    /**
-     * Reduce the number of edits by eliminating operationally trivial equalities.
-     * @param {!Array.<!DiffMatchPatch.Diff>} diffs Array of diff tuples.
-     */
-    DiffMatchPatch.prototype.diffCleanupEfficiency = function( diffs ) {
-        var changes, equalities, equalitiesLength, lastequality,
-			pointer, preIns, preDel, postIns, postDel;
-        changes = false;
-        equalities = []; // Stack of indices where equalities are found.
-        equalitiesLength = 0; // Keeping our own length var is faster in JS.
-        /** @type {?string} */
-        lastequality = null;
-        // Always equal to diffs[equalities[equalitiesLength - 1]][1]
-        pointer = 0; // Index of current position.
-        // Is there an insertion operation before the last equality.
-        preIns = false;
-        // Is there a deletion operation before the last equality.
-        preDel = false;
-        // Is there an insertion operation after the last equality.
-        postIns = false;
-        // Is there a deletion operation after the last equality.
-        postDel = false;
-        while ( pointer < diffs.length ) {
-            if ( diffs[ pointer ][ 0 ] === DIFF_EQUAL ) { // Equality found.
-                if ( diffs[ pointer ][ 1 ].length < this.DiffEditCost && ( postIns || postDel ) ) {
-                    // Candidate found.
-                    equalities[ equalitiesLength++ ] = pointer;
-                    preIns = postIns;
-                    preDel = postDel;
-                    lastequality = diffs[ pointer ][ 1 ];
-                } else {
-                    // Not a candidate, and can never become one.
-                    equalitiesLength = 0;
-                    lastequality = null;
-                }
-                postIns = postDel = false;
-            } else { // An insertion or deletion.
-                if ( diffs[ pointer ][ 0 ] === DIFF_DELETE ) {
-                    postDel = true;
-                } else {
-                    postIns = true;
-                }
-                /*
-                 * Five types to be split:
-                 * <ins>A</ins><del>B</del>XY<ins>C</ins><del>D</del>
-                 * <ins>A</ins>X<ins>C</ins><del>D</del>
-                 * <ins>A</ins><del>B</del>X<ins>C</ins>
-                 * <ins>A</del>X<ins>C</ins><del>D</del>
-                 * <ins>A</ins><del>B</del>X<del>C</del>
-                 */
-                if ( lastequality && ( ( preIns && preDel && postIns && postDel ) ||
-                        ( ( lastequality.length < this.DiffEditCost / 2 ) &&
-                            ( preIns + preDel + postIns + postDel ) === 3 ) ) ) {
-                    // Duplicate record.
-                    diffs.splice( equalities[equalitiesLength - 1], 0, [ DIFF_DELETE, lastequality ] );
-                    // Change second copy to insert.
-                    diffs[ equalities[ equalitiesLength - 1 ] + 1 ][ 0 ] = DIFF_INSERT;
-                    equalitiesLength--; // Throw away the equality we just deleted;
-                    lastequality = null;
-                    if (preIns && preDel) {
-                        // No changes made which could affect previous entry, keep going.
-                        postIns = postDel = true;
-                        equalitiesLength = 0;
-                    } else {
-                        equalitiesLength--; // Throw away the previous equality.
-                        pointer = equalitiesLength > 0 ? equalities[ equalitiesLength - 1 ] : -1;
-                        postIns = postDel = false;
-                    }
-                    changes = true;
-                }
-            }
-            pointer++;
-        }
-
-        if ( changes ) {
-            this.diffCleanupMerge( diffs );
-        }
-    };
-
-    /**
-     * Convert a diff array into a pretty HTML report.
-     * @param {!Array.<!DiffMatchPatch.Diff>} diffs Array of diff tuples.
-     * @param {integer} string to be beautified.
-     * @return {string} HTML representation.
-     */
-    DiffMatchPatch.prototype.diffPrettyHtml = function( diffs ) {
-        var op, data, x, html = [];
-        for ( x = 0; x < diffs.length; x++ ) {
-            op = diffs[x][0]; // Operation (insert, delete, equal)
-            data = diffs[x][1]; // Text of change.
-            switch ( op ) {
-                case DIFF_INSERT:
-                    html[x] = "<ins>" + data + "</ins>";
-                    break;
-                case DIFF_DELETE:
-                    html[x] = "<del>" + data + "</del>";
-                    break;
-                case DIFF_EQUAL:
-                    html[x] = "<span>" + data + "</span>";
-                    break;
-            }
-        }
-        return html.join("");
-    };
-
-    /**
-     * Determine the common prefix of two strings.
-     * @param {string} text1 First string.
-     * @param {string} text2 Second string.
-     * @return {number} The number of characters common to the start of each
-     *     string.
-     */
-    DiffMatchPatch.prototype.diffCommonPrefix = function( text1, text2 ) {
-        var pointermid, pointermax, pointermin, pointerstart;
-        // Quick check for common null cases.
-        if ( !text1 || !text2 || text1.charAt(0) !== text2.charAt(0) ) {
-            return 0;
-        }
-        // Binary search.
-        // Performance analysis: http://neil.fraser.name/news/2007/10/09/
-        pointermin = 0;
-        pointermax = Math.min( text1.length, text2.length );
-        pointermid = pointermax;
-        pointerstart = 0;
-        while ( pointermin < pointermid ) {
-            if ( text1.substring( pointerstart, pointermid ) === text2.substring( pointerstart, pointermid ) ) {
-                pointermin = pointermid;
-                pointerstart = pointermin;
-            } else {
-                pointermax = pointermid;
-            }
-            pointermid = Math.floor( ( pointermax - pointermin ) / 2 + pointermin );
-        }
-        return pointermid;
-    };
-
-    /**
-     * Determine the common suffix of two strings.
-     * @param {string} text1 First string.
-     * @param {string} text2 Second string.
-     * @return {number} The number of characters common to the end of each string.
-     */
-    DiffMatchPatch.prototype.diffCommonSuffix = function( text1, text2 ) {
-        var pointermid, pointermax, pointermin, pointerend;
-        // Quick check for common null cases.
-        if (!text1 || !text2 || text1.charAt(text1.length - 1) !== text2.charAt(text2.length - 1)) {
-            return 0;
-        }
-        // Binary search.
-        // Performance analysis: http://neil.fraser.name/news/2007/10/09/
-        pointermin = 0;
-        pointermax = Math.min(text1.length, text2.length);
-        pointermid = pointermax;
-        pointerend = 0;
-        while ( pointermin < pointermid ) {
-            if (text1.substring( text1.length - pointermid, text1.length - pointerend ) ===
-                text2.substring( text2.length - pointermid, text2.length - pointerend ) ) {
-                pointermin = pointermid;
-                pointerend = pointermin;
-            } else {
-                pointermax = pointermid;
-            }
-            pointermid = Math.floor( ( pointermax - pointermin ) / 2 + pointermin );
-        }
-        return pointermid;
-    };
-
-    /**
-     * Find the differences between two texts.  Assumes that the texts do not
-     * have any common prefix or suffix.
-     * @param {string} text1 Old string to be diffed.
-     * @param {string} text2 New string to be diffed.
-     * @param {boolean} checklines Speedup flag.  If false, then don't run a
-     *     line-level diff first to identify the changed areas.
-     *     If true, then run a faster, slightly less optimal diff.
-     * @param {number} deadline Time when the diff should be complete by.
-     * @return {!Array.<!DiffMatchPatch.Diff>} Array of diff tuples.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffCompute = function( text1, text2, checklines, deadline ) {
-        var diffs, longtext, shorttext, i, hm,
-			text1A, text2A, text1B, text2B,
-			midCommon, diffsA, diffsB;
-
-        if ( !text1 ) {
-            // Just add some text (speedup).
-            return [
-                [ DIFF_INSERT, text2 ]
-            ];
-        }
-
-        if (!text2) {
-            // Just delete some text (speedup).
-            return [
-                [ DIFF_DELETE, text1 ]
-            ];
-        }
-
-        longtext = text1.length > text2.length ? text1 : text2;
-        shorttext = text1.length > text2.length ? text2 : text1;
-        i = longtext.indexOf( shorttext );
-        if ( i !== -1 ) {
-            // Shorter text is inside the longer text (speedup).
-            diffs = [
-                [ DIFF_INSERT, longtext.substring( 0, i ) ],
-                [ DIFF_EQUAL, shorttext ],
-                [ DIFF_INSERT, longtext.substring( i + shorttext.length ) ]
-            ];
-            // Swap insertions for deletions if diff is reversed.
-            if ( text1.length > text2.length ) {
-                diffs[0][0] = diffs[2][0] = DIFF_DELETE;
-            }
-            return diffs;
-        }
-
-        if ( shorttext.length === 1 ) {
-            // Single character string.
-            // After the previous speedup, the character can't be an equality.
-            return [
-                [ DIFF_DELETE, text1 ],
-                [ DIFF_INSERT, text2 ]
-            ];
-        }
-
-        // Check to see if the problem can be split in two.
-        hm = this.diffHalfMatch(text1, text2);
-        if (hm) {
-            // A half-match was found, sort out the return data.
-            text1A = hm[0];
-            text1B = hm[1];
-            text2A = hm[2];
-            text2B = hm[3];
-            midCommon = hm[4];
-            // Send both pairs off for separate processing.
-            diffsA = this.DiffMain(text1A, text2A, checklines, deadline);
-            diffsB = this.DiffMain(text1B, text2B, checklines, deadline);
-            // Merge the results.
-            return diffsA.concat([
-                [ DIFF_EQUAL, midCommon ]
-            ], diffsB);
-        }
-
-        if (checklines && text1.length > 100 && text2.length > 100) {
-            return this.diffLineMode(text1, text2, deadline);
-        }
-
-        return this.diffBisect(text1, text2, deadline);
-    };
-
-    /**
-     * Do the two texts share a substring which is at least half the length of the
-     * longer text?
-     * This speedup can produce non-minimal diffs.
-     * @param {string} text1 First string.
-     * @param {string} text2 Second string.
-     * @return {Array.<string>} Five element Array, containing the prefix of
-     *     text1, the suffix of text1, the prefix of text2, the suffix of
-     *     text2 and the common middle.  Or null if there was no match.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffHalfMatch = function(text1, text2) {
-        var longtext, shorttext, dmp,
-			text1A, text2B, text2A, text1B, midCommon,
-			hm1, hm2, hm;
-        if (this.DiffTimeout <= 0) {
-            // Don't risk returning a non-optimal diff if we have unlimited time.
-            return null;
-        }
-        longtext = text1.length > text2.length ? text1 : text2;
-        shorttext = text1.length > text2.length ? text2 : text1;
-        if (longtext.length < 4 || shorttext.length * 2 < longtext.length) {
-            return null; // Pointless.
-        }
-        dmp = this; // 'this' becomes 'window' in a closure.
-
-        /**
-         * Does a substring of shorttext exist within longtext such that the substring
-         * is at least half the length of longtext?
-         * Closure, but does not reference any external variables.
-         * @param {string} longtext Longer string.
-         * @param {string} shorttext Shorter string.
-         * @param {number} i Start index of quarter length substring within longtext.
-         * @return {Array.<string>} Five element Array, containing the prefix of
-         *     longtext, the suffix of longtext, the prefix of shorttext, the suffix
-         *     of shorttext and the common middle.  Or null if there was no match.
-         * @private
-         */
-        function diffHalfMatchI(longtext, shorttext, i) {
-            var seed, j, bestCommon, prefixLength, suffixLength,
-				bestLongtextA, bestLongtextB, bestShorttextA, bestShorttextB;
-            // Start with a 1/4 length substring at position i as a seed.
-            seed = longtext.substring(i, i + Math.floor(longtext.length / 4));
-            j = -1;
-            bestCommon = "";
-            while ((j = shorttext.indexOf(seed, j + 1)) !== -1) {
-                prefixLength = dmp.diffCommonPrefix(longtext.substring(i),
-                    shorttext.substring(j));
-                suffixLength = dmp.diffCommonSuffix(longtext.substring(0, i),
-                    shorttext.substring(0, j));
-                if (bestCommon.length < suffixLength + prefixLength) {
-                    bestCommon = shorttext.substring(j - suffixLength, j) +
-                        shorttext.substring(j, j + prefixLength);
-                    bestLongtextA = longtext.substring(0, i - suffixLength);
-                    bestLongtextB = longtext.substring(i + prefixLength);
-                    bestShorttextA = shorttext.substring(0, j - suffixLength);
-                    bestShorttextB = shorttext.substring(j + prefixLength);
-                }
-            }
-            if (bestCommon.length * 2 >= longtext.length) {
-                return [ bestLongtextA, bestLongtextB,
-                    bestShorttextA, bestShorttextB, bestCommon
-                ];
-            } else {
-                return null;
-            }
-        }
-
-        // First check if the second quarter is the seed for a half-match.
-        hm1 = diffHalfMatchI(longtext, shorttext,
-            Math.ceil(longtext.length / 4));
-        // Check again based on the third quarter.
-        hm2 = diffHalfMatchI(longtext, shorttext,
-            Math.ceil(longtext.length / 2));
-        if (!hm1 && !hm2) {
-            return null;
-        } else if (!hm2) {
-            hm = hm1;
-        } else if (!hm1) {
-            hm = hm2;
-        } else {
-            // Both matched.  Select the longest.
-            hm = hm1[4].length > hm2[4].length ? hm1 : hm2;
-        }
-
-        // A half-match was found, sort out the return data.
-        text1A, text1B, text2A, text2B;
-        if (text1.length > text2.length) {
-            text1A = hm[0];
-            text1B = hm[1];
-            text2A = hm[2];
-            text2B = hm[3];
-        } else {
-            text2A = hm[0];
-            text2B = hm[1];
-            text1A = hm[2];
-            text1B = hm[3];
-        }
-        midCommon = hm[4];
-        return [ text1A, text1B, text2A, text2B, midCommon ];
-    };
-
-    /**
-     * Do a quick line-level diff on both strings, then rediff the parts for
-     * greater accuracy.
-     * This speedup can produce non-minimal diffs.
-     * @param {string} text1 Old string to be diffed.
-     * @param {string} text2 New string to be diffed.
-     * @param {number} deadline Time when the diff should be complete by.
-     * @return {!Array.<!DiffMatchPatch.Diff>} Array of diff tuples.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffLineMode = function(text1, text2, deadline) {
-        var a, diffs, linearray, pointer, countInsert,
-			countDelete, textInsert, textDelete, j;
-        // Scan the text on a line-by-line basis first.
-        a = this.diffLinesToChars(text1, text2);
-        text1 = a.chars1;
-        text2 = a.chars2;
-        linearray = a.lineArray;
-
-        diffs = this.DiffMain(text1, text2, false, deadline);
-
-        // Convert the diff back to original text.
-        this.diffCharsToLines(diffs, linearray);
-        // Eliminate freak matches (e.g. blank lines)
-        this.diffCleanupSemantic(diffs);
-
-        // Rediff any replacement blocks, this time character-by-character.
-        // Add a dummy entry at the end.
-        diffs.push( [ DIFF_EQUAL, "" ] );
-        pointer = 0;
-        countDelete = 0;
-        countInsert = 0;
-        textDelete = "";
-        textInsert = "";
-        while (pointer < diffs.length) {
-            switch ( diffs[pointer][0] ) {
-                case DIFF_INSERT:
-                    countInsert++;
-                    textInsert += diffs[pointer][1];
-                    break;
-                case DIFF_DELETE:
-                    countDelete++;
-                    textDelete += diffs[pointer][1];
-                    break;
-                case DIFF_EQUAL:
-                    // Upon reaching an equality, check for prior redundancies.
-                    if (countDelete >= 1 && countInsert >= 1) {
-                        // Delete the offending records and add the merged ones.
-                        diffs.splice(pointer - countDelete - countInsert,
-                            countDelete + countInsert);
-                        pointer = pointer - countDelete - countInsert;
-                        a = this.DiffMain(textDelete, textInsert, false, deadline);
-                        for (j = a.length - 1; j >= 0; j--) {
-                            diffs.splice( pointer, 0, a[j] );
-                        }
-                        pointer = pointer + a.length;
-                    }
-                    countInsert = 0;
-                    countDelete = 0;
-                    textDelete = "";
-                    textInsert = "";
-                    break;
-            }
-            pointer++;
-        }
-        diffs.pop(); // Remove the dummy entry at the end.
-
-        return diffs;
-    };
-
-    /**
-     * Find the 'middle snake' of a diff, split the problem in two
-     * and return the recursively constructed diff.
-     * See Myers 1986 paper: An O(ND) Difference Algorithm and Its Variations.
-     * @param {string} text1 Old string to be diffed.
-     * @param {string} text2 New string to be diffed.
-     * @param {number} deadline Time at which to bail if not yet complete.
-     * @return {!Array.<!DiffMatchPatch.Diff>} Array of diff tuples.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffBisect = function(text1, text2, deadline) {
-        var text1Length, text2Length, maxD, vOffset, vLength,
-			v1, v2, x, delta, front, k1start, k1end, k2start,
-			k2end, k2Offset, k1Offset, x1, x2, y1, y2, d, k1, k2;
-        // Cache the text lengths to prevent multiple calls.
-        text1Length = text1.length;
-        text2Length = text2.length;
-        maxD = Math.ceil((text1Length + text2Length) / 2);
-        vOffset = maxD;
-        vLength = 2 * maxD;
-        v1 = new Array(vLength);
-        v2 = new Array(vLength);
-        // Setting all elements to -1 is faster in Chrome & Firefox than mixing
-        // integers and undefined.
-        for (x = 0; x < vLength; x++) {
-            v1[x] = -1;
-            v2[x] = -1;
-        }
-        v1[vOffset + 1] = 0;
-        v2[vOffset + 1] = 0;
-        delta = text1Length - text2Length;
-        // If the total number of characters is odd, then the front path will collide
-        // with the reverse path.
-        front = (delta % 2 !== 0);
-        // Offsets for start and end of k loop.
-        // Prevents mapping of space beyond the grid.
-        k1start = 0;
-        k1end = 0;
-        k2start = 0;
-        k2end = 0;
-        for (d = 0; d < maxD; d++) {
-            // Bail out if deadline is reached.
-            if ((new Date()).getTime() > deadline) {
-                break;
-            }
-
-            // Walk the front path one step.
-            for (k1 = -d + k1start; k1 <= d - k1end; k1 += 2) {
-                k1Offset = vOffset + k1;
-                if ( k1 === -d || ( k1 !== d && v1[ k1Offset - 1 ] < v1[ k1Offset + 1 ] ) ) {
-                    x1 = v1[k1Offset + 1];
-                } else {
-                    x1 = v1[k1Offset - 1] + 1;
-                }
-                y1 = x1 - k1;
-                while (x1 < text1Length && y1 < text2Length &&
-                    text1.charAt(x1) === text2.charAt(y1)) {
-                    x1++;
-                    y1++;
-                }
-                v1[k1Offset] = x1;
-                if (x1 > text1Length) {
-                    // Ran off the right of the graph.
-                    k1end += 2;
-                } else if (y1 > text2Length) {
-                    // Ran off the bottom of the graph.
-                    k1start += 2;
-                } else if (front) {
-                    k2Offset = vOffset + delta - k1;
-                    if (k2Offset >= 0 && k2Offset < vLength && v2[k2Offset] !== -1) {
-                        // Mirror x2 onto top-left coordinate system.
-                        x2 = text1Length - v2[k2Offset];
-                        if (x1 >= x2) {
-                            // Overlap detected.
-                            return this.diffBisectSplit(text1, text2, x1, y1, deadline);
-                        }
-                    }
-                }
-            }
-
-            // Walk the reverse path one step.
-            for (k2 = -d + k2start; k2 <= d - k2end; k2 += 2) {
-                k2Offset = vOffset + k2;
-                if ( k2 === -d || (k2 !== d && v2[ k2Offset - 1 ] < v2[ k2Offset + 1 ] ) ) {
-                    x2 = v2[k2Offset + 1];
-                } else {
-                    x2 = v2[k2Offset - 1] + 1;
-                }
-                y2 = x2 - k2;
-                while (x2 < text1Length && y2 < text2Length &&
-                    text1.charAt(text1Length - x2 - 1) ===
-                    text2.charAt(text2Length - y2 - 1)) {
-                    x2++;
-                    y2++;
-                }
-                v2[k2Offset] = x2;
-                if (x2 > text1Length) {
-                    // Ran off the left of the graph.
-                    k2end += 2;
-                } else if (y2 > text2Length) {
-                    // Ran off the top of the graph.
-                    k2start += 2;
-                } else if (!front) {
-                    k1Offset = vOffset + delta - k2;
-                    if (k1Offset >= 0 && k1Offset < vLength && v1[k1Offset] !== -1) {
-                        x1 = v1[k1Offset];
-                        y1 = vOffset + x1 - k1Offset;
-                        // Mirror x2 onto top-left coordinate system.
-                        x2 = text1Length - x2;
-                        if (x1 >= x2) {
-                            // Overlap detected.
-                            return this.diffBisectSplit(text1, text2, x1, y1, deadline);
-                        }
-                    }
-                }
-            }
-        }
-        // Diff took too long and hit the deadline or
-        // number of diffs equals number of characters, no commonality at all.
-        return [
-            [ DIFF_DELETE, text1 ],
-            [ DIFF_INSERT, text2 ]
-        ];
-    };
-
-    /**
-     * Given the location of the 'middle snake', split the diff in two parts
-     * and recurse.
-     * @param {string} text1 Old string to be diffed.
-     * @param {string} text2 New string to be diffed.
-     * @param {number} x Index of split point in text1.
-     * @param {number} y Index of split point in text2.
-     * @param {number} deadline Time at which to bail if not yet complete.
-     * @return {!Array.<!DiffMatchPatch.Diff>} Array of diff tuples.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffBisectSplit = function( text1, text2, x, y, deadline ) {
-        var text1a, text1b, text2a, text2b, diffs, diffsb;
-        text1a = text1.substring(0, x);
-        text2a = text2.substring(0, y);
-        text1b = text1.substring(x);
-        text2b = text2.substring(y);
-
-        // Compute both diffs serially.
-        diffs = this.DiffMain(text1a, text2a, false, deadline);
-        diffsb = this.DiffMain(text1b, text2b, false, deadline);
-
-        return diffs.concat(diffsb);
-    };
-
-    /**
-     * Reduce the number of edits by eliminating semantically trivial equalities.
-     * @param {!Array.<!DiffMatchPatch.Diff>} diffs Array of diff tuples.
-     */
-    DiffMatchPatch.prototype.diffCleanupSemantic = function(diffs) {
-        var changes, equalities, equalitiesLength, lastequality,
-			pointer, lengthInsertions2, lengthDeletions2, lengthInsertions1,
-			lengthDeletions1, deletion, insertion, overlapLength1, overlapLength2;
-        changes = false;
-        equalities = []; // Stack of indices where equalities are found.
-        equalitiesLength = 0; // Keeping our own length var is faster in JS.
-        /** @type {?string} */
-        lastequality = null;
-        // Always equal to diffs[equalities[equalitiesLength - 1]][1]
-        pointer = 0; // Index of current position.
-        // Number of characters that changed prior to the equality.
-        lengthInsertions1 = 0;
-        lengthDeletions1 = 0;
-        // Number of characters that changed after the equality.
-        lengthInsertions2 = 0;
-        lengthDeletions2 = 0;
-        while (pointer < diffs.length) {
-            if (diffs[pointer][0] === DIFF_EQUAL) { // Equality found.
-                equalities[equalitiesLength++] = pointer;
-                lengthInsertions1 = lengthInsertions2;
-                lengthDeletions1 = lengthDeletions2;
-                lengthInsertions2 = 0;
-                lengthDeletions2 = 0;
-                lastequality = diffs[pointer][1];
-            } else { // An insertion or deletion.
-                if (diffs[pointer][0] === DIFF_INSERT) {
-                    lengthInsertions2 += diffs[pointer][1].length;
-                } else {
-                    lengthDeletions2 += diffs[pointer][1].length;
-                }
-                // Eliminate an equality that is smaller or equal to the edits on both
-                // sides of it.
-                if (lastequality && (lastequality.length <=
-                        Math.max(lengthInsertions1, lengthDeletions1)) &&
-                    (lastequality.length <= Math.max(lengthInsertions2,
-                        lengthDeletions2))) {
-                    // Duplicate record.
-                    diffs.splice( equalities[ equalitiesLength - 1 ], 0, [ DIFF_DELETE, lastequality ] );
-                    // Change second copy to insert.
-                    diffs[equalities[equalitiesLength - 1] + 1][0] = DIFF_INSERT;
-                    // Throw away the equality we just deleted.
-                    equalitiesLength--;
-                    // Throw away the previous equality (it needs to be reevaluated).
-                    equalitiesLength--;
-                    pointer = equalitiesLength > 0 ? equalities[equalitiesLength - 1] : -1;
-                    lengthInsertions1 = 0; // Reset the counters.
-                    lengthDeletions1 = 0;
-                    lengthInsertions2 = 0;
-                    lengthDeletions2 = 0;
-                    lastequality = null;
-                    changes = true;
-                }
-            }
-            pointer++;
-        }
-
-        // Normalize the diff.
-        if (changes) {
-            this.diffCleanupMerge(diffs);
-        }
-
-        // Find any overlaps between deletions and insertions.
-        // e.g: <del>abcxxx</del><ins>xxxdef</ins>
-        //   -> <del>abc</del>xxx<ins>def</ins>
-        // e.g: <del>xxxabc</del><ins>defxxx</ins>
-        //   -> <ins>def</ins>xxx<del>abc</del>
-        // Only extract an overlap if it is as big as the edit ahead or behind it.
-        pointer = 1;
-        while (pointer < diffs.length) {
-            if (diffs[pointer - 1][0] === DIFF_DELETE &&
-                diffs[pointer][0] === DIFF_INSERT) {
-                deletion = diffs[pointer - 1][1];
-                insertion = diffs[pointer][1];
-                overlapLength1 = this.diffCommonOverlap(deletion, insertion);
-                overlapLength2 = this.diffCommonOverlap(insertion, deletion);
-                if (overlapLength1 >= overlapLength2) {
-                    if (overlapLength1 >= deletion.length / 2 ||
-                        overlapLength1 >= insertion.length / 2) {
-                        // Overlap found.  Insert an equality and trim the surrounding edits.
-                        diffs.splice( pointer, 0, [ DIFF_EQUAL, insertion.substring( 0, overlapLength1 ) ] );
-                        diffs[pointer - 1][1] =
-                            deletion.substring(0, deletion.length - overlapLength1);
-                        diffs[pointer + 1][1] = insertion.substring(overlapLength1);
-                        pointer++;
-                    }
-                } else {
-                    if (overlapLength2 >= deletion.length / 2 ||
-                        overlapLength2 >= insertion.length / 2) {
-                        // Reverse overlap found.
-                        // Insert an equality and swap and trim the surrounding edits.
-                        diffs.splice( pointer, 0, [ DIFF_EQUAL, deletion.substring( 0, overlapLength2 ) ] );
-                        diffs[pointer - 1][0] = DIFF_INSERT;
-                        diffs[pointer - 1][1] =
-                            insertion.substring(0, insertion.length - overlapLength2);
-                        diffs[pointer + 1][0] = DIFF_DELETE;
-                        diffs[pointer + 1][1] =
-                            deletion.substring(overlapLength2);
-                        pointer++;
-                    }
-                }
-                pointer++;
-            }
-            pointer++;
-        }
-    };
-
-    /**
-     * Determine if the suffix of one string is the prefix of another.
-     * @param {string} text1 First string.
-     * @param {string} text2 Second string.
-     * @return {number} The number of characters common to the end of the first
-     *     string and the start of the second string.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffCommonOverlap = function(text1, text2) {
-        var text1Length, text2Length, textLength,
-			best, length, pattern, found;
-        // Cache the text lengths to prevent multiple calls.
-        text1Length = text1.length;
-        text2Length = text2.length;
-        // Eliminate the null case.
-        if (text1Length === 0 || text2Length === 0) {
-            return 0;
-        }
-        // Truncate the longer string.
-        if (text1Length > text2Length) {
-            text1 = text1.substring(text1Length - text2Length);
-        } else if (text1Length < text2Length) {
-            text2 = text2.substring(0, text1Length);
-        }
-        textLength = Math.min(text1Length, text2Length);
-        // Quick check for the worst case.
-        if (text1 === text2) {
-            return textLength;
-        }
-
-        // Start by looking for a single character match
-        // and increase length until no match is found.
-        // Performance analysis: http://neil.fraser.name/news/2010/11/04/
-        best = 0;
-        length = 1;
-        while (true) {
-            pattern = text1.substring(textLength - length);
-            found = text2.indexOf(pattern);
-            if (found === -1) {
-                return best;
-            }
-            length += found;
-            if (found === 0 || text1.substring(textLength - length) ===
-                text2.substring(0, length)) {
-                best = length;
-                length++;
-            }
-        }
-    };
-
-    /**
-     * Split two texts into an array of strings.  Reduce the texts to a string of
-     * hashes where each Unicode character represents one line.
-     * @param {string} text1 First string.
-     * @param {string} text2 Second string.
-     * @return {{chars1: string, chars2: string, lineArray: !Array.<string>}}
-     *     An object containing the encoded text1, the encoded text2 and
-     *     the array of unique strings.
-     *     The zeroth element of the array of unique strings is intentionally blank.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffLinesToChars = function(text1, text2) {
-        var lineArray, lineHash, chars1, chars2;
-        lineArray = []; // e.g. lineArray[4] === 'Hello\n'
-        lineHash = {}; // e.g. lineHash['Hello\n'] === 4
-
-        // '\x00' is a valid character, but various debuggers don't like it.
-        // So we'll insert a junk entry to avoid generating a null character.
-        lineArray[0] = "";
-
-        /**
-         * Split a text into an array of strings.  Reduce the texts to a string of
-         * hashes where each Unicode character represents one line.
-         * Modifies linearray and linehash through being a closure.
-         * @param {string} text String to encode.
-         * @return {string} Encoded string.
-         * @private
-         */
-        function diffLinesToCharsMunge(text) {
-            var chars, lineStart, lineEnd, lineArrayLength, line;
-            chars = "";
-            // Walk the text, pulling out a substring for each line.
-            // text.split('\n') would would temporarily double our memory footprint.
-            // Modifying text would create many large strings to garbage collect.
-            lineStart = 0;
-            lineEnd = -1;
-            // Keeping our own length variable is faster than looking it up.
-            lineArrayLength = lineArray.length;
-            while (lineEnd < text.length - 1) {
-                lineEnd = text.indexOf("\n", lineStart);
-                if (lineEnd === -1) {
-                    lineEnd = text.length - 1;
-                }
-                line = text.substring(lineStart, lineEnd + 1);
-                lineStart = lineEnd + 1;
-
-                if (lineHash.hasOwnProperty ? lineHash.hasOwnProperty(line) :
-                    (lineHash[line] !== undefined)) {
-                    chars += String.fromCharCode( lineHash[ line ] );
-                } else {
-                    chars += String.fromCharCode(lineArrayLength);
-                    lineHash[line] = lineArrayLength;
-                    lineArray[lineArrayLength++] = line;
-                }
-            }
-            return chars;
-        }
-
-        chars1 = diffLinesToCharsMunge(text1);
-        chars2 = diffLinesToCharsMunge(text2);
-        return {
-            chars1: chars1,
-            chars2: chars2,
-            lineArray: lineArray
-        };
-    };
-
-    /**
-     * Rehydrate the text in a diff from a string of line hashes to real lines of
-     * text.
-     * @param {!Array.<!DiffMatchPatch.Diff>} diffs Array of diff tuples.
-     * @param {!Array.<string>} lineArray Array of unique strings.
-     * @private
-     */
-    DiffMatchPatch.prototype.diffCharsToLines = function( diffs, lineArray ) {
-        var x, chars, text, y;
-        for ( x = 0; x < diffs.length; x++ ) {
-            chars = diffs[x][1];
-            text = [];
-            for ( y = 0; y < chars.length; y++ ) {
-                text[y] = lineArray[chars.charCodeAt(y)];
-            }
-            diffs[x][1] = text.join("");
-        }
-    };
-
-    /**
-     * Reorder and merge like edit sections.  Merge equalities.
-     * Any edit section can move as long as it doesn't cross an equality.
-     * @param {!Array.<!DiffMatchPatch.Diff>} diffs Array of diff tuples.
-     */
-    DiffMatchPatch.prototype.diffCleanupMerge = function(diffs) {
-        var pointer, countDelete, countInsert, textInsert, textDelete,
-			commonlength, changes;
-        diffs.push( [ DIFF_EQUAL, "" ] ); // Add a dummy entry at the end.
-        pointer = 0;
-        countDelete = 0;
-        countInsert = 0;
-        textDelete = "";
-        textInsert = "";
-        commonlength;
-        while (pointer < diffs.length) {
-            switch ( diffs[ pointer ][ 0 ] ) {
-                case DIFF_INSERT:
-                    countInsert++;
-                    textInsert += diffs[pointer][1];
-                    pointer++;
-                    break;
-                case DIFF_DELETE:
-                    countDelete++;
-                    textDelete += diffs[pointer][1];
-                    pointer++;
-                    break;
-                case DIFF_EQUAL:
-                    // Upon reaching an equality, check for prior redundancies.
-                    if (countDelete + countInsert > 1) {
-                        if (countDelete !== 0 && countInsert !== 0) {
-                            // Factor out any common prefixies.
-                            commonlength = this.diffCommonPrefix(textInsert, textDelete);
-                            if (commonlength !== 0) {
-                                if ((pointer - countDelete - countInsert) > 0 &&
-                                    diffs[pointer - countDelete - countInsert - 1][0] ===
-                                    DIFF_EQUAL) {
-                                    diffs[pointer - countDelete - countInsert - 1][1] +=
-                                        textInsert.substring(0, commonlength);
-                                } else {
-                                    diffs.splice( 0, 0, [ DIFF_EQUAL,
-                                        textInsert.substring( 0, commonlength )
-                                     ] );
-                                    pointer++;
-                                }
-                                textInsert = textInsert.substring(commonlength);
-                                textDelete = textDelete.substring(commonlength);
-                            }
-                            // Factor out any common suffixies.
-                            commonlength = this.diffCommonSuffix(textInsert, textDelete);
-                            if (commonlength !== 0) {
-                                diffs[pointer][1] = textInsert.substring(textInsert.length -
-                                    commonlength) + diffs[pointer][1];
-                                textInsert = textInsert.substring(0, textInsert.length -
-                                    commonlength);
-                                textDelete = textDelete.substring(0, textDelete.length -
-                                    commonlength);
-                            }
-                        }
-                        // Delete the offending records and add the merged ones.
-                        if (countDelete === 0) {
-                            diffs.splice( pointer - countInsert,
-                                countDelete + countInsert, [ DIFF_INSERT, textInsert ] );
-                        } else if (countInsert === 0) {
-                            diffs.splice( pointer - countDelete,
-                                countDelete + countInsert, [ DIFF_DELETE, textDelete ] );
-                        } else {
-                            diffs.splice( pointer - countDelete - countInsert,
-                                countDelete + countInsert, [ DIFF_DELETE, textDelete ], [ DIFF_INSERT, textInsert ] );
-                        }
-                        pointer = pointer - countDelete - countInsert +
-                            (countDelete ? 1 : 0) + (countInsert ? 1 : 0) + 1;
-                    } else if (pointer !== 0 && diffs[pointer - 1][0] === DIFF_EQUAL) {
-                        // Merge this equality with the previous one.
-                        diffs[pointer - 1][1] += diffs[pointer][1];
-                        diffs.splice(pointer, 1);
-                    } else {
-                        pointer++;
-                    }
-                    countInsert = 0;
-                    countDelete = 0;
-                    textDelete = "";
-                    textInsert = "";
-                    break;
-            }
-        }
-        if (diffs[diffs.length - 1][1] === "") {
-            diffs.pop(); // Remove the dummy entry at the end.
-        }
-
-        // Second pass: look for single edits surrounded on both sides by equalities
-        // which can be shifted sideways to eliminate an equality.
-        // e.g: A<ins>BA</ins>C -> <ins>AB</ins>AC
-        changes = false;
-        pointer = 1;
-        // Intentionally ignore the first and last element (don't need checking).
-        while (pointer < diffs.length - 1) {
-            if (diffs[pointer - 1][0] === DIFF_EQUAL &&
-                diffs[pointer + 1][0] === DIFF_EQUAL) {
-                // This is a single edit surrounded by equalities.
-                if ( diffs[ pointer ][ 1 ].substring( diffs[ pointer ][ 1 ].length -
-                        diffs[ pointer - 1 ][ 1 ].length ) === diffs[ pointer - 1 ][ 1 ] ) {
-                    // Shift the edit over the previous equality.
-                    diffs[pointer][1] = diffs[pointer - 1][1] +
-                        diffs[pointer][1].substring(0, diffs[pointer][1].length -
-                            diffs[pointer - 1][1].length);
-                    diffs[pointer + 1][1] = diffs[pointer - 1][1] + diffs[pointer + 1][1];
-                    diffs.splice(pointer - 1, 1);
-                    changes = true;
-                } else if ( diffs[ pointer ][ 1 ].substring( 0, diffs[ pointer + 1 ][ 1 ].length ) ===
-                    diffs[ pointer + 1 ][ 1 ] ) {
-                    // Shift the edit over the next equality.
-                    diffs[pointer - 1][1] += diffs[pointer + 1][1];
-                    diffs[pointer][1] =
-                        diffs[pointer][1].substring(diffs[pointer + 1][1].length) +
-                        diffs[pointer + 1][1];
-                    diffs.splice(pointer + 1, 1);
-                    changes = true;
-                }
-            }
-            pointer++;
-        }
-        // If shifts were made, the diff needs reordering and another shift sweep.
-        if (changes) {
-            this.diffCleanupMerge(diffs);
-        }
-    };
-
-    return function(o, n) {
-		var diff, output, text;
-        diff = new DiffMatchPatch();
-        output = diff.DiffMain(o, n);
-        //console.log(output);
-        diff.diffCleanupEfficiency(output);
-        text = diff.diffPrettyHtml(output);
-
-        return text;
-    };
-}());
-// jscs:enable
-
-(function() {
-
-// Deprecated QUnit.init - Ref #530
-// Re-initialize the configuration options
-QUnit.init = function() {
-	var tests, banner, result, qunit,
-		config = QUnit.config;
-
-	config.stats = { all: 0, bad: 0 };
-	config.moduleStats = { all: 0, bad: 0 };
-	config.started = 0;
-	config.updateRate = 1000;
-	config.blocking = false;
-	config.autostart = true;
-	config.autorun = false;
-	config.filter = "";
-	config.queue = [];
-
-	// Return on non-browser environments
-	// This is necessary to not break on node tests
-	if ( typeof window === "undefined" ) {
-		return;
-	}
-
-	qunit = id( "qunit" );
-	if ( qunit ) {
-		qunit.innerHTML =
-			"<h1 id='qunit-header'>" + escapeText( document.title ) + "</h1>" +
-			"<h2 id='qunit-banner'></h2>" +
-			"<div id='qunit-testrunner-toolbar'></div>" +
-			"<h2 id='qunit-userAgent'></h2>" +
-			"<ol id='qunit-tests'></ol>";
-	}
-
-	tests = id( "qunit-tests" );
-	banner = id( "qunit-banner" );
-	result = id( "qunit-testresult" );
-
-	if ( tests ) {
-		tests.innerHTML = "";
-	}
-
-	if ( banner ) {
-		banner.className = "";
-	}
-
-	if ( result ) {
-		result.parentNode.removeChild( result );
-	}
-
-	if ( tests ) {
-		result = document.createElement( "p" );
-		result.id = "qunit-testresult";
-		result.className = "result";
-		tests.parentNode.insertBefore( result, tests );
-		result.innerHTML = "Running...<br />&#160;";
-	}
-};
-
-// Don't load the HTML Reporter on non-Browser environments
-if ( typeof window === "undefined" ) {
-	return;
-}
-
-var config = QUnit.config,
-	hasOwn = Object.prototype.hasOwnProperty,
-	defined = {
-		document: window.document !== undefined,
-		sessionStorage: (function() {
-			var x = "qunit-test-string";
-			try {
-				sessionStorage.setItem( x, x );
-				sessionStorage.removeItem( x );
-				return true;
-			} catch ( e ) {
-				return false;
-			}
-		}())
-	},
-	modulesList = [];
-
-/**
-* Escape text for attribute or text content.
-*/
-function escapeText( s ) {
-	if ( !s ) {
-		return "";
-	}
-	s = s + "";
-
-	// Both single quotes and double quotes (for attributes)
-	return s.replace( /['"<>&]/g, function( s ) {
-		switch ( s ) {
-		case "'":
-			return "&#039;";
-		case "\"":
-			return "&quot;";
-		case "<":
-			return "&lt;";
-		case ">":
-			return "&gt;";
-		case "&":
-			return "&amp;";
-		}
-	});
-}
-
-/**
- * @param {HTMLElement} elem
- * @param {string} type
- * @param {Function} fn
- */
-function addEvent( elem, type, fn ) {
-	if ( elem.addEventListener ) {
-
-		// Standards-based browsers
-		elem.addEventListener( type, fn, false );
-	} else if ( elem.attachEvent ) {
-
-		// support: IE <9
-		elem.attachEvent( "on" + type, function() {
-			var event = window.event;
-			if ( !event.target ) {
-				event.target = event.srcElement || document;
-			}
-
-			fn.call( elem, event );
-		});
-	}
-}
-
-/**
- * @param {Array|NodeList} elems
- * @param {string} type
- * @param {Function} fn
- */
-function addEvents( elems, type, fn ) {
-	var i = elems.length;
-	while ( i-- ) {
-		addEvent( elems[ i ], type, fn );
-	}
-}
-
-function hasClass( elem, name ) {
-	return ( " " + elem.className + " " ).indexOf( " " + name + " " ) >= 0;
-}
-
-function addClass( elem, name ) {
-	if ( !hasClass( elem, name ) ) {
-		elem.className += ( elem.className ? " " : "" ) + name;
-	}
-}
-
-function toggleClass( elem, name ) {
-	if ( hasClass( elem, name ) ) {
-		removeClass( elem, name );
-	} else {
-		addClass( elem, name );
-	}
-}
-
-function removeClass( elem, name ) {
-	var set = " " + elem.className + " ";
-
-	// Class name may appear multiple times
-	while ( set.indexOf( " " + name + " " ) >= 0 ) {
-		set = set.replace( " " + name + " ", " " );
-	}
-
-	// trim for prettiness
-	elem.className = typeof set.trim === "function" ? set.trim() : set.replace( /^\s+|\s+$/g, "" );
-}
-
-function id( name ) {
-	return defined.document && document.getElementById && document.getElementById( name );
-}
-
-function getUrlConfigHtml() {
-	var i, j, val,
-		escaped, escapedTooltip,
-		selection = false,
-		len = config.urlConfig.length,
-		urlConfigHtml = "";
-
-	for ( i = 0; i < len; i++ ) {
-		val = config.urlConfig[ i ];
-		if ( typeof val === "string" ) {
-			val = {
-				id: val,
-				label: val
-			};
-		}
-
-		escaped = escapeText( val.id );
-		escapedTooltip = escapeText( val.tooltip );
-
-		if ( config[ val.id ] === undefined ) {
-			config[ val.id ] = QUnit.urlParams[ val.id ];
-		}
-
-		if ( !val.value || typeof val.value === "string" ) {
-			urlConfigHtml += "<input id='qunit-urlconfig-" + escaped +
-				"' name='" + escaped + "' type='checkbox'" +
-				( val.value ? " value='" + escapeText( val.value ) + "'" : "" ) +
-				( config[ val.id ] ? " checked='checked'" : "" ) +
-				" title='" + escapedTooltip + "' /><label for='qunit-urlconfig-" + escaped +
-				"' title='" + escapedTooltip + "'>" + val.label + "</label>";
-		} else {
-			urlConfigHtml += "<label for='qunit-urlconfig-" + escaped +
-				"' title='" + escapedTooltip + "'>" + val.label +
-				": </label><select id='qunit-urlconfig-" + escaped +
-				"' name='" + escaped + "' title='" + escapedTooltip + "'><option></option>";
-
-			if ( QUnit.is( "array", val.value ) ) {
-				for ( j = 0; j < val.value.length; j++ ) {
-					escaped = escapeText( val.value[ j ] );
-					urlConfigHtml += "<option value='" + escaped + "'" +
-						( config[ val.id ] === val.value[ j ] ?
-							( selection = true ) && " selected='selected'" : "" ) +
-						">" + escaped + "</option>";
-				}
-			} else {
-				for ( j in val.value ) {
-					if ( hasOwn.call( val.value, j ) ) {
-						urlConfigHtml += "<option value='" + escapeText( j ) + "'" +
-							( config[ val.id ] === j ?
-								( selection = true ) && " selected='selected'" : "" ) +
-							">" + escapeText( val.value[ j ] ) + "</option>";
-					}
-				}
-			}
-			if ( config[ val.id ] && !selection ) {
-				escaped = escapeText( config[ val.id ] );
-				urlConfigHtml += "<option value='" + escaped +
-					"' selected='selected' disabled='disabled'>" + escaped + "</option>";
-			}
-			urlConfigHtml += "</select>";
-		}
-	}
-
-	return urlConfigHtml;
-}
-
-// Handle "click" events on toolbar checkboxes and "change" for select menus.
-// Updates the URL with the new state of `config.urlConfig` values.
-function toolbarChanged() {
-	var updatedUrl, value,
-		field = this,
-		params = {};
-
-	// Detect if field is a select menu or a checkbox
-	if ( "selectedIndex" in field ) {
-		value = field.options[ field.selectedIndex ].value || undefined;
-	} else {
-		value = field.checked ? ( field.defaultValue || true ) : undefined;
-	}
-
-	params[ field.name ] = value;
-	updatedUrl = setUrl( params );
-
-	if ( "hidepassed" === field.name && "replaceState" in window.history ) {
-		config[ field.name ] = value || false;
-		if ( value ) {
-			addClass( id( "qunit-tests" ), "hidepass" );
-		} else {
-			removeClass( id( "qunit-tests" ), "hidepass" );
-		}
-
-		// It is not necessary to refresh the whole page
-		window.history.replaceState( null, "", updatedUrl );
-	} else {
-		window.location = updatedUrl;
-	}
-}
-
-function setUrl( params ) {
-	var key,
-		querystring = "?";
-
-	params = QUnit.extend( QUnit.extend( {}, QUnit.urlParams ), params );
-
-	for ( key in params ) {
-		if ( hasOwn.call( params, key ) ) {
-			if ( params[ key ] === undefined ) {
-				continue;
-			}
-			querystring += encodeURIComponent( key );
-			if ( params[ key ] !== true ) {
-				querystring += "=" + encodeURIComponent( params[ key ] );
-			}
-			querystring += "&";
-		}
-	}
-	return location.protocol + "//" + location.host +
-		location.pathname + querystring.slice( 0, -1 );
-}
-
-function applyUrlParams() {
-	var selectedModule,
-		modulesList = id( "qunit-modulefilter" ),
-		filter = id( "qunit-filter-input" ).value;
-
-	selectedModule = modulesList ?
-		decodeURIComponent( modulesList.options[ modulesList.selectedIndex ].value ) :
-		undefined;
-
-	window.location = setUrl({
-		module: ( selectedModule === "" ) ? undefined : selectedModule,
-		filter: ( filter === "" ) ? undefined : filter,
-
-		// Remove testId filter
-		testId: undefined
-	});
-}
-
-function toolbarUrlConfigContainer() {
-	var urlConfigContainer = document.createElement( "span" );
-
-	urlConfigContainer.innerHTML = getUrlConfigHtml();
-	addClass( urlConfigContainer, "qunit-url-config" );
-
-	// For oldIE support:
-	// * Add handlers to the individual elements instead of the container
-	// * Use "click" instead of "change" for checkboxes
-	addEvents( urlConfigContainer.getElementsByTagName( "input" ), "click", toolbarChanged );
-	addEvents( urlConfigContainer.getElementsByTagName( "select" ), "change", toolbarChanged );
-
-	return urlConfigContainer;
-}
-
-function toolbarLooseFilter() {
-	var filter = document.createElement( "form" ),
-		label = document.createElement( "label" ),
-		input = document.createElement( "input" ),
-		button = document.createElement( "button" );
-
-	addClass( filter, "qunit-filter" );
-
-	label.innerHTML = "Filter: ";
-
-	input.type = "text";
-	input.value = config.filter || "";
-	input.name = "filter";
-	input.id = "qunit-filter-input";
-
-	button.innerHTML = "Go";
-
-	label.appendChild( input );
-
-	filter.appendChild( label );
-	filter.appendChild( button );
-	addEvent( filter, "submit", function( ev ) {
-		applyUrlParams();
-
-		if ( ev && ev.preventDefault ) {
-			ev.preventDefault();
-		}
-
-		return false;
-	});
-
-	return filter;
-}
-
-function toolbarModuleFilterHtml() {
-	var i,
-		moduleFilterHtml = "";
-
-	if ( !modulesList.length ) {
-		return false;
-	}
-
-	modulesList.sort(function( a, b ) {
-		return a.localeCompare( b );
-	});
-
-	moduleFilterHtml += "<label for='qunit-modulefilter'>Module: </label>" +
-		"<select id='qunit-modulefilter' name='modulefilter'><option value='' " +
-		( QUnit.urlParams.module === undefined ? "selected='selected'" : "" ) +
-		">< All Modules ></option>";
-
-	for ( i = 0; i < modulesList.length; i++ ) {
-		moduleFilterHtml += "<option value='" +
-			escapeText( encodeURIComponent( modulesList[ i ] ) ) + "' " +
-			( QUnit.urlParams.module === modulesList[ i ] ? "selected='selected'" : "" ) +
-			">" + escapeText( modulesList[ i ] ) + "</option>";
-	}
-	moduleFilterHtml += "</select>";
-
-	return moduleFilterHtml;
-}
-
-function toolbarModuleFilter() {
-	var toolbar = id( "qunit-testrunner-toolbar" ),
-		moduleFilter = document.createElement( "span" ),
-		moduleFilterHtml = toolbarModuleFilterHtml();
-
-	if ( !toolbar || !moduleFilterHtml ) {
-		return false;
-	}
-
-	moduleFilter.setAttribute( "id", "qunit-modulefilter-container" );
-	moduleFilter.innerHTML = moduleFilterHtml;
-
-	addEvent( moduleFilter.lastChild, "change", applyUrlParams );
-
-	toolbar.appendChild( moduleFilter );
-}
-
-function appendToolbar() {
-	var toolbar = id( "qunit-testrunner-toolbar" );
-
-	if ( toolbar ) {
-		toolbar.appendChild( toolbarUrlConfigContainer() );
-		toolbar.appendChild( toolbarLooseFilter() );
-	}
-}
-
-function appendHeader() {
-	var header = id( "qunit-header" );
-
-	if ( header ) {
-		header.innerHTML = "<a href='" +
-			setUrl({ filter: undefined, module: undefined, testId: undefined }) +
-			"'>" + header.innerHTML + "</a> ";
-	}
-}
-
-function appendBanner() {
-	var banner = id( "qunit-banner" );
-
-	if ( banner ) {
-		banner.className = "";
-	}
-}
-
-function appendTestResults() {
-	var tests = id( "qunit-tests" ),
-		result = id( "qunit-testresult" );
-
-	if ( result ) {
-		result.parentNode.removeChild( result );
-	}
-
-	if ( tests ) {
-		tests.innerHTML = "";
-		result = document.createElement( "p" );
-		result.id = "qunit-testresult";
-		result.className = "result";
-		tests.parentNode.insertBefore( result, tests );
-		result.innerHTML = "Running...<br />&#160;";
-	}
-}
-
-function storeFixture() {
-	var fixture = id( "qunit-fixture" );
-	if ( fixture ) {
-		config.fixture = fixture.innerHTML;
-	}
-}
-
-function appendUserAgent() {
-	var userAgent = id( "qunit-userAgent" );
-
-	if ( userAgent ) {
-		userAgent.innerHTML = "";
-		userAgent.appendChild(
-			document.createTextNode(
-				"QUnit " + QUnit.version  + "; " + navigator.userAgent
-			)
-		);
-	}
-}
-
-function appendTestsList( modules ) {
-	var i, l, x, z, test, moduleObj;
-
-	for ( i = 0, l = modules.length; i < l; i++ ) {
-		moduleObj = modules[ i ];
-
-		if ( moduleObj.name ) {
-			modulesList.push( moduleObj.name );
-		}
-
-		for ( x = 0, z = moduleObj.tests.length; x < z; x++ ) {
-			test = moduleObj.tests[ x ];
-
-			appendTest( test.name, test.testId, moduleObj.name );
-		}
-	}
-}
-
-function appendTest( name, testId, moduleName ) {
-	var title, rerunTrigger, testBlock, assertList,
-		tests = id( "qunit-tests" );
-
-	if ( !tests ) {
-		return;
-	}
-
-	title = document.createElement( "strong" );
-	title.innerHTML = getNameHtml( name, moduleName );
-
-	rerunTrigger = document.createElement( "a" );
-	rerunTrigger.innerHTML = "Rerun";
-	rerunTrigger.href = setUrl({ testId: testId });
-
-	testBlock = document.createElement( "li" );
-	testBlock.appendChild( title );
-	testBlock.appendChild( rerunTrigger );
-	testBlock.id = "qunit-test-output-" + testId;
-
-	assertList = document.createElement( "ol" );
-	assertList.className = "qunit-assert-list";
-
-	testBlock.appendChild( assertList );
-
-	tests.appendChild( testBlock );
-}
-
-// HTML Reporter initialization and load
-QUnit.begin(function( details ) {
-	var qunit = id( "qunit" );
-
-	// Fixture is the only one necessary to run without the #qunit element
-	storeFixture();
-
-	if ( qunit ) {
-		qunit.innerHTML =
-			"<h1 id='qunit-header'>" + escapeText( document.title ) + "</h1>" +
-			"<h2 id='qunit-banner'></h2>" +
-			"<div id='qunit-testrunner-toolbar'></div>" +
-			"<h2 id='qunit-userAgent'></h2>" +
-			"<ol id='qunit-tests'></ol>";
-	}
-
-	appendHeader();
-	appendBanner();
-	appendTestResults();
-	appendUserAgent();
-	appendToolbar();
-	appendTestsList( details.modules );
-	toolbarModuleFilter();
-
-	if ( qunit && config.hidepassed ) {
-		addClass( qunit.lastChild, "hidepass" );
-	}
-});
-
-QUnit.done(function( details ) {
-	var i, key,
-		banner = id( "qunit-banner" ),
-		tests = id( "qunit-tests" ),
-		html = [
-			"Tests completed in ",
-			details.runtime,
-			" milliseconds.<br />",
-			"<span class='passed'>",
-			details.passed,
-			"</span> assertions of <span class='total'>",
-			details.total,
-			"</span> passed, <span class='failed'>",
-			details.failed,
-			"</span> failed."
-		].join( "" );
-
-	if ( banner ) {
-		banner.className = details.failed ? "qunit-fail" : "qunit-pass";
-	}
-
-	if ( tests ) {
-		id( "qunit-testresult" ).innerHTML = html;
-	}
-
-	if ( config.altertitle && defined.document && document.title ) {
-
-		// show ✖ for good, ✔ for bad suite result in title
-		// use escape sequences in case file gets loaded with non-utf-8-charset
-		document.title = [
-			( details.failed ? "\u2716" : "\u2714" ),
-			document.title.replace( /^[\u2714\u2716] /i, "" )
-		].join( " " );
-	}
-
-	// clear own sessionStorage items if all tests passed
-	if ( config.reorder && defined.sessionStorage && details.failed === 0 ) {
-		for ( i = 0; i < sessionStorage.length; i++ ) {
-			key = sessionStorage.key( i++ );
-			if ( key.indexOf( "qunit-test-" ) === 0 ) {
-				sessionStorage.removeItem( key );
-			}
-		}
-	}
-
-	// scroll back to top to show results
-	if ( config.scrolltop && window.scrollTo ) {
-		window.scrollTo( 0, 0 );
-	}
-});
-
-function getNameHtml( name, module ) {
-	var nameHtml = "";
-
-	if ( module ) {
-		nameHtml = "<span class='module-name'>" + escapeText( module ) + "</span>: ";
-	}
-
-	nameHtml += "<span class='test-name'>" + escapeText( name ) + "</span>";
-
-	return nameHtml;
-}
-
-QUnit.testStart(function( details ) {
-	var running, testBlock, bad;
-
-	testBlock = id( "qunit-test-output-" + details.testId );
-	if ( testBlock ) {
-		testBlock.className = "running";
-	} else {
-
-		// Report later registered tests
-		appendTest( details.name, details.testId, details.module );
-	}
-
-	running = id( "qunit-testresult" );
-	if ( running ) {
-		bad = QUnit.config.reorder && defined.sessionStorage &&
-			+sessionStorage.getItem( "qunit-test-" + details.module + "-" + details.name );
-
-		running.innerHTML = ( bad ?
-			"Rerunning previously failed test: <br />" :
-			"Running: <br />" ) +
-			getNameHtml( details.name, details.module );
-	}
-
-});
-
-QUnit.log(function( details ) {
-	var assertList, assertLi,
-		message, expected, actual,
-		testItem = id( "qunit-test-output-" + details.testId );
-
-	if ( !testItem ) {
-		return;
-	}
-
-	message = escapeText( details.message ) || ( details.result ? "okay" : "failed" );
-	message = "<span class='test-message'>" + message + "</span>";
-	message += "<span class='runtime'>@ " + details.runtime + " ms</span>";
-
-	// pushFailure doesn't provide details.expected
-	// when it calls, it's implicit to also not show expected and diff stuff
-	// Also, we need to check details.expected existence, as it can exist and be undefined
-	if ( !details.result && hasOwn.call( details, "expected" ) ) {
-		expected = escapeText( QUnit.dump.parse( details.expected ) );
-		actual = escapeText( QUnit.dump.parse( details.actual ) );
-		message += "<table><tr class='test-expected'><th>Expected: </th><td><pre>" +
-			expected +
-			"</pre></td></tr>";
-
-		if ( actual !== expected ) {
-			message += "<tr class='test-actual'><th>Result: </th><td><pre>" +
-				actual + "</pre></td></tr>" +
-				"<tr class='test-diff'><th>Diff: </th><td><pre>" +
-				QUnit.diff( expected, actual ) + "</pre></td></tr>";
-		} else {
-			if ( expected.indexOf( "[object Array]" ) !== -1 ||
-					expected.indexOf( "[object Object]" ) !== -1 ) {
-				message += "<tr class='test-message'><th>Message: </th><td>" +
-					"Diff suppressed as the depth of object is more than current max depth (" +
-					QUnit.config.maxDepth + ").<p>Hint: Use <code>QUnit.dump.maxDepth</code> to " +
-					" run with a higher max depth or <a href='" + setUrl({ maxDepth: -1 }) + "'>" +
-					"Rerun</a> without max depth.</p></td></tr>";
-			}
-		}
-
-		if ( details.source ) {
-			message += "<tr class='test-source'><th>Source: </th><td><pre>" +
-				escapeText( details.source ) + "</pre></td></tr>";
-		}
-
-		message += "</table>";
-
-	// this occours when pushFailure is set and we have an extracted stack trace
-	} else if ( !details.result && details.source ) {
-		message += "<table>" +
-			"<tr class='test-source'><th>Source: </th><td><pre>" +
-			escapeText( details.source ) + "</pre></td></tr>" +
-			"</table>";
-	}
-
-	assertList = testItem.getElementsByTagName( "ol" )[ 0 ];
-
-	assertLi = document.createElement( "li" );
-	assertLi.className = details.result ? "pass" : "fail";
-	assertLi.innerHTML = message;
-	assertList.appendChild( assertLi );
-});
-
-QUnit.testDone(function( details ) {
-	var testTitle, time, testItem, assertList,
-		good, bad, testCounts, skipped,
-		tests = id( "qunit-tests" );
-
-	if ( !tests ) {
-		return;
-	}
-
-	testItem = id( "qunit-test-output-" + details.testId );
-
-	assertList = testItem.getElementsByTagName( "ol" )[ 0 ];
-
-	good = details.passed;
-	bad = details.failed;
-
-	// store result when possible
-	if ( config.reorder && defined.sessionStorage ) {
-		if ( bad ) {
-			sessionStorage.setItem( "qunit-test-" + details.module + "-" + details.name, bad );
-		} else {
-			sessionStorage.removeItem( "qunit-test-" + details.module + "-" + details.name );
-		}
-	}
-
-	if ( bad === 0 ) {
-		addClass( assertList, "qunit-collapsed" );
-	}
-
-	// testItem.firstChild is the test name
-	testTitle = testItem.firstChild;
-
-	testCounts = bad ?
-		"<b class='failed'>" + bad + "</b>, " + "<b class='passed'>" + good + "</b>, " :
-		"";
-
-	testTitle.innerHTML += " <b class='counts'>(" + testCounts +
-		details.assertions.length + ")</b>";
-
-	if ( details.skipped ) {
-		testItem.className = "skipped";
-		skipped = document.createElement( "em" );
-		skipped.className = "qunit-skipped-label";
-		skipped.innerHTML = "skipped";
-		testItem.insertBefore( skipped, testTitle );
-	} else {
-		addEvent( testTitle, "click", function() {
-			toggleClass( assertList, "qunit-collapsed" );
-		});
-
-		testItem.className = bad ? "fail" : "pass";
-
-		time = document.createElement( "span" );
-		time.className = "runtime";
-		time.innerHTML = details.runtime + " ms";
-		testItem.insertBefore( time, assertList );
-	}
-});
-
-if ( defined.document ) {
-	if ( document.readyState === "complete" ) {
-		QUnit.load();
-	} else {
-		addEvent( window, "load", QUnit.load );
-	}
-} else {
-	config.pageLoaded = true;
-	config.autorun = true;
-}
-
-})();

+ 4 - 4
test/unit/qunit-utils.js

@@ -60,10 +60,10 @@ function checkGeometryClone( geom ) {
 	var excludedProperties = [ 'parameters', 'widthSegments', 'heightSegments', 'depthSegments' ];
 
 	var differingProp = getDifferingProp( geom, copy, excludedProperties );
-	ok( differingProp === undefined, 'properties are equal' );
+	QUnit.assert.ok( differingProp === undefined, 'properties are equal' );
 
 	differingProp = getDifferingProp( copy, geom, excludedProperties );
-	ok( differingProp === undefined, 'properties are equal' );
+	QUnit.assert.ok( differingProp === undefined, 'properties are equal' );
 
 	// json round trip with clone
 	checkGeometryJsonRoundtrip( copy );
@@ -151,10 +151,10 @@ function checkGeometryJsonReading( json, geom ) {
 	var excludedProperties = [ 'bones' ];
 
 	var differingProp = getDifferingProp( output[ geom.uuid ], geom, excludedProperties );
-	ok( differingProp === undefined, 'properties are equal' );
+	QUnit.assert.ok( differingProp === undefined, 'properties are equal' );
 
 	differingProp = getDifferingProp( geom, output[ geom.uuid ], excludedProperties );
-	ok( differingProp === undefined, 'properties are equal' );
+	QUnit.assert.ok( differingProp === undefined, 'properties are equal' );
 }
 
 // Verify geom -> json -> geom

+ 34 - 0
test/unit/src/animation/AnimationAction.js

@@ -0,0 +1,34 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AnimationAction")
+
+//QUnit.module( "AnimationAction" );
+//
+//QUnit.test( "Instancing", function( assert ) {
+//
+//    var mixer = new THREE.AnimationMixer();
+//    var clip = new THREE.AnimationClip();
+//
+//    assert.throws(
+//        function() {
+//            new THREE.AnimationAction()
+//        },
+//        new Error("Mixer can't be null or undefined !"),
+//        "raised error instance about undefined or null mixer"
+//    );
+//
+//    assert.throws(
+//        function() {
+//            new THREE.AnimationAction(mixer)
+//        },
+//        new Error("Clip can't be null or undefined !"),
+//        "raised error instance about undefined or null clip"
+//    );
+//
+//    var animationAction = new THREE.AnimationAction(mixer, clip);
+//    assert.ok( animationAction, "animationAction instanciated" );
+//
+//} );

+ 6 - 0
test/unit/src/animation/AnimationClip.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AnimationClip")

+ 6 - 0
test/unit/src/animation/AnimationMixer.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AnimationMixer")

+ 9 - 9
test/unit/animation/AnimationObjectGroup.js → test/unit/src/animation/AnimationObjectGroup.js

@@ -2,7 +2,7 @@
  * @author tschw
  */
 
-module( "AnimationObjectGroup" );
+QUnit.module( "AnimationObjectGroup" );
 
 var ObjectA = new THREE.Object3D(),
 	ObjectB = new THREE.Object3D(),
@@ -17,7 +17,7 @@ var ObjectA = new THREE.Object3D(),
 	ParsedPathC = THREE.PropertyBinding.parseTrackName( PathC );
 
 
-test( "smoke test", function() {
+QUnit.test( "smoke test", function( assert ) {
 
 	var expect = function expect( testIndex, group, bindings, path, cached, roots ) {
 
@@ -36,23 +36,23 @@ test( "smoke test", function() {
 
 		}
 
-		ok( pathsOk, testIndex + " paths" );
-		ok( nodesOk, testIndex + " nodes");
-		ok( group.nCachedObjects_ === cached, testIndex + " cache size" );
-		ok( bindings.length - group.nCachedObjects_ === roots.length, testIndex + " object count" );
+		assert.ok( pathsOk, testIndex + " paths" );
+		assert.ok( nodesOk, testIndex + " nodes");
+		assert.ok( group.nCachedObjects_ === cached, testIndex + " cache size" );
+		assert.ok( bindings.length - group.nCachedObjects_ === roots.length, testIndex + " object count" );
 
 	};
 
 	// initial state
 
 	var groupA = new THREE.AnimationObjectGroup();
-	ok( groupA instanceof THREE.AnimationObjectGroup, "constructor (w/o args)" );
+	assert.ok( groupA instanceof THREE.AnimationObjectGroup, "constructor (w/o args)" );
 
 	var bindingsAA = groupA.subscribe_( PathA, ParsedPathA );
 	expect( 0, groupA, bindingsAA, PathA, 0, [] );
 
 	var groupB = new THREE.AnimationObjectGroup( ObjectA, ObjectB );
-	ok( groupB instanceof THREE.AnimationObjectGroup, "constructor (with args)" );
+	assert.ok( groupB instanceof THREE.AnimationObjectGroup, "constructor (with args)" );
 
 	var bindingsBB = groupB.subscribe_( PathB, ParsedPathB );
 	expect( 1, groupB, bindingsBB, PathB, 0, [ ObjectA, ObjectB ] );
@@ -91,7 +91,7 @@ test( "smoke test", function() {
 	var copyOfBindingsBC = bindingsBC.slice();
 	groupB.unsubscribe_( PathC );
 	groupB.add( ObjectC );
-	deepEqual( bindingsBC, copyOfBindingsBC, "no more update after unsubscribe" );
+	assert.deepEqual( bindingsBC, copyOfBindingsBC, "no more update after unsubscribe" );
 
 	// uncache active
 

+ 6 - 0
test/unit/src/animation/AnimationUtils.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AnimationUtils")

+ 6 - 0
test/unit/src/animation/KeyframeTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of KeyframeTrack")

+ 6 - 0
test/unit/src/animation/KeyframeTrackConstructor.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of KeyframeTrackConstructor")

+ 6 - 0
test/unit/src/animation/KeyframeTrackPrototype.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of KeyframeTrackPrototype")

+ 6 - 0
test/unit/src/animation/PropertyBinding.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of PropertyBinding")

+ 6 - 0
test/unit/src/animation/PropertyMixer.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of PropertyMixer")

+ 6 - 0
test/unit/src/animation/tracks/BooleanKeyframeTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of BooleanKeyframeTrack")

+ 6 - 0
test/unit/src/animation/tracks/ColorKeyframeTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of ColorKeyframeTrack")

+ 6 - 0
test/unit/src/animation/tracks/NumberKeyframeTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of NumberKeyframeTrack")

+ 6 - 0
test/unit/src/animation/tracks/QuaternionKeyframeTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of QuaternionKeyframeTrack")

+ 6 - 0
test/unit/src/animation/tracks/StringKeyframeTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of StringKeyframeTrack")

+ 6 - 0
test/unit/src/animation/tracks/VectorKeyFrameTrack.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of VectorKeyFrameTrack")

+ 6 - 0
test/unit/src/audio/Audio.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Audio")

+ 6 - 0
test/unit/src/audio/AudioAnalyser.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AudioAnalyser")

+ 6 - 0
test/unit/src/audio/AudioContext.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AudioContext")

+ 6 - 0
test/unit/src/audio/AudioListener.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of AudioListener")

+ 6 - 0
test/unit/src/audio/PositionalAudio.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of PositionalAudio")

+ 6 - 6
test/unit/cameras/Camera.js → test/unit/src/cameras/Camera.js

@@ -2,16 +2,16 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "Camera" );
+QUnit.module( "Camera" );
 
-test( "lookAt", function() {
+QUnit.test( "lookAt" , function( assert ) {
 	var cam = new THREE.Camera();
 	cam.lookAt(new THREE.Vector3(0, 1, -1));
 
-	ok( cam.rotation.x * (180 / Math.PI) === 45 , "x is equal" );
+	assert.ok( cam.rotation.x * (180 / Math.PI) === 45 , "x is equal" );
 });
 
-test( "clone", function() {
+QUnit.test( "clone" , function( assert ) {
 	var cam = new THREE.Camera();
 
 	// fill the matrices with any nonsense values just to see if they get copied
@@ -20,6 +20,6 @@ test( "clone", function() {
 
 	var clonedCam = cam.clone();
 
-	ok( cam.matrixWorldInverse.equals(clonedCam.matrixWorldInverse) , "matrixWorldInverse is equal" );
-	ok( cam.projectionMatrix.equals(clonedCam.projectionMatrix) , "projectionMatrix is equal" );
+	assert.ok( cam.matrixWorldInverse.equals(clonedCam.matrixWorldInverse) , "matrixWorldInverse is equal" );
+	assert.ok( cam.projectionMatrix.equals(clonedCam.projectionMatrix) , "projectionMatrix is equal" );
 });

+ 6 - 0
test/unit/src/cameras/CubeCamera.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of CubeCamera")

+ 41 - 0
test/unit/src/cameras/OrthographicCamera.js

@@ -0,0 +1,41 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "OrthographicCamera" );
+
+QUnit.test( "updateProjectionMatrix" , function( assert ) {
+	var left = -1, right = 1, top = 1, bottom = -1, near = 1, far = 3;
+	var cam = new THREE.OrthographicCamera(left, right, top, bottom, near, far);
+
+	// updateProjectionMatrix is called in contructor
+	var pMatrix = cam.projectionMatrix.elements;
+
+	// orthographic projection is given my the 4x4 Matrix
+	// 2/r-l		0			 0		-(l+r/r-l)
+	//   0		2/t-b		 0		-(t+b/t-b)
+	//   0			0		-2/f-n	-(f+n/f-n)
+	//   0			0			 0				1
+
+	assert.ok( pMatrix[0] === 2 / ( right - left ), "m[0,0] === 2 / (r - l)" );
+	assert.ok( pMatrix[5] === 2 / ( top - bottom ), "m[1,1] === 2 / (t - b)" );
+	assert.ok( pMatrix[10] === -2 / ( far - near ), "m[2,2] === -2 / (f - n)" );
+	assert.ok( pMatrix[12] === - ( ( right + left ) / ( right - left ) ), "m[3,0] === -(r+l/r-l)" );
+	assert.ok( pMatrix[13] === - ( ( top + bottom ) / ( top - bottom ) ), "m[3,1] === -(t+b/b-t)" );
+	assert.ok( pMatrix[14] === - ( ( far + near ) / ( far - near ) ), "m[3,2] === -(f+n/f-n)" );
+});
+
+QUnit.test( "clone" , function( assert ) {
+	var left = -1.5, right = 1.5, top = 1, bottom = -1, near = 0.1, far = 42;
+	var cam = new THREE.OrthographicCamera(left, right, top, bottom, near, far);
+
+	var clonedCam = cam.clone();
+
+	assert.ok( cam.left === clonedCam.left , "left is equal" );
+	assert.ok( cam.right === clonedCam.right , "right is equal" );
+	assert.ok( cam.top === clonedCam.top , "top is equal" );
+	assert.ok( cam.bottom === clonedCam.bottom , "bottom is equal" );
+	assert.ok( cam.near === clonedCam.near , "near is equal" );
+	assert.ok( cam.far === clonedCam.far , "far is equal" );
+	assert.ok( cam.zoom === clonedCam.zoom , "zoom is equal" );
+});

+ 10 - 10
test/unit/cameras/PerspectiveCamera.js → test/unit/src/cameras/PerspectiveCamera.js

@@ -2,9 +2,9 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "PerspectiveCamera" );
+QUnit.module( "PerspectiveCamera" );
 
-test( "updateProjectionMatrix", function() {
+QUnit.test( "updateProjectionMatrix" , function( assert ) {
 
 	var cam = new THREE.PerspectiveCamera( 75, 16 / 9, 0.1, 300.0 );
 
@@ -26,10 +26,10 @@ test( "updateProjectionMatrix", function() {
 		0, 0, -1, 0
 	);
 
-	ok( reference.equals(m) );
+	assert.ok( reference.equals(m) );
 });
 
-test( "clone", function() {
+QUnit.test( "clone" , function( assert ) {
 	var near = 1,
 			far = 3,
 			bottom = -1,
@@ -41,10 +41,10 @@ test( "clone", function() {
 
 	var clonedCam = cam.clone();
 
-	ok( cam.fov === clonedCam.fov , "fov is equal" );
-	ok( cam.aspect === clonedCam.aspect , "aspect is equal" );
-	ok( cam.near === clonedCam.near , "near is equal" );
-	ok( cam.far === clonedCam.far , "far is equal" );
-	ok( cam.zoom === clonedCam.zoom , "zoom is equal" );
-	ok( cam.projectionMatrix.equals(clonedCam.projectionMatrix) , "projectionMatrix is equal" );
+	assert.ok( cam.fov === clonedCam.fov , "fov is equal" );
+	assert.ok( cam.aspect === clonedCam.aspect , "aspect is equal" );
+	assert.ok( cam.near === clonedCam.near , "near is equal" );
+	assert.ok( cam.far === clonedCam.far , "far is equal" );
+	assert.ok( cam.zoom === clonedCam.zoom , "zoom is equal" );
+	assert.ok( cam.projectionMatrix.equals(clonedCam.projectionMatrix) , "projectionMatrix is equal" );
 });

+ 6 - 0
test/unit/src/cameras/StereoCamera.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of StereoCamera")

+ 6 - 0
test/unit/src/constants.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Constants")

+ 117 - 0
test/unit/src/core/BufferAttribute.js

@@ -0,0 +1,117 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "BufferAttribute" );
+
+QUnit.test( "count" , function( assert ) {
+	assert.ok(
+		new THREE.BufferAttribute( new Float32Array( [1, 2, 3, 4, 5, 6] ), 3 ).count === 2,
+		'count is equal to the number of chunks'
+	);
+});
+
+QUnit.test( "copy" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array( [1, 2, 3, 4, 5, 6] ), 3 );
+	attr.setDynamic( true );
+	attr.needsUpdate = true;
+
+	var attrCopy = new THREE.BufferAttribute().copy( attr );
+
+	assert.ok( attr.count === attrCopy.count, 'count is equal' );
+	assert.ok( attr.itemSize === attrCopy.itemSize, 'itemSize is equal' );
+	assert.ok( attr.dynamic === attrCopy.dynamic, 'dynamic is equal' );
+	assert.ok( attr.array.length === attrCopy.array.length, 'array length is equal' );
+	assert.ok( attr.version === 1 && attrCopy.version === 0, 'version is not copied which is good' );
+});
+
+QUnit.test( "copyAt" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array( [1, 2, 3, 4, 5, 6, 7, 8, 9] ), 3 );
+	var attr2 = new THREE.BufferAttribute( new Float32Array(9), 3 );
+
+	attr2.copyAt( 1, attr, 2 );
+	attr2.copyAt( 0, attr, 1 );
+	attr2.copyAt( 2, attr, 0 );
+
+	var i = attr.array;
+	var i2 = attr2.array; // should be [4, 5, 6, 7, 8, 9, 1, 2, 3]
+
+	assert.ok( i2[0] === i[3] && i2[1] === i[4] && i2[2] === i[5], 'chunck copied to correct place' );
+	assert.ok( i2[3] === i[6] && i2[4] === i[7] && i2[5] === i[8], 'chunck copied to correct place' );
+	assert.ok( i2[6] === i[0] && i2[7] === i[1] && i2[8] === i[2], 'chunck copied to correct place' );
+});
+
+QUnit.test( "copyColorsArray" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array(6), 3 );
+
+	attr.copyColorsArray( [
+		new THREE.Color( 0, 0.5, 1 ),
+		new THREE.Color( 0.25, 1, 0 )
+	]);
+
+	var i = attr.array;
+	assert.ok( i[0] === 0 && i[1] === 0.5 && i[2] === 1, 'first color was copied correctly' );
+	assert.ok( i[3] === 0.25 && i[4] === 1 && i[5] === 0, 'second color was copied correctly' );
+});
+
+QUnit.test( "copyIndicesArray" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array(6), 3 );
+
+	attr.copyIndicesArray( [
+		{a: 1, b: 2, c: 3},
+		{a: 4, b: 5, c: 6}
+	]);
+
+	var i = attr.array;
+	assert.ok( i[0] === 1 && i[1] === 2 && i[2] === 3, 'first indices were copied correctly' );
+	assert.ok( i[3] === 4 && i[4] === 5 && i[5] === 6, 'second indices were copied correctly' );
+});
+
+QUnit.test( "copyVector2sArray" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array(4), 2 );
+
+	attr.copyVector2sArray( [
+		new THREE.Vector2(1, 2),
+		new THREE.Vector2(4, 5)
+	]);
+
+	var i = attr.array;
+	assert.ok( i[0] === 1 && i[1] === 2, 'first vector was copied correctly' );
+	assert.ok( i[2] === 4 && i[3] === 5, 'second vector was copied correctly' );
+});
+
+QUnit.test( "copyVector3sArray" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array(6), 2 );
+
+	attr.copyVector3sArray( [
+		new THREE.Vector3(1, 2, 3),
+		new THREE.Vector3(10, 20, 30)
+	]);
+
+	var i = attr.array;
+	assert.ok( i[0] === 1 && i[1] === 2 && i[2] === 3, 'first vector was copied correctly' );
+	assert.ok( i[3] === 10 && i[4] === 20 && i[5] === 30, 'second vector was copied correctly' );
+});
+
+QUnit.test( "copyVector4sArray" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array(8), 2 );
+
+	attr.copyVector4sArray( [
+		new THREE.Vector4(1, 2, 3, 4),
+		new THREE.Vector4(10, 20, 30, 40)
+	]);
+
+	var i = attr.array;
+	assert.ok( i[0] === 1 && i[1] === 2 && i[2] === 3 && i[3] === 4, 'first vector was copied correctly' );
+	assert.ok( i[4] === 10 && i[5] === 20 && i[6] === 30 && i[7] === 40, 'second vector was copied correctly' );
+});
+
+QUnit.test( "clone" , function( assert ) {
+	var attr = new THREE.BufferAttribute( new Float32Array([1, 2, 3, 4, 0.12, -12]), 2 );
+	var attrCopy = attr.clone();
+
+	assert.ok( attr.array.length === attrCopy.array.length, 'attribute was cloned' );
+	for ( var i = 0; i < attr.array.length; i++ ) {
+		assert.ok( attr.array[i] === attrCopy.array[i], 'array item is equal' );
+	}
+});

+ 54 - 54
test/unit/core/BufferGeometry.js → test/unit/src/core/BufferGeometry.js

@@ -2,26 +2,26 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "BufferGeometry" );
+QUnit.module( "BufferGeometry" );
 
 var DegToRad = Math.PI / 180;
 
-test( "add / delete Attribute", function() {
+QUnit.test( "add / delete Attribute", function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	var attributeName = "position";
 
-	ok ( geometry.attributes[attributeName] === undefined , 'no attribute defined' );
+	assert.ok ( geometry.attributes[attributeName] === undefined , 'no attribute defined' );
 
 	geometry.addAttribute( attributeName, new THREE.BufferAttribute( new Float32Array( [1, 2, 3], 1 ) ) );
 
-	ok ( geometry.attributes[attributeName] !== undefined , 'attribute is defined' );
+	assert.ok ( geometry.attributes[attributeName] !== undefined , 'attribute is defined' );
 
 	geometry.removeAttribute( attributeName );
 
-	ok ( geometry.attributes[attributeName] === undefined , 'no attribute defined' );
+	assert.ok ( geometry.attributes[attributeName] === undefined , 'no attribute defined' );
 });
 
-test( "applyMatrix", function() {
+QUnit.test( "applyMatrix" , function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	geometry.addAttribute( "position", new THREE.BufferAttribute( new Float32Array(6), 3 ) );
 
@@ -35,12 +35,12 @@ test( "applyMatrix", function() {
 
 	var position = geometry.attributes.position.array;
 	var m = matrix.elements;
-	ok( position[0] === m[12] && position[1] === m[13] && position[2] === m[14], "position was extracted from matrix" );
-	ok( position[3] === m[12] && position[4] === m[13] && position[5] === m[14], "position was extracted from matrix twice" );
-	ok( geometry.attributes.position.version === 1, "version was increased during update" );
+	assert.ok( position[0] === m[12] && position[1] === m[13] && position[2] === m[14], "position was extracted from matrix" );
+	assert.ok( position[3] === m[12] && position[4] === m[13] && position[5] === m[14], "position was extracted from matrix twice" );
+	assert.ok( geometry.attributes.position.version === 1, "version was increased during update" );
 });
 
-test( "rotateX/Y/Z", function() {
+QUnit.test( "rotateX/Y/Z", function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	geometry.addAttribute( "position", new THREE.BufferAttribute( new Float32Array([1, 2, 3, 4, 5, 6]), 3 ) );
 
@@ -49,26 +49,26 @@ test( "rotateX/Y/Z", function() {
 	geometry.rotateX( 180 * DegToRad );
 
 	// object was rotated around x so all items should be flipped but the x ones
-	ok( pos[0] === 1 && pos[1] === -2 && pos[2] === -3 &&
+	assert.ok( pos[0] === 1 && pos[1] === -2 && pos[2] === -3 &&
 			pos[3] === 4 && pos[4] === -5 && pos[5] === -6, "vertices were rotated around x by 180 degrees" );
 
 
 	geometry.rotateY( 180 * DegToRad );
 
 	// vertices were rotated around y so all items should be flipped again but the y ones
-	ok( pos[0] === -1 && pos[1] === -2 && pos[2] === 3 &&
+	assert.ok( pos[0] === -1 && pos[1] === -2 && pos[2] === 3 &&
 			pos[3] === -4 && pos[4] === -5 && pos[5] === 6, "vertices were rotated around y by 180 degrees" );
 
 
 	geometry.rotateZ( 180 * DegToRad );
 
 	// vertices were rotated around z so all items should be flipped again but the z ones
-	ok( pos[0] === 1 && pos[1] === 2 && pos[2] === 3 &&
+	assert.ok( pos[0] === 1 && pos[1] === 2 && pos[2] === 3 &&
 			pos[3] === 4 && pos[4] === 5 && pos[5] === 6, "vertices were rotated around z by 180 degrees" );
 });
 
 
-test( "translate", function() {
+QUnit.test( "translate" , function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	geometry.addAttribute( "position", new THREE.BufferAttribute( new Float32Array([1, 2, 3, 4, 5, 6]), 3 ) );
 
@@ -76,11 +76,11 @@ test( "translate", function() {
 
 	geometry.translate( 10, 20, 30 );
 
-	ok( pos[0] === 11 && pos[1] === 22 && pos[2] === 33 &&
+	assert.ok( pos[0] === 11 && pos[1] === 22 && pos[2] === 33 &&
 			pos[3] === 14 && pos[4] === 25 && pos[5] === 36, "vertices were translated" );
 });
 
-test( "scale", function() {
+QUnit.test( "scale" , function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	geometry.addAttribute( "position", new THREE.BufferAttribute( new Float32Array([-1, -1, -1, 2, 2, 2]), 3 ) );
 
@@ -88,11 +88,11 @@ test( "scale", function() {
 
 	geometry.scale( 1, 2, 3 );
 
-	ok( pos[0] === -1 && pos[1] === -2 && pos[2] === -3 &&
+	assert.ok( pos[0] === -1 && pos[1] === -2 && pos[2] === -3 &&
 			pos[3] === 2 && pos[4] === 4 && pos[5] === 6, "vertices were scaled" );
 });
 
-test( "center", function() {
+QUnit.test( "center" , function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	geometry.addAttribute( "position", new THREE.BufferAttribute( new Float32Array([
 		-1, -1, -1,
@@ -107,12 +107,12 @@ test( "center", function() {
 
 	// the boundingBox should go from (-1, -1, -1) to (4, 4, 4) so it has a size of (5, 5, 5)
 	// after centering it the vertices should be placed between (-2.5, -2.5, -2.5) and (2.5, 2.5, 2.5)
-	ok( pos[0] === -2.5 && pos[1] === -2.5 && pos[2] === -2.5 &&
+	assert.ok( pos[0] === -2.5 && pos[1] === -2.5 && pos[2] === -2.5 &&
 			pos[3] === -0.5 && pos[4] === -0.5 && pos[5] === -0.5 &&
 			pos[6] === 2.5 && pos[7] === 2.5 && pos[8] === 2.5, "vertices were replaced by boundingBox dimensions" );
 });
 
-test( "setFromObject", function() {
+QUnit.test( "setFromObject" , function( assert ) {
 	var lineGeo = new THREE.Geometry();
 	lineGeo.vertices.push(
 		new THREE.Vector3( -10, 0, 0 ),
@@ -134,7 +134,7 @@ test( "setFromObject", function() {
 	var v = lineGeo.vertices;
 	var c = lineGeo.colors;
 
-	ok(
+	assert.ok(
 		 // position exists
 			pos !== undefined &&
 
@@ -150,7 +150,7 @@ test( "setFromObject", function() {
 			pos[6] === v[2].x && pos[7] === v[2].y && pos[8] === v[2].z
 			, "positions are equal" );
 
-	ok(
+	assert.ok(
 		 // color exists
 			col !== undefined &&
 
@@ -167,31 +167,31 @@ test( "setFromObject", function() {
 			, "colors are equal" );
 });
 
-test( "computeBoundingBox", function() {
+QUnit.test( "computeBoundingBox" , function( assert ) {
 	var bb = getBBForVertices( [-1, -2, -3, 13, -2, -3.5, -1, -20, 0, -4, 5, 6] );
 
-	ok( bb.min.x === -4 && bb.min.y === -20 && bb.min.z === -3.5, "min values are set correctly" );
-	ok( bb.max.x === 13 && bb.max.y === 5 && bb.max.z === 6, "max values are set correctly" );
+	assert.ok( bb.min.x === -4 && bb.min.y === -20 && bb.min.z === -3.5, "min values are set correctly" );
+	assert.ok( bb.max.x === 13 && bb.max.y === 5 && bb.max.z === 6, "max values are set correctly" );
 
 
 	bb = getBBForVertices( [-1, -1, -1] );
 
-	ok( bb.min.x === bb.max.x && bb.min.y === bb.max.y && bb.min.z === bb.max.z, "since there is only one vertex, max and min are equal" );
-	ok( bb.min.x === -1 && bb.min.y === -1 && bb.min.z === -1, "since there is only one vertex, min and max are this vertex" );
+	assert.ok( bb.min.x === bb.max.x && bb.min.y === bb.max.y && bb.min.z === bb.max.z, "since there is only one vertex, max and min are equal" );
+	assert.ok( bb.min.x === -1 && bb.min.y === -1 && bb.min.z === -1, "since there is only one vertex, min and max are this vertex" );
 });
 
-test( "computeBoundingSphere", function() {
+QUnit.test( "computeBoundingSphere" , function( assert ) {
 	var bs = getBSForVertices( [-10, 0, 0, 10, 0, 0] );
 
-	ok( bs.radius === (10 + 10) / 2, "radius is equal to deltaMinMax / 2" )
-	ok( bs.center.x === 0 && bs.center.y === 0 && bs.center.y === 0, "bounding sphere is at ( 0, 0, 0 )" )
+	assert.ok( bs.radius === (10 + 10) / 2, "radius is equal to deltaMinMax / 2" )
+	assert.ok( bs.center.x === 0 && bs.center.y === 0 && bs.center.y === 0, "bounding sphere is at ( 0, 0, 0 )" )
 
 
 	var bs = getBSForVertices( [-5, 11, -3, 5, -11, 3] );
 	var radius = new THREE.Vector3(5, 11, 3).length();
 
-	ok( bs.radius === radius, "radius is equal to directionLength" )
-	ok( bs.center.x === 0 && bs.center.y === 0 && bs.center.y === 0, "bounding sphere is at ( 0, 0, 0 )" )
+	assert.ok( bs.radius === radius, "radius is equal to directionLength" )
+	assert.ok( bs.center.x === 0 && bs.center.y === 0 && bs.center.y === 0, "bounding sphere is at ( 0, 0, 0 )" )
 });
 
 function getBBForVertices(vertices) {
@@ -212,34 +212,34 @@ function getBSForVertices(vertices) {
 	return geometry.boundingSphere;
 }
 
-test( "computeVertexNormals", function() {
+QUnit.test( "computeVertexNormals" , function( assert ) {
 	// get normals for a counter clockwise created triangle
-	var normals = getNormalsForVertices([-1, 0, 0, 1, 0, 0, 0, 1, 0]);
+	var normals = getNormalsForVertices([-1, 0, 0, 1, 0, 0, 0, 1, 0], assert);
 
-	ok( normals[0] === 0 && normals[1] === 0 && normals[2] === 1,
+	assert.ok( normals[0] === 0 && normals[1] === 0 && normals[2] === 1,
 		"first normal is pointing to screen since the the triangle was created counter clockwise" );
 
-	ok( normals[3] === 0 && normals[4] === 0 && normals[5] === 1,
+	assert.ok( normals[3] === 0 && normals[4] === 0 && normals[5] === 1,
 		"second normal is pointing to screen since the the triangle was created counter clockwise" );
 
-	ok( normals[6] === 0 && normals[7] === 0 && normals[8] === 1,
+	assert.ok( normals[6] === 0 && normals[7] === 0 && normals[8] === 1,
 		"third normal is pointing to screen since the the triangle was created counter clockwise" );
 
 
 	// get normals for a clockwise created triangle
-	var normals = getNormalsForVertices([1, 0, 0, -1, 0, 0, 0, 1, 0]);
+	var normals = getNormalsForVertices([1, 0, 0, -1, 0, 0, 0, 1, 0], assert);
 
-	ok( normals[0] === 0 && normals[1] === 0 && normals[2] === -1,
+	assert.ok( normals[0] === 0 && normals[1] === 0 && normals[2] === -1,
 		"first normal is pointing to screen since the the triangle was created clockwise" );
 
-	ok( normals[3] === 0 && normals[4] === 0 && normals[5] === -1,
+	assert.ok( normals[3] === 0 && normals[4] === 0 && normals[5] === -1,
 		"second normal is pointing to screen since the the triangle was created clockwise" );
 
-	ok( normals[6] === 0 && normals[7] === 0 && normals[8] === -1,
+	assert.ok( normals[6] === 0 && normals[7] === 0 && normals[8] === -1,
 		"third normal is pointing to screen since the the triangle was created clockwise" );
 
 
-	var normals = getNormalsForVertices([0, 0, 1, 0, 0, -1, 1, 1, 0]);
+	var normals = getNormalsForVertices([0, 0, 1, 0, 0, -1, 1, 1, 0], assert);
 
 	// the triangle is rotated by 45 degrees to the right so the normals of the three vertices
 	// should point to (1, -1, 0).normalized(). The simplest solution is to check against a normalized
@@ -249,29 +249,29 @@ test( "computeVertexNormals", function() {
 	// which can be taken from Number.EPSILON
 	var direction = new THREE.Vector3(1, 1, 0).normalize(); // a vector which should have 90 degrees difference to normals
 	var difference = direction.dot( new THREE.Vector3( normals[0], normals[1], normals[2] ) );
-	ok( difference < Number.EPSILON, "normal is equal to reference vector");
+	assert.ok( difference < Number.EPSILON, "normal is equal to reference vector");
 
 
 	// get normals for a line should be NAN because you need min a triangle to calculate normals
-	var normals = getNormalsForVertices([1, 0, 0, -1, 0, 0]);
+	var normals = getNormalsForVertices([1, 0, 0, -1, 0, 0], assert);
 	for (var i = 0; i < normals.length; i++) {
-		ok ( !normals[i], "normals can't be calculated which is good");
+		assert.ok ( !normals[i], "normals can't be calculated which is good");
 	}
 });
 
-function getNormalsForVertices(vertices) {
+function getNormalsForVertices(vertices, assert) {
 	var geometry = new THREE.BufferGeometry();
 
 	geometry.addAttribute( "position", new THREE.BufferAttribute( new Float32Array(vertices), 3 ) );
 
 	geometry.computeVertexNormals();
 
-	ok( geometry.attributes.normal !== undefined, "normal attribute was created" );
+	assert.ok( geometry.attributes.normal !== undefined, "normal attribute was created" );
 
 	return geometry.attributes.normal.array;
 }
 
-test( "merge", function() {
+QUnit.test( "merge" , function( assert ) {
 	var geometry1 = new THREE.BufferGeometry();
 	geometry1.addAttribute( "attrName", new THREE.BufferAttribute( new Float32Array([1, 2, 3, 0, 0, 0]), 3 ) );
 
@@ -284,28 +284,28 @@ test( "merge", function() {
 
 	// merged array should be 1, 2, 3, 4, 5, 6
 	for (var i = 0; i < attr.length; i++) {
-	  ok( attr[i] === i + 1, "");
+	  assert.ok( attr[i] === i + 1, "");
 	}
 
 	geometry1.merge(geometry2);
-	ok( attr[0] === 4 && attr[1] === 5 && attr[2] === 6, "copied the 3 attributes without offset" );
+	assert.ok( attr[0] === 4 && attr[1] === 5 && attr[2] === 6, "copied the 3 attributes without offset" );
 });
 
-test( "copy", function() {
+QUnit.test( "copy" , function( assert ) {
 	var geometry = new THREE.BufferGeometry();
 	geometry.addAttribute( "attrName", new THREE.BufferAttribute( new Float32Array([1, 2, 3, 4, 5, 6]), 3 ) );
 	geometry.addAttribute( "attrName2", new THREE.BufferAttribute( new Float32Array([0, 1, 3, 5, 6]), 1 ) );
 
 	var copy = new THREE.BufferGeometry().copy(geometry);
 
-	ok( copy !== geometry && geometry.id !== copy.id, "new object was created" );
+	assert.ok( copy !== geometry && geometry.id !== copy.id, "new object was created" );
 
 	Object.keys(geometry.attributes).forEach(function(key) {
 		var attribute = geometry.attributes[key];
-		ok( attribute !== undefined, "all attributes where copied");
+		assert.ok( attribute !== undefined, "all attributes where copied");
 
 		for (var i = 0; i < attribute.array.length; i++) {
-			ok( attribute.array[i] === copy.attributes[key].array[i], "values of the attribute are equal" );
+			assert.ok( attribute.array[i] === copy.attributes[key].array[i], "values of the attribute are equal" );
 		}
 	});
 });

+ 5 - 5
test/unit/core/Clock.js → test/unit/src/core/Clock.js

@@ -2,7 +2,7 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "Clock" );
+QUnit.module( "Clock" );
 
 function mockPerformance() {
 	self.performance = {
@@ -18,7 +18,7 @@ function mockPerformance() {
 	};
 }
 
-test( "clock with performance", function() {
+QUnit.test( "clock with performance", function( assert ) {
 	mockPerformance();
 
 	var clock = new THREE.Clock();
@@ -26,13 +26,13 @@ test( "clock with performance", function() {
 	clock.start();
 
 	self.performance.next(123);
-	ok( clock.getElapsedTime() === 0.123 , "okay");
+	assert.ok( clock.getElapsedTime() === 0.123 , "okay");
 
 	self.performance.next(100);
-	ok( clock.getElapsedTime() === 0.223 , "okay");
+	assert.ok( clock.getElapsedTime() === 0.223 , "okay");
 
 	clock.stop();
 
 	self.performance.next(1000);
-	ok( clock.getElapsedTime() === 0.223 , "don't update time if the clock was stopped");
+	assert.ok( clock.getElapsedTime() === 0.223 , "don't update time if the clock was stopped");
 });

+ 6 - 0
test/unit/src/core/DirectGeometry.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of DirectGeometry")

+ 76 - 0
test/unit/src/core/EventDispatcher.js

@@ -0,0 +1,76 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "EventDispatcher" );
+
+QUnit.test( "addEventListener" , function( assert ) {
+	var eventDispatcher = new THREE.EventDispatcher();
+
+	var listener = {};
+	eventDispatcher.addEventListener( 'anyType', listener );
+
+	assert.ok( eventDispatcher._listeners.anyType.length === 1, "listener with unknown type was added" );
+	assert.ok( eventDispatcher._listeners.anyType[0] === listener, "listener with unknown type was added" );
+
+	eventDispatcher.addEventListener( 'anyType', listener );
+
+	assert.ok( eventDispatcher._listeners.anyType.length === 1, "can't add one listener twice to same type" );
+	assert.ok( eventDispatcher._listeners.anyType[0] === listener, "listener is still there" );
+});
+
+QUnit.test( "hasEventListener" , function( assert ) {
+	var eventDispatcher = new THREE.EventDispatcher();
+
+	var listener = {};
+	eventDispatcher.addEventListener( 'anyType', listener );
+
+	assert.ok( eventDispatcher.hasEventListener( 'anyType', listener ), "listener was found" );
+	assert.ok( !eventDispatcher.hasEventListener( 'anotherType', listener ), "listener was not found which is good" );
+});
+
+QUnit.test( "removeEventListener" , function( assert ) {
+	var eventDispatcher = new THREE.EventDispatcher();
+
+	var listener = {};
+
+	assert.ok( eventDispatcher._listeners === undefined, "there are no listeners by default" );
+
+	eventDispatcher.addEventListener( 'anyType', listener );
+	assert.ok( Object.keys( eventDispatcher._listeners ).length === 1 &&
+		eventDispatcher._listeners.anyType.length === 1, "if a listener was added, there is a new key" );
+
+	eventDispatcher.removeEventListener( 'anyType', listener );
+	assert.ok( eventDispatcher._listeners.anyType.length === 0, "listener was deleted" );
+
+	eventDispatcher.removeEventListener( 'unknownType', listener );
+	assert.ok( eventDispatcher._listeners.unknownType === undefined, "unknown types will be ignored" );
+
+	eventDispatcher.removeEventListener( 'anyType', undefined );
+	assert.ok( eventDispatcher._listeners.anyType.length === 0, "undefined listeners are ignored" );
+});
+
+QUnit.test( "dispatchEvent" , function( assert ) {
+	var eventDispatcher = new THREE.EventDispatcher();
+
+	var callCount = 0;
+	var listener = function() { callCount++; };
+
+	eventDispatcher.addEventListener( 'anyType', listener );
+	assert.ok( callCount === 0, "no event, no call" );
+
+	eventDispatcher.dispatchEvent( { type: 'anyType' } );
+	assert.ok( callCount === 1, "one event, one call" );
+
+	eventDispatcher.dispatchEvent( { type: 'anyType' } );
+	assert.ok( callCount === 2, "two events, two calls" );
+});
+
+
+
+
+
+
+
+
+//

+ 17 - 17
test/unit/core/Face3.js → test/unit/src/core/Face3.js

@@ -2,38 +2,38 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "Face3" );
+QUnit.module( "Face3" );
 
-test( "copy", function() {
+QUnit.test( "copy" , function( assert ) {
 	var instance = new THREE.Face3(0, 1, 2, new THREE.Vector3(0, 1, 0), new THREE.Color(0.25, 0.5, 0.75), 2);
 	var copiedInstance = instance.copy(instance);
 
-	checkCopy(copiedInstance);
-	checkVertexAndColors(copiedInstance);
+	checkCopy(copiedInstance, assert);
+	checkVertexAndColors(copiedInstance, assert);
 });
 
-test( "copy", function() {
+QUnit.test( "copy" , function( assert ) {
 	var instance = new THREE.Face3(0, 1, 2,
 		[new THREE.Vector3(0, 1, 0), new THREE.Vector3(1, 0, 1)],
 		[new THREE.Color(0.25, 0.5, 0.75), new THREE.Color(1, 0, 0.4)],
 		2);
 	var copiedInstance = instance.copy(instance);
 
-	checkCopy(copiedInstance);
-	checkVertexAndColorArrays(copiedInstance);
+	checkCopy(copiedInstance, assert);
+	checkVertexAndColorArrays(copiedInstance, assert);
 });
 
-test( "clone", function() {
+QUnit.test( "clone" , function( assert ) {
 	var instance = new THREE.Face3(0, 1, 2, new THREE.Vector3(0, 1, 0), new THREE.Color(0.25, 0.5, 0.75), 2);
 	var copiedInstance = instance.clone();
 
-	checkCopy(copiedInstance);
-	checkVertexAndColors(copiedInstance);
+	checkCopy(copiedInstance, assert);
+	checkVertexAndColors(copiedInstance, assert);
 });
 
-function checkCopy(copiedInstance) {
-	ok( copiedInstance instanceof THREE.Face3, "copy created the correct type" );
-	ok(
+function checkCopy(copiedInstance, assert) {
+	assert.ok( copiedInstance instanceof THREE.Face3, "copy created the correct type" );
+	assert.ok(
 		copiedInstance.a === 0 &&
 		copiedInstance.b === 1 &&
 		copiedInstance.c === 2 &&
@@ -41,15 +41,15 @@ function checkCopy(copiedInstance) {
 		,"properties where copied" );
 }
 
-function checkVertexAndColors(copiedInstance) {
-	ok(
+function checkVertexAndColors(copiedInstance, assert) {
+	assert.ok(
 		copiedInstance.normal.x === 0 && copiedInstance.normal.y === 1 && copiedInstance.normal.z === 0 &&
 		copiedInstance.color.r === 0.25 && copiedInstance.color.g === 0.5 && copiedInstance.color.b === 0.75
 		,"properties where copied" );
 }
 
-function checkVertexAndColorArrays(copiedInstance) {
-	ok(
+function checkVertexAndColorArrays(copiedInstance, assert) {
+	assert.ok(
 		copiedInstance.vertexNormals[0].x === 0 && copiedInstance.vertexNormals[0].y === 1 && copiedInstance.vertexNormals[0].z === 0 &&
 		copiedInstance.vertexNormals[1].x === 1 && copiedInstance.vertexNormals[1].y === 0 && copiedInstance.vertexNormals[1].z === 1 &&
 		copiedInstance.vertexColors[0].r === 0.25 && copiedInstance.vertexColors[0].g === 0.5 && copiedInstance.vertexColors[0].b === 0.75 &&

+ 21 - 22
test/unit/core/Geometry.js → test/unit/src/core/Geometry.js

@@ -2,9 +2,9 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "Geometry" );
+QUnit.module( "Geometry" );
 
-test( "rotateX", function() {
+QUnit.test( "rotateX" , function( assert ) {
 	var geometry = getGeometry();
 
 	var matrix = new THREE.Matrix4();
@@ -13,13 +13,12 @@ test( "rotateX", function() {
 	geometry.applyMatrix( matrix );
 
 	var v0 = geometry.vertices[0], v1 = geometry.vertices[1], v2 = geometry.vertices[2];
-	ok ( v0.x === -0.5 && v0.y === 0 && v0.z === 0, "first vertex was rotated" );
-	ok ( v1.x === 0.5 && v1.y === 0 && v1.z === 0, "second vertex was rotated" );
-	ok ( v2.x === 0 && v2.y < Number.EPSILON && v2.z === 1, "third vertex was rotated" );
+	assert.ok( v0.x === -0.5 && v0.y === 0 && v0.z === 0, "first vertex was rotated" );
+	assert.ok( v1.x === 0.5 && v1.y === 0 && v1.z === 0, "second vertex was rotated" );
+	assert.ok( v2.x === 0 && v2.y < Number.EPSILON && v2.z === 1, "third vertex was rotated" );
 });
 
-
-test( "rotateY", function() {
+QUnit.test( "rotateY" , function( assert ) {
 	var geometry = getGeometry();
 
 	var matrix = new THREE.Matrix4();
@@ -28,12 +27,12 @@ test( "rotateY", function() {
 	geometry.applyMatrix( matrix );
 
 	var v0 = geometry.vertices[0], v1 = geometry.vertices[1], v2 = geometry.vertices[2];
-	ok ( v0.x === 0.5 && v0.y === 0 && v0.z < Number.EPSILON, "first vertex was rotated" );
-	ok ( v1.x === -0.5 && v1.y === 0 && v1.z < Number.EPSILON, "second vertex was rotated" );
-	ok ( v2.x === 0 && v2.y === 1 && v2.z === 0, "third vertex was rotated" );
+	assert.ok( v0.x === 0.5 && v0.y === 0 && v0.z < Number.EPSILON, "first vertex was rotated" );
+	assert.ok( v1.x === -0.5 && v1.y === 0 && v1.z < Number.EPSILON, "second vertex was rotated" );
+	assert.ok( v2.x === 0 && v2.y === 1 && v2.z === 0, "third vertex was rotated" );
 });
 
-test( "rotateZ", function() {
+QUnit.test( "rotateZ" , function( assert ) {
 	var geometry = getGeometry();
 
 	var matrix = new THREE.Matrix4();
@@ -42,12 +41,12 @@ test( "rotateZ", function() {
 	geometry.applyMatrix( matrix );
 
 	var v0 = geometry.vertices[0], v1 = geometry.vertices[1], v2 = geometry.vertices[2];
-	ok ( v0.x < Number.EPSILON && v0.y === 0.5 && v0.z === 0, "first vertex was rotated" );
-	ok ( v1.x < Number.EPSILON && v1.y === -0.5 && v1.z === 0, "second vertex was rotated" );
-	ok ( v2.x === 1 && v2.y < Number.EPSILON && v2.z === 0, "third vertex was rotated" );
+	assert.ok( v0.x < Number.EPSILON && v0.y === 0.5 && v0.z === 0, "first vertex was rotated" );
+	assert.ok( v1.x < Number.EPSILON && v1.y === -0.5 && v1.z === 0, "second vertex was rotated" );
+	assert.ok( v2.x === 1 && v2.y < Number.EPSILON && v2.z === 0, "third vertex was rotated" );
 });
 
-test( "fromBufferGeometry", function() {
+QUnit.test( "fromBufferGeometry" , function( assert ) {
 	var bufferGeometry = new THREE.BufferGeometry();
 	bufferGeometry.addAttribute('position', new THREE.BufferAttribute(new Float32Array( [1, 2, 3, 4, 5, 6, 7, 8, 9] ), 3 ) );
 	bufferGeometry.addAttribute('color', new THREE.BufferAttribute(new Float32Array( [0, 0, 0, 0.5, 0.5, 0.5, 1, 1, 1] ), 3 ) );
@@ -58,35 +57,35 @@ test( "fromBufferGeometry", function() {
 	var geometry = new THREE.Geometry().fromBufferGeometry( bufferGeometry );
 
 	var colors = geometry.colors;
-	ok (
+	assert.ok(
 		colors[0].r === 0 && colors[0].g === 0 && colors[0].b === 0 &&
 		colors[1].r === 0.5 && colors[1].g === 0.5 && colors[1].b === 0.5 &&
 		colors[2].r === 1 && colors[2].g === 1 && colors[2].b === 1
 		, "colors were created well" );
 
 	var vertices = geometry.vertices;
-	ok (
+	assert.ok(
 		vertices[0].x === 1 && vertices[0].y === 2 && vertices[0].z === 3 &&
 		vertices[1].x === 4 && vertices[1].y === 5 && vertices[1].z === 6 &&
 		vertices[2].x === 7 && vertices[2].y === 8 && vertices[2].z === 9
 		, "vertices were created well" );
 
 	var vNormals = geometry.faces[0].vertexNormals;
-	ok (
+	assert.ok(
 		vNormals[0].x === 0 && vNormals[0].y === 1 && vNormals[0].z === 0 &&
 		vNormals[1].x === 1 && vNormals[1].y === 0 && vNormals[1].z === 1 &&
 		vNormals[2].x === 1 && vNormals[2].y === 1 && vNormals[2].z === 0
 		, "vertex normals were created well" );
 });
 
-test( "normalize", function() {
+QUnit.test( "normalize" , function( assert ) {
 	var geometry = getGeometry();
 	geometry.computeLineDistances();
 
 	var distances = geometry.lineDistances;
-	ok( distances[0] === 0, "distance to the 1st point is 0" );
-	ok( distances[1] === 1 + distances[0], "distance from the 1st to the 2nd is sqrt(2nd - 1st) + distance - 1" );
-	ok( distances[2] === Math.sqrt( 0.5 * 0.5 + 1 ) + distances[1], "distance from the 1st to the 3nd is sqrt(3rd - 2nd) + distance - 1" );
+	assert.ok( distances[0] === 0, "distance to the 1st point is 0" );
+	assert.ok( distances[1] === 1 + distances[0], "distance from the 1st to the 2nd is sqrt(2nd - 1st) + distance - 1" );
+	assert.ok( distances[2] === Math.sqrt( 0.5 * 0.5 + 1 ) + distances[1], "distance from the 1st to the 3nd is sqrt(3rd - 2nd) + distance - 1" );
 });
 
 function getGeometryByParams( x1, y1, z1, x2, y2, z2, x3, y3, z3 ) {

+ 29 - 0
test/unit/src/core/InstancedBufferAttribute.js

@@ -0,0 +1,29 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "InstancedBufferAttribute" );
+
+QUnit.test( "can be created", function( assert ) {
+	var instance = new THREE.InstancedBufferAttribute(new Float32Array(10), 2);
+	assert.ok( instance.meshPerAttribute === 1, "ok" );
+
+	instance = new THREE.InstancedBufferAttribute(new Float32Array(10), 2, 123);
+	assert.ok( instance.meshPerAttribute === 123, "ok" );
+
+});
+
+QUnit.test( "copy" , function( assert ) {
+	var array = new Float32Array( [1, 2, 3, 7, 8, 9] );
+	var instance = new THREE.InstancedBufferAttribute( array, 2, 123 );
+	var copiedInstance = instance.copy( instance );
+
+	assert.ok( copiedInstance instanceof THREE.InstancedBufferAttribute, "the clone has the correct type" );
+	assert.ok( copiedInstance.itemSize === 2, "itemSize was copied" );
+	assert.ok( copiedInstance.meshPerAttribute === 123, "meshPerAttribute was copied" );
+
+	for (var i = 0; i < array.length; i++) {
+		assert.ok( copiedInstance.array[i] === array[i], "array was copied" );
+	}
+
+});

+ 53 - 0
test/unit/src/core/InstancedBufferGeometry.js

@@ -0,0 +1,53 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "InstancedBufferGeometry" );
+
+function createClonableMock() {
+	return {
+		callCount: 0,
+
+		clone: function() {
+			this.callCount++;
+
+			return this;
+		}
+	}
+}
+
+QUnit.test( "copy" , function( assert ) {
+	var instanceMock1 = {};
+	var instanceMock2 = {};
+	var indexMock = createClonableMock();
+	var defaultAttribute1 = new THREE.BufferAttribute([1]);
+	var defaultAttribute2 = new THREE.BufferAttribute([2]);
+
+	var instance = new THREE.InstancedBufferGeometry();
+
+	instance.addGroup( 0, 10, instanceMock1 );
+	instance.addGroup( 10, 5, instanceMock2 );
+	instance.setIndex( indexMock );
+	instance.addAttribute( 'defaultAttribute1', defaultAttribute1 );
+	instance.addAttribute( 'defaultAttribute2', defaultAttribute2 );
+
+	var copiedInstance = instance.copy( instance );
+
+	assert.ok( copiedInstance instanceof THREE.InstancedBufferGeometry, "the clone has the correct type" );
+
+	assert.ok( copiedInstance.index === indexMock, "index was copied" );
+	assert.ok( copiedInstance.index.callCount === 1, "index.clone was called once" );
+
+	assert.ok( copiedInstance.attributes['defaultAttribute1'] instanceof THREE.BufferAttribute, "attribute was created" );
+	// the given attribute mock was passed to the array property of the created buffer attribute
+	assert.ok( copiedInstance.attributes['defaultAttribute1'].array[0] === defaultAttribute1.array, "attribute was copied" );
+	assert.ok( copiedInstance.attributes['defaultAttribute2'].array[0] === defaultAttribute2.array, "attribute was copied" );
+
+	assert.ok( copiedInstance.groups[0].start === 0, "group was copied" );
+	assert.ok( copiedInstance.groups[0].count === 10, "group was copied" );
+	assert.ok( copiedInstance.groups[0].instances === instanceMock1, "group was copied" );
+
+	assert.ok( copiedInstance.groups[1].start === 10, "group was copied" );
+	assert.ok( copiedInstance.groups[1].count === 5, "group was copied" );
+	assert.ok( copiedInstance.groups[1].instances === instanceMock2, "group was copied" );
+});

+ 5 - 5
test/unit/core/InstancedInterleavedBuffer.js → test/unit/src/core/InstancedInterleavedBuffer.js

@@ -2,19 +2,19 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "InstancedInterleavedBuffer" );
+QUnit.module( "InstancedInterleavedBuffer" );
 
-test( "can be created", function() {
+QUnit.test( "can be created", function( assert ) {
 	var array = new Float32Array( [1, 2, 3, 7, 8, 9] );
 	var instance = new THREE.InstancedInterleavedBuffer( array, 3 );
 
-	ok( instance.meshPerAttribute === 1, "ok" );
+	assert.ok( instance.meshPerAttribute === 1, "ok" );
 });
 
-test( "copy", function() {
+QUnit.test( "copy" , function( assert ) {
 	var array = new Float32Array( [1, 2, 3, 7, 8, 9] );
 	var instance = new THREE.InstancedInterleavedBuffer( array, 3 );
 	var copiedInstance = instance.copy( instance );
 
-	ok( copiedInstance.meshPerAttribute === 1, "additional attribute was copied" );
+	assert.ok( copiedInstance.meshPerAttribute === 1, "additional attribute was copied" );
 });

+ 46 - 0
test/unit/src/core/InterleavedBuffer.js

@@ -0,0 +1,46 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "InterleavedBuffer" );
+
+function checkInstanceAgainstCopy( instance, copiedInstance, assert ) {
+	assert.ok( copiedInstance instanceof THREE.InterleavedBuffer, "the clone has the correct type" );
+
+	for ( var i = 0; i < instance.array.length; i++ ) {
+		assert.ok( copiedInstance.array[i] === instance.array[i], "array was copied" );
+	}
+
+	assert.ok( copiedInstance.stride === instance.stride, "stride was copied" );
+	assert.ok( copiedInstance.dynamic === true, "dynamic was copied" );
+}
+
+QUnit.test( "length and count", function( assert ) {
+	var instance = new THREE.InterleavedBuffer( new Float32Array( [1, 2, 3, 7, 8 ,9] ), 3 );
+
+	assert.ok( instance.length === 6, "length is calculated via array length" );
+	assert.ok( instance.count === 2, "count is calculated via array length / stride" );
+});
+
+QUnit.test( "copy" , function( assert ) {
+	var array = new Float32Array( [1, 2, 3, 7, 8 ,9] );
+	var instance = new THREE.InterleavedBuffer( array, 3 );
+	instance.setDynamic( true );
+
+	checkInstanceAgainstCopy(instance, instance.copy( instance ), assert );
+});
+
+QUnit.test( "clone" , function( assert ) {
+	var array = new Float32Array( [1, 2, 3, 7, 8 ,9] );
+	var instance = new THREE.InterleavedBuffer( array, 3 );
+	instance.setDynamic( true );
+
+	checkInstanceAgainstCopy( instance, instance.clone(), assert );
+});
+
+QUnit.test( "set" , function( assert ) {
+	var instance = new THREE.InterleavedBuffer( new Float32Array( [1, 2, 3, 7, 8 ,9] ), 3 );
+
+	instance.set( [0, -1] );
+	assert.ok( instance.array[0] === 0 && instance.array[1] === -1, "replace at first by default" );
+});

+ 6 - 6
test/unit/core/InterleavedBufferAttribute.js → test/unit/src/core/InterleavedBufferAttribute.js

@@ -2,23 +2,23 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "InterleavedBufferAttribute" );
+QUnit.module( "InterleavedBufferAttribute" );
 
-test( "length and count", function() {
+QUnit.test( "length and count", function( assert ) {
 	var buffer = new THREE.InterleavedBuffer( new Float32Array( [1, 2, 3, 7, 8 ,9] ), 3 );
 	var instance = new THREE.InterleavedBufferAttribute( buffer, 2, 0 );
 
-	ok( instance.count === 2, "count is calculated via array length / stride" );
+	assert.ok( instance.count === 2, "count is calculated via array length / stride" );
 });
 
-test( "setX", function() {
+QUnit.test( "setX" , function( assert ) {
 	var buffer = new THREE.InterleavedBuffer( new Float32Array( [1, 2, 3, 7, 8 ,9] ), 3 );
 	var instance = new THREE.InterleavedBufferAttribute( buffer, 2, 0 );
 
 	instance.setX( 0, 123 );
 	instance.setX( 1, 321 );
 
-	ok( instance.data.array[0] === 123 &&
+	assert.ok( instance.data.array[0] === 123 &&
 			instance.data.array[3] === 321, "x was calculated correct based on index and default offset" );
 
 
@@ -29,7 +29,7 @@ test( "setX", function() {
 	instance.setX( 1, 321 );
 
 	// the offset was defined as 1, so go one step futher in the array
-	ok( instance.data.array[1] === 123 &&
+	assert.ok( instance.data.array[1] === 123 &&
 			instance.data.array[4] === 321, "x was calculated correct based on index and default offset" );
 });
 

+ 6 - 0
test/unit/src/core/Layers.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Layers")

+ 102 - 0
test/unit/src/core/Object3D.js

@@ -0,0 +1,102 @@
+/**
+ * @author simonThiele / https://github.com/simonThiele
+ */
+
+QUnit.module( "Object3D" );
+
+var RadToDeg = 180 / Math.PI;
+
+QUnit.test( "rotateX" , function( assert ) {
+	var obj = new THREE.Object3D();
+
+	var angleInRad = 1.562;
+	obj.rotateX(angleInRad);
+
+	// should calculate the correct rotation on x
+	checkIfFloatsAreEqual(obj.rotation.x, angleInRad, assert);
+});
+
+QUnit.test( "rotateY" , function( assert ) {
+	var obj = new THREE.Object3D();
+
+	var angleInRad = -0.346;
+	obj.rotateY(angleInRad);
+
+	// should calculate the correct rotation on y
+	checkIfFloatsAreEqual(obj.rotation.y, angleInRad, assert);
+});
+
+QUnit.test( "rotateZ" , function( assert ) {
+	var obj = new THREE.Object3D();
+
+	var angleInRad = 1;
+	obj.rotateZ(angleInRad);
+
+	// should calculate the correct rotation on y
+	checkIfFloatsAreEqual(obj.rotation.z, angleInRad, assert);
+});
+
+QUnit.test( "translateOnAxis" , function( assert ) {
+	var obj = new THREE.Object3D();
+
+	// get a reference object for comparing
+	var reference = {x: 1, y: 1.23, z: -4.56};
+	obj.translateOnAxis(new THREE.Vector3(1, 0, 0), 1);
+	obj.translateOnAxis(new THREE.Vector3(0, 1, 0), 1.23);
+	obj.translateOnAxis(new THREE.Vector3(0, 0, 1), -4.56);
+
+	checkIfPropsAreEqual(reference, obj.position, assert);
+});
+
+QUnit.test( "translateX" , function( assert ) {
+	var obj = new THREE.Object3D();
+	obj.translateX(1.234);
+
+	assert.ok( obj.position.x === 1.234 , "x is equal" );
+});
+
+QUnit.test( "translateY" , function( assert ) {
+	var obj = new THREE.Object3D();
+	obj.translateY(1.234);
+
+	assert.ok( obj.position.y === 1.234 , "y is equal" );
+});
+
+QUnit.test( "translateZ" , function( assert ) {
+	var obj = new THREE.Object3D();
+	obj.translateZ(1.234);
+
+	assert.ok( obj.position.z === 1.234 , "z is equal" );
+});
+
+QUnit.test( "lookAt" , function( assert ) {
+	var obj = new THREE.Object3D();
+	obj.lookAt(new THREE.Vector3(0, -1, 1));
+
+	assert.ok( obj.rotation.x * RadToDeg === 45 , "x is equal" );
+});
+
+QUnit.test( "getWorldRotation" , function( assert ) {
+	var obj = new THREE.Object3D();
+
+	obj.lookAt(new THREE.Vector3(0, -1, 1));
+	assert.ok( obj.getWorldRotation().x * RadToDeg === 45 , "x is equal" );
+
+	obj.lookAt(new THREE.Vector3(1, 0, 0));
+	assert.ok( obj.getWorldRotation().y * RadToDeg === 90 , "y is equal" );
+});
+
+function checkIfPropsAreEqual(reference, obj, assert) {
+	assert.ok( obj.x === reference.x , "x is equal" );
+	assert.ok( obj.y === reference.y , "y is equal!" );
+	assert.ok( obj.z === reference.z , "z is equal!" );
+}
+
+// since float equal checking is a mess in js, one solution is to cut off
+// decimal places
+function checkIfFloatsAreEqual(f1, f2, assert) {
+	var f1Rounded = ((f1 * 1000) | 0) / 1000;
+	var f2Rounded = ((f2 * 1000) | 0) / 1000;
+
+	assert.ok( f1Rounded === f2Rounded, "passed" );
+}

+ 14 - 14
test/unit/core/Raycaster.js → test/unit/src/core/Raycaster.js

@@ -2,51 +2,51 @@
  * @author simonThiele / https://github.com/simonThiele
  */
 
-module( "Raycaster" );
+QUnit.module( "Raycaster" );
 
-test( "intersectObjects", function() {
+QUnit.test( "intersectObjects" , function( assert ) {
 	var raycaster = getRaycaster();
 	var objectsToCheck = getObjectsToCheck();
 
-	ok ( raycaster.intersectObjects( objectsToCheck ).length === 1,
+	assert.ok( raycaster.intersectObjects( objectsToCheck ).length === 1,
 		"no recursive search should lead to one hit" );
 
-	ok ( raycaster.intersectObjects( objectsToCheck, true ).length === 3,
+	assert.ok( raycaster.intersectObjects( objectsToCheck, true ).length === 3,
 		"recursive search should lead to three hits" );
 
 	var intersections = raycaster.intersectObjects( objectsToCheck, true );
 	for ( var i = 0; i < intersections.length - 1; i++ ) {
 
-	  ok( intersections[ i ].distance <= intersections[ i + 1 ].distance, "intersections are sorted" );
+	  assert.ok( intersections[ i ].distance <= intersections[ i + 1 ].distance, "intersections are sorted" );
 
 	}
 });
 
-test( "intersectObject", function() {
+QUnit.test( "intersectObject" , function( assert ) {
 	var raycaster = getRaycaster();
 	var objectsToCheck = getObjectsToCheck();
 
-	ok ( raycaster.intersectObject( objectsToCheck[ 0 ] ).length === 1,
+	assert.ok( raycaster.intersectObject( objectsToCheck[ 0 ] ).length === 1,
 		"no recursive search should lead to one hit" );
 
-	ok ( raycaster.intersectObject( objectsToCheck[ 0 ], true ).length === 3,
+	assert.ok( raycaster.intersectObject( objectsToCheck[ 0 ], true ).length === 3,
 		"recursive search should lead to three hits" );
 
 	var intersections = raycaster.intersectObject( objectsToCheck[ 0 ], true );
 	for ( var i = 0; i < intersections.length - 1; i++ ) {
 
-	  ok( intersections[ i ].distance <= intersections[ i + 1 ].distance, "intersections are sorted" );
+	  assert.ok( intersections[ i ].distance <= intersections[ i + 1 ].distance, "intersections are sorted" );
 
 	}
 });
 
-test( "setFromCamera", function() {
+QUnit.test( "setFromCamera" , function( assert ) {
 	var raycaster = new THREE.Raycaster();
 	var rayDirection = raycaster.ray.direction;
 	var camera = new THREE.PerspectiveCamera( 90, 1, 1, 1000 );
 
 	raycaster.setFromCamera( { x : 0, y: 0 }, camera );
-	ok( rayDirection.x === 0, rayDirection.y === 0, rayDirection.z === -1,
+	assert.ok( rayDirection.x === 0, rayDirection.y === 0, rayDirection.z === -1,
 		"camera is looking straight to -z and so does the ray in the middle of the screen" );
 
 	var step = 0.1;
@@ -59,15 +59,15 @@ test( "setFromCamera", function() {
 
 			var refVector = new THREE.Vector3( x, y, -1 ).normalize();
 
-			checkRayDirectionAgainstReferenceVector( rayDirection, refVector );
+			checkRayDirectionAgainstReferenceVector( rayDirection, refVector, assert );
 
 		}
 
 	}
 });
 
-function checkRayDirectionAgainstReferenceVector( rayDirection, refVector ) {
-	ok( refVector.x - rayDirection.x <= Number.EPSILON &&
+function checkRayDirectionAgainstReferenceVector( rayDirection, refVector, assert ) {
+	assert.ok( refVector.x - rayDirection.x <= Number.EPSILON &&
 			refVector.y - rayDirection.y <= Number.EPSILON &&
 			refVector.z - rayDirection.z <= Number.EPSILON,
 			"camera is pointing to the same direction as expected" );

+ 6 - 0
test/unit/src/core/Uniform.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Uniform")

+ 6 - 0
test/unit/src/extras/SceneUtils.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of SceneUtils")

+ 6 - 0
test/unit/src/extras/ShapeUtils.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of ShapeUtils")

+ 6 - 0
test/unit/src/extras/core/Curve.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Curve")

+ 6 - 0
test/unit/src/extras/core/CurvePath.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of CurvePath")

+ 6 - 0
test/unit/src/extras/core/Font.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Font")

+ 6 - 0
test/unit/src/extras/core/Interpolations.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Interpolations")

+ 6 - 0
test/unit/src/extras/core/Path.js

@@ -0,0 +1,6 @@
+/**
+ * @author TristanVALCKE / https://github.com/TristanVALCKE
+ */
+
+//Todo
+console.warn("Todo: Unit tests of Path")

이 변경점에서 너무 많은 파일들이 변경되어 몇몇 파일들은 표시되지 않았습니다.