浏览代码

convert tabs

santi 5 年之前
父节点
当前提交
057e36e06a
共有 1 个文件被更改,包括 443 次插入443 次删除
  1. 443 443
      examples/webgl_gpgpu_birds_gltf.html

+ 443 - 443
examples/webgl_gpgpu_birds_gltf.html

@@ -1,476 +1,476 @@
 <!DOCTYPE html>
 <html lang="en">
-	<head>
-		<title>three.js webgl - gpgpu - flocking</title>
-		<meta charset="utf-8">
-		<meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
-		<link type="text/css" rel="stylesheet" href="main.css">
-		<style>
-			body {
-				background-color: #fff;
-				color: #444;
-			}
-			a {
-				color:#08f;
-			}
-		</style>
-	</head>
-	<body>
+    <head>
+        <title>three.js webgl - gpgpu - flocking</title>
+        <meta charset="utf-8">
+        <meta name="viewport" content="width=device-width, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0">
+        <link type="text/css" rel="stylesheet" href="main.css">
+        <style>
+            body {
+                background-color: #fff;
+                color: #444;
+            }
+            a {
+                color:#08f;
+            }
+        </style>
+    </head>
+    <body>
 
-		<div id="info">
-			<a href="https://threejs.org" target="_blank" rel="noopener">three.js</a> - webgl gpgpu birds + GLTF mesh<br/>
-			Flamingo by <a href="http://mirada.com/">mirada</a> from <a href="http://ro.me">rome</a><br/>
-			Move mouse to disturb birds. 
-		</div>
+        <div id="info">
+            <a href="https://threejs.org" target="_blank" rel="noopener">three.js</a> - webgl gpgpu birds + GLTF mesh<br/>
+            Flamingo by <a href="http://mirada.com/">mirada</a> from <a href="http://ro.me">rome</a><br/>
+            Move mouse to disturb birds. 
+        </div>
 
-		<!-- shader for bird's position -->
-		<script id="fragmentShaderPosition" type="x-shader/x-fragment">
+        <!-- shader for bird's position -->
+        <script id="fragmentShaderPosition" type="x-shader/x-fragment">
 
-			uniform float time;
-			uniform float delta;
+            uniform float time;
+            uniform float delta;
 
-			void main()	{
+            void main()	{
 
-				vec2 uv = gl_FragCoord.xy / resolution.xy;
-				vec4 tmpPos = texture2D( texturePosition, uv );
-				vec3 position = tmpPos.xyz;
-				vec3 velocity = texture2D( textureVelocity, uv ).xyz;
+                vec2 uv = gl_FragCoord.xy / resolution.xy;
+                vec4 tmpPos = texture2D( texturePosition, uv );
+                vec3 position = tmpPos.xyz;
+                vec3 velocity = texture2D( textureVelocity, uv ).xyz;
 
-				float phase = tmpPos.w;
+                float phase = tmpPos.w;
 
-				phase = mod( ( phase + delta +
-					length( velocity.xz ) * delta * 3. +
-					max( velocity.y, 0.0 ) * delta * 6. ), 62.83 );
+                phase = mod( ( phase + delta +
+                    length( velocity.xz ) * delta * 3. +
+                    max( velocity.y, 0.0 ) * delta * 6. ), 62.83 );
 
-				gl_FragColor = vec4( position + velocity * delta * 15. , phase );
+                gl_FragColor = vec4( position + velocity * delta * 15. , phase );
 
-			}
+            }
 
-		</script>
+        </script>
 
-		<!-- shader for bird's velocity -->
-		<script id="fragmentShaderVelocity" type="x-shader/x-fragment">
+        <!-- shader for bird's velocity -->
+        <script id="fragmentShaderVelocity" type="x-shader/x-fragment">
 
-			uniform float time;
-			uniform float testing;
-			uniform float delta; // about 0.016
-			uniform float separationDistance; // 20
-			uniform float alignmentDistance; // 40
-			uniform float cohesionDistance; //
-			uniform float freedomFactor;
-			uniform vec3 predator;
+            uniform float time;
+            uniform float testing;
+            uniform float delta; // about 0.016
+            uniform float separationDistance; // 20
+            uniform float alignmentDistance; // 40
+            uniform float cohesionDistance; //
+            uniform float freedomFactor;
+            uniform vec3 predator;
 
-			const float width = resolution.x;
-			const float height = resolution.y;
+            const float width = resolution.x;
+            const float height = resolution.y;
 
-			const float PI = 3.141592653589793;
-			const float PI_2 = PI * 2.0;
-			// const float VISION = PI * 0.55;
+            const float PI = 3.141592653589793;
+            const float PI_2 = PI * 2.0;
+            // const float VISION = PI * 0.55;
 
-			float zoneRadius = 40.0;
-			float zoneRadiusSquared = 1600.0;
+            float zoneRadius = 40.0;
+            float zoneRadiusSquared = 1600.0;
 
-			float separationThresh = 0.45;
-			float alignmentThresh = 0.65;
+            float separationThresh = 0.45;
+            float alignmentThresh = 0.65;
 
-			const float UPPER_BOUNDS = BOUNDS;
-			const float LOWER_BOUNDS = -UPPER_BOUNDS;
+            const float UPPER_BOUNDS = BOUNDS;
+            const float LOWER_BOUNDS = -UPPER_BOUNDS;
 
-			const float SPEED_LIMIT = 9.0;
+            const float SPEED_LIMIT = 9.0;
 
-			float rand( vec2 co ){
-				return fract( sin( dot( co.xy, vec2(12.9898,78.233) ) ) * 43758.5453 );
-			}
+            float rand( vec2 co ){
+                return fract( sin( dot( co.xy, vec2(12.9898,78.233) ) ) * 43758.5453 );
+            }
 
-			void main() {
+            void main() {
 
-				zoneRadius = separationDistance + alignmentDistance + cohesionDistance;
-				separationThresh = separationDistance / zoneRadius;
-				alignmentThresh = ( separationDistance + alignmentDistance ) / zoneRadius;
-				zoneRadiusSquared = zoneRadius * zoneRadius;
+                zoneRadius = separationDistance + alignmentDistance + cohesionDistance;
+                separationThresh = separationDistance / zoneRadius;
+                alignmentThresh = ( separationDistance + alignmentDistance ) / zoneRadius;
+                zoneRadiusSquared = zoneRadius * zoneRadius;
 
 
-				vec2 uv = gl_FragCoord.xy / resolution.xy;
-				vec3 birdPosition, birdVelocity;
+                vec2 uv = gl_FragCoord.xy / resolution.xy;
+                vec3 birdPosition, birdVelocity;
 
-				vec3 selfPosition = texture2D( texturePosition, uv ).xyz;
-				vec3 selfVelocity = texture2D( textureVelocity, uv ).xyz;
+                vec3 selfPosition = texture2D( texturePosition, uv ).xyz;
+                vec3 selfVelocity = texture2D( textureVelocity, uv ).xyz;
 
-				float dist;
-				vec3 dir; // direction
-				float distSquared;
+                float dist;
+                vec3 dir; // direction
+                float distSquared;
 
-				float separationSquared = separationDistance * separationDistance;
-				float cohesionSquared = cohesionDistance * cohesionDistance;
+                float separationSquared = separationDistance * separationDistance;
+                float cohesionSquared = cohesionDistance * cohesionDistance;
 
-				float f;
-				float percent;
+                float f;
+                float percent;
 
-				vec3 velocity = selfVelocity;
+                vec3 velocity = selfVelocity;
 
-				float limit = SPEED_LIMIT;
+                float limit = SPEED_LIMIT;
 
-				dir = predator * UPPER_BOUNDS - selfPosition;
-				dir.z = 0.;
-				// dir.z *= 0.6;
-				dist = length( dir );
-				distSquared = dist * dist;
+                dir = predator * UPPER_BOUNDS - selfPosition;
+                dir.z = 0.;
+                // dir.z *= 0.6;
+                dist = length( dir );
+                distSquared = dist * dist;
 
-				float preyRadius = 150.0;
-				float preyRadiusSq = preyRadius * preyRadius;
+                float preyRadius = 150.0;
+                float preyRadiusSq = preyRadius * preyRadius;
 
 
-				// move birds away from predator
-				if ( dist < preyRadius ) {
+                // move birds away from predator
+                if ( dist < preyRadius ) {
 
-					f = ( distSquared / preyRadiusSq - 1.0 ) * delta * 100.;
-					velocity += normalize( dir ) * f;
-					limit += 5.0;
-				}
+                    f = ( distSquared / preyRadiusSq - 1.0 ) * delta * 100.;
+                    velocity += normalize( dir ) * f;
+                    limit += 5.0;
+                }
 
 
-				// if (testing == 0.0) {}
-				// if ( rand( uv + time ) < freedomFactor ) {}
+                // if (testing == 0.0) {}
+                // if ( rand( uv + time ) < freedomFactor ) {}
 
 
-				// Attract flocks to the center
-				vec3 central = vec3( 0., 0., 0. );
-				dir = selfPosition - central;
-				dist = length( dir );
+                // Attract flocks to the center
+                vec3 central = vec3( 0., 0., 0. );
+                dir = selfPosition - central;
+                dist = length( dir );
 
-				dir.y *= 2.5;
-				velocity -= normalize( dir ) * delta * 5.;
+                dir.y *= 2.5;
+                velocity -= normalize( dir ) * delta * 5.;
 
-				for ( float y = 0.0; y < height; y++ ) {
-					for ( float x = 0.0; x < width; x++ ) {
+                for ( float y = 0.0; y < height; y++ ) {
+                    for ( float x = 0.0; x < width; x++ ) {
 
-						vec2 ref = vec2( x + 0.5, y + 0.5 ) / resolution.xy;
-						birdPosition = texture2D( texturePosition, ref ).xyz;
+                        vec2 ref = vec2( x + 0.5, y + 0.5 ) / resolution.xy;
+                        birdPosition = texture2D( texturePosition, ref ).xyz;
 
-						dir = birdPosition - selfPosition;
-						dist = length( dir );
+                        dir = birdPosition - selfPosition;
+                        dist = length( dir );
 
-						if ( dist < 0.0001 ) continue;
+                        if ( dist < 0.0001 ) continue;
 
-						distSquared = dist * dist;
+                        distSquared = dist * dist;
 
-						if ( distSquared > zoneRadiusSquared ) continue;
+                        if ( distSquared > zoneRadiusSquared ) continue;
 
-						percent = distSquared / zoneRadiusSquared;
+                        percent = distSquared / zoneRadiusSquared;
 
-						if ( percent < separationThresh ) { // low
+                        if ( percent < separationThresh ) { // low
 
-							// Separation - Move apart for comfort
-							f = ( separationThresh / percent - 1.0 ) * delta;
-							velocity -= normalize( dir ) * f;
+                            // Separation - Move apart for comfort
+                            f = ( separationThresh / percent - 1.0 ) * delta;
+                            velocity -= normalize( dir ) * f;
 
-						} else if ( percent < alignmentThresh ) { // high
+                        } else if ( percent < alignmentThresh ) { // high
 
-							// Alignment - fly the same direction
-							float threshDelta = alignmentThresh - separationThresh;
-							float adjustedPercent = ( percent - separationThresh ) / threshDelta;
+                            // Alignment - fly the same direction
+                            float threshDelta = alignmentThresh - separationThresh;
+                            float adjustedPercent = ( percent - separationThresh ) / threshDelta;
 
-							birdVelocity = texture2D( textureVelocity, ref ).xyz;
+                            birdVelocity = texture2D( textureVelocity, ref ).xyz;
 
-							f = ( 0.5 - cos( adjustedPercent * PI_2 ) * 0.5 + 0.5 ) * delta;
-							velocity += normalize( birdVelocity ) * f;
+                            f = ( 0.5 - cos( adjustedPercent * PI_2 ) * 0.5 + 0.5 ) * delta;
+                            velocity += normalize( birdVelocity ) * f;
 
-						} else {
+                        } else {
 
-							// Attraction / Cohesion - move closer
-							float threshDelta = 1.0 - alignmentThresh;
-							float adjustedPercent = ( percent - alignmentThresh ) / threshDelta;
+                            // Attraction / Cohesion - move closer
+                            float threshDelta = 1.0 - alignmentThresh;
+                            float adjustedPercent = ( percent - alignmentThresh ) / threshDelta;
 
-							f = ( 0.5 - ( cos( adjustedPercent * PI_2 ) * -0.5 + 0.5 ) ) * delta;
+                            f = ( 0.5 - ( cos( adjustedPercent * PI_2 ) * -0.5 + 0.5 ) ) * delta;
 
-							velocity += normalize( dir ) * f;
+                            velocity += normalize( dir ) * f;
 
-						}
+                        }
 
-					}
+                    }
 
-				}
+                }
 
-				// this make tends to fly around than down or up
-				// if (velocity.y > 0.) velocity.y *= (1. - 0.2 * delta);
+                // this make tends to fly around than down or up
+                // if (velocity.y > 0.) velocity.y *= (1. - 0.2 * delta);
 
-				// Speed Limits
-				if ( length( velocity ) > limit ) {
-					velocity = normalize( velocity ) * limit;
-				}
+                // Speed Limits
+                if ( length( velocity ) > limit ) {
+                    velocity = normalize( velocity ) * limit;
+                }
 
-				gl_FragColor = vec4( velocity, 1.0 );
+                gl_FragColor = vec4( velocity, 1.0 );
 
-			}
+            }
 
-		</script>
+        </script>
 
-		<script type="module">
+        <script type="module">
 
-			import * as THREE from '../build/three.module.js';
-			import Stats from './jsm/libs/stats.module.js';
-			import { GUI } from './jsm/libs/dat.gui.module.js';
-			import { GLTFLoader } from './jsm/loaders/GLTFLoader.js';
-			import { GPUComputationRenderer } from './jsm/misc/GPUComputationRenderer.js';
+            import * as THREE from '../build/three.module.js';
+            import Stats from './jsm/libs/stats.module.js';
+            import { GUI } from './jsm/libs/dat.gui.module.js';
+            import { GLTFLoader } from './jsm/loaders/GLTFLoader.js';
+            import { GPUComputationRenderer } from './jsm/misc/GPUComputationRenderer.js';
 
-			/* TEXTURE WIDTH FOR SIMULATION */
-			var WIDTH = 64
-			var BIRDS = WIDTH * WIDTH;
-			
-			/* BAKE ANIMATION INTO TEXTURE and CREATE GEOMETRY FROM BASE MODEL */
-			var BirdGeometry = new THREE.BufferGeometry();
-			var textureAnimation, durationAnimation, originalMaterial,birdMesh, materialShader, vertexPerBird;
-			function nextPowerOf2( n ) { return Math.pow( 2, Math.ceil( Math.log( n ) / Math.log( 2 ) ) ) };
+            /* TEXTURE WIDTH FOR SIMULATION */
+            var WIDTH = 64
+            var BIRDS = WIDTH * WIDTH;
+            
+            /* BAKE ANIMATION INTO TEXTURE and CREATE GEOMETRY FROM BASE MODEL */
+            var BirdGeometry = new THREE.BufferGeometry();
+            var textureAnimation, durationAnimation, originalMaterial,birdMesh, materialShader, vertexPerBird;
+            function nextPowerOf2( n ) { return Math.pow( 2, Math.ceil( Math.log( n ) / Math.log( 2 ) ) ) };
 
-			Math.lerp = function (value1, value2, amount) {
+            Math.lerp = function (value1, value2, amount) {
 
-				amount = Math.max( Math.min( amount, 1 ), 0 );
-				return value1 + (value2 - value1) * amount;
-				
-			};
+                amount = Math.max( Math.min( amount, 1 ), 0 );
+                return value1 + (value2 - value1) * amount;
+                
+            };
 
-			var gltfs = [ 'models/gltf/Parrot.glb', 'models/gltf/Flamingo.glb' ]
+            var gltfs = [ 'models/gltf/Parrot.glb', 'models/gltf/Flamingo.glb' ]
             var colors = [ 0xccFFFF, 0xffdeff ]
             var sizes = [ 0.2, 0.1 ]
-			var selectModel = Math.floor( Math.random() * gltfs.length )
-			new GLTFLoader().load( gltfs[ selectModel ], function ( gltf ) {
+            var selectModel = Math.floor( Math.random() * gltfs.length )
+            new GLTFLoader().load( gltfs[ selectModel ], function ( gltf ) {
 
-				var animations = gltf.animations;
-				durationAnimation = Math.round( animations[ 0 ].duration * 60 );
-				var birdGeo = gltf.scene.children[ 0 ].geometry;
-				originalMaterial = gltf.scene.children[ 0 ].material;
-				var morphAttributes = birdGeo.morphAttributes.position;
-				var tHeight = nextPowerOf2( durationAnimation );
-				var tWidth = nextPowerOf2( birdGeo.getAttribute( 'position' ).count );
-				vertexPerBird = birdGeo.getAttribute( 'position' ).count;
-				var tData = new Float32Array( 3 * tWidth * tHeight );
+                var animations = gltf.animations;
+                durationAnimation = Math.round( animations[ 0 ].duration * 60 );
+                var birdGeo = gltf.scene.children[ 0 ].geometry;
+                originalMaterial = gltf.scene.children[ 0 ].material;
+                var morphAttributes = birdGeo.morphAttributes.position;
+                var tHeight = nextPowerOf2( durationAnimation );
+                var tWidth = nextPowerOf2( birdGeo.getAttribute( 'position' ).count );
+                vertexPerBird = birdGeo.getAttribute( 'position' ).count;
+                var tData = new Float32Array( 3 * tWidth * tHeight );
 
-				for( var i = 0 ; i < tWidth ; i++ ){
+                for( var i = 0 ; i < tWidth ; i++ ){
 
-					for( var j = 0 ; j < tHeight ; j++ ){
+                    for( var j = 0 ; j < tHeight ; j++ ){
 
-						var offset = j * tWidth * 3;
+                        var offset = j * tWidth * 3;
 
-						var curFrame = j;
-						var curMorph = Math.floor( j / durationAnimation * morphAttributes.length );
-						var nextMorph = ( Math.floor( j / durationAnimation * morphAttributes.length ) + 1 ) % morphAttributes.length;
-						var lerpAmount = j / durationAnimation * morphAttributes.length % 1;
+                        var curFrame = j;
+                        var curMorph = Math.floor( j / durationAnimation * morphAttributes.length );
+                        var nextMorph = ( Math.floor( j / durationAnimation * morphAttributes.length ) + 1 ) % morphAttributes.length;
+                        var lerpAmount = j / durationAnimation * morphAttributes.length % 1;
 
-						if( j < durationAnimation ){
+                        if( j < durationAnimation ){
 
-							tData[ offset + i * 3 ] = Math.lerp( morphAttributes[ curMorph ].array[ i * 3 ], morphAttributes[ nextMorph ].array[ i * 3 ], lerpAmount );
-							tData[ offset + i * 3 + 1 ] = Math.lerp( morphAttributes[ curMorph ].array[ i * 3 + 1 ], morphAttributes[ nextMorph ].array[ i * 3 + 1 ], lerpAmount );
-							tData[ offset + i * 3 + 2 ] = Math.lerp( morphAttributes[ curMorph ].array[ i * 3 + 2 ], morphAttributes[ nextMorph ].array[ i * 3 + 2 ], lerpAmount );
-						
-						}
-					}
+                            tData[ offset + i * 3 ] = Math.lerp( morphAttributes[ curMorph ].array[ i * 3 ], morphAttributes[ nextMorph ].array[ i * 3 ], lerpAmount );
+                            tData[ offset + i * 3 + 1 ] = Math.lerp( morphAttributes[ curMorph ].array[ i * 3 + 1 ], morphAttributes[ nextMorph ].array[ i * 3 + 1 ], lerpAmount );
+                            tData[ offset + i * 3 + 2 ] = Math.lerp( morphAttributes[ curMorph ].array[ i * 3 + 2 ], morphAttributes[ nextMorph ].array[ i * 3 + 2 ], lerpAmount );
+                        
+                        }
+                    }
 
-				}
-				
-				textureAnimation = new THREE.DataTexture( tData, tWidth, tHeight, THREE.RGBFormat, THREE.FloatType );
-				textureAnimation.needsUpdate = true;
+                }
+                
+                textureAnimation = new THREE.DataTexture( tData, tWidth, tHeight, THREE.RGBFormat, THREE.FloatType );
+                textureAnimation.needsUpdate = true;
 
-				var vertices = [], color = [], reference = [], seeds = [], indices = [];
-				var totalVertices = birdGeo.getAttribute( 'position' ).count * 3 * BIRDS;
-				for( var i = 0 ; i < totalVertices ; i++ ){
+                var vertices = [], color = [], reference = [], seeds = [], indices = [];
+                var totalVertices = birdGeo.getAttribute( 'position' ).count * 3 * BIRDS;
+                for( var i = 0 ; i < totalVertices ; i++ ){
 
-					var bIndex = i % ( birdGeo.getAttribute( 'position' ).count * 3 );
-					vertices.push( birdGeo.getAttribute( 'position' ).array[ bIndex ] );
-					color.push( birdGeo.getAttribute( 'color' ).array[ bIndex ] );
+                    var bIndex = i % ( birdGeo.getAttribute( 'position' ).count * 3 );
+                    vertices.push( birdGeo.getAttribute( 'position' ).array[ bIndex ] );
+                    color.push( birdGeo.getAttribute( 'color' ).array[ bIndex ] );
 
-				}
+                }
 
-				var r = Math.random();
-				for( var i = 0 ; i < birdGeo.getAttribute( 'position' ).count * BIRDS ; i++ ){
-					
-					var bIndex = i % ( birdGeo.getAttribute( 'position' ).count );
-					var bird = Math.floor( i / birdGeo.getAttribute( 'position' ).count );
-					if( bIndex == 0 ) r = Math.random();
-					var j = ~ ~ bird;
-					var x = ( j % WIDTH ) / WIDTH;
-					var y = ~ ~ ( j / WIDTH ) / WIDTH;
-					reference.push( x, y, bIndex / tWidth, durationAnimation / tHeight );
-					seeds.push( bird, r, Math.random(), Math.random() );
+                var r = Math.random();
+                for( var i = 0 ; i < birdGeo.getAttribute( 'position' ).count * BIRDS ; i++ ){
+                    
+                    var bIndex = i % ( birdGeo.getAttribute( 'position' ).count );
+                    var bird = Math.floor( i / birdGeo.getAttribute( 'position' ).count );
+                    if( bIndex == 0 ) r = Math.random();
+                    var j = ~ ~ bird;
+                    var x = ( j % WIDTH ) / WIDTH;
+                    var y = ~ ~ ( j / WIDTH ) / WIDTH;
+                    reference.push( x, y, bIndex / tWidth, durationAnimation / tHeight );
+                    seeds.push( bird, r, Math.random(), Math.random() );
 
-				}
+                }
 
-				for( var i = 0 ; i < birdGeo.index.array.length * BIRDS ; i++ ){
+                for( var i = 0 ; i < birdGeo.index.array.length * BIRDS ; i++ ){
 
-					var offset = Math.floor( i / birdGeo.index.array.length ) * ( birdGeo.getAttribute( 'position' ).count );				
-					indices.push( birdGeo.index.array[ i % birdGeo.index.array.length ] + offset );
+                    var offset = Math.floor( i / birdGeo.index.array.length ) * ( birdGeo.getAttribute( 'position' ).count );				
+                    indices.push( birdGeo.index.array[ i % birdGeo.index.array.length ] + offset );
 
-				}
+                }
 
-				BirdGeometry.setAttribute( 'position', new THREE.BufferAttribute( new Float32Array( vertices ), 3 ) );
-				BirdGeometry.setAttribute( 'birdColor', new THREE.BufferAttribute( new Float32Array( color ), 3 ) );
-				BirdGeometry.setAttribute( 'color', new THREE.BufferAttribute( new Float32Array( color ), 3 ) );
-				BirdGeometry.setAttribute( 'reference', new THREE.BufferAttribute( new Float32Array( reference ), 4 ) );
-				BirdGeometry.setAttribute( 'seeds', new THREE.BufferAttribute( new Float32Array( seeds ), 4 ) );
+                BirdGeometry.setAttribute( 'position', new THREE.BufferAttribute( new Float32Array( vertices ), 3 ) );
+                BirdGeometry.setAttribute( 'birdColor', new THREE.BufferAttribute( new Float32Array( color ), 3 ) );
+                BirdGeometry.setAttribute( 'color', new THREE.BufferAttribute( new Float32Array( color ), 3 ) );
+                BirdGeometry.setAttribute( 'reference', new THREE.BufferAttribute( new Float32Array( reference ), 4 ) );
+                BirdGeometry.setAttribute( 'seeds', new THREE.BufferAttribute( new Float32Array( seeds ), 4 ) );
 
-				BirdGeometry.setIndex( indices );
+                BirdGeometry.setIndex( indices );
 
-				init();
-				animate();
+                init();
+                animate();
 
-			} );
+            } );
 
-			var container, stats;
-			var camera, scene, renderer;
-			var mouseX = 0, mouseY = 0;
+            var container, stats;
+            var camera, scene, renderer;
+            var mouseX = 0, mouseY = 0;
 
-			var windowHalfX = window.innerWidth / 2;
-			var windowHalfY = window.innerHeight / 2;
+            var windowHalfX = window.innerWidth / 2;
+            var windowHalfY = window.innerHeight / 2;
 
-			var BOUNDS = 800, BOUNDS_HALF = BOUNDS / 2;
+            var BOUNDS = 800, BOUNDS_HALF = BOUNDS / 2;
 
-			var last = performance.now();
+            var last = performance.now();
 
-			var gpuCompute;
-			var velocityVariable;
-			var positionVariable;
-			var positionUniforms;
-			var velocityUniforms;
-			var birdUniforms;
+            var gpuCompute;
+            var velocityVariable;
+            var positionVariable;
+            var positionUniforms;
+            var velocityUniforms;
+            var birdUniforms;
 
-			function init() {
+            function init() {
 
-				container = document.createElement( 'div' );
-				document.body.appendChild( container );
+                container = document.createElement( 'div' );
+                document.body.appendChild( container );
 
-				camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 1, 3000 );
-				camera.position.z = 350;
+                camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 1, 3000 );
+                camera.position.z = 350;
 
-				scene = new THREE.Scene();
-				scene.background = new THREE.Color( colors[ selectModel ] );
-				scene.fog = new THREE.Fog( colors[ selectModel ], 100, 1000 );
+                scene = new THREE.Scene();
+                scene.background = new THREE.Color( colors[ selectModel ] );
+                scene.fog = new THREE.Fog( colors[ selectModel ], 100, 1000 );
 
-				// LIGHTS
+                // LIGHTS
 
-				var hemiLight = new THREE.HemisphereLight( colors[ selectModel ], 0xffffff, 1.6 );
-				hemiLight.color.setHSL( 0.6, 1, 0.6 );
-				hemiLight.groundColor.setHSL( 0.095, 1, 0.75 );
-				hemiLight.position.set( 0, 50, 0 );
-				scene.add( hemiLight );
+                var hemiLight = new THREE.HemisphereLight( colors[ selectModel ], 0xffffff, 1.6 );
+                hemiLight.color.setHSL( 0.6, 1, 0.6 );
+                hemiLight.groundColor.setHSL( 0.095, 1, 0.75 );
+                hemiLight.position.set( 0, 50, 0 );
+                scene.add( hemiLight );
 
-				var dirLight = new THREE.DirectionalLight( 0x00CED1, 0.6 );
-				dirLight.color.setHSL( 0.1, 1, 0.95 );
-				dirLight.position.set( - 1, 1.75, 1 );
-				dirLight.position.multiplyScalar( 30 );
-				scene.add( dirLight );
+                var dirLight = new THREE.DirectionalLight( 0x00CED1, 0.6 );
+                dirLight.color.setHSL( 0.1, 1, 0.95 );
+                dirLight.position.set( - 1, 1.75, 1 );
+                dirLight.position.multiplyScalar( 30 );
+                scene.add( dirLight );
 
-				renderer = new THREE.WebGLRenderer( { antialias : true, alpha : true } );
-				renderer.setPixelRatio( window.devicePixelRatio );
-				renderer.setSize( window.innerWidth, window.innerHeight );
-				container.appendChild( renderer.domElement );
+                renderer = new THREE.WebGLRenderer( { antialias : true, alpha : true } );
+                renderer.setPixelRatio( window.devicePixelRatio );
+                renderer.setSize( window.innerWidth, window.innerHeight );
+                container.appendChild( renderer.domElement );
 
-				initComputeRenderer();
+                initComputeRenderer();
 
-				stats = new Stats();
-				container.appendChild( stats.dom );
+                stats = new Stats();
+                container.appendChild( stats.dom );
 
-				document.addEventListener( 'mousemove', onDocumentMouseMove, false );
-				document.addEventListener( 'touchstart', onDocumentTouchStart, false );
-				document.addEventListener( 'touchmove', onDocumentTouchMove, false );
+                document.addEventListener( 'mousemove', onDocumentMouseMove, false );
+                document.addEventListener( 'touchstart', onDocumentTouchStart, false );
+                document.addEventListener( 'touchmove', onDocumentTouchMove, false );
 
-				window.addEventListener( 'resize', onWindowResize, false );
+                window.addEventListener( 'resize', onWindowResize, false );
 
-				var gui = new GUI();
+                var gui = new GUI();
 
-				var effectController = {
+                var effectController = {
 
-					separation: 20.0,
-					alignment: 20.0,
-					cohesion: 20.0,
-					freedom: 0.75,
-					size: sizes[ selectModel ],
-					count: BIRDS
+                    separation: 20.0,
+                    alignment: 20.0,
+                    cohesion: 20.0,
+                    freedom: 0.75,
+                    size: sizes[ selectModel ],
+                    count: BIRDS
 
-				};
+                };
 
-				var valuesChanger = function () {
+                var valuesChanger = function () {
 
-					velocityUniforms[ "separationDistance" ].value = effectController.separation;
-					velocityUniforms[ "alignmentDistance" ].value = effectController.alignment;
-					velocityUniforms[ "cohesionDistance" ].value = effectController.cohesion;
-					velocityUniforms[ "freedomFactor" ].value = effectController.freedom;
-					if( materialShader ) materialShader.uniforms[ "size" ].value = effectController.size;
-					BirdGeometry.setDrawRange ( 0, vertexPerBird * effectController.count )
+                    velocityUniforms[ "separationDistance" ].value = effectController.separation;
+                    velocityUniforms[ "alignmentDistance" ].value = effectController.alignment;
+                    velocityUniforms[ "cohesionDistance" ].value = effectController.cohesion;
+                    velocityUniforms[ "freedomFactor" ].value = effectController.freedom;
+                    if( materialShader ) materialShader.uniforms[ "size" ].value = effectController.size;
+                    BirdGeometry.setDrawRange ( 0, vertexPerBird * effectController.count )
 
-				};
+                };
 
-				valuesChanger();
+                valuesChanger();
 
                 gui.add( effectController, "separation", 0.0, 100.0, 1.0 ).onChange( valuesChanger );
-				gui.add( effectController, "alignment", 0.0, 100, 0.001 ).onChange( valuesChanger );
-				gui.add( effectController, "cohesion", 0.0, 100, 0.025 ).onChange( valuesChanger );
-				gui.add( effectController, "size", 0, 1, 0.01 ).onChange( valuesChanger );
-				gui.add( effectController, "count", 0, BIRDS, 1 ).onChange( valuesChanger );
-				gui.close();
-
-				initBirds();
-
-			}
-
-			function initComputeRenderer() {
-
-				gpuCompute = new GPUComputationRenderer( WIDTH, WIDTH, renderer );
-
-				var dtPosition = gpuCompute.createTexture();
-				var dtVelocity = gpuCompute.createTexture();
-				fillPositionTexture( dtPosition );
-				fillVelocityTexture( dtVelocity );
-
-				velocityVariable = gpuCompute.addVariable( "textureVelocity", document.getElementById( 'fragmentShaderVelocity' ).textContent, dtVelocity );
-				positionVariable = gpuCompute.addVariable( "texturePosition", document.getElementById( 'fragmentShaderPosition' ).textContent, dtPosition );
-
-				gpuCompute.setVariableDependencies( velocityVariable, [ positionVariable, velocityVariable ] );
-				gpuCompute.setVariableDependencies( positionVariable, [ positionVariable, velocityVariable ] );
-
-				positionUniforms = positionVariable.material.uniforms;
-				velocityUniforms = velocityVariable.material.uniforms;
-
-				positionUniforms[ "time" ] = { value: 0.0 };
-				positionUniforms[ "delta" ] = { value: 0.0 };
-				velocityUniforms[ "time" ] = { value: 1.0 };
-				velocityUniforms[ "delta" ] = { value: 0.0 };
-				velocityUniforms[ "testing" ] = { value: 1.0 };
-				velocityUniforms[ "separationDistance" ] = { value: 1.0 };
-				velocityUniforms[ "alignmentDistance" ] = { value: 1.0 };
-				velocityUniforms[ "cohesionDistance" ] = { value: 1.0 };
-				velocityUniforms[ "freedomFactor" ] = { value: 1.0 };
-				velocityUniforms[ "predator" ] = { value: new THREE.Vector3() };
-				velocityVariable.material.defines.BOUNDS = BOUNDS.toFixed( 2 );
-
-				velocityVariable.wrapS = THREE.RepeatWrapping;
-				velocityVariable.wrapT = THREE.RepeatWrapping;
-				positionVariable.wrapS = THREE.RepeatWrapping;
-				positionVariable.wrapT = THREE.RepeatWrapping;
-				
-				var error = gpuCompute.init();
-				if ( error !== null ) {
-				    console.error( error );
-				}
-			}
-
-			function initBirds() {
-
-				var geometry = BirdGeometry;
-
-				var m = new THREE.MeshStandardMaterial({
-					vertexColors : true,
-					flatShading : true,
-					roughness : 1,
-					metalness : 0
-				})
-
-				m.onBeforeCompile = ( shader ) => {
-
-					shader.uniforms.texturePosition = { value : null };
-					shader.uniforms.textureVelocity = { value : null };
-					shader.uniforms.textureAnimation = { value : textureAnimation };
-					shader.uniforms.time = { value : 1.0 };
-					shader.uniforms.size = { value : 0.1 };
-					shader.uniforms.delta = { value : 0.0 };
+                gui.add( effectController, "alignment", 0.0, 100, 0.001 ).onChange( valuesChanger );
+                gui.add( effectController, "cohesion", 0.0, 100, 0.025 ).onChange( valuesChanger );
+                gui.add( effectController, "size", 0, 1, 0.01 ).onChange( valuesChanger );
+                gui.add( effectController, "count", 0, BIRDS, 1 ).onChange( valuesChanger );
+                gui.close();
+
+                initBirds();
+
+            }
+
+            function initComputeRenderer() {
+
+                gpuCompute = new GPUComputationRenderer( WIDTH, WIDTH, renderer );
+
+                var dtPosition = gpuCompute.createTexture();
+                var dtVelocity = gpuCompute.createTexture();
+                fillPositionTexture( dtPosition );
+                fillVelocityTexture( dtVelocity );
+
+                velocityVariable = gpuCompute.addVariable( "textureVelocity", document.getElementById( 'fragmentShaderVelocity' ).textContent, dtVelocity );
+                positionVariable = gpuCompute.addVariable( "texturePosition", document.getElementById( 'fragmentShaderPosition' ).textContent, dtPosition );
+
+                gpuCompute.setVariableDependencies( velocityVariable, [ positionVariable, velocityVariable ] );
+                gpuCompute.setVariableDependencies( positionVariable, [ positionVariable, velocityVariable ] );
+
+                positionUniforms = positionVariable.material.uniforms;
+                velocityUniforms = velocityVariable.material.uniforms;
+
+                positionUniforms[ "time" ] = { value: 0.0 };
+                positionUniforms[ "delta" ] = { value: 0.0 };
+                velocityUniforms[ "time" ] = { value: 1.0 };
+                velocityUniforms[ "delta" ] = { value: 0.0 };
+                velocityUniforms[ "testing" ] = { value: 1.0 };
+                velocityUniforms[ "separationDistance" ] = { value: 1.0 };
+                velocityUniforms[ "alignmentDistance" ] = { value: 1.0 };
+                velocityUniforms[ "cohesionDistance" ] = { value: 1.0 };
+                velocityUniforms[ "freedomFactor" ] = { value: 1.0 };
+                velocityUniforms[ "predator" ] = { value: new THREE.Vector3() };
+                velocityVariable.material.defines.BOUNDS = BOUNDS.toFixed( 2 );
+
+                velocityVariable.wrapS = THREE.RepeatWrapping;
+                velocityVariable.wrapT = THREE.RepeatWrapping;
+                positionVariable.wrapS = THREE.RepeatWrapping;
+                positionVariable.wrapT = THREE.RepeatWrapping;
+                
+                var error = gpuCompute.init();
+                if ( error !== null ) {
+                    console.error( error );
+                }
+            }
+
+            function initBirds() {
+
+                var geometry = BirdGeometry;
+
+                var m = new THREE.MeshStandardMaterial({
+                    vertexColors : true,
+                    flatShading : true,
+                    roughness : 1,
+                    metalness : 0
+                })
+
+                m.onBeforeCompile = ( shader ) => {
+
+                    shader.uniforms.texturePosition = { value : null };
+                    shader.uniforms.textureVelocity = { value : null };
+                    shader.uniforms.textureAnimation = { value : textureAnimation };
+                    shader.uniforms.time = { value : 1.0 };
+                    shader.uniforms.size = { value : 0.1 };
+                    shader.uniforms.delta = { value : 0.0 };
 
                     var token = '#define STANDARD';
                     
@@ -485,7 +485,7 @@
                         uniform float time;
                     `;
 
-					shader.vertexShader = shader.vertexShader.replace( token, token + insert );
+                    shader.vertexShader = shader.vertexShader.replace( token, token + insert );
 
                     var token = '#include <begin_vertex>';
                         
@@ -519,146 +519,146 @@
                         
                         vec3 transformed = vec3( newPosition );
                     `;
-					
-        			shader.vertexShader = shader.vertexShader.replace( token, insert );
+                    
+                    shader.vertexShader = shader.vertexShader.replace( token, insert );
 
-					materialShader = shader;
+                    materialShader = shader;
 
-				}    
+                }    
 
-				birdMesh = new THREE.Mesh( geometry, m );
-				birdMesh.rotation.y = Math.PI / 2;
-				
-				birdMesh.castShadow = true;
-				birdMesh.receiveShadow = true;
+                birdMesh = new THREE.Mesh( geometry, m );
+                birdMesh.rotation.y = Math.PI / 2;
+                
+                birdMesh.castShadow = true;
+                birdMesh.receiveShadow = true;
 
-				scene.add( birdMesh );
+                scene.add( birdMesh );
 
-			}
+            }
 
-			function fillPositionTexture( texture ) {
+            function fillPositionTexture( texture ) {
 
-				var theArray = texture.image.data;
+                var theArray = texture.image.data;
 
-				for ( var k = 0, kl = theArray.length; k < kl; k += 4 ) {
+                for ( var k = 0, kl = theArray.length; k < kl; k += 4 ) {
 
-					var x = Math.random() * BOUNDS - BOUNDS_HALF;
-					var y = Math.random() * BOUNDS - BOUNDS_HALF;
-					var z = Math.random() * BOUNDS - BOUNDS_HALF;
+                    var x = Math.random() * BOUNDS - BOUNDS_HALF;
+                    var y = Math.random() * BOUNDS - BOUNDS_HALF;
+                    var z = Math.random() * BOUNDS - BOUNDS_HALF;
 
-					theArray[ k + 0 ] = x;
-					theArray[ k + 1 ] = y;
-					theArray[ k + 2 ] = z;
-					theArray[ k + 3 ] = 1;
+                    theArray[ k + 0 ] = x;
+                    theArray[ k + 1 ] = y;
+                    theArray[ k + 2 ] = z;
+                    theArray[ k + 3 ] = 1;
 
-				}
+                }
 
-			}
+            }
 
-			function fillVelocityTexture( texture ) {
+            function fillVelocityTexture( texture ) {
 
-				var theArray = texture.image.data;
+                var theArray = texture.image.data;
 
-				for ( var k = 0, kl = theArray.length; k < kl; k += 4 ) {
+                for ( var k = 0, kl = theArray.length; k < kl; k += 4 ) {
 
-					var x = Math.random() - 0.5;
-					var y = Math.random() - 0.5;
-					var z = Math.random() - 0.5;
+                    var x = Math.random() - 0.5;
+                    var y = Math.random() - 0.5;
+                    var z = Math.random() - 0.5;
 
-					theArray[ k + 0 ] = x * 10;
-					theArray[ k + 1 ] = y * 10;
-					theArray[ k + 2 ] = z * 10;
-					theArray[ k + 3 ] = 1;
+                    theArray[ k + 0 ] = x * 10;
+                    theArray[ k + 1 ] = y * 10;
+                    theArray[ k + 2 ] = z * 10;
+                    theArray[ k + 3 ] = 1;
 
-				}
+                }
 
-			}
+            }
 
 
-			function onWindowResize() {
+            function onWindowResize() {
 
-				windowHalfX = window.innerWidth / 2;
-				windowHalfY = window.innerHeight / 2;
+                windowHalfX = window.innerWidth / 2;
+                windowHalfY = window.innerHeight / 2;
 
-				camera.aspect = window.innerWidth / window.innerHeight;
-				camera.updateProjectionMatrix();
+                camera.aspect = window.innerWidth / window.innerHeight;
+                camera.updateProjectionMatrix();
 
-				renderer.setSize( window.innerWidth, window.innerHeight );
+                renderer.setSize( window.innerWidth, window.innerHeight );
 
-			}
+            }
 
-			function onDocumentMouseMove( event ) {
+            function onDocumentMouseMove( event ) {
 
-				mouseX = event.clientX - windowHalfX;
-				mouseY = event.clientY - windowHalfY;
+                mouseX = event.clientX - windowHalfX;
+                mouseY = event.clientY - windowHalfY;
 
-			}
+            }
 
-			function onDocumentTouchStart( event ) {
+            function onDocumentTouchStart( event ) {
 
-				if ( event.touches.length === 1 ) {
+                if ( event.touches.length === 1 ) {
 
-					event.preventDefault();
+                    event.preventDefault();
 
-					mouseX = event.touches[ 0 ].pageX - windowHalfX;
-					mouseY = event.touches[ 0 ].pageY - windowHalfY;
+                    mouseX = event.touches[ 0 ].pageX - windowHalfX;
+                    mouseY = event.touches[ 0 ].pageY - windowHalfY;
 
-				}
+                }
 
-			}
+            }
 
-			function onDocumentTouchMove( event ) {
+            function onDocumentTouchMove( event ) {
 
-				if ( event.touches.length === 1 ) {
+                if ( event.touches.length === 1 ) {
 
-					event.preventDefault();
+                    event.preventDefault();
 
-					mouseX = event.touches[ 0 ].pageX - windowHalfX;
-					mouseY = event.touches[ 0 ].pageY - windowHalfY;
+                    mouseX = event.touches[ 0 ].pageX - windowHalfX;
+                    mouseY = event.touches[ 0 ].pageY - windowHalfY;
 
-				}
+                }
 
-			}
+            }
 
-			//
+            //
 
-			function animate() {
+            function animate() {
 
-				requestAnimationFrame( animate );
+                requestAnimationFrame( animate );
 
-				render();
-				stats.update();
+                render();
+                stats.update();
 
-			}
+            }
 
-			function render() {
+            function render() {
 
-				var now = performance.now();
-				var delta = ( now - last ) / 1000;
-				
-				if ( delta > 1 ) delta = 1; // safety cap on large deltas
-				last = now;
+                var now = performance.now();
+                var delta = ( now - last ) / 1000;
+                
+                if ( delta > 1 ) delta = 1; // safety cap on large deltas
+                last = now;
 
-				positionUniforms[ "time" ].value = now;
-				positionUniforms[ "delta" ].value = delta;
-				velocityUniforms[ "time" ].value = now;
-				velocityUniforms[ "delta" ].value = delta;
-				if( materialShader ) materialShader.uniforms[ "time" ].value = now;
-				if( materialShader ) materialShader.uniforms[ "delta" ].value = delta;
+                positionUniforms[ "time" ].value = now;
+                positionUniforms[ "delta" ].value = delta;
+                velocityUniforms[ "time" ].value = now;
+                velocityUniforms[ "delta" ].value = delta;
+                if( materialShader ) materialShader.uniforms[ "time" ].value = now;
+                if( materialShader ) materialShader.uniforms[ "delta" ].value = delta;
 
-				velocityUniforms[ "predator" ].value.set( 0.5 * mouseX / windowHalfX, - 0.5 * mouseY / windowHalfY, 0 );
+                velocityUniforms[ "predator" ].value.set( 0.5 * mouseX / windowHalfX, - 0.5 * mouseY / windowHalfY, 0 );
 
-				mouseX = 10000;
-				mouseY = 10000;
+                mouseX = 10000;
+                mouseY = 10000;
 
-				gpuCompute.compute();
-				
-				if( materialShader ) materialShader.uniforms[ "texturePosition" ].value = gpuCompute.getCurrentRenderTarget( positionVariable ).texture;
-				if( materialShader ) materialShader.uniforms[ "textureVelocity" ].value = gpuCompute.getCurrentRenderTarget( velocityVariable ).texture;
-				
-				renderer.render( scene, camera );
-			}
+                gpuCompute.compute();
+                
+                if( materialShader ) materialShader.uniforms[ "texturePosition" ].value = gpuCompute.getCurrentRenderTarget( positionVariable ).texture;
+                if( materialShader ) materialShader.uniforms[ "textureVelocity" ].value = gpuCompute.getCurrentRenderTarget( velocityVariable ).texture;
+                
+                renderer.render( scene, camera );
+            }
 
-		</script>
-	</body>
+        </script>
+    </body>
 </html>