Browse Source

Started to explore physically based shading / linear color space.

Do not merge, this is very experimental, not sure about correctness, also tons of unsolved things.
alteredq 14 years ago
parent
commit
3ce8fbb3b6

File diff suppressed because it is too large
+ 86 - 86
build/Three.js


+ 3 - 3
build/custom/ThreeCanvas.js

@@ -1,8 +1,8 @@
 // ThreeCanvas.js r46dev - http://github.com/mrdoob/three.js
 var THREE=THREE||{};if(!self.Int32Array)self.Int32Array=Array,self.Float32Array=Array;THREE.Color=function(a){a!==void 0&&this.setHex(a);return this};
-THREE.Color.prototype={constructor:THREE.Color,r:1,g:1,b:1,copy:function(a){this.r=a.r;this.g=a.g;this.b=a.b;return this},setRGB:function(a,b,c){this.r=a;this.g=b;this.b=c;return this},setHSV:function(a,b,c){var d,f,e;if(c==0)this.r=this.g=this.b=0;else switch(d=Math.floor(a*6),f=a*6-d,a=c*(1-b),e=c*(1-b*f),b=c*(1-b*(1-f)),d){case 1:this.r=e;this.g=c;this.b=a;break;case 2:this.r=a;this.g=c;this.b=b;break;case 3:this.r=a;this.g=e;this.b=c;break;case 4:this.r=b;this.g=a;this.b=c;break;case 5:this.r=
-c;this.g=a;this.b=e;break;case 6:case 0:this.r=c,this.g=b,this.b=a}return this},setHex:function(a){a=Math.floor(a);this.r=(a>>16&255)/255;this.g=(a>>8&255)/255;this.b=(a&255)/255;return this},getHex:function(){return~~(this.r*255)<<16^~~(this.g*255)<<8^~~(this.b*255)},getContextStyle:function(){return"rgb("+Math.floor(this.r*255)+","+Math.floor(this.g*255)+","+Math.floor(this.b*255)+")"},clone:function(){return(new THREE.Color).setRGB(this.r,this.g,this.b)}};
-THREE.Vector2=function(a,b){this.x=a||0;this.y=b||0};
+THREE.Color.prototype={constructor:THREE.Color,r:1,g:1,b:1,copy:function(a){this.r=a.r;this.g=a.g;this.b=a.b;return this},copyGammaToLinear:function(a){this.r=a.r*a.r;this.g=a.g*a.g;this.b=a.b*a.b;return this},copyLinearToGamma:function(a){this.r=Math.sqrt(a.r);this.g=Math.sqrt(a.g);this.b=Math.sqrt(a.b);return this},setRGB:function(a,b,c){this.r=a;this.g=b;this.b=c;return this},setHSV:function(a,b,c){var d,f,e;if(c==0)this.r=this.g=this.b=0;else switch(d=Math.floor(a*6),f=a*6-d,a=c*(1-b),e=c*(1-
+b*f),b=c*(1-b*(1-f)),d){case 1:this.r=e;this.g=c;this.b=a;break;case 2:this.r=a;this.g=c;this.b=b;break;case 3:this.r=a;this.g=e;this.b=c;break;case 4:this.r=b;this.g=a;this.b=c;break;case 5:this.r=c;this.g=a;this.b=e;break;case 6:case 0:this.r=c,this.g=b,this.b=a}return this},setHex:function(a){a=Math.floor(a);this.r=(a>>16&255)/255;this.g=(a>>8&255)/255;this.b=(a&255)/255;return this},getHex:function(){return~~(this.r*255)<<16^~~(this.g*255)<<8^~~(this.b*255)},getContextStyle:function(){return"rgb("+
+Math.floor(this.r*255)+","+Math.floor(this.g*255)+","+Math.floor(this.b*255)+")"},clone:function(){return(new THREE.Color).setRGB(this.r,this.g,this.b)}};THREE.Vector2=function(a,b){this.x=a||0;this.y=b||0};
 THREE.Vector2.prototype={constructor:THREE.Vector2,set:function(a,b){this.x=a;this.y=b;return this},copy:function(a){this.x=a.x;this.y=a.y;return this},clone:function(){return new THREE.Vector2(this.x,this.y)},add:function(a,b){this.x=a.x+b.x;this.y=a.y+b.y;return this},addSelf:function(a){this.x+=a.x;this.y+=a.y;return this},sub:function(a,b){this.x=a.x-b.x;this.y=a.y-b.y;return this},subSelf:function(a){this.x-=a.x;this.y-=a.y;return this},multiplyScalar:function(a){this.x*=a;this.y*=a;return this},
 divideScalar:function(a){a?(this.x/=a,this.y/=a):this.set(0,0);return this},negate:function(){return this.multiplyScalar(-1)},dot:function(a){return this.x*a.x+this.y*a.y},lengthSq:function(){return this.x*this.x+this.y*this.y},length:function(){return Math.sqrt(this.lengthSq())},normalize:function(){return this.divideScalar(this.length())},distanceTo:function(a){return Math.sqrt(this.distanceToSquared(a))},distanceToSquared:function(a){var b=this.x-a.x,a=this.y-a.y;return b*b+a*a},setLength:function(a){return this.normalize().multiplyScalar(a)},
 equals:function(a){return a.x==this.x&&a.y==this.y}};THREE.Vector3=function(a,b,c){this.x=a||0;this.y=b||0;this.z=c||0};

+ 3 - 3
build/custom/ThreeDOM.js

@@ -1,8 +1,8 @@
 // ThreeDOM.js r46dev - http://github.com/mrdoob/three.js
 var THREE=THREE||{};if(!self.Int32Array)self.Int32Array=Array,self.Float32Array=Array;THREE.Color=function(a){a!==void 0&&this.setHex(a);return this};
-THREE.Color.prototype={constructor:THREE.Color,r:1,g:1,b:1,copy:function(a){this.r=a.r;this.g=a.g;this.b=a.b;return this},setRGB:function(a,b,c){this.r=a;this.g=b;this.b=c;return this},setHSV:function(a,b,c){var d,e,g;if(c==0)this.r=this.g=this.b=0;else switch(d=Math.floor(a*6),e=a*6-d,a=c*(1-b),g=c*(1-b*e),b=c*(1-b*(1-e)),d){case 1:this.r=g;this.g=c;this.b=a;break;case 2:this.r=a;this.g=c;this.b=b;break;case 3:this.r=a;this.g=g;this.b=c;break;case 4:this.r=b;this.g=a;this.b=c;break;case 5:this.r=
-c;this.g=a;this.b=g;break;case 6:case 0:this.r=c,this.g=b,this.b=a}return this},setHex:function(a){a=Math.floor(a);this.r=(a>>16&255)/255;this.g=(a>>8&255)/255;this.b=(a&255)/255;return this},getHex:function(){return~~(this.r*255)<<16^~~(this.g*255)<<8^~~(this.b*255)},getContextStyle:function(){return"rgb("+Math.floor(this.r*255)+","+Math.floor(this.g*255)+","+Math.floor(this.b*255)+")"},clone:function(){return(new THREE.Color).setRGB(this.r,this.g,this.b)}};
-THREE.Vector2=function(a,b){this.x=a||0;this.y=b||0};
+THREE.Color.prototype={constructor:THREE.Color,r:1,g:1,b:1,copy:function(a){this.r=a.r;this.g=a.g;this.b=a.b;return this},copyGammaToLinear:function(a){this.r=a.r*a.r;this.g=a.g*a.g;this.b=a.b*a.b;return this},copyLinearToGamma:function(a){this.r=Math.sqrt(a.r);this.g=Math.sqrt(a.g);this.b=Math.sqrt(a.b);return this},setRGB:function(a,b,c){this.r=a;this.g=b;this.b=c;return this},setHSV:function(a,b,c){var d,e,g;if(c==0)this.r=this.g=this.b=0;else switch(d=Math.floor(a*6),e=a*6-d,a=c*(1-b),g=c*(1-
+b*e),b=c*(1-b*(1-e)),d){case 1:this.r=g;this.g=c;this.b=a;break;case 2:this.r=a;this.g=c;this.b=b;break;case 3:this.r=a;this.g=g;this.b=c;break;case 4:this.r=b;this.g=a;this.b=c;break;case 5:this.r=c;this.g=a;this.b=g;break;case 6:case 0:this.r=c,this.g=b,this.b=a}return this},setHex:function(a){a=Math.floor(a);this.r=(a>>16&255)/255;this.g=(a>>8&255)/255;this.b=(a&255)/255;return this},getHex:function(){return~~(this.r*255)<<16^~~(this.g*255)<<8^~~(this.b*255)},getContextStyle:function(){return"rgb("+
+Math.floor(this.r*255)+","+Math.floor(this.g*255)+","+Math.floor(this.b*255)+")"},clone:function(){return(new THREE.Color).setRGB(this.r,this.g,this.b)}};THREE.Vector2=function(a,b){this.x=a||0;this.y=b||0};
 THREE.Vector2.prototype={constructor:THREE.Vector2,set:function(a,b){this.x=a;this.y=b;return this},copy:function(a){this.x=a.x;this.y=a.y;return this},clone:function(){return new THREE.Vector2(this.x,this.y)},add:function(a,b){this.x=a.x+b.x;this.y=a.y+b.y;return this},addSelf:function(a){this.x+=a.x;this.y+=a.y;return this},sub:function(a,b){this.x=a.x-b.x;this.y=a.y-b.y;return this},subSelf:function(a){this.x-=a.x;this.y-=a.y;return this},multiplyScalar:function(a){this.x*=a;this.y*=a;return this},
 divideScalar:function(a){a?(this.x/=a,this.y/=a):this.set(0,0);return this},negate:function(){return this.multiplyScalar(-1)},dot:function(a){return this.x*a.x+this.y*a.y},lengthSq:function(){return this.x*this.x+this.y*this.y},length:function(){return Math.sqrt(this.lengthSq())},normalize:function(){return this.divideScalar(this.length())},distanceTo:function(a){return Math.sqrt(this.distanceToSquared(a))},distanceToSquared:function(a){var b=this.x-a.x,a=this.y-a.y;return b*b+a*a},setLength:function(a){return this.normalize().multiplyScalar(a)},
 equals:function(a){return a.x==this.x&&a.y==this.y}};THREE.Vector3=function(a,b,c){this.x=a||0;this.y=b||0;this.z=c||0};

+ 3 - 3
build/custom/ThreeSVG.js

@@ -1,8 +1,8 @@
 // ThreeSVG.js r46dev - http://github.com/mrdoob/three.js
 var THREE=THREE||{};if(!self.Int32Array)self.Int32Array=Array,self.Float32Array=Array;THREE.Color=function(a){a!==void 0&&this.setHex(a);return this};
-THREE.Color.prototype={constructor:THREE.Color,r:1,g:1,b:1,copy:function(a){this.r=a.r;this.g=a.g;this.b=a.b;return this},setRGB:function(a,b,c){this.r=a;this.g=b;this.b=c;return this},setHSV:function(a,b,c){var d,f,e;if(c==0)this.r=this.g=this.b=0;else switch(d=Math.floor(a*6),f=a*6-d,a=c*(1-b),e=c*(1-b*f),b=c*(1-b*(1-f)),d){case 1:this.r=e;this.g=c;this.b=a;break;case 2:this.r=a;this.g=c;this.b=b;break;case 3:this.r=a;this.g=e;this.b=c;break;case 4:this.r=b;this.g=a;this.b=c;break;case 5:this.r=
-c;this.g=a;this.b=e;break;case 6:case 0:this.r=c,this.g=b,this.b=a}return this},setHex:function(a){a=Math.floor(a);this.r=(a>>16&255)/255;this.g=(a>>8&255)/255;this.b=(a&255)/255;return this},getHex:function(){return~~(this.r*255)<<16^~~(this.g*255)<<8^~~(this.b*255)},getContextStyle:function(){return"rgb("+Math.floor(this.r*255)+","+Math.floor(this.g*255)+","+Math.floor(this.b*255)+")"},clone:function(){return(new THREE.Color).setRGB(this.r,this.g,this.b)}};
-THREE.Vector2=function(a,b){this.x=a||0;this.y=b||0};
+THREE.Color.prototype={constructor:THREE.Color,r:1,g:1,b:1,copy:function(a){this.r=a.r;this.g=a.g;this.b=a.b;return this},copyGammaToLinear:function(a){this.r=a.r*a.r;this.g=a.g*a.g;this.b=a.b*a.b;return this},copyLinearToGamma:function(a){this.r=Math.sqrt(a.r);this.g=Math.sqrt(a.g);this.b=Math.sqrt(a.b);return this},setRGB:function(a,b,c){this.r=a;this.g=b;this.b=c;return this},setHSV:function(a,b,c){var d,f,e;if(c==0)this.r=this.g=this.b=0;else switch(d=Math.floor(a*6),f=a*6-d,a=c*(1-b),e=c*(1-
+b*f),b=c*(1-b*(1-f)),d){case 1:this.r=e;this.g=c;this.b=a;break;case 2:this.r=a;this.g=c;this.b=b;break;case 3:this.r=a;this.g=e;this.b=c;break;case 4:this.r=b;this.g=a;this.b=c;break;case 5:this.r=c;this.g=a;this.b=e;break;case 6:case 0:this.r=c,this.g=b,this.b=a}return this},setHex:function(a){a=Math.floor(a);this.r=(a>>16&255)/255;this.g=(a>>8&255)/255;this.b=(a&255)/255;return this},getHex:function(){return~~(this.r*255)<<16^~~(this.g*255)<<8^~~(this.b*255)},getContextStyle:function(){return"rgb("+
+Math.floor(this.r*255)+","+Math.floor(this.g*255)+","+Math.floor(this.b*255)+")"},clone:function(){return(new THREE.Color).setRGB(this.r,this.g,this.b)}};THREE.Vector2=function(a,b){this.x=a||0;this.y=b||0};
 THREE.Vector2.prototype={constructor:THREE.Vector2,set:function(a,b){this.x=a;this.y=b;return this},copy:function(a){this.x=a.x;this.y=a.y;return this},clone:function(){return new THREE.Vector2(this.x,this.y)},add:function(a,b){this.x=a.x+b.x;this.y=a.y+b.y;return this},addSelf:function(a){this.x+=a.x;this.y+=a.y;return this},sub:function(a,b){this.x=a.x-b.x;this.y=a.y-b.y;return this},subSelf:function(a){this.x-=a.x;this.y-=a.y;return this},multiplyScalar:function(a){this.x*=a;this.y*=a;return this},
 divideScalar:function(a){a?(this.x/=a,this.y/=a):this.set(0,0);return this},negate:function(){return this.multiplyScalar(-1)},dot:function(a){return this.x*a.x+this.y*a.y},lengthSq:function(){return this.x*this.x+this.y*this.y},length:function(){return Math.sqrt(this.lengthSq())},normalize:function(){return this.divideScalar(this.length())},distanceTo:function(a){return Math.sqrt(this.distanceToSquared(a))},distanceToSquared:function(a){var b=this.x-a.x,a=this.y-a.y;return b*b+a*a},setLength:function(a){return this.normalize().multiplyScalar(a)},
 equals:function(a){return a.x==this.x&&a.y==this.y}};THREE.Vector3=function(a,b,c){this.x=a||0;this.y=b||0;this.z=c||0};

File diff suppressed because it is too large
+ 36 - 36
build/custom/ThreeWebGL.js


+ 521 - 0
examples/webgl_shading_physical.html

@@ -0,0 +1,521 @@
+<!doctype html>
+<html lang="en">
+	<head>
+		<title>three.js webgl - physically based shading</title>
+		<meta charset="utf-8">
+		<meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
+		<style>
+		    body {
+			color: #222;
+			font-family:Monospace;
+			font-size:13px;
+			text-align:center;
+			font-weight: bold;
+
+			background-color: #fff;
+			margin: 0px;
+			overflow: hidden;
+		    }
+
+		    #info {
+			color:#000;
+			position: relative;
+			margin: 0 auto -2.1em;
+			top: 0px;
+			width: 550px;
+			padding: 5px;
+			z-index:100;
+		    }
+
+		    a { color: skyblue; }
+		</style>
+	</head>
+
+	<body>
+		<div id="info">
+			<a href="http://github.com/mrdoob/three.js" target="_blank">three.js</a> - webgl physically based shading testbed
+		</div>
+
+		<!--
+		<script src="../build/Three.js"></script>
+		-->
+
+		<script type="text/javascript" src="../src/Three.js"></script>
+		<script type="text/javascript" src="../src/core/Color.js"></script>
+		<script type="text/javascript" src="../src/core/Vector2.js"></script>
+		<script type="text/javascript" src="../src/core/Vector3.js"></script>
+		<script type="text/javascript" src="../src/core/Vector4.js"></script>
+		<script type="text/javascript" src="../src/core/Ray.js"></script>
+		<script type="text/javascript" src="../src/core/Rectangle.js"></script>
+		<script type="text/javascript" src="../src/core/Matrix3.js"></script>
+		<script type="text/javascript" src="../src/core/Matrix4.js"></script>
+		<script type="text/javascript" src="../src/core/Object3D.js"></script>
+		<script type="text/javascript" src="../src/core/Projector.js"></script>
+		<script type="text/javascript" src="../src/core/Quaternion.js"></script>
+		<script type="text/javascript" src="../src/core/Vertex.js"></script>
+		<script type="text/javascript" src="../src/core/Face3.js"></script>
+		<script type="text/javascript" src="../src/core/Face4.js"></script>
+		<script type="text/javascript" src="../src/core/UV.js"></script>
+		<script type="text/javascript" src="../src/core/Geometry.js"></script>
+		<script type="text/javascript" src="../src/core/Spline.js"></script>
+		<script type="text/javascript" src="../src/core/Edge.js"></script>
+		<script type="text/javascript" src="../src/cameras/Camera.js"></script>
+		<script type="text/javascript" src="../src/cameras/OrthographicCamera.js"></script>
+		<script type="text/javascript" src="../src/cameras/PerspectiveCamera.js"></script>
+		<script type="text/javascript" src="../src/lights/Light.js"></script>
+		<script type="text/javascript" src="../src/lights/AmbientLight.js"></script>
+		<script type="text/javascript" src="../src/lights/DirectionalLight.js"></script>
+		<script type="text/javascript" src="../src/lights/PointLight.js"></script>
+		<script type="text/javascript" src="../src/lights/SpotLight.js"></script>
+		<script type="text/javascript" src="../src/materials/Material.js"></script>
+		<script type="text/javascript" src="../src/materials/LineBasicMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshBasicMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshLambertMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshPhongMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshDepthMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshNormalMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshFaceMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/MeshShaderMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/ParticleBasicMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/ParticleCanvasMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/ParticleDOMMaterial.js"></script>
+		<script type="text/javascript" src="../src/materials/ShaderMaterial.js"></script>
+		<script type="text/javascript" src="../src/textures/Texture.js"></script>
+		<script type="text/javascript" src="../src/textures/DataTexture.js"></script>
+		<script type="text/javascript" src="../src/objects/Particle.js"></script>
+		<script type="text/javascript" src="../src/objects/ParticleSystem.js"></script>
+		<script type="text/javascript" src="../src/objects/Line.js"></script>
+		<script type="text/javascript" src="../src/objects/Mesh.js"></script>
+		<script type="text/javascript" src="../src/objects/Bone.js"></script>
+		<script type="text/javascript" src="../src/objects/SkinnedMesh.js"></script>
+		<script type="text/javascript" src="../src/objects/Ribbon.js"></script>
+		<script type="text/javascript" src="../src/objects/LOD.js"></script>
+		<script type="text/javascript" src="../src/objects/Sprite.js"></script>
+		<script type="text/javascript" src="../src/scenes/Scene.js"></script>
+		<script type="text/javascript" src="../src/scenes/Fog.js"></script>
+		<script type="text/javascript" src="../src/scenes/FogExp2.js"></script>
+		<script type="text/javascript" src="../src/renderers/DOMRenderer.js"></script>
+		<script type="text/javascript" src="../src/renderers/CanvasRenderer.js"></script>
+		<script type="text/javascript" src="../src/renderers/SVGRenderer.js"></script>
+		<script type="text/javascript" src="../src/renderers/WebGLShaders.js"></script>
+		<script type="text/javascript" src="../src/renderers/WebGLRenderer.js"></script>
+		<script type="text/javascript" src="../src/renderers/WebGLRenderTarget.js"></script>
+		<script type="text/javascript" src="../src/renderers/WebGLRenderTargetCube.js"></script>
+		<script type="text/javascript" src="../src/renderers/renderables/RenderableVertex.js"></script>
+		<script type="text/javascript" src="../src/renderers/renderables/RenderableFace3.js"></script>
+		<script type="text/javascript" src="../src/renderers/renderables/RenderableFace4.js"></script>
+		<script type="text/javascript" src="../src/renderers/renderables/RenderableObject.js"></script>
+		<script type="text/javascript" src="../src/renderers/renderables/RenderableParticle.js"></script>
+		<script type="text/javascript" src="../src/renderers/renderables/RenderableLine.js"></script>
+		<script type="text/javascript" src="../src/extras/ColorUtils.js"></script>
+		<script type="text/javascript" src="../src/extras/GeometryUtils.js"></script>
+		<script type="text/javascript" src="../src/extras/ImageUtils.js"></script>
+		<script type="text/javascript" src="../src/extras/SceneUtils.js"></script>
+		<script type="text/javascript" src="../src/extras/ShaderUtils.js"></script>
+		<script type="text/javascript" src="../src/extras/core/Curve.js"></script>
+		<script type="text/javascript" src="../src/extras/core/CurvePath.js"></script>
+		<script type="text/javascript" src="../src/extras/core/Path.js"></script>
+		<script type="text/javascript" src="../src/extras/core/Shape.js"></script>
+		<script type="text/javascript" src="../src/extras/core/TextPath.js"></script>
+		<script type="text/javascript" src="../src/extras/animation/AnimationHandler.js"></script>
+		<script type="text/javascript" src="../src/extras/animation/Animation.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/CubeCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/FirstPersonCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/PathCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/FlyCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/RollCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/TrackballCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/cameras/CombinedCamera.js"></script>
+		<script type="text/javascript" src="../src/extras/controls/FirstPersonControls.js"></script>
+		<script type="text/javascript" src="../src/extras/controls/PathControls.js"></script>
+		<script type="text/javascript" src="../src/extras/controls/FlyControls.js"></script>
+		<script type="text/javascript" src="../src/extras/controls/RollControls.js"></script>
+		<script type="text/javascript" src="../src/extras/controls/TrackballControls.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/CubeGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/CylinderGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/ExtrudeGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/IcosahedronGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/LatheGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/OctahedronGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/PlaneGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/SphereGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/TextGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/TorusGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/geometries/TorusKnotGeometry.js"></script>
+		<script type="text/javascript" src="../src/extras/modifiers/SubdivisionModifier.js"></script>
+		<script type="text/javascript" src="../src/extras/loaders/Loader.js"></script>
+		<script type="text/javascript" src="../src/extras/loaders/BinaryLoader.js"></script>
+		<script type="text/javascript" src="../src/extras/loaders/ColladaLoader.js"></script>
+		<script type="text/javascript" src="../src/extras/loaders/JSONLoader.js"></script>
+		<script type="text/javascript" src="../src/extras/loaders/SceneLoader.js"></script>
+		<script type="text/javascript" src="../src/extras/loaders/UTF8Loader.js"></script>
+		<script type="text/javascript" src="../src/extras/objects/Axes.js"></script>
+		<script type="text/javascript" src="../src/extras/objects/MarchingCubes.js"></script>
+		<script type="text/javascript" src="../src/extras/physics/Collisions.js"></script>
+		<script type="text/javascript" src="../src/extras/physics/CollisionUtils.js"></script>
+		<script type="text/javascript" src="../src/extras/renderers/AnaglyphWebGLRenderer.js"></script>
+		<script type="text/javascript" src="../src/extras/renderers/CrosseyedWebGLRenderer.js"></script>
+
+		<script src="js/ShaderExtras.js"></script>
+
+		<script src="js/postprocessing/EffectComposer.js"></script>
+		<script src="js/postprocessing/RenderPass.js"></script>
+		<script src="js/postprocessing/BloomPass.js"></script>
+		<script src="js/postprocessing/ShaderPass.js"></script>
+		<script src="js/postprocessing/MaskPass.js"></script>
+		<script src="js/postprocessing/SavePass.js"></script>
+
+
+		<script src="js/Detector.js"></script>
+		<script src="js/RequestAnimationFrame.js"></script>
+		<script src="js/Stats.js"></script>
+
+		<script>
+
+			var MARGIN = 0;
+
+			var SCREEN_WIDTH = window.innerWidth;
+			var SCREEN_HEIGHT = window.innerHeight - 2 * MARGIN;
+
+			var FAR = 10000;
+
+			var container, stats;
+
+			var camera, scene, renderer;
+
+			var mesh, geometry;
+
+
+			init();
+			animate();
+
+			function init() {
+
+				container = document.createElement( 'div' );
+				document.body.appendChild( container );
+
+				camera = new THREE.PerspectiveCamera( 45, SCREEN_WIDTH / SCREEN_HEIGHT, 2, FAR );
+				camera.position.set( 700, 250, 1200 );
+
+				controls = new THREE.TrackballControls( camera );
+
+				controls.rotateSpeed = 1.0;
+				controls.zoomSpeed = 1.2;
+				controls.panSpeed = 0.8;
+
+				controls.noZoom = false;
+				controls.noPan = false;
+
+				controls.staticMoving = true;
+				controls.dynamicDampingFactor = 0.3;
+
+				controls.keys = [ 65, 83, 68 ];
+
+				// CUBE CAMERA
+
+				cubeCamera = new THREE.CubeCamera( 1, FAR, 0, 128 );
+				var cubeTarget = cubeCamera.renderTarget;
+
+
+				scene = new THREE.Scene();
+
+				scene.fog = new THREE.Fog( 0x00aaff, 1000, FAR );
+				scene.fog.color.setHSV( 0.13, 0.25, 0.99 );
+				//THREE.ColorUtils.adjustHSV( scene.fog.color, 0, 0, 0.5 );
+
+				// TEXTURES
+
+				var x = document.createElement( "canvas" );
+				var xc = x.getContext("2d");
+				x.width = x.height = 128;
+				xc.fillStyle = "#fff";
+				xc.fillRect(0, 0, 128, 128);
+				xc.fillStyle = "#000";
+				xc.fillRect(0, 0, 64, 64);
+				xc.fillStyle = "#999";
+				xc.fillRect(32, 32, 32, 32);
+				xc.fillStyle = "#000";
+				xc.fillRect(64, 64, 64, 64);
+				xc.fillStyle = "#555";
+				xc.fillRect(96, 96, 32, 32);
+
+				var texturePattern = new THREE.Texture( x, new THREE.UVMapping(), THREE.RepeatWrapping, THREE.RepeatWrapping );
+				texturePattern.needsUpdate = true;
+				texturePattern.repeat.set( 1000, 1000 );
+
+				var textureSquares = THREE.ImageUtils.loadTexture( "textures/patterns/bright_squares256.png" );
+				textureSquares.wrapS = textureSquares.wrapT = THREE.RepeatWrapping;
+				textureSquares.magFilter = THREE.NearestFilter;
+				textureSquares.repeat.set( 50, 50 );
+
+				var textureNoiseColor = THREE.ImageUtils.loadTexture( "textures/disturb.jpg" );
+				textureNoiseColor.repeat.set( 1, 1 );
+				textureNoiseColor.wrapS = textureNoiseColor.wrapT = THREE.RepeatWrapping;
+
+				var textureLava = THREE.ImageUtils.loadTexture( "textures/lava/lavatile.jpg" );
+				textureLava.repeat.set( 6, 2 );
+				textureLava.wrapS = textureLava.wrapT = THREE.RepeatWrapping;
+
+				//
+
+				var path = "textures/cube/SwedishRoyalCastle/";
+				var format = '.jpg';
+				var urls = [
+						path + 'px' + format, path + 'nx' + format,
+						path + 'py' + format, path + 'ny' + format,
+						path + 'pz' + format, path + 'nz' + format
+					];
+
+				var reflectionCube = THREE.ImageUtils.loadTextureCube( urls );
+
+				// GROUND
+
+				var groundMaterial = new THREE.MeshPhongMaterial( { shininess: 80, ambient: 0x222222, color: 0xffffff, specular: 0xffffff, map: textureSquares } );
+				//groundMaterial.color.setHSV( 0.1, 0.1, 0.99 );
+
+				var planeGeometry = new THREE.PlaneGeometry( 100, 100 );
+
+				var ground = new THREE.Mesh( planeGeometry, groundMaterial );
+				ground.position.set( 0, 0, 0 );
+				ground.rotation.x = -Math.PI/2;
+				ground.scale.set( 1000, 1000, 1000 );
+
+				ground.receiveShadow = true;
+
+				scene.add( ground );
+
+				// MATERIALS
+
+				var shader = THREE.ShaderUtils.lib[ "cube" ];
+				shader.uniforms[ "tCube" ].texture = cubeTarget;
+				shader.uniforms[ "tFlip" ].value = 1;
+
+				var materialCube = new THREE.ShaderMaterial( {
+
+					fragmentShader: shader.fragmentShader,
+					vertexShader: shader.vertexShader,
+					uniforms: shader.uniforms
+
+				} );
+
+				var materialLambert = new THREE.MeshPhongMaterial( { shininess: 50, color: 0xffffff, map: textureNoiseColor } );
+				var materialPhong = new THREE.MeshPhongMaterial( { shininess: 50, ambient: 0x222222, color: 0xffffff, specular: 0x999999, map: textureLava } );
+				var materialPhongCube = new THREE.MeshPhongMaterial( { shininess: 50, ambient: 0x222222, color: 0xffffff, specular: 0x999999, envMap: cubeTarget } );
+
+				// OBJECTS
+
+				var sphereGeometry = new THREE.SphereGeometry( 100, 64, 32 );
+				var torusGeometry = new THREE.TorusGeometry( 240, 60, 32, 64 );
+				var cubeGeometry = new THREE.CubeGeometry( 150, 150, 150 );
+
+				addObject( torusGeometry, materialPhong, 0, 100, 0, 0 );
+				addObject( cubeGeometry, materialLambert, 350, 75, 300, 0 );
+				mesh = addObject( sphereGeometry, materialPhongCube, 350, 100, -350, 0 );
+
+				function addObjectColor( geometry, color, x, y, z, ry ) {
+
+					var material = new THREE.MeshPhongMaterial( { color: color, ambient: 0x222222 } );
+					return addObject( geometry, material, x, y, z, ry );
+
+				}
+
+				function addObject( geometry, material, x, y, z, ry ) {
+
+					var tmpMesh = new THREE.Mesh( geometry, material );
+
+					THREE.ColorUtils.adjustHSV( tmpMesh.materials[ 0 ].color, 0.1, -0.1, 0 );
+
+					tmpMesh.position.set( x, y, z );
+
+					tmpMesh.rotation.y = ry;
+
+					tmpMesh.castShadow = true;
+					tmpMesh.receiveShadow = true;
+
+					scene.add( tmpMesh );
+
+					return tmpMesh;
+
+				}
+
+				var bigCube = new THREE.CubeGeometry( 50, 500, 50 );
+				var midCube = new THREE.CubeGeometry( 50, 200, 50 );
+				var smallCube = new THREE.CubeGeometry( 100, 100, 100 );
+
+				addObjectColor( bigCube,   0xff0000, -500, 250, 0, 0 );
+				addObjectColor( smallCube, 0xff0000, -500, 50, -150, 0 );
+
+				addObjectColor( midCube,   0x00ff00, 500, 100, 0, 0 );
+				addObjectColor( smallCube, 0x00ff00, 500, 50, -150, 0 );
+
+				addObjectColor( midCube,   0x0000ff, 0, 100, -500, 0 );
+				addObjectColor( smallCube, 0x0000ff, -150, 50, -500, 0 );
+
+				addObjectColor( midCube,   0xff00ff, 0, 100, 500, 0 );
+				addObjectColor( smallCube, 0xff00ff, -150, 50, 500, 0 );
+
+				addObjectColor( new THREE.CubeGeometry( 500, 10, 10 ), 0xffff00, 0, 600, 0, Math.PI/4 );
+				addObjectColor( new THREE.CubeGeometry( 250, 10, 10 ), 0xffff00, 0, 600, 0, 0 );
+
+				addObjectColor( new THREE.SphereGeometry( 100, 32, 26 ), 0xffffff, -300, 100, 300, 0 );
+
+				// LIGHTS
+
+				var ambient = new THREE.AmbientLight( 0x222222 );
+				scene.add( ambient );
+
+				var pointLight = new THREE.PointLight( 0xffffff, 1 );
+				pointLight.position.set( -1000, 1000, -1000 );
+				//scene.add( pointLight );
+
+				var spotLight = new THREE.SpotLight( 0xffffff, 1 );
+				spotLight.position.set( 1000, 2000, 1000 );
+				spotLight.castShadow = true;
+				scene.add( spotLight );
+
+				// RENDERER
+
+				renderer = new THREE.WebGLRenderer( { clearColor: 0x00aaff, clearAlpha: 1, antialias: true } );
+				renderer.setSize( SCREEN_WIDTH, SCREEN_HEIGHT );
+
+				if ( scene.fog )
+				renderer.setClearColor( scene.fog.color, 1 );
+
+				renderer.domElement.style.position = "absolute";
+				renderer.domElement.style.top = MARGIN + "px";
+				renderer.domElement.style.left = "0px";
+
+				container.appendChild( renderer.domElement );
+
+
+				//
+
+				renderer.shadowMapEnabled = true;
+				renderer.shadowMapDarkness = 0.75;
+				renderer.shadowMapBias = 0.00390125;
+
+				//
+
+				renderer.gammaInput = true;
+				renderer.gammaOutput = true;
+				renderer.physicallyBasedShading = true;
+
+
+				// STATS
+
+				stats = new Stats();
+				stats.domElement.style.position = 'absolute';
+				stats.domElement.style.top = '0px';
+				stats.domElement.style.zIndex = 100;
+
+				stats.domElement.children[ 0 ].children[ 0 ].style.color = "#222";
+				stats.domElement.children[ 0 ].style.background = "transparent";
+				stats.domElement.children[ 0 ].children[ 1 ].style.display = "none";
+
+				container.appendChild( stats.domElement );
+
+				// EVENTS
+
+				window.addEventListener( 'resize', onWindowResize, false );
+
+				// COMPOSER
+
+				renderer.autoClear = false;
+
+				renderTargetParameters = { minFilter: THREE.LinearFilter, magFilter: THREE.LinearFilter, format: THREE.RGBFormat, stencilBufer: false };
+				renderTarget = new THREE.WebGLRenderTarget( SCREEN_WIDTH, SCREEN_HEIGHT, renderTargetParameters );
+
+				effectFXAA = new THREE.ShaderPass( THREE.ShaderExtras[ "fxaa" ] );
+				var effectVignette = new THREE.ShaderPass( THREE.ShaderExtras[ "vignette" ] );
+
+				hblur = new THREE.ShaderPass( THREE.ShaderExtras[ "horizontalTiltShift" ] );
+				vblur = new THREE.ShaderPass( THREE.ShaderExtras[ "verticalTiltShift" ] );
+
+				var bluriness = 4;
+
+				hblur.uniforms[ 'h' ].value = bluriness / SCREEN_WIDTH;
+				vblur.uniforms[ 'v' ].value = bluriness / SCREEN_HEIGHT;
+
+				hblur.uniforms[ 'r' ].value = vblur.uniforms[ 'r' ].value = 0.5;
+
+				effectFXAA.uniforms[ 'resolution' ].value.set( 1 / SCREEN_WIDTH, 1 / SCREEN_HEIGHT );
+
+				composer = new THREE.EffectComposer( renderer, renderTarget );
+
+				var renderModel = new THREE.RenderPass( scene, camera );
+
+				effectVignette.renderToScreen = true;
+				vblur.renderToScreen = true;
+
+				composer = new THREE.EffectComposer( renderer, renderTarget );
+
+				composer.addPass( renderModel );
+
+				composer.addPass( effectFXAA );
+
+				composer.addPass( hblur );
+				composer.addPass( vblur );
+
+				//composer.addPass( effectVignette );
+
+			}
+
+			//
+
+
+			function onWindowResize( event ) {
+
+				SCREEN_WIDTH = window.innerWidth;
+				SCREEN_HEIGHT = window.innerHeight - 2 * MARGIN;
+
+				renderer.setSize( SCREEN_WIDTH, SCREEN_HEIGHT );
+
+				camera.aspect = SCREEN_WIDTH / SCREEN_HEIGHT;
+				camera.updateProjectionMatrix();
+
+				renderTarget = new THREE.WebGLRenderTarget( SCREEN_WIDTH, SCREEN_HEIGHT, renderTargetParameters );
+
+				composer.reset( renderTarget );
+
+				hblur.uniforms[ 'h' ].value = 4 / SCREEN_WIDTH;
+				vblur.uniforms[ 'v' ].value = 4 / SCREEN_HEIGHT;
+
+				effectFXAA.uniforms[ 'resolution' ].value.set( 1 / SCREEN_WIDTH, 1 / SCREEN_HEIGHT );
+
+			}
+
+			//
+
+			function animate() {
+
+				requestAnimationFrame( animate );
+
+				render();
+				stats.update();
+
+			}
+
+			function render() {
+
+				controls.update();
+
+				mesh.visible = false;
+
+				renderer.autoClear = true;
+				cubeCamera.updatePosition( mesh.position );
+				cubeCamera.updateCubeMap( renderer, scene );
+				renderer.autoClear = false;
+
+				mesh.visible = true;
+
+				//renderer.render( scene, camera );
+				//renderer.clearTarget( null, 1, 1, 1 );
+				composer.render( 0.1 );
+
+			}
+
+		</script>
+
+	</body>
+</html>
+

+ 21 - 1
src/core/Color.js

@@ -12,7 +12,7 @@ THREE.Color = function ( hex ) {
 THREE.Color.prototype = {
 
 	constructor: THREE.Color,
-	
+
 	r: 1, g: 1, b: 1,
 
 	copy: function ( color ) {
@@ -25,6 +25,26 @@ THREE.Color.prototype = {
 
 	},
 
+	copyGammaToLinear: function ( color ) {
+
+		this.r = color.r * color.r;
+		this.g = color.g * color.g;
+		this.b = color.b * color.b;
+
+		return this;
+
+	},
+
+	copyLinearToGamma: function ( color ) {
+
+		this.r = Math.sqrt( color.r );
+		this.g = Math.sqrt( color.g );
+		this.b = Math.sqrt( color.b );
+
+		return this;
+
+	},
+
 	setRGB: function ( r, g, b ) {
 
 		this.r = r;

+ 100 - 16
src/renderers/WebGLRenderer.js

@@ -105,6 +105,12 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 	this.sortObjects = true;
 
+	// physically based shading
+
+	this.gammaInput = false;
+	this.gammaOutput = false;
+	this.physicallyBasedShading = false;
+
 	// shadow map
 
 	this.shadowMapBias = 0.0039;
@@ -412,17 +418,37 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 			if ( light instanceof THREE.AmbientLight ) {
 
-				r += color.r;
-				g += color.g;
-				b += color.b;
+				if ( _this.gammaInput ) {
+
+					r += color.r * color.r;
+					g += color.g * color.g;
+					b += color.b * color.b;
+
+				} else {
+
+					r += color.r;
+					g += color.g;
+					b += color.b;
+
+				}
 
 			} else if ( light instanceof THREE.DirectionalLight ) {
 
 				doffset = dlength * 3;
 
-				dcolors[ doffset ]     = color.r * intensity;
-				dcolors[ doffset + 1 ] = color.g * intensity;
-				dcolors[ doffset + 2 ] = color.b * intensity;
+				if ( _this.gammaInput ) {
+
+					dcolors[ doffset ]     = color.r * color.r * intensity * intensity;
+					dcolors[ doffset + 1 ] = color.g * color.g * intensity * intensity;
+					dcolors[ doffset + 2 ] = color.b * color.b * intensity * intensity;
+
+				} else {
+
+					dcolors[ doffset ]     = color.r * intensity;
+					dcolors[ doffset + 1 ] = color.g * intensity;
+					dcolors[ doffset + 2 ] = color.b * intensity;
+
+				}
 
 				dpositions[ doffset ]     = position.x;
 				dpositions[ doffset + 1 ] = position.y;
@@ -434,9 +460,19 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 				doffset = dlength * 3;
 
-				dcolors[ doffset ]     = color.r * intensity;
-				dcolors[ doffset + 1 ] = color.g * intensity;
-				dcolors[ doffset + 2 ] = color.b * intensity;
+				if ( _this.gammaInput ) {
+
+					dcolors[ doffset ]     = color.r * color.r * intensity * intensity;
+					dcolors[ doffset + 1 ] = color.g * color.g * intensity * intensity;
+					dcolors[ doffset + 2 ] = color.b * color.b * intensity * intensity;
+
+				} else {
+
+					dcolors[ doffset ]     = color.r * intensity;
+					dcolors[ doffset + 1 ] = color.g * intensity;
+					dcolors[ doffset + 2 ] = color.b * intensity;
+
+				}
 
 				n = 1 / position.length();
 
@@ -450,9 +486,19 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 				poffset = plength * 3;
 
-				pcolors[ poffset ]     = color.r * intensity;
-				pcolors[ poffset + 1 ] = color.g * intensity;
-				pcolors[ poffset + 2 ] = color.b * intensity;
+				if ( _this.gammaInput ) {
+
+					pcolors[ poffset ]     = color.r * color.r * intensity * intensity;
+					pcolors[ poffset + 1 ] = color.g * color.g * intensity * intensity;
+					pcolors[ poffset + 2 ] = color.b * color.b * intensity * intensity;
+
+				} else {
+
+					pcolors[ poffset ]     = color.r * intensity;
+					pcolors[ poffset + 1 ] = color.g * intensity;
+					pcolors[ poffset + 2 ] = color.b * intensity;
+
+				}
 
 				ppositions[ poffset ]     = position.x;
 				ppositions[ poffset + 1 ] = position.y;
@@ -2489,9 +2535,18 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 	function refreshUniformsCommon( uniforms, material ) {
 
-		uniforms.diffuse.value = material.color;
 		uniforms.opacity.value = material.opacity;
 
+		if ( _this.gammaInput ) {
+
+			uniforms.diffuse.value.copyGammaToLinear( material.color );
+
+		} else {
+
+			uniforms.diffuse.value = material.color;
+
+		}
+
 		uniforms.map.texture = material.map;
 		if ( material.map ) {
 
@@ -2503,7 +2558,18 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 		uniforms.envMap.texture = material.envMap;
 		uniforms.flipEnvMap.value = ( material.envMap instanceof THREE.WebGLRenderTargetCube ) ? 1 : -1;
-		uniforms.reflectivity.value = material.reflectivity;
+
+		if ( _this.gammaInput ) {
+
+			//uniforms.reflectivity.value = material.reflectivity * material.reflectivity;
+			uniforms.reflectivity.value = material.reflectivity;
+
+		} else {
+
+			uniforms.reflectivity.value = material.reflectivity;
+
+		}
+
 		uniforms.refractionRatio.value = material.refractionRatio;
 		uniforms.combine.value = material.combine;
 		uniforms.useRefract.value = material.envMap && material.envMap.mapping instanceof THREE.CubeRefractionMapping;
@@ -2547,10 +2613,20 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 	function refreshUniformsPhong( uniforms, material ) {
 
-		uniforms.ambient.value = material.ambient;
-		uniforms.specular.value = material.specular;
 		uniforms.shininess.value = material.shininess;
 
+		if ( _this.gammaInput ) {
+
+			uniforms.ambient.value.copyGammaToLinear( material.ambient );
+			uniforms.specular.value.copyGammaToLinear( material.specular );
+
+		} else {
+
+			uniforms.ambient.value = material.ambient;
+			uniforms.specular.value = material.specular;
+
+		}
+
 	};
 
 
@@ -4759,6 +4835,10 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 			_supportsVertexTextures ? "#define VERTEX_TEXTURES" : "",
 
+			_this.gammaInput ? "#define GAMMA_INPUT" : "",
+			_this.gammaOutput ? "#define GAMMA_OUTPUT" : "",
+			_this.physicallyBasedShading ? "#define PHYSICALLY_BASED_SHADING" : "",
+
 			"#define MAX_DIR_LIGHTS " + parameters.maxDirLights,
 			"#define MAX_POINT_LIGHTS " + parameters.maxPointLights,
 
@@ -4837,6 +4917,10 @@ THREE.WebGLRenderer = function ( parameters ) {
 
 			parameters.alphaTest ? "#define ALPHATEST " + parameters.alphaTest: "",
 
+			_this.gammaInput ? "#define GAMMA_INPUT" : "",
+			_this.gammaOutput ? "#define GAMMA_OUTPUT" : "",
+			_this.physicallyBasedShading ? "#define PHYSICALLY_BASED_SHADING" : "",
+
 			( parameters.useFog && parameters.fog ) ? "#define USE_FOG" : "",
 			( parameters.useFog && parameters.fog instanceof THREE.FogExp2 ) ? "#define FOG_EXP2" : "",
 

+ 114 - 12
src/renderers/WebGLShaders.js

@@ -76,6 +76,12 @@ THREE.ShaderChunk = {
 
 			"vec4 cubeColor = textureCube( envMap, vec3( flipEnvMap * vReflect.x, vReflect.yz ) );",
 
+			"#ifdef GAMMA_INPUT",
+
+				"cubeColor.xyz *= cubeColor.xyz;",
+
+			"#endif",
+
 			"if ( combine == 1 ) {",
 
 				"gl_FragColor.xyz = mix( gl_FragColor.xyz, cubeColor.xyz, reflectivity );",
@@ -185,7 +191,18 @@ THREE.ShaderChunk = {
 
 		"#ifdef USE_MAP",
 
-			"gl_FragColor = gl_FragColor * texture2D( map, vUv );",
+			"#ifdef GAMMA_INPUT",
+
+				"vec4 texelColor = texture2D( map, vUv );",
+				"texelColor.xyz *= texelColor.xyz;",
+
+				"gl_FragColor = gl_FragColor * texelColor;",
+
+			"#else",
+
+				"gl_FragColor = gl_FragColor * texture2D( map, vUv );",
+
+			"#endif",
 
 		"#endif"
 
@@ -391,8 +408,18 @@ THREE.ShaderChunk = {
 
 				"float pointSpecularWeight = pow( pointDotNormalHalf, shininess );",
 
+				"#ifdef PHYSICALLY_BASED_SHADING",
+
+					"vec3 schlick = specular + vec3( 1.0 - specular ) * pow( dot( pointVector, pointHalfVector ), 5.0 );",
+					"pointSpecular += schlick * pointLightColor[ i ] * pointSpecularWeight * pointDiffuseWeight * pointDistance;",
+
+				"#else",
+
+					"pointSpecular += specular * pointLightColor[ i ] * pointSpecularWeight * pointDiffuseWeight * pointDistance;",
+
+				"#endif",
+
 				"pointDiffuse  += diffuse * pointLightColor[ i ] * pointDiffuseWeight * pointDistance;",
-				"pointSpecular += specular * pointLightColor[ i ] * pointSpecularWeight * pointDiffuseWeight * pointDistance;",
 
 			"}",
 
@@ -415,8 +442,42 @@ THREE.ShaderChunk = {
 
 				"float dirSpecularWeight = pow( dirDotNormalHalf, shininess );",
 
+				"#ifdef PHYSICALLY_BASED_SHADING",
+
+					/*
+					// fresnel term from skin shader
+					"const float F0 = 0.128;",
+
+					"float base = 1.0 - dot( viewPosition, dirHalfVector );",
+					"float exponential = pow( base, 5.0 );",
+
+					"float fresnel = exponential + F0 * ( 1.0 - exponential );",
+					*/
+
+					/*
+					// fresnel term from fresnel shader
+					"const float mFresnelBias = 0.08;",
+					"const float mFresnelScale = 0.3;",
+					"const float mFresnelPower = 5.0;",
+
+					"float fresnel = mFresnelBias + mFresnelScale * pow( 1.0 + dot( normalize( -viewPosition ), normal ), mFresnelPower );",
+					*/
+
+					// normalization factor
+					//float specularNormalization = ( shininess + 2.0 ) / 8.0;
+
+					//"dirSpecular += specular * directionalLightColor[ i ] * dirSpecularWeight * dirDiffuseWeight * specularNormalization * fresnel;",
+
+					"vec3 schlick = specular + vec3( 1.0 - specular ) * pow( dot( dirVector, dirHalfVector ), 5.0 );",
+					"dirSpecular += schlick * directionalLightColor[ i ] * dirSpecularWeight * dirDiffuseWeight;",
+
+				"#else",
+
+					"dirSpecular += specular * directionalLightColor[ i ] * dirSpecularWeight * dirDiffuseWeight;",
+
+				"#endif",
+
 				"dirDiffuse  += diffuse * directionalLightColor[ i ] * dirDiffuseWeight;",
-				"dirSpecular += specular * directionalLightColor[ i ] * dirSpecularWeight * dirDiffuseWeight;",
 
 			"}",
 
@@ -439,7 +500,7 @@ THREE.ShaderChunk = {
 
 		"#endif",
 
-		"gl_FragColor.xyz = gl_FragColor.xyz * ( totalDiffuse + ambientLightColor * ambient ) + totalSpecular;"
+		"gl_FragColor.xyz = gl_FragColor.xyz * ( totalDiffuse + ambientLightColor * ambient * diffuse ) + totalSpecular;"
 
 	].join("\n"),
 
@@ -481,7 +542,15 @@ THREE.ShaderChunk = {
 
 		"#ifdef USE_COLOR",
 
-			"vColor = color;",
+			"#ifdef GAMMA_INPUT",
+
+				"vColor = color * color;",
+
+			"#else",
+
+				"vColor = color;",
+
+			"#endif",
 
 		"#endif"
 
@@ -600,7 +669,7 @@ THREE.ShaderChunk = {
 
 			"#endif",
 
-			"vec4 shadowColor = vec4( 1.0 );",
+			"vec3 shadowColor = vec3( 1.0 );",
 
 			"for( int i = 0; i < MAX_SHADOWS; i ++ ) {",
 
@@ -634,7 +703,18 @@ THREE.ShaderChunk = {
 
 						"shadow /= 9.0;",
 
-						"shadowColor = shadowColor * vec4( vec3( ( 1.0 - shadowDarkness * shadow ) ), 1.0 );",
+						"#ifdef GAMMA_OUTPUT",
+
+							"vec3 darkening = vec3( ( 1.0 - shadowDarkness * shadow ) );",
+							"darkening *= darkening;",
+
+							"shadowColor = shadowColor * darkening;",
+
+						"#else",
+
+							"shadowColor = shadowColor * vec3( ( 1.0 - shadowDarkness * shadow ) );",
+
+						"#endif",
 
 					"#else",
 
@@ -645,11 +725,11 @@ THREE.ShaderChunk = {
 
 							// spot with multiple shadows is darker
 
-							"shadowColor = shadowColor * vec4( vec3( shadowDarkness ), 1.0 );",
+							"shadowColor = shadowColor * vec3( shadowDarkness );",
 
 							// spot with multiple shadows has the same color as single shadow spot
 
-							//"shadowColor = min( shadowColor, vec4( vec3( shadowDarkness ), 1.0 ) );",
+							//"shadowColor = min( shadowColor, vec3( shadowDarkness ) );",
 
 					"#endif",
 
@@ -658,11 +738,11 @@ THREE.ShaderChunk = {
 
 				// uncomment to see light frustum boundaries
 				//"if ( !( shadowCoord.x >= 0.0 && shadowCoord.x <= 1.0 && shadowCoord.y >= 0.0 && shadowCoord.y <= 1.0 ) )",
-				//	"gl_FragColor =  gl_FragColor * vec4( 1.0, 0.0, 0.0, 1.0 );",
+				//	"gl_FragColor.xyz =  gl_FragColor.xyz * vec3( 1.0, 0.0, 0.0 );",
 
 			"}",
 
-			"gl_FragColor = gl_FragColor * shadowColor;",
+			"gl_FragColor.xyz = gl_FragColor.xyz * shadowColor;",
 
 		"#endif"
 
@@ -703,7 +783,20 @@ THREE.ShaderChunk = {
 
 		"#endif"
 
-	].join("\n")
+	].join("\n"),
+
+	// LINEAR SPACE
+
+	linear_to_gamma_fragment: [
+
+		"#ifdef GAMMA_OUTPUT",
+
+			"gl_FragColor.xyz = sqrt( gl_FragColor.xyz );",
+
+		"#endif"
+
+	].join("\n"),
+
 
 };
 
@@ -1050,6 +1143,9 @@ THREE.ShaderLib = {
 				THREE.ShaderChunk[ "color_fragment" ],
 				THREE.ShaderChunk[ "envmap_fragment" ],
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
+
+				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
+
 				THREE.ShaderChunk[ "fog_fragment" ],
 
 			"}"
@@ -1131,6 +1227,9 @@ THREE.ShaderLib = {
 				THREE.ShaderChunk[ "color_fragment" ],
 				THREE.ShaderChunk[ "envmap_fragment" ],
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
+
+				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
+
 				THREE.ShaderChunk[ "fog_fragment" ],
 
 			"}"
@@ -1230,6 +1329,9 @@ THREE.ShaderLib = {
 				THREE.ShaderChunk[ "color_fragment" ],
 				THREE.ShaderChunk[ "envmap_fragment" ],
 				THREE.ShaderChunk[ "shadowmap_fragment" ],
+
+				THREE.ShaderChunk[ "linear_to_gamma_fragment" ],
+
 				THREE.ShaderChunk[ "fog_fragment" ],
 
 			"}"

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