Mr.doob 10 years ago
parent
commit
c8bcf9a5ab
100 changed files with 2634 additions and 2074 deletions
  1. 240 144
      build/three.js
  2. 237 229
      build/three.min.js
  3. 1 1
      docs/api/cameras/CubeCamera.html
  4. 3 1
      docs/api/constants/CustomBlendingEquations.html
  5. 1 1
      docs/api/constants/GLState.html
  6. 14 3
      docs/api/constants/Textures.html
  7. 4 6
      docs/api/core/Object3D.html
  8. 4 4
      docs/api/core/Raycaster.html
  9. 6 4
      docs/api/extras/geometries/CylinderGeometry.html
  10. 3 3
      docs/api/extras/helpers/ArrowHelper.html
  11. 1 1
      docs/api/extras/helpers/BoundingBoxHelper.html
  12. 45 0
      docs/api/extras/helpers/BoxHelper.html
  13. 1 1
      docs/api/extras/helpers/CameraHelper.html
  14. 12 12
      docs/api/extras/helpers/DirectionalLightHelper.html
  15. 23 15
      docs/api/extras/helpers/EdgesHelper.html
  16. 23 11
      docs/api/extras/helpers/FaceNormalsHelper.html
  17. 1 0
      docs/api/extras/helpers/GridHelper.html
  18. 9 11
      docs/api/extras/helpers/HemisphereLightHelper.html
  19. 1 0
      docs/api/extras/helpers/PointLightHelper.html
  20. 23 11
      docs/api/extras/helpers/VertexNormalsHelper.html
  21. 22 12
      docs/api/extras/helpers/VertexTangentsHelper.html
  22. 24 15
      docs/api/extras/helpers/WireframeHelper.html
  23. 26 31
      docs/api/lights/DirectionalLight.html
  24. 9 34
      docs/api/lights/SpotLight.html
  25. 2 3
      docs/api/loaders/ColladaLoader.html
  26. 1 1
      docs/api/loaders/OBJMTLLoader.html
  27. 0 114
      docs/api/loaders/SceneLoader.html
  28. 1 6
      docs/api/materials/MeshLambertMaterial.html
  29. 6 13
      docs/api/materials/MeshNormalMaterial.html
  30. 2 7
      docs/api/materials/MeshPhongMaterial.html
  31. 1 1
      docs/api/materials/SpriteMaterial.html
  32. 8 0
      docs/api/math/Color.html
  33. 141 138
      docs/api/math/Euler.html
  34. 1 2
      docs/api/math/Matrix4.html
  35. 8 5
      docs/api/math/Quaternion.html
  36. 14 1
      docs/api/math/Vector2.html
  37. 14 1
      docs/api/math/Vector3.html
  38. 14 6
      docs/api/math/Vector4.html
  39. 1 1
      docs/api/renderers/WebGLRenderTarget.html
  40. 16 4
      docs/index.html
  41. 1 1
      docs/list.js
  42. 1 5
      docs/scenes/js/material.js
  43. 25 16
      editor/css/dark.css
  44. 14 13
      editor/css/light.css
  45. 16 0
      editor/css/main.css
  46. 4 7
      editor/examples/arkanoid.app.json
  47. 63 53
      editor/examples/camera.app.json
  48. 6 8
      editor/examples/particles.app.json
  49. 4 7
      editor/examples/pong.app.json
  50. 14 3
      editor/index.html
  51. 6 5
      editor/js/Config.js
  52. 28 17
      editor/js/Editor.js
  53. 0 32
      editor/js/Menubar.Edit.js
  54. 15 8
      editor/js/Menubar.File.js
  55. 2 2
      editor/js/Player.js
  56. 87 4
      editor/js/Script.js
  57. 2 2
      editor/js/Sidebar.Geometry.BufferGeometry.js
  58. 2 2
      editor/js/Sidebar.Geometry.Geometry.js
  59. 62 2
      editor/js/Sidebar.Geometry.js
  60. 33 44
      editor/js/Sidebar.Material.js
  61. 73 6
      editor/js/Sidebar.Object3D.js
  62. 27 12
      editor/js/Sidebar.Project.js
  63. 3 3
      editor/js/Sidebar.Scene.js
  64. 1 1
      editor/js/Sidebar.Script.js
  65. 1 1
      editor/js/Sidebar.js
  66. 1 1
      editor/js/Storage.js
  67. 0 2
      editor/js/Toolbar.js
  68. 1 7
      editor/js/Viewport.js
  69. 104 21
      editor/js/libs/app.js
  70. 197 0
      editor/js/libs/esprima.js
  71. 1 0
      editor/js/libs/sortable.min.js
  72. 17 174
      editor/js/libs/ui.js
  73. 176 0
      editor/js/libs/ui.three.js
  74. 7 4
      examples/index.html
  75. 1 1
      examples/js/AudioObject.js
  76. 9 9
      examples/js/BlendCharacter.js
  77. 3 3
      examples/js/Car.js
  78. 26 26
      examples/js/Cloth.js
  79. 9 9
      examples/js/CurveExtras.js
  80. 1 1
      examples/js/Detector.js
  81. 10 10
      examples/js/ImprovedNoise.js
  82. 1 1
      examples/js/MD2Character.js
  83. 3 3
      examples/js/MD2CharacterComplex.js
  84. 23 23
      examples/js/MarchingCubes.js
  85. 10 9
      examples/js/Ocean.js
  86. 43 43
      examples/js/Octree.js
  87. 6 6
      examples/js/ParametricGeometries.js
  88. 11 10
      examples/js/ShaderDeferred.js
  89. 54 92
      examples/js/ShaderSkin.js
  90. 25 59
      examples/js/ShaderTerrain.js
  91. 233 233
      examples/js/SimplexNoise.js
  92. 2 2
      examples/js/SimulationRenderer.js
  93. 16 23
      examples/js/SkyShader.js
  94. 154 154
      examples/js/Sparks.js
  95. 5 5
      examples/js/TypedArrayUtils.js
  96. 1 1
      examples/js/cameras/CombinedCamera.js
  97. 3 7
      examples/js/controls/EditorControls.js
  98. 2 2
      examples/js/controls/FirstPersonControls.js
  99. 1 1
      examples/js/controls/FlyControls.js
  100. 25 25
      examples/js/controls/MouseControls.js

File diff suppressed because it is too large
+ 240 - 144
build/three.js


File diff suppressed because it is too large
+ 237 - 229
build/three.min.js


+ 1 - 1
docs/api/cameras/CubeCamera.html

@@ -24,7 +24,7 @@
 		scene.add( cubeCamera );
 		scene.add( cubeCamera );
 		
 		
 		//Create car
 		//Create car
-		var chromeMaterial = new THREE.MeshLambertMaterial( { color: 0xffffff, ambient: 0xffffff, envMap: cubeCamera.renderTarget } );
+		var chromeMaterial = new THREE.MeshLambertMaterial( { color: 0xffffff, envMap: cubeCamera.renderTarget } );
 		var car = new Mesh( carGeometry, chromeMaterial );
 		var car = new Mesh( carGeometry, chromeMaterial );
 		scene.add( car );
 		scene.add( car );
 		
 		

+ 3 - 1
docs/api/constants/CustomBlendingEquations.html

@@ -13,7 +13,9 @@
 		<div>
 		<div>
 		THREE.AddEquation<br />
 		THREE.AddEquation<br />
 		THREE.SubtractEquation<br />
 		THREE.SubtractEquation<br />
-		THREE.ReverseSubtractEquation
+		THREE.ReverseSubtractEquation<br />
+		THREE.MinEquation<br />
+		THREE.MaxEquation
 		</div>
 		</div>
 
 
 		<h2>Destination Factors</h2>
 		<h2>Destination Factors</h2>

+ 1 - 1
docs/api/constants/GLState.html

@@ -7,7 +7,7 @@
 		<link type="text/css" rel="stylesheet" href="../../page.css" />
 		<link type="text/css" rel="stylesheet" href="../../page.css" />
 	</head>
 	</head>
 	<body>
 	<body>
-		<h1>GL State Conflicts</h1>
+		<h1>GL State Constants</h1>
 
 
 		<h2>Cull Face</h2>
 		<h2>Cull Face</h2>
 		<div>
 		<div>

+ 14 - 3
docs/api/constants/Textures.html

@@ -21,6 +21,8 @@
 		THREE.UVMapping<br />
 		THREE.UVMapping<br />
 		THREE.CubeReflectionMapping<br />
 		THREE.CubeReflectionMapping<br />
 		THREE.CubeRefractionMapping<br />
 		THREE.CubeRefractionMapping<br />
+		THREE.EquirectangularReflectionMapping<br />
+		THREE.EquirectangularRefractionMapping<br />
 		THREE.SphericalReflectionMapping
 		THREE.SphericalReflectionMapping
 		</div>
 		</div>
 
 
@@ -49,7 +51,8 @@
 		THREE.UnsignedShortType<br />
 		THREE.UnsignedShortType<br />
 		THREE.IntType<br />
 		THREE.IntType<br />
 		THREE.UnsignedIntType<br />
 		THREE.UnsignedIntType<br />
-		THREE.FloatType
+		THREE.FloatType<br />
+		THREE.HalfFloatType
 		</div>
 		</div>
 
 
 		<h2>Pixel Types</h2>
 		<h2>Pixel Types</h2>
@@ -65,10 +68,11 @@
 		THREE.RGBFormat<br />
 		THREE.RGBFormat<br />
 		THREE.RGBAFormat<br />
 		THREE.RGBAFormat<br />
 		THREE.LuminanceFormat<br />
 		THREE.LuminanceFormat<br />
-		THREE.LuminanceAlphaFormat
+		THREE.LuminanceAlphaFormat<br />
+		THREE.RGBEFormat
 		</div>
 		</div>
 
 
-		<h2>Compressed Texture Formats</h2>
+		<h2>DDS / ST3C Compressed Texture Formats</h2>
 		<div>
 		<div>
 		THREE.RGB_S3TC_DXT1_Format<br />
 		THREE.RGB_S3TC_DXT1_Format<br />
 		THREE.RGBA_S3TC_DXT1_Format<br />
 		THREE.RGBA_S3TC_DXT1_Format<br />
@@ -76,6 +80,13 @@
 		THREE.RGBA_S3TC_DXT5_Format
 		THREE.RGBA_S3TC_DXT5_Format
 		</div>
 		</div>
 
 
+		<h2>PVRTC Compressed Texture Formats</h2>
+		<div>
+		THREE.RGB_PVRTC_4BPPV1_Format<br />
+		THREE.RGB_PVRTC_2BPPV1_Format<br />
+		THREE.RGBA_PVRTC_4BPPV1_Format<br />
+		THREE.RGBA_PVRTC_2BPPV1_Format
+		</div>
 
 
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 

+ 4 - 6
docs/api/core/Object3D.html

@@ -263,22 +263,20 @@
 		</div>
 		</div>
 
 
 
 
-		<h3>[method:Object3D getObjectByName]([page:String name], [page:Boolean recursive])</h3>
+		<h3>[method:Object3D getObjectByName]([page:String name])</h3>
 		<div>
 		<div>
 		name -- String to match to the children's Object3d.name property. <br />
 		name -- String to match to the children's Object3d.name property. <br />
-		recursive -- Boolean whether to search through the children's children. Default is false.
 		</div>
 		</div>
 		<div>
 		<div>
-		Searches through the object's children and returns the first with a matching name, optionally recursive.
+		Searches through the object's children and returns the first with a matching name.
 		</div>
 		</div>
 
 
-		<h3>[method:Object3D getObjectById]([page:Integer id], [page:Boolean recursive])</h3>
+		<h3>[method:Object3D getObjectById]([page:Integer id])</h3>
 		<div>
 		<div>
 		id -- Unique number of the object instance<br />
 		id -- Unique number of the object instance<br />
-		recursive -- Boolean whether to search through the children's children. Default is false.
 		</div>
 		</div>
 		<div>
 		<div>
-		Searches through the object's children and returns the first with a matching id, optionally recursive.
+		Searches through the object's children and returns the first with a matching id.
 		</div>
 		</div>
 
 
 		<h3>[method:Object3D translateOnAxis]([page:Vector3 axis], [page:Float distance])</h3>
 		<h3>[method:Object3D translateOnAxis]([page:Vector3 axis], [page:Float distance])</h3>

+ 4 - 4
docs/api/core/Raycaster.html

@@ -23,8 +23,8 @@
 			// calculate mouse position in normalized device coordinates
 			// calculate mouse position in normalized device coordinates
 			// (-1 to +1) for both components
 			// (-1 to +1) for both components
 
 
-			mouse.x = ( event.clientX / window.innerWidth ) * 2 - 1
-			mouse.y = - ( event.clientY / window.innerHeight ) * 2 + 1		
+			mouse.x = ( event.clientX / window.innerWidth ) * 2 - 1;
+			mouse.y = - ( event.clientY / window.innerHeight ) * 2 + 1;		
 		
 		
 		}
 		}
 
 
@@ -36,9 +36,9 @@
 			// calculate objects intersecting the picking ray
 			// calculate objects intersecting the picking ray
 			var intersects = raycaster.intersectObjects( scene.children );
 			var intersects = raycaster.intersectObjects( scene.children );
 
 
-			for ( var intersect in intersects ) {
+			for ( var i = 0; i < intersects.length; i++ ) {
 
 
-				intersect.object.material.color = new THREE.Color( 0xff0000 );
+				intersects[ i ].object.material.color.set( 0xff0000 );
 			
 			
 			}
 			}
 			
 			

+ 6 - 4
docs/api/extras/geometries/CylinderGeometry.html

@@ -8,7 +8,7 @@
 	</head>
 	</head>
 	<body>
 	<body>
 		[page:Geometry] &rarr;
 		[page:Geometry] &rarr;
-		
+
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
 		<div class="desc">A class for generating cylinder geometries</div>
 		<div class="desc">A class for generating cylinder geometries</div>
@@ -26,21 +26,23 @@
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
 
 
 
 
-		<h3>[name]([page:Float radiusTop], [page:Float radiusBottom], [page:Float height], [page:Integer radiusSegments], [page:Integer heightSegments], [page:Boolean openEnded])</h3>
+		<h3>[name]([page:Float radiusTop], [page:Float radiusBottom], [page:Float height], [page:Integer radiusSegments], [page:Integer heightSegments], [page:Boolean openEnded], [page:Float thetaStart], [page:Float thetaLength])</h3>
 		<div>
 		<div>
 		radiusTop — Radius of the cylinder at the top. Default is 20.<br />
 		radiusTop — Radius of the cylinder at the top. Default is 20.<br />
 		radiusBottom — Radius of the cylinder at the bottom. Default is 20.<br />
 		radiusBottom — Radius of the cylinder at the bottom. Default is 20.<br />
 		height — Height of the cylinder. Default is 100.<br />
 		height — Height of the cylinder. Default is 100.<br />
 		radiusSegments — Number of segmented faces around the circumference of the cylinder. Default is 8<br />
 		radiusSegments — Number of segmented faces around the circumference of the cylinder. Default is 8<br />
 		heightSegments — Number of rows of faces along the height of the cylinder. Default is 1.<br />
 		heightSegments — Number of rows of faces along the height of the cylinder. Default is 1.<br />
-		openEnded — A Boolean indicating whether the ends of the cylinder are open or capped. Default is false, meaning capped.
+		openEnded — A Boolean indicating whether the ends of the cylinder are open or capped. Default is false, meaning capped.<br />
+		thetaStart — Start angle for first segment, default = 0 (three o'clock position).<br />
+		thetaLength — The central angle, often called theta, of the circular sector. The default is 2*Pi, which makes for a complete cylinder.
 		</div>
 		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
 		<div>
 		<div>
-		Each of the contructor parameters is accessible as a property of the same name. Any modification of these properties after instantiation does not change the geometry.
+		Each of the constructor parameters is accessible as a property of the same name. Any modification of these properties after instantiation does not change the geometry.
 		</div>
 		</div>
 
 
 
 

+ 3 - 3
docs/api/extras/helpers/ArrowHelper.html

@@ -74,15 +74,15 @@
 		<div>
 		<div>
 		length -- The desired length<br />
 		length -- The desired length<br />
 		headLength -- The length of the head of the arrow<br />
 		headLength -- The length of the head of the arrow<br />
-		headWidth -- The length of the width of the arrow		
+		headWidth -- The length of the width of the arrow
 		</div>
 		</div>
 		<div>
 		<div>
 		Sets the length of the arrowhelper.
 		Sets the length of the arrowhelper.
 		</div>
 		</div>
 
 
-		<h3>[method:null setDirection]([page:vector3 dir])</h3>
+		<h3>[method:null setDirection]([page:Vector3 dir])</h3>
 		<div>
 		<div>
-		dir -- The desired direction in euler format.
+		dir -- The desired direction. Must be a unit vector.
 		</div>
 		</div>
 		<div>
 		<div>
 		Sets the direction of the arrowhelper.
 		Sets the direction of the arrowhelper.

+ 1 - 1
docs/api/extras/helpers/BoundingBoxHelper.html

@@ -26,7 +26,7 @@
 		bbox.update();
 		bbox.update();
 		scene.add( bbox );
 		scene.add( bbox );
 		</code>
 		</code>
-
+		<div>Note that this helper will create a wireframe [page:Mesh] object with a [page:BoxGeometry]; the resulting bounding box object will therefore have face diagonals. You may want to use [page:BoxHelper], which generates a [page:Line] object without face diagonals.</div>
 
 
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>

+ 45 - 0
docs/api/extras/helpers/BoxHelper.html

@@ -0,0 +1,45 @@
+<!DOCTYPE html>
+<html lang="en">
+	<head>
+		<meta charset="utf-8" />
+		<script src="../../../list.js"></script>
+		<script src="../../../page.js"></script>
+		<link type="text/css" rel="stylesheet" href="../../../page.css" />
+	</head>
+	<body>
+		[page:Line] &rarr;
+		
+		<h1>[name]</h1>
+
+		<div class="desc">Helper object to show a wireframe box (with no face diagonals) around an object</div>
+
+
+		<h2>Example</h2>
+
+		<code>var sphere = new THREE.SphereGeometry();
+		var object = new THREE.Mesh( sphere, new THREE.MeshBasicMaterial(0xff0000) );
+		var box = new THREE.BoxHelper( object );
+		scene.add( box );
+		</code>
+
+
+		<h2>Constructor</h2>
+
+		<h3>[name]( [page:Object3D object] )</h3>
+		<div>Creates a new wireframe box matching the size of the passed box.</div>
+
+		<h2>Properties</h2>
+
+		<div>(none)</div>
+
+		<h2>Methods</h2>
+
+		<h3>[method:null update]( [page:Object3D object] )</h3>
+		<div>
+		Updates the helper's geometry to match the dimensions of the [page:Geometry.boundingBox bounding box] of the passed object's geometry.
+
+		<h2>Source</h2>
+
+		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]
+	</body>
+</html>

+ 1 - 1
docs/api/extras/helpers/CameraHelper.html

@@ -45,7 +45,7 @@
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 
 
 
 
-		<h3>[method:todo update]()</h3>
+		<h3>[method:null update]()</h3>
 		<div>
 		<div>
 		Updates the helper based on the projectionMatrix of the camera.
 		Updates the helper based on the projectionMatrix of the camera.
 		</div>
 		</div>

+ 12 - 12
docs/api/extras/helpers/DirectionalLightHelper.html

@@ -11,46 +11,46 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Visualize a [page:DirectionalLight]'s effect on the scene</div>
 
 
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
 
 
 
 
-		<h3>[name]([page:todo light], [page:todo sphereSize])</h3>
+		<h3>[name]([page:DirectionalLight light], [page:Number size])</h3>
 		<div>
 		<div>
-		light -- todo <br />
-		sphereSize -- todo
+		light -- [page:DirectionalLight] -- Light to visualize <br />
+		size -- dimensions of the plane
 		</div>
 		</div>
 		<div>
 		<div>
-		todo
+		Creates a line and plane to visualize the light's position and direction
 		</div>
 		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 		
 		
 
 
-		<h3>[property:Mesh lightSphere]</h3>
+		<h3>[property:Line lightPlane]</h3>
 		<div>
 		<div>
-		todo
+		Contains the line mesh showing the location of the directional light.
 		</div> 
 		</div> 
 
 
 		<h3>[property:DirectionalLight light]</h3>
 		<h3>[property:DirectionalLight light]</h3>
 		<div>
 		<div>
-		todo
+		Contains the directionalLight.
 		</div> 
 		</div> 
 
 
 		<h3>[property:Line targetLine]</h3>
 		<h3>[property:Line targetLine]</h3>
 		<div>
 		<div>
-		todo
-		</div> 
+		Contains the line mesh that shows the direction of the light. 
+		</div>
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 
 
 
 
-		<h3>.update() [page:todo]</h3>
+		<h3>.[method:null update]()</h3>
 		<div>
 		<div>
-		todo
+		Updates the helper to match the position and direction of the [page:.light].
 		</div>
 		</div>
 
 
 		<h2>Source</h2>
 		<h2>Source</h2>

+ 23 - 15
docs/api/extras/helpers/EdgesHelper.html

@@ -11,36 +11,44 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Creates a wireframe object that shows the "hard" edges of another object's geometry. To draw a full wireframe image of an object, see [page:WireframeHelper].</div>
 
 
 		<h2>Example</h2>
 		<h2>Example</h2>
 
 
-		<code>todo</code>
+		<code>
+		geometry = new THREE.BoxGeometry( 10, 10, 10, 2, 2, 2 );
+		material = new THREE.MeshBasicMaterial( { color: 0xff0000 } );
+		object = new THREE.Mesh( geometry, material );
 
 
-		<h2>Constructor</h2>
+		edges = new THREE.EdgesHelper( object, 0x00ff00 );
+
+		scene.add( object );
+		scene.add( edges );
+		</code>
 
 
+		<h2>Constructor</h2>
+		<h3>[name]( [page:Object3D object], [page:Color color], [page:Float thresholdAngle] )</h3>
+		<div>
+		object -- Object of which to draw edges <br />
+		color -- Color of the edges.<br />
+		thresholdAngle -- the minimim angle (in degrees), between the face normals of adjacent faces, that is required to render an edge. Default is 0.1.
 
 
-		<h3>todo</h3>
-		<div></div>
+		</div>
+		<div>
+		Creates a [page:Line], showing only the "hard" edges of the passed object; specifically, no edge will be drawn between faces which are adjacent and coplanar (or nearly coplanar).
+		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
-		<h3>todo</h3>
-		<div>
-		todo
-		</div> 
+		<div>none</div>
 
 
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 		
 		
-
-		<h3>todo</h3>
-		<div>todo</div>
-		<div>
-		todo
-		</div>
+		<div>none</div>
 		
 		
+
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 
 		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]
 		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]

+ 23 - 11
docs/api/extras/helpers/FaceNormalsHelper.html

@@ -11,35 +11,47 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Renders [page:ArrowHelper arrows] to visualize an object's [page:Face3 face] normals. Requires that the object's geometry be an instance of [page:Geometry] (does not work with [page:BufferGeometry]), and that face normals have been specified on all [page:Face3 faces] or calculated with [page:Geometry.computeFaceNormals computeFaceNormals].</div>
 
 
 		<h2>Example</h2>
 		<h2>Example</h2>
 
 
-		<code>todo</code>
+		<code>
+		geometry = new THREE.BoxGeometry( 10, 10, 10, 2, 2, 2 );
+		material = new THREE.MeshBasicMaterial( { color: 0xff0000 } );
+		object = new THREE.Mesh( geometry, material );
+
+		edges = new THREE.FaceNormalsHelper( object, 2, 0x00ff00, 1 );
+
+		scene.add( object );
+		scene.add( edges );
+		</code>
+		[example:webgl_helpers Example using various helpers]
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
 
 
 
 
-		<h3>todo</h3>
-		<div></div>
+		<h3>[name]( [page:Object3D object], [page:Number size], [page:Color color], [page:Number linewidth] )</h3>
+		<div>object -- object for which to render face normals
+		size -- size (length) of the arrows
+		color -- color of the arrows
+		linewidth -- width of the arrow lines
+		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
-		<h3>todo</h3>
+		<h3>[property:Object3D object]</h3>
 		<div>
 		<div>
-		todo
+		The attached object
 		</div> 
 		</div> 
 
 
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 		
 		
 
 
-		<h3>todo</h3>
-		<div>todo</div>
-		<div>
-		todo
-		</div>
+		<h3>[method:null update]()</h3>
+		<div>Updates the face normal preview based on movement of the object.</div>
+
 		
 		
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 

+ 1 - 0
docs/api/extras/helpers/GridHelper.html

@@ -22,6 +22,7 @@
 		var gridHelper = new THREE.GridHelper( size, step );		
 		var gridHelper = new THREE.GridHelper( size, step );		
 		scene.add( gridHelper );
 		scene.add( gridHelper );
 		</code>
 		</code>
+		[example:webgl_helpers Example using various helpers]
 
 
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>

+ 9 - 11
docs/api/extras/helpers/HemisphereLightHelper.html

@@ -11,20 +11,18 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Creates a visual aid for a [page:HemisphereLight HemisphereLight].</div>
 
 
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
 
 
-		<h3>[name]([page:todo light], [page:todo sphereSize], [page:todo arrowLength], [page:todo domeSize])</h3>
+		<h3>[name]([page:HemisphereLight light], [page:Number sphereSize])</h3>
 		<div>
 		<div>
-		light -- todo <br />
-		sphereSize -- todo <br />
-		arrowLength -- todo <br />
-		domeSize -- todo
+		light -- The HemisphereLight. <br />
+		sphereSize -- The size of the sphere that shows the location.
 		</div>
 		</div>
 		<div>
 		<div>
-		todo
+		Creates an helper for the hemispherelight.
 		</div>
 		</div>
 
 
 
 
@@ -32,20 +30,20 @@
 
 
 		<h3>[property:Mesh lightSphere]</h3>
 		<h3>[property:Mesh lightSphere]</h3>
 		<div>
 		<div>
-		todo
+		The sphere mesh that shows the location of the hemispherelight. 
 		</div> 
 		</div> 
 
 
 		<h3>[property:HemisphereLight light]</h3>
 		<h3>[property:HemisphereLight light]</h3>
 		<div>
 		<div>
-		todo
+		Contains the HemisphereLight.
 		</div> 
 		</div> 
 
 
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 
 
-		<h3>[method:todo update]()</h3>
+		<h3>[method:null update]()</h3>
 		<div>
 		<div>
-		todo
+		Updates the helper to match the position and direction of the [page:.light].
 		</div>
 		</div>
 
 
 
 

+ 1 - 0
docs/api/extras/helpers/PointLightHelper.html

@@ -24,6 +24,7 @@
 		var pointLightHelper = new THREE.PointLightHelper( pointLight, sphereSize );
 		var pointLightHelper = new THREE.PointLightHelper( pointLight, sphereSize );
 		scene.add( pointLightHelper );
 		scene.add( pointLightHelper );
 		</code>
 		</code>
+		[example:webgl_helpers Example using various helpers]
 
 
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>

+ 23 - 11
docs/api/extras/helpers/VertexNormalsHelper.html

@@ -11,35 +11,47 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Renders [page:ArrowHelper arrows] to visualize an object's vertex normal vectors. Requires that normals have been specified in a [page:BufferAttribute custom attribute] or have been calculated using [page:Geometry.computeVertexNormals computeVertexNormals]. </div>
 
 
 		<h2>Example</h2>
 		<h2>Example</h2>
 
 
-		<code>todo</code>
+		<code>
+		geometry = new THREE.BoxGeometry( 10, 10, 10, 2, 2, 2 );
+		material = new THREE.MeshBasicMaterial( { color: 0xff0000 } );
+		object = new THREE.Mesh( geometry, material );
+
+		edges = new THREE.VertexNormalsHelper( object, 2, 0x00ff00, 1 );
+
+		scene.add( object );
+		scene.add( edges );
+		</code>
+		[example:webgl_helpers Example using various helpers]
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
 
 
 
 
-		<h3>todo</h3>
-		<div></div>
+		<h3>[name]( [page:Object3D object], [page:Number size], [page:Color color], [page:Number linewidth] )</h3>
+		<div>object -- object for which to render vertex normals
+		size -- size (length) of the arrows
+		color -- color of the arrows
+		linewidth -- width of the arrow lines
+		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
-		<h3>todo</h3>
+		<h3>[property:Object3D object]</h3>
 		<div>
 		<div>
-		todo
+		The attached object
 		</div> 
 		</div> 
 
 
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 		
 		
 
 
-		<h3>todo</h3>
-		<div>todo</div>
-		<div>
-		todo
-		</div>
+		<h3>[method:null update]()</h3>
+		<div>Updates the vertex normal preview based on movement of the object.</div>
+
 		
 		
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 

+ 22 - 12
docs/api/extras/helpers/VertexTangentsHelper.html

@@ -11,36 +11,46 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Renders [page:ArrowHelper arrows] to visualize an object's vertex tangent vectors. Requires that tangents have been specified in a [page:BufferAttribute custom attribute] or have been computed using [page:Geometry.computeTangents computeTangents]. </div>
 
 
 		<h2>Example</h2>
 		<h2>Example</h2>
 
 
-		<code>todo</code>
+		<code>
+		geometry = new THREE.BoxGeometry( 10, 10, 10, 2, 2, 2 );
+		material = new THREE.MeshBasicMaterial( { color: 0xff0000 } );
+		object = new THREE.Mesh( geometry, material );
+
+		edges = new THREE.VertexTangentsHelper( object, 2, 0x00ff00, 1 );
+
+		scene.add( object );
+		scene.add( edges );
+		</code>
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
 
 
 
 
-		<h3>todo</h3>
-		<div></div>
+		<h3>[name]( [page:Object3D object], [page:Number size], [page:Color color], [page:Number linewidth] )</h3>
+		<div>object -- object for which to render vertex tangents
+		size -- size (length) of the arrows
+		color -- color of the arrows
+		linewidth -- width of the arrow lines
+		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
-		<h3>todo</h3>
+		<h3>[property:Object3D object]</h3>
 		<div>
 		<div>
-		todo
+		The attached object
 		</div> 
 		</div> 
 
 
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 		
 		
 
 
-		<h3>todo</h3>
-		<div>todo</div>
-		<div>
-		todo
-		</div>
-		
+		<h3>[method:null update]()</h3>
+		<div>Updates the vertex tangent preview arrows based on the new position and tangents of the object.</div>
+
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 
 		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]
 		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]

+ 24 - 15
docs/api/extras/helpers/WireframeHelper.html

@@ -11,36 +11,45 @@
 		
 		
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">todo</div>
+		<div class="desc">Creates a wireframe object that shows the edges of another object's geometry. To draw a  wireframe image showing only "hard" edges (edges between non-coplanar faces), see [page:EdgesHelper].</div>
 
 
 		<h2>Example</h2>
 		<h2>Example</h2>
 
 
-		<code>todo</code>
+		<code>
+		geometry = new THREE.BoxGeometry( 10, 10, 10, 2, 2, 2 );
+		material = new THREE.MeshBasicMaterial( { color: 0xff0000 } );
+		object = new THREE.Mesh( geometry, material );
 
 
-		<h2>Constructor</h2>
+		wireframe = new THREE.WireframeHelper( object, 0x00ff00 );
+
+		scene.add( object );
+		scene.add( wireframe );
 
 
+		</code>
+		[example:webgl_helpers Example using various helpers], [example:webgl_materials_wireframe Alternative approach using a shader.]
 
 
-		<h3>todo</h3>
-		<div></div>
+		<h2>Constructor</h2>
+		<h3>[name]( [page:Object3D object], [page:Color color] )</h3>
+		<div>
+		object -- Object of which to draw edges <br />
+		color -- Color of the edges.
+		</div>
+		<div>
+		Creates a [page:Line], showing only the edges between vertices of an object.
+		</div>
 
 
 
 
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
-		<h3>todo</h3>
-		<div>
-		todo
-		</div> 
+		<div>none</div>
 
 
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 		
 		
-
-		<h3>todo</h3>
-		<div>todo</div>
-		<div>
-		todo
-		</div>
+		<div>none</div>
 		
 		
+
+		<h2>Source</h2>
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 
 		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]
 		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]

+ 26 - 31
docs/api/lights/DirectionalLight.html

@@ -103,7 +103,7 @@ scene.add( directionalLight );</code>
 
 
 		<h3>[property:Float shadowBias]</h3>
 		<h3>[property:Float shadowBias]</h3>
 		<div>
 		<div>
-			Shadow map bias.<br />
+			Shadow map bias, how much to add or subtract from the normalized depth when deciding whether a surface is in shadow.<br />
 			Default — *0*.
 			Default — *0*.
 		</div>
 		</div>
 
 
@@ -127,81 +127,76 @@ scene.add( directionalLight );</code>
 
 
 		<h3>[property:Boolean shadowCascade]</h3>
 		<h3>[property:Boolean shadowCascade]</h3>
 		<div>
 		<div>
-			??? <br />
+			**Experimental** If true, use a series of shadow maps in a cascade. This can give better z-depth resolution for a directional light. <br />
 			Default — *false*.
 			Default — *false*.
 		</div>
 		</div>
 
 
-		<h3>[property:Vector3 shadowCascadeOffset]</h3>
+		<h3>[property:Integer shadowCascadeCount]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — *Three.Vector3( 0, 0, -1000 )*.
+			Number of shadow maps to allocate in a cascade (one after another). <br />
+			Default — *2*.
 		</div>
 		</div>
 
 
-		<h3>[property:Integer shadowCascadeCount]</h3>
+		<h3>[property:Vector3 shadowCascadeOffset]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — *2*.
+			A relative position to real camera where virtual shadow cameras are attached. A magic vector; scene and light orientation dependent. <br />
+			Default — *Three.Vector3( 0, 0, -1000 )*.
 		</div>
 		</div>
 
 
 		<h3>[property:Array shadowCascadeBias]</h3>
 		<h3>[property:Array shadowCascadeBias]</h3>
 		<div>
 		<div>
-			??? <br />
+			An array of shadowMapBias values for the corresponding shadow map in the cascade, near to far. <br />
 			Default — <strong>[ 0, 0, 0 ]</strong>.
 			Default — <strong>[ 0, 0, 0 ]</strong>.
 		</div>
 		</div>
 
 
 		<h3>[property:Array shadowCascadeWidth]</h3>
 		<h3>[property:Array shadowCascadeWidth]</h3>
 		<div>
 		<div>
-			??? <br />
+			An array of shadowMapWidth values for the corresponding shadow map in the cascade, near to far. <br />
 			Default — <strong>[ 512, 512, 512 ]</strong>.
 			Default — <strong>[ 512, 512, 512 ]</strong>.
 		</div>
 		</div>
 
 
 		<h3>[property:Array shadowCascadeHeight]</h3>
 		<h3>[property:Array shadowCascadeHeight]</h3>
 		<div>
 		<div>
-			??? <br />
+			An array of shadowMapHeight values for the corresponding shadow map in the cascade, near to far. <br />
 			Default — <strong>[ 512, 512, 512 ]</strong>.
 			Default — <strong>[ 512, 512, 512 ]</strong>.
 		</div>
 		</div>
 
 
 		<h3>[property:Array shadowCascadeNearZ]</h3>
 		<h3>[property:Array shadowCascadeNearZ]</h3>
 		<div>
 		<div>
-			??? <br />
+			An array of shadowMapNear values for the corresponding shadow map in the cascade, near to far. These typically start with -1.0 (near plane) and match with the previous shadowCascadeFarZ array value.<br />
 			Default — <strong>[ -1.000, 0.990, 0.998 ]</strong>.
 			Default — <strong>[ -1.000, 0.990, 0.998 ]</strong>.
 		</div>
 		</div>
 
 
 		<h3>[property:Array shadowCascadeFarZ]</h3>
 		<h3>[property:Array shadowCascadeFarZ]</h3>
 		<div>
 		<div>
-			??? <br />
+			An array of shadowMapFar values for the corresponding shadow map in the cascade, near to far. These typically match with the next shadowCascadeNearZ array value, ending in 1.0.<br />
 			Default — <strong>[ 0.990, 0.998, 1.000 ]</strong>.
 			Default — <strong>[ 0.990, 0.998, 1.000 ]</strong>.
 		</div>
 		</div>
 
 
 		<h3>[property:Array shadowCascadeArray]</h3>
 		<h3>[property:Array shadowCascadeArray]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — <strong>[ ]</strong>.
+			Array of size shadowCascadeCount of [page:DirectionalLight THREE.DirectionalLight] objects. This holds the series of separate shadow maps in a cascade, near to far. Created internally.
 		</div>
 		</div>
 
 
-		<h3>[property:RenderTarget shadowMap]</h3>
+		<h3>[property:Vector2 shadowMapSize]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — *null*.
-		</div>
+			The shadowMapWidth and shadowMapHeight stored in a [page:Vector2 THREE.Vector2]. Set internally during rendering.
+		</div> 
 
 
-		<h3>[property:Integer shadowMapSize]</h3>
+		<h3>[property:OrthographicCamera shadowCamera]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — *null*.
-		</div>
+			The shadow's view of the world. Computed internally during rendering from the shadowCamera* settings.
+		</div> 
 
 
-		<h3>[property:Camera shadowCamera]</h3>
+		<h3>[property:Matrix4 shadowMatrix]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — *null*.
-		</div>
+			Model to shadow camera space, to compute location and depth in shadow map. Computed internally during rendering.
+		</div> 
 
 
-		<h3>[property:Matrix shadowMatrix]</h3>
+		<h3>[property:WebGLRenderTarget shadowMap]</h3>
 		<div>
 		<div>
-			??? <br />
-			Default — *null*.
-		</div>
+		    The depth map generated using the shadowCamera; a location beyond a pixel's depth is in shadow. Computed internally during rendering.
+		</div> 
 		
 		
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 
 

+ 9 - 34
docs/api/lights/SpotLight.html

@@ -121,7 +121,7 @@ scene.add( spotLight );</code>
 		
 		
 		<h3>[property:Float shadowBias]</h3>
 		<h3>[property:Float shadowBias]</h3>
 		<div>
 		<div>
-			Shadow map bias.<br />
+			Shadow map bias, how much to add or subtract from the normalized depth when deciding whether a surface is in shadow.<br />
 			Default — *0*.
 			Default — *0*.
 		</div>
 		</div>
 
 
@@ -143,49 +143,24 @@ scene.add( spotLight );</code>
 			Default — *512*.
 			Default — *512*.
 		</div>
 		</div>
 		
 		
-		<h3>[property:Float shadowBias]</h3>
-		<div>
-			Shadow map bias.<br />
-			Default — *0*.
-		</div>
-
-		<h3>[property:Float shadowDarkness]</h3>
-		<div>
-			Darkness of shadow casted by this light (from *0* to *1*).<br />
-			Default — *0.5*.
-		</div>
-
-		<h3>[property:Integer shadowMapWidth]</h3>
-		<div>
-			Shadow map texture width in pixels.<br />
-			Default — *512*.
-		</div>
-
-		<h3>[property:Integer shadowMapHeight]</h3>
-		<div>
-			Shadow map texture height in pixels.<br />
-			Default — *512*.
-		</div>
-
-
-		<h3>[property:object shadowMatrix]</h3>
+		<h3>[property:Vector2 shadowMapSize]</h3>
 		<div>
 		<div>
-		todo
+			The shadowMapWidth and shadowMapHeight stored in a [page:Vector2 THREE.Vector2]. Set internally during rendering.
 		</div> 
 		</div> 
 
 
-		<h3>[property:object shadowMapSize]</h3>
+		<h3>[property:PerspectiveCamera shadowCamera]</h3>
 		<div>
 		<div>
-		todo
+			The shadow's view of the world. Computed internally during rendering from the shadowCamera* settings.
 		</div> 
 		</div> 
 
 
-		<h3>[property:object shadowCamera]</h3>
+		<h3>[property:Matrix4 shadowMatrix]</h3>
 		<div>
 		<div>
-		todo
+			Model to shadow camera space, to compute location and depth in shadow map. Computed internally during rendering.
 		</div> 
 		</div> 
 
 
-		<h3>[property:object shadowMap]</h3>
+		<h3>[property:WebGLRenderTarget shadowMap]</h3>
 		<div>
 		<div>
-		todo
+		    The depth map generated using the shadowCamera; a location beyond a pixel's depth is in shadow. Computed internally during rendering.
 		</div> 
 		</div> 
 
 
 		<h2>Methods</h2>		
 		<h2>Methods</h2>		

+ 2 - 3
docs/api/loaders/ColladaLoader.html

@@ -10,7 +10,7 @@
 
 
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
-		<div class="desc">A loader for loading an <em>.babylon</em> resource.</div>
+		<div class="desc">A loader for <em>Collada</em> files.</div>
 
 
 
 
 		<h2>Constructor</h2>
 		<h2>Constructor</h2>
@@ -86,7 +86,6 @@
 		// instantiate a loader
 		// instantiate a loader
 		var loader = new THREE.ColladaLoader();
 		var loader = new THREE.ColladaLoader();
 
 
-		// load a Babylon resource
 		loader.load(
 		loader.load(
 			// resource URL
 			// resource URL
 			'models/collada/monster/monster.dae',
 			'models/collada/monster/monster.dae',
@@ -109,6 +108,6 @@
 
 
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 
-		[link:https://github.com/mrdoob/three.js/blob/master/examples/js/loaders/OBJLoader.js examples/js/loaders/BabylonLoader.js]
+		[link:https://github.com/mrdoob/three.js/blob/master/examples/js/loaders/ColladaLoader.js examples/js/loaders/ColladaLoader.js]
 	</body>
 	</body>
 </html>
 </html>

+ 1 - 1
docs/api/loaders/OBJMTLLoader.html

@@ -47,7 +47,7 @@
 		</div>
 		</div>
 		<div>
 		<div>
 		Parse an <em>obj</em> text structure and return an [page:Object3D].<br />
 		Parse an <em>obj</em> text structure and return an [page:Object3D].<br />
-		Found objects are converted to [page:Mesh] with a [page:BufferGeometry] and materials are converted to [page:MeshLambertMaterial].
+		Found objects are converted to a [page:Mesh] and materials are converted to [page:MeshLambertMaterial].
 		</div>
 		</div>
 
 
 		<h2>Example</h2>
 		<h2>Example</h2>

+ 0 - 114
docs/api/loaders/SceneLoader.html

@@ -1,114 +0,0 @@
-<!DOCTYPE html>
-<html lang="en">
-	<head>
-		<meta charset="utf-8" />
-		<script src="../../list.js"></script>
-		<script src="../../page.js"></script>
-		<link type="text/css" rel="stylesheet" href="../../page.css" />
-	</head>
-	<body>
-
-		<h1>[name]</h1>
-
-		<div class="desc">A loader for loading a [page:Scene] from a <em>JSON</em> resource.</div>
-
-
-		<h2>Constructor</h2>
-
-		<h3>[name]( [page:LoadingManager manager] )</h3>
-		<div>
-		[page:LoadingManager manager] — The [page:LoadingManager loadingManager] for the loader to use. Default is [page:LoadingManager THREE.DefaultLoadingManager].
-		</div>
-		<div>
-		Creates a new [name].
-		</div>
-
-		<h2>Properties</h2>
-
-
-		<h2>Methods</h2>
-
-		<h3>[method:null load]( [page:String url], [page:Function onLoad], [page:Function onProgress], [page:Function onError] )</h3>
-		<div>
-		[page:String url] — required<br />
-		[page:Function onLoad] — Will be called when load completes. The argument will be an [page:Object] containing the loaded components.<br />
-		[page:Function onProgress] — Will be called while load progresses. The argument will be the XmlHttpRequest instance, that contain .[page:Integer total] and .[page:Integer loaded] bytes.<br />
-		[page:Function onError] — Will be called when load errors.<br />
-		</div>
-		<div>
-		Begin loading from url and call onLoad with the parsed scene.
-		</div>
-
-		<h3>[method:Object parse]( [page:Object json], [page:Function callbackFinished], [page:String url] )</h3>
-		<div>
-		[page:Object json] — The <em>JSON</em> structure to parse.<br />
-		[page:Function callbackFinished] — Will be called when parse completes.<br />
-		[page:String url] — Will be used as base for assets' relative URLs.<br />
-		</div>
-		<div>
-		Parse a <em>JSON</em> scene description and return a new [page:Object] with fully instantiated Three.js objects.
-		</div>
-
-		<h3>[method:null setCrossOrigin]( [page:String value] )</h3>
-		<div>
-		[page:String value] — The crossOrigin string to implement CORS for loading the url from a different domain that allows CORS.
-		</div>
-
-		<h3>[method:null addGeometryHandler]( [page:String typeID], [page:Function loaderClass] )</h3>
-		<div>
-		[page:String typeID] — The type to handle.<br />
-		[page:Function loaderClass] — The handler class.<br />
-		</div>
-		<div>
-		Add an handler for a specific geometry type.
-		</div>
-
-		<h3>[method:null addHierarchyHandler]( [page:String typeID], [page:Function loaderClass] )</h3>
-		<div>
-		[page:String typeID] — The type to handle.<br />
-		[page:Function loaderClass] — The handler class.<br />
-		</div>
-		<div>
-		Add an handler for a specific object type.
-		</div>
-
-
-		<h2>Example</h2>
-
-		<code>
-		// instantiate a loader
-		var loader = new THREE.SceneLoader();
-
-		// Handle STL geometries
-		loader.addGeometryHandler( "stl", THREE.STLLoader );
-
-		// Handle OBJ objects
-		loader.addHierarchyHandler( "obj", THREE.OBJLoader );
-
-		// load a JSON resource
-		loader.load(
-			// resource URL
-			'scenes/test_scene.js',
-			// Function when resource is loaded
-			function ( result ) {
-				scene.add( result.scene );
-			},
-			// Function called when download progresses
-			function ( xhr ) {
-				console.log( (xhr.loaded / xhr.total * 100) + '% loaded' );
-			},
-			// Function called when download errors
-			function ( xhr ) {
-				console.log( 'An error happened' );
-			}
-		);
-		</code>
-
-		[example:webgl_loader_scene]
-
-
-		<h2>Source</h2>
-
-		[link:https://github.com/mrdoob/three.js/blob/master/examples/js/loaders/SceneLoader.js examples/js/loaders/SceneLoader.js]
-	</body>
-</html>

+ 1 - 6
docs/api/materials/MeshLambertMaterial.html

@@ -29,7 +29,7 @@
 		specularMap — Set specular map. Default is null.<br />
 		specularMap — Set specular map. Default is null.<br />
 		alphaMap — Set alpha map. Default is null.<br />
 		alphaMap — Set alpha map. Default is null.<br />
 		envMap — Set env map. Default is null.<br />
 		envMap — Set env map. Default is null.<br />
-		fog — Define whether the material color is affected by global fog settings. Default is false.
+		fog — Define whether the material color is affected by global fog settings. Default is false.<br />
 		shading — How the triangles of a curved surface are rendered. Default is [page:Materials THREE.SmoothShading].<br/>
 		shading — How the triangles of a curved surface are rendered. Default is [page:Materials THREE.SmoothShading].<br/>
 		wireframe — Render geometry as wireframe. Default is false (i.e. render as smooth shaded).<br/>
 		wireframe — Render geometry as wireframe. Default is false (i.e. render as smooth shaded).<br/>
 		wireframeLinewidth — Controls wireframe thickness. Default is 1.<br/>
 		wireframeLinewidth — Controls wireframe thickness. Default is 1.<br/>
@@ -49,11 +49,6 @@
 		Diffuse color of the material. Default is white.<br />
 		Diffuse color of the material. Default is white.<br />
 		</div>
 		</div>
 
 
-		<h3>[property:Color ambient]</h3>
-		<div>
-		Ambient color of the material, multiplied by the color of the [page:AmbientLight]. Default is white.<br />
-		</div>
-
 		<h3>[property:Color emissive]</h3>
 		<h3>[property:Color emissive]</h3>
 		<div>
 		<div>
 		Emissive (light) color of the material, essentially a solid color unaffected by other lighting. Default is black.<br />
 		Emissive (light) color of the material, essentially a solid color unaffected by other lighting. Default is black.<br />

+ 6 - 13
docs/api/materials/MeshNormalMaterial.html

@@ -12,7 +12,7 @@
 		<h1>[name]</h1>
 		<h1>[name]</h1>
 
 
 		<div class="desc">A material that maps the normal vectors to RGB colors.</div>
 		<div class="desc">A material that maps the normal vectors to RGB colors.</div>
-		
+
 		<iframe src='../../scenes/material-browser.html#MeshNormalMaterial'></iframe>
 		<iframe src='../../scenes/material-browser.html#MeshNormalMaterial'></iframe>
 
 
 
 
@@ -21,10 +21,9 @@
 
 
 		<h3>[name]([page:Object parameters])</h3>
 		<h3>[name]([page:Object parameters])</h3>
 		<div>
 		<div>
-		parameters is an object with one or more properties defining the material's appearance. 
+		parameters is an object with one or more properties defining the material's appearance.
 		</div>
 		</div>
 		<div>
 		<div>
-		shading --  How the triangles of a curved surface are rendered. Default is [page:Materials THREE.FlatShading].<br/>
 		wireframe -- Render geometry as wireframe. Default is false (i.e. render as smooth shaded).<br/>
 		wireframe -- Render geometry as wireframe. Default is false (i.e. render as smooth shaded).<br/>
 		wireframeLinewidth -- Controls wireframe thickness. Default is 1.<br/>
 		wireframeLinewidth -- Controls wireframe thickness. Default is 1.<br/>
 		morphTargets -- Define whether the material uses morphTargets. Default is false.<br/>
 		morphTargets -- Define whether the material uses morphTargets. Default is false.<br/>
@@ -34,25 +33,19 @@
 		<h2>Properties</h2>
 		<h2>Properties</h2>
 
 
 
 
-		<h3>[property:number shading]</h3>
+		<h3>[property:boolean wireframe]</h3>
 		<div>
 		<div>
-			How the triangles of a curved surface are rendered: as a smooth surface, as flat separate facets, or no shading at all.<br/><br/>
-			Options are [page:Materials THREE.SmoothShading], [page:Materials THREE.FlatShading](default)
+			Render geometry as wireframe. Default is false (i.e. render as smooth shaded).
 		</div>
 		</div>
 
 
-		<h3>[property:boolean wireframe]</h3>
-		<div>
-			Render geometry as wireframe. Default is false (i.e. render as smooth shaded). 
-		</div> 
-		
 		<h3>[property:number wireframeLinewidth]</h3>
 		<h3>[property:number wireframeLinewidth]</h3>
 		<div>
 		<div>
 			Controls wireframe thickness. Default is 1.<br/><br/>
 			Controls wireframe thickness. Default is 1.<br/><br/>
 			Due to limitations in the ANGLE layer, on Windows platforms linewidth will always be 1 regardless of the set value.
 			Due to limitations in the ANGLE layer, on Windows platforms linewidth will always be 1 regardless of the set value.
-		</div> 
+		</div>
 
 
 		<h3>[property:boolean morphTargets]</h3>
 		<h3>[property:boolean morphTargets]</h3>
-		<div>Define whether the material uses morphTargets. Default is false.</div> 
+		<div>Define whether the material uses morphTargets. Default is false.</div>
 
 
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 
 

+ 2 - 7
docs/api/materials/MeshPhongMaterial.html

@@ -41,7 +41,7 @@
 		</div>
 		</div>
 		<div>
 		<div>
 		Example:<br>
 		Example:<br>
-		materials.push( new THREE.MeshPhongMaterial( { ambient: 0x030303, color: 0xdddddd, specular: 0x009900, shininess: 30, shading: THREE.FlatShading } ) );
+		materials.push( new THREE.MeshPhongMaterial( { color: 0xdddddd, specular: 0x009900, shininess: 30, shading: THREE.FlatShading } ) );
 	
 	
 		</div>
 		</div>
 
 
@@ -54,11 +54,6 @@
 		Diffuse color of the material. Default is white.<br />
 		Diffuse color of the material. Default is white.<br />
 		</div>
 		</div>
 
 
-		<h3>[property:Color ambient]</h3>
-		<div>
-		Ambient color of the material, multiplied by the color of the [page:AmbientLight]. Default is white.<br />
-		</div>
-
 		<h3>[property:Color emissive]</h3>
 		<h3>[property:Color emissive]</h3>
 		<div>
 		<div>
 		Emissive (light) color of the material, essentially a solid color unaffected by other lighting. Default is black.<br />
 		Emissive (light) color of the material, essentially a solid color unaffected by other lighting. Default is black.<br />
@@ -70,7 +65,7 @@
 		</div>
 		</div>
 
 
 		<h3>[property:Float shininess]</h3>
 		<h3>[property:Float shininess]</h3>
-		<div>How shiny the specular highlight is; a higher value gives a sharper highlight. Default is *30*.</div>
+		<div>How shiny the specular highlight is; a higher value gives a sharper highlight. Default is *30*. It should not be set to 0.</div>
 
 
 		<h3>[property:boolean metal]</h3>
 		<h3>[property:boolean metal]</h3>
 		<div>
 		<div>

+ 1 - 1
docs/api/materials/SpriteMaterial.html

@@ -24,7 +24,7 @@
 		<div>
 		<div>
 		color - color of the sprite<br/>
 		color - color of the sprite<br/>
 		map - the texture map<br/>
 		map - the texture map<br/>
-		rotation - the rotation of the sprite
+		rotation - the rotation of the sprite<br/>
 		fog - whether or not to use the scene fog<br/>
 		fog - whether or not to use the scene fog<br/>
 		</div>
 		</div>
 
 

+ 8 - 0
docs/api/math/Color.html

@@ -176,6 +176,14 @@
 		Linear interpolation of this colors rgb values and the rgb values of the first argument. The alpha argument can be thought of as the percent between the two colors, where 0 is this color and 1 is the first argument.
 		Linear interpolation of this colors rgb values and the rgb values of the first argument. The alpha argument can be thought of as the percent between the two colors, where 0 is this color and 1 is the first argument.
 		</div>
 		</div>
 
 
+		<h3>[method:Array toArray]( [page:Array array] )</h3>
+		<div>
+		array -- Optional array to store the color.
+		</div>
+		<div>
+		Returns an array [r,g,b]
+		</div>
+
 		<h3>[method:Color equals]( [page:Color c] ) [page:Color this]</h3>
 		<h3>[method:Color equals]( [page:Color c] ) [page:Color this]</h3>
 		<div>
 		<div>
 		Compares this color and c and returns true if they are the same, false otherwise.
 		Compares this color and c and returns true if they are the same, false otherwise.

+ 141 - 138
docs/api/math/Euler.html

@@ -1,141 +1,144 @@
 <!DOCTYPE html>
 <!DOCTYPE html>
 <html lang="en">
 <html lang="en">
-  <head>
-    <meta charset="utf-8" />
-    <script src="../../list.js"></script>
-    <script src="../../page.js"></script>
-    <link type="text/css" rel="stylesheet" href="../../page.css" />
-  </head>
-  <body>
-    <h1>[name]</h1>
-
-    <div class="desc">Euler Angles. <br/><br/>
-    
-    Euler angles describe a rotation transformation by rotating an object on its various axes in specified amounts per axis, and a specified axis order.
-    (More information on <a href='http://en.wikipedia.org/wiki/Euler_angles' target='blank'>Wikipedia</a>)</div>
-
-    <h2>Example</h2>
-
-    <code>var a = new THREE.Euler( 0, 1, 1.57, 'XYZ' );
-    var b = new THREE.Vector3( 1, 0, 1 );
-    b.applyEuler(a);
-    </code>
-
-
-    <h2>Constructor</h2>
-
-
-    <h3>[name]( [page:Float x], [page:Float y], [page:Float z], [page:String order] )</h3>
-    <div>
-    x -- [page:Float] the angle of the x axis in radians<br />
-    y -- [page:Float] the angle of the y axis in radians<br />
-    z -- [page:Float] the angle of the z axis in radians<br />
-    order -- [page:String] A string representing the order that the rotations are applied, defaults to 'XYZ' (must be upper case).
-    </div>
-    <div>
-    A euler angle for transforming
-    </div>
-
-
-    <h2>Properties</h2>
-
-    <h3>[property:Float x]</h3>
-
-    <h3>[property:Float y]</h3>
-
-    <h3>[property:Float z]</h3>
-
-    <h3>[property:String order]</h3>
-
-
-
-    <h2>Methods</h2>
-
-    <h3>[method:Euler set]( [page:Float x], [page:Float y], [page:Float z], [page:String order] ) [page:Euler this]</h3>
-    <div>
-    x -- [page:Float] Angle in x axis in radians<br />
-    y -- [page:Float] Angle in y axis in radians<br />
-    z -- [page:Float] Angle in z axis in radians<br />
-    order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
-    </div>
-    <div>
-    Sets the angles of this euler transform.
-    </div>
-
-    <h3>[method:Euler copy]( [page:Euler euler] ) [page:Euler this]</h3>
-    <div>
-    Copies value of *euler* to this euler.
-    </div>
-
-    <h3>[method:Euler setFromRotationMatrix]( [page:Matrix4 m], [page:String order] ) [page:Euler this]</h3>
-    <div>
-    m -- [page:Matrix4] assumes upper 3x3 of matrix is a pure rotation matrix (i.e. unscaled)<br />
-    order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
-    </div>
-    <div>
-    Sets the angles of this euler transform from a pure rotation matrix based on the orientation specified by order.
-    </div>
-
-    <h3>[method:Euler setFromQuaternion]( [page:Quaternion q], [page:String order] ) [page:Euler this]</h3>
-    <div>
-    q -- [page:Quaternion] quaternion must be normalized<br />
-    order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
-    </div>
-    <div>
-    Sets the angles of this euler transform from a normalized quaternion based on the orientation specified by order.
-    </div>
-
-    <h3>[method:Euler reorder]( [page:String newOrder] ) [page:Euler this]</h3>
-    <div>
-    Resets the euler angle with a new order by creating a quaternion from this euler angle and then setting this euler angle with the quaternion and the new order. <br />
-    WARNING: this discards revolution information.
-    </div>
-
-    <h3>[method:Euler setFromVector3]([page:Vector3 vector], [page:String order]) [page:Euler this]</h3>
-    <div>
-    vector -- [page:Vector3].
-    order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
-    </div>
-    <div>
-    Optionally Vector3 to the XYZ parameters of Euler, and order to the Euler's order property.
-    </div>
-
-    <h3>[method:Vector3 toVector3]()</h3>
-    <div>
-    Returns the Euler's XYZ properties as a Vector3.
-    </div>
-
-    <h3>[method:Euler fromArray]([page:Array array]) [page:Euler this]</h3>
-    <div>
-    array -- [page:Array] of length 3 or 4. array[3] is an optional order argument.
-    </div>
-    <div>
-    Assigns this euler's x angle to array[0]. <br />
-    Assigns this euler's y angle to array[1]. <br />
-    Assigns this euler's z angle to array[2]. <br />
-    Optionally assigns this euler's order to array[3].
-    </div>
-
-    <h3>[method:Array toArray]()</h3>
-    <div>
-    Returns an array [x, y, z, order].
-    </div>
-
-    <h3>[method:Boolean equals]( [page:Euler euler] )</h3>
-    <div>
-    Checks for strict equality of this euler and *euler*.
-    </div>
-
-    <h3>[method:Euler clone]()</h3>
-    <div>
-    Returns a new euler created from this euler.
-    </div>
-
-
-
-
-    <h2>Source</h2>
-
-    [link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]
-  </body>
+	<head>
+		<meta charset="utf-8" />
+		<script src="../../list.js"></script>
+		<script src="../../page.js"></script>
+		<link type="text/css" rel="stylesheet" href="../../page.css" />
+	</head>
+	<body>
+		<h1>[name]</h1>
+
+		<div class="desc">Euler Angles. <br/><br/>
+
+		Euler angles describe a rotation transformation by rotating an object on its various axes in specified amounts per axis, and a specified axis order.
+		(More information on <a href='http://en.wikipedia.org/wiki/Euler_angles' target='blank'>Wikipedia</a>)</div>
+
+		<h2>Example</h2>
+
+		<code>var a = new THREE.Euler( 0, 1, 1.57, 'XYZ' );
+		var b = new THREE.Vector3( 1, 0, 1 );
+		b.applyEuler(a);
+		</code>
+
+
+		<h2>Constructor</h2>
+
+
+		<h3>[name]( [page:Float x], [page:Float y], [page:Float z], [page:String order] )</h3>
+		<div>
+		x -- [page:Float] the angle of the x axis in radians<br />
+		y -- [page:Float] the angle of the y axis in radians<br />
+		z -- [page:Float] the angle of the z axis in radians<br />
+		order -- [page:String] A string representing the order that the rotations are applied, defaults to 'XYZ' (must be upper case).
+		</div>
+		<div>
+		A euler angle for transforming
+		</div>
+
+
+		<h2>Properties</h2>
+
+		<h3>[property:Float x]</h3>
+
+		<h3>[property:Float y]</h3>
+
+		<h3>[property:Float z]</h3>
+
+		<h3>[property:String order]</h3>
+
+
+
+		<h2>Methods</h2>
+
+		<h3>[method:Euler set]( [page:Float x], [page:Float y], [page:Float z], [page:String order] ) [page:Euler this]</h3>
+		<div>
+		x -- [page:Float] Angle in x axis in radians<br />
+		y -- [page:Float] Angle in y axis in radians<br />
+		z -- [page:Float] Angle in z axis in radians<br />
+		order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
+		</div>
+		<div>
+		Sets the angles of this euler transform.
+		</div>
+
+		<h3>[method:Euler copy]( [page:Euler euler] ) [page:Euler this]</h3>
+		<div>
+		Copies value of *euler* to this euler.
+		</div>
+
+		<h3>[method:Euler setFromRotationMatrix]( [page:Matrix4 m], [page:String order] ) [page:Euler this]</h3>
+		<div>
+		m -- [page:Matrix4] assumes upper 3x3 of matrix is a pure rotation matrix (i.e. unscaled)<br />
+		order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
+		</div>
+		<div>
+		Sets the angles of this euler transform from a pure rotation matrix based on the orientation specified by order.
+		</div>
+
+		<h3>[method:Euler setFromQuaternion]( [page:Quaternion q], [page:String order] ) [page:Euler this]</h3>
+		<div>
+		q -- [page:Quaternion] quaternion must be normalized<br />
+		order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
+		</div>
+		<div>
+		Sets the angles of this euler transform from a normalized quaternion based on the orientation specified by order.
+		</div>
+
+		<h3>[method:Euler reorder]( [page:String newOrder] ) [page:Euler this]</h3>
+		<div>
+		Resets the euler angle with a new order by creating a quaternion from this euler angle and then setting this euler angle with the quaternion and the new order. <br />
+		WARNING: this discards revolution information.
+		</div>
+
+		<h3>[method:Euler setFromVector3]([page:Vector3 vector], [page:String order]) [page:Euler this]</h3>
+		<div>
+		vector -- [page:Vector3].
+		order -- [page:string] Order of axes, defaults to 'XYZ' (must be upper case)
+		</div>
+		<div>
+		Optionally Vector3 to the XYZ parameters of Euler, and order to the Euler's order property.
+		</div>
+
+		<h3>[method:Vector3 toVector3]()</h3>
+		<div>
+		Returns the Euler's XYZ properties as a Vector3.
+		</div>
+
+		<h3>[method:Euler fromArray]([page:Array array]) [page:Euler this]</h3>
+		<div>
+		array -- [page:Array] of length 3 or 4. array[3] is an optional order argument.
+		</div>
+		<div>
+		Assigns this euler's x angle to array[0]. <br />
+		Assigns this euler's y angle to array[1]. <br />
+		Assigns this euler's z angle to array[2]. <br />
+		Optionally assigns this euler's order to array[3].
+		</div>
+
+		<h3>[method:Array toArray]( [page:Array array] )</h3>
+		<div>
+		array -- Optional array to store the euler.
+		</div>
+		<div>
+		Returns an array [x, y, z, order]
+		</div>
+
+		<h3>[method:Boolean equals]( [page:Euler euler] )</h3>
+		<div>
+		Checks for strict equality of this euler and *euler*.
+		</div>
+
+		<h3>[method:Euler clone]()</h3>
+		<div>
+		Returns a new euler created from this euler.
+		</div>
+
+
+
+
+		<h2>Source</h2>
+
+		[link:https://github.com/mrdoob/three.js/blob/master/src/[path].js src/[path].js]
+	</body>
 </html>
 </html>

+ 1 - 2
docs/api/math/Matrix4.html

@@ -165,8 +165,7 @@
 
 
 		<h3>[method:Array decompose]( [page:Vector3 translation], [page:Quaternion quaternion], [page:Vector3 scale] )</h3>
 		<h3>[method:Array decompose]( [page:Vector3 translation], [page:Quaternion quaternion], [page:Vector3 scale] )</h3>
 		<div>
 		<div>
-		Decomposes this matrix into the *translation*, *quaternion* and *scale* components.<br />
-		If parameters are not passed, new instances will be created.
+		Decomposes this matrix into the *translation*, *quaternion* and *scale* components.
 		</div>
 		</div>
 
 
 		<h3>[method:Matrix4 makeTranslation]( [page:Float x], [page:Float y], [page:Float z] ) [page:Matrix4 this]</h3>
 		<h3>[method:Matrix4 makeTranslation]( [page:Float x], [page:Float y], [page:Float z] ) [page:Matrix4 this]</h3>

+ 8 - 5
docs/api/math/Quaternion.html

@@ -131,15 +131,18 @@
 		<h3>[method:Quaternion slerp]([page:Quaternion qb], [page:float t])</h3>
 		<h3>[method:Quaternion slerp]([page:Quaternion qb], [page:float t])</h3>
 		<div>
 		<div>
 		qb -- Target quaternion rotation.<br />
 		qb -- Target quaternion rotation.<br />
-		t -- Normalized [0..1] interpolation factor. 
+		t -- Normalized [0..1] interpolation factor.
 		</div>
 		</div>
 		<div>
 		<div>
 		Handles the spherical linear interpolation between this quaternion's configuration
 		Handles the spherical linear interpolation between this quaternion's configuration
-		and that of *qb*. *t* represents how close to the current (0) or target (1) rotation the 
-		result should be. 
+		and that of *qb*. *t* represents how close to the current (0) or target (1) rotation the
+		result should be.
 		</div>
 		</div>
 
 
-		<h3>.toArray() [page: Array]</h3>
+		<h3>[method:Array toArray]( [page:Array array] )</h3>
+		<div>
+		array -- Array to store the quaternion.
+		</div>
 		<div>
 		<div>
 		Returns the numerical elements of this quaternion in an array of format (x, y, z, w).
 		Returns the numerical elements of this quaternion in an array of format (x, y, z, w).
 		</div>
 		</div>
@@ -155,7 +158,7 @@
 
 
 		<h3>[method:Float lengthSq]()</h3>
 		<h3>[method:Float lengthSq]()</h3>
 		<div>
 		<div>
-		Calculates the squared length of the quaternion. 
+		Calculates the squared length of the quaternion.
 		</div>
 		</div>
 
 
 		<h3>[method:Quaternion fromArray]([page:Array array])</h3>
 		<h3>[method:Quaternion fromArray]([page:Array array])</h3>

+ 14 - 1
docs/api/math/Vector2.html

@@ -181,6 +181,16 @@
 		Linear interpolation between this vector and v, where alpha is the percent along the line.
 		Linear interpolation between this vector and v, where alpha is the percent along the line.
 		</div>
 		</div>
 
 
+		<h3>[method:Vector2 lerpVectors]([page:Vector2 v1], [page:Vector2 v2], [page:Float alpha]) [page:Vector2 this]</h3>
+		<div>
+		v1 -- [page:Vector2] <br />
+		v2 -- [page:Vector2] <br />
+		alpha -- [page:Float] between 0 and 1.
+		</div>
+		<div>
+		Sets this vector to be the vector linearly interpolated between *v1* and *v2* with *alpha* factor.
+		</div>
+
 		<h3>[method:undefined setComponent]([page:Integer index], [page:Float value])</h3>
 		<h3>[method:undefined setComponent]([page:Integer index], [page:Float value])</h3>
 		<div>
 		<div>
 		index -- 0 or 1 <br />
 		index -- 0 or 1 <br />
@@ -216,7 +226,10 @@
 		Sets this vector's x value to be array[0] and y value to be array[1].
 		Sets this vector's x value to be array[0] and y value to be array[1].
 		</div>
 		</div>
 
 
-		<h3>[method:Array toArray]()</h3>
+		<h3>[method:Array toArray]( [page:Array array] )</h3>
+		<div>
+		array -- Optional array to store the vector.
+		</div>
 		<div>
 		<div>
 		Returns an array [x, y].
 		Returns an array [x, y].
 		</div>
 		</div>

+ 14 - 1
docs/api/math/Vector3.html

@@ -342,6 +342,16 @@
 		Linear Interpolation between this vector and vector v, where alpha is the percent along the line.
 		Linear Interpolation between this vector and vector v, where alpha is the percent along the line.
 		</div>
 		</div>
 
 
+		<h3>[method:Vector3 lerpVectors]([page:Vector3 v1], [page:Vector3 v2], [page:Float alpha]) [page:Vector3 this]</h3>
+		<div>
+		v1 -- [page:Vector3] <br />
+		v2 -- [page:Vector3] <br />
+		alpha -- [page:Float] between 0 and 1.
+		</div>
+		<div>
+		Sets this vector to be the vector linearly interpolated between *v1* and *v2* with *alpha* factor.
+		</div>
+
 		<h3>[method:Float angleTo]([page:Vector3 v])</h3>
 		<h3>[method:Float angleTo]([page:Vector3 v])</h3>
 		<div>
 		<div>
 		v -- [page:Vector3]
 		v -- [page:Vector3]
@@ -391,7 +401,10 @@
 		Multiplies this vector and m, and divides by perspective.
 		Multiplies this vector and m, and divides by perspective.
 		</div>
 		</div>
 
 
-		<h3>[method:Array toArray]()</h3>
+		<h3>[method:Array toArray]( [page:Array array] )</h3>
+		<div>
+		array -- Optional array to store the vector.
+		</div>
 		<div>
 		<div>
 		Assigns this vector's x value to array[0]. <br />
 		Assigns this vector's x value to array[0]. <br />
 		Assigns this vector's y value to array[1]. <br />
 		Assigns this vector's y value to array[1]. <br />

+ 14 - 6
docs/api/math/Vector4.html

@@ -113,6 +113,11 @@
 		Linearly interpolate between this vector and *v* with *alpha* factor.
 		Linearly interpolate between this vector and *v* with *alpha* factor.
 		</div>
 		</div>
 
 
+		<h3>[method:Vector4 lerpVectors]( [page:Vector4 v1], [page:Vector4 v2], [page:Float alpha] ) [page:Vector4 this]</h3>
+		<div>
+		Sets this vector to be the vector linearly interpolated between *v1* and *v2* with *alpha* factor.
+		</div>
+
 		<h3>[method:Vector4 clone]()</h3>
 		<h3>[method:Vector4 clone]()</h3>
 		<div>
 		<div>
 		Clones this vector.
 		Clones this vector.
@@ -181,7 +186,7 @@
 		v -- [page:Vector4]
 		v -- [page:Vector4]
 		</div>
 		</div>
 		<div>
 		<div>
-		If this vector's x, y, z, or w value is greater than vector v's x, y, z, or w value, that value is replaced by the corresponding vector v value. 
+		If this vector's x, y, z, or w value is greater than vector v's x, y, z, or w value, that value is replaced by the corresponding vector v value.
 		</div>
 		</div>
 
 
 		<h3>[method:Vector4 addScalar]([page:Float s]) [page:Vector4 this]</h3>
 		<h3>[method:Vector4 addScalar]([page:Float s]) [page:Vector4 this]</h3>
@@ -199,7 +204,7 @@
 		<div>
 		<div>
 		Checks to see if this vector matches vector v.
 		Checks to see if this vector matches vector v.
 		</div>
 		</div>
-		
+
 		<h3>[method:Vector4 setAxisAngleFromRotationMatrix]([page:Matrix4 m]) [page:Vector4 this]</h3>
 		<h3>[method:Vector4 setAxisAngleFromRotationMatrix]([page:Matrix4 m]) [page:Vector4 this]</h3>
 		<div>
 		<div>
 		m -- [page:Matrix4]
 		m -- [page:Matrix4]
@@ -231,7 +236,7 @@
 		Index 1: y<br/>
 		Index 1: y<br/>
 		Index 2: z<br/>
 		Index 2: z<br/>
 		Index 3: w<br/>
 		Index 3: w<br/>
- 
+
 		</div>
 		</div>
 
 
 		<h3>[method:null setComponent]([page:Integer index], [page:Float value])</h3>
 		<h3>[method:null setComponent]([page:Integer index], [page:Float value])</h3>
@@ -241,13 +246,13 @@
 		</div>
 		</div>
 		<div>
 		<div>
 		Sets the value of the vector component	x, y, or z by an index.<br/><br/>
 		Sets the value of the vector component	x, y, or z by an index.<br/><br/>
-		
+
 		Index 0: x<br/>
 		Index 0: x<br/>
 		Index 1: y<br/>
 		Index 1: y<br/>
 		Index 2: z<br/>
 		Index 2: z<br/>
 		Index 3: w<br/>
 		Index 3: w<br/>
 		</div>
 		</div>
-		
+
 		<h3>[method:Vector4 fromArray]([page:Array array]) [page:Vector4 this]</h3>
 		<h3>[method:Vector4 fromArray]([page:Array array]) [page:Vector4 this]</h3>
 		<div>
 		<div>
 		array -- [page:Array] An array formatted [x, y, z, w]
 		array -- [page:Array] An array formatted [x, y, z, w]
@@ -256,7 +261,10 @@
 		Sets the vector's components based on an array formatted like [x, y, z, w]
 		Sets the vector's components based on an array formatted like [x, y, z, w]
 		</div>
 		</div>
 
 
-		<h3>[method:Array toArray]()</h3>
+		<h3>[method:Array toArray]( [page:Array array] )</h3>
+		<div>
+		array -- Optional array to store the vector.
+		</div>
 		<div>
 		<div>
 		Returns an array in the format [x, y, z, w]
 		Returns an array in the format [x, y, z, w]
 		</div>
 		</div>

+ 1 - 1
docs/api/renderers/WebGLRenderTarget.html

@@ -69,7 +69,7 @@
 
 
 		<h3>[property:number type]</h3>
 		<h3>[property:number type]</h3>
 		<div>
 		<div>
-		The default is THREE.UnsignedByteType. Other valid types (as WebGL allows) are THREE.ByteType, THREE.ShortType, THREE.UnsignedShortType, THREE.IntType, THREE.UnsignedIntType, THREE.FloatType, THREE.UnsignedShort4444Type, THREE.UnsignedShort5551Type, and THREE.UnsignedShort565Type.
+		The default is THREE.UnsignedByteType. Other valid types (as WebGL allows) are THREE.ByteType, THREE.ShortType, THREE.UnsignedShortType, THREE.IntType, THREE.UnsignedIntType, THREE.HalfFloatType, THREE.FloatType, THREE.UnsignedShort4444Type, THREE.UnsignedShort5551Type, and THREE.UnsignedShort565Type.
 		</div>
 		</div>
 		
 		
 		<h3>[property:boolean depthBuffer]</h3>
 		<h3>[property:boolean depthBuffer]</h3>

+ 16 - 4
docs/index.html

@@ -282,11 +282,11 @@
 						var li = document.createElement( 'li' );
 						var li = document.createElement( 'li' );
 						var a = document.createElement( 'a' );
 						var a = document.createElement( 'a' );
 						a.setAttribute( 'href', '#' );
 						a.setAttribute( 'href', '#' );
-						( function( s, c, p ) { 
+						( function( s, c, p ) {
 							a.addEventListener( 'click', function( e ) {
 							a.addEventListener( 'click', function( e ) {
 								goTo( s, c, p );
 								goTo( s, c, p );
 								e.preventDefault();
 								e.preventDefault();
-							} ) 
+							} )
 						} )( section, category, page[ 0 ] )
 						} )( section, category, page[ 0 ] )
 						a.textContent = page[ 0 ];
 						a.textContent = page[ 0 ];
 						li.appendChild( a );
 						li.appendChild( a );
@@ -383,7 +383,7 @@
 					// Resolve links of the form 'Class.member'
 					// Resolve links of the form 'Class.member'
 					if(section.indexOf(MEMBER_DELIMITER) !== -1) {
 					if(section.indexOf(MEMBER_DELIMITER) !== -1) {
 						parts = section.split(MEMBER_DELIMITER)
 						parts = section.split(MEMBER_DELIMITER)
-						section = parts[0]; 
+						section = parts[0];
 						member = parts[1];
 						member = parts[1];
 					}
 					}
 
 
@@ -392,7 +392,7 @@
 					section = location.section;
 					section = location.section;
 					category = location.category;
 					category = location.category;
 					name = location.name;
 					name = location.name;
-				} 
+				}
 
 
 				var title = 'three.js - documentation - ' + section + ' - ' + name;
 				var title = 'three.js - documentation - ' + section + ' - ' + name;
 				var url = encodeUrl(section) + DELIMITER + encodeUrl( category ) + DELIMITER + encodeUrl(name) + (!!member ? MEMBER_DELIMITER + encodeUrl(member) : '');
 				var url = encodeUrl(section) + DELIMITER + encodeUrl( category ) + DELIMITER + encodeUrl(name) + (!!member ? MEMBER_DELIMITER + encodeUrl(member) : '');
@@ -418,6 +418,18 @@
 
 
 			if ( window.location.hash.length > 0 ) goToHash();
 			if ( window.location.hash.length > 0 ) goToHash();
 
 
+			console.log([
+				'   __     __',
+				' __/ __\\  / __\\__   ____   _____   _____',
+				'/ __/  /\\/ /  /___\\/ ____\\/ _____\\/ _____\\',
+				'\\/_   __/ /   _   / /  __/ / __  / / __  /_   __   _____',
+				'/ /  / / /  / /  / /  / / /  ___/ /  ___/\\ _\\/ __\\/ _____\\',
+				'\\/__/  \\/__/\\/__/\\/__/  \\/_____/\\/_____/\\/__/ /  / /  ___/',
+				'                                         / __/  /  \\__  \\',
+				'                                         \\/____/\\/_____/'
+			].join('\n'));
+
 		</script>
 		</script>
+		<script src="../build/three.min.js"></script>
 	</body>
 	</body>
 </html>
 </html>

+ 1 - 1
docs/list.js

@@ -63,7 +63,6 @@ var list = {
 			[ "ObjectLoader", "api/loaders/ObjectLoader" ],
 			[ "ObjectLoader", "api/loaders/ObjectLoader" ],
 			[ "PDBLoader", "api/loaders/PDBLoader" ],
 			[ "PDBLoader", "api/loaders/PDBLoader" ],
 			[ "SVGLoader", "api/loaders/SVGLoader" ],
 			[ "SVGLoader", "api/loaders/SVGLoader" ],
-			[ "SceneLoader", "api/loaders/SceneLoader" ],
 			[ "TextureLoader", "api/loaders/TextureLoader" ],
 			[ "TextureLoader", "api/loaders/TextureLoader" ],
 			[ "TGALoader", "api/loaders/TGALoader" ],
 			[ "TGALoader", "api/loaders/TGALoader" ],
 			[ "XHRLoader", "api/loaders/XHRLoader" ]
 			[ "XHRLoader", "api/loaders/XHRLoader" ]
@@ -219,6 +218,7 @@ var list = {
 			[ "ArrowHelper", "api/extras/helpers/ArrowHelper" ],
 			[ "ArrowHelper", "api/extras/helpers/ArrowHelper" ],
 			[ "AxisHelper", "api/extras/helpers/AxisHelper" ],
 			[ "AxisHelper", "api/extras/helpers/AxisHelper" ],
 			[ "BoundingBoxHelper", "api/extras/helpers/BoundingBoxHelper" ],
 			[ "BoundingBoxHelper", "api/extras/helpers/BoundingBoxHelper" ],
+			[ "BoxHelper", "api/extras/helpers/BoxHelper" ],
 			[ "CameraHelper", "api/extras/helpers/CameraHelper" ],
 			[ "CameraHelper", "api/extras/helpers/CameraHelper" ],
 			[ "DirectionalLightHelper", "api/extras/helpers/DirectionalLightHelper" ],
 			[ "DirectionalLightHelper", "api/extras/helpers/DirectionalLightHelper" ],
 			[ "EdgesHelper", "api/extras/helpers/EdgesHelper" ],
 			[ "EdgesHelper", "api/extras/helpers/EdgesHelper" ],

+ 1 - 5
docs/scenes/js/material.js

@@ -393,7 +393,6 @@ function guiMeshLambertMaterial ( gui, mesh, material, geometry ) {
 
 
 	var data = {
 	var data = {
 		color : material.color.getHex(),
 		color : material.color.getHex(),
-		ambient : material.ambient.getHex(),
 		emissive : material.emissive.getHex(),
 		emissive : material.emissive.getHex(),
 		envMaps : envMapKeys,
 		envMaps : envMapKeys,
 		map : textureMapKeys,
 		map : textureMapKeys,
@@ -407,7 +406,6 @@ function guiMeshLambertMaterial ( gui, mesh, material, geometry ) {
 	var folder = gui.addFolder('THREE.MeshLambertMaterial');
 	var folder = gui.addFolder('THREE.MeshLambertMaterial');
 
 
 	folder.addColor( data, 'color' ).onChange( handleColorChange( material.color ) );
 	folder.addColor( data, 'color' ).onChange( handleColorChange( material.color ) );
-	folder.addColor( data, 'ambient' ).onChange( handleColorChange( material.ambient ) );
 	folder.addColor( data, 'emissive' ).onChange( handleColorChange( material.emissive ) );
 	folder.addColor( data, 'emissive' ).onChange( handleColorChange( material.emissive ) );
 
 
 	folder.add( material, 'shading', constants.shading ).onChange( needsUpdate( material, geometry ) );
 	folder.add( material, 'shading', constants.shading ).onChange( needsUpdate( material, geometry ) );
@@ -433,7 +431,6 @@ function guiMeshPhongMaterial ( gui, mesh, material, geometry ) {
 
 
 	var data = {
 	var data = {
 		color : material.color.getHex(),
 		color : material.color.getHex(),
-		ambient : material.ambient.getHex(),
 		emissive : material.emissive.getHex(),
 		emissive : material.emissive.getHex(),
 		specular : material.specular.getHex(),
 		specular : material.specular.getHex(),
 		envMaps : envMapKeys,
 		envMaps : envMapKeys,
@@ -446,11 +443,10 @@ function guiMeshPhongMaterial ( gui, mesh, material, geometry ) {
 	var folder = gui.addFolder('THREE.MeshPhongMaterial');
 	var folder = gui.addFolder('THREE.MeshPhongMaterial');
 
 
 	folder.addColor( data, 'color' ).onChange( handleColorChange( material.color ) );
 	folder.addColor( data, 'color' ).onChange( handleColorChange( material.color ) );
-	folder.addColor( data, 'ambient' ).onChange( handleColorChange( material.ambient ) );
 	folder.addColor( data, 'emissive' ).onChange( handleColorChange( material.emissive ) );
 	folder.addColor( data, 'emissive' ).onChange( handleColorChange( material.emissive ) );
 	folder.addColor( data, 'specular' ).onChange( handleColorChange( material.specular ) );
 	folder.addColor( data, 'specular' ).onChange( handleColorChange( material.specular ) );
 
 
-	folder.add( material, 'shininess', 0, 100);
+	folder.add( material, 'shininess', 1, 100);
 	folder.add( material, 'shading', constants.shading).onChange( needsUpdate( material, geometry ) );
 	folder.add( material, 'shading', constants.shading).onChange( needsUpdate( material, geometry ) );
 	folder.add( material, 'wireframe' );
 	folder.add( material, 'wireframe' );
 	folder.add( material, 'wireframeLinewidth', 0, 10 );
 	folder.add( material, 'wireframeLinewidth', 0, 10 );

+ 25 - 16
editor/css/dark.css

@@ -1,23 +1,34 @@
-.FancySelect {
+.Outliner {
+	color: #868686;
 	background: #222;
 	background: #222;
-	border: 1px solid #3C3C3C;
 	padding: 0;
 	padding: 0;
+	width: 100%;
+	height: 140px;
+	font-size: 12px;
 	cursor: default;
 	cursor: default;
 	overflow: auto;
 	overflow: auto;
 	outline: none;
 	outline: none;
 }
 }
 
 
-	.FancySelect .option {
+	.Outliner .option {
 		padding: 4px;
 		padding: 4px;
 		white-space: nowrap;
 		white-space: nowrap;
 	}
 	}
 
 
-	.FancySelect .option.active {
+	.Outliner .option.active {
 		background-color: #153C5E;
 		background-color: #153C5E;
 	}
 	}
 
 
+.Panel.Collapsible.collapsed .Static .Button {
+	border-left-color: #444;
+}
+
+.Panel.Collapsible:not(.collapsed) .Static .Button {
+	border-top-color: #444;
+}
+
 input.Number {
 input.Number {
-	color: #2A75B7;
+	color: #2A75B7!important;
 	font-size: 12px;							/** TODO: Use of !imporant is not ideal **/
 	font-size: 12px;							/** TODO: Use of !imporant is not ideal **/
 	background-color: transparent!important;	/* For now this is a quick fix a rendering issue due to inherited background */
 	background-color: transparent!important;	/* For now this is a quick fix a rendering issue due to inherited background */
 	border: 1px solid transparent;
 	border: 1px solid transparent;
@@ -97,11 +108,11 @@ input.Number {
 		}
 		}
 
 
 			#menubar .menu .options hr {
 			#menubar .menu .options hr {
-				border-color: #444;
+				border-color: #333;
 			}
 			}
 
 
 			#menubar .menu .options .option {
 			#menubar .menu .options .option {
-				color: #666;
+				color: #888;
 				background-color: transparent;
 				background-color: transparent;
 				padding: 5px 10px;
 				padding: 5px 10px;
 				margin: 0px !important;
 				margin: 0px !important;
@@ -113,7 +124,6 @@ input.Number {
 				}
 				}
 
 
 				#menubar .menu .options .option:active {
 				#menubar .menu .options .option:active {
-					color: #666;
 					background: transparent;
 					background: transparent;
 				}
 				}
 
 
@@ -134,7 +144,9 @@ input.Number {
 	#sidebar input,
 	#sidebar input,
 	#sidebar textarea,
 	#sidebar textarea,
 	#sidebar select {
 	#sidebar select {
-		background: #ccc;
+		background: #222;
+		border: 1px solid transparent;
+		color: #888;
 	}
 	}
 
 
 	#sidebar .Panel {
 	#sidebar .Panel {
@@ -151,13 +163,6 @@ input.Number {
 		border-top: 1px solid #333;
 		border-top: 1px solid #333;
 	}
 	}
 
 
-	#sidebar #outliner {
-		width: 100%;
-		height: 140px;
-		color: #868686;
-		font-size: 12px;
-	}
-
 	#sidebar .Panel.Material canvas {
 	#sidebar .Panel.Material canvas {
 
 
 		border: solid 1px #5A5A5A;
 		border: solid 1px #5A5A5A;
@@ -174,6 +179,10 @@ input.Number {
 	color: #333;
 	color: #333;
 }
 }
 
 
+	#toolbar * {
+		vertical-align: middle;
+	}
+
 	#toolbar .Panel {
 	#toolbar .Panel {
 		padding: 4px;
 		padding: 4px;
 		color: #888;
 		color: #888;

+ 14 - 13
editor/css/light.css

@@ -1,24 +1,27 @@
-.FancySelect {
+.Outliner {
+	color: #444;
 	background: #fff;
 	background: #fff;
-	border: 1px solid #ccc;
 	padding: 0;
 	padding: 0;
+	width: 100%;
+	height: 140px;
+	font-size: 12px;
 	cursor: default;
 	cursor: default;
 	overflow: auto;
 	overflow: auto;
 	outline: none;
 	outline: none;
 }
 }
 
 
-	.FancySelect .option {
+	.Outliner .option {
 		padding: 4px;
 		padding: 4px;
 		color: #666;
 		color: #666;
 		white-space: nowrap;
 		white-space: nowrap;
 	}
 	}
 
 
-	.FancySelect .option.active {
+	.Outliner .option.active {
 		background-color: #f8f8f8;
 		background-color: #f8f8f8;
 	}
 	}
 
 
 input.Number {
 input.Number {
-	color: #0080f0;
+	color: #0080f0!important;
 	font-size: 12px;							/** TODO: Use of !imporant is not ideal **/
 	font-size: 12px;							/** TODO: Use of !imporant is not ideal **/
 	background-color: transparent!important;	/* For now this is a quick fix a rendering issue due to inherited background */
 	background-color: transparent!important;	/* For now this is a quick fix a rendering issue due to inherited background */
 	border: 1px solid transparent;
 	border: 1px solid transparent;
@@ -135,7 +138,8 @@ input.Number {
 	#sidebar input,
 	#sidebar input,
 	#sidebar textarea,
 	#sidebar textarea,
 	#sidebar select {
 	#sidebar select {
-		/* background: #ccc; */
+		border: 1px solid transparent;
+		color: #444;
 	}
 	}
 
 
 	#sidebar .Panel {
 	#sidebar .Panel {
@@ -152,13 +156,6 @@ input.Number {
 		border-top: 1px solid #ccc;
 		border-top: 1px solid #ccc;
 	}
 	}
 
 
-	#sidebar #outliner {
-		width: 100%;
-		height: 140px;
-		color: #444;
-		font-size: 12px;
-	}
-
 #toolbar {
 #toolbar {
 	position: absolute;
 	position: absolute;
 	left: 0px;
 	left: 0px;
@@ -169,6 +166,10 @@ input.Number {
 	color: #333;
 	color: #333;
 }
 }
 
 
+	#toolbar * {
+		vertical-align: middle;
+	}
+
 	#toolbar .Panel {
 	#toolbar .Panel {
 		padding: 4px;
 		padding: 4px;
 		color: #888;
 		color: #888;

+ 16 - 0
editor/css/main.css

@@ -67,6 +67,8 @@ textarea, input { outline: none; } /* osx */
 		display: none;
 		display: none;
 	}
 	}
 
 
+/* CodeMirror */
+
 .CodeMirror {
 .CodeMirror {
 
 
 	position: absolute !important;
 	position: absolute !important;
@@ -76,6 +78,20 @@ textarea, input { outline: none; } /* osx */
 
 
 }
 }
 
 
+	.CodeMirror .errorLine {
+
+		background: rgba(255,0,0,0.25);
+
+	}
+
+	.CodeMirror .esprima-error {
+
+		color: #f00;
+		text-align: right;
+		padding: 0px 20px;
+
+	}
+
 /* scene types */
 /* scene types */
 
 
 .type {
 .type {

+ 4 - 7
editor/examples/arkanoid.app.json

@@ -6,7 +6,7 @@
 			"generator": "ObjectExporter"
 			"generator": "ObjectExporter"
 		},
 		},
 		"object": {
 		"object": {
-			"uuid": "A32F9E56-4DDC-442E-8A0D-F23B9E93EEA9",
+			"uuid": "8EFB9C06-6312-4975-B04A-C9E4549BE348",
 			"type": "PerspectiveCamera",
 			"type": "PerspectiveCamera",
 			"name": "Camera",
 			"name": "Camera",
 			"fov": 50,
 			"fov": 50,
@@ -67,7 +67,6 @@
 				"uuid": "2F69AF3A-DDF5-4BBA-87B5-80159F90DDBF",
 				"uuid": "2F69AF3A-DDF5-4BBA-87B5-80159F90DDBF",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 86015,
 				"color": 86015,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -76,7 +75,6 @@
 				"uuid": "CFBEAD4C-6695-4A99-887B-8161E2947225",
 				"uuid": "CFBEAD4C-6695-4A99-887B-8161E2947225",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 16777215,
 				"color": 16777215,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -85,7 +83,6 @@
 				"uuid": "043B208C-1F83-42C6-802C-E0E35621C27C",
 				"uuid": "043B208C-1F83-42C6-802C-E0E35621C27C",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 16777215,
 				"color": 16777215,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -94,7 +91,6 @@
 				"uuid": "40EC9BDA-91C0-4671-937A-2BCB6DA7EEBB",
 				"uuid": "40EC9BDA-91C0-4671-937A-2BCB6DA7EEBB",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 13486790,
 				"color": 13486790,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -111,7 +107,7 @@
 					"name": "Ground",
 					"name": "Ground",
 					"geometry": "8F05A1F2-3877-478B-8DFC-F572AC61AB3A",
 					"geometry": "8F05A1F2-3877-478B-8DFC-F572AC61AB3A",
 					"material": "2F69AF3A-DDF5-4BBA-87B5-80159F90DDBF",
 					"material": "2F69AF3A-DDF5-4BBA-87B5-80159F90DDBF",
-					"matrix": [1,0,0,0,0,0.0007962886593304574,-0.9999997019767761,0,0,0.9999997019767761,0.0007962886593304574,0,0,0,0,1]
+					"matrix": [1,0,0,0,0,0.000796250649727881,-0.9999997019767761,0,0,0.9999997019767761,0.000796250649727881,0,0,0,0,1]
 				},
 				},
 				{
 				{
 					"uuid": "6EE2E764-43E0-48E0-85F2-E0C8823C20DC",
 					"uuid": "6EE2E764-43E0-48E0-85F2-E0C8823C20DC",
@@ -152,6 +148,7 @@
 					"color": 16777215,
 					"color": 16777215,
 					"intensity": 1,
 					"intensity": 1,
 					"distance": 0,
 					"distance": 0,
+					"decay": 1,
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,-116.54356384277344,69.48957061767578,-206.8248291015625,1]
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,-116.54356384277344,69.48957061767578,-206.8248291015625,1]
 				}]
 				}]
 		}
 		}
@@ -165,7 +162,7 @@
 		"31517222-A9A7-4EAF-B5F6-60751C0BABA3": [
 		"31517222-A9A7-4EAF-B5F6-60751C0BABA3": [
 			{
 			{
 				"name": "Game Logic",
 				"name": "Game Logic",
-				"source": "var ball = this.getObjectByName( 'Ball' );\n\nvar direction = new THREE.Vector3();\ndirection.x = Math.random() - 0.5;\ndirection.z = - 0.5;\ndirection.normalize();\n\nvar speed = new THREE.Vector3();\n\n//\n\nvar group = new THREE.Group();\nthis.add( group );\n\nvar paddle = this.getObjectByName( 'Paddle' );\ngroup.add( paddle );\n\nvar brick = this.getObjectByName( 'Brick' );\n\nfor ( var j = 0; j < 8; j ++  ) {\n\n\tvar material = new THREE.MeshPhongMaterial( { color: Math.random() * 0xffffff } );\n\n\tfor ( var i = 0; i < 12; i ++ ) {\n\t\t\n\t\tvar object = brick.clone();\n\t\tobject.position.x = i * 22 - 120;\n\t\tobject.position.z = j * 14 - 120;\n\t\tobject.material = material;\n\t\tgroup.add( object );\n\t\t\n\t}\n\t\n}\n\nbrick.visible = false;\n\n//\n\nvar raycaster = new THREE.Raycaster();\n\nfunction update( event ) {\n\t\n\tif ( ball.position.x < - 150 || ball.position.x > 150 ) direction.x = - direction.x;\n\tif ( ball.position.z < - 200 || ball.position.z > 200 ) direction.z = - direction.z;\n\n\tball.position.add( speed.copy( direction ).multiplyScalar( 4 ) );\n\t\n\traycaster.set( ball.position, direction );\n\t\n\tvar intersections = raycaster.intersectObjects( group.children );\n\t\n\tif ( intersections.length > 0 ) {\n\t\n\t\tvar intersection = intersections[ 0 ];\n\t\t\n\t\tif ( intersection.distance < 5 ) {\n\t\t\t\n\t\t\tif ( intersection.object !== paddle ) {\n\n\t\t\t\tgroup.remove( intersection.object );\n\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tdirection.reflect( intersection.face.normal );\n\t\t\t\n\t\t}\n\t\t\n\t}\n\n}"
+				"source": "var ball = this.getObjectByName( 'Ball' );\n\nvar direction = new THREE.Vector3();\ndirection.x = Math.random() - 0.5;\ndirection.z = - 0.5;\ndirection.normalize();\n\nvar speed = new THREE.Vector3();\n\n//\n\nvar group = new THREE.Group();\nthis.add( group );\n\nvar paddle = this.getObjectByName( 'Paddle' );\ngroup.add( paddle );\n\nvar brick = this.getObjectByName( 'Brick' );\n\nfor ( var j = 0; j < 8; j ++ ) {\n\n\tvar material = new THREE.MeshPhongMaterial( { color: Math.random() * 0xffffff } );\n\n\tfor ( var i = 0; i < 12; i ++ ) {\n\t\t\n\t\tvar object = brick.clone();\n\t\tobject.material = material;\n\t\tobject.position.x = i * 22 - 120;\n\t\tobject.position.z = j * 14 - 120;\n\t\tgroup.add( object );\n\t\t\n\t}\n\t\n}\n\nbrick.visible = false;\n\n//\n\nvar raycaster = new THREE.Raycaster();\n\nfunction update( event ) {\n\t\n\tif ( ball.position.x < - 150 || ball.position.x > 150 ) direction.x = - direction.x;\n\tif ( ball.position.z < - 200 || ball.position.z > 200 ) direction.z = - direction.z;\n\n\tball.position.x = Math.max( - 150, Math.min( 150, ball.position.x ) );\n\tball.position.z = Math.max( - 200, Math.min( 200, ball.position.z ) );\n\t\n\tball.position.add( speed.copy( direction ).multiplyScalar( event.delta / 4 ) );\n\t\n\traycaster.set( ball.position, direction );\n\t\n\tvar intersections = raycaster.intersectObjects( group.children );\n\t\n\tif ( intersections.length > 0 ) {\n\t\n\t\tvar intersection = intersections[ 0 ];\n\t\t\n\t\tif ( intersection.distance < 5 ) {\n\t\t\t\n\t\t\tif ( intersection.object !== paddle ) {\n\n\t\t\t\tgroup.remove( intersection.object );\n\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tdirection.reflect( intersection.face.normal );\n\t\t\t\n\t\t}\n\t\t\n\t}\n\n}"
 			}]
 			}]
 	}
 	}
 }
 }

+ 63 - 53
editor/examples/camera.app.json

@@ -6,14 +6,14 @@
 			"generator": "ObjectExporter"
 			"generator": "ObjectExporter"
 		},
 		},
 		"object": {
 		"object": {
-			"uuid": "F0D8434F-4603-415B-8024-792FE97B9600",
+			"uuid": "C7FB195B-270E-47B4-95C9-1754652A9D11",
 			"type": "PerspectiveCamera",
 			"type": "PerspectiveCamera",
 			"name": "Camera",
 			"name": "Camera",
 			"fov": 50,
 			"fov": 50,
 			"aspect": 1.2252042007001167,
 			"aspect": 1.2252042007001167,
 			"near": 0.1,
 			"near": 0.1,
 			"far": 100000,
 			"far": 100000,
-			"matrix": [0.9700406789779663,-5.500052080442686e-10,-0.24294254183769226,0,-0.04822639003396034,0.9800989627838135,-0.19256223738193512,0,0.23810774087905884,0.19850945472717285,0.950735867023468,0,159.0158233642578,132.5708465576172,634.9312744140625,1]
+			"matrix": [0.9700406789779663,-2.851828329042405e-9,-0.24294254183769226,0,-0.04822639003396034,0.9800989627838135,-0.1925622522830963,0,0.23810774087905884,0.19850945472717285,0.950735867023468,0,154.7735595703125,129.03408813476562,617.992431640625,1]
 		}
 		}
 	},
 	},
 	"scene": {
 	"scene": {
@@ -23,6 +23,14 @@
 			"generator": "ObjectExporter"
 			"generator": "ObjectExporter"
 		},
 		},
 		"geometries": [
 		"geometries": [
+			{
+				"uuid": "51BB3E54-D2DF-4576-9953-FB8E940588B5",
+				"type": "PlaneGeometry",
+				"width": 1000,
+				"height": 1000,
+				"widthSegments": 1,
+				"heightSegments": 1
+			},
 			{
 			{
 				"uuid": "D8E200D3-27BC-49F8-A5C5-7384206E70FE",
 				"uuid": "D8E200D3-27BC-49F8-A5C5-7384206E70FE",
 				"type": "BoxGeometry",
 				"type": "BoxGeometry",
@@ -43,14 +51,6 @@
 				"heightSegments": 1,
 				"heightSegments": 1,
 				"openEnded": false
 				"openEnded": false
 			},
 			},
-			{
-				"uuid": "51BB3E54-D2DF-4576-9953-FB8E940588B5",
-				"type": "PlaneGeometry",
-				"width": 1000,
-				"height": 1000,
-				"widthSegments": 1,
-				"heightSegments": 1
-			},
 			{
 			{
 				"uuid": "4DECFAB5-6FD1-4D84-9A29-565807B074EA",
 				"uuid": "4DECFAB5-6FD1-4D84-9A29-565807B074EA",
 				"type": "IcosahedronGeometry",
 				"type": "IcosahedronGeometry",
@@ -59,28 +59,25 @@
 			}],
 			}],
 		"materials": [
 		"materials": [
 			{
 			{
-				"uuid": "B5943856-E404-45D9-A427-4774202C2CD0",
+				"uuid": "4AE8130E-B6A8-47BC-ACCF-060973C74044",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
-				"color": 37119,
-				"ambient": 16777215,
+				"color": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
 			},
 			},
 			{
 			{
-				"uuid": "3F872310-2067-4BE4-9250-5B3F4E43797E",
+				"uuid": "B5943856-E404-45D9-A427-4774202C2CD0",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
-				"color": 15859456,
-				"ambient": 16777215,
+				"color": 37119,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
 			},
 			},
 			{
 			{
-				"uuid": "4AE8130E-B6A8-47BC-ACCF-060973C74044",
+				"uuid": "3F872310-2067-4BE4-9250-5B3F4E43797E",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
-				"color": 16777215,
-				"ambient": 16777215,
+				"color": 15859456,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -89,7 +86,6 @@
 				"uuid": "E1826901-7922-4584-A25D-6D487E2C9BBD",
 				"uuid": "E1826901-7922-4584-A25D-6D487E2C9BBD",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 16711680,
 				"color": 16711680,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -101,19 +97,34 @@
 			"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1],
 			"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1],
 			"children": [
 			"children": [
 				{
 				{
-					"uuid": "60B69C58-4201-43FD-815E-AD2EDFBBD0CE",
-					"type": "PerspectiveCamera",
-					"name": "PerspectiveCamera 1",
-					"fov": 50,
-					"aspect": 1,
-					"near": 100,
-					"far": 10000,
-					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,100,400,1]
+					"uuid": "B7CBBC6F-EC26-49B5-8D0D-67D9C535924B",
+					"type": "Group",
+					"name": "Dummy",
+					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,100,400,1],
+					"children": [
+						{
+							"uuid": "60B69C58-4201-43FD-815E-AD2EDFBBD0CE",
+							"type": "PerspectiveCamera",
+							"name": "PerspectiveCamera",
+							"fov": 50,
+							"aspect": 1,
+							"near": 100,
+							"far": 10000,
+							"matrix": [-1,0,-1.2246468525851679e-16,0,0,1,0,0,1.2246468525851679e-16,0,-1,0,0,0,0,1]
+						}]
+				},
+				{
+					"uuid": "A460C230-DC88-4A8F-A3FB-AA0FE735F3ED",
+					"type": "Mesh",
+					"name": "Plane",
+					"geometry": "51BB3E54-D2DF-4576-9953-FB8E940588B5",
+					"material": "4AE8130E-B6A8-47BC-ACCF-060973C74044",
+					"matrix": [1,0,0,0,0,0.040785226970911026,-0.9991679191589355,0,0,0.9991679191589355,0.040785226970911026,0,0,-50,0,1]
 				},
 				},
 				{
 				{
 					"uuid": "26DAAD69-725D-43B7-AF9D-990A99DEF8C5",
 					"uuid": "26DAAD69-725D-43B7-AF9D-990A99DEF8C5",
 					"type": "Mesh",
 					"type": "Mesh",
-					"name": "Box 1",
+					"name": "Box",
 					"geometry": "D8E200D3-27BC-49F8-A5C5-7384206E70FE",
 					"geometry": "D8E200D3-27BC-49F8-A5C5-7384206E70FE",
 					"material": "B5943856-E404-45D9-A427-4774202C2CD0",
 					"material": "B5943856-E404-45D9-A427-4774202C2CD0",
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1]
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1]
@@ -121,27 +132,18 @@
 				{
 				{
 					"uuid": "AAAFF2D6-4725-4AFC-A9FE-26419B11011F",
 					"uuid": "AAAFF2D6-4725-4AFC-A9FE-26419B11011F",
 					"type": "Mesh",
 					"type": "Mesh",
-					"name": "Cylinder 3",
+					"name": "Cylinder",
 					"geometry": "25BA32DB-8B02-4ABA-A77C-69868C464A1A",
 					"geometry": "25BA32DB-8B02-4ABA-A77C-69868C464A1A",
 					"material": "3F872310-2067-4BE4-9250-5B3F4E43797E",
 					"material": "3F872310-2067-4BE4-9250-5B3F4E43797E",
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,-130,-15,0,1]
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,-130,-15,0,1]
 				},
 				},
 				{
 				{
-					"uuid": "A460C230-DC88-4A8F-A3FB-AA0FE735F3ED",
+					"uuid": "B855E267-A266-4098-ACD6-6A1FDE7B88BA",
 					"type": "Mesh",
 					"type": "Mesh",
-					"name": "Plane 4",
-					"geometry": "51BB3E54-D2DF-4576-9953-FB8E940588B5",
-					"material": "4AE8130E-B6A8-47BC-ACCF-060973C74044",
-					"matrix": [1,0,0,0,0,0.040785059332847595,-0.9991679191589355,0,0,0.9991679191589355,0.040785059332847595,0,0,-50,0,1]
-				},
-				{
-					"uuid": "3412781E-27CC-43C3-A5DB-54C0C8E42ED6",
-					"type": "PointLight",
-					"name": "PointLight 2",
-					"color": 12773063,
-					"intensity": 1,
-					"distance": 0,
-					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,88.12999725341797,8.3100004196167,125.44999694824219,1]
+					"name": "Icosahedron",
+					"geometry": "4DECFAB5-6FD1-4D84-9A29-565807B074EA",
+					"material": "E1826901-7922-4584-A25D-6D487E2C9BBD",
+					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,130,-10,0,1]
 				},
 				},
 				{
 				{
 					"uuid": "E2939A7B-5E40-438A-8C1B-32126FBC6892",
 					"uuid": "E2939A7B-5E40-438A-8C1B-32126FBC6892",
@@ -150,23 +152,31 @@
 					"color": 9474221,
 					"color": 9474221,
 					"intensity": 0.75,
 					"intensity": 0.75,
 					"distance": 0,
 					"distance": 0,
+					"decay": 1,
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,-93.86000061035156,127.12999725341797,-114.30000305175781,1]
 					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,-93.86000061035156,127.12999725341797,-114.30000305175781,1]
 				},
 				},
 				{
 				{
-					"uuid": "B855E267-A266-4098-ACD6-6A1FDE7B88BA",
-					"type": "Mesh",
-					"name": "Icosahedron 1",
-					"geometry": "4DECFAB5-6FD1-4D84-9A29-565807B074EA",
-					"material": "E1826901-7922-4584-A25D-6D487E2C9BBD",
-					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,130,-10,0,1]
+					"uuid": "3412781E-27CC-43C3-A5DB-54C0C8E42ED6",
+					"type": "PointLight",
+					"name": "PointLight 2",
+					"color": 12773063,
+					"intensity": 1,
+					"distance": 0,
+					"decay": 1,
+					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,88.12999725341797,8.3100004196167,125.44999694824219,1]
 				}]
 				}]
 		}
 		}
 	},
 	},
 	"scripts": {
 	"scripts": {
 		"60B69C58-4201-43FD-815E-AD2EDFBBD0CE": [
 		"60B69C58-4201-43FD-815E-AD2EDFBBD0CE": [
 			{
 			{
-				"name": "Camera Orbit",
-				"source": "player.setCamera( this );\n\nfunction update( event ) {\n\n\tvar time = event.time * 0.001;\n\n\tthis.position.x = Math.sin( time ) * 400;\n\tthis.position.z = Math.cos( time ) * 400;\n\tthis.lookAt( scene.position );\n\n}"
+				"name": "Player Camera",
+				"source": "player.setCamera( this );"
+			}],
+		"B7CBBC6F-EC26-49B5-8D0D-67D9C535924B": [
+			{
+				"name": "Orbit",
+				"source": "function update( event ) {\n\n\tvar time = event.time * 0.001;\n\n\tthis.position.x = Math.sin( time ) * 400;\n\tthis.position.z = Math.cos( time ) * 400;\n\tthis.lookAt( scene.position );\n\n}"
 			}]
 			}]
 	}
 	}
-}
+}

+ 6 - 8
editor/examples/particles.app.json

@@ -46,14 +46,13 @@
 				"uuid": "6EDB0369-7E11-4B0F-BF98-4BD761846D65",
 				"uuid": "6EDB0369-7E11-4B0F-BF98-4BD761846D65",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 16777215,
 				"color": 16777215,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
 			},
 			},
 			{
 			{
-				"uuid": "D586E672-03FC-4C82-9D6E-CCCF899DDDB1",
-				"type": "MeshBasicMaterial",
+				"uuid": "F5361474-F5F1-412F-8D99-3699B868092D",
+				"type": "SpriteMaterial",
 				"color": 16777215
 				"color": 16777215
 			}],
 			}],
 		"object": {
 		"object": {
@@ -71,12 +70,11 @@
 					"matrix": [1,0,0,0,0,0.0007962886593304574,-0.9999997019767761,0,0,0.9999997019767761,0.0007962886593304574,0,0,-2,0,1]
 					"matrix": [1,0,0,0,0,0.0007962886593304574,-0.9999997019767761,0,0,0.9999997019767761,0.0007962886593304574,0,0,-2,0,1]
 				},
 				},
 				{
 				{
-					"uuid": "9DFA44C6-C85A-4F2F-9252-E9564C2785C5",
-					"type": "Mesh",
+					"uuid": "0A3CB873-07E6-4EEB-830B-68192504111B",
+					"type": "Sprite",
 					"name": "Particle",
 					"name": "Particle",
-					"geometry": "8693E7B2-0009-4C4C-94C5-8E031557AEC2",
-					"material": "D586E672-03FC-4C82-9D6E-CCCF899DDDB1",
-					"matrix": [1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1]
+					"material": "F5361474-F5F1-412F-8D99-3699B868092D",
+					"matrix": [3,0,0,0,0,3,0,0,0,0,1,0,0,0,0,1]
 				},
 				},
 				{
 				{
 					"uuid": "40E5CDA4-0E39-4265-9293-3E9EC3207F61",
 					"uuid": "40E5CDA4-0E39-4265-9293-3E9EC3207F61",

+ 4 - 7
editor/examples/pong.app.json

@@ -6,7 +6,7 @@
 			"generator": "ObjectExporter"
 			"generator": "ObjectExporter"
 		},
 		},
 		"object": {
 		"object": {
-			"uuid": "E5C76691-3D55-4E26-862E-24BADC21F4D7",
+			"uuid": "8EFB9C06-6312-4975-B04A-C9E4549BE348",
 			"type": "PerspectiveCamera",
 			"type": "PerspectiveCamera",
 			"name": "Camera",
 			"name": "Camera",
 			"fov": 50,
 			"fov": 50,
@@ -56,7 +56,6 @@
 				"uuid": "7EDF7C08-6325-418A-BBAB-89341C694730",
 				"uuid": "7EDF7C08-6325-418A-BBAB-89341C694730",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 16777215,
 				"color": 16777215,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 16777215,
 				"specular": 16777215,
 				"shininess": 30
 				"shininess": 30
@@ -65,7 +64,6 @@
 				"uuid": "B1CAF098-FE36-45E1-BEBE-8D6AC04821CC",
 				"uuid": "B1CAF098-FE36-45E1-BEBE-8D6AC04821CC",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 16711680,
 				"color": 16711680,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -74,7 +72,6 @@
 				"uuid": "FBDBE66D-B613-4741-802D-5AE1DE07DE46",
 				"uuid": "FBDBE66D-B613-4741-802D-5AE1DE07DE46",
 				"type": "MeshPhongMaterial",
 				"type": "MeshPhongMaterial",
 				"color": 2752767,
 				"color": 2752767,
-				"ambient": 16777215,
 				"emissive": 0,
 				"emissive": 0,
 				"specular": 1118481,
 				"specular": 1118481,
 				"shininess": 30
 				"shininess": 30
@@ -91,7 +88,7 @@
 					"name": "Ground",
 					"name": "Ground",
 					"geometry": "77B20ED1-2871-4B14-A652-8F823B2A817E",
 					"geometry": "77B20ED1-2871-4B14-A652-8F823B2A817E",
 					"material": "7EDF7C08-6325-418A-BBAB-89341C694730",
 					"material": "7EDF7C08-6325-418A-BBAB-89341C694730",
-					"matrix": [1,0,0,0,0,0.0007961748051457107,-0.9999997019767761,0,0,0.9999997019767761,0.0007961748051457107,0,0,-10,0,1]
+					"matrix": [1,0,0,0,0,0.0007960614748299122,-0.9999997019767761,0,0,0.9999997019767761,0.0007960614748299122,0,0,-10,0,1]
 				},
 				},
 				{
 				{
 					"uuid": "CE13E58A-4E8B-4F72-9E2E-7DE57C58F989",
 					"uuid": "CE13E58A-4E8B-4F72-9E2E-7DE57C58F989",
@@ -131,7 +128,7 @@
 		"31517222-A9A7-4EAF-B5F6-60751C0BABA3": [
 		"31517222-A9A7-4EAF-B5F6-60751C0BABA3": [
 			{
 			{
 				"name": "Game logic",
 				"name": "Game logic",
-				"source": "var ball = this.getObjectByName( 'Ball' );\n\nvar position = ball.position;\n\nvar velocity = new THREE.Vector3();\n\nvar direction = new THREE.Vector3();\ndirection.x = Math.random() - 0.5;\ndirection.z = Math.random() - 0.5;\ndirection.normalize();\n\nvar pad1 = this.getObjectByName( 'Pad 1' );\nvar pad2 = this.getObjectByName( 'Pad 2' );\n\nvar raycaster = new THREE.Raycaster();\nvar objects = [ pad1, pad2 ];\n\n//\n\nfunction mousemove( event ) {\n\n\tpad1.position.z = ( event.clientX / player.width ) * 300 - 150;\n\tpad2.position.z = - pad1.position.z;\n\n}\n\nfunction update( event ) {\n\n\tif ( position.x < -300 || position.x > 300 ) {\n\t\t\n\t\tdirection.x = - direction.x;\n\t\t\n\t}\n\n\tif ( position.z < -200 || position.z > 200 ) {\n\t\t\n\t\tdirection.z = - direction.z;\n\t\t\n\t}\n\t\n\traycaster.set( position, direction );\n\t\n\tvar intersections = raycaster.intersectObjects( objects );\n\t\n\tif ( intersections.length > 0 ) {\n\n\t\tvar intersection = intersections[ 0 ];\n\t\t\n\t\tif ( intersection.distance < 10 ) {\n\t\t\t\n\t\t\tdirection.reflect( intersection.face.normal );\n\t\t\t\n\t\t}\n\t\t\n\t}\n\n\tposition.add( velocity.copy( direction ).multiplyScalar( 8 ) );\n\n}"
+				"source": "var ball = this.getObjectByName( 'Ball' );\n\nvar position = ball.position;\n\nvar velocity = new THREE.Vector3();\n\nvar direction = new THREE.Vector3();\ndirection.x = Math.random() - 0.5;\ndirection.z = Math.random() - 0.5;\ndirection.normalize();\n\nvar pad1 = this.getObjectByName( 'Pad 1' );\nvar pad2 = this.getObjectByName( 'Pad 2' );\n\nvar raycaster = new THREE.Raycaster();\nvar objects = [ pad1, pad2 ];\n\n//\n\nfunction mousemove( event ) {\n\n\tpad1.position.z = ( event.clientX / player.width ) * 300 - 150;\n\tpad2.position.z = - pad1.position.z;\n\n}\n\nfunction update( event ) {\n\t\n\tif ( position.x < -300 || position.x > 300 ) direction.x = - direction.x;\n\tif ( position.z < -200 || position.z > 200 ) direction.z = - direction.z;\n\t\n\tposition.x = Math.max( - 300, Math.min( 300, position.x ) );\n\tposition.z = Math.max( - 200, Math.min( 200, position.z ) );\n\t\n\traycaster.set( position, direction );\n\t\n\tvar intersections = raycaster.intersectObjects( objects );\n\t\n\tif ( intersections.length > 0 ) {\n\n\t\tvar intersection = intersections[ 0 ];\n\t\t\n\t\tif ( intersection.distance < 10 ) {\n\t\t\t\n\t\t\tdirection.reflect( intersection.face.normal );\n\t\t\t\n\t\t}\n\t\t\n\t}\n\n\tposition.add( velocity.copy( direction ).multiplyScalar( event.delta / 2 ) );\n\n}"
 			}]
 			}]
 	}
 	}
-}
+}

+ 14 - 3
editor/index.html

@@ -33,7 +33,6 @@
 		<script src="../examples/js/loaders/ColladaLoader.js"></script>
 		<script src="../examples/js/loaders/ColladaLoader.js"></script>
 		<script src="../examples/js/loaders/OBJLoader.js"></script>
 		<script src="../examples/js/loaders/OBJLoader.js"></script>
 		<script src="../examples/js/loaders/PLYLoader.js"></script>
 		<script src="../examples/js/loaders/PLYLoader.js"></script>
-		<script src="../examples/js/loaders/SceneLoader.js"></script>
 		<script src="../examples/js/loaders/STLLoader.js"></script>
 		<script src="../examples/js/loaders/STLLoader.js"></script>
 		<script src="../examples/js/loaders/UTF8Loader.js"></script>
 		<script src="../examples/js/loaders/UTF8Loader.js"></script>
 		<script src="../examples/js/loaders/VRMLLoader.js"></script>
 		<script src="../examples/js/loaders/VRMLLoader.js"></script>
@@ -44,6 +43,8 @@
 		<script src="../examples/js/exporters/OBJExporter.js"></script>
 		<script src="../examples/js/exporters/OBJExporter.js"></script>
 		<script src="../examples/js/exporters/STLExporter.js"></script>
 		<script src="../examples/js/exporters/STLExporter.js"></script>
 
 
+		<script src="../examples/js/loaders/deprecated/SceneLoader.js"></script>
+
 		<script src="../examples/js/renderers/Projector.js"></script>
 		<script src="../examples/js/renderers/Projector.js"></script>
 		<script src="../examples/js/renderers/CanvasRenderer.js"></script>
 		<script src="../examples/js/renderers/CanvasRenderer.js"></script>
 		<script src="../examples/js/renderers/RaytracingRenderer.js"></script>
 		<script src="../examples/js/renderers/RaytracingRenderer.js"></script>
@@ -54,8 +55,10 @@
 		<link rel="stylesheet" href="js/libs/codemirror/theme/monokai.css">
 		<link rel="stylesheet" href="js/libs/codemirror/theme/monokai.css">
 		<script src="js/libs/codemirror/codemirror.js"></script>
 		<script src="js/libs/codemirror/codemirror.js"></script>
 		<script src="js/libs/codemirror/mode/javascript.js"></script>
 		<script src="js/libs/codemirror/mode/javascript.js"></script>
+		<script src="js/libs/esprima.js"></script>
 
 
 		<script src="js/libs/jszip.min.js"></script>
 		<script src="js/libs/jszip.min.js"></script>
+		<script src="js/libs/sortable.min.js"></script>
 		<script src="js/libs/signals.min.js"></script>
 		<script src="js/libs/signals.min.js"></script>
 		<script src="js/libs/ui.js"></script>
 		<script src="js/libs/ui.js"></script>
 		<script src="js/libs/ui.three.js"></script>
 		<script src="js/libs/ui.three.js"></script>
@@ -64,6 +67,9 @@
 		<script src="js/Player.js"></script>
 		<script src="js/Player.js"></script>
 		<script src="js/Script.js"></script>
 		<script src="js/Script.js"></script>
 
 
+		<script src="../examples/js/effects/VREffect.js"></script>
+		<script src="../examples/js/controls/VRControls.js"></script>
+
 		<script src="js/Storage.js"></script>
 		<script src="js/Storage.js"></script>
 
 
 		<script src="js/Editor.js"></script>
 		<script src="js/Editor.js"></script>
@@ -79,7 +85,7 @@
 		<script src="js/Menubar.Help.js"></script>
 		<script src="js/Menubar.Help.js"></script>
 		<script src="js/Menubar.Status.js"></script>
 		<script src="js/Menubar.Status.js"></script>
 		<script src="js/Sidebar.js"></script>
 		<script src="js/Sidebar.js"></script>
-		<script src="js/Sidebar.Renderer.js"></script>
+		<script src="js/Sidebar.Project.js"></script>
 		<script src="js/Sidebar.Scene.js"></script>
 		<script src="js/Sidebar.Scene.js"></script>
 		<script src="js/Sidebar.Object3D.js"></script>
 		<script src="js/Sidebar.Object3D.js"></script>
 		<script src="js/Sidebar.Animation.js"></script>
 		<script src="js/Sidebar.Animation.js"></script>
@@ -227,7 +233,12 @@
 			document.addEventListener( 'drop', function ( event ) {
 			document.addEventListener( 'drop', function ( event ) {
 
 
 				event.preventDefault();
 				event.preventDefault();
-				editor.loader.loadFile( event.dataTransfer.files[ 0 ] );
+
+				if ( event.dataTransfer.files.length > 0 ) {
+
+					editor.loader.loadFile( event.dataTransfer.files[ 0 ] );
+
+				}
 
 
 			}, false );
 			}, false );
 
 

+ 6 - 5
editor/js/Config.js

@@ -9,10 +9,11 @@ var Config = function () {
 	var storage = {
 	var storage = {
 		'autosave': true,
 		'autosave': true,
 		'theme': 'css/light.css',
 		'theme': 'css/light.css',
-		
-		'renderer': 'WebGLRenderer',
-		'renderer/antialias': true,
-	
+
+		'project/renderer': 'WebGLRenderer',
+		'project/renderer/antialias': true,
+		'project/vr': false,
+
 		'camera/position': [ 500, 250, 500 ],
 		'camera/position': [ 500, 250, 500 ],
 		'camera/target': [ 0, 0, 0 ],
 		'camera/target': [ 0, 0, 0 ],
 
 
@@ -20,7 +21,7 @@ var Config = function () {
 		'ui/sidebar/geometry/collapsed': true,
 		'ui/sidebar/geometry/collapsed': true,
 		'ui/sidebar/material/collapsed': true,
 		'ui/sidebar/material/collapsed': true,
 		'ui/sidebar/object3d/collapsed': false,
 		'ui/sidebar/object3d/collapsed': false,
-		'ui/sidebar/renderer/collapsed': true,
+		'ui/sidebar/project/collapsed': true,
 		'ui/sidebar/scene/collapsed': false,
 		'ui/sidebar/scene/collapsed': false,
 		'ui/sidebar/script/collapsed': true
 		'ui/sidebar/script/collapsed': true
 	};
 	};

+ 28 - 17
editor/js/Editor.js

@@ -155,7 +155,31 @@ Editor.prototype = {
 
 
 	},
 	},
 
 
-	setObjectName: function ( object, name ) {
+	moveObject: function ( object, parent, before ) {
+
+		if ( parent === undefined ) {
+
+			parent = this.scene;
+
+		}
+
+		parent.add( object );
+
+		// sort children array
+
+		if ( before !== undefined ) {
+
+			var index = parent.children.indexOf( before );
+			parent.children.splice( index, 0, object );
+			parent.children.pop();
+
+		}
+
+		this.signals.sceneGraphChanged.dispatch();
+
+	},
+
+	nameObject: function ( object, name ) {
 
 
 		object.name = name;
 		object.name = name;
 		this.signals.sceneGraphChanged.dispatch();
 		this.signals.sceneGraphChanged.dispatch();
@@ -319,22 +343,6 @@ Editor.prototype = {
 
 
 	//
 	//
 
 
-	parent: function ( object, parent ) {
-
-		if ( parent === undefined ) {
-
-			parent = this.scene;
-
-		}
-
-		parent.add( object );
-
-		this.signals.sceneGraphChanged.dispatch();
-
-	},
-
-	//
-
 	select: function ( object ) {
 	select: function ( object ) {
 
 
 		if ( this.selected === object ) return;
 		if ( this.selected === object ) return;
@@ -462,6 +470,9 @@ Editor.prototype = {
 
 
 		return {
 		return {
 
 
+			project: {
+				vr: this.config.getKey( 'project/vr' )
+			},
 			camera: this.camera.toJSON(),
 			camera: this.camera.toJSON(),
 			scene: this.scene.toJSON(),
 			scene: this.scene.toJSON(),
 			scripts: this.scripts
 			scripts: this.scripts

+ 0 - 32
editor/js/Menubar.Edit.js

@@ -53,38 +53,6 @@ Menubar.Edit = function ( editor ) {
 	} );
 	} );
 	options.add( option );
 	options.add( option );
 
 
-	//
-
-	options.add( new UI.HorizontalRule() );
-
-	// Flatten
-
-	var option = new UI.Panel();
-	option.setClass( 'option' );
-	option.setTextContent( 'Flatten' );
-	option.onClick( function () {
-
-		var object = editor.selected;
-
-		if ( object.parent === undefined ) return; // avoid flattening the camera or scene
-
-		if ( confirm( 'Flatten ' + object.name + '?' ) === false ) return;
-
-		var geometry = object.geometry;
-
-		geometry.applyMatrix( object.matrix );
-		geometry.verticesNeedUpdate = true;
-		geometry.normalsNeedUpdate = true;
-
-		object.position.set( 0, 0, 0 );
-		object.rotation.set( 0, 0, 0 );
-		object.scale.set( 1, 1, 1 );
-
-		editor.signals.objectChanged.dispatch( object );
-
-	} );
-	options.add( option );
-
 	return container;
 	return container;
 
 
 };
 };

+ 15 - 8
editor/js/Menubar.File.js

@@ -89,7 +89,7 @@ Menubar.File = function ( editor ) {
 		output = JSON.stringify( output, null, '\t' );
 		output = JSON.stringify( output, null, '\t' );
 		output = output.replace( /[\n\t]+([\d\.e\-\[\]]+)/g, '$1' );
 		output = output.replace( /[\n\t]+([\d\.e\-\[\]]+)/g, '$1' );
 
 
-		exportString( output );
+		exportString( output, 'geometry.json' );
 
 
 	} );
 	} );
 	options.add( option );
 	options.add( option );
@@ -114,7 +114,7 @@ Menubar.File = function ( editor ) {
 		output = JSON.stringify( output, null, '\t' );
 		output = JSON.stringify( output, null, '\t' );
 		output = output.replace( /[\n\t]+([\d\.e\-\[\]]+)/g, '$1' );
 		output = output.replace( /[\n\t]+([\d\.e\-\[\]]+)/g, '$1' );
 
 
-		exportString( output );
+		exportString( output, 'model.json' );
 
 
 	} );
 	} );
 	options.add( option );
 	options.add( option );
@@ -130,7 +130,7 @@ Menubar.File = function ( editor ) {
 		output = JSON.stringify( output, null, '\t' );
 		output = JSON.stringify( output, null, '\t' );
 		output = output.replace( /[\n\t]+([\d\.e\-\[\]]+)/g, '$1' );
 		output = output.replace( /[\n\t]+([\d\.e\-\[\]]+)/g, '$1' );
 
 
-		exportString( output );
+		exportString( output, 'scene.json' );
 
 
 	} );
 	} );
 	options.add( option );
 	options.add( option );
@@ -153,7 +153,7 @@ Menubar.File = function ( editor ) {
 
 
 		var exporter = new THREE.OBJExporter();
 		var exporter = new THREE.OBJExporter();
 
 
-		exportString( exporter.parse( object ) );
+		exportString( exporter.parse( object ), 'model.obj' );
 
 
 	} );
 	} );
 	options.add( option );
 	options.add( option );
@@ -167,7 +167,7 @@ Menubar.File = function ( editor ) {
 
 
 		var exporter = new THREE.STLExporter();
 		var exporter = new THREE.STLExporter();
 
 
-		exportString( exporter.parse( editor.scene ) );
+		exportString( exporter.parse( editor.scene ), 'model.stl' );
 
 
 	} );
 	} );
 	options.add( option );
 	options.add( option );
@@ -217,6 +217,10 @@ Menubar.File = function ( editor ) {
 			'',
 			'',
 			'				document.body.appendChild( player.dom );',
 			'				document.body.appendChild( player.dom );',
 			'',
 			'',
+			'				window.addEventListener( \'resize\', function () {',
+			'					player.setSize( window.innerWidth, window.innerHeight );',
+			'				} );',
+			'',
 			'			} );',
 			'			} );',
 			'',
 			'',
 			'		</script>',
 			'		</script>',
@@ -274,13 +278,16 @@ Menubar.File = function ( editor ) {
 
 
 	//
 	//
 
 
-	var exportString = function ( output ) {
+	var exportString = function ( output, filename ) {
 
 
 		var blob = new Blob( [ output ], { type: 'text/plain' } );
 		var blob = new Blob( [ output ], { type: 'text/plain' } );
 		var objectURL = URL.createObjectURL( blob );
 		var objectURL = URL.createObjectURL( blob );
 
 
-		window.open( objectURL, '_blank' );
-		window.focus();
+		var link = document.createElement( 'a' );
+		link.href = objectURL;
+		link.download = filename || 'data.json';
+		link.target = '_blank';
+		link.click();
 
 
 	};
 	};
 
 

+ 2 - 2
editor/js/Player.js

@@ -19,7 +19,7 @@ var Player = function ( editor ) {
 
 
 		if ( player.dom === undefined ) return;
 		if ( player.dom === undefined ) return;
 
 
-		player.setSize( container.dom.offsetWidth, container.dom.offsetHeight );
+		player.setSize( container.dom.clientWidth, container.dom.clientHeight );
 
 
 	} );
 	} );
 
 
@@ -28,7 +28,7 @@ var Player = function ( editor ) {
 		container.setDisplay( '' );
 		container.setDisplay( '' );
 
 
 		player.load( editor.toJSON() );
 		player.load( editor.toJSON() );
-		player.setSize( container.dom.offsetWidth, container.dom.offsetHeight );
+		player.setSize( container.dom.clientWidth, container.dom.clientHeight );
 		player.play();
 		player.play();
 
 
 		container.dom.appendChild( player.dom );
 		container.dom.appendChild( player.dom );

+ 87 - 4
editor/js/Script.js

@@ -15,7 +15,7 @@ var Script = function ( editor ) {
 	var header = new UI.Panel();
 	var header = new UI.Panel();
 	header.setPadding( '10px' );
 	header.setPadding( '10px' );
 	container.add( header );
 	container.add( header );
-	
+
 	var title = new UI.Text().setColor( '#fff' );
 	var title = new UI.Text().setColor( '#fff' );
 	header.add( title );
 	header.add( title );
 
 
@@ -59,16 +59,99 @@ var Script = function ( editor ) {
 		clearTimeout( delay );
 		clearTimeout( delay );
 		delay = setTimeout( function () {
 		delay = setTimeout( function () {
 
 
-			currentScript.source = codemirror.getValue();
+			var value = codemirror.getValue();
+
+			if ( validate( value ) ) {
+
+				currentScript.source = value;
+				signals.scriptChanged.dispatch( currentScript );
 
 
-			signals.scriptChanged.dispatch( currentScript );
+			}
 
 
 		}, 300 );
 		}, 300 );
 
 
 	});
 	});
 
 
+	// validate
+
+	var errorLines = [];
+	var widgets = [];
+
+	var validate = function ( string ) {
+
+		var syntax, errors;
+
+		return codemirror.operation( function () {
+
+			while ( errorLines.length > 0 ) {
+
+				codemirror.removeLineClass( errorLines.shift(), 'background', 'errorLine' );
+
+			}
+
+			while ( widgets.length > 0 ) {
+
+				codemirror.removeLineWidget( widgets.shift() );
+
+			}
+
+			//
+
+			try {
+
+				syntax = esprima.parse( string, { tolerant: true } );
+				errors = syntax.errors;
+
+				for ( var i = 0; i < errors.length; i ++ ) {
+
+					var error = errors[ i ];
+
+					var message = document.createElement( 'div' );
+					message.className = 'esprima-error';
+					message.textContent = error.message.replace(/Line [0-9]+: /, '');
+
+					var lineNumber = error.lineNumber - 1;
+					errorLines.push( lineNumber );
+
+					codemirror.addLineClass( lineNumber, 'background', 'errorLine' );
+
+					var widget = codemirror.addLineWidget(
+						lineNumber,
+						message
+					);
+
+					widgets.push( widget );
+
+				}
+
+			} catch ( error ) {
+
+				var message = document.createElement( 'div' );
+				message.className = 'esprima-error';
+				message.textContent = error.message.replace(/Line [0-9]+: /, '');
+
+				var lineNumber = error.lineNumber - 1;
+				errorLines.push( lineNumber );
+
+				codemirror.addLineClass( lineNumber, 'background', 'errorLine' );
+
+				var widget = codemirror.addLineWidget(
+					lineNumber,
+					message
+				);
+
+				widgets.push( widget );
+
+			}
+
+			return errorLines.length === 0;
+
+		});
+
+	};
+
 	//
 	//
-	
+
 	signals.editorCleared.add( function () {
 	signals.editorCleared.add( function () {
 
 
 		container.setDisplay( 'none' );
 		container.setDisplay( 'none' );

+ 2 - 2
editor/js/Sidebar.Geometry.BufferGeometry.js

@@ -9,7 +9,7 @@ Sidebar.Geometry.BufferGeometry = function ( signals ) {
 	// vertices
 	// vertices
 
 
 	var verticesRow = new UI.Panel();
 	var verticesRow = new UI.Panel();
-	var vertices = new UI.Text().setColor( '#444' ).setFontSize( '12px' );
+	var vertices = new UI.Text().setFontSize( '12px' );
 
 
 	verticesRow.add( new UI.Text( 'Vertices' ).setWidth( '90px' ) );
 	verticesRow.add( new UI.Text( 'Vertices' ).setWidth( '90px' ) );
 	verticesRow.add( vertices );
 	verticesRow.add( vertices );
@@ -19,7 +19,7 @@ Sidebar.Geometry.BufferGeometry = function ( signals ) {
 	// faces
 	// faces
 
 
 	var facesRow = new UI.Panel();
 	var facesRow = new UI.Panel();
-	var faces = new UI.Text().setColor( '#444' ).setFontSize( '12px' );
+	var faces = new UI.Text().setFontSize( '12px' );
 
 
 	facesRow.add( new UI.Text( 'Faces' ).setWidth( '90px' ) );
 	facesRow.add( new UI.Text( 'Faces' ).setWidth( '90px' ) );
 	facesRow.add( faces );
 	facesRow.add( faces );

+ 2 - 2
editor/js/Sidebar.Geometry.Geometry.js

@@ -9,7 +9,7 @@ Sidebar.Geometry.Geometry = function ( signals ) {
 	// vertices
 	// vertices
 
 
 	var verticesRow = new UI.Panel();
 	var verticesRow = new UI.Panel();
-	var vertices = new UI.Text().setColor( '#444' ).setFontSize( '12px' );
+	var vertices = new UI.Text().setFontSize( '12px' );
 
 
 	verticesRow.add( new UI.Text( 'Vertices' ).setWidth( '90px' ) );
 	verticesRow.add( new UI.Text( 'Vertices' ).setWidth( '90px' ) );
 	verticesRow.add( vertices );
 	verticesRow.add( vertices );
@@ -19,7 +19,7 @@ Sidebar.Geometry.Geometry = function ( signals ) {
 	// faces
 	// faces
 
 
 	var facesRow = new UI.Panel();
 	var facesRow = new UI.Panel();
-	var faces = new UI.Text().setColor( '#444' ).setFontSize( '12px' );
+	var faces = new UI.Text().setFontSize( '12px' );
 
 
 	facesRow.add( new UI.Text( 'Faces' ).setWidth( '90px' ) );
 	facesRow.add( new UI.Text( 'Faces' ).setWidth( '90px' ) );
 	facesRow.add( faces );
 	facesRow.add( faces );

+ 62 - 2
editor/js/Sidebar.Geometry.js

@@ -17,12 +17,72 @@ Sidebar.Geometry = function ( editor ) {
 
 
 	var geometryType = new UI.Text().setTextTransform( 'uppercase' );
 	var geometryType = new UI.Text().setTextTransform( 'uppercase' );
 	container.addStatic( geometryType );
 	container.addStatic( geometryType );
+
+	// Actions
+
+	var objectActions = new UI.Select().setPosition('absolute').setRight( '8px' ).setFontSize( '11px' );
+	objectActions.setOptions( {
+
+		'Actions': 'Actions',
+		'Center': 'Center',
+		'Flatten': 'Flatten'
+
+	} );
+	objectActions.onClick( function ( event ) {
+
+		event.stopPropagation(); // Avoid panel collapsing
+
+	} );
+	objectActions.onChange( function ( event ) {
+
+		var action = this.getValue();
+
+		var object = editor.selected;
+		var geometry = object.geometry;
+
+		if ( confirm( action + ' ' + object.name + '?' ) === false ) return;
+
+		switch ( action ) {
+
+			case 'Center':
+
+				var offset = geometry.center();
+
+				object.position.sub( offset );
+
+				editor.signals.geometryChanged.dispatch( geometry );
+				editor.signals.objectChanged.dispatch( object );
+
+				break;
+
+			case 'Flatten':
+
+				geometry.applyMatrix( object.matrix );
+
+				object.position.set( 0, 0, 0 );
+				object.rotation.set( 0, 0, 0 );
+				object.scale.set( 1, 1, 1 );
+
+				editor.signals.geometryChanged.dispatch( geometry );
+				editor.signals.objectChanged.dispatch( object );
+
+				break;
+
+		}
+
+		this.setValue( 'Actions' );
+
+		signals.objectChanged.dispatch( object );
+
+	} );
+	container.addStatic( objectActions );
+
 	container.add( new UI.Break() );
 	container.add( new UI.Break() );
 
 
 	// uuid
 	// uuid
 
 
 	var geometryUUIDRow = new UI.Panel();
 	var geometryUUIDRow = new UI.Panel();
-	var geometryUUID = new UI.Input().setWidth( '115px' ).setColor( '#444' ).setFontSize( '12px' ).setDisabled( true );
+	var geometryUUID = new UI.Input().setWidth( '115px' ).setFontSize( '12px' ).setDisabled( true );
 	var geometryUUIDRenew = new UI.Button( '⟳' ).setMarginLeft( '7px' ).onClick( function () {
 	var geometryUUIDRenew = new UI.Button( '⟳' ).setMarginLeft( '7px' ).onClick( function () {
 
 
 		geometryUUID.setValue( THREE.Math.generateUUID() );
 		geometryUUID.setValue( THREE.Math.generateUUID() );
@@ -40,7 +100,7 @@ Sidebar.Geometry = function ( editor ) {
 	// name
 	// name
 
 
 	var geometryNameRow = new UI.Panel();
 	var geometryNameRow = new UI.Panel();
-	var geometryName = new UI.Input().setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( function () {
+	var geometryName = new UI.Input().setWidth( '150px' ).setFontSize( '12px' ).onChange( function () {
 
 
 		editor.setGeometryName( editor.selected.geometry, geometryName.getValue() );
 		editor.setGeometryName( editor.selected.geometry, geometryName.getValue() );
 
 

+ 33 - 44
editor/js/Sidebar.Material.js

@@ -40,7 +40,7 @@ Sidebar.Material = function ( editor ) {
 	// uuid
 	// uuid
 
 
 	var materialUUIDRow = new UI.Panel();
 	var materialUUIDRow = new UI.Panel();
-	var materialUUID = new UI.Input().setWidth( '115px' ).setColor( '#444' ).setFontSize( '12px' ).setDisabled( true );
+	var materialUUID = new UI.Input().setWidth( '115px' ).setFontSize( '12px' ).setDisabled( true );
 	var materialUUIDRenew = new UI.Button( '⟳' ).setMarginLeft( '7px' ).onClick( function () {
 	var materialUUIDRenew = new UI.Button( '⟳' ).setMarginLeft( '7px' ).onClick( function () {
 
 
 		materialUUID.setValue( THREE.Math.generateUUID() );
 		materialUUID.setValue( THREE.Math.generateUUID() );
@@ -57,7 +57,7 @@ Sidebar.Material = function ( editor ) {
 	// name
 	// name
 
 
 	var materialNameRow = new UI.Panel();
 	var materialNameRow = new UI.Panel();
-	var materialName = new UI.Input().setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( function () {
+	var materialName = new UI.Input().setWidth( '150px' ).setFontSize( '12px' ).onChange( function () {
 
 
 		editor.setMaterialName( editor.selected.material, materialName.getValue() );
 		editor.setMaterialName( editor.selected.material, materialName.getValue() );
 
 
@@ -84,7 +84,7 @@ Sidebar.Material = function ( editor ) {
 		'ShaderMaterial': 'ShaderMaterial',
 		'ShaderMaterial': 'ShaderMaterial',
 		'SpriteMaterial': 'SpriteMaterial'
 		'SpriteMaterial': 'SpriteMaterial'
 
 
-	} ).setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( update );
+	} ).setWidth( '150px' ).setFontSize( '12px' ).onChange( update );
 
 
 	materialClassRow.add( new UI.Text( 'Type' ).setWidth( '90px' ) );
 	materialClassRow.add( new UI.Text( 'Type' ).setWidth( '90px' ) );
 	materialClassRow.add( materialClass );
 	materialClassRow.add( materialClass );
@@ -101,16 +101,6 @@ Sidebar.Material = function ( editor ) {
 
 
 	container.add( materialColorRow );
 	container.add( materialColorRow );
 
 
-	// ambient
-
-	var materialAmbientRow = new UI.Panel();
-	var materialAmbient = new UI.Color().onChange( update );
-
-	materialAmbientRow.add( new UI.Text( 'Ambient' ).setWidth( '90px' ) );
-	materialAmbientRow.add( materialAmbient );
-
-	container.add( materialAmbientRow );
-
 	// emissive
 	// emissive
 
 
 	var materialEmissiveRow = new UI.Panel();
 	var materialEmissiveRow = new UI.Panel();
@@ -204,7 +194,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialMapRow = new UI.Panel();
 	var materialMapRow = new UI.Panel();
 	var materialMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialMap = new UI.Texture().setColor( '#444' ).onChange( update );
+	var materialMap = new UI.Texture().onChange( update );
 
 
 	materialMapRow.add( new UI.Text( 'Map' ).setWidth( '90px' ) );
 	materialMapRow.add( new UI.Text( 'Map' ).setWidth( '90px' ) );
 	materialMapRow.add( materialMapEnabled );
 	materialMapRow.add( materialMapEnabled );
@@ -216,7 +206,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialAlphaMapRow = new UI.Panel();
 	var materialAlphaMapRow = new UI.Panel();
 	var materialAlphaMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialAlphaMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialAlphaMap = new UI.Texture().setColor( '#444' ).onChange( update );
+	var materialAlphaMap = new UI.Texture().onChange( update );
 
 
 	materialAlphaMapRow.add( new UI.Text( 'Alpha Map' ).setWidth( '90px' ) );
 	materialAlphaMapRow.add( new UI.Text( 'Alpha Map' ).setWidth( '90px' ) );
 	materialAlphaMapRow.add( materialAlphaMapEnabled );
 	materialAlphaMapRow.add( materialAlphaMapEnabled );
@@ -228,7 +218,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialLightMapRow = new UI.Panel();
 	var materialLightMapRow = new UI.Panel();
 	var materialLightMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialLightMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialLightMap = new UI.Texture().setColor( '#444' ).onChange( update );
+	var materialLightMap = new UI.Texture().onChange( update );
 
 
 	materialLightMapRow.add( new UI.Text( 'Light Map' ).setWidth( '90px' ) );
 	materialLightMapRow.add( new UI.Text( 'Light Map' ).setWidth( '90px' ) );
 	materialLightMapRow.add( materialLightMapEnabled );
 	materialLightMapRow.add( materialLightMapEnabled );
@@ -240,7 +230,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialBumpMapRow = new UI.Panel();
 	var materialBumpMapRow = new UI.Panel();
 	var materialBumpMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialBumpMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialBumpMap = new UI.Texture().setColor( '#444' ).onChange( update );
+	var materialBumpMap = new UI.Texture().onChange( update );
 	var materialBumpScale = new UI.Number( 1 ).setWidth( '30px' ).onChange( update );
 	var materialBumpScale = new UI.Number( 1 ).setWidth( '30px' ).onChange( update );
 
 
 	materialBumpMapRow.add( new UI.Text( 'Bump Map' ).setWidth( '90px' ) );
 	materialBumpMapRow.add( new UI.Text( 'Bump Map' ).setWidth( '90px' ) );
@@ -254,7 +244,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialNormalMapRow = new UI.Panel();
 	var materialNormalMapRow = new UI.Panel();
 	var materialNormalMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialNormalMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialNormalMap = new UI.Texture().setColor( '#444' ).onChange( update );
+	var materialNormalMap = new UI.Texture().onChange( update );
 
 
 	materialNormalMapRow.add( new UI.Text( 'Normal Map' ).setWidth( '90px' ) );
 	materialNormalMapRow.add( new UI.Text( 'Normal Map' ).setWidth( '90px' ) );
 	materialNormalMapRow.add( materialNormalMapEnabled );
 	materialNormalMapRow.add( materialNormalMapEnabled );
@@ -266,7 +256,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialSpecularMapRow = new UI.Panel();
 	var materialSpecularMapRow = new UI.Panel();
 	var materialSpecularMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialSpecularMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialSpecularMap = new UI.Texture().setColor( '#444' ).onChange( update );
+	var materialSpecularMap = new UI.Texture().onChange( update );
 
 
 	materialSpecularMapRow.add( new UI.Text( 'Specular Map' ).setWidth( '90px' ) );
 	materialSpecularMapRow.add( new UI.Text( 'Specular Map' ).setWidth( '90px' ) );
 	materialSpecularMapRow.add( materialSpecularMapEnabled );
 	materialSpecularMapRow.add( materialSpecularMapEnabled );
@@ -278,7 +268,7 @@ Sidebar.Material = function ( editor ) {
 
 
 	var materialEnvMapRow = new UI.Panel();
 	var materialEnvMapRow = new UI.Panel();
 	var materialEnvMapEnabled = new UI.Checkbox( false ).onChange( update );
 	var materialEnvMapEnabled = new UI.Checkbox( false ).onChange( update );
-	var materialEnvMap = new UI.Texture( THREE.SphericalReflectionMapping ).setColor( '#444' ).onChange( update );
+	var materialEnvMap = new UI.Texture( THREE.SphericalReflectionMapping ).onChange( update );
 	var materialReflectivity = new UI.Number( 1 ).setWidth( '30px' ).onChange( update );
 	var materialReflectivity = new UI.Number( 1 ).setWidth( '30px' ).onChange( update );
 
 
 	materialEnvMapRow.add( new UI.Text( 'Env Map' ).setWidth( '90px' ) );
 	materialEnvMapRow.add( new UI.Text( 'Env Map' ).setWidth( '90px' ) );
@@ -297,7 +287,7 @@ Sidebar.Material = function ( editor ) {
 		1: 'Back',
 		1: 'Back',
 		2: 'Double'
 		2: 'Double'
 
 
-	} ).setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( update );
+	} ).setWidth( '150px' ).setFontSize( '12px' ).onChange( update );
 
 
 	materialSideRow.add( new UI.Text( 'Side' ).setWidth( '90px' ) );
 	materialSideRow.add( new UI.Text( 'Side' ).setWidth( '90px' ) );
 	materialSideRow.add( materialSide );
 	materialSideRow.add( materialSide );
@@ -313,7 +303,7 @@ Sidebar.Material = function ( editor ) {
 		1: 'Flat',
 		1: 'Flat',
 		2: 'Smooth'
 		2: 'Smooth'
 
 
-	} ).setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( update );
+	} ).setWidth( '150px' ).setFontSize( '12px' ).onChange( update );
 
 
 	materialShadingRow.add( new UI.Text( 'Shading' ).setWidth( '90px' ) );
 	materialShadingRow.add( new UI.Text( 'Shading' ).setWidth( '90px' ) );
 	materialShadingRow.add( materialShading );
 	materialShadingRow.add( materialShading );
@@ -332,7 +322,7 @@ Sidebar.Material = function ( editor ) {
 		4: 'Multiply',
 		4: 'Multiply',
 		5: 'Custom'
 		5: 'Custom'
 
 
-	} ).setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( update );
+	} ).setWidth( '150px' ).setFontSize( '12px' ).onChange( update );
 
 
 	materialBlendingRow.add( new UI.Text( 'Blending' ).setWidth( '90px' ) );
 	materialBlendingRow.add( new UI.Text( 'Blending' ).setWidth( '90px' ) );
 	materialBlendingRow.add( materialBlending );
 	materialBlendingRow.add( materialBlending );
@@ -379,7 +369,7 @@ Sidebar.Material = function ( editor ) {
 
 
 		var geometry = object.geometry;
 		var geometry = object.geometry;
 		var material = object.material;
 		var material = object.material;
-		
+
 		var textureWarning = false;
 		var textureWarning = false;
 		var objectHasUvs = false;
 		var objectHasUvs = false;
 
 
@@ -408,12 +398,6 @@ Sidebar.Material = function ( editor ) {
 
 
 			}
 			}
 
 
-			if ( material.ambient !== undefined ) {
-
-				material.ambient.setHex( materialAmbient.getHexValue() );
-
-			}
-
 			if ( material.emissive !== undefined ) {
 			if ( material.emissive !== undefined ) {
 
 
 				material.emissive.setHex( materialEmissive.getHexValue() );
 				material.emissive.setHex( materialEmissive.getHexValue() );
@@ -452,8 +436,20 @@ Sidebar.Material = function ( editor ) {
 
 
 			if ( material.vertexColors !== undefined ) {
 			if ( material.vertexColors !== undefined ) {
 
 
-				material.vertexColors = parseInt( materialVertexColors.getValue() );
-				material.needsUpdate = true;
+				var vertexColors = parseInt( materialVertexColors.getValue() );
+
+				if ( material.vertexColors !== vertexColors ) {
+
+					if ( geometry instanceof THREE.Geometry ) {
+
+						geometry.groupsNeedUpdate = true;
+
+					}
+
+					material.vertexColors = vertexColors;
+					material.needsUpdate = true;
+
+				}
 
 
 			}
 			}
 
 
@@ -467,7 +463,7 @@ Sidebar.Material = function ( editor ) {
 
 
 				var mapEnabled = materialMapEnabled.getValue() === true;
 				var mapEnabled = materialMapEnabled.getValue() === true;
 
 
-				if ( objectHasUvs )  {
+				if ( objectHasUvs ) {
 
 
 					material.map = mapEnabled ? materialMap.getValue() : null;
 					material.map = mapEnabled ? materialMap.getValue() : null;
 					material.needsUpdate = true;
 					material.needsUpdate = true;
@@ -484,7 +480,7 @@ Sidebar.Material = function ( editor ) {
 
 
 				var mapEnabled = materialAlphaMapEnabled.getValue() === true;
 				var mapEnabled = materialAlphaMapEnabled.getValue() === true;
 
 
-				if ( objectHasUvs )  {
+				if ( objectHasUvs ) {
 
 
 					material.alphaMap = mapEnabled ? materialAlphaMap.getValue() : null;
 					material.alphaMap = mapEnabled ? materialAlphaMap.getValue() : null;
 					material.needsUpdate = true;
 					material.needsUpdate = true;
@@ -520,7 +516,7 @@ Sidebar.Material = function ( editor ) {
 
 
 				var bumpMapEnabled = materialBumpMapEnabled.getValue() === true;
 				var bumpMapEnabled = materialBumpMapEnabled.getValue() === true;
 
 
-				if ( objectHasUvs )  {
+				if ( objectHasUvs ) {
 
 
 					material.bumpMap = bumpMapEnabled ? materialBumpMap.getValue() : null;
 					material.bumpMap = bumpMapEnabled ? materialBumpMap.getValue() : null;
 					material.bumpScale = materialBumpScale.getValue();
 					material.bumpScale = materialBumpScale.getValue();
@@ -538,7 +534,7 @@ Sidebar.Material = function ( editor ) {
 
 
 				var normalMapEnabled = materialNormalMapEnabled.getValue() === true;
 				var normalMapEnabled = materialNormalMapEnabled.getValue() === true;
 
 
-				if ( objectHasUvs )  {
+				if ( objectHasUvs ) {
 
 
 					material.normalMap = normalMapEnabled ? materialNormalMap.getValue() : null;
 					material.normalMap = normalMapEnabled ? materialNormalMap.getValue() : null;
 					material.needsUpdate = true;
 					material.needsUpdate = true;
@@ -555,7 +551,7 @@ Sidebar.Material = function ( editor ) {
 
 
 				var specularMapEnabled = materialSpecularMapEnabled.getValue() === true;
 				var specularMapEnabled = materialSpecularMapEnabled.getValue() === true;
 
 
-				if ( objectHasUvs )  {
+				if ( objectHasUvs ) {
 
 
 					material.specularMap = specularMapEnabled ? materialSpecularMap.getValue() : null;
 					material.specularMap = specularMapEnabled ? materialSpecularMap.getValue() : null;
 					material.needsUpdate = true;
 					material.needsUpdate = true;
@@ -639,7 +635,6 @@ Sidebar.Material = function ( editor ) {
 		var properties = {
 		var properties = {
 			'name': materialNameRow,
 			'name': materialNameRow,
 			'color': materialColorRow,
 			'color': materialColorRow,
-			'ambient': materialAmbientRow,
 			'emissive': materialEmissiveRow,
 			'emissive': materialEmissiveRow,
 			'specular': materialSpecularRow,
 			'specular': materialSpecularRow,
 			'shininess': materialShininessRow,
 			'shininess': materialShininessRow,
@@ -703,12 +698,6 @@ Sidebar.Material = function ( editor ) {
 
 
 			}
 			}
 
 
-			if ( material.ambient !== undefined ) {
-
-				materialAmbient.setHexValue( material.ambient.getHexString() );
-
-			}
-
 			if ( material.emissive !== undefined ) {
 			if ( material.emissive !== undefined ) {
 
 
 				materialEmissive.setHexValue( material.emissive.getHexString() );
 				materialEmissive.setHexValue( material.emissive.getHexString() );

+ 73 - 6
editor/js/Sidebar.Object3D.js

@@ -17,12 +17,56 @@ Sidebar.Object3D = function ( editor ) {
 
 
 	var objectType = new UI.Text().setTextTransform( 'uppercase' );
 	var objectType = new UI.Text().setTextTransform( 'uppercase' );
 	container.addStatic( objectType );
 	container.addStatic( objectType );
+
+	// Actions
+
+	var objectActions = new UI.Select().setPosition('absolute').setRight( '8px' ).setFontSize( '11px' );
+	objectActions.setOptions( {
+
+		'Actions': 'Actions',
+		'Reset Position': 'Reset Position',
+		'Reset Rotation': 'Reset Rotation',
+		'Reset Scale': 'Reset Scale'
+
+	} );
+	objectActions.onClick( function ( event ) {
+
+		event.stopPropagation(); // Avoid panel collapsing
+
+	} );
+	objectActions.onChange( function ( event ) {
+
+		var object = editor.selected;
+
+		switch ( this.getValue() ) {
+
+			case 'Reset Position':
+				object.position.set( 0, 0, 0 );
+				break;
+
+			case 'Reset Rotation':
+				object.rotation.set( 0, 0, 0 );
+				break;
+
+			case 'Reset Scale':
+				object.scale.set( 1, 1, 1 );
+				break;
+
+		}
+
+		this.setValue( 'Actions' );
+
+		signals.objectChanged.dispatch( object );
+
+	} );
+	container.addStatic( objectActions );
+
 	container.add( new UI.Break() );
 	container.add( new UI.Break() );
 
 
 	// uuid
 	// uuid
 
 
 	var objectUUIDRow = new UI.Panel();
 	var objectUUIDRow = new UI.Panel();
-	var objectUUID = new UI.Input().setWidth( '115px' ).setColor( '#444' ).setFontSize( '12px' ).setDisabled( true );
+	var objectUUID = new UI.Input().setWidth( '115px' ).setFontSize( '12px' ).setDisabled( true );
 	var objectUUIDRenew = new UI.Button( '⟳' ).setMarginLeft( '7px' ).onClick( function () {
 	var objectUUIDRenew = new UI.Button( '⟳' ).setMarginLeft( '7px' ).onClick( function () {
 
 
 		objectUUID.setValue( THREE.Math.generateUUID() );
 		objectUUID.setValue( THREE.Math.generateUUID() );
@@ -42,7 +86,7 @@ Sidebar.Object3D = function ( editor ) {
 	var objectNameRow = new UI.Panel();
 	var objectNameRow = new UI.Panel();
 	var objectName = new UI.Input().setWidth( '150px' ).setFontSize( '12px' ).onChange( function () {
 	var objectName = new UI.Input().setWidth( '150px' ).setFontSize( '12px' ).onChange( function () {
 
 
-			editor.setObjectName( editor.selected, objectName.getValue() );
+		editor.nameObject( editor.selected, objectName.getValue() );
 
 
 	} );
 	} );
 
 
@@ -189,6 +233,16 @@ Sidebar.Object3D = function ( editor ) {
 
 
 	container.add( objectExponentRow );
 	container.add( objectExponentRow );
 
 
+	// decay
+
+	var objectDecayRow = new UI.Panel();
+	var objectDecay = new UI.Number().setRange( 0, Infinity ).onChange( update );
+
+	objectDecayRow.add( new UI.Text( 'Decay' ).setWidth( '90px' ) );
+	objectDecayRow.add( objectDecay );
+
+	container.add( objectDecayRow );
+
 	// visible
 	// visible
 
 
 	var objectVisibleRow = new UI.Panel();
 	var objectVisibleRow = new UI.Panel();
@@ -204,7 +258,7 @@ Sidebar.Object3D = function ( editor ) {
 	var timeout;
 	var timeout;
 
 
 	var objectUserDataRow = new UI.Panel();
 	var objectUserDataRow = new UI.Panel();
-	var objectUserData = new UI.TextArea().setWidth( '150px' ).setHeight( '40px' ).setColor( '#444' ).setFontSize( '12px' ).onChange( update );
+	var objectUserData = new UI.TextArea().setWidth( '150px' ).setHeight( '40px' ).setFontSize( '12px' ).onChange( update );
 	objectUserData.onKeyUp( function () {
 	objectUserData.onKeyUp( function () {
 
 
 		try {
 		try {
@@ -294,7 +348,7 @@ Sidebar.Object3D = function ( editor ) {
 
 
 				if ( object.parent.id !== newParentId && object.id !== newParentId ) {
 				if ( object.parent.id !== newParentId && object.id !== newParentId ) {
 
 
-					editor.parent( object, editor.scene.getObjectById( newParentId, true ) );
+					editor.moveObject( object, editor.scene.getObjectById( newParentId ) );
 
 
 				}
 				}
 
 
@@ -367,6 +421,12 @@ Sidebar.Object3D = function ( editor ) {
 
 
 			}
 			}
 
 
+			if ( object.decay !== undefined ) {
+
+				object.decay = objectDecay.getValue();
+
+			}
+
 			object.visible = objectVisible.getValue();
 			object.visible = objectVisible.getValue();
 
 
 			try {
 			try {
@@ -397,7 +457,8 @@ Sidebar.Object3D = function ( editor ) {
 			'groundColor': objectGroundColorRow,
 			'groundColor': objectGroundColorRow,
 			'distance' : objectDistanceRow,
 			'distance' : objectDistanceRow,
 			'angle' : objectAngleRow,
 			'angle' : objectAngleRow,
-			'exponent' : objectExponentRow
+			'exponent' : objectExponentRow,
+			'decay' : objectDecayRow
 		};
 		};
 
 
 		for ( var property in properties ) {
 		for ( var property in properties ) {
@@ -546,6 +607,12 @@ Sidebar.Object3D = function ( editor ) {
 
 
 		}
 		}
 
 
+		if ( object.decay !== undefined ) {
+
+			objectDecay.setValue( object.decay );
+
+		}
+
 		objectVisible.setValue( object.visible );
 		objectVisible.setValue( object.visible );
 
 
 		try {
 		try {
@@ -558,7 +625,7 @@ Sidebar.Object3D = function ( editor ) {
 
 
 		}
 		}
 
 
-		objectUserData.setBorderColor( '#ccc' );
+		objectUserData.setBorderColor( 'transparent' );
 		objectUserData.setBackgroundColor( '' );
 		objectUserData.setBackgroundColor( '' );
 
 
 		updateTransformRows( object );
 		updateTransformRows( object );

+ 27 - 12
editor/js/Sidebar.Renderer.js → editor/js/Sidebar.Project.js

@@ -2,7 +2,7 @@
  * @author mrdoob / http://mrdoob.com/
  * @author mrdoob / http://mrdoob.com/
  */
  */
 
 
-Sidebar.Renderer = function ( editor ) {
+Sidebar.Project = function ( editor ) {
 
 
 	var signals = editor.signals;
 	var signals = editor.signals;
 
 
@@ -17,14 +17,14 @@ Sidebar.Renderer = function ( editor ) {
 	};
 	};
 
 
 	var container = new UI.CollapsiblePanel();
 	var container = new UI.CollapsiblePanel();
-	container.setCollapsed( editor.config.getKey( 'ui/sidebar/renderer/collapsed' ) );
+	container.setCollapsed( editor.config.getKey( 'ui/sidebar/project/collapsed' ) );
 	container.onCollapsedChange( function ( boolean ) {
 	container.onCollapsedChange( function ( boolean ) {
 
 
-		editor.config.setKey( 'ui/sidebar/renderer/collapsed', boolean );
+		editor.config.setKey( 'ui/sidebar/project/collapsed', boolean );
 
 
 	} );
 	} );
 
 
-	container.addStatic( new UI.Text( 'RENDERER' ) );
+	container.addStatic( new UI.Text( 'PROJECT' ) );
 	container.add( new UI.Break() );
 	container.add( new UI.Break() );
 
 
 	// class
 	// class
@@ -40,30 +40,30 @@ Sidebar.Renderer = function ( editor ) {
 	}
 	}
 
 
 	var rendererTypeRow = new UI.Panel();
 	var rendererTypeRow = new UI.Panel();
-	var rendererType = new UI.Select().setOptions( options ).setWidth( '150px' ).setColor( '#444' ).onChange( function () {
+	var rendererType = new UI.Select().setOptions( options ).setWidth( '150px' ).onChange( function () {
 
 
-		editor.config.setKey( 'renderer', this.getValue() );
+		editor.config.setKey( 'project/renderer', this.getValue() );
 		updateRenderer();
 		updateRenderer();
 
 
 	} );
 	} );
 
 
-	rendererTypeRow.add( new UI.Text( 'Type' ).setWidth( '90px' ) );
+	rendererTypeRow.add( new UI.Text( 'Renderer' ).setWidth( '90px' ) );
 	rendererTypeRow.add( rendererType );
 	rendererTypeRow.add( rendererType );
 
 
 	container.add( rendererTypeRow );
 	container.add( rendererTypeRow );
 
 
-	if ( editor.config.getKey( 'renderer' ) !== undefined ) {
+	if ( editor.config.getKey( 'project/renderer' ) !== undefined ) {
 
 
-		rendererType.setValue( editor.config.getKey( 'renderer' ) );
+		rendererType.setValue( editor.config.getKey( 'project/renderer' ) );
 
 
 	}
 	}
-	
+
 	// antialiasing
 	// antialiasing
 
 
 	var rendererAntialiasRow = new UI.Panel();
 	var rendererAntialiasRow = new UI.Panel();
-	var rendererAntialias = new UI.Checkbox( editor.config.getKey( 'renderer/antialias' ) ).setLeft( '100px' ).onChange( function () {
+	var rendererAntialias = new UI.Checkbox( editor.config.getKey( 'project/renderer/antialias' ) ).setLeft( '100px' ).onChange( function () {
 
 
-		editor.config.setKey( 'renderer/antialias', this.getValue() );
+		editor.config.setKey( 'project/renderer/antialias', this.getValue() );
 		// updateRenderer();
 		// updateRenderer();
 
 
 	} );
 	} );
@@ -73,6 +73,21 @@ Sidebar.Renderer = function ( editor ) {
 
 
 	container.add( rendererAntialiasRow );
 	container.add( rendererAntialiasRow );
 
 
+	// VR
+
+	var vrRow = new UI.Panel();
+	var vr = new UI.Checkbox( editor.config.getKey( 'project/vr' ) ).setLeft( '100px' ).onChange( function () {
+
+		editor.config.setKey( 'project/vr', this.getValue() );
+		// updateRenderer();
+
+	} );
+
+	vrRow.add( new UI.Text( 'VR' ).setWidth( '90px' ) );
+	vrRow.add( vr );
+
+	container.add( vrRow );
+
 	//
 	//
 
 
 	function updateRenderer() {
 	function updateRenderer() {

+ 3 - 3
editor/js/Sidebar.Scene.js

@@ -19,7 +19,7 @@ Sidebar.Scene = function ( editor ) {
 
 
 	var ignoreObjectSelectedSignal = false;
 	var ignoreObjectSelectedSignal = false;
 
 
-	var outliner = new UI.FancySelect().setId( 'outliner' );
+	var outliner = new UI.Outliner( editor );
 	outliner.onChange( function () {
 	outliner.onChange( function () {
 
 
 		ignoreObjectSelectedSignal = true;
 		ignoreObjectSelectedSignal = true;
@@ -56,7 +56,7 @@ Sidebar.Scene = function ( editor ) {
 		'Fog': 'Linear',
 		'Fog': 'Linear',
 		'FogExp2': 'Exponential'
 		'FogExp2': 'Exponential'
 
 
-	} ).setWidth( '150px' ).setColor( '#444' ).setFontSize( '12px' )
+	} ).setWidth( '150px' );
 	fogType.onChange( function () {
 	fogType.onChange( function () {
 
 
 		var type = fogType.getValue();
 		var type = fogType.getValue();
@@ -134,7 +134,7 @@ Sidebar.Scene = function ( editor ) {
 		var options = [];
 		var options = [];
 
 
 		// options.push( { value: camera.id, html: '<span class="type ' + camera.type + '"></span> ' + camera.name } );
 		// options.push( { value: camera.id, html: '<span class="type ' + camera.type + '"></span> ' + camera.name } );
-		options.push( { value: scene.id, html: '<span class="type ' + scene.type + '"></span> ' + scene.name } );
+		options.push( { static: true, value: scene.id, html: '<span class="type ' + scene.type + '"></span> ' + scene.name } );
 
 
 		( function addObjects( objects, pad ) {
 		( function addObjects( objects, pad ) {
 
 

+ 1 - 1
editor/js/Sidebar.Script.js

@@ -84,7 +84,7 @@ Sidebar.Script = function ( editor ) {
 
 
 					} );
 					} );
 					scriptsContainer.add( remove );
 					scriptsContainer.add( remove );
-					
+
 					scriptsContainer.add( new UI.Break() );
 					scriptsContainer.add( new UI.Break() );
 
 
 				} )( object, scripts[ i ] )
 				} )( object, scripts[ i ] )

+ 1 - 1
editor/js/Sidebar.js

@@ -7,7 +7,7 @@ var Sidebar = function ( editor ) {
 	var container = new UI.Panel();
 	var container = new UI.Panel();
 	container.setId( 'sidebar' );
 	container.setId( 'sidebar' );
 
 
-	container.add( new Sidebar.Renderer( editor ) );
+	container.add( new Sidebar.Project( editor ) );
 	container.add( new Sidebar.Scene( editor ) );
 	container.add( new Sidebar.Scene( editor ) );
 	container.add( new Sidebar.Object3D( editor ) );
 	container.add( new Sidebar.Object3D( editor ) );
 	container.add( new Sidebar.Geometry( editor ) );
 	container.add( new Sidebar.Geometry( editor ) );

+ 1 - 1
editor/js/Storage.js

@@ -8,7 +8,7 @@ var Storage = function () {
 
 
 	if ( indexedDB === undefined  ) {
 	if ( indexedDB === undefined  ) {
 		console.warn( 'Storage: IndexedDB not available.' );
 		console.warn( 'Storage: IndexedDB not available.' );
-		return { init: function (){}, get: function (){}, set: function (){}, clear: function (){} };
+		return { init: function () {}, get: function () {}, set: function () {}, clear: function () {} };
 	}
 	}
 
 
 	var name = 'threejs-editor';
 	var name = 'threejs-editor';

+ 0 - 2
editor/js/Toolbar.js

@@ -62,8 +62,6 @@ var Toolbar = function ( editor ) {
 
 
 	}
 	}
 
 
-	update();
-
 	return container;
 	return container;
 
 
 }
 }

+ 1 - 7
editor/js/Viewport.js

@@ -370,12 +370,6 @@ var Viewport = function ( editor ) {
 
 
 		transformControls.update();
 		transformControls.update();
 
 
-		if ( object.geometry !== undefined ) {
-
-			selectionBox.update( object );
-
-		}
-
 		if ( object instanceof THREE.PerspectiveCamera ) {
 		if ( object instanceof THREE.PerspectiveCamera ) {
 
 
 			object.updateProjectionMatrix();
 			object.updateProjectionMatrix();
@@ -535,7 +529,7 @@ var Viewport = function ( editor ) {
 	};
 	};
 
 
 	var clearColor;
 	var clearColor;
-	var renderer = createRenderer( editor.config.getKey( 'renderer' ), editor.config.getKey( 'renderer/antialias' ) );
+	var renderer = createRenderer( editor.config.getKey( 'project/renderer' ), editor.config.getKey( 'project/renderer/antialias' ) );
 	container.dom.appendChild( renderer.domElement );
 	container.dom.appendChild( renderer.domElement );
 
 
 	animate();
 	animate();

+ 104 - 21
editor/js/libs/app.js

@@ -6,10 +6,14 @@ var APP = {
 
 
 	Player: function () {
 	Player: function () {
 
 
+		var scope = this;
+
 		var loader = new THREE.ObjectLoader();
 		var loader = new THREE.ObjectLoader();
 		var camera, scene, renderer;
 		var camera, scene, renderer;
 
 
-		var scripts = {};
+		var vr, controls;
+
+		var events = {};
 
 
 		this.dom = undefined;
 		this.dom = undefined;
 
 
@@ -18,18 +22,25 @@ var APP = {
 
 
 		this.load = function ( json ) {
 		this.load = function ( json ) {
 
 
+			vr = json.project.vr;
+
 			renderer = new THREE.WebGLRenderer( { antialias: true } );
 			renderer = new THREE.WebGLRenderer( { antialias: true } );
+			renderer.setClearColor( 0x000000 );
 			renderer.setPixelRatio( window.devicePixelRatio );
 			renderer.setPixelRatio( window.devicePixelRatio );
+			this.dom = renderer.domElement;
 
 
-			camera = loader.parse( json.camera );
-			scene = loader.parse( json.scene );
+			this.setScene( loader.parse( json.scene ) );
+			this.setCamera( loader.parse( json.camera ) );
 
 
-			scripts = {
+			events = {
 				keydown: [],
 				keydown: [],
 				keyup: [],
 				keyup: [],
 				mousedown: [],
 				mousedown: [],
 				mouseup: [],
 				mouseup: [],
 				mousemove: [],
 				mousemove: [],
+				touchstart: [],
+				touchend: [],
+				touchmove: [],
 				update: []
 				update: []
 			};
 			};
 
 
@@ -37,26 +48,26 @@ var APP = {
 
 
 				var object = scene.getObjectByProperty( 'uuid', uuid, true );
 				var object = scene.getObjectByProperty( 'uuid', uuid, true );
 
 
-				var sources = json.scripts[ uuid ];
+				var scripts = json.scripts[ uuid ];
 
 
-				for ( var i = 0; i < sources.length; i ++ ) {
+				for ( var i = 0; i < scripts.length; i ++ ) {
 
 
-					var script = sources[ i ];
+					var script = scripts[ i ];
 
 
-					var events = ( new Function( 'player', 'scene', 'keydown', 'keyup', 'mousedown', 'mouseup', 'mousemove', 'update', script.source + '\nreturn { keydown: keydown, keyup: keyup, mousedown: mousedown, mouseup: mouseup, mousemove: mousemove, update: update };' ).bind( object ) )( this, scene );
+					var functions = ( new Function( 'player, scene, keydown, keyup, mousedown, mouseup, mousemove, touchstart, touchend, touchmove, update', script.source + '\nreturn { keydown: keydown, keyup: keyup, mousedown: mousedown, mouseup: mouseup, mousemove: mousemove, touchstart: touchstart, touchend: touchend, touchmove: touchmove, update: update };' ).bind( object ) )( this, scene );
 
 
-					for ( var name in events ) {
+					for ( var name in functions ) {
 
 
-						if ( events[ name ] === undefined ) continue;
+						if ( functions[ name ] === undefined ) continue;
 
 
-						if ( scripts[ name ] === undefined ) {
+						if ( events[ name ] === undefined ) {
 
 
 							console.warn( 'APP.Player: event type not supported (', name, ')' );
 							console.warn( 'APP.Player: event type not supported (', name, ')' );
 							continue;
 							continue;
 
 
 						}
 						}
 
 
-						scripts[ name ].push( events[ name ].bind( object ) );
+						events[ name ].push( functions[ name ].bind( object ) );
 
 
 					}
 					}
 
 
@@ -64,8 +75,6 @@ var APP = {
 
 
 			}
 			}
 
 
-			this.dom = renderer.domElement;
-
 		};
 		};
 
 
 		this.setCamera = function ( value ) {
 		this.setCamera = function ( value ) {
@@ -74,10 +83,55 @@ var APP = {
 			camera.aspect = this.width / this.height;
 			camera.aspect = this.width / this.height;
 			camera.updateProjectionMatrix();
 			camera.updateProjectionMatrix();
 
 
+
+			if ( vr === true ) {
+
+				if ( camera.parent === undefined ) {
+
+					// camera needs to be in the scene so camera2 matrix updates
+					
+					scene.add( camera );
+
+				}
+
+				var camera2 = camera.clone();
+				camera.add( camera2 );
+
+				camera = camera2;
+
+				controls = new THREE.VRControls( camera );
+				renderer = new THREE.VREffect( renderer );
+
+				document.addEventListener( 'keyup', function ( event ) {
+
+					switch ( event.keyCode ) {
+						case 90:
+							controls.zeroSensor();
+							break;
+					}
+
+				} );
+
+				this.dom.addEventListener( 'dblclick', function () {
+
+					renderer.setFullScreen( true );
+
+				} );
+
+			}
+
 		};
 		};
 
 
+		this.setScene = function ( value ) {
+
+			scene = value;
+
+		},
+
 		this.setSize = function ( width, height ) {
 		this.setSize = function ( width, height ) {
 
 
+			if ( renderer._fullScreen ) return;
+
 			this.width = width;
 			this.width = width;
 			this.height = height;
 			this.height = height;
 
 
@@ -98,16 +152,20 @@ var APP = {
 
 
 		};
 		};
 
 
-		var request;
+		var prevTime, request;
 
 
 		var animate = function ( time ) {
 		var animate = function ( time ) {
 
 
 			request = requestAnimationFrame( animate );
 			request = requestAnimationFrame( animate );
 
 
-			dispatch( scripts.update, { time: time } );
+			dispatch( events.update, { time: time, delta: time - prevTime } );
+
+			if ( vr ) controls.update();
 
 
 			renderer.render( scene, camera );
 			renderer.render( scene, camera );
 
 
+			prevTime = time;
+
 		};
 		};
 
 
 		this.play = function () {
 		this.play = function () {
@@ -117,8 +175,12 @@ var APP = {
 			document.addEventListener( 'mousedown', onDocumentMouseDown );
 			document.addEventListener( 'mousedown', onDocumentMouseDown );
 			document.addEventListener( 'mouseup', onDocumentMouseUp );
 			document.addEventListener( 'mouseup', onDocumentMouseUp );
 			document.addEventListener( 'mousemove', onDocumentMouseMove );
 			document.addEventListener( 'mousemove', onDocumentMouseMove );
+			document.addEventListener( 'touchstart', onDocumentTouchStart );
+			document.addEventListener( 'touchend', onDocumentTouchEnd );
+			document.addEventListener( 'touchmove', onDocumentTouchMove );
 
 
 			request = requestAnimationFrame( animate );
 			request = requestAnimationFrame( animate );
+			prevTime = performance.now();
 
 
 		};
 		};
 
 
@@ -129,6 +191,9 @@ var APP = {
 			document.removeEventListener( 'mousedown', onDocumentMouseDown );
 			document.removeEventListener( 'mousedown', onDocumentMouseDown );
 			document.removeEventListener( 'mouseup', onDocumentMouseUp );
 			document.removeEventListener( 'mouseup', onDocumentMouseUp );
 			document.removeEventListener( 'mousemove', onDocumentMouseMove );
 			document.removeEventListener( 'mousemove', onDocumentMouseMove );
+			document.removeEventListener( 'touchstart', onDocumentTouchStart );
+			document.removeEventListener( 'touchend', onDocumentTouchEnd );
+			document.removeEventListener( 'touchmove', onDocumentTouchMove );
 
 
 			cancelAnimationFrame( request );
 			cancelAnimationFrame( request );
 
 
@@ -138,31 +203,49 @@ var APP = {
 
 
 		var onDocumentKeyDown = function ( event ) {
 		var onDocumentKeyDown = function ( event ) {
 
 
-			dispatch( scripts.keydown, event );
+			dispatch( events.keydown, event );
 
 
 		};
 		};
 
 
 		var onDocumentKeyUp = function ( event ) {
 		var onDocumentKeyUp = function ( event ) {
 
 
-			dispatch( scripts.keyup, event );
+			dispatch( events.keyup, event );
 
 
 		};
 		};
 
 
 		var onDocumentMouseDown = function ( event ) {
 		var onDocumentMouseDown = function ( event ) {
 
 
-			dispatch( scripts.mousedown, event );
+			dispatch( events.mousedown, event );
 
 
 		};
 		};
 
 
 		var onDocumentMouseUp = function ( event ) {
 		var onDocumentMouseUp = function ( event ) {
 
 
-			dispatch( scripts.mouseup, event );
+			dispatch( events.mouseup, event );
 
 
 		};
 		};
 
 
 		var onDocumentMouseMove = function ( event ) {
 		var onDocumentMouseMove = function ( event ) {
 
 
-			dispatch( scripts.mousemove, event );
+			dispatch( events.mousemove, event );
+
+		};
+
+		var onDocumentTouchStart = function ( event ) {
+
+			dispatch( events.touchstart, event );
+
+		};
+
+		var onDocumentTouchEnd = function ( event ) {
+
+			dispatch( events.touchend, event );
+
+		};
+
+		var onDocumentTouchMove = function ( event ) {
+
+			dispatch( events.touchmove, event );
 
 
 		};
 		};
 
 

File diff suppressed because it is too large
+ 197 - 0
editor/js/libs/esprima.js


File diff suppressed because it is too large
+ 1 - 0
editor/js/libs/sortable.min.js


+ 17 - 174
editor/js/libs/ui.js

@@ -15,7 +15,7 @@ UI.Element.prototype = {
 	setId: function ( id ) {
 	setId: function ( id ) {
 
 
 		this.dom.id = id;
 		this.dom.id = id;
-		
+
 		return this;
 		return this;
 
 
 	},
 	},
@@ -137,7 +137,7 @@ UI.Panel.prototype.add = function () {
 UI.Panel.prototype.remove = function () {
 UI.Panel.prototype.remove = function () {
 
 
 	for ( var i = 0; i < arguments.length; i ++ ) {
 	for ( var i = 0; i < arguments.length; i ++ ) {
-	
+
 		var argument = arguments[ i ];
 		var argument = arguments[ i ];
 
 
 		if ( argument instanceof UI.Element ) {
 		if ( argument instanceof UI.Element ) {
@@ -341,7 +341,7 @@ UI.Input = function ( text ) {
 	var dom = document.createElement( 'input' );
 	var dom = document.createElement( 'input' );
 	dom.className = 'Input';
 	dom.className = 'Input';
 	dom.style.padding = '2px';
 	dom.style.padding = '2px';
-	dom.style.border = '1px solid #ccc';
+	dom.style.border = '1px solid transparent';
 
 
 	dom.addEventListener( 'keydown', function ( event ) {
 	dom.addEventListener( 'keydown', function ( event ) {
 
 
@@ -385,7 +385,6 @@ UI.TextArea = function () {
 	var dom = document.createElement( 'textarea' );
 	var dom = document.createElement( 'textarea' );
 	dom.className = 'TextArea';
 	dom.className = 'TextArea';
 	dom.style.padding = '2px';
 	dom.style.padding = '2px';
-	dom.style.border = '1px solid #ccc';
 	dom.spellcheck = false;
 	dom.spellcheck = false;
 
 
 	dom.addEventListener( 'keydown', function ( event ) {
 	dom.addEventListener( 'keydown', function ( event ) {
@@ -440,10 +439,7 @@ UI.Select = function () {
 
 
 	var dom = document.createElement( 'select' );
 	var dom = document.createElement( 'select' );
 	dom.className = 'Select';
 	dom.className = 'Select';
-	dom.style.width = '64px';
-	dom.style.height = '16px';
-	dom.style.border = '0px';
-	dom.style.padding = '0px';
+	dom.style.padding = '2px';
 
 
 	this.dom = dom;
 	this.dom = dom;
 
 
@@ -507,159 +503,6 @@ UI.Select.prototype.setValue = function ( value ) {
 
 
 };
 };
 
 
-// FancySelect
-
-UI.FancySelect = function () {
-
-	UI.Element.call( this );
-
-	var scope = this;
-
-	var dom = document.createElement( 'div' );
-	dom.className = 'FancySelect';
-	dom.tabIndex = 0;	// keyup event is ignored without setting tabIndex
-
-	// Broadcast for object selection after arrow navigation
-	var changeEvent = document.createEvent('HTMLEvents');
-	changeEvent.initEvent( 'change', true, true );
-
-	// Prevent native scroll behavior
-	dom.addEventListener( 'keydown', function (event) {
-
-		switch ( event.keyCode ) {
-			case 38: // up
-			case 40: // down
-				event.preventDefault();
-				event.stopPropagation();
-				break;
-		}
-
-	}, false);
-
-	// Keybindings to support arrow navigation
-	dom.addEventListener( 'keyup', function (event) {
-
-		switch ( event.keyCode ) {
-			case 38: // up
-			case 40: // down
-				scope.selectedIndex += ( event.keyCode == 38 ) ? -1 : 1;
-
-				if ( scope.selectedIndex >= 0 && scope.selectedIndex < scope.options.length ) {
-
-					// Highlight selected dom elem and scroll parent if needed
-					scope.setValue( scope.options[ scope.selectedIndex ].value );
-
-					scope.dom.dispatchEvent( changeEvent );
-
-				}
-
-				break;
-		}
-
-	}, false);
-
-	this.dom = dom;
-
-	this.options = [];
-	this.selectedIndex = -1;
-	this.selectedValue = null;
-
-	return this;
-
-};
-
-UI.FancySelect.prototype = Object.create( UI.Element.prototype );
-UI.FancySelect.prototype.constructor = UI.FancySelect;
-
-UI.FancySelect.prototype.setOptions = function ( options ) {
-
-	var scope = this;
-
-	var changeEvent = document.createEvent( 'HTMLEvents' );
-	changeEvent.initEvent( 'change', true, true );
-
-	while ( scope.dom.children.length > 0 ) {
-
-		scope.dom.removeChild( scope.dom.firstChild );
-
-	}
-
-	scope.options = [];
-
-	for ( var i = 0; i < options.length; i ++ ) {
-
-		var option = options[ i ];
-
-		var div = document.createElement( 'div' );
-		div.className = 'option';
-		div.innerHTML = option.html;
-		div.value = option.value;
-		scope.dom.appendChild( div );
-
-		scope.options.push( div );
-
-		div.addEventListener( 'click', function ( event ) {
-
-			scope.setValue( this.value );
-			scope.dom.dispatchEvent( changeEvent );
-
-		}, false );
-
-	}
-
-	return scope;
-
-};
-
-UI.FancySelect.prototype.getValue = function () {
-
-	return this.selectedValue;
-
-};
-
-UI.FancySelect.prototype.setValue = function ( value ) {
-
-	for ( var i = 0; i < this.options.length; i ++ ) {
-
-		var element = this.options[ i ];
-
-		if ( element.value === value ) {
-
-			element.classList.add( 'active' );
-
-			// scroll into view
-
-			var y = element.offsetTop - this.dom.offsetTop;
-			var bottomY = y + element.offsetHeight;
-			var minScroll = bottomY - this.dom.offsetHeight;
-
-			if ( this.dom.scrollTop > y ) {
-
-				this.dom.scrollTop = y
-
-			} else if ( this.dom.scrollTop < minScroll ) {
-
-				this.dom.scrollTop = minScroll;
-
-			}
-
-			this.selectedIndex = i;
-
-		} else {
-
-			element.classList.remove( 'active' );
-
-		}
-
-	}
-
-	this.selectedValue = value;
-
-	return this;
-
-};
-
-
 // Checkbox
 // Checkbox
 
 
 UI.Checkbox = function ( boolean ) {
 UI.Checkbox = function ( boolean ) {
@@ -797,8 +640,8 @@ UI.Number = function ( number ) {
 	var distance = 0;
 	var distance = 0;
 	var onMouseDownValue = 0;
 	var onMouseDownValue = 0;
 
 
-	var pointer = new THREE.Vector2();
-	var prevPointer = new THREE.Vector2();
+	var pointer = [ 0, 0 ];
+	var prevPointer = [ 0, 0 ];
 
 
 	var onMouseDown = function ( event ) {
 	var onMouseDown = function ( event ) {
 
 
@@ -808,7 +651,7 @@ UI.Number = function ( number ) {
 
 
 		onMouseDownValue = parseFloat( dom.value );
 		onMouseDownValue = parseFloat( dom.value );
 
 
-		prevPointer.set( event.clientX, event.clientY );
+		prevPointer = [ event.clientX, event.clientY ];
 
 
 		document.addEventListener( 'mousemove', onMouseMove, false );
 		document.addEventListener( 'mousemove', onMouseMove, false );
 		document.addEventListener( 'mouseup', onMouseUp, false );
 		document.addEventListener( 'mouseup', onMouseUp, false );
@@ -819,9 +662,9 @@ UI.Number = function ( number ) {
 
 
 		var currentValue = dom.value;
 		var currentValue = dom.value;
 
 
-		pointer.set( event.clientX, event.clientY );
+		pointer = [ event.clientX, event.clientY ];
 
 
-		distance += ( pointer.x - prevPointer.x ) - ( pointer.y - prevPointer.y );
+		distance += ( pointer[ 0 ] - prevPointer[ 0 ] ) - ( pointer[ 1 ] - prevPointer[ 1 ] );
 
 
 		var number = onMouseDownValue + ( distance / ( event.shiftKey ? 5 : 50 ) ) * scope.step;
 		var number = onMouseDownValue + ( distance / ( event.shiftKey ? 5 : 50 ) ) * scope.step;
 
 
@@ -829,7 +672,7 @@ UI.Number = function ( number ) {
 
 
 		if ( currentValue !== dom.value ) dom.dispatchEvent( changeEvent );
 		if ( currentValue !== dom.value ) dom.dispatchEvent( changeEvent );
 
 
-		prevPointer.set( event.clientX, event.clientY );
+		prevPointer = [ event.clientX, event.clientY ];
 
 
 	};
 	};
 
 
@@ -961,8 +804,8 @@ UI.Integer = function ( number ) {
 	var distance = 0;
 	var distance = 0;
 	var onMouseDownValue = 0;
 	var onMouseDownValue = 0;
 
 
-	var pointer = new THREE.Vector2();
-	var prevPointer = new THREE.Vector2();
+	var pointer = [ 0, 0 ];
+	var prevPointer = [ 0, 0 ];
 
 
 	var onMouseDown = function ( event ) {
 	var onMouseDown = function ( event ) {
 
 
@@ -972,7 +815,7 @@ UI.Integer = function ( number ) {
 
 
 		onMouseDownValue = parseFloat( dom.value );
 		onMouseDownValue = parseFloat( dom.value );
 
 
-		prevPointer.set( event.clientX, event.clientY );
+		prevPointer = [ event.clientX, event.clientY ];
 
 
 		document.addEventListener( 'mousemove', onMouseMove, false );
 		document.addEventListener( 'mousemove', onMouseMove, false );
 		document.addEventListener( 'mouseup', onMouseUp, false );
 		document.addEventListener( 'mouseup', onMouseUp, false );
@@ -983,9 +826,9 @@ UI.Integer = function ( number ) {
 
 
 		var currentValue = dom.value;
 		var currentValue = dom.value;
 
 
-		pointer.set( event.clientX, event.clientY );
+		pointer = [ event.clientX, event.clientY ];
 
 
-		distance += ( pointer.x - prevPointer.x ) - ( pointer.y - prevPointer.y );
+		distance += ( pointer[ 0 ] - prevPointer[ 0 ] ) - ( pointer[ 1 ] - prevPointer[ 1 ] );
 
 
 		var number = onMouseDownValue + ( distance / ( event.shiftKey ? 5 : 50 ) ) * scope.step;
 		var number = onMouseDownValue + ( distance / ( event.shiftKey ? 5 : 50 ) ) * scope.step;
 
 
@@ -993,7 +836,7 @@ UI.Integer = function ( number ) {
 
 
 		if ( currentValue !== dom.value ) dom.dispatchEvent( changeEvent );
 		if ( currentValue !== dom.value ) dom.dispatchEvent( changeEvent );
 
 
-		prevPointer.set( event.clientX, event.clientY );
+		prevPointer = [ event.clientX, event.clientY ];
 
 
 	};
 	};
 
 
@@ -1158,7 +1001,7 @@ UI.Button.prototype.setLabel = function ( value ) {
 UI.Dialog = function ( value ) {
 UI.Dialog = function ( value ) {
 
 
 	var scope = this;
 	var scope = this;
-	
+
 	var dom = document.createElement( 'dialog' );
 	var dom = document.createElement( 'dialog' );
 
 
 	if ( dom.showModal === undefined ) {
 	if ( dom.showModal === undefined ) {

+ 176 - 0
editor/js/libs/ui.three.js

@@ -133,3 +133,179 @@ UI.Texture.prototype.onChange = function ( callback ) {
 	return this;
 	return this;
 
 
 };
 };
+
+// Outliner
+
+UI.Outliner = function ( editor ) {
+
+	UI.Element.call( this );
+
+	var scope = this;
+
+	var dom = document.createElement( 'div' );
+	dom.className = 'Outliner';
+	dom.tabIndex = 0;	// keyup event is ignored without setting tabIndex
+
+	var scene = editor.scene;
+
+	var sortable = Sortable.create( dom, {
+		draggable: '.draggable',
+		onUpdate: function ( event ) {
+
+			var item = event.item;
+
+			var object = scene.getObjectById( item.value );
+
+			if ( item.nextSibling === null ) {
+
+				editor.moveObject( object, editor.scene );
+
+			} else {
+
+				var nextObject = scene.getObjectById( item.nextSibling.value );
+				editor.moveObject( object, nextObject.parent, nextObject );
+
+			}
+
+		}
+	} );
+
+	// Broadcast for object selection after arrow navigation
+	var changeEvent = document.createEvent('HTMLEvents');
+	changeEvent.initEvent( 'change', true, true );
+
+	// Prevent native scroll behavior
+	dom.addEventListener( 'keydown', function (event) {
+
+		switch ( event.keyCode ) {
+			case 38: // up
+			case 40: // down
+			event.preventDefault();
+			event.stopPropagation();
+			break;
+		}
+
+	}, false);
+
+	// Keybindings to support arrow navigation
+	dom.addEventListener( 'keyup', function (event) {
+
+		switch ( event.keyCode ) {
+			case 38: // up
+			case 40: // down
+			scope.selectedIndex += ( event.keyCode == 38 ) ? -1 : 1;
+
+			if ( scope.selectedIndex >= 0 && scope.selectedIndex < scope.options.length ) {
+
+				// Highlight selected dom elem and scroll parent if needed
+				scope.setValue( scope.options[ scope.selectedIndex ].value );
+
+				scope.dom.dispatchEvent( changeEvent );
+
+			}
+
+			break;
+		}
+
+	}, false);
+
+	this.dom = dom;
+
+	this.options = [];
+	this.selectedIndex = -1;
+	this.selectedValue = null;
+
+	return this;
+
+};
+
+UI.Outliner.prototype = Object.create( UI.Element.prototype );
+UI.Outliner.prototype.constructor = UI.Outliner;
+
+UI.Outliner.prototype.setOptions = function ( options ) {
+
+	var scope = this;
+
+	var changeEvent = document.createEvent( 'HTMLEvents' );
+	changeEvent.initEvent( 'change', true, true );
+
+	while ( scope.dom.children.length > 0 ) {
+
+		scope.dom.removeChild( scope.dom.firstChild );
+
+	}
+
+	scope.options = [];
+
+	for ( var i = 0; i < options.length; i ++ ) {
+
+		var option = options[ i ];
+
+		var div = document.createElement( 'div' );
+		div.className = 'option ' + ( option.static === true ? '': 'draggable' );
+		div.innerHTML = option.html;
+		div.value = option.value;
+		scope.dom.appendChild( div );
+
+		scope.options.push( div );
+
+		div.addEventListener( 'click', function ( event ) {
+
+			scope.setValue( this.value );
+			scope.dom.dispatchEvent( changeEvent );
+
+		}, false );
+
+	}
+
+	return scope;
+
+};
+
+UI.Outliner.prototype.getValue = function () {
+
+	return this.selectedValue;
+
+};
+
+UI.Outliner.prototype.setValue = function ( value ) {
+
+	for ( var i = 0; i < this.options.length; i ++ ) {
+
+		var element = this.options[ i ];
+
+		if ( element.value === value ) {
+
+			element.classList.add( 'active' );
+
+			// scroll into view
+
+			var y = element.offsetTop - this.dom.offsetTop;
+			var bottomY = y + element.offsetHeight;
+			var minScroll = bottomY - this.dom.offsetHeight;
+
+			if ( this.dom.scrollTop > y ) {
+
+				this.dom.scrollTop = y
+
+			} else if ( this.dom.scrollTop < minScroll ) {
+
+				this.dom.scrollTop = minScroll;
+
+			}
+
+			this.selectedIndex = i;
+
+		} else {
+
+			element.classList.remove( 'active' );
+
+		}
+
+	}
+
+	this.selectedValue = value;
+
+	return this;
+
+};

+ 7 - 4
examples/index.html

@@ -196,7 +196,7 @@
 			</a>
 			</a>
 			<div id="content"></div>
 			<div id="content"></div>
 		</div>
 		</div>
-		<iframe id="viewer" allowfullscreen></iframe>
+		<iframe id="viewer" allowfullscreen onmousewheel=""></iframe>
 
 
 		<script>
 		<script>
 
 
@@ -222,10 +222,8 @@
 				"webgl_custom_attributes_particles3",
 				"webgl_custom_attributes_particles3",
 				"webgl_decals",
 				"webgl_decals",
 				"webgl_effects_anaglyph",
 				"webgl_effects_anaglyph",
-				"webgl_effects_oculusrift",
 				"webgl_effects_parallaxbarrier",
 				"webgl_effects_parallaxbarrier",
 				"webgl_effects_stereo",
 				"webgl_effects_stereo",
-				"webgl_effects_vr",
 				"webgl_geometries",
 				"webgl_geometries",
 				"webgl_geometries2",
 				"webgl_geometries2",
 				"webgl_geometry_colors",
 				"webgl_geometry_colors",
@@ -372,6 +370,8 @@
 				"webgl_shaders_vector",
 				"webgl_shaders_vector",
 				"webgl_shadowmap",
 				"webgl_shadowmap",
 				"webgl_shadowmap_performance",
 				"webgl_shadowmap_performance",
+				"webgl_shadowmap_viewer",
+				"webgl_shadowmesh",
 				"webgl_sprites",
 				"webgl_sprites",
 				"webgl_terrain_dynamic",
 				"webgl_terrain_dynamic",
 				"webgl_test_memory",
 				"webgl_test_memory",
@@ -384,6 +384,10 @@
 				"webgldeferred_arealights",
 				"webgldeferred_arealights",
 				"webgldeferred_pointlights"
 				"webgldeferred_pointlights"
 			],
 			],
+			"vr": [
+				"vr_cubes",
+				"vr_video"
+			],
 			"css3d": [
 			"css3d": [
 				"css3d_molecules",
 				"css3d_molecules",
 				"css3d_panorama",
 				"css3d_panorama",
@@ -399,7 +403,6 @@
 				"misc_animation_keys",
 				"misc_animation_keys",
 				"misc_controls_deviceorientation",
 				"misc_controls_deviceorientation",
 				"misc_controls_fly",
 				"misc_controls_fly",
-				"misc_controls_oculusrift",
 				"misc_controls_orbit",
 				"misc_controls_orbit",
 				"misc_controls_pointerlock",
 				"misc_controls_pointerlock",
 				"misc_controls_trackball",
 				"misc_controls_trackball",

+ 1 - 1
examples/js/AudioObject.js

@@ -40,7 +40,7 @@ THREE.AudioObject = function ( url, volume, playbackRate, loop ) {
 
 
 			THREE.AudioObject.prototype.context = new webkitAudioContext();
 			THREE.AudioObject.prototype.context = new webkitAudioContext();
 
 
-		} catch( error ) {
+		} catch ( error ) {
 
 
 			console.warn( "THREE.AudioObject: webkitAudioContext not found" );
 			console.warn( "THREE.AudioObject: webkitAudioContext not found" );
 			return this;
 			return this;

+ 9 - 9
examples/js/BlendCharacter.js

@@ -22,7 +22,7 @@ THREE.BlendCharacter = function () {
 
 
 			// Create the animations
 			// Create the animations
 
 
-			for ( var i = 0; i < geometry.animations.length; ++i ) {
+			for ( var i = 0; i < geometry.animations.length; ++ i ) {
 
 
 				var animName = geometry.animations[ i ].name;
 				var animName = geometry.animations[ i ].name;
 				scope.animations[ animName ] = new THREE.Animation( scope, geometry.animations[ i ] );
 				scope.animations[ animName ] = new THREE.Animation( scope, geometry.animations[ i ] );
@@ -46,7 +46,7 @@ THREE.BlendCharacter = function () {
 
 
 	this.update = function( dt ) {
 	this.update = function( dt ) {
 
 
-		for ( var i = this.weightSchedule.length - 1; i >= 0; --i ) {
+		for ( var i = this.weightSchedule.length - 1; i >= 0; -- i ) {
 
 
 			var data = this.weightSchedule[ i ];
 			var data = this.weightSchedule[ i ];
 			data.timeElapsed += dt;
 			data.timeElapsed += dt;
@@ -87,7 +87,7 @@ THREE.BlendCharacter = function () {
 		// lengths match. This is useful for smoothing out transitions that get out of
 		// lengths match. This is useful for smoothing out transitions that get out of
 		// phase such as between a walk and run cycle
 		// phase such as between a walk and run cycle
 
 
-		for ( var i = this.warpSchedule.length - 1; i >= 0; --i ) {
+		for ( var i = this.warpSchedule.length - 1; i >= 0; -- i ) {
 
 
 			var data = this.warpSchedule[ i ];
 			var data = this.warpSchedule[ i ];
 			data.timeElapsed += dt;
 			data.timeElapsed += dt;
@@ -203,17 +203,17 @@ THREE.BlendCharacter = function () {
 
 
 	this.unPauseAll = function() {
 	this.unPauseAll = function() {
 
 
-	for ( var a in this.animations ) {
+		for ( var a in this.animations ) {
 
 
-	  if ( this.animations[ a ].isPlaying && this.animations[ a ].isPaused ) {
+			if ( this.animations[ a ].isPlaying && this.animations[ a ].isPaused ) {
 
 
-		this.animations[ a ].pause();
+				this.animations[ a ].pause();
 
 
-	  }
+			}
 
 
-	}
+		}
 
 
-  };
+	};
 
 
 
 
 	this.stopAll = function() {
 	this.stopAll = function() {

+ 3 - 3
examples/js/Car.js

@@ -195,7 +195,7 @@ THREE.Car = function () {
 
 
 		var forwardDelta = this.speed * delta;
 		var forwardDelta = this.speed * delta;
 
 
-		this.carOrientation += ( forwardDelta * this.STEERING_RADIUS_RATIO )* this.wheelOrientation;
+		this.carOrientation += ( forwardDelta * this.STEERING_RADIUS_RATIO ) * this.wheelOrientation;
 
 
 		// displacement
 		// displacement
 
 
@@ -363,8 +363,8 @@ THREE.Car = function () {
 	};
 	};
 
 
 	function quadraticEaseOut( k ) { return - k * ( k - 2 ); }
 	function quadraticEaseOut( k ) { return - k * ( k - 2 ); }
-	function cubicEaseOut( k ) { return --k * k * k + 1; }
-	function circularEaseOut( k ) { return Math.sqrt( 1 - --k * k ); }
+	function cubicEaseOut( k ) { return -- k * k * k + 1; }
+	function circularEaseOut( k ) { return Math.sqrt( 1 - -- k * k ); }
 	function sinusoidalEaseOut( k ) { return Math.sin( k * Math.PI / 2 ); }
 	function sinusoidalEaseOut( k ) { return Math.sin( k * Math.PI / 2 ); }
 	function exponentialEaseOut( k ) { return k === 1 ? 1 : - Math.pow( 2, - 10 * k ) + 1; }
 	function exponentialEaseOut( k ) { return k === 1 ? 1 : - Math.pow( 2, - 10 * k ) + 1; }
 
 

+ 26 - 26
examples/js/Cloth.js

@@ -48,8 +48,8 @@ var lastTime;
 function plane(width, height) {
 function plane(width, height) {
 
 
 	return function(u, v) {
 	return function(u, v) {
-		var x = (u-0.5) * width;
-		var y = (v+0.5) * height;
+		var x = (u - 0.5) * width;
+		var y = (v + 0.5) * height;
 		var z = 0;
 		var z = 0;
 
 
 		return new THREE.Vector3(x, y, z);
 		return new THREE.Vector3(x, y, z);
@@ -94,8 +94,8 @@ var diff = new THREE.Vector3();
 function satisifyConstrains(p1, p2, distance) {
 function satisifyConstrains(p1, p2, distance) {
 	diff.subVectors(p2.position, p1.position);
 	diff.subVectors(p2.position, p1.position);
 	var currentDist = diff.length();
 	var currentDist = diff.length();
-	if (currentDist==0) return; // prevents division by 0
-	var correction = diff.multiplyScalar(1 - distance/currentDist);
+	if (currentDist == 0) return; // prevents division by 0
+	var correction = diff.multiplyScalar(1 - distance / currentDist);
 	var correctionHalf = correction.multiplyScalar(0.5);
 	var correctionHalf = correction.multiplyScalar(0.5);
 	p1.position.add(correctionHalf);
 	p1.position.add(correctionHalf);
 	p2.position.sub(correctionHalf);
 	p2.position.sub(correctionHalf);
@@ -114,47 +114,47 @@ function Cloth(w, h) {
 	var u, v;
 	var u, v;
 
 
 	// Create particles
 	// Create particles
-	for (v=0;v<=h;v++) {
-		for (u=0;u<=w;u++) {
+	for (v = 0; v <= h; v ++) {
+		for (u = 0; u <= w; u ++) {
 			particles.push(
 			particles.push(
-				new Particle(u/w, v/h, 0, MASS)
+				new Particle(u / w, v / h, 0, MASS)
 			);
 			);
 		}
 		}
 	}
 	}
 
 
 	// Structural
 	// Structural
 
 
-	for (v=0;v<h;v++) {
-		for (u=0;u<w;u++) {
+	for (v = 0; v < h; v ++) {
+		for (u = 0; u < w; u ++) {
 
 
 			constrains.push([
 			constrains.push([
 				particles[index(u, v)],
 				particles[index(u, v)],
-				particles[index(u, v+1)],
+				particles[index(u, v + 1)],
 				restDistance
 				restDistance
 			]);
 			]);
 
 
 			constrains.push([
 			constrains.push([
 				particles[index(u, v)],
 				particles[index(u, v)],
-				particles[index(u+1, v)],
+				particles[index(u + 1, v)],
 				restDistance
 				restDistance
 			]);
 			]);
 
 
 		}
 		}
 	}
 	}
 
 
-	for (u=w, v=0;v<h;v++) {
+	for (u = w, v = 0; v < h; v ++) {
 		constrains.push([
 		constrains.push([
 			particles[index(u, v)],
 			particles[index(u, v)],
-			particles[index(u, v+1)],
+			particles[index(u, v + 1)],
 			restDistance
 			restDistance
 
 
 		]);
 		]);
 	}
 	}
 
 
-	for (v=h, u=0;u<w;u++) {
+	for (v = h, u = 0; u < w; u ++) {
 		constrains.push([
 		constrains.push([
 			particles[index(u, v)],
 			particles[index(u, v)],
-			particles[index(u+1, v)],
+			particles[index(u + 1, v)],
 			restDistance
 			restDistance
 		]);
 		]);
 	}
 	}
@@ -211,7 +211,7 @@ function simulate(time) {
 
 
 		particles = cloth.particles;
 		particles = cloth.particles;
 
 
-		for (i=0,il=faces.length;i<il;i++) {
+		for (i = 0,il = faces.length; i < il; i ++) {
 			face = faces[i];
 			face = faces[i];
 			normal = face.normal;
 			normal = face.normal;
 
 
@@ -222,8 +222,8 @@ function simulate(time) {
 		}
 		}
 	}
 	}
 	
 	
-	for (particles = cloth.particles, i=0, il = particles.length
-			;i<il;i++) {
+	for (particles = cloth.particles, i = 0, il = particles.length
+			; i < il; i ++) {
 		particle = particles[i];
 		particle = particles[i];
 		particle.addForce(gravity);
 		particle.addForce(gravity);
 
 
@@ -234,7 +234,7 @@ function simulate(time) {
 
 
 	constrains = cloth.constrains,
 	constrains = cloth.constrains,
 	il = constrains.length;
 	il = constrains.length;
-	for (i=0;i<il;i++) {
+	for (i = 0; i < il; i ++) {
 		constrain = constrains[i];
 		constrain = constrains[i];
 		satisifyConstrains(constrain[0], constrain[1], constrain[2]);
 		satisifyConstrains(constrain[0], constrain[1], constrain[2]);
 	}
 	}
@@ -242,12 +242,12 @@ function simulate(time) {
 	// Ball Constrains
 	// Ball Constrains
 
 
 
 
-	ballPosition.z = -Math.sin(Date.now()/600) * 90 ; //+ 40;
-	ballPosition.x = Math.cos(Date.now()/400) * 70
+	ballPosition.z = -Math.sin(Date.now() / 600) * 90 ; //+ 40;
+	ballPosition.x = Math.cos(Date.now() / 400) * 70
 
 
 	if (sphere.visible)
 	if (sphere.visible)
-	for (particles = cloth.particles, i=0, il = particles.length
-			;i<il;i++) {
+	for (particles = cloth.particles, i = 0, il = particles.length
+			; i < il; i ++) {
 		particle = particles[i];
 		particle = particles[i];
 		pos = particle.position;
 		pos = particle.position;
 		diff.subVectors(pos, ballPosition);
 		diff.subVectors(pos, ballPosition);
@@ -259,8 +259,8 @@ function simulate(time) {
 	}
 	}
 
 
 	// Floor Constains
 	// Floor Constains
-	for (particles = cloth.particles, i=0, il = particles.length
-			;i<il;i++) {
+	for (particles = cloth.particles, i = 0, il = particles.length
+			; i < il; i ++) {
 		particle = particles[i];
 		particle = particles[i];
 		pos = particle.position;
 		pos = particle.position;
 		if (pos.y < -250) {
 		if (pos.y < -250) {
@@ -269,7 +269,7 @@ function simulate(time) {
 	}
 	}
 
 
 	// Pin Constrains
 	// Pin Constrains
-	for (i=0, il=pins.length;i<il;i++) {
+	for (i = 0, il = pins.length; i < il; i ++) {
 		var xy = pins[i];
 		var xy = pins[i];
 		var p = particles[xy];
 		var p = particles[xy];
 		p.position.copy(p.original);
 		p.position.copy(p.original);

+ 9 - 9
examples/js/CurveExtras.js

@@ -15,15 +15,15 @@
 THREE.Curves = {};
 THREE.Curves = {};
 
 
 
 
- THREE.Curves.GrannyKnot = THREE.Curve.create( function(){},
+ THREE.Curves.GrannyKnot = THREE.Curve.create( function() {},
 
 
 	 function(t) {
 	 function(t) {
-	    t = 2 * Math.PI * t;
+		t = 2 * Math.PI * t;
 
 
-	    var x = -0.22 * Math.cos(t) - 1.28 * Math.sin(t) - 0.44 * Math.cos(3 * t) - 0.78 * Math.sin(3 * t);
-	    var y = -0.1 * Math.cos(2 * t) - 0.27 * Math.sin(2 * t) + 0.38 * Math.cos(4 * t) + 0.46 * Math.sin(4 * t);
-	    var z = 0.7 * Math.cos(3 * t) - 0.4 * Math.sin(3 * t);
-	    return new THREE.Vector3(x, y, z).multiplyScalar(20);
+		var x = -0.22 * Math.cos(t) - 1.28 * Math.sin(t) - 0.44 * Math.cos(3 * t) - 0.78 * Math.sin(3 * t);
+		var y = -0.1 * Math.cos(2 * t) - 0.27 * Math.sin(2 * t) + 0.38 * Math.cos(4 * t) + 0.46 * Math.sin(4 * t);
+		var z = 0.7 * Math.cos(3 * t) - 0.4 * Math.sin(3 * t);
+		return new THREE.Vector3(x, y, z).multiplyScalar(20);
 	}
 	}
 );
 );
 
 
@@ -214,10 +214,10 @@ THREE.Curves.TrefoilPolynomialKnot = THREE.Curve.create(
 // }
 // }
 var scaleTo = function(x, y, t) {
 var scaleTo = function(x, y, t) {
 
 
-		var r = y - x;
-		return t * r + x;
+	var r = y - x;
+	return t * r + x;
 
 
-	}
+}
 
 
 THREE.Curves.FigureEightPolynomialKnot = THREE.Curve.create(
 THREE.Curves.FigureEightPolynomialKnot = THREE.Curve.create(
 
 

+ 1 - 1
examples/js/Detector.js

@@ -6,7 +6,7 @@
 var Detector = {
 var Detector = {
 
 
 	canvas: !! window.CanvasRenderingContext2D,
 	canvas: !! window.CanvasRenderingContext2D,
-	webgl: ( function () { try { var canvas = document.createElement( 'canvas' ); return !! ( window.WebGLRenderingContext && ( canvas.getContext( 'webgl' ) || canvas.getContext( 'experimental-webgl' ) ) ); } catch( e ) { return false; } } )(),
+	webgl: ( function () { try { var canvas = document.createElement( 'canvas' ); return !! ( window.WebGLRenderingContext && ( canvas.getContext( 'webgl' ) || canvas.getContext( 'experimental-webgl' ) ) ); } catch ( e ) { return false; } } )(),
 	workers: !! window.Worker,
 	workers: !! window.Worker,
 	fileapi: window.File && window.FileReader && window.FileList && window.Blob,
 	fileapi: window.File && window.FileReader && window.FileList && window.Blob,
 
 

+ 10 - 10
examples/js/ImprovedNoise.js

@@ -2,7 +2,7 @@
 
 
 var ImprovedNoise = function () {
 var ImprovedNoise = function () {
 
 
-	var p = [151,160,137,91,90,15,131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,
+	var p = [ 151,160,137,91,90,15,131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,
 		 23,190,6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33,88,237,149,56,87,
 		 23,190,6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33,88,237,149,56,87,
 		 174,20,125,136,171,168,68,175,74,165,71,134,139,48,27,166,77,146,158,231,83,111,229,122,60,211,
 		 174,20,125,136,171,168,68,175,74,165,71,134,139,48,27,166,77,146,158,231,83,111,229,122,60,211,
 		 133,230,220,105,92,41,55,46,245,40,244,102,143,54,65,25,63,161,1,216,80,73,209,76,132,187,208,
 		 133,230,220,105,92,41,55,46,245,40,244,102,143,54,65,25,63,161,1,216,80,73,209,76,132,187,208,
@@ -11,11 +11,11 @@ var ImprovedNoise = function () {
 		 248,152,2,44,154,163,70,221,153,101,155,167,43,172,9,129,22,39,253,19,98,108,110,79,113,224,232,
 		 248,152,2,44,154,163,70,221,153,101,155,167,43,172,9,129,22,39,253,19,98,108,110,79,113,224,232,
 		 178,185,112,104,218,246,97,228,251,34,242,193,238,210,144,12,191,179,162,241,81,51,145,235,249,
 		 178,185,112,104,218,246,97,228,251,34,242,193,238,210,144,12,191,179,162,241,81,51,145,235,249,
 		 14,239,107,49,192,214,31,181,199,106,157,184,84,204,176,115,121,50,45,127,4,150,254,138,236,205,
 		 14,239,107,49,192,214,31,181,199,106,157,184,84,204,176,115,121,50,45,127,4,150,254,138,236,205,
-		 93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180];
+		 93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180 ];
 
 
-	for (var i=0; i < 256 ; i++) {
+	for (var i = 0; i < 256 ; i ++) {
 
 
-		p[256+i] = p[i];
+		p[256 + i] = p[i];
 
 
 	}
 	}
 
 
@@ -51,20 +51,20 @@ var ImprovedNoise = function () {
 			y -= floorY;
 			y -= floorY;
 			z -= floorZ;
 			z -= floorZ;
 
 
-			var xMinus1 = x -1, yMinus1 = y - 1, zMinus1 = z - 1;
+			var xMinus1 = x - 1, yMinus1 = y - 1, zMinus1 = z - 1;
 
 
 			var u = fade(x), v = fade(y), w = fade(z);
 			var u = fade(x), v = fade(y), w = fade(z);
 
 
-			var A = p[X]+Y, AA = p[A]+Z, AB = p[A+1]+Z, B = p[X+1]+Y, BA = p[B]+Z, BB = p[B+1]+Z;
+			var A = p[X] + Y, AA = p[A] + Z, AB = p[A + 1] + Z, B = p[X + 1] + Y, BA = p[B] + Z, BB = p[B + 1] + Z;
 
 
 			return lerp(w, lerp(v, lerp(u, grad(p[AA], x, y, z), 
 			return lerp(w, lerp(v, lerp(u, grad(p[AA], x, y, z), 
 							grad(p[BA], xMinus1, y, z)),
 							grad(p[BA], xMinus1, y, z)),
 						lerp(u, grad(p[AB], x, yMinus1, z),
 						lerp(u, grad(p[AB], x, yMinus1, z),
 							grad(p[BB], xMinus1, yMinus1, z))),
 							grad(p[BB], xMinus1, yMinus1, z))),
-					lerp(v, lerp(u, grad(p[AA+1], x, y, zMinus1),
-							grad(p[BA+1], xMinus1, y, z-1)),
-						lerp(u, grad(p[AB+1], x, yMinus1, zMinus1),
-							grad(p[BB+1], xMinus1, yMinus1, zMinus1))));
+					lerp(v, lerp(u, grad(p[AA + 1], x, y, zMinus1),
+							grad(p[BA + 1], xMinus1, y, z - 1)),
+						lerp(u, grad(p[AB + 1], x, yMinus1, zMinus1),
+							grad(p[BB + 1], xMinus1, yMinus1, zMinus1))));
 
 
 		}
 		}
 	}
 	}

+ 1 - 1
examples/js/MD2Character.js

@@ -210,7 +210,7 @@ THREE.MD2Character = function () {
 		//
 		//
 
 
 		var mesh = new THREE.MorphAnimMesh( geometry, materialTexture );
 		var mesh = new THREE.MorphAnimMesh( geometry, materialTexture );
-		mesh.rotation.y = -Math.PI/2;
+		mesh.rotation.y = -Math.PI / 2;
 
 
 		mesh.castShadow = true;
 		mesh.castShadow = true;
 		mesh.receiveShadow = true;
 		mesh.receiveShadow = true;

+ 3 - 3
examples/js/MD2CharacterComplex.js

@@ -402,7 +402,7 @@ THREE.MD2CharacterComplex = function () {
 
 
 		if ( controls.moveForward ) {
 		if ( controls.moveForward ) {
 
 
-			if ( this.meshBody )   {
+			if ( this.meshBody ) {
 
 
 				this.meshBody.setAnimationDirectionForward( this.activeAnimation );
 				this.meshBody.setAnimationDirectionForward( this.activeAnimation );
 				this.meshBody.setAnimationDirectionForward( this.oldAnimation );
 				this.meshBody.setAnimationDirectionForward( this.oldAnimation );
@@ -445,7 +445,7 @@ THREE.MD2CharacterComplex = function () {
 		// speed based on controls
 		// speed based on controls
 
 
 		if ( controls.crouch ) 	this.maxSpeed = this.crouchSpeed;
 		if ( controls.crouch ) 	this.maxSpeed = this.crouchSpeed;
-		else  					this.maxSpeed = this.walkSpeed;
+		else this.maxSpeed = this.walkSpeed;
 
 
 		this.maxReverseSpeed = -this.maxSpeed;
 		this.maxReverseSpeed = -this.maxSpeed;
 
 
@@ -533,7 +533,7 @@ THREE.MD2CharacterComplex = function () {
 		//
 		//
 
 
 		var mesh = new THREE.MorphBlendMesh( geometry, materialTexture );
 		var mesh = new THREE.MorphBlendMesh( geometry, materialTexture );
-		mesh.rotation.y = -Math.PI/2;
+		mesh.rotation.y = -Math.PI / 2;
 
 
 		//
 		//
 
 

+ 23 - 23
examples/js/MarchingCubes.js

@@ -224,7 +224,7 @@ THREE.MarchingCubes = function ( resolution, material, enableUvs, enableColors )
 
 
 		// bottom of the cube
 		// bottom of the cube
 
 
-		if ( bits & 16 )  {
+		if ( bits & 16 ) {
 
 
 			this.compNorm( qz );
 			this.compNorm( qz );
 			this.compNorm( q1z );
 			this.compNorm( q1z );
@@ -232,7 +232,7 @@ THREE.MarchingCubes = function ( resolution, material, enableUvs, enableColors )
 
 
 		};
 		};
 
 
-		if ( bits & 32 )  {
+		if ( bits & 32 ) {
 
 
 			this.compNorm( q1z );
 			this.compNorm( q1z );
 			this.compNorm( q1yz );
 			this.compNorm( q1yz );
@@ -485,22 +485,22 @@ THREE.MarchingCubes = function ( resolution, material, enableUvs, enableColors )
 
 
 		var x, y, z, y_offset, z_offset, fx, fy, fz, fz2, fy2, val;
 		var x, y, z, y_offset, z_offset, fx, fy, fz, fz2, fy2, val;
 
 
-		for ( z = min_z; z < max_z; z++ ) {
+		for ( z = min_z; z < max_z; z ++ ) {
 
 
 			z_offset = this.size2 * z,
 			z_offset = this.size2 * z,
 			fz = z / this.size - ballz,
 			fz = z / this.size - ballz,
 			fz2 = fz * fz;
 			fz2 = fz * fz;
 
 
-			for ( y = min_y; y < max_y; y++ ) {
+			for ( y = min_y; y < max_y; y ++ ) {
 
 
 				y_offset = z_offset + this.size * y;
 				y_offset = z_offset + this.size * y;
 				fy = y / this.size - bally;
 				fy = y / this.size - bally;
 				fy2 = fy * fy;
 				fy2 = fy * fy;
 
 
-				for ( x = min_x; x < max_x; x++ ) {
+				for ( x = min_x; x < max_x; x ++ ) {
 
 
 					fx = x / this.size - ballx;
 					fx = x / this.size - ballx;
-					val = strength / ( 0.000001 + fx*fx + fy2 + fz2 ) - subtract;
+					val = strength / ( 0.000001 + fx * fx + fy2 + fz2 ) - subtract;
 					if ( val > 0.0 ) this.field[ y_offset + x ] += val;
 					if ( val > 0.0 ) this.field[ y_offset + x ] += val;
 
 
 				}
 				}
@@ -763,38 +763,38 @@ THREE.MarchingCubes.prototype.constructor = THREE.MarchingCubes;
 // who in turn got them from Cory Gene Bloyd.
 // who in turn got them from Cory Gene Bloyd.
 
 
 THREE.edgeTable = new Int32Array([
 THREE.edgeTable = new Int32Array([
-0x0  , 0x109, 0x203, 0x30a, 0x406, 0x50f, 0x605, 0x70c,
+0x0, 0x109, 0x203, 0x30a, 0x406, 0x50f, 0x605, 0x70c,
 0x80c, 0x905, 0xa0f, 0xb06, 0xc0a, 0xd03, 0xe09, 0xf00,
 0x80c, 0x905, 0xa0f, 0xb06, 0xc0a, 0xd03, 0xe09, 0xf00,
-0x190, 0x99 , 0x393, 0x29a, 0x596, 0x49f, 0x795, 0x69c,
+0x190, 0x99, 0x393, 0x29a, 0x596, 0x49f, 0x795, 0x69c,
 0x99c, 0x895, 0xb9f, 0xa96, 0xd9a, 0xc93, 0xf99, 0xe90,
 0x99c, 0x895, 0xb9f, 0xa96, 0xd9a, 0xc93, 0xf99, 0xe90,
-0x230, 0x339, 0x33 , 0x13a, 0x636, 0x73f, 0x435, 0x53c,
+0x230, 0x339, 0x33, 0x13a, 0x636, 0x73f, 0x435, 0x53c,
 0xa3c, 0xb35, 0x83f, 0x936, 0xe3a, 0xf33, 0xc39, 0xd30,
 0xa3c, 0xb35, 0x83f, 0x936, 0xe3a, 0xf33, 0xc39, 0xd30,
-0x3a0, 0x2a9, 0x1a3, 0xaa , 0x7a6, 0x6af, 0x5a5, 0x4ac,
+0x3a0, 0x2a9, 0x1a3, 0xaa, 0x7a6, 0x6af, 0x5a5, 0x4ac,
 0xbac, 0xaa5, 0x9af, 0x8a6, 0xfaa, 0xea3, 0xda9, 0xca0,
 0xbac, 0xaa5, 0x9af, 0x8a6, 0xfaa, 0xea3, 0xda9, 0xca0,
-0x460, 0x569, 0x663, 0x76a, 0x66 , 0x16f, 0x265, 0x36c,
+0x460, 0x569, 0x663, 0x76a, 0x66, 0x16f, 0x265, 0x36c,
 0xc6c, 0xd65, 0xe6f, 0xf66, 0x86a, 0x963, 0xa69, 0xb60,
 0xc6c, 0xd65, 0xe6f, 0xf66, 0x86a, 0x963, 0xa69, 0xb60,
-0x5f0, 0x4f9, 0x7f3, 0x6fa, 0x1f6, 0xff , 0x3f5, 0x2fc,
+0x5f0, 0x4f9, 0x7f3, 0x6fa, 0x1f6, 0xff, 0x3f5, 0x2fc,
 0xdfc, 0xcf5, 0xfff, 0xef6, 0x9fa, 0x8f3, 0xbf9, 0xaf0,
 0xdfc, 0xcf5, 0xfff, 0xef6, 0x9fa, 0x8f3, 0xbf9, 0xaf0,
-0x650, 0x759, 0x453, 0x55a, 0x256, 0x35f, 0x55 , 0x15c,
+0x650, 0x759, 0x453, 0x55a, 0x256, 0x35f, 0x55, 0x15c,
 0xe5c, 0xf55, 0xc5f, 0xd56, 0xa5a, 0xb53, 0x859, 0x950,
 0xe5c, 0xf55, 0xc5f, 0xd56, 0xa5a, 0xb53, 0x859, 0x950,
-0x7c0, 0x6c9, 0x5c3, 0x4ca, 0x3c6, 0x2cf, 0x1c5, 0xcc ,
+0x7c0, 0x6c9, 0x5c3, 0x4ca, 0x3c6, 0x2cf, 0x1c5, 0xcc,
 0xfcc, 0xec5, 0xdcf, 0xcc6, 0xbca, 0xac3, 0x9c9, 0x8c0,
 0xfcc, 0xec5, 0xdcf, 0xcc6, 0xbca, 0xac3, 0x9c9, 0x8c0,
 0x8c0, 0x9c9, 0xac3, 0xbca, 0xcc6, 0xdcf, 0xec5, 0xfcc,
 0x8c0, 0x9c9, 0xac3, 0xbca, 0xcc6, 0xdcf, 0xec5, 0xfcc,
-0xcc , 0x1c5, 0x2cf, 0x3c6, 0x4ca, 0x5c3, 0x6c9, 0x7c0,
+0xcc, 0x1c5, 0x2cf, 0x3c6, 0x4ca, 0x5c3, 0x6c9, 0x7c0,
 0x950, 0x859, 0xb53, 0xa5a, 0xd56, 0xc5f, 0xf55, 0xe5c,
 0x950, 0x859, 0xb53, 0xa5a, 0xd56, 0xc5f, 0xf55, 0xe5c,
-0x15c, 0x55 , 0x35f, 0x256, 0x55a, 0x453, 0x759, 0x650,
+0x15c, 0x55, 0x35f, 0x256, 0x55a, 0x453, 0x759, 0x650,
 0xaf0, 0xbf9, 0x8f3, 0x9fa, 0xef6, 0xfff, 0xcf5, 0xdfc,
 0xaf0, 0xbf9, 0x8f3, 0x9fa, 0xef6, 0xfff, 0xcf5, 0xdfc,
-0x2fc, 0x3f5, 0xff , 0x1f6, 0x6fa, 0x7f3, 0x4f9, 0x5f0,
+0x2fc, 0x3f5, 0xff, 0x1f6, 0x6fa, 0x7f3, 0x4f9, 0x5f0,
 0xb60, 0xa69, 0x963, 0x86a, 0xf66, 0xe6f, 0xd65, 0xc6c,
 0xb60, 0xa69, 0x963, 0x86a, 0xf66, 0xe6f, 0xd65, 0xc6c,
-0x36c, 0x265, 0x16f, 0x66 , 0x76a, 0x663, 0x569, 0x460,
+0x36c, 0x265, 0x16f, 0x66, 0x76a, 0x663, 0x569, 0x460,
 0xca0, 0xda9, 0xea3, 0xfaa, 0x8a6, 0x9af, 0xaa5, 0xbac,
 0xca0, 0xda9, 0xea3, 0xfaa, 0x8a6, 0x9af, 0xaa5, 0xbac,
-0x4ac, 0x5a5, 0x6af, 0x7a6, 0xaa , 0x1a3, 0x2a9, 0x3a0,
+0x4ac, 0x5a5, 0x6af, 0x7a6, 0xaa, 0x1a3, 0x2a9, 0x3a0,
 0xd30, 0xc39, 0xf33, 0xe3a, 0x936, 0x83f, 0xb35, 0xa3c,
 0xd30, 0xc39, 0xf33, 0xe3a, 0x936, 0x83f, 0xb35, 0xa3c,
-0x53c, 0x435, 0x73f, 0x636, 0x13a, 0x33 , 0x339, 0x230,
+0x53c, 0x435, 0x73f, 0x636, 0x13a, 0x33, 0x339, 0x230,
 0xe90, 0xf99, 0xc93, 0xd9a, 0xa96, 0xb9f, 0x895, 0x99c,
 0xe90, 0xf99, 0xc93, 0xd9a, 0xa96, 0xb9f, 0x895, 0x99c,
-0x69c, 0x795, 0x49f, 0x596, 0x29a, 0x393, 0x99 , 0x190,
+0x69c, 0x795, 0x49f, 0x596, 0x29a, 0x393, 0x99, 0x190,
 0xf00, 0xe09, 0xd03, 0xc0a, 0xb06, 0xa0f, 0x905, 0x80c,
 0xf00, 0xe09, 0xd03, 0xc0a, 0xb06, 0xa0f, 0x905, 0x80c,
-0x70c, 0x605, 0x50f, 0x406, 0x30a, 0x203, 0x109, 0x0])
+0x70c, 0x605, 0x50f, 0x406, 0x30a, 0x203, 0x109, 0x0 ])
 
 
 THREE.triTable = new Int32Array([
 THREE.triTable = new Int32Array([
 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
@@ -1052,4 +1052,4 @@ THREE.triTable = new Int32Array([
 1, 3, 8, 9, 1, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
 1, 3, 8, 9, 1, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
 0, 9, 1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
 0, 9, 1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
 0, 3, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
 0, 3, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
--1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1]);
+-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1 ]);

+ 10 - 9
examples/js/Ocean.js

@@ -20,8 +20,8 @@
 		return value !== undefined ? value : defaultValue;
 		return value !== undefined ? value : defaultValue;
 	};
 	};
 	options = options || {};
 	options = options || {};
-	this.clearColor = optionalParameter(options.CLEAR_COLOR, [1.0, 1.0, 1.0, 0.0]);
-	this.geometryOrigin = optionalParameter(options.GEOMETRY_ORIGIN, [-1000.0, -1000.0]);
+	this.clearColor = optionalParameter(options.CLEAR_COLOR, [ 1.0, 1.0, 1.0, 0.0 ]);
+	this.geometryOrigin = optionalParameter(options.GEOMETRY_ORIGIN, [ -1000.0, -1000.0 ]);
 	this.sunDirectionX = optionalParameter(options.SUN_DIRECTION[0], -1.0);
 	this.sunDirectionX = optionalParameter(options.SUN_DIRECTION[0], -1.0);
 	this.sunDirectionY = optionalParameter(options.SUN_DIRECTION[1], 1.0);
 	this.sunDirectionY = optionalParameter(options.SUN_DIRECTION[1], 1.0);
 	this.sunDirectionZ = optionalParameter(options.SUN_DIRECTION[2], 1.0);
 	this.sunDirectionZ = optionalParameter(options.SUN_DIRECTION[2], 1.0);
@@ -41,6 +41,7 @@
 	this.matrixNeedsUpdate = false;
 	this.matrixNeedsUpdate = false;
 	
 	
 	// Setup framebuffer pipeline
 	// Setup framebuffer pipeline
+	var renderTargetType = optionalParameter(options.USE_HALF_FLOAT, false) ? THREE.HalfFloatType : THREE.FloatType;
 	var LinearClampParams = {
 	var LinearClampParams = {
 		minFilter: THREE.LinearFilter,
 		minFilter: THREE.LinearFilter,
 		magFilter: THREE.LinearFilter,
 		magFilter: THREE.LinearFilter,
@@ -50,7 +51,7 @@
 		stencilBuffer: false,
 		stencilBuffer: false,
 		depthBuffer: false,
 		depthBuffer: false,
 		premultiplyAlpha: false,
 		premultiplyAlpha: false,
-		type: THREE.FloatType
+		type: renderTargetType
 	};
 	};
 	var NearestClampParams = {
 	var NearestClampParams = {
 		minFilter: THREE.NearestFilter,
 		minFilter: THREE.NearestFilter,
@@ -61,7 +62,7 @@
 		stencilBuffer: false,
 		stencilBuffer: false,
 		depthBuffer: false,
 		depthBuffer: false,
 		premultiplyAlpha:false,
 		premultiplyAlpha:false,
-		type: THREE.FloatType
+		type: renderTargetType
 	};
 	};
 	var NearestRepeatParams = {
 	var NearestRepeatParams = {
 		minFilter: THREE.NearestFilter,
 		minFilter: THREE.NearestFilter,
@@ -72,7 +73,7 @@
 		stencilBuffer: false,
 		stencilBuffer: false,
 		depthBuffer: false,
 		depthBuffer: false,
 		premultiplyAlpha: false,
 		premultiplyAlpha: false,
-		type: THREE.FloatType
+		type: renderTargetType
 	};
 	};
 	this.initialSpectrumFramebuffer = new THREE.WebGLRenderTarget(this.resolution, this.resolution, NearestRepeatParams);
 	this.initialSpectrumFramebuffer = new THREE.WebGLRenderTarget(this.resolution, this.resolution, NearestRepeatParams);
 	this.spectrumFramebuffer = new THREE.WebGLRenderTarget(this.resolution, this.resolution, NearestClampParams);
 	this.spectrumFramebuffer = new THREE.WebGLRenderTarget(this.resolution, this.resolution, NearestClampParams);
@@ -227,8 +228,8 @@ THREE.Ocean.prototype.generateSeedPhaseTexture = function() {
 	// Setup the seed texture
 	// Setup the seed texture
 	this.pingPhase = true;
 	this.pingPhase = true;
 	var phaseArray = new window.Float32Array(this.resolution * this.resolution * 4);
 	var phaseArray = new window.Float32Array(this.resolution * this.resolution * 4);
-	for (var i = 0; i < this.resolution; i++) {
-		for (var j = 0; j < this.resolution; j++) {
+	for (var i = 0; i < this.resolution; i ++) {
+		for (var j = 0; j < this.resolution; j ++) {
 			phaseArray[i * this.resolution * 4 + j * 4] =  Math.random() * 2.0 * Math.PI;
 			phaseArray[i * this.resolution * 4 + j * 4] =  Math.random() * 2.0 * Math.PI;
 			phaseArray[i * this.resolution * 4 + j * 4 + 1] = 0.0;
 			phaseArray[i * this.resolution * 4 + j * 4 + 1] = 0.0;
 			phaseArray[i * this.resolution * 4 + j * 4 + 2] = 0.0;
 			phaseArray[i * this.resolution * 4 + j * 4 + 2] = 0.0;
@@ -282,7 +283,7 @@ THREE.Ocean.prototype.renderSpectrumFFT = function() {
 	
 	
 	this.scene.overrideMaterial = this.materialOceanHorizontal;
 	this.scene.overrideMaterial = this.materialOceanHorizontal;
 
 
-	for (var i = 0; i < iterations; i++) {
+	for (var i = 0; i < iterations; i ++) {
 		if (i === 0) {
 		if (i === 0) {
 			this.materialOceanHorizontal.uniforms.u_input.value = this.spectrumFramebuffer;
 			this.materialOceanHorizontal.uniforms.u_input.value = this.spectrumFramebuffer;
 			this.materialOceanHorizontal.uniforms.u_subtransformSize.value = Math.pow(2, (i % (iterations)) + 1);
 			this.materialOceanHorizontal.uniforms.u_subtransformSize.value = Math.pow(2, (i % (iterations)) + 1);
@@ -300,7 +301,7 @@ THREE.Ocean.prototype.renderSpectrumFFT = function() {
 		}
 		}
 	}
 	}
 	this.scene.overrideMaterial = this.materialOceanVertical;
 	this.scene.overrideMaterial = this.materialOceanVertical;
-	for (var i = iterations; i < iterations*2; i++) {
+	for (var i = iterations; i < iterations * 2; i ++) {
 		if (i === iterations * 2 - 1) {
 		if (i === iterations * 2 - 1) {
 			this.materialOceanVertical.uniforms.u_input.value = (iterations % 2 === 0) ? this.pingTransformFramebuffer : this.pongTransformFramebuffer;
 			this.materialOceanVertical.uniforms.u_input.value = (iterations % 2 === 0) ? this.pingTransformFramebuffer : this.pongTransformFramebuffer;
 			this.materialOceanVertical.uniforms.u_subtransformSize.value = Math.pow(2, (i % (iterations)) + 1);
 			this.materialOceanVertical.uniforms.u_subtransformSize.value = Math.pow(2, (i % (iterations)) + 1);

+ 43 - 43
examples/js/Octree.js

@@ -29,7 +29,7 @@
 	
 	
 	function indexOfValue( array, value ) {
 	function indexOfValue( array, value ) {
 		
 		
-		for ( var i = 0, il = array.length; i < il; i++ ) {
+		for ( var i = 0, il = array.length; i < il; i ++ ) {
 			
 			
 			if ( array[ i ] === value ) {
 			if ( array[ i ] === value ) {
 				
 				
@@ -45,7 +45,7 @@
 	
 	
 	function indexOfPropertyWithValue( array, property, value ) {
 	function indexOfPropertyWithValue( array, property, value ) {
 		
 		
-		for ( var i = 0, il = array.length; i < il; i++ ) {
+		for ( var i = 0, il = array.length; i < il; i ++ ) {
 			
 			
 			if ( array[ i ][ property ] === value ) {
 			if ( array[ i ][ property ] === value ) {
 				
 				
@@ -140,7 +140,7 @@
 			
 			
 			if ( this.objectsDeferred.length > 0 ) {
 			if ( this.objectsDeferred.length > 0 ) {
 				
 				
-				for ( var i = 0, il = this.objectsDeferred.length; i < il; i++ ) {
+				for ( var i = 0, il = this.objectsDeferred.length; i < il; i ++ ) {
 					
 					
 					var deferred = this.objectsDeferred[ i ];
 					var deferred = this.objectsDeferred[ i ];
 					
 					
@@ -221,7 +221,7 @@
 					geometry = object.geometry;
 					geometry = object.geometry;
 					vertices = geometry.vertices;
 					vertices = geometry.vertices;
 					
 					
-					for ( i = 0, l = vertices.length; i < l; i++ ) {
+					for ( i = 0, l = vertices.length; i < l; i ++ ) {
 						
 						
 						this.addObjectData( object, vertices[ i ] );
 						this.addObjectData( object, vertices[ i ] );
 						
 						
@@ -232,7 +232,7 @@
 					geometry = object.geometry;
 					geometry = object.geometry;
 					faces = geometry.faces;
 					faces = geometry.faces;
 					
 					
-					for ( i = 0, l = faces.length; i < l; i++ ) {
+					for ( i = 0, l = faces.length; i < l; i ++ ) {
 						
 						
 						this.addObjectData( object, faces[ i ] );
 						this.addObjectData( object, faces[ i ] );
 						
 						
@@ -297,7 +297,7 @@
 					
 					
 					// remove from objects data list
 					// remove from objects data list
 					
 					
-					for ( i = 0, l = objectsDataRemoved.length; i < l; i++ ) {
+					for ( i = 0, l = objectsDataRemoved.length; i < l; i ++ ) {
 						
 						
 						objectData = objectsDataRemoved[ i ];
 						objectData = objectsDataRemoved[ i ];
 						
 						
@@ -341,7 +341,7 @@
 				
 				
 				objectsData = octree.objectsData;
 				objectsData = octree.objectsData;
 				
 				
-				for ( i = 0, l = objectsData.length; i < l; i++ ) {
+				for ( i = 0, l = objectsData.length; i < l; i ++ ) {
 					
 					
 					objectData = objectsData[ i ];
 					objectData = objectsData[ i ];
 					
 					
@@ -366,7 +366,7 @@
 			// check all object data for changes in position
 			// check all object data for changes in position
 			// assumes all object matrices are up to date
 			// assumes all object matrices are up to date
 			
 			
-			for ( i = 0, l = this.objectsData.length; i < l; i++ ) {
+			for ( i = 0, l = this.objectsData.length; i < l; i ++ ) {
 				
 				
 				objectData = this.objectsData[ i ];
 				objectData = this.objectsData[ i ];
 				
 				
@@ -402,7 +402,7 @@
 			
 			
 			// update changed objects
 			// update changed objects
 			
 			
-			for ( i = 0, l = objectsUpdate.length; i < l; i++ ) {
+			for ( i = 0, l = objectsUpdate.length; i < l; i ++ ) {
 				
 				
 				objectData = objectsUpdate[ i ];
 				objectData = objectsUpdate[ i ];
 				
 				
@@ -429,14 +429,14 @@
 			
 			
 			parent = object.parent;
 			parent = object.parent;
 			
 			
-			while( parent ) {
+			while ( parent ) {
 				
 				
 				parentCascade.push( parent );
 				parentCascade.push( parent );
 				parent = parent.parent;
 				parent = parent.parent;
 				
 				
 			}
 			}
 			
 			
-			for ( i = 0, l = parentCascade.length; i < l; i++ ) {
+			for ( i = 0, l = parentCascade.length; i < l; i ++ ) {
 				
 				
 				parent = parentCascade[ i ];
 				parent = parentCascade[ i ];
 				
 				
@@ -494,7 +494,7 @@
 			
 			
 			// search each node of root
 			// search each node of root
 			
 			
-			for ( i = 0, l = this.root.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.root.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				node = this.root.nodesByIndex[ this.root.nodesIndices[ i ] ];
 				node = this.root.nodesByIndex[ this.root.nodesIndices[ i ] ];
 				
 				
@@ -511,7 +511,7 @@
 				
 				
 				// for each object data found
 				// for each object data found
 				
 				
-				for ( i = 0, l = objects.length; i < l; i++ ) {
+				for ( i = 0, l = objects.length; i < l; i ++ ) {
 					
 					
 					objectData = objects[ i ];
 					objectData = objects[ i ];
 					object = objectData.object;
 					object = objectData.object;
@@ -739,7 +739,7 @@
 		
 		
 		// basic properties
 		// basic properties
 		
 		
-		this.id = this.tree.nodeCount++;
+		this.id = this.tree.nodeCount ++;
 		this.position = parameters.position instanceof THREE.Vector3 ? parameters.position : new THREE.Vector3();
 		this.position = parameters.position instanceof THREE.Vector3 ? parameters.position : new THREE.Vector3();
 		this.radius = parameters.radius > 0 ? parameters.radius : 1;
 		this.radius = parameters.radius > 0 ? parameters.radius : 1;
 		this.indexOctant = parameters.indexOctant;
 		this.indexOctant = parameters.indexOctant;
@@ -811,7 +811,7 @@
 			
 			
 			// cascade
 			// cascade
 			
 			
-			for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				this.nodesByIndex[ this.nodesIndices[ i ] ].updateProperties();
 				this.nodesByIndex[ this.nodesIndices[ i ] ].updateProperties();
 				
 				
@@ -832,7 +832,7 @@
 			
 			
 			// unset parent in nodes
 			// unset parent in nodes
 			
 			
-			for ( i = 0, l = nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = nodesIndices.length; i < l; i ++ ) {
 				
 				
 				node = nodesByIndex[ nodesIndices[ i ] ];
 				node = nodesByIndex[ nodesIndices[ i ] ];
 				
 				
@@ -949,7 +949,7 @@
 			var i, l,
 			var i, l,
 				object;
 				object;
 
 
-			for ( i = 0, l = objects.length; i < l; i++ ) {
+			for ( i = 0, l = objects.length; i < l; i ++ ) {
 				
 				
 				object = objects[ i ];
 				object = objects[ i ];
 				
 				
@@ -977,7 +977,7 @@
 			
 			
 			if ( nodesRemovedFrom.length > 0 ) {
 			if ( nodesRemovedFrom.length > 0 ) {
 				
 				
-				for ( i = 0, l = nodesRemovedFrom.length; i < l; i++ ) {
+				for ( i = 0, l = nodesRemovedFrom.length; i < l; i ++ ) {
 					
 					
 					nodesRemovedFrom[ i ].shrink();
 					nodesRemovedFrom[ i ].shrink();
 					
 					
@@ -1021,7 +1021,7 @@
 			
 			
 				// search each object data for object and remove (slow)
 				// search each object data for object and remove (slow)
 				
 				
-				for ( i = this.objects.length - 1; i >= 0; i-- ) {
+				for ( i = this.objects.length - 1; i >= 0; i -- ) {
 					
 					
 					objectData = this.objects[ i ];
 					objectData = this.objects[ i ];
 					
 					
@@ -1059,7 +1059,7 @@
 			
 			
 			if ( removeData.searchComplete !== true ) {
 			if ( removeData.searchComplete !== true ) {
 				
 				
-				for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+				for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 					
 					
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					
 					
@@ -1106,7 +1106,7 @@
 			
 			
 			// for each object
 			// for each object
 			
 			
-			for ( i = 0, l = this.objects.length; i < l; i++ ) {
+			for ( i = 0, l = this.objects.length; i < l; i ++ ) {
 				
 				
 				object = this.objects[ i ];
 				object = this.objects[ i ];
 				
 				
@@ -1183,7 +1183,7 @@
 				
 				
 				// for each object
 				// for each object
 				
 				
-				for ( i = 0, l = objects.length; i < l; i++ ) {
+				for ( i = 0, l = objects.length; i < l; i ++ ) {
 					
 					
 					object = objects[ i ];
 					object = objects[ i ];
 					
 					
@@ -1314,7 +1314,7 @@
 				
 				
 				// reset counts
 				// reset counts
 				
 				
-				for ( i = 0, l = iom.length; i < l; i++ ) {
+				for ( i = 0, l = iom.length; i < l; i ++ ) {
 					
 					
 					iom[ i ].count = 0;
 					iom[ i ].count = 0;
 					
 					
@@ -1322,7 +1322,7 @@
 				
 				
 				// for all outside objects, find outside octants containing most objects
 				// for all outside objects, find outside octants containing most objects
 				
 				
-				for ( i = 0, l = objects.length; i < l; i++ ) {
+				for ( i = 0, l = objects.length; i < l; i ++ ) {
 					
 					
 					object = objects[ i ];
 					object = objects[ i ];
 					
 					
@@ -1344,11 +1344,11 @@
 						
 						
 						if ( flagsOutside & this.tree.FLAG_POS_X ) {
 						if ( flagsOutside & this.tree.FLAG_POS_X ) {
 							
 							
-							iom[ this.tree.INDEX_OUTSIDE_POS_X ].count++;
+							iom[ this.tree.INDEX_OUTSIDE_POS_X ].count ++;
 							
 							
 						} else if ( flagsOutside & this.tree.FLAG_NEG_X ) {
 						} else if ( flagsOutside & this.tree.FLAG_NEG_X ) {
 							
 							
-							iom[ this.tree.INDEX_OUTSIDE_NEG_X ].count++;
+							iom[ this.tree.INDEX_OUTSIDE_NEG_X ].count ++;
 							
 							
 						}
 						}
 						
 						
@@ -1356,11 +1356,11 @@
 						
 						
 						if ( flagsOutside & this.tree.FLAG_POS_Y ) {
 						if ( flagsOutside & this.tree.FLAG_POS_Y ) {
 							
 							
-							iom[ this.tree.INDEX_OUTSIDE_POS_Y ].count++;
+							iom[ this.tree.INDEX_OUTSIDE_POS_Y ].count ++;
 							
 							
 						} else if ( flagsOutside & this.tree.FLAG_NEG_Y ) {
 						} else if ( flagsOutside & this.tree.FLAG_NEG_Y ) {
 							
 							
-							iom[ this.tree.INDEX_OUTSIDE_NEG_Y ].count++;
+							iom[ this.tree.INDEX_OUTSIDE_NEG_Y ].count ++;
 							
 							
 						}
 						}
 						
 						
@@ -1368,11 +1368,11 @@
 						
 						
 						if ( flagsOutside & this.tree.FLAG_POS_Z ) {
 						if ( flagsOutside & this.tree.FLAG_POS_Z ) {
 							
 							
-							iom[ this.tree.INDEX_OUTSIDE_POS_Z ].count++;
+							iom[ this.tree.INDEX_OUTSIDE_POS_Z ].count ++;
 							
 							
 						} else if ( flagsOutside & this.tree.FLAG_NEG_Z ) {
 						} else if ( flagsOutside & this.tree.FLAG_NEG_Z ) {
 							
 							
-							iom[ this.tree.INDEX_OUTSIDE_NEG_Z ].count++;
+							iom[ this.tree.INDEX_OUTSIDE_NEG_Z ].count ++;
 							
 							
 						}
 						}
 						
 						
@@ -1474,7 +1474,7 @@
 					
 					
 					// add all expand objects to parent
 					// add all expand objects to parent
 					
 					
-					for ( i = 0, l = objectsExpand.length; i < l; i++ ) {
+					for ( i = 0, l = objectsExpand.length; i < l; i ++ ) {
 						
 						
 						this.tree.root.addObject( objectsExpand[ i ] );
 						this.tree.root.addObject( objectsExpand[ i ] );
 						
 						
@@ -1546,7 +1546,7 @@
 			
 			
 			nodes = toArray( nodes );
 			nodes = toArray( nodes );
 			
 			
-			for ( i = 0, l = nodes.length; i < l; i++ ) {
+			for ( i = 0, l = nodes.length; i < l; i ++ ) {
 				
 				
 				node = nodes[ i ];
 				node = nodes[ i ];
 				
 				
@@ -1586,7 +1586,7 @@
 				nodeHeaviestObjectsCount = 0;
 				nodeHeaviestObjectsCount = 0;
 				outsideHeaviestObjectsCount = this.objects.length;
 				outsideHeaviestObjectsCount = this.objects.length;
 				
 				
-				for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+				for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 					
 					
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					
 					
@@ -1625,7 +1625,7 @@
 			
 			
 			// handle all nodes
 			// handle all nodes
 			
 			
-			for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 				node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 				
 				
@@ -1848,7 +1848,7 @@
 				
 				
 				// search subtree
 				// search subtree
 				
 				
-				for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+				for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 					
 					
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					
 					
@@ -1917,7 +1917,7 @@
 			tmin = Math.max( Math.max( Math.min( t1, t2), Math.min( t3, t4)), Math.min( t5, t6));
 			tmin = Math.max( Math.max( Math.min( t1, t2), Math.min( t3, t4)), Math.min( t5, t6));
 			
 			
 			// if tmin > tmax or tmin > ray distance, ray doesn't intersect AABB
 			// if tmin > tmax or tmin > ray distance, ray doesn't intersect AABB
-			if( tmin > tmax || tmin > distance ) {
+			if ( tmin > tmax || tmin > distance ) {
 				return false;
 				return false;
 			}
 			}
 			
 			
@@ -1932,7 +1932,7 @@
 
 
 			if ( this.nodesIndices.length > 0 ) {
 			if ( this.nodesIndices.length > 0 ) {
 				
 				
-				for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+				for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 
 
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 					node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 
 
@@ -1961,7 +1961,7 @@
 			var i, l,
 			var i, l,
 				count = this.nodesIndices.length;
 				count = this.nodesIndices.length;
 			
 			
-			for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				count += this.nodesByIndex[ this.nodesIndices[ i ] ].getNodeCountRecursive();
 				count += this.nodesByIndex[ this.nodesIndices[ i ] ].getNodeCountRecursive();
 				
 				
@@ -1978,7 +1978,7 @@
 			
 			
 			objects = ( objects || [] ).concat( this.objects );
 			objects = ( objects || [] ).concat( this.objects );
 			
 			
-			for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 				node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 				
 				
@@ -1995,7 +1995,7 @@
 			var i, l,
 			var i, l,
 				count = this.objects.length;
 				count = this.objects.length;
 			
 			
-			for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				count += this.nodesByIndex[ this.nodesIndices[ i ] ].getObjectCountEnd();
 				count += this.nodesByIndex[ this.nodesIndices[ i ] ].getObjectCountEnd();
 				
 				
@@ -2010,7 +2010,7 @@
 			var count = this.objects.length,
 			var count = this.objects.length,
 				parent = this.parent;
 				parent = this.parent;
 			
 			
-			while( parent instanceof THREE.OctreeNode ) {
+			while ( parent instanceof THREE.OctreeNode ) {
 				
 				
 				count += parent.objects.length;
 				count += parent.objects.length;
 				parent = parent.parent;
 				parent = parent.parent;
@@ -2033,7 +2033,7 @@
 			console.log( ( this.parent ? space + ' ' : ' ' ), '+ objects ( ', this.objects.length, ' ) ', this.objects );
 			console.log( ( this.parent ? space + ' ' : ' ' ), '+ objects ( ', this.objects.length, ' ) ', this.objects );
 			console.log( ( this.parent ? space + ' ' : ' ' ), '+ children ( ', this.nodesIndices.length, ' )', this.nodesIndices, this.nodesByIndex );
 			console.log( ( this.parent ? space + ' ' : ' ' ), '+ children ( ', this.nodesIndices.length, ' )', this.nodesIndices, this.nodesByIndex );
 			
 			
-			for ( i = 0, l = this.nodesIndices.length; i < l; i++ ) {
+			for ( i = 0, l = this.nodesIndices.length; i < l; i ++ ) {
 				
 				
 				node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 				node = this.nodesByIndex[ this.nodesIndices[ i ] ];
 				
 				
@@ -2101,7 +2101,7 @@
 		var i, il,
 		var i, il,
 			intersects = [];
 			intersects = [];
 		
 		
-		for ( i = 0, il = objects.length; i < il; i++ ) {
+		for ( i = 0, il = objects.length; i < il; i ++ ) {
 			
 			
 			intersects = intersects.concat( this.intersectOctreeObject( objects[ i ], recursive ) );
 			intersects = intersects.concat( this.intersectOctreeObject( objects[ i ], recursive ) );
 		
 		

+ 6 - 6
examples/js/ParametricGeometries.js

@@ -48,9 +48,9 @@ THREE.ParametricGeometries = {
 		var x, y, z;
 		var x, y, z;
 
 
 		var a = 2;
 		var a = 2;
-		x = Math.cos(v) * (a + u * Math.cos(v/2));
-		y = Math.sin(v) * (a + u * Math.cos(v/2));
-		z = u * Math.sin(v/2);
+		x = Math.cos(v) * (a + u * Math.cos(v / 2));
+		y = Math.sin(v) * (a + u * Math.cos(v / 2));
+		z = u * Math.sin(v / 2);
 		return new THREE.Vector3(x, y, z);
 		return new THREE.Vector3(x, y, z);
 
 
 	},
 	},
@@ -108,9 +108,9 @@ THREE.ParametricGeometries.TubeGeometry = function(path, segments, radius, segme
 		binormals = frames.binormals;
 		binormals = frames.binormals;
 
 
 		// proxy internals
 		// proxy internals
-		this.tangents = tangents;
-		this.normals = normals;
-		this.binormals = binormals;
+	this.tangents = tangents;
+	this.normals = normals;
+	this.binormals = binormals;
 
 
 
 
 
 

+ 11 - 10
examples/js/ShaderDeferred.js

@@ -147,6 +147,7 @@ THREE.ShaderDeferred = {
 			"uniform float wrapAround;",
 			"uniform float wrapAround;",
 			"uniform float additiveSpecular;",
 			"uniform float additiveSpecular;",
 
 
+			THREE.ShaderChunk[ "common" ],
 			THREE.ShaderChunk[ "color_pars_fragment" ],
 			THREE.ShaderChunk[ "color_pars_fragment" ],
 			THREE.ShaderChunk[ "map_pars_fragment" ],
 			THREE.ShaderChunk[ "map_pars_fragment" ],
 			THREE.ShaderChunk[ "lightmap_pars_fragment" ],
 			THREE.ShaderChunk[ "lightmap_pars_fragment" ],
@@ -186,7 +187,8 @@ THREE.ShaderDeferred = {
 
 
 				"const float opacity = 1.0;",
 				"const float opacity = 1.0;",
 
 
-				"gl_FragColor = vec4( diffuse, opacity );",
+				"vec3 outgoingLight = vec3( 0.0 );",	// outgoing light does not have an alpha, the surface does
+				"vec4 diffuseColor = vec4( diffuse, opacity );",
 
 
 				THREE.ShaderChunk[ "map_fragment" ],
 				THREE.ShaderChunk[ "map_fragment" ],
 				THREE.ShaderChunk[ "alphatest_fragment" ],
 				THREE.ShaderChunk[ "alphatest_fragment" ],
@@ -194,6 +196,8 @@ THREE.ShaderDeferred = {
 				THREE.ShaderChunk[ "lightmap_fragment" ],
 				THREE.ShaderChunk[ "lightmap_fragment" ],
 				THREE.ShaderChunk[ "color_fragment" ],
 				THREE.ShaderChunk[ "color_fragment" ],
 
 
+				"outgoingLight = diffuseColor.rgb;",
+
 				"#ifdef USE_ENVMAP",
 				"#ifdef USE_ENVMAP",
 
 
 					"vec2 texCoord = gl_FragCoord.xy / vec2( viewWidth, viewHeight );",
 					"vec2 texCoord = gl_FragCoord.xy / vec2( viewWidth, viewHeight );",
@@ -225,23 +229,19 @@ THREE.ShaderDeferred = {
 
 
 					"#endif",
 					"#endif",
 
 
-					"#ifdef GAMMA_INPUT",
-
-						"cubeColor.xyz *= cubeColor.xyz;",
-
-					"#endif",
+					"cubeColor.xyz = inputToLinear( cubeColor.xyz );",
 
 
 					"if ( combine == 1 ) {",
 					"if ( combine == 1 ) {",
 
 
-						"gl_FragColor.xyz = mix( gl_FragColor.xyz, cubeColor.xyz, specularStrength * reflectivity );",
+						"outgoingLight = mix( outgoingLight, cubeColor.xyz, specularStrength * reflectivity );",
 
 
 					"} else if ( combine == 2 ) {",
 					"} else if ( combine == 2 ) {",
 
 
-						"gl_FragColor.xyz += cubeColor.xyz * specularStrength * reflectivity;",
+						"outgoingLight += cubeColor.xyz * specularStrength * reflectivity;",
 
 
 					"} else {",
 					"} else {",
 
 
-						"gl_FragColor.xyz = mix( gl_FragColor.xyz, gl_FragColor.xyz * cubeColor.xyz, specularStrength * reflectivity );",
+						"outgoingLight = mix( outgoingLight, diffuseColor.xyz * cubeColor.xyz, specularStrength * reflectivity );",
 
 
 					"}",
 					"}",
 
 
@@ -270,7 +270,7 @@ THREE.ShaderDeferred = {
 
 
 				// diffuse color
 				// diffuse color
 
 
-				"gl_FragColor.x = vec3_to_float( compressionScale * gl_FragColor.xyz );",
+				"gl_FragColor.x = vec3_to_float( compressionScale * outgoingLight );",
 
 
 				// specular color
 				// specular color
 
 
@@ -308,6 +308,7 @@ THREE.ShaderDeferred = {
 
 
 		vertexShader : [
 		vertexShader : [
 
 
+			THREE.ShaderChunk[ "common" ],
 			THREE.ShaderChunk[ "map_pars_vertex" ],
 			THREE.ShaderChunk[ "map_pars_vertex" ],
 			THREE.ShaderChunk[ "lightmap_pars_vertex" ],
 			THREE.ShaderChunk[ "lightmap_pars_vertex" ],
 			THREE.ShaderChunk[ "color_pars_vertex" ],
 			THREE.ShaderChunk[ "color_pars_vertex" ],

+ 54 - 92
examples/js/ShaderSkin.js

@@ -38,7 +38,6 @@ THREE.ShaderSkin = {
 
 
 			"diffuse":  { type: "c", value: new THREE.Color( 0xeeeeee ) },
 			"diffuse":  { type: "c", value: new THREE.Color( 0xeeeeee ) },
 			"specular": { type: "c", value: new THREE.Color( 0x111111 ) },
 			"specular": { type: "c", value: new THREE.Color( 0x111111 ) },
-			"ambient":  { type: "c", value: new THREE.Color( 0x050505 ) },
 			"opacity": 	  { type: "f", value: 1 },
 			"opacity": 	  { type: "f", value: 1 },
 
 
 			"uRoughness": 	  		{ type: "f", value: 0.15 },
 			"uRoughness": 	  		{ type: "f", value: 0.15 },
@@ -65,7 +64,6 @@ THREE.ShaderSkin = {
 			"uniform bool enableBump;",
 			"uniform bool enableBump;",
 			"uniform bool enableSpecular;",
 			"uniform bool enableSpecular;",
 
 
-			"uniform vec3 ambient;",
 			"uniform vec3 diffuse;",
 			"uniform vec3 diffuse;",
 			"uniform vec3 specular;",
 			"uniform vec3 specular;",
 			"uniform float opacity;",
 			"uniform float opacity;",
@@ -105,11 +103,13 @@ THREE.ShaderSkin = {
 				"uniform vec3 pointLightColor[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightColor[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
+				"uniform float pointLightDecay[ MAX_POINT_LIGHTS ];",
 
 
 			"#endif",
 			"#endif",
 
 
 			"varying vec3 vViewPosition;",
 			"varying vec3 vViewPosition;",
 
 
+			THREE.ShaderChunk[ "common" ],
 			THREE.ShaderChunk[ "shadowmap_pars_fragment" ],
 			THREE.ShaderChunk[ "shadowmap_pars_fragment" ],
 			THREE.ShaderChunk[ "fog_pars_fragment" ],
 			THREE.ShaderChunk[ "fog_pars_fragment" ],
 			THREE.ShaderChunk[ "bumpmap_pars_fragment" ],
 			THREE.ShaderChunk[ "bumpmap_pars_fragment" ],
@@ -159,12 +159,13 @@ THREE.ShaderSkin = {
 
 
 			"void main() {",
 			"void main() {",
 
 
-				"gl_FragColor = vec4( vec3( 1.0 ), opacity );",
+				"vec3 outgoingLight = vec3( 0.0 );",	// outgoing light does not have an alpha, the surface does
+				"vec4 diffuseColor = vec4( diffuse, opacity );",
 
 
 				"vec4 colDiffuse = texture2D( tDiffuse, vUv );",
 				"vec4 colDiffuse = texture2D( tDiffuse, vUv );",
 				"colDiffuse.rgb *= colDiffuse.rgb;",
 				"colDiffuse.rgb *= colDiffuse.rgb;",
 
 
-				"gl_FragColor = gl_FragColor * colDiffuse;",
+				"diffuseColor = diffuseColor * colDiffuse;",
 
 
 				"vec3 normal = normalize( vNormal );",
 				"vec3 normal = normalize( vNormal );",
 				"vec3 viewPosition = normalize( vViewPosition );",
 				"vec3 viewPosition = normalize( vViewPosition );",
@@ -190,22 +191,18 @@ THREE.ShaderSkin = {
 
 
 				// point lights
 				// point lights
 
 
-				"vec3 specularTotal = vec3( 0.0 );",
+				"vec3 totalSpecularLight = vec3( 0.0 );",
+				"vec3 totalDiffuseLight = vec3( 0.0 );",
 
 
 				"#if MAX_POINT_LIGHTS > 0",
 				"#if MAX_POINT_LIGHTS > 0",
 
 
-					"vec3 pointTotal = vec3( 0.0 );",
-
 					"for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {",
 					"for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {",
 
 
 						"vec4 lPosition = viewMatrix * vec4( pointLightPosition[ i ], 1.0 );",
 						"vec4 lPosition = viewMatrix * vec4( pointLightPosition[ i ], 1.0 );",
 
 
 						"vec3 lVector = lPosition.xyz + vViewPosition.xyz;",
 						"vec3 lVector = lPosition.xyz + vViewPosition.xyz;",
 
 
-						"float lDistance = 1.0;",
-
-						"if ( pointLightDistance[ i ] > 0.0 )",
-							"lDistance = 1.0 - min( ( length( lVector ) / pointLightDistance[ i ] ), 1.0 );",
+						"float attenuation = calcLightAttenuation( length( lVector ), pointLightDistance[ i ], pointLightDecay[i] );",
 
 
 						"lVector = normalize( lVector );",
 						"lVector = normalize( lVector );",
 
 
@@ -215,8 +212,8 @@ THREE.ShaderSkin = {
 
 
 						"float pointSpecularWeight = KS_Skin_Specular( normal, lVector, viewPosition, uRoughness, uSpecularBrightness );",
 						"float pointSpecularWeight = KS_Skin_Specular( normal, lVector, viewPosition, uRoughness, uSpecularBrightness );",
 
 
-						"pointTotal    += lDistance * diffuse * pointLightColor[ i ] * pointDiffuseWeight;",
-						"specularTotal += lDistance * specular * pointLightColor[ i ] * pointSpecularWeight * specularStrength;",
+						"totalDiffuseLight += attenuation * pointLightColor[ i ] * pointDiffuseWeight;",
+						"totalSpecularLight += attenuation * specular * pointLightColor[ i ] * pointSpecularWeight * specularStrength;",
 
 
 					"}",
 					"}",
 
 
@@ -226,22 +223,18 @@ THREE.ShaderSkin = {
 
 
 				"#if MAX_DIR_LIGHTS > 0",
 				"#if MAX_DIR_LIGHTS > 0",
 
 
-					"vec3 dirTotal = vec3( 0.0 );",
-
 					"for( int i = 0; i < MAX_DIR_LIGHTS; i++ ) {",
 					"for( int i = 0; i < MAX_DIR_LIGHTS; i++ ) {",
 
 
-						"vec4 lDirection = viewMatrix * vec4( directionalLightDirection[ i ], 0.0 );",
-
-						"vec3 dirVector = normalize( lDirection.xyz );",
+						"vec3 dirVector = transformDirection( directionalLightDirection[ i ], viewMatrix );",
 
 
 						"float dirDiffuseWeightFull = max( dot( normal, dirVector ), 0.0 );",
 						"float dirDiffuseWeightFull = max( dot( normal, dirVector ), 0.0 );",
 						"float dirDiffuseWeightHalf = max( 0.5 * dot( normal, dirVector ) + 0.5, 0.0 );",
 						"float dirDiffuseWeightHalf = max( 0.5 * dot( normal, dirVector ) + 0.5, 0.0 );",
 						"vec3 dirDiffuseWeight = mix( vec3 ( dirDiffuseWeightFull ), vec3( dirDiffuseWeightHalf ), uWrapRGB );",
 						"vec3 dirDiffuseWeight = mix( vec3 ( dirDiffuseWeightFull ), vec3( dirDiffuseWeightHalf ), uWrapRGB );",
 
 
-						"float dirSpecularWeight =  KS_Skin_Specular( normal, dirVector, viewPosition, uRoughness, uSpecularBrightness );",
+						"float dirSpecularWeight = KS_Skin_Specular( normal, dirVector, viewPosition, uRoughness, uSpecularBrightness );",
 
 
-						"dirTotal 	   += diffuse * directionalLightColor[ i ] * dirDiffuseWeight;",
-						"specularTotal += specular * directionalLightColor[ i ] * dirSpecularWeight * specularStrength;",
+						"totalDiffuseLight += directionalLightColor[ i ] * dirDiffuseWeight;",
+						"totalSpecularLight += specular * directionalLightColor[ i ] * dirSpecularWeight * specularStrength;",
 
 
 					"}",
 					"}",
 
 
@@ -251,17 +244,14 @@ THREE.ShaderSkin = {
 
 
 				"#if MAX_HEMI_LIGHTS > 0",
 				"#if MAX_HEMI_LIGHTS > 0",
 
 
-					"vec3 hemiTotal = vec3( 0.0 );",
-
 					"for ( int i = 0; i < MAX_HEMI_LIGHTS; i ++ ) {",
 					"for ( int i = 0; i < MAX_HEMI_LIGHTS; i ++ ) {",
 
 
-						"vec4 lDirection = viewMatrix * vec4( hemisphereLightDirection[ i ], 0.0 );",
-						"vec3 lVector = normalize( lDirection.xyz );",
+						"vec3 lVector = transformDirection( hemisphereLightDirection[ i ], viewMatrix );",
 
 
 						"float dotProduct = dot( normal, lVector );",
 						"float dotProduct = dot( normal, lVector );",
 						"float hemiDiffuseWeight = 0.5 * dotProduct + 0.5;",
 						"float hemiDiffuseWeight = 0.5 * dotProduct + 0.5;",
 
 
-						"hemiTotal += diffuse * mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight );",
+						"totalDiffuseLight += mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight );",
 
 
 						// specular (sky light)
 						// specular (sky light)
 
 
@@ -273,34 +263,21 @@ THREE.ShaderSkin = {
 						"vec3 lVectorGround = -lVector;",
 						"vec3 lVectorGround = -lVector;",
 						"hemiSpecularWeight += KS_Skin_Specular( normal, lVectorGround, viewPosition, uRoughness, uSpecularBrightness );",
 						"hemiSpecularWeight += KS_Skin_Specular( normal, lVectorGround, viewPosition, uRoughness, uSpecularBrightness );",
 
 
-						"specularTotal += specular * mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight ) * hemiSpecularWeight * specularStrength;",
+						"totalSpecularLight += specular * mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight ) * hemiSpecularWeight * specularStrength;",
 
 
 					"}",
 					"}",
 
 
 				"#endif",
 				"#endif",
 
 
-				// all lights contribution summation
-
-				"vec3 totalLight = vec3( 0.0 );",
-
-				"#if MAX_DIR_LIGHTS > 0",
-					"totalLight += dirTotal;",
-				"#endif",
-
-				"#if MAX_POINT_LIGHTS > 0",
-					"totalLight += pointTotal;",
-				"#endif",
-
-				"#if MAX_HEMI_LIGHTS > 0",
-					"totalLight += hemiTotal;",
-				"#endif",
-
-				"gl_FragColor.xyz = gl_FragColor.xyz * ( totalLight + ambientLightColor * ambient ) + specularTotal;",
+				"outgoingLight += diffuseColor.xyz * ( totalDiffuseLight + ambientLightColor * diffuse ) + totalSpecularLight;",
 
 
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
 				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
 				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
 				THREE.ShaderChunk[ "fog_fragment" ],
 				THREE.ShaderChunk[ "fog_fragment" ],
 
 
+				"gl_FragColor = vec4( outgoingLight, diffuseColor.a );",	// TODO, this should be pre-multiplied to allow for bright highlights on very transparent objects
+
+
 			"}"
 			"}"
 
 
 		].join("\n"),
 		].join("\n"),
@@ -314,6 +291,7 @@ THREE.ShaderSkin = {
 
 
 			"varying vec3 vViewPosition;",
 			"varying vec3 vViewPosition;",
 
 
+			THREE.ShaderChunk[ "common" ],
 			THREE.ShaderChunk[ "shadowmap_pars_vertex" ],
 			THREE.ShaderChunk[ "shadowmap_pars_vertex" ],
 
 
 			"void main() {",
 			"void main() {",
@@ -377,7 +355,6 @@ THREE.ShaderSkin = {
 
 
 			"diffuse":  { type: "c", value: new THREE.Color( 0xeeeeee ) },
 			"diffuse":  { type: "c", value: new THREE.Color( 0xeeeeee ) },
 			"specular": { type: "c", value: new THREE.Color( 0x111111 ) },
 			"specular": { type: "c", value: new THREE.Color( 0x111111 ) },
-			"ambient":  { type: "c", value: new THREE.Color( 0x050505 ) },
 			"opacity": 	  { type: "f", value: 1 },
 			"opacity": 	  { type: "f", value: 1 },
 
 
 			"uRoughness": 	  		{ type: "f", value: 0.15 },
 			"uRoughness": 	  		{ type: "f", value: 0.15 },
@@ -389,7 +366,6 @@ THREE.ShaderSkin = {
 
 
 		fragmentShader: [
 		fragmentShader: [
 
 
-			"uniform vec3 ambient;",
 			"uniform vec3 diffuse;",
 			"uniform vec3 diffuse;",
 			"uniform vec3 specular;",
 			"uniform vec3 specular;",
 			"uniform float opacity;",
 			"uniform float opacity;",
@@ -430,6 +406,7 @@ THREE.ShaderSkin = {
 
 
 			"varying vec3 vViewPosition;",
 			"varying vec3 vViewPosition;",
 
 
+			THREE.ShaderChunk[ "common" ],
 			THREE.ShaderChunk[ "fog_pars_fragment" ],
 			THREE.ShaderChunk[ "fog_pars_fragment" ],
 
 
 			"float fresnelReflectance( vec3 H, vec3 V, float F0 ) {",
 			"float fresnelReflectance( vec3 H, vec3 V, float F0 ) {",
@@ -474,9 +451,9 @@ THREE.ShaderSkin = {
 
 
 			"void main() {",
 			"void main() {",
 
 
-				"gl_FragColor = vec4( 1.0 );",
+				"vec3 outgoingLight = vec3( 0.0 );",	// outgoing light does not have an alpha, the surface does
+				"vec4 diffuseColor = vec4( diffuse, opacity );",
 
 
-				"vec4 mColor = vec4( diffuse, opacity );",
 				"vec4 mSpecular = vec4( specular, opacity );",
 				"vec4 mSpecular = vec4( specular, opacity );",
 
 
 				"vec3 normalTex = texture2D( tNormal, vUv ).xyz * 2.0 - 1.0;",
 				"vec3 normalTex = texture2D( tNormal, vUv ).xyz * 2.0 - 1.0;",
@@ -486,7 +463,7 @@ THREE.ShaderSkin = {
 				"vec4 colDiffuse = texture2D( tDiffuse, vUv );",
 				"vec4 colDiffuse = texture2D( tDiffuse, vUv );",
 				"colDiffuse *= colDiffuse;",
 				"colDiffuse *= colDiffuse;",
 
 
-				"gl_FragColor = gl_FragColor * colDiffuse;",
+				"diffuseColor *= colDiffuse;",
 
 
 				"mat3 tsb = mat3( vTangent, vBinormal, vNormal );",
 				"mat3 tsb = mat3( vTangent, vBinormal, vNormal );",
 				"vec3 finalNormal = tsb * normalTex;",
 				"vec3 finalNormal = tsb * normalTex;",
@@ -496,12 +473,11 @@ THREE.ShaderSkin = {
 
 
 				// point lights
 				// point lights
 
 
-				"vec3 specularTotal = vec3( 0.0 );",
+				"vec3 totalDiffuseLight = vec3( 0.0 );",
+				"vec3 totalSpecularLight = vec3( 0.0 );",
 
 
 				"#if MAX_POINT_LIGHTS > 0",
 				"#if MAX_POINT_LIGHTS > 0",
 
 
-					"vec4 pointTotal = vec4( vec3( 0.0 ), 1.0 );",
-
 					"for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {",
 					"for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {",
 
 
 						"vec3 pointVector = normalize( vPointLight[ i ].xyz );",
 						"vec3 pointVector = normalize( vPointLight[ i ].xyz );",
@@ -509,10 +485,10 @@ THREE.ShaderSkin = {
 
 
 						"float pointDiffuseWeight = max( dot( normal, pointVector ), 0.0 );",
 						"float pointDiffuseWeight = max( dot( normal, pointVector ), 0.0 );",
 
 
-						"pointTotal  += pointDistance * vec4( pointLightColor[ i ], 1.0 ) * ( mColor * pointDiffuseWeight );",
+						"totalDiffuseLight += pointDistance * pointLightColor[ i ] * pointDiffuseWeight;",
 
 
 						"if ( passID == 1 )",
 						"if ( passID == 1 )",
-							"specularTotal += pointDistance * mSpecular.xyz * pointLightColor[ i ] * KS_Skin_Specular( normal, pointVector, viewPosition, uRoughness, uSpecularBrightness );",
+							"totalSpecularLight += pointDistance * mSpecular.xyz * pointLightColor[ i ] * KS_Skin_Specular( normal, pointVector, viewPosition, uRoughness, uSpecularBrightness );",
 
 
 					"}",
 					"}",
 
 
@@ -522,42 +498,27 @@ THREE.ShaderSkin = {
 
 
 				"#if MAX_DIR_LIGHTS > 0",
 				"#if MAX_DIR_LIGHTS > 0",
 
 
-					"vec4 dirTotal = vec4( vec3( 0.0 ), 1.0 );",
-
 					"for( int i = 0; i < MAX_DIR_LIGHTS; i++ ) {",
 					"for( int i = 0; i < MAX_DIR_LIGHTS; i++ ) {",
 
 
-						"vec4 lDirection = viewMatrix * vec4( directionalLightDirection[ i ], 0.0 );",
-
-						"vec3 dirVector = normalize( lDirection.xyz );",
+						"vec3 dirVector = transformDirection( directionalLightDirection[ i ], viewMatrix );",
 
 
 						"float dirDiffuseWeight = max( dot( normal, dirVector ), 0.0 );",
 						"float dirDiffuseWeight = max( dot( normal, dirVector ), 0.0 );",
 
 
-						"dirTotal  += vec4( directionalLightColor[ i ], 1.0 ) * ( mColor * dirDiffuseWeight );",
+						"totalDiffuseLight += directionalLightColor[ i ] * dirDiffuseWeight;",
 
 
 						"if ( passID == 1 )",
 						"if ( passID == 1 )",
-							"specularTotal += mSpecular.xyz * directionalLightColor[ i ] * KS_Skin_Specular( normal, dirVector, viewPosition, uRoughness, uSpecularBrightness );",
+							"totalSpecularLight += mSpecular.xyz * directionalLightColor[ i ] * KS_Skin_Specular( normal, dirVector, viewPosition, uRoughness, uSpecularBrightness );",
 
 
 					"}",
 					"}",
 
 
 				"#endif",
 				"#endif",
 
 
-				// all lights contribution summation
-
-				"vec4 totalLight = vec4( vec3( 0.0 ), opacity );",
-
-				"#if MAX_DIR_LIGHTS > 0",
-					"totalLight += dirTotal;",
-				"#endif",
-
-				"#if MAX_POINT_LIGHTS > 0",
-					"totalLight += pointTotal;",
-				"#endif",
 
 
-				"gl_FragColor = gl_FragColor * totalLight;",
+				"outgoingLight += diffuseColor.rgb * ( totalDiffuseLight + totalSpecularLight );",
 
 
 				"if ( passID == 0 ) {",
 				"if ( passID == 0 ) {",
 
 
-					"gl_FragColor = vec4( sqrt( gl_FragColor.xyz ), gl_FragColor.w );",
+					"outgoingLight = sqrt( outgoingLight );",
 
 
 				"} else if ( passID == 1 ) {",
 				"} else if ( passID == 1 ) {",
 
 
@@ -565,11 +526,11 @@ THREE.ShaderSkin = {
 
 
 					"#ifdef VERSION1",
 					"#ifdef VERSION1",
 
 
-						"vec3 nonblurColor = sqrt( gl_FragColor.xyz );",
+						"vec3 nonblurColor = sqrt(outgoingLight );",
 
 
 					"#else",
 					"#else",
 
 
-						"vec3 nonblurColor = gl_FragColor.xyz;",
+						"vec3 nonblurColor = outgoingLight;",
 
 
 					"#endif",
 					"#endif",
 
 
@@ -586,20 +547,19 @@ THREE.ShaderSkin = {
 					//"gl_FragColor = vec4( vec3( 0.25, 0.6, 0.8 ) * nonblurColor + vec3( 0.15, 0.25, 0.2 ) * blur1Color + vec3( 0.15, 0.15, 0.0 ) * blur2Color + vec3( 0.45, 0.0, 0.0 ) * blur3Color, gl_FragColor.w );",
 					//"gl_FragColor = vec4( vec3( 0.25, 0.6, 0.8 ) * nonblurColor + vec3( 0.15, 0.25, 0.2 ) * blur1Color + vec3( 0.15, 0.15, 0.0 ) * blur2Color + vec3( 0.45, 0.0, 0.0 ) * blur3Color, gl_FragColor.w );",
 
 
 
 
-					"gl_FragColor = vec4( vec3( 0.22,  0.437, 0.635 ) * nonblurColor + ",
+					"outgoingLight = vec3( vec3( 0.22,  0.437, 0.635 ) * nonblurColor + ",
 										 "vec3( 0.101, 0.355, 0.365 ) * blur1Color + ",
 										 "vec3( 0.101, 0.355, 0.365 ) * blur1Color + ",
 										 "vec3( 0.119, 0.208, 0.0 )   * blur2Color + ",
 										 "vec3( 0.119, 0.208, 0.0 )   * blur2Color + ",
 										 "vec3( 0.114, 0.0,   0.0 )   * blur3Color + ",
 										 "vec3( 0.114, 0.0,   0.0 )   * blur3Color + ",
-										 "vec3( 0.444, 0.0,   0.0 )   * blur4Color",
-										 ", gl_FragColor.w );",
+										 "vec3( 0.444, 0.0,   0.0 )   * blur4Color );",
 
 
-					"gl_FragColor.xyz *= pow( colDiffuse.xyz, vec3( 0.5 ) );",
+					"outgoingLight *= sqrt( colDiffuse.xyz );",
 
 
-					"gl_FragColor.xyz += ambientLightColor * ambient * colDiffuse.xyz + specularTotal;",
+					"outgoingLight += ambientLightColor * diffuse * colDiffuse.xyz + totalSpecularLight;",
 
 
 					"#ifndef VERSION1",
 					"#ifndef VERSION1",
 
 
-						"gl_FragColor.xyz = sqrt( gl_FragColor.xyz );",
+						"outgoingLight = sqrt( outgoingLight );",
 
 
 					"#endif",
 					"#endif",
 
 
@@ -607,6 +567,8 @@ THREE.ShaderSkin = {
 
 
 				THREE.ShaderChunk[ "fog_fragment" ],
 				THREE.ShaderChunk[ "fog_fragment" ],
 
 
+				"gl_FragColor = vec4( outgoingLight, diffuseColor.a );",	// TODO, this should be pre-multiplied to allow for bright highlights on very transparent objects
+
 			"}"
 			"}"
 
 
 		].join("\n"),
 		].join("\n"),
@@ -632,6 +594,7 @@ THREE.ShaderSkin = {
 
 
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
+				"uniform float pointLightDecay[ MAX_POINT_LIGHTS ];",
 
 
 				"varying vec4 vPointLight[ MAX_POINT_LIGHTS ];",
 				"varying vec4 vPointLight[ MAX_POINT_LIGHTS ];",
 
 
@@ -639,6 +602,8 @@ THREE.ShaderSkin = {
 
 
 			"varying vec3 vViewPosition;",
 			"varying vec3 vViewPosition;",
 
 
+			THREE.ShaderChunk[ "common" ],
+
 			"void main() {",
 			"void main() {",
 
 
 				"vec4 worldPosition = modelMatrix * vec4( position, 1.0 );",
 				"vec4 worldPosition = modelMatrix * vec4( position, 1.0 );",
@@ -668,14 +633,11 @@ THREE.ShaderSkin = {
 
 
 						"vec3 lVector = lPosition.xyz - mvPosition.xyz;",
 						"vec3 lVector = lPosition.xyz - mvPosition.xyz;",
 
 
-						"float lDistance = 1.0;",
-
-						"if ( pointLightDistance[ i ] > 0.0 )",
-							"lDistance = 1.0 - min( ( length( lVector ) / pointLightDistance[ i ] ), 1.0 );",
+						"float attenuation = calcLightAttenuation( length( lVector ), pointLightDistance[ i ], pointLightDecay[i] );",
 
 
 						"lVector = normalize( lVector );",
 						"lVector = normalize( lVector );",
 
 
-						"vPointLight[ i ] = vec4( lVector, lDistance );",
+						"vPointLight[ i ] = vec4( lVector, attenuation );",
 
 
 					"}",
 					"}",
 
 
@@ -721,6 +683,7 @@ THREE.ShaderSkin = {
 
 
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
+				"uniform float pointLightDecay[ MAX_POINT_LIGHTS ];",
 
 
 				"varying vec4 vPointLight[ MAX_POINT_LIGHTS ];",
 				"varying vec4 vPointLight[ MAX_POINT_LIGHTS ];",
 
 
@@ -728,6 +691,8 @@ THREE.ShaderSkin = {
 
 
 			"varying vec3 vViewPosition;",
 			"varying vec3 vViewPosition;",
 
 
+			THREE.ShaderChunk[ "common" ],
+
 			"void main() {",
 			"void main() {",
 
 
 				"vec4 worldPosition = modelMatrix * vec4( position, 1.0 );",
 				"vec4 worldPosition = modelMatrix * vec4( position, 1.0 );",
@@ -757,14 +722,11 @@ THREE.ShaderSkin = {
 
 
 						"vec3 lVector = lPosition.xyz - mvPosition.xyz;",
 						"vec3 lVector = lPosition.xyz - mvPosition.xyz;",
 
 
-						"float lDistance = 1.0;",
-
-						"if ( pointLightDistance[ i ] > 0.0 )",
-							"lDistance = 1.0 - min( ( length( lVector ) / pointLightDistance[ i ] ), 1.0 );",
+						"float attenuation = calcLightAttenuation( length( lVector ), pointLightDistance[ i ], pointLightDecay[i] );",
 
 
 						"lVector = normalize( lVector );",
 						"lVector = normalize( lVector );",
 
 
-						"vPointLight[ i ] = vec4( lVector, lDistance );",
+						"vPointLight[ i ] = vec4( lVector, attenuation );",
 
 
 					"}",
 					"}",
 
 

+ 25 - 59
examples/js/ShaderTerrain.js

@@ -42,7 +42,6 @@ THREE.ShaderTerrain = {
 
 
 			"diffuse": { type: "c", value: new THREE.Color( 0xeeeeee ) },
 			"diffuse": { type: "c", value: new THREE.Color( 0xeeeeee ) },
 			"specular": { type: "c", value: new THREE.Color( 0x111111 ) },
 			"specular": { type: "c", value: new THREE.Color( 0x111111 ) },
-			"ambient": { type: "c", value: new THREE.Color( 0x050505 ) },
 			"shininess": { type: "f", value: 30 },
 			"shininess": { type: "f", value: 30 },
 			"opacity": { type: "f", value: 1 },
 			"opacity": { type: "f", value: 1 },
 
 
@@ -57,7 +56,6 @@ THREE.ShaderTerrain = {
 
 
 		fragmentShader: [
 		fragmentShader: [
 
 
-			"uniform vec3 ambient;",
 			"uniform vec3 diffuse;",
 			"uniform vec3 diffuse;",
 			"uniform vec3 specular;",
 			"uniform vec3 specular;",
 			"uniform float shininess;",
 			"uniform float shininess;",
@@ -108,17 +106,20 @@ THREE.ShaderTerrain = {
 				"uniform vec3 pointLightColor[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightColor[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
 				"uniform float pointLightDistance[ MAX_POINT_LIGHTS ];",
+				"uniform float pointLightDecay[ MAX_POINT_LIGHTS ];",
 
 
 			"#endif",
 			"#endif",
 
 
 			"varying vec3 vViewPosition;",
 			"varying vec3 vViewPosition;",
 
 
+			THREE.ShaderChunk[ "common" ],
 			THREE.ShaderChunk[ "shadowmap_pars_fragment" ],
 			THREE.ShaderChunk[ "shadowmap_pars_fragment" ],
 			THREE.ShaderChunk[ "fog_pars_fragment" ],
 			THREE.ShaderChunk[ "fog_pars_fragment" ],
 
 
 			"void main() {",
 			"void main() {",
 
 
-				"gl_FragColor = vec4( vec3( 1.0 ), opacity );",
+				"vec3 outgoingLight = vec3( 0.0 );",	// outgoing light does not have an alpha, the surface does
+				"vec4 diffuseColor = vec4( diffuse, opacity );",
 
 
 				"vec3 specularTex = vec3( 1.0 );",
 				"vec3 specularTex = vec3( 1.0 );",
 
 
@@ -134,22 +135,18 @@ THREE.ShaderTerrain = {
 					"vec4 colDiffuse1 = texture2D( tDiffuse1, uvOverlay );",
 					"vec4 colDiffuse1 = texture2D( tDiffuse1, uvOverlay );",
 					"vec4 colDiffuse2 = texture2D( tDiffuse2, uvOverlay );",
 					"vec4 colDiffuse2 = texture2D( tDiffuse2, uvOverlay );",
 
 
-					"#ifdef GAMMA_INPUT",
+					"colDiffuse1.xyz = inputToLinear( colDiffuse1.xyz );",
+					"colDiffuse2.xyz = inputToLinear( colDiffuse2.xyz );",
 
 
-						"colDiffuse1.xyz *= colDiffuse1.xyz;",
-						"colDiffuse2.xyz *= colDiffuse2.xyz;",
-
-					"#endif",
-
-					"gl_FragColor = gl_FragColor * mix ( colDiffuse1, colDiffuse2, 1.0 - texture2D( tDisplacement, uvBase ) );",
+					"diffuseColor *= mix ( colDiffuse1, colDiffuse2, 1.0 - texture2D( tDisplacement, uvBase ) );",
 
 
 				" } else if( enableDiffuse1 ) {",
 				" } else if( enableDiffuse1 ) {",
 
 
-					"gl_FragColor = gl_FragColor * texture2D( tDiffuse1, uvOverlay );",
+					"diffuseColor *= texture2D( tDiffuse1, uvOverlay );",
 
 
 				"} else if( enableDiffuse2 ) {",
 				"} else if( enableDiffuse2 ) {",
 
 
-					"gl_FragColor = gl_FragColor * texture2D( tDiffuse2, uvOverlay );",
+					"diffuseColor *= texture2D( tDiffuse2, uvOverlay );",
 
 
 				"}",
 				"}",
 
 
@@ -162,34 +159,31 @@ THREE.ShaderTerrain = {
 				"vec3 normal = normalize( finalNormal );",
 				"vec3 normal = normalize( finalNormal );",
 				"vec3 viewPosition = normalize( vViewPosition );",
 				"vec3 viewPosition = normalize( vViewPosition );",
 
 
+				"vec3 totalDiffuseLight = vec3( 0.0 );",
+				"vec3 totalSpecularLight = vec3( 0.0 );",
+
 				// point lights
 				// point lights
 
 
 				"#if MAX_POINT_LIGHTS > 0",
 				"#if MAX_POINT_LIGHTS > 0",
 
 
-					"vec3 pointDiffuse = vec3( 0.0 );",
-					"vec3 pointSpecular = vec3( 0.0 );",
-
 					"for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {",
 					"for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {",
 
 
 						"vec4 lPosition = viewMatrix * vec4( pointLightPosition[ i ], 1.0 );",
 						"vec4 lPosition = viewMatrix * vec4( pointLightPosition[ i ], 1.0 );",
 						"vec3 lVector = lPosition.xyz + vViewPosition.xyz;",
 						"vec3 lVector = lPosition.xyz + vViewPosition.xyz;",
 
 
-						"float lDistance = 1.0;",
-						"if ( pointLightDistance[ i ] > 0.0 )",
-							"lDistance = 1.0 - min( ( length( lVector ) / pointLightDistance[ i ] ), 1.0 );",
+						"float attenuation = calcLightAttenuation( length( lVector ), pointLightDistance[ i ], pointLightDecay[i] );",
 
 
 						"lVector = normalize( lVector );",
 						"lVector = normalize( lVector );",
 
 
 						"vec3 pointHalfVector = normalize( lVector + viewPosition );",
 						"vec3 pointHalfVector = normalize( lVector + viewPosition );",
-						"float pointDistance = lDistance;",
 
 
 						"float pointDotNormalHalf = max( dot( normal, pointHalfVector ), 0.0 );",
 						"float pointDotNormalHalf = max( dot( normal, pointHalfVector ), 0.0 );",
 						"float pointDiffuseWeight = max( dot( normal, lVector ), 0.0 );",
 						"float pointDiffuseWeight = max( dot( normal, lVector ), 0.0 );",
 
 
 						"float pointSpecularWeight = specularTex.r * max( pow( pointDotNormalHalf, shininess ), 0.0 );",
 						"float pointSpecularWeight = specularTex.r * max( pow( pointDotNormalHalf, shininess ), 0.0 );",
 
 
-						"pointDiffuse += pointDistance * pointLightColor[ i ] * diffuse * pointDiffuseWeight;",
-						"pointSpecular += pointDistance * pointLightColor[ i ] * specular * pointSpecularWeight * pointDiffuseWeight;",
+						"totalDiffuseLight += attenuation * pointLightColor[ i ] * pointDiffuseWeight;",
+						"totalSpecularLight += attenuation * pointLightColor[ i ] * specular * pointSpecularWeight * pointDiffuseWeight;",
 
 
 					"}",
 					"}",
 
 
@@ -204,9 +198,7 @@ THREE.ShaderTerrain = {
 
 
 					"for( int i = 0; i < MAX_DIR_LIGHTS; i++ ) {",
 					"for( int i = 0; i < MAX_DIR_LIGHTS; i++ ) {",
 
 
-						"vec4 lDirection = viewMatrix * vec4( directionalLightDirection[ i ], 0.0 );",
-
-						"vec3 dirVector = normalize( lDirection.xyz );",
+						"vec3 dirVector = transformDirection( directionalLightDirection[ i ], viewMatrix );",
 						"vec3 dirHalfVector = normalize( dirVector + viewPosition );",
 						"vec3 dirHalfVector = normalize( dirVector + viewPosition );",
 
 
 						"float dirDotNormalHalf = max( dot( normal, dirHalfVector ), 0.0 );",
 						"float dirDotNormalHalf = max( dot( normal, dirHalfVector ), 0.0 );",
@@ -214,8 +206,8 @@ THREE.ShaderTerrain = {
 
 
 						"float dirSpecularWeight = specularTex.r * max( pow( dirDotNormalHalf, shininess ), 0.0 );",
 						"float dirSpecularWeight = specularTex.r * max( pow( dirDotNormalHalf, shininess ), 0.0 );",
 
 
-						"dirDiffuse += directionalLightColor[ i ] * diffuse * dirDiffuseWeight;",
-						"dirSpecular += directionalLightColor[ i ] * specular * dirSpecularWeight * dirDiffuseWeight;",
+						"totalDiffuseLight += directionalLightColor[ i ] * dirDiffuseWeight;",
+						"totalSpecularLight += directionalLightColor[ i ] * specular * dirSpecularWeight * dirDiffuseWeight;",
 
 
 					"}",
 					"}",
 
 
@@ -226,19 +218,18 @@ THREE.ShaderTerrain = {
 				"#if MAX_HEMI_LIGHTS > 0",
 				"#if MAX_HEMI_LIGHTS > 0",
 
 
 					"vec3 hemiDiffuse  = vec3( 0.0 );",
 					"vec3 hemiDiffuse  = vec3( 0.0 );",
-					"vec3 hemiSpecular = vec3( 0.0 );" ,
+					"vec3 hemiSpecular = vec3( 0.0 );",
 
 
 					"for( int i = 0; i < MAX_HEMI_LIGHTS; i ++ ) {",
 					"for( int i = 0; i < MAX_HEMI_LIGHTS; i ++ ) {",
 
 
-						"vec4 lDirection = viewMatrix * vec4( hemisphereLightDirection[ i ], 0.0 );",
-						"vec3 lVector = normalize( lDirection.xyz );",
+						"vec3 lVector = transformDirection( hemisphereLightDirection[ i ], viewMatrix );",
 
 
 						// diffuse
 						// diffuse
 
 
 						"float dotProduct = dot( normal, lVector );",
 						"float dotProduct = dot( normal, lVector );",
 						"float hemiDiffuseWeight = 0.5 * dotProduct + 0.5;",
 						"float hemiDiffuseWeight = 0.5 * dotProduct + 0.5;",
 
 
-						"hemiDiffuse += diffuse * mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight );",
+						"totalDiffuseLight += mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight );",
 
 
 						// specular (sky light)
 						// specular (sky light)
 
 
@@ -256,45 +247,20 @@ THREE.ShaderTerrain = {
 						"float hemiDotNormalHalfGround = 0.5 * dot( normal, hemiHalfVectorGround ) + 0.5;",
 						"float hemiDotNormalHalfGround = 0.5 * dot( normal, hemiHalfVectorGround ) + 0.5;",
 						"hemiSpecularWeight += specularTex.r * max( pow( hemiDotNormalHalfGround, shininess ), 0.0 );",
 						"hemiSpecularWeight += specularTex.r * max( pow( hemiDotNormalHalfGround, shininess ), 0.0 );",
 
 
-						"hemiSpecular += specular * mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight ) * hemiSpecularWeight * hemiDiffuseWeight;",
+						"totalSpecularLight += specular * mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight ) * hemiSpecularWeight * hemiDiffuseWeight;",
 
 
 					"}",
 					"}",
 
 
 				"#endif",
 				"#endif",
 
 
-				// all lights contribution summation
-
-				"vec3 totalDiffuse = vec3( 0.0 );",
-				"vec3 totalSpecular = vec3( 0.0 );",
-
-				"#if MAX_DIR_LIGHTS > 0",
-
-					"totalDiffuse += dirDiffuse;",
-					"totalSpecular += dirSpecular;",
-
-				"#endif",
-
-				"#if MAX_HEMI_LIGHTS > 0",
-
-					"totalDiffuse += hemiDiffuse;",
-					"totalSpecular += hemiSpecular;",
-
-				"#endif",
-
-				"#if MAX_POINT_LIGHTS > 0",
-
-					"totalDiffuse += pointDiffuse;",
-					"totalSpecular += pointSpecular;",
-
-				"#endif",
-
-				//"gl_FragColor.xyz = gl_FragColor.xyz * ( totalDiffuse + ambientLightColor * ambient) + totalSpecular;",
-				"gl_FragColor.xyz = gl_FragColor.xyz * ( totalDiffuse + ambientLightColor * ambient + totalSpecular );",
+				"outgoingLight += diffuseColor.xyz * ( totalDiffuseLight + ambientLightColor + totalSpecularLight );",
 
 
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
 				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
 				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
 				THREE.ShaderChunk[ "fog_fragment" ],
 				THREE.ShaderChunk[ "fog_fragment" ],
 
 
+				"gl_FragColor = vec4( outgoingLight, diffuseColor.a );",	// TODO, this should be pre-multiplied to allow for bright highlights on very transparent objects
+
 			"}"
 			"}"
 
 
 		].join("\n"),
 		].join("\n"),

+ 233 - 233
examples/js/SimplexNoise.js

@@ -13,190 +13,190 @@
  */
  */
 var SimplexNoise = function(r) {
 var SimplexNoise = function(r) {
 	if (r == undefined) r = Math;
 	if (r == undefined) r = Math;
-  this.grad3 = [[1,1,0],[-1,1,0],[1,-1,0],[-1,-1,0], 
-                                 [1,0,1],[-1,0,1],[1,0,-1],[-1,0,-1], 
-                                 [0,1,1],[0,-1,1],[0,1,-1],[0,-1,-1]]; 
+	this.grad3 = [[ 1,1,0 ],[ -1,1,0 ],[ 1,-1,0 ],[ -1,-1,0 ], 
+                                 [ 1,0,1 ],[ -1,0,1 ],[ 1,0,-1 ],[ -1,0,-1 ], 
+                                 [ 0,1,1 ],[ 0,-1,1 ],[ 0,1,-1 ],[ 0,-1,-1 ]]; 
 
 
-  this.grad4 = [[0,1,1,1], [0,1,1,-1], [0,1,-1,1], [0,1,-1,-1],
-	     [0,-1,1,1], [0,-1,1,-1], [0,-1,-1,1], [0,-1,-1,-1],
-	     [1,0,1,1], [1,0,1,-1], [1,0,-1,1], [1,0,-1,-1],
-	     [-1,0,1,1], [-1,0,1,-1], [-1,0,-1,1], [-1,0,-1,-1],
-	     [1,1,0,1], [1,1,0,-1], [1,-1,0,1], [1,-1,0,-1],
-	     [-1,1,0,1], [-1,1,0,-1], [-1,-1,0,1], [-1,-1,0,-1],
-	     [1,1,1,0], [1,1,-1,0], [1,-1,1,0], [1,-1,-1,0],
-	     [-1,1,1,0], [-1,1,-1,0], [-1,-1,1,0], [-1,-1,-1,0]];
+	this.grad4 = [[ 0,1,1,1 ], [ 0,1,1,-1 ], [ 0,1,-1,1 ], [ 0,1,-1,-1 ],
+	     [ 0,-1,1,1 ], [ 0,-1,1,-1 ], [ 0,-1,-1,1 ], [ 0,-1,-1,-1 ],
+	     [ 1,0,1,1 ], [ 1,0,1,-1 ], [ 1,0,-1,1 ], [ 1,0,-1,-1 ],
+	     [ -1,0,1,1 ], [ -1,0,1,-1 ], [ -1,0,-1,1 ], [ -1,0,-1,-1 ],
+	     [ 1,1,0,1 ], [ 1,1,0,-1 ], [ 1,-1,0,1 ], [ 1,-1,0,-1 ],
+	     [ -1,1,0,1 ], [ -1,1,0,-1 ], [ -1,-1,0,1 ], [ -1,-1,0,-1 ],
+	     [ 1,1,1,0 ], [ 1,1,-1,0 ], [ 1,-1,1,0 ], [ 1,-1,-1,0 ],
+	     [ -1,1,1,0 ], [ -1,1,-1,0 ], [ -1,-1,1,0 ], [ -1,-1,-1,0 ]];
 
 
-  this.p = [];
-  for (var i=0; i<256; i++) {
-	  this.p[i] = Math.floor(r.random()*256);
-  }
+	this.p = [];
+	for (var i = 0; i < 256; i ++) {
+		this.p[i] = Math.floor(r.random() * 256);
+	}
   // To remove the need for index wrapping, double the permutation table length 
   // To remove the need for index wrapping, double the permutation table length 
-  this.perm = []; 
-  for(var i=0; i<512; i++) {
-		this.perm[i]=this.p[i & 255];
+	this.perm = []; 
+	for (var i = 0; i < 512; i ++) {
+		this.perm[i] = this.p[i & 255];
 	} 
 	} 
 
 
   // A lookup table to traverse the simplex around a given point in 4D. 
   // A lookup table to traverse the simplex around a given point in 4D. 
   // Details can be found where this table is used, in the 4D noise method. 
   // Details can be found where this table is used, in the 4D noise method. 
-  this.simplex = [ 
-    [0,1,2,3],[0,1,3,2],[0,0,0,0],[0,2,3,1],[0,0,0,0],[0,0,0,0],[0,0,0,0],[1,2,3,0], 
-    [0,2,1,3],[0,0,0,0],[0,3,1,2],[0,3,2,1],[0,0,0,0],[0,0,0,0],[0,0,0,0],[1,3,2,0], 
-    [0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0], 
-    [1,2,0,3],[0,0,0,0],[1,3,0,2],[0,0,0,0],[0,0,0,0],[0,0,0,0],[2,3,0,1],[2,3,1,0], 
-    [1,0,2,3],[1,0,3,2],[0,0,0,0],[0,0,0,0],[0,0,0,0],[2,0,3,1],[0,0,0,0],[2,1,3,0], 
-    [0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0], 
-    [2,0,1,3],[0,0,0,0],[0,0,0,0],[0,0,0,0],[3,0,1,2],[3,0,2,1],[0,0,0,0],[3,1,2,0], 
-    [2,1,0,3],[0,0,0,0],[0,0,0,0],[0,0,0,0],[3,1,0,2],[0,0,0,0],[3,2,0,1],[3,2,1,0]]; 
+	this.simplex = [ 
+    [ 0,1,2,3 ],[ 0,1,3,2 ],[ 0,0,0,0 ],[ 0,2,3,1 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 1,2,3,0 ], 
+    [ 0,2,1,3 ],[ 0,0,0,0 ],[ 0,3,1,2 ],[ 0,3,2,1 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 1,3,2,0 ], 
+    [ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ], 
+    [ 1,2,0,3 ],[ 0,0,0,0 ],[ 1,3,0,2 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 2,3,0,1 ],[ 2,3,1,0 ], 
+    [ 1,0,2,3 ],[ 1,0,3,2 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 2,0,3,1 ],[ 0,0,0,0 ],[ 2,1,3,0 ], 
+    [ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ], 
+    [ 2,0,1,3 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 3,0,1,2 ],[ 3,0,2,1 ],[ 0,0,0,0 ],[ 3,1,2,0 ], 
+    [ 2,1,0,3 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 0,0,0,0 ],[ 3,1,0,2 ],[ 0,0,0,0 ],[ 3,2,0,1 ],[ 3,2,1,0 ]]; 
 };
 };
 
 
 SimplexNoise.prototype.dot = function(g, x, y) { 
 SimplexNoise.prototype.dot = function(g, x, y) { 
-	return g[0]*x + g[1]*y;
+	return g[0] * x + g[1] * y;
 };
 };
 
 
 SimplexNoise.prototype.dot3 = function(g, x, y, z) {
 SimplexNoise.prototype.dot3 = function(g, x, y, z) {
-  return g[0]*x + g[1]*y + g[2]*z; 
+	return g[0] * x + g[1] * y + g[2] * z; 
 }
 }
 
 
 SimplexNoise.prototype.dot4 = function(g, x, y, z, w) {
 SimplexNoise.prototype.dot4 = function(g, x, y, z, w) {
-  return g[0]*x + g[1]*y + g[2]*z + g[3]*w;
+	return g[0] * x + g[1] * y + g[2] * z + g[3] * w;
 };
 };
 
 
 SimplexNoise.prototype.noise = function(xin, yin) { 
 SimplexNoise.prototype.noise = function(xin, yin) { 
-  var n0, n1, n2; // Noise contributions from the three corners 
+	var n0, n1, n2; // Noise contributions from the three corners 
   // Skew the input space to determine which simplex cell we're in 
   // Skew the input space to determine which simplex cell we're in 
-  var F2 = 0.5*(Math.sqrt(3.0)-1.0); 
-  var s = (xin+yin)*F2; // Hairy factor for 2D 
-  var i = Math.floor(xin+s); 
-  var j = Math.floor(yin+s); 
-  var G2 = (3.0-Math.sqrt(3.0))/6.0; 
-  var t = (i+j)*G2; 
-  var X0 = i-t; // Unskew the cell origin back to (x,y) space 
-  var Y0 = j-t; 
-  var x0 = xin-X0; // The x,y distances from the cell origin 
-  var y0 = yin-Y0; 
+	var F2 = 0.5 * (Math.sqrt(3.0) - 1.0); 
+	var s = (xin + yin) * F2; // Hairy factor for 2D 
+	var i = Math.floor(xin + s); 
+	var j = Math.floor(yin + s); 
+	var G2 = (3.0 - Math.sqrt(3.0)) / 6.0; 
+	var t = (i + j) * G2; 
+	var X0 = i - t; // Unskew the cell origin back to (x,y) space 
+	var Y0 = j - t; 
+	var x0 = xin - X0; // The x,y distances from the cell origin 
+	var y0 = yin - Y0; 
   // For the 2D case, the simplex shape is an equilateral triangle. 
   // For the 2D case, the simplex shape is an equilateral triangle. 
   // Determine which simplex we are in. 
   // Determine which simplex we are in. 
-  var i1, j1; // Offsets for second (middle) corner of simplex in (i,j) coords 
-  if(x0>y0) {i1=1; j1=0;} // lower triangle, XY order: (0,0)->(1,0)->(1,1) 
-  else {i1=0; j1=1;}      // upper triangle, YX order: (0,0)->(0,1)->(1,1) 
+	var i1, j1; // Offsets for second (middle) corner of simplex in (i,j) coords 
+	if (x0 > y0) {i1 = 1; j1 = 0;} // lower triangle, XY order: (0,0)->(1,0)->(1,1) 
+	else {i1 = 0; j1 = 1;}      // upper triangle, YX order: (0,0)->(0,1)->(1,1) 
   // A step of (1,0) in (i,j) means a step of (1-c,-c) in (x,y), and 
   // A step of (1,0) in (i,j) means a step of (1-c,-c) in (x,y), and 
   // a step of (0,1) in (i,j) means a step of (-c,1-c) in (x,y), where 
   // a step of (0,1) in (i,j) means a step of (-c,1-c) in (x,y), where 
   // c = (3-sqrt(3))/6 
   // c = (3-sqrt(3))/6 
-  var x1 = x0 - i1 + G2; // Offsets for middle corner in (x,y) unskewed coords 
-  var y1 = y0 - j1 + G2; 
-  var x2 = x0 - 1.0 + 2.0 * G2; // Offsets for last corner in (x,y) unskewed coords 
-  var y2 = y0 - 1.0 + 2.0 * G2; 
+	var x1 = x0 - i1 + G2; // Offsets for middle corner in (x,y) unskewed coords 
+	var y1 = y0 - j1 + G2; 
+	var x2 = x0 - 1.0 + 2.0 * G2; // Offsets for last corner in (x,y) unskewed coords 
+	var y2 = y0 - 1.0 + 2.0 * G2; 
   // Work out the hashed gradient indices of the three simplex corners 
   // Work out the hashed gradient indices of the three simplex corners 
-  var ii = i & 255; 
-  var jj = j & 255; 
-  var gi0 = this.perm[ii+this.perm[jj]] % 12; 
-  var gi1 = this.perm[ii+i1+this.perm[jj+j1]] % 12; 
-  var gi2 = this.perm[ii+1+this.perm[jj+1]] % 12; 
+	var ii = i & 255; 
+	var jj = j & 255; 
+	var gi0 = this.perm[ii + this.perm[jj]] % 12; 
+	var gi1 = this.perm[ii + i1 + this.perm[jj + j1]] % 12; 
+	var gi2 = this.perm[ii + 1 + this.perm[jj + 1]] % 12; 
   // Calculate the contribution from the three corners 
   // Calculate the contribution from the three corners 
-  var t0 = 0.5 - x0*x0-y0*y0; 
-  if(t0<0) n0 = 0.0; 
-  else { 
-    t0 *= t0; 
-    n0 = t0 * t0 * this.dot(this.grad3[gi0], x0, y0);  // (x,y) of grad3 used for 2D gradient 
-  } 
-  var t1 = 0.5 - x1*x1-y1*y1; 
-  if(t1<0) n1 = 0.0; 
-  else { 
-    t1 *= t1; 
-    n1 = t1 * t1 * this.dot(this.grad3[gi1], x1, y1); 
-  }
-  var t2 = 0.5 - x2*x2-y2*y2; 
-  if(t2<0) n2 = 0.0; 
-  else { 
-    t2 *= t2; 
-    n2 = t2 * t2 * this.dot(this.grad3[gi2], x2, y2); 
-  } 
+	var t0 = 0.5 - x0 * x0 - y0 * y0; 
+	if (t0 < 0) n0 = 0.0; 
+	else { 
+		t0 *= t0; 
+		n0 = t0 * t0 * this.dot(this.grad3[gi0], x0, y0);  // (x,y) of grad3 used for 2D gradient 
+	} 
+	var t1 = 0.5 - x1 * x1 - y1 * y1; 
+	if (t1 < 0) n1 = 0.0; 
+	else { 
+		t1 *= t1; 
+		n1 = t1 * t1 * this.dot(this.grad3[gi1], x1, y1); 
+	}
+	var t2 = 0.5 - x2 * x2 - y2 * y2; 
+	if (t2 < 0) n2 = 0.0; 
+	else { 
+		t2 *= t2; 
+		n2 = t2 * t2 * this.dot(this.grad3[gi2], x2, y2); 
+	} 
   // Add contributions from each corner to get the final noise value. 
   // Add contributions from each corner to get the final noise value. 
   // The result is scaled to return values in the interval [-1,1]. 
   // The result is scaled to return values in the interval [-1,1]. 
-  return 70.0 * (n0 + n1 + n2); 
+	return 70.0 * (n0 + n1 + n2); 
 };
 };
 
 
 // 3D simplex noise 
 // 3D simplex noise 
 SimplexNoise.prototype.noise3d = function(xin, yin, zin) { 
 SimplexNoise.prototype.noise3d = function(xin, yin, zin) { 
-  var n0, n1, n2, n3; // Noise contributions from the four corners 
+	var n0, n1, n2, n3; // Noise contributions from the four corners 
   // Skew the input space to determine which simplex cell we're in 
   // Skew the input space to determine which simplex cell we're in 
-  var F3 = 1.0/3.0; 
-  var s = (xin+yin+zin)*F3; // Very nice and simple skew factor for 3D 
-  var i = Math.floor(xin+s); 
-  var j = Math.floor(yin+s); 
-  var k = Math.floor(zin+s); 
-  var G3 = 1.0/6.0; // Very nice and simple unskew factor, too 
-  var t = (i+j+k)*G3; 
-  var X0 = i-t; // Unskew the cell origin back to (x,y,z) space 
-  var Y0 = j-t; 
-  var Z0 = k-t; 
-  var x0 = xin-X0; // The x,y,z distances from the cell origin 
-  var y0 = yin-Y0; 
-  var z0 = zin-Z0; 
+	var F3 = 1.0 / 3.0; 
+	var s = (xin + yin + zin) * F3; // Very nice and simple skew factor for 3D 
+	var i = Math.floor(xin + s); 
+	var j = Math.floor(yin + s); 
+	var k = Math.floor(zin + s); 
+	var G3 = 1.0 / 6.0; // Very nice and simple unskew factor, too 
+	var t = (i + j + k) * G3; 
+	var X0 = i - t; // Unskew the cell origin back to (x,y,z) space 
+	var Y0 = j - t; 
+	var Z0 = k - t; 
+	var x0 = xin - X0; // The x,y,z distances from the cell origin 
+	var y0 = yin - Y0; 
+	var z0 = zin - Z0; 
   // For the 3D case, the simplex shape is a slightly irregular tetrahedron. 
   // For the 3D case, the simplex shape is a slightly irregular tetrahedron. 
   // Determine which simplex we are in. 
   // Determine which simplex we are in. 
-  var i1, j1, k1; // Offsets for second corner of simplex in (i,j,k) coords 
-  var i2, j2, k2; // Offsets for third corner of simplex in (i,j,k) coords 
-  if(x0>=y0) { 
-    if(y0>=z0) 
-      { i1=1; j1=0; k1=0; i2=1; j2=1; k2=0; } // X Y Z order 
-      else if(x0>=z0) { i1=1; j1=0; k1=0; i2=1; j2=0; k2=1; } // X Z Y order 
-      else { i1=0; j1=0; k1=1; i2=1; j2=0; k2=1; } // Z X Y order 
-    } 
-  else { // x0<y0 
-    if(y0<z0) { i1=0; j1=0; k1=1; i2=0; j2=1; k2=1; } // Z Y X order 
-    else if(x0<z0) { i1=0; j1=1; k1=0; i2=0; j2=1; k2=1; } // Y Z X order 
-    else { i1=0; j1=1; k1=0; i2=1; j2=1; k2=0; } // Y X Z order 
-  } 
+	var i1, j1, k1; // Offsets for second corner of simplex in (i,j,k) coords 
+	var i2, j2, k2; // Offsets for third corner of simplex in (i,j,k) coords 
+	if (x0 >= y0) { 
+		if (y0 >= z0) 
+      { i1 = 1; j1 = 0; k1 = 0; i2 = 1; j2 = 1; k2 = 0; } // X Y Z order 
+      else if (x0 >= z0) { i1 = 1; j1 = 0; k1 = 0; i2 = 1; j2 = 0; k2 = 1; } // X Z Y order 
+		else { i1 = 0; j1 = 0; k1 = 1; i2 = 1; j2 = 0; k2 = 1; } // Z X Y order 
+	} 
+	else { // x0<y0 
+		if (y0 < z0) { i1 = 0; j1 = 0; k1 = 1; i2 = 0; j2 = 1; k2 = 1; } // Z Y X order 
+    else if (x0 < z0) { i1 = 0; j1 = 1; k1 = 0; i2 = 0; j2 = 1; k2 = 1; } // Y Z X order 
+		else { i1 = 0; j1 = 1; k1 = 0; i2 = 1; j2 = 1; k2 = 0; } // Y X Z order 
+	} 
   // A step of (1,0,0) in (i,j,k) means a step of (1-c,-c,-c) in (x,y,z), 
   // A step of (1,0,0) in (i,j,k) means a step of (1-c,-c,-c) in (x,y,z), 
   // a step of (0,1,0) in (i,j,k) means a step of (-c,1-c,-c) in (x,y,z), and 
   // a step of (0,1,0) in (i,j,k) means a step of (-c,1-c,-c) in (x,y,z), and 
   // a step of (0,0,1) in (i,j,k) means a step of (-c,-c,1-c) in (x,y,z), where 
   // a step of (0,0,1) in (i,j,k) means a step of (-c,-c,1-c) in (x,y,z), where 
   // c = 1/6.
   // c = 1/6.
-  var x1 = x0 - i1 + G3; // Offsets for second corner in (x,y,z) coords 
-  var y1 = y0 - j1 + G3; 
-  var z1 = z0 - k1 + G3; 
-  var x2 = x0 - i2 + 2.0*G3; // Offsets for third corner in (x,y,z) coords 
-  var y2 = y0 - j2 + 2.0*G3; 
-  var z2 = z0 - k2 + 2.0*G3; 
-  var x3 = x0 - 1.0 + 3.0*G3; // Offsets for last corner in (x,y,z) coords 
-  var y3 = y0 - 1.0 + 3.0*G3; 
-  var z3 = z0 - 1.0 + 3.0*G3; 
+	var x1 = x0 - i1 + G3; // Offsets for second corner in (x,y,z) coords 
+	var y1 = y0 - j1 + G3; 
+	var z1 = z0 - k1 + G3; 
+	var x2 = x0 - i2 + 2.0 * G3; // Offsets for third corner in (x,y,z) coords 
+	var y2 = y0 - j2 + 2.0 * G3; 
+	var z2 = z0 - k2 + 2.0 * G3; 
+	var x3 = x0 - 1.0 + 3.0 * G3; // Offsets for last corner in (x,y,z) coords 
+	var y3 = y0 - 1.0 + 3.0 * G3; 
+	var z3 = z0 - 1.0 + 3.0 * G3; 
   // Work out the hashed gradient indices of the four simplex corners 
   // Work out the hashed gradient indices of the four simplex corners 
-  var ii = i & 255; 
-  var jj = j & 255; 
-  var kk = k & 255; 
-  var gi0 = this.perm[ii+this.perm[jj+this.perm[kk]]] % 12; 
-  var gi1 = this.perm[ii+i1+this.perm[jj+j1+this.perm[kk+k1]]] % 12; 
-  var gi2 = this.perm[ii+i2+this.perm[jj+j2+this.perm[kk+k2]]] % 12; 
-  var gi3 = this.perm[ii+1+this.perm[jj+1+this.perm[kk+1]]] % 12; 
+	var ii = i & 255; 
+	var jj = j & 255; 
+	var kk = k & 255; 
+	var gi0 = this.perm[ii + this.perm[jj + this.perm[kk]]] % 12; 
+	var gi1 = this.perm[ii + i1 + this.perm[jj + j1 + this.perm[kk + k1]]] % 12; 
+	var gi2 = this.perm[ii + i2 + this.perm[jj + j2 + this.perm[kk + k2]]] % 12; 
+	var gi3 = this.perm[ii + 1 + this.perm[jj + 1 + this.perm[kk + 1]]] % 12; 
   // Calculate the contribution from the four corners 
   // Calculate the contribution from the four corners 
-  var t0 = 0.6 - x0*x0 - y0*y0 - z0*z0; 
-  if(t0<0) n0 = 0.0; 
-  else { 
-    t0 *= t0; 
-    n0 = t0 * t0 * this.dot3(this.grad3[gi0], x0, y0, z0); 
-  }
-  var t1 = 0.6 - x1*x1 - y1*y1 - z1*z1; 
-  if(t1<0) n1 = 0.0; 
-  else { 
-    t1 *= t1; 
-    n1 = t1 * t1 * this.dot3(this.grad3[gi1], x1, y1, z1); 
-  } 
-  var t2 = 0.6 - x2*x2 - y2*y2 - z2*z2; 
-  if(t2<0) n2 = 0.0; 
-  else { 
-    t2 *= t2; 
-    n2 = t2 * t2 * this.dot3(this.grad3[gi2], x2, y2, z2); 
-  } 
-  var t3 = 0.6 - x3*x3 - y3*y3 - z3*z3; 
-  if(t3<0) n3 = 0.0; 
-  else { 
-    t3 *= t3; 
-    n3 = t3 * t3 * this.dot3(this.grad3[gi3], x3, y3, z3); 
-  } 
+	var t0 = 0.6 - x0 * x0 - y0 * y0 - z0 * z0; 
+	if (t0 < 0) n0 = 0.0; 
+	else { 
+		t0 *= t0; 
+		n0 = t0 * t0 * this.dot3(this.grad3[gi0], x0, y0, z0); 
+	}
+	var t1 = 0.6 - x1 * x1 - y1 * y1 - z1 * z1; 
+	if (t1 < 0) n1 = 0.0; 
+	else { 
+		t1 *= t1; 
+		n1 = t1 * t1 * this.dot3(this.grad3[gi1], x1, y1, z1); 
+	} 
+	var t2 = 0.6 - x2 * x2 - y2 * y2 - z2 * z2; 
+	if (t2 < 0) n2 = 0.0; 
+	else { 
+		t2 *= t2; 
+		n2 = t2 * t2 * this.dot3(this.grad3[gi2], x2, y2, z2); 
+	} 
+	var t3 = 0.6 - x3 * x3 - y3 * y3 - z3 * z3; 
+	if (t3 < 0) n3 = 0.0; 
+	else { 
+		t3 *= t3; 
+		n3 = t3 * t3 * this.dot3(this.grad3[gi3], x3, y3, z3); 
+	} 
   // Add contributions from each corner to get the final noise value. 
   // Add contributions from each corner to get the final noise value. 
   // The result is scaled to stay just inside [-1,1] 
   // The result is scaled to stay just inside [-1,1] 
-  return 32.0*(n0 + n1 + n2 + n3); 
+	return 32.0 * (n0 + n1 + n2 + n3); 
 };
 };
 
 
 // 4D simplex noise
 // 4D simplex noise
@@ -207,24 +207,24 @@ SimplexNoise.prototype.noise4d = function( x, y, z, w ) {
 	var perm = this.perm;
 	var perm = this.perm;
 	
 	
    // The skewing and unskewing factors are hairy again for the 4D case
    // The skewing and unskewing factors are hairy again for the 4D case
-   var F4 = (Math.sqrt(5.0)-1.0)/4.0;
-   var G4 = (5.0-Math.sqrt(5.0))/20.0;
-   var n0, n1, n2, n3, n4; // Noise contributions from the five corners
+	var F4 = (Math.sqrt(5.0) - 1.0) / 4.0;
+	var G4 = (5.0 - Math.sqrt(5.0)) / 20.0;
+	var n0, n1, n2, n3, n4; // Noise contributions from the five corners
    // Skew the (x,y,z,w) space to determine which cell of 24 simplices we're in
    // Skew the (x,y,z,w) space to determine which cell of 24 simplices we're in
-   var s = (x + y + z + w) * F4; // Factor for 4D skewing
-   var i = Math.floor(x + s);
-   var j = Math.floor(y + s);
-   var k = Math.floor(z + s);
-   var l = Math.floor(w + s);
-   var t = (i + j + k + l) * G4; // Factor for 4D unskewing
-   var X0 = i - t; // Unskew the cell origin back to (x,y,z,w) space
-   var Y0 = j - t;
-   var Z0 = k - t;
-   var W0 = l - t;
-   var x0 = x - X0;  // The x,y,z,w distances from the cell origin
-   var y0 = y - Y0;
-   var z0 = z - Z0;
-   var w0 = w - W0;
+	var s = (x + y + z + w) * F4; // Factor for 4D skewing
+	var i = Math.floor(x + s);
+	var j = Math.floor(y + s);
+	var k = Math.floor(z + s);
+	var l = Math.floor(w + s);
+	var t = (i + j + k + l) * G4; // Factor for 4D unskewing
+	var X0 = i - t; // Unskew the cell origin back to (x,y,z,w) space
+	var Y0 = j - t;
+	var Z0 = k - t;
+	var W0 = l - t;
+	var x0 = x - X0;  // The x,y,z,w distances from the cell origin
+	var y0 = y - Y0;
+	var z0 = z - Z0;
+	var w0 = w - W0;
 
 
    // For the 4D case, the simplex is a 4D shape I won't even try to describe.
    // For the 4D case, the simplex is a 4D shape I won't even try to describe.
    // To find out which of the 24 possible simplices we're in, we need to
    // To find out which of the 24 possible simplices we're in, we need to
@@ -234,91 +234,91 @@ SimplexNoise.prototype.noise4d = function( x, y, z, w ) {
    // First, six pair-wise comparisons are performed between each possible pair
    // First, six pair-wise comparisons are performed between each possible pair
    // of the four coordinates, and the results are used to add up binary bits
    // of the four coordinates, and the results are used to add up binary bits
    // for an integer index.
    // for an integer index.
-   var c1 = (x0 > y0) ? 32 : 0;
-   var c2 = (x0 > z0) ? 16 : 0;
-   var c3 = (y0 > z0) ? 8 : 0;
-   var c4 = (x0 > w0) ? 4 : 0;
-   var c5 = (y0 > w0) ? 2 : 0;
-   var c6 = (z0 > w0) ? 1 : 0;
-   var c = c1 + c2 + c3 + c4 + c5 + c6;
-   var i1, j1, k1, l1; // The integer offsets for the second simplex corner
-   var i2, j2, k2, l2; // The integer offsets for the third simplex corner
-   var i3, j3, k3, l3; // The integer offsets for the fourth simplex corner
+	var c1 = (x0 > y0) ? 32 : 0;
+	var c2 = (x0 > z0) ? 16 : 0;
+	var c3 = (y0 > z0) ? 8 : 0;
+	var c4 = (x0 > w0) ? 4 : 0;
+	var c5 = (y0 > w0) ? 2 : 0;
+	var c6 = (z0 > w0) ? 1 : 0;
+	var c = c1 + c2 + c3 + c4 + c5 + c6;
+	var i1, j1, k1, l1; // The integer offsets for the second simplex corner
+	var i2, j2, k2, l2; // The integer offsets for the third simplex corner
+	var i3, j3, k3, l3; // The integer offsets for the fourth simplex corner
    // simplex[c] is a 4-vector with the numbers 0, 1, 2 and 3 in some order.
    // simplex[c] is a 4-vector with the numbers 0, 1, 2 and 3 in some order.
    // Many values of c will never occur, since e.g. x>y>z>w makes x<z, y<w and x<w
    // Many values of c will never occur, since e.g. x>y>z>w makes x<z, y<w and x<w
    // impossible. Only the 24 indices which have non-zero entries make any sense.
    // impossible. Only the 24 indices which have non-zero entries make any sense.
    // We use a thresholding to set the coordinates in turn from the largest magnitude.
    // We use a thresholding to set the coordinates in turn from the largest magnitude.
    // The number 3 in the "simplex" array is at the position of the largest coordinate.
    // The number 3 in the "simplex" array is at the position of the largest coordinate.
-   i1 = simplex[c][0]>=3 ? 1 : 0;
-   j1 = simplex[c][1]>=3 ? 1 : 0;
-   k1 = simplex[c][2]>=3 ? 1 : 0;
-   l1 = simplex[c][3]>=3 ? 1 : 0;
+	i1 = simplex[c][0] >= 3 ? 1 : 0;
+	j1 = simplex[c][1] >= 3 ? 1 : 0;
+	k1 = simplex[c][2] >= 3 ? 1 : 0;
+	l1 = simplex[c][3] >= 3 ? 1 : 0;
    // The number 2 in the "simplex" array is at the second largest coordinate.
    // The number 2 in the "simplex" array is at the second largest coordinate.
-   i2 = simplex[c][0]>=2 ? 1 : 0;
-   j2 = simplex[c][1]>=2 ? 1 : 0;    k2 = simplex[c][2]>=2 ? 1 : 0;
-   l2 = simplex[c][3]>=2 ? 1 : 0;
+	i2 = simplex[c][0] >= 2 ? 1 : 0;
+	j2 = simplex[c][1] >= 2 ? 1 : 0;    k2 = simplex[c][2] >= 2 ? 1 : 0;
+	l2 = simplex[c][3] >= 2 ? 1 : 0;
    // The number 1 in the "simplex" array is at the second smallest coordinate.
    // The number 1 in the "simplex" array is at the second smallest coordinate.
-   i3 = simplex[c][0]>=1 ? 1 : 0;
-   j3 = simplex[c][1]>=1 ? 1 : 0;
-   k3 = simplex[c][2]>=1 ? 1 : 0;
-   l3 = simplex[c][3]>=1 ? 1 : 0;
+	i3 = simplex[c][0] >= 1 ? 1 : 0;
+	j3 = simplex[c][1] >= 1 ? 1 : 0;
+	k3 = simplex[c][2] >= 1 ? 1 : 0;
+	l3 = simplex[c][3] >= 1 ? 1 : 0;
    // The fifth corner has all coordinate offsets = 1, so no need to look that up.
    // The fifth corner has all coordinate offsets = 1, so no need to look that up.
-   var x1 = x0 - i1 + G4; // Offsets for second corner in (x,y,z,w) coords
-   var y1 = y0 - j1 + G4;
-   var z1 = z0 - k1 + G4;
-   var w1 = w0 - l1 + G4;
-   var x2 = x0 - i2 + 2.0*G4; // Offsets for third corner in (x,y,z,w) coords
-   var y2 = y0 - j2 + 2.0*G4;
-   var z2 = z0 - k2 + 2.0*G4;
-   var w2 = w0 - l2 + 2.0*G4;
-   var x3 = x0 - i3 + 3.0*G4; // Offsets for fourth corner in (x,y,z,w) coords
-   var y3 = y0 - j3 + 3.0*G4;
-   var z3 = z0 - k3 + 3.0*G4;
-   var w3 = w0 - l3 + 3.0*G4;
-   var x4 = x0 - 1.0 + 4.0*G4; // Offsets for last corner in (x,y,z,w) coords
-   var y4 = y0 - 1.0 + 4.0*G4;
-   var z4 = z0 - 1.0 + 4.0*G4;
-   var w4 = w0 - 1.0 + 4.0*G4;
+	var x1 = x0 - i1 + G4; // Offsets for second corner in (x,y,z,w) coords
+	var y1 = y0 - j1 + G4;
+	var z1 = z0 - k1 + G4;
+	var w1 = w0 - l1 + G4;
+	var x2 = x0 - i2 + 2.0 * G4; // Offsets for third corner in (x,y,z,w) coords
+	var y2 = y0 - j2 + 2.0 * G4;
+	var z2 = z0 - k2 + 2.0 * G4;
+	var w2 = w0 - l2 + 2.0 * G4;
+	var x3 = x0 - i3 + 3.0 * G4; // Offsets for fourth corner in (x,y,z,w) coords
+	var y3 = y0 - j3 + 3.0 * G4;
+	var z3 = z0 - k3 + 3.0 * G4;
+	var w3 = w0 - l3 + 3.0 * G4;
+	var x4 = x0 - 1.0 + 4.0 * G4; // Offsets for last corner in (x,y,z,w) coords
+	var y4 = y0 - 1.0 + 4.0 * G4;
+	var z4 = z0 - 1.0 + 4.0 * G4;
+	var w4 = w0 - 1.0 + 4.0 * G4;
    // Work out the hashed gradient indices of the five simplex corners
    // Work out the hashed gradient indices of the five simplex corners
-   var ii = i & 255;
-   var jj = j & 255;
-   var kk = k & 255;
-   var ll = l & 255;
-   var gi0 = perm[ii+perm[jj+perm[kk+perm[ll]]]] % 32;
-   var gi1 = perm[ii+i1+perm[jj+j1+perm[kk+k1+perm[ll+l1]]]] % 32;
-   var gi2 = perm[ii+i2+perm[jj+j2+perm[kk+k2+perm[ll+l2]]]] % 32;
-   var gi3 = perm[ii+i3+perm[jj+j3+perm[kk+k3+perm[ll+l3]]]] % 32;
-   var gi4 = perm[ii+1+perm[jj+1+perm[kk+1+perm[ll+1]]]] % 32;
+	var ii = i & 255;
+	var jj = j & 255;
+	var kk = k & 255;
+	var ll = l & 255;
+	var gi0 = perm[ii + perm[jj + perm[kk + perm[ll]]]] % 32;
+	var gi1 = perm[ii + i1 + perm[jj + j1 + perm[kk + k1 + perm[ll + l1]]]] % 32;
+	var gi2 = perm[ii + i2 + perm[jj + j2 + perm[kk + k2 + perm[ll + l2]]]] % 32;
+	var gi3 = perm[ii + i3 + perm[jj + j3 + perm[kk + k3 + perm[ll + l3]]]] % 32;
+	var gi4 = perm[ii + 1 + perm[jj + 1 + perm[kk + 1 + perm[ll + 1]]]] % 32;
    // Calculate the contribution from the five corners
    // Calculate the contribution from the five corners
-   var t0 = 0.6 - x0*x0 - y0*y0 - z0*z0 - w0*w0;
-   if(t0<0) n0 = 0.0;
-   else {
-     t0 *= t0;
-     n0 = t0 * t0 * this.dot4(grad4[gi0], x0, y0, z0, w0);
-   }
-  var t1 = 0.6 - x1*x1 - y1*y1 - z1*z1 - w1*w1;
-   if(t1<0) n1 = 0.0;
-   else {
-     t1 *= t1;
-     n1 = t1 * t1 * this.dot4(grad4[gi1], x1, y1, z1, w1);
-   }
-  var t2 = 0.6 - x2*x2 - y2*y2 - z2*z2 - w2*w2;
-   if(t2<0) n2 = 0.0;
-   else {
-     t2 *= t2;
-     n2 = t2 * t2 * this.dot4(grad4[gi2], x2, y2, z2, w2);
-   }   var t3 = 0.6 - x3*x3 - y3*y3 - z3*z3 - w3*w3;
-   if(t3<0) n3 = 0.0;
-   else {
-     t3 *= t3;
-     n3 = t3 * t3 * this.dot4(grad4[gi3], x3, y3, z3, w3);
-   }
-  var t4 = 0.6 - x4*x4 - y4*y4 - z4*z4 - w4*w4;
-   if(t4<0) n4 = 0.0;
-   else {
-     t4 *= t4;
-     n4 = t4 * t4 * this.dot4(grad4[gi4], x4, y4, z4, w4);
-   }
+	var t0 = 0.6 - x0 * x0 - y0 * y0 - z0 * z0 - w0 * w0;
+	if (t0 < 0) n0 = 0.0;
+	else {
+		t0 *= t0;
+		n0 = t0 * t0 * this.dot4(grad4[gi0], x0, y0, z0, w0);
+	}
+	var t1 = 0.6 - x1 * x1 - y1 * y1 - z1 * z1 - w1 * w1;
+	if (t1 < 0) n1 = 0.0;
+	else {
+		t1 *= t1;
+		n1 = t1 * t1 * this.dot4(grad4[gi1], x1, y1, z1, w1);
+	}
+	var t2 = 0.6 - x2 * x2 - y2 * y2 - z2 * z2 - w2 * w2;
+	if (t2 < 0) n2 = 0.0;
+	else {
+		t2 *= t2;
+		n2 = t2 * t2 * this.dot4(grad4[gi2], x2, y2, z2, w2);
+	}   var t3 = 0.6 - x3 * x3 - y3 * y3 - z3 * z3 - w3 * w3;
+	if (t3 < 0) n3 = 0.0;
+	else {
+		t3 *= t3;
+		n3 = t3 * t3 * this.dot4(grad4[gi3], x3, y3, z3, w3);
+	}
+	var t4 = 0.6 - x4 * x4 - y4 * y4 - z4 * z4 - w4 * w4;
+	if (t4 < 0) n4 = 0.0;
+	else {
+		t4 *= t4;
+		n4 = t4 * t4 * this.dot4(grad4[gi4], x4, y4, z4, w4);
+	}
    // Sum up and scale the result to cover the range [-1,1]
    // Sum up and scale the result to cover the range [-1,1]
-   return 27.0 * (n0 + n1 + n2 + n3 + n4);
+	return 27.0 * (n0 + n1 + n2 + n3 + n4);
 };
 };

+ 2 - 2
examples/js/SimulationRenderer.js

@@ -19,12 +19,12 @@ function SimulationRenderer(WIDTH, renderer) {
 	// Init RTT stuff
 	// Init RTT stuff
 	gl = renderer.getContext();
 	gl = renderer.getContext();
 
 
-	if( !gl.getExtension( "OES_texture_float" )) {
+	if ( !gl.getExtension( "OES_texture_float" )) {
 		alert( "No OES_texture_float support for float textures!" );
 		alert( "No OES_texture_float support for float textures!" );
 		return;
 		return;
 	}
 	}
 
 
-	if( gl.getParameter(gl.MAX_VERTEX_TEXTURE_IMAGE_UNITS) == 0) {
+	if ( gl.getParameter(gl.MAX_VERTEX_TEXTURE_IMAGE_UNITS) == 0) {
 		alert( "No support for vertex shader textures!" );
 		alert( "No support for vertex shader textures!" );
 		return;
 		return;
 	}
 	}

+ 16 - 23
examples/js/SkyShader.js

@@ -1,16 +1,16 @@
 /**
 /**
  * @author zz85 / https://github.com/zz85
  * @author zz85 / https://github.com/zz85
- * 
- * Based on "A Practical Analytic Model for Daylight" 
+ *
+ * Based on "A Practical Analytic Model for Daylight"
  * aka The Preetham Model, the de facto standard analytic skydome model
  * aka The Preetham Model, the de facto standard analytic skydome model
  * http://www.cs.utah.edu/~shirley/papers/sunsky/sunsky.pdf
  * http://www.cs.utah.edu/~shirley/papers/sunsky/sunsky.pdf
- * 
+ *
  * First implemented by Simon Wallner
  * First implemented by Simon Wallner
  * http://www.simonwallner.at/projects/atmospheric-scattering
  * http://www.simonwallner.at/projects/atmospheric-scattering
- * 
+ *
  * Improved by Martin Upitis
  * Improved by Martin Upitis
  * http://blenderartists.org/forum/showthread.php?245954-preethams-sky-impementation-HDR
  * http://blenderartists.org/forum/showthread.php?245954-preethams-sky-impementation-HDR
- * 
+ *
  * Three.js integration by zz85 http://twitter.com/blurspline
  * Three.js integration by zz85 http://twitter.com/blurspline
 */
 */
 
 
@@ -30,13 +30,11 @@ THREE.ShaderLib['sky'] = {
 	vertexShader: [
 	vertexShader: [
 
 
 		"varying vec3 vWorldPosition;",
 		"varying vec3 vWorldPosition;",
-		"varying vec2 vUv;",
 
 
 		"void main() {",
 		"void main() {",
 
 
 			"vec4 worldPosition = modelMatrix * vec4( position, 1.0 );",
 			"vec4 worldPosition = modelMatrix * vec4( position, 1.0 );",
 			"vWorldPosition = worldPosition.xyz;",
 			"vWorldPosition = worldPosition.xyz;",
-			"vUv = uv;",
 
 
 			"gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );",
 			"gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );",
 
 
@@ -46,12 +44,9 @@ THREE.ShaderLib['sky'] = {
 
 
 	fragmentShader: [
 	fragmentShader: [
 
 
-
 		"uniform sampler2D skySampler;",
 		"uniform sampler2D skySampler;",
 		"uniform vec3 sunPosition;",
 		"uniform vec3 sunPosition;",
 		"varying vec3 vWorldPosition;",
 		"varying vec3 vWorldPosition;",
-		"varying vec2 vUv;",
-
 
 
 		"vec3 cameraPos = vec3(0., 0., 0.);",
 		"vec3 cameraPos = vec3(0., 0., 0.);",
 		"// uniform sampler2D sDiffuse;",
 		"// uniform sampler2D sDiffuse;",
@@ -67,7 +62,6 @@ THREE.ShaderLib['sky'] = {
 		"uniform float mieCoefficient;",
 		"uniform float mieCoefficient;",
 		"uniform float mieDirectionalG;",
 		"uniform float mieDirectionalG;",
 
 
-
 		"vec3 sunDirection = normalize(sunPosition);",
 		"vec3 sunDirection = normalize(sunPosition);",
 		"float reileighCoefficient = reileigh;",
 		"float reileighCoefficient = reileigh;",
 
 
@@ -165,9 +159,9 @@ THREE.ShaderLib['sky'] = {
 			"// luminance =  1.0 ;// vWorldPosition.y / 450000. + 0.5; //sunPosition.y / 450000. * 1. + 0.5;",
 			"// luminance =  1.0 ;// vWorldPosition.y / 450000. + 0.5; //sunPosition.y / 450000. * 1. + 0.5;",
 
 
 			 "// gl_FragColor = vec4(sunfade, sunfade, sunfade, 1.0);",
 			 "// gl_FragColor = vec4(sunfade, sunfade, sunfade, 1.0);",
-			
+
 			"reileighCoefficient = reileighCoefficient - (1.0* (1.0-sunfade));",
 			"reileighCoefficient = reileighCoefficient - (1.0* (1.0-sunfade));",
-			
+
 			"float sunE = sunIntensity(dot(sunDirection, up));",
 			"float sunE = sunIntensity(dot(sunDirection, up));",
 
 
 			"// extinction (absorbtion + out scattering) ",
 			"// extinction (absorbtion + out scattering) ",
@@ -210,7 +204,7 @@ THREE.ShaderLib['sky'] = {
 			"vec2 uv = vec2(phi, theta) / vec2(2.0*pi, pi) + vec2(0.5, 0.0);",
 			"vec2 uv = vec2(phi, theta) / vec2(2.0*pi, pi) + vec2(0.5, 0.0);",
 			"// vec3 L0 = texture2D(skySampler, uv).rgb+0.1 * Fex;",
 			"// vec3 L0 = texture2D(skySampler, uv).rgb+0.1 * Fex;",
 			"vec3 L0 = vec3(0.1) * Fex;",
 			"vec3 L0 = vec3(0.1) * Fex;",
-			
+
 			"// composition + solar disc",
 			"// composition + solar disc",
 			"//if (cosTheta > sunAngularDiameterCos)",
 			"//if (cosTheta > sunAngularDiameterCos)",
 			"float sundisk = smoothstep(sunAngularDiameterCos,sunAngularDiameterCos+0.00002,cosTheta);",
 			"float sundisk = smoothstep(sunAngularDiameterCos,sunAngularDiameterCos+0.00002,cosTheta);",
@@ -219,25 +213,25 @@ THREE.ShaderLib['sky'] = {
 
 
 
 
 			"vec3 whiteScale = 1.0/Uncharted2Tonemap(vec3(W));",
 			"vec3 whiteScale = 1.0/Uncharted2Tonemap(vec3(W));",
-			
+
 			"vec3 texColor = (Lin+L0);   ",
 			"vec3 texColor = (Lin+L0);   ",
 			"texColor *= 0.04 ;",
 			"texColor *= 0.04 ;",
 			"texColor += vec3(0.0,0.001,0.0025)*0.3;",
 			"texColor += vec3(0.0,0.001,0.0025)*0.3;",
-			
+
 			"float g_fMaxLuminance = 1.0;",
 			"float g_fMaxLuminance = 1.0;",
 			"float fLumScaled = 0.1 / luminance;     ",
 			"float fLumScaled = 0.1 / luminance;     ",
 			"float fLumCompressed = (fLumScaled * (1.0 + (fLumScaled / (g_fMaxLuminance * g_fMaxLuminance)))) / (1.0 + fLumScaled); ",
 			"float fLumCompressed = (fLumScaled * (1.0 + (fLumScaled / (g_fMaxLuminance * g_fMaxLuminance)))) / (1.0 + fLumScaled); ",
 
 
 			"float ExposureBias = fLumCompressed;",
 			"float ExposureBias = fLumCompressed;",
-		   
+
 			"vec3 curr = Uncharted2Tonemap((log2(2.0/pow(luminance,4.0)))*texColor);",
 			"vec3 curr = Uncharted2Tonemap((log2(2.0/pow(luminance,4.0)))*texColor);",
 			"vec3 color = curr*whiteScale;",
 			"vec3 color = curr*whiteScale;",
 
 
 			"vec3 retColor = pow(color,vec3(1.0/(1.2+(1.2*sunfade))));",
 			"vec3 retColor = pow(color,vec3(1.0/(1.2+(1.2*sunfade))));",
 
 
-			
+
 			"gl_FragColor.rgb = retColor;",
 			"gl_FragColor.rgb = retColor;",
-				
+
 			"gl_FragColor.a = 1.0;",
 			"gl_FragColor.a = 1.0;",
 		"}",
 		"}",
 
 
@@ -250,9 +244,9 @@ THREE.Sky = function () {
 	var skyShader = THREE.ShaderLib[ "sky" ];
 	var skyShader = THREE.ShaderLib[ "sky" ];
 	var skyUniforms = THREE.UniformsUtils.clone( skyShader.uniforms );
 	var skyUniforms = THREE.UniformsUtils.clone( skyShader.uniforms );
 
 
-	var skyMat = new THREE.ShaderMaterial( { 
-		fragmentShader: skyShader.fragmentShader, 
-		vertexShader: skyShader.vertexShader, 
+	var skyMat = new THREE.ShaderMaterial( {
+		fragmentShader: skyShader.fragmentShader,
+		vertexShader: skyShader.vertexShader,
 		uniforms: skyUniforms,
 		uniforms: skyUniforms,
 		side: THREE.BackSide
 		side: THREE.BackSide
 	} );
 	} );
@@ -265,5 +259,4 @@ THREE.Sky = function () {
 	this.mesh = skyMesh;
 	this.mesh = skyMesh;
 	this.uniforms = skyUniforms;
 	this.uniforms = skyUniforms;
 
 
-
 };
 };

+ 154 - 154
examples/js/Sparks.js

@@ -19,18 +19,18 @@ var SPARKS = {};
 
 
 SPARKS.Emitter = function (counter) {
 SPARKS.Emitter = function (counter) {
 
 
-    this._counter = counter ? counter : new SPARKS.SteadyCounter(10); // provides number of particles to produce
+	this._counter = counter ? counter : new SPARKS.SteadyCounter(10); // provides number of particles to produce
 
 
-    this._particles = [];
+	this._particles = [];
 
 
 
 
-    this._initializers = []; // use for creation of particles
-    this._actions = [];     // uses action to update particles
-    this._activities = [];  //  not supported yet
+	this._initializers = []; // use for creation of particles
+	this._actions = [];     // uses action to update particles
+	this._activities = [];  //  not supported yet
 
 
-    this._handlers = [];
+	this._handlers = [];
 
 
-    this.callbacks = {};
+	this.callbacks = {};
 };
 };
 
 
 
 
@@ -77,14 +77,14 @@ SPARKS.Emitter.prototype = {
 				elapsed = maxBlock;
 				elapsed = maxBlock;
 			}
 			}
 
 
-			while(elapsed >= emitter._TIMESTEP) {
+			while (elapsed >= emitter._TIMESTEP) {
 				emitter.update(emitter._TIMESTEP / 1000);
 				emitter.update(emitter._TIMESTEP / 1000);
 				elapsed -= emitter._TIMESTEP;
 				elapsed -= emitter._TIMESTEP;
 			}
 			}
 			emitter._lastTime = time - elapsed;
 			emitter._lastTime = time - elapsed;
 
 
 		} else {
 		} else {
-			emitter.update(elapsed/1000);
+			emitter.update(elapsed / 1000);
 			emitter._lastTime = time;
 			emitter._lastTime = time;
 		}
 		}
 
 
@@ -99,108 +99,108 @@ SPARKS.Emitter.prototype = {
 	// Update particle engine in seconds, not milliseconds
 	// Update particle engine in seconds, not milliseconds
     update: function(time) {
     update: function(time) {
 
 
-		var i, j;
-        var len = this._counter.updateEmitter( this, time );
+	var i, j;
+	var len = this._counter.updateEmitter( this, time );
 
 
         // Create particles
         // Create particles
-        for( i = 0; i < len; i++ ) {
-            this.createParticle();
-        }
+	for ( i = 0; i < len; i ++ ) {
+		this.createParticle();
+	}
 
 
         // Update activities
         // Update activities
-        len = this._activities.length;
-        for ( i = 0; i < len; i++ )
+	len = this._activities.length;
+	for ( i = 0; i < len; i ++ )
         {
         {
-            this._activities[i].update( this, time );
-        }
+		this._activities[i].update( this, time );
+	}
 
 
 
 
-        len = this._actions.length;
+	len = this._actions.length;
 
 
-		var particle;
-		var action;
-        var len2 = this._particles.length;
+	var particle;
+	var action;
+	var len2 = this._particles.length;
 
 
-        for( j = 0; j < len; j++ )
+	for ( j = 0; j < len; j ++ )
         {
         {
-            action = this._actions[j];
-            for ( i = 0; i < len2; ++i )
+		action = this._actions[j];
+		for ( i = 0; i < len2; ++ i )
             {
             {
-                particle = this._particles[i];
-                action.update( this, particle, time );
-            }
-        }
+			particle = this._particles[i];
+			action.update( this, particle, time );
+		}
+	}
 
 
 
 
         // remove dead particles
         // remove dead particles
-        for ( i = len2; i--; )
+	for ( i = len2; i --; )
         {
         {
-            particle = this._particles[i];
-            if ( particle.isDead )
+		particle = this._particles[i];
+		if ( particle.isDead )
             {
             {
                 //particle =
                 //particle =
-				this._particles.splice( i, 1 );
-                this.dispatchEvent("dead", particle);
-				SPARKS.VectorPool.release(particle.position); //
-				SPARKS.VectorPool.release(particle.velocity);
+			this._particles.splice( i, 1 );
+			this.dispatchEvent("dead", particle);
+			SPARKS.VectorPool.release(particle.position); //
+			SPARKS.VectorPool.release(particle.velocity);
 
 
-            } else {
-                this.dispatchEvent("updated", particle);
-            }
-        }
+		} else {
+			this.dispatchEvent("updated", particle);
+		}
+	}
 
 
-		this.dispatchEvent("loopUpdated");
+	this.dispatchEvent("loopUpdated");
 
 
     },
     },
 
 
     createParticle: function() {
     createParticle: function() {
-        var particle = new SPARKS.Particle();
+	var particle = new SPARKS.Particle();
         // In future, use a Particle Factory
         // In future, use a Particle Factory
-        var len = this._initializers.length, i;
+	var len = this._initializers.length, i;
 
 
-        for ( i = 0; i < len; i++ ) {
-            this._initializers[i].initialize( this, particle );
-        }
+	for ( i = 0; i < len; i ++ ) {
+		this._initializers[i].initialize( this, particle );
+	}
 
 
-        this._particles.push( particle );
+	this._particles.push( particle );
 
 
-        this.dispatchEvent("created", particle); // ParticleCreated
+	this.dispatchEvent("created", particle); // ParticleCreated
 
 
-        return particle;
+	return particle;
     },
     },
 
 
     addInitializer: function (initializer) {
     addInitializer: function (initializer) {
-        this._initializers.push(initializer);
+	this._initializers.push(initializer);
     },
     },
 
 
     addAction: function (action) {
     addAction: function (action) {
-        this._actions.push(action);
+	this._actions.push(action);
     },
     },
 
 
     removeInitializer: function (initializer) {
     removeInitializer: function (initializer) {
-		var index = this._initializers.indexOf(initializer);
-		if (index > -1) {
-			this._initializers.splice( index, 1 );
-		}
+	var index = this._initializers.indexOf(initializer);
+	if (index > -1) {
+		this._initializers.splice( index, 1 );
+	}
     },
     },
 
 
     removeAction: function (action) {
     removeAction: function (action) {
-		var index = this._actions.indexOf(action);
-		if (index > -1) {
-			this._actions.splice( index, 1 );
-		}
+	var index = this._actions.indexOf(action);
+	if (index > -1) {
+		this._actions.splice( index, 1 );
+	}
 		//console.log('removeAction', index, this._actions);
 		//console.log('removeAction', index, this._actions);
     },
     },
 
 
     addCallback: function(name, callback) {
     addCallback: function(name, callback) {
-        this.callbacks[name] = callback;
+	this.callbacks[name] = callback;
     },
     },
 
 
     dispatchEvent: function(name, args) {
     dispatchEvent: function(name, args) {
-        var callback = this.callbacks[name];
-        if (callback) {
-            callback(args);
-        }
+	var callback = this.callbacks[name];
+	if (callback) {
+		callback(args);
+	}
 
 
     }
     }
 
 
@@ -227,7 +227,7 @@ SPARKS.EVENT_LOOP_UPDATED = "loopUpdated";
 
 
 // Number of particles per seconds
 // Number of particles per seconds
 SPARKS.SteadyCounter = function(rate) {
 SPARKS.SteadyCounter = function(rate) {
-    this.rate = rate;
+	this.rate = rate;
 
 
 	// we use a shortfall counter to make up for slow emitters
 	// we use a shortfall counter to make up for slow emitters
 	this.leftover = 0;
 	this.leftover = 0;
@@ -277,32 +277,32 @@ SPARKS.Particle = function() {
     /**
     /**
      * The lifetime of the particle, in seconds.
      * The lifetime of the particle, in seconds.
      */
      */
-    this.lifetime = 0;
+	this.lifetime = 0;
 
 
     /**
     /**
      * The age of the particle, in seconds.
      * The age of the particle, in seconds.
      */
      */
-    this.age = 0;
+	this.age = 0;
 
 
     /**
     /**
      * The energy of the particle.
      * The energy of the particle.
      */
      */
-    this.energy = 1;
+	this.energy = 1;
 
 
     /**
     /**
      * Whether the particle is dead and should be removed from the stage.
      * Whether the particle is dead and should be removed from the stage.
      */
      */
-    this.isDead = false;
+	this.isDead = false;
 
 
-    this.target = null; // tag
+	this.target = null; // tag
 
 
     /**
     /**
      * For 3D
      * For 3D
      */
      */
 
 
-     this.position = SPARKS.VectorPool.get().set(0,0,0); //new THREE.Vector3( 0, 0, 0 );
-     this.velocity = SPARKS.VectorPool.get().set(0,0,0); //new THREE.Vector3( 0, 0, 0 );
-	this._oldvelocity = SPARKS.VectorPool.get().set(0,0,0);
+	this.position = SPARKS.VectorPool.get().set(0, 0, 0); //new THREE.Vector3( 0, 0, 0 );
+	this.velocity = SPARKS.VectorPool.get().set(0, 0, 0); //new THREE.Vector3( 0, 0, 0 );
+	this._oldvelocity = SPARKS.VectorPool.get().set(0, 0, 0);
      // rotation vec3
      // rotation vec3
      // angVelocity vec3
      // angVelocity vec3
      // faceAxis vec3
      // faceAxis vec3
@@ -317,26 +317,26 @@ SPARKS.Particle = function() {
 *   update function
 *   update function
 *********************************/
 *********************************/
 SPARKS.Action = function() {
 SPARKS.Action = function() {
-    this._priority = 0;
+	this._priority = 0;
 };
 };
 
 
 
 
 SPARKS.Age = function(easing) {
 SPARKS.Age = function(easing) {
-    this._easing = (easing == null) ? TWEEN.Easing.Linear.None : easing;
+	this._easing = (easing == null) ? TWEEN.Easing.Linear.None : easing;
 };
 };
 
 
 SPARKS.Age.prototype.update = function (emitter, particle, time) {
 SPARKS.Age.prototype.update = function (emitter, particle, time) {
-    particle.age += time;
-    if( particle.age >= particle.lifetime )
+	particle.age += time;
+	if ( particle.age >= particle.lifetime )
     {
     {
-        particle.energy = 0;
-        particle.isDead = true;
-    }
+		particle.energy = 0;
+		particle.isDead = true;
+	}
     else
     else
-    {
-        var t = this._easing(particle.age / particle.lifetime);
-        particle.energy = -1 * t + 1;
-    }
+	{
+		var t = this._easing(particle.age / particle.lifetime);
+		particle.energy = -1 * t + 1;
+	}
 };
 };
 
 
 /*
 /*
@@ -360,9 +360,9 @@ SPARKS.Move = function() {
 
 
 SPARKS.Move.prototype.update = function(emitter, particle, time) {
 SPARKS.Move.prototype.update = function(emitter, particle, time) {
     // attempt verlet velocity updating.
     // attempt verlet velocity updating.
-    var p = particle.position;
+	var p = particle.position;
 	var v = particle.velocity;
 	var v = particle.velocity;
-    var old = particle._oldvelocity;
+	var old = particle._oldvelocity;
 
 
 	if (this._velocityVerlet) {
 	if (this._velocityVerlet) {
 		p.x += (v.x + old.x) * 0.5 * time;
 		p.x += (v.x + old.x) * 0.5 * time;
@@ -384,12 +384,12 @@ SPARKS.Move.prototype.update = function(emitter, particle, time) {
 
 
 /* Marks particles found in specified zone dead */
 /* Marks particles found in specified zone dead */
 SPARKS.DeathZone = function(zone) {
 SPARKS.DeathZone = function(zone) {
-    this.zone = zone;
+	this.zone = zone;
 };
 };
 
 
 SPARKS.DeathZone.prototype.update = function(emitter, particle, time) {
 SPARKS.DeathZone.prototype.update = function(emitter, particle, time) {
 
 
-    if (this.zone.contains(particle.position)) {
+	if (this.zone.contains(particle.position)) {
 		particle.isDead = true;
 		particle.isDead = true;
 	}
 	}
 
 
@@ -400,12 +400,12 @@ SPARKS.DeathZone.prototype.update = function(emitter, particle, time) {
  */
  */
 SPARKS.ActionZone = function(action, zone) {
 SPARKS.ActionZone = function(action, zone) {
 	this.action = action;
 	this.action = action;
-    this.zone = zone;
+	this.zone = zone;
 };
 };
 
 
 SPARKS.ActionZone.prototype.update = function(emitter, particle, time) {
 SPARKS.ActionZone.prototype.update = function(emitter, particle, time) {
 
 
-    if (this.zone.contains(particle.position)) {
+	if (this.zone.contains(particle.position)) {
 		this.action.update( emitter, particle, time );
 		this.action.update( emitter, particle, time );
 	}
 	}
 
 
@@ -421,20 +421,20 @@ SPARKS.Accelerate = function(x,y,z) {
 		return;
 		return;
 	}
 	}
 
 
-    this.acceleration = new THREE.Vector3(x,y,z);
+	this.acceleration = new THREE.Vector3(x,y,z);
 
 
 };
 };
 
 
 SPARKS.Accelerate.prototype.update = function(emitter, particle, time) {
 SPARKS.Accelerate.prototype.update = function(emitter, particle, time) {
-    var acc = this.acceleration;
+	var acc = this.acceleration;
 
 
-    var v = particle.velocity;
+	var v = particle.velocity;
 
 
 	particle._oldvelocity.set(v.x, v.y, v.z);
 	particle._oldvelocity.set(v.x, v.y, v.z);
 
 
-    v.x += acc.x * time;
-    v.y += acc.y * time;
-    v.z += acc.z * time;
+	v.x += acc.x * time;
+	v.y += acc.y * time;
+	v.z += acc.z * time;
 
 
 };
 };
 
 
@@ -442,16 +442,16 @@ SPARKS.Accelerate.prototype.update = function(emitter, particle, time) {
  * Accelerate Factor accelerate based on a factor of particle's velocity.
  * Accelerate Factor accelerate based on a factor of particle's velocity.
  */
  */
 SPARKS.AccelerateFactor = function(factor) {
 SPARKS.AccelerateFactor = function(factor) {
-    this.factor = factor;
+	this.factor = factor;
 };
 };
 
 
 SPARKS.AccelerateFactor.prototype.update = function(emitter, particle, time) {
 SPARKS.AccelerateFactor.prototype.update = function(emitter, particle, time) {
-    var factor = this.factor;
+	var factor = this.factor;
 
 
-    var v = particle.velocity;
+	var v = particle.velocity;
 	var len = v.length();
 	var len = v.length();
 	var adjFactor;
 	var adjFactor;
-    if (len>0) {
+	if (len > 0) {
 
 
 		adjFactor = factor * time / len;
 		adjFactor = factor * time / len;
 		adjFactor += 1;
 		adjFactor += 1;
@@ -475,14 +475,14 @@ SPARKS.AccelerateVelocity = function(factor) {
 };
 };
 
 
 SPARKS.AccelerateVelocity.prototype.update = function(emitter, particle, time) {
 SPARKS.AccelerateVelocity.prototype.update = function(emitter, particle, time) {
-    var factor = this.factor;
+	var factor = this.factor;
 
 
-    var v = particle.velocity;
+	var v = particle.velocity;
 
 
 
 
-    v.z += - v.x * factor;
-    v.y += v.z * factor;
-    v.x +=  v.y * factor;
+	v.z += - v.x * factor;
+	v.y += v.z * factor;
+	v.x +=  v.y * factor;
 
 
 };
 };
 
 
@@ -494,18 +494,18 @@ SPARKS.RandomDrift = function(x,y,z) {
 		return;
 		return;
 	}
 	}
 
 
-    this.drift = new THREE.Vector3(x,y,z);
+	this.drift = new THREE.Vector3(x,y,z);
 }
 }
 
 
 
 
 SPARKS.RandomDrift.prototype.update = function(emitter, particle, time) {
 SPARKS.RandomDrift.prototype.update = function(emitter, particle, time) {
-    var drift = this.drift;
+	var drift = this.drift;
 
 
-    var v = particle.velocity;
+	var v = particle.velocity;
 
 
-    v.x += ( Math.random() - 0.5 ) * drift.x * time;
-    v.y += ( Math.random() - 0.5 ) * drift.y * time;
-    v.z += ( Math.random() - 0.5 ) * drift.z * time;
+	v.x += ( Math.random() - 0.5 ) * drift.x * time;
+	v.y += ( Math.random() - 0.5 ) * drift.y * time;
+	v.z += ( Math.random() - 0.5 ) * drift.z * time;
 
 
 };
 };
 
 
@@ -521,29 +521,29 @@ SPARKS.Zone = function() {
 // TODO, contains() for Zone
 // TODO, contains() for Zone
 
 
 SPARKS.PointZone = function(pos) {
 SPARKS.PointZone = function(pos) {
-    this.pos = pos;
+	this.pos = pos;
 };
 };
 
 
 SPARKS.PointZone.prototype.getLocation = function() {
 SPARKS.PointZone.prototype.getLocation = function() {
-    return this.pos;
+	return this.pos;
 };
 };
 
 
 SPARKS.PointZone = function(pos) {
 SPARKS.PointZone = function(pos) {
-    this.pos = pos;
+	this.pos = pos;
 };
 };
 
 
 SPARKS.PointZone.prototype.getLocation = function() {
 SPARKS.PointZone.prototype.getLocation = function() {
-    return this.pos;
+	return this.pos;
 };
 };
 
 
 SPARKS.LineZone = function(start, end) {
 SPARKS.LineZone = function(start, end) {
-    this.start = start;
+	this.start = start;
 	this.end = end;
 	this.end = end;
 	this._length = end.clone().sub( start );
 	this._length = end.clone().sub( start );
 };
 };
 
 
 SPARKS.LineZone.prototype.getLocation = function() {
 SPARKS.LineZone.prototype.getLocation = function() {
-    var len = this._length.clone();
+	var len = this._length.clone();
 
 
 	len.multiplyScalar( Math.random() );
 	len.multiplyScalar( Math.random() );
 	return len.add( this.start );
 	return len.add( this.start );
@@ -552,7 +552,7 @@ SPARKS.LineZone.prototype.getLocation = function() {
 
 
 // Basically a RectangleZone
 // Basically a RectangleZone
 SPARKS.ParallelogramZone = function(corner, side1, side2) {
 SPARKS.ParallelogramZone = function(corner, side1, side2) {
-    this.corner = corner;
+	this.corner = corner;
 	this.side1 = side1;
 	this.side1 = side1;
 	this.side2 = side2;
 	this.side2 = side2;
 };
 };
@@ -567,7 +567,7 @@ SPARKS.ParallelogramZone.prototype.getLocation = function() {
 };
 };
 
 
 SPARKS.CubeZone = function(position, x, y, z) {
 SPARKS.CubeZone = function(position, x, y, z) {
-    this.position = position;
+	this.position = position;
 	this.x = x;
 	this.x = x;
 	this.y = y;
 	this.y = y;
 	this.z = z;
 	this.z = z;
@@ -595,17 +595,17 @@ SPARKS.CubeZone.prototype.contains = function(position) {
 	var y = this.y; // depth
 	var y = this.y; // depth
 	var z = this.z; // height
 	var z = this.z; // height
 
 
-	if (x<0) {
+	if (x < 0) {
 		startX += x;
 		startX += x;
 		x = Math.abs(x);
 		x = Math.abs(x);
 	}
 	}
 
 
-	if (y<0) {
+	if (y < 0) {
 		startY += y;
 		startY += y;
 		y = Math.abs(y);
 		y = Math.abs(y);
 	}
 	}
 
 
-	if (z<0) {
+	if (z < 0) {
 		startZ += z;
 		startZ += z;
 		z = Math.abs(z);
 		z = Math.abs(z);
 	}
 	}
@@ -674,29 +674,29 @@ SPARKS.DiscZone.prototype.getLocation = function() {
 */
 */
 
 
 SPARKS.SphereCapZone = function(x, y, z, minr, maxr, angle) {
 SPARKS.SphereCapZone = function(x, y, z, minr, maxr, angle) {
-    this.x = x;
-    this.y = y;
-    this.z = z;
-    this.minr = minr;
-    this.maxr = maxr;
-    this.angle = angle;
+	this.x = x;
+	this.y = y;
+	this.z = z;
+	this.minr = minr;
+	this.maxr = maxr;
+	this.angle = angle;
 };
 };
 
 
 SPARKS.SphereCapZone.prototype.getLocation = function() {
 SPARKS.SphereCapZone.prototype.getLocation = function() {
-    var theta = Math.PI *2  * SPARKS.Utils.random();
-    var r = SPARKS.Utils.random();
+	var theta = Math.PI * 2  * SPARKS.Utils.random();
+	var r = SPARKS.Utils.random();
 
 
     //new THREE.Vector3
     //new THREE.Vector3
-    var v =  SPARKS.VectorPool.get().set(r * Math.cos(theta), -1 / Math.tan(this.angle * SPARKS.Utils.DEGREE_TO_RADIAN), r * Math.sin(theta));
+	var v =  SPARKS.VectorPool.get().set(r * Math.cos(theta), -1 / Math.tan(this.angle * SPARKS.Utils.DEGREE_TO_RADIAN), r * Math.sin(theta));
 
 
     //v.length = StardustMath.interpolate(0, _minRadius, 1, _maxRadius, Math.random());
     //v.length = StardustMath.interpolate(0, _minRadius, 1, _maxRadius, Math.random());
 
 
-    var i = this.minr - ((this.minr-this.maxr) *  Math.random() );
-    v.multiplyScalar(i);
+	var i = this.minr - ((this.minr - this.maxr) *  Math.random() );
+	v.multiplyScalar(i);
 
 
 	v.__markedForReleased = true;
 	v.__markedForReleased = true;
 
 
-    return v;
+	return v;
 };
 };
 
 
 
 
@@ -709,33 +709,33 @@ SPARKS.SphereCapZone.prototype.getLocation = function() {
 
 
 // Specifies random life between max and min
 // Specifies random life between max and min
 SPARKS.Lifetime = function(min, max) {
 SPARKS.Lifetime = function(min, max) {
-    this._min = min;
+	this._min = min;
 
 
-    this._max = max ? max : min;
+	this._max = max ? max : min;
 
 
 };
 };
 
 
 SPARKS.Lifetime.prototype.initialize = function( emitter/*Emitter*/, particle/*Particle*/ ) {
 SPARKS.Lifetime.prototype.initialize = function( emitter/*Emitter*/, particle/*Particle*/ ) {
-    particle.lifetime = this._min + SPARKS.Utils.random() * ( this._max - this._min );
+	particle.lifetime = this._min + SPARKS.Utils.random() * ( this._max - this._min );
 };
 };
 
 
 
 
 SPARKS.Position = function(zone) {
 SPARKS.Position = function(zone) {
-    this.zone = zone;
+	this.zone = zone;
 };
 };
 
 
 SPARKS.Position.prototype.initialize = function( emitter/*Emitter*/, particle/*Particle*/ ) {
 SPARKS.Position.prototype.initialize = function( emitter/*Emitter*/, particle/*Particle*/ ) {
-    var pos = this.zone.getLocation();
-    particle.position.set(pos.x, pos.y, pos.z);
+	var pos = this.zone.getLocation();
+	particle.position.set(pos.x, pos.y, pos.z);
 };
 };
 
 
 SPARKS.Velocity = function(zone) {
 SPARKS.Velocity = function(zone) {
-    this.zone = zone;
+	this.zone = zone;
 };
 };
 
 
 SPARKS.Velocity.prototype.initialize = function( emitter/*Emitter*/, particle/*Particle*/ ) {
 SPARKS.Velocity.prototype.initialize = function( emitter/*Emitter*/, particle/*Particle*/ ) {
-    var pos = this.zone.getLocation();
-    particle.velocity.set(pos.x, pos.y, pos.z);
+	var pos = this.zone.getLocation();
+	particle.velocity.set(pos.x, pos.y, pos.z);
 	if (pos.__markedForReleased) {
 	if (pos.__markedForReleased) {
 		//console.log("release");
 		//console.log("release");
 		SPARKS.VectorPool.release(pos);
 		SPARKS.VectorPool.release(pos);
@@ -744,17 +744,17 @@ SPARKS.Velocity.prototype.initialize = function( emitter/*Emitter*/, particle/*P
 };
 };
 
 
 SPARKS.Target = function(target, callback) {
 SPARKS.Target = function(target, callback) {
-    this.target = target;
-    this.callback = callback;
+	this.target = target;
+	this.callback = callback;
 };
 };
 
 
 SPARKS.Target.prototype.initialize = function( emitter, particle ) {
 SPARKS.Target.prototype.initialize = function( emitter, particle ) {
 
 
-    if (this.callback) {
-        particle.target = this.callback();
-    } else {
-        particle.target = this.target;
-    }
+	if (this.callback) {
+		particle.target = this.callback();
+	} else {
+		particle.target = this.target;
+	}
 
 
 };
 };
 
 
@@ -769,7 +769,7 @@ SPARKS.VectorPool = {
 
 
 	// Get a new Vector
 	// Get a new Vector
 	get: function() {
 	get: function() {
-		if (this.__pools.length>0) {
+		if (this.__pools.length > 0) {
 			return this.__pools.pop();
 			return this.__pools.pop();
 		}
 		}
 
 
@@ -786,7 +786,7 @@ SPARKS.VectorPool = {
 	_addToPool: function() {
 	_addToPool: function() {
 		//console.log("creating some pools");
 		//console.log("creating some pools");
 
 
-		for (var i=0, size = 100; i < size; i++) {
+		for (var i = 0, size = 100; i < size; i ++) {
 			this.__pools.push(new THREE.Vector3());
 			this.__pools.push(new THREE.Vector3());
 		}
 		}
 
 
@@ -807,7 +807,7 @@ SPARKS.VectorPool = {
 *********************************/
 *********************************/
 SPARKS.Utils = {
 SPARKS.Utils = {
     random: function() {
     random: function() {
-        return Math.random();
+	return Math.random();
     },
     },
     DEGREE_TO_RADIAN: Math.PI / 180,
     DEGREE_TO_RADIAN: Math.PI / 180,
 	TWOPI: Math.PI * 2,
 	TWOPI: Math.PI * 2,
@@ -821,7 +821,7 @@ SPARKS.Utils = {
 
 
 	getPerpendicular: function( v )
 	getPerpendicular: function( v )
 	{
 	{
-		if( v.x == 0 )
+		if ( v.x == 0 )
 		{
 		{
 			return new THREE.Vector3D( 1, 0, 0 );
 			return new THREE.Vector3D( 1, 0, 0 );
 		}
 		}

+ 5 - 5
examples/js/TypedArrayUtils.js

@@ -33,8 +33,8 @@ THREE.TypedArrayUtils.quicksortIP = function ( arr, eleSize, orderElement ) {
 		for ( y = 0; y < eleSize; y ++ ) {
 		for ( y = 0; y < eleSize; y ++ ) {
 
 
 			tmp = arr[ a + y ];
 			tmp = arr[ a + y ];
-			arr[ a + y ]=arr[ b + y ];
-			arr[ b + y ]=tmp;
+			arr[ a + y ] = arr[ b + y ];
+			arr[ b + y ] = tmp;
 
 
 		}
 		}
 
 
@@ -46,7 +46,7 @@ THREE.TypedArrayUtils.quicksortIP = function ( arr, eleSize, orderElement ) {
 
 
 		if ( right - left <= 25 ) {
 		if ( right - left <= 25 ) {
 
 
-			for ( j= left + 1; j <= right; j ++ ) {
+			for ( j = left + 1; j <= right; j ++ ) {
 
 
 				for ( x = 0; x < eleSize; x ++ ) {
 				for ( x = 0; x < eleSize; x ++ ) {
 			
 			
@@ -214,7 +214,7 @@ THREE.TypedArrayUtils.quicksortIP = function ( arr, eleSize, orderElement ) {
 		
 		
 		median = Math.floor( plength / 2 );
 		median = Math.floor( plength / 2 );
 		
 		
-		node = new self.Node( getPointSet( points, median ) , depth, parent, median + pos );
+		node = new self.Node( getPointSet( points, median ), depth, parent, median + pos );
 		node.left = buildTree( points.subarray( 0, median * eleSize), depth + 1, node, pos );
 		node.left = buildTree( points.subarray( 0, median * eleSize), depth + 1, node, pos );
 		node.right = buildTree( points.subarray( ( median + 1 ) * eleSize, points.length ), depth + 1, node, pos + median + 1 );
 		node.right = buildTree( points.subarray( ( median + 1 ) * eleSize, points.length ), depth + 1, node, pos + median + 1 );
 
 
@@ -226,7 +226,7 @@ THREE.TypedArrayUtils.quicksortIP = function ( arr, eleSize, orderElement ) {
 		
 		
 	this.getMaxDepth = function () { return maxDepth; };
 	this.getMaxDepth = function () { return maxDepth; };
 	
 	
-	this.nearest = function ( point, maxNodes , maxDistance ) {
+	this.nearest = function ( point, maxNodes, maxDistance ) {
 	
 	
 		 /* point: array of size eleSize 
 		 /* point: array of size eleSize 
 			maxNodes: max amount of nodes to return 
 			maxNodes: max amount of nodes to return 

+ 1 - 1
examples/js/cameras/CombinedCamera.js

@@ -29,7 +29,7 @@ THREE.CombinedCamera = function ( width, height, fov, near, far, orthoNear, orth
 
 
 	this.toPerspective();
 	this.toPerspective();
 
 
-	var aspect = width/height;
+	var aspect = width / height;
 
 
 };
 };
 
 

+ 3 - 7
examples/js/controls/EditorControls.js

@@ -116,8 +116,6 @@ THREE.EditorControls = function ( object, domElement ) {
 
 
 		if ( scope.enabled === false ) return;
 		if ( scope.enabled === false ) return;
 
 
-		event.preventDefault();
-
 		if ( event.button === 0 ) {
 		if ( event.button === 0 ) {
 
 
 			state = STATE.ROTATE;
 			state = STATE.ROTATE;
@@ -145,8 +143,6 @@ THREE.EditorControls = function ( object, domElement ) {
 
 
 		if ( scope.enabled === false ) return;
 		if ( scope.enabled === false ) return;
 
 
-		event.preventDefault();
-
 		pointer.set( event.clientX, event.clientY );
 		pointer.set( event.clientX, event.clientY );
 
 
 		var movementX = pointer.x - pointerOld.x;
 		var movementX = pointer.x - pointerOld.x;
@@ -266,7 +262,7 @@ THREE.EditorControls = function ( object, domElement ) {
 			case 1:
 			case 1:
 				touches[ 0 ].set( event.touches[ 0 ].pageX, event.touches[ 0 ].pageY, 0 );
 				touches[ 0 ].set( event.touches[ 0 ].pageX, event.touches[ 0 ].pageY, 0 );
 				touches[ 1 ].set( event.touches[ 0 ].pageX, event.touches[ 0 ].pageY, 0 );
 				touches[ 1 ].set( event.touches[ 0 ].pageX, event.touches[ 0 ].pageY, 0 );
-				scope.rotate( touches[ 0 ].sub( getClosest( touches[ 0 ] ,prevTouches ) ).multiplyScalar( - 0.005 ) );
+				scope.rotate( touches[ 0 ].sub( getClosest( touches[ 0 ], prevTouches ) ).multiplyScalar( - 0.005 ) );
 				break;
 				break;
 
 
 			case 2:
 			case 2:
@@ -277,8 +273,8 @@ THREE.EditorControls = function ( object, domElement ) {
 				prevDistance = distance;
 				prevDistance = distance;
 
 
 
 
-				var offset0 = touches[ 0 ].clone().sub( getClosest( touches[ 0 ] ,prevTouches ) );
-				var offset1 = touches[ 1 ].clone().sub( getClosest( touches[ 1 ] ,prevTouches ) );
+				var offset0 = touches[ 0 ].clone().sub( getClosest( touches[ 0 ], prevTouches ) );
+				var offset1 = touches[ 1 ].clone().sub( getClosest( touches[ 1 ], prevTouches ) );
 				offset0.x = -offset0.x;
 				offset0.x = -offset0.x;
 				offset1.x = -offset1.x;
 				offset1.x = -offset1.x;
 
 

+ 2 - 2
examples/js/controls/FirstPersonControls.js

@@ -163,7 +163,7 @@ THREE.FirstPersonControls = function ( object, domElement ) {
 
 
 	this.onKeyUp = function ( event ) {
 	this.onKeyUp = function ( event ) {
 
 
-		switch( event.keyCode ) {
+		switch ( event.keyCode ) {
 
 
 			case 38: /*up*/
 			case 38: /*up*/
 			case 87: /*W*/ this.moveForward = false; break;
 			case 87: /*W*/ this.moveForward = false; break;
@@ -229,7 +229,7 @@ THREE.FirstPersonControls = function ( object, domElement ) {
 		}
 		}
 
 
 		this.lon += this.mouseX * actualLookSpeed;
 		this.lon += this.mouseX * actualLookSpeed;
-		if( this.lookVertical ) this.lat -= this.mouseY * actualLookSpeed * verticalLookRatio;
+		if ( this.lookVertical ) this.lat -= this.mouseY * actualLookSpeed * verticalLookRatio;
 
 
 		this.lat = Math.max( - 85, Math.min( 85, this.lat ) );
 		this.lat = Math.max( - 85, Math.min( 85, this.lat ) );
 		this.phi = THREE.Math.degToRad( 90 - this.lat );
 		this.phi = THREE.Math.degToRad( 90 - this.lat );

+ 1 - 1
examples/js/controls/FlyControls.js

@@ -80,7 +80,7 @@ THREE.FlyControls = function ( object, domElement ) {
 
 
 	this.keyup = function( event ) {
 	this.keyup = function( event ) {
 
 
-		switch( event.keyCode ) {
+		switch ( event.keyCode ) {
 
 
 			case 16: /* shift */ this.movementSpeedMultiplier = 1; break;
 			case 16: /* shift */ this.movementSpeedMultiplier = 1; break;
 
 

+ 25 - 25
examples/js/controls/MouseControls.js

@@ -6,50 +6,50 @@
 
 
 THREE.MouseControls = function ( object ) {
 THREE.MouseControls = function ( object ) {
 
 
-  var scope = this;
-  var PI_2 = Math.PI / 2;
-  var mouseQuat = {
+	var scope = this;
+	var PI_2 = Math.PI / 2;
+	var mouseQuat = {
     x: new THREE.Quaternion(),
     x: new THREE.Quaternion(),
     y: new THREE.Quaternion()
     y: new THREE.Quaternion()
   };
   };
-  var object = object;
-  var xVector = new THREE.Vector3( 1, 0, 0 );
-  var yVector = new THREE.Vector3( 0, 1, 0 );
+	var object = object;
+	var xVector = new THREE.Vector3( 1, 0, 0 );
+	var yVector = new THREE.Vector3( 0, 1, 0 );
 
 
-  var onMouseMove = function ( event ) {
+	var onMouseMove = function ( event ) {
 
 
-    if ( scope.enabled === false ) return;
+		if ( scope.enabled === false ) return;
 
 
-    var orientation = scope.orientation;
+		var orientation = scope.orientation;
 
 
-    var movementX = event.movementX || event.mozMovementX || event.webkitMovementX || 0;
-    var movementY = event.movementY || event.mozMovementY || event.webkitMovementY || 0;
+		var movementX = event.movementX || event.mozMovementX || event.webkitMovementX || 0;
+		var movementY = event.movementY || event.mozMovementY || event.webkitMovementY || 0;
 
 
-    orientation.y += movementX * 0.0025;
-    orientation.x += movementY * 0.0025;
+		orientation.y += movementX * 0.0025;
+		orientation.x += movementY * 0.0025;
 
 
-    orientation.x = Math.max( - PI_2, Math.min( PI_2, orientation.x ) );
+		orientation.x = Math.max( - PI_2, Math.min( PI_2, orientation.x ) );
 
 
-  };
+	};
 
 
-  this.enabled = true;
+	this.enabled = true;
 
 
-  this.orientation = {
+	this.orientation = {
     x: 0,
     x: 0,
     y: 0,
     y: 0,
   };
   };
 
 
-  this.update = function() {
+	this.update = function() {
 
 
-    if ( this.enabled === false ) return;
+		if ( this.enabled === false ) return;
 
 
-    mouseQuat.x.setFromAxisAngle( xVector, this.orientation.x );
-    mouseQuat.y.setFromAxisAngle( yVector, this.orientation.y );
-    object.quaternion.copy(mouseQuat.y).multiply(mouseQuat.x)
-    return;
+		mouseQuat.x.setFromAxisAngle( xVector, this.orientation.x );
+		mouseQuat.y.setFromAxisAngle( yVector, this.orientation.y );
+		object.quaternion.copy(mouseQuat.y).multiply(mouseQuat.x)
+		return;
 
 
-  };
+	};
 
 
-  document.addEventListener( 'mousemove', onMouseMove, false );
+	document.addEventListener( 'mousemove', onMouseMove, false );
 
 
 };
 };

Some files were not shown because too many files changed in this diff