var Scene = (function() {
	var lerp = function(s, e, p) {
		return s - ((s - e) * p);
	}

	return {
		id: getIdForLastLoadedScript(),
		load: function()
		{
			this.scene = new THREE.Scene();
/*
			var ambient = new THREE.AmbientLight( 0xffffff );
			ambient.color.setHSL( 0.1, 0.3, 0.2 );
			this.scene.add( ambient );

			var dirLight = new THREE.DirectionalLight( 0xffffff, 0.125 );
			dirLight.position.set( 0, 10, -20 ).normalize();
			dirLight.color.setHSL( 0.1, 0.7, 0.7 );
			this.scene.add( dirLight );

			var light = new THREE.PointLight( 0xffffff, 1.5, 4500 );
			light.color.setHSL( 0.55, 0.9, 0.5 );
			light.position.set( -10, 10, -10 );
			this.scene.add( light );
*/
			
			/*
			var light = new THREE.HemisphereLight( 0xffffff, 0x000000, .5 );
			light.position.y = 100;
			this.scene.add( light );
			*/

			this.light2 = new THREE.PointLight(0xffffff, 1, 1000);
			//this.light2.castShadow = true;
			this.light2.position.set(50,50,50);
			this.scene.add(this.light2);

			var mat = new THREE.MeshLambertMaterial({
					ambient: 0x999999,
					color: 0xfd7a7b,
					emissive: 0x6a2323,
					shading: THREE.FlatShading,
					side: THREE.DoubleSide,
					wireframe: false
				});

			
			this.skyGeo = new THREE.SphereGeometry(1000, 30,30);
			this.skyMat = new THREE.MeshBasicMaterial({
				color: 0xd1f2e9,
				side: THREE.DoubleSide
			});
			this.sky = new THREE.Mesh(this.skyGeo, this.skyMat);
			this.sky.customOverrideMaterial = new THREE.MeshBasicMaterial({color:0x000000});
			this.scene.add(this.sky);


			this.islandPositions = [
				new THREE.Vector3(0,0,0),
				new THREE.Vector3(25,0,-50),
				new THREE.Vector3(0,0,-100),
				new THREE.Vector3(25,0,-150),
				new THREE.Vector3(0,0,-200),
				new THREE.Vector3(25,0,-250),
				//new THREE.Vector3(0,0,300),
				//new THREE.Vector3(25,0,350),
				//new THREE.Vector3(0,0,400),
			];

			this.cameraPoints = [];
			this.cameraPoints.push(new THREE.Vector3(0,20,100));
			/*for (var i=0; i<this.islandPositions.length; i++)
			{
				var v = this.islandPositions[i];
				this.cameraPoints.push(new THREE.Vector3(v.x, v.y+20, v.z));
			}*/
			this.cameraPoints.push(new THREE.Vector3(0,20,-250));

			this.cameraSpline = new THREE.SplineCurve3(this.cameraPoints);

			var splineMaterial = new THREE.LineBasicMaterial({ color: 0xff0000 });
			var geometry = new THREE.Geometry();
			var splinePoints = this.cameraSpline.getPoints(100);

			for(var i = 0; i < splinePoints.length; i++){
				geometry.vertices.push(splinePoints[i]);  
			}

			var line = new THREE.Line(geometry, splineMaterial);
			//this.scene.add(line);



			this.islands = []
			for (var i=0; i<this.islandPositions.length; i++)
			{
				this.islands.push(new THREE.FloatingIsland(1));
				this.islands[i].position.copy(this.islandPositions[i]);
				this.islands[i].animate(1);
				this.scene.add(this.islands[i]);
			}

			this.islandhouse = new THREE.House(4, 4, 2, 35);
			this.islandhouse.position.copy(new THREE.Vector3(22, 2, -41));
			this.islandhouse.rotation.y = deg2rad(10);
			this.islandhouse.animate(1);
			this.islands[2].add(this.islandhouse);
			
			this.balloon = new THREE.Balloon();
			this.balloon.position.copy(new THREE.Vector3(0, -5, -170));
			this.balloon.scale.set(0.3, 0.3, 0.3);
			this.scene.add(this.balloon);

			this.helper = new THREE.Mesh( new THREE.BoxGeometry(0.2,0.2,0.2,1,1,1), new THREE.MeshBasicMaterial({color:0xff0000}) );
			this.scene.add(this.helper);

			/** Pig 1 **/

			this.safepig1 = new THREE.Pig();
			this.safepig1.scale.multiplyScalar(0.2);
			this.safepig1.position.set(2, 3, 3);
			
			this.safepig1.ground = this.safepig1.position.y;
			this.safepig1.pop = this.safepig1.ground;
			this.safepig1.pop += 4;

			this.islands[1].add(this.safepig1);

			this.poff1 = new THREE.Poff(5, 15, 40, 1);
			this.poff1.animate(0);
			this.safepig1.add(this.poff1);

			/** Pig 2 **/

			this.safepig2 = new THREE.Pig();
			this.safepig2.scale.multiplyScalar(0.2);
			this.safepig2.position.set(-2, 3, 6);

			this.safepig2.ground = this.safepig2.position.y;
			this.safepig2.pop = this.safepig2.ground;
			this.safepig2.pop += 4;

			this.islands[1].add(this.safepig2);

			this.poff2 = new THREE.Poff(5, 15, 40, 1);
			this.poff2.animate(0);
			this.safepig2.add(this.poff2);

			/** Falling pig **/

			this.fallingpig = new THREE.Pig();
			this.fallingpig.scale.multiplyScalar(0.2);
			this.fallingpig.position.copy(this.islands[1].position);
			this.fallingpig.position.y += 6;
			this.fallingpig.position.x -= 8;
			this.fallingpig.position.z -= 30;
			this.fallingpig.pop = this.fallingpig.position.y
			this.fallingpig.ground = this.fallingpig.pop - 20;
			this.scene.add(this.fallingpig);

			this.poff3 = new THREE.Poff(5, 15, 40, 1);
			this.poff3.animate(0);
			this.fallingpig.add(this.poff3);

			/** Gravestone **/

			this.gravestone = new THREE.Gravestone();
			this.gravestone.position.set(8, 1.7, 2);
			this.gravestone.scale.set(0.7, 0.7, 0.7);
			this.islands[2].add(this.gravestone);

			/*
			this.island = new THREE.FloatingIsland(1);
			this.scene.add(this.island);

			this.island2 = new THREE.FloatingIsland(1);
			this.island2.position.set(50,0,0);
			this.scene.add(this.island2);

			this.island3 = new THREE.FloatingIsland(1);
			this.island3.position.set(50,-5,50);
			this.scene.add(this.island3);

			this.island4 = new THREE.FloatingIsland(1);
			this.island4.position.set(0,4,-40);
			this.scene.add(this.island4);
			*/

			//var rock = makeRock(2,4,23423);
			//this.scene.add(rock);

			this.composer = new THREE.EffectComposer(renderer);

			this.camera = new THREE.PerspectiveCamera(45, 16/9, 0.1, 5000);
			this.camera.position.set(0, 20, 20);
			this.camera.lookAt(new THREE.Vector3(0, 0, 0));

			this.controls = new THREE.OrbitControls( this.camera );

			//var material = new THREE.MeshPhongMaterial( { ambient: 0x333333, color: 0xffffff, specular: 0xffffff, shininess: 50 } )

			// SSAO Depth
			this.depthShader = THREE.ShaderLib[ "depthRGBA" ];
			this.depthUniforms = THREE.UniformsUtils.clone( this.depthShader.uniforms );

			this.depthMaterial = new THREE.ShaderMaterial({
				fragmentShader: this.depthShader.fragmentShader,
				vertexShader: this.depthShader.vertexShader,
				uniforms: this.depthUniforms
			});
			this.depthMaterial.blending = THREE.NoBlending;

			this.depthTarget = new THREE.WebGLRenderTarget( wWidth, wHeight, {
				minFilter: THREE.NearestFilter,
				magFilter: THREE.NearestFilter,
				format: THREE.RGBAFormat
			});

			
			this.renderPass = new THREE.RenderPass(this.scene, this.camera);
			this.composer.addPass(this.renderPass);

			this.SSAOPass = new THREE.ShaderPass( THREE.SSAOShader );
			this.SSAOPass.uniforms[ 'tDepth' ].value = this.depthTarget;
			this.SSAOPass.uniforms[ 'size' ].value.set( wWidth * 0.75, wHeight * 0.75 );
			this.SSAOPass.uniforms[ 'cameraNear' ].value = this.camera.near;
			this.SSAOPass.uniforms[ 'cameraFar' ].value = this.camera.far;
			this.SSAOPass.uniforms[ 'aoClamp' ].value = 0.5;
			this.SSAOPass.enabled = true;
			this.composer.addPass( this.SSAOPass );
			
			this.fxaaPass = new THREE.ShaderPass(THREE.FXAAShader);
			this.fxaaPass.uniforms[ 'resolution' ].value = new THREE.Vector2( 1 / wWidth, 1 / wHeight );
			this.composer.addPass(this.fxaaPass);
			

			this.composer.addPass(final_pass);
		},

		render: function(time, percent) 
		{
			
			//this.controls.update();



			var campos = this.cameraSpline.getPointAt(getVal('percent')/100)
			var lookpos = this.cameraSpline.getPointAt(getVal('var1')/100)
			
			//console.log(campos);
			

			//this.controls.update();

			var camVector = new THREE.Vector3(campos.x + getVal('camx'), campos.y + getVal('camy'), campos.z + getVal('camz'));
			//var lookVector = new THREE.Vector3(lookpos.x + getVal('cam2x'), lookpos.y + getVal('cam2y'), lookpos.z + getVal('cam2z'));
			var lookVector = new THREE.Vector3( deg2rad(getVal('cam2x')), deg2rad(getVal('cam2y')), deg2rad(getVal('cam2z')) );

			this.camera.position.copy(camVector);
			//this.camera.lookAt(lookVector);

			this.camera.rotation.set(lookVector.x, lookVector.y, lookVector.z);

			var cam_islandoffset = new THREE.Vector3().subVectors(this.camera.position, this.islands[1].position);
			cam_islandoffset.y = 0;

			this.safepig1.lookAt(cam_islandoffset);
			this.safepig2.lookAt(cam_islandoffset);

			// Pig 1

			var pigscale = 0.00001 + segmentTransition(0.60, 0.65, getVal('var3'));
			this.poff1.animate(pigscale);
			pigscale = easeOne('easeOutElastic', pigscale) * 0.2;
			this.safepig1.scale.set(pigscale, pigscale, pigscale);

			//this.poof.animate(segmentTransition(0.0, 1.0, getVal('var3')));
			this.safepig1.position.y = morph(this.safepig1.pop, this.safepig1.ground, easeOne('easeOutBounce', segmentTransition(0.65, 0.77, getVal('var3'))));
			this.safepig1.visible = (getVal('var3') > 0.60);

			// Pig 2

			var pigscale = 0.00001 + segmentTransition(0.65, 0.70, getVal('var3'));
			this.poff2.animate(pigscale);
			pigscale = easeOne('easeOutElastic', pigscale) * 0.2;
			this.safepig2.scale.set(pigscale, pigscale, pigscale);

			this.safepig2.position.y = morph(this.safepig2.pop, this.safepig2.ground, easeOne('easeOutBounce', segmentTransition(0.70, 0.83, getVal('var3'))));
			this.safepig2.visible = (getVal('var3') > 0.65);

			// Falling Pig

			var pigscale = 0.00001 + segmentTransition(0.80, 0.85, getVal('var3'));
			this.poff3.animate(pigscale);
			pigscale = easeOne('easeOutElastic', pigscale) * 0.2;
			this.fallingpig.scale.set(pigscale, pigscale, pigscale);			

			this.fallingpig.position.y = morph(this.fallingpig.pop, this.fallingpig.ground, easeOne('easeInQuint', segmentTransition(76, 78, time)));
			this.fallingpig.visible = (getVal('var3') > 0.80 && getVal('var3') < 0.99);			

			// Gravestone

			this.gravestone.rotation.x = (1 - easeOne('easeOutBounce', segmentTransition(79, 80, time))) * deg2rad(-90);

/*
			this.camera.position.copy(cameraVector);

			this.camera.lookAt(new THREE.Vector3(0,0,-400));
*/
	
			//this.helper.position.copy(lookVector);

/*
			var islandN = getVal('var3');
			var islandTime = 0.3;

			var lol = (1 - islandTime)/this.islands.length;

			for (var i=0; i<this.islands.length; i++)
			{
				//var ipct = i/(this.islands.length+islandTime);

				var ipct = lol*i;

				var islN = segmentTransition(ipct, ipct+islandTime, islandN);
				this.islands[i].animate(islN);
			}
*/

			this.islands[0].animate(getVal('var2'));
			this.islands[1].animate(getVal('var3'));
			this.islands[2].animate(getVal('var4'));
			this.islands[3].animate(getVal('var5'));
			this.islands[4].animate(getVal('var6'));
			this.islands[5].animate(getVal('var7'));


			this.islandhouse.animate(segmentTransition(0.5, 1.0, getVal('var5')));

			this.balloon.visible = (time > 80);
			this.balloon.position.y = -6 + (segmentTransition(80, 95, time) * 20) + Math.sin(time * 1.5) * 3;
			this.balloon.position.x = 30 - (segmentTransition(76, 92, time) * 50);
			this.balloon.position.z = -180 + (segmentTransition(80, 95, time) * 20);


			/*this.island.position.y = Math.sin(time);
			this.island2.position.y = Math.sin(time+1);
			this.island3.position.y = Math.sin(time+2);
			this.island4.position.y = Math.sin(time+3);
*/
			
			//this.island.rotation.y = time/10;
			//this.island2.rotation.y = time/10;
			//this.island3.rotation.y = time/10;
			//this.island4.rotation.y = time/10;
			


			var n = getVal('var1');

			var n1 = segmentTransition(0.0, 0.7, n);
			var n2 = segmentTransition(0.1, 0.8, n);
			var n3 = segmentTransition(0.2, 0.9, n);
			var n4 = segmentTransition(0.3, 1.0, n);

/*			this.island.animate(n1);
			this.island2.animate(n2);
			this.island3.animate(n3);
			this.island4.animate(n4);
*/
			/*this.mat3.uniforms.time.value = getVal('var1');


			this.light2.position.x = Math.sin(time) * 40;
			this.light2.position.z = Math.cos(time) * 40;*/

			this.poff1.visible = false;
			this.poff2.visible = false;
			this.poff3.visible = false;
			this.scene.overrideMaterial = this.depthMaterial;
			renderer.render( this.scene, this.camera, this.depthTarget );

			this.poff1.visible = true;
			this.poff2.visible = true;
			this.poff3.visible = true;
			this.scene.overrideMaterial = null;
			this.composer.render();

		}
	};
})();

var scenes = scenes || [];
scenes[Scene.id] = Scene;

