7 var THREE = { REVISION:
'73' };
11 if ( typeof define ===
'function' && define.amd ) {
13 define(
'three', THREE );
15 }
else if (
'undefined' !== typeof exports &&
'undefined' !== typeof module ) {
17 module.exports = THREE;
24 if (
self.requestAnimationFrame === undefined ||
self.cancelAnimationFrame === undefined ) {
31 var vendors = [
'ms',
'moz',
'webkit',
'o' ];
33 for ( var x = 0; x < vendors.length && !
self.requestAnimationFrame; ++ x ) {
35 self.requestAnimationFrame =
self[ vendors[ x ] +
'RequestAnimationFrame' ];
36 self.cancelAnimationFrame =
self[ vendors[ x ] +
'CancelAnimationFrame' ] ||
self[ vendors[ x ] +
'CancelRequestAnimationFrame' ];
40 if (
self.requestAnimationFrame === undefined &&
self.setTimeout !== undefined ) {
42 self.requestAnimationFrame =
function ( callback ) {
44 var currTime = Date.now(), timeToCall = Math.max( 0, 16 - ( currTime - lastTime ) );
45 var
id =
self.setTimeout(
function () {
47 callback( currTime + timeToCall );
50 lastTime = currTime + timeToCall;
57 if (
self.cancelAnimationFrame === undefined &&
self.clearTimeout !== undefined ) {
59 self.cancelAnimationFrame =
function ( id ) {
61 self.clearTimeout(
id );
73 if (
self.performance === undefined ) {
75 self.performance = {};
79 if (
self.performance.now === undefined ) {
83 var start = Date.now();
85 self.performance.now =
function () {
87 return Date.now() - start;
97 if ( Number.EPSILON === undefined ) {
99 Number.EPSILON = Math.pow( 2, -52 );
105 if ( Math.sign === undefined ) {
109 Math.sign =
function ( x ) {
111 return ( x < 0 ) ? - 1 : ( x > 0 ) ? 1 : + x;
117 if ( Function.prototype.name === undefined && Object.defineProperty !== undefined ) {
122 Object.defineProperty( Function.prototype,
'name', {
126 return this.toString().match( /^\s*
function\s*(\S*)\s*\(/ )[ 1 ];
136 THREE.MOUSE = { LEFT: 0, MIDDLE: 1, RIGHT: 2 };
140 THREE.CullFaceNone = 0;
141 THREE.CullFaceBack = 1;
142 THREE.CullFaceFront = 2;
143 THREE.CullFaceFrontBack = 3;
145 THREE.FrontFaceDirectionCW = 0;
146 THREE.FrontFaceDirectionCCW = 1;
150 THREE.BasicShadowMap = 0;
151 THREE.PCFShadowMap = 1;
152 THREE.PCFSoftShadowMap = 2;
160 THREE.DoubleSide = 2;
164 THREE.FlatShading = 1;
165 THREE.SmoothShading = 2;
170 THREE.FaceColors = 1;
171 THREE.VertexColors = 2;
175 THREE.NoBlending = 0;
176 THREE.NormalBlending = 1;
177 THREE.AdditiveBlending = 2;
178 THREE.SubtractiveBlending = 3;
179 THREE.MultiplyBlending = 4;
180 THREE.CustomBlending = 5;
186 THREE.AddEquation = 100;
187 THREE.SubtractEquation = 101;
188 THREE.ReverseSubtractEquation = 102;
189 THREE.MinEquation = 103;
190 THREE.MaxEquation = 104;
194 THREE.ZeroFactor = 200;
195 THREE.OneFactor = 201;
196 THREE.SrcColorFactor = 202;
197 THREE.OneMinusSrcColorFactor = 203;
198 THREE.SrcAlphaFactor = 204;
199 THREE.OneMinusSrcAlphaFactor = 205;
200 THREE.DstAlphaFactor = 206;
201 THREE.OneMinusDstAlphaFactor = 207;
211 THREE.DstColorFactor = 208;
212 THREE.OneMinusDstColorFactor = 209;
213 THREE.SrcAlphaSaturateFactor = 210;
217 THREE.NeverDepth = 0;
218 THREE.AlwaysDepth = 1;
220 THREE.LessEqualDepth = 3;
221 THREE.EqualDepth = 4;
222 THREE.GreaterEqualDepth = 5;
223 THREE.GreaterDepth = 6;
224 THREE.NotEqualDepth = 7;
229 THREE.MultiplyOperation = 0;
230 THREE.MixOperation = 1;
231 THREE.AddOperation = 2;
235 THREE.UVMapping = 300;
237 THREE.CubeReflectionMapping = 301;
238 THREE.CubeRefractionMapping = 302;
240 THREE.EquirectangularReflectionMapping = 303;
241 THREE.EquirectangularRefractionMapping = 304;
243 THREE.SphericalReflectionMapping = 305;
247 THREE.RepeatWrapping = 1000;
248 THREE.ClampToEdgeWrapping = 1001;
249 THREE.MirroredRepeatWrapping = 1002;
253 THREE.NearestFilter = 1003;
254 THREE.NearestMipMapNearestFilter = 1004;
255 THREE.NearestMipMapLinearFilter = 1005;
256 THREE.LinearFilter = 1006;
257 THREE.LinearMipMapNearestFilter = 1007;
258 THREE.LinearMipMapLinearFilter = 1008;
262 THREE.UnsignedByteType = 1009;
263 THREE.ByteType = 1010;
264 THREE.ShortType = 1011;
265 THREE.UnsignedShortType = 1012;
266 THREE.IntType = 1013;
267 THREE.UnsignedIntType = 1014;
268 THREE.FloatType = 1015;
269 THREE.HalfFloatType = 1025;
274 THREE.UnsignedShort4444Type = 1016;
275 THREE.UnsignedShort5551Type = 1017;
276 THREE.UnsignedShort565Type = 1018;
280 THREE.AlphaFormat = 1019;
281 THREE.RGBFormat = 1020;
282 THREE.RGBAFormat = 1021;
283 THREE.LuminanceFormat = 1022;
284 THREE.LuminanceAlphaFormat = 1023;
286 THREE.RGBEFormat = THREE.RGBAFormat;
290 THREE.RGB_S3TC_DXT1_Format = 2001;
291 THREE.RGBA_S3TC_DXT1_Format = 2002;
292 THREE.RGBA_S3TC_DXT3_Format = 2003;
293 THREE.RGBA_S3TC_DXT5_Format = 2004;
298 THREE.RGB_PVRTC_4BPPV1_Format = 2100;
299 THREE.RGB_PVRTC_2BPPV1_Format = 2101;
300 THREE.RGBA_PVRTC_4BPPV1_Format = 2102;
301 THREE.RGBA_PVRTC_2BPPV1_Format = 2103;
305 THREE.LoopOnce = 2200;
306 THREE.LoopRepeat = 2201;
307 THREE.LoopPingPong = 2202;
311 THREE.Projector =
function () {
313 console.error(
'THREE.Projector has been moved to /examples/js/renderers/Projector.js.' );
315 this.projectVector =
function ( vector, camera ) {
317 console.warn(
'THREE.Projector: .projectVector() is now vector.project().' );
318 vector.project( camera );
322 this.unprojectVector =
function ( vector, camera ) {
324 console.warn(
'THREE.Projector: .unprojectVector() is now vector.unproject().' );
325 vector.unproject( camera );
329 this.pickingRay =
function ( vector, camera ) {
331 console.error(
'THREE.Projector: .pickingRay() is now raycaster.setFromCamera().' );
337 THREE.CanvasRenderer =
function () {
339 console.error(
'THREE.CanvasRenderer has been moved to /examples/js/renderers/CanvasRenderer.js' );
341 this.domElement = document.createElement(
'canvas' );
342 this.clear =
function () {};
343 this.render =
function () {};
344 this.setClearColor =
function () {};
345 this.setSize =
function () {};
355 THREE.Color =
function ( color ) {
357 if ( arguments.length === 3 ) {
359 return this.fromArray( arguments );
363 return this.set( color );
367 THREE.Color.prototype = {
369 constructor: THREE.Color,
373 set:
function ( value ) {
375 if ( value instanceof THREE.Color ) {
379 }
else if ( typeof value ===
'number' ) {
381 this.setHex( value );
383 }
else if ( typeof value ===
'string' ) {
385 this.setStyle( value );
393 setHex:
function ( hex ) {
395 hex = Math.floor( hex );
397 this.r = ( hex >> 16 & 255 ) / 255;
398 this.g = ( hex >> 8 & 255 ) / 255;
399 this.b = ( hex & 255 ) / 255;
405 setRGB:
function ( r, g, b ) {
415 setHSL:
function () {
417 function hue2rgb( p, q, t ) {
421 if ( t < 1 / 6 )
return p + ( q - p ) * 6 * t;
422 if ( t < 1 / 2 )
return q;
423 if ( t < 2 / 3 )
return p + ( q - p ) * 6 * ( 2 / 3 - t );
428 return function ( h, s, l ) {
431 h = THREE.Math.euclideanModulo( h, 1 );
432 s = THREE.Math.clamp( s, 0, 1 );
433 l = THREE.Math.clamp( l, 0, 1 );
437 this.r = this.g = this.b = l;
441 var p = l <= 0.5 ? l * ( 1 + s ) : l + s - ( l * s );
442 var q = ( 2 * l ) - p;
444 this.r = hue2rgb( q, p, h + 1 / 3 );
445 this.g = hue2rgb( q, p, h );
446 this.b = hue2rgb( q, p, h - 1 / 3 );
456 setStyle:
function ( style ) {
458 function handleAlpha(
string ) {
460 if (
string === undefined )
return;
462 if ( parseFloat(
string ) < 1 ) {
464 console.warn(
'THREE.Color: Alpha component of ' + style +
' will be ignored.' );
473 if ( m = /^((?:rgb|hsl)a?)\(\s*([^\)]*)\)/.exec( style ) ) {
479 var components = m[ 2 ];
486 if ( color = /^(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*(,\s*([0-9]*\.?[0-9]+)\s*)?$/.exec( components ) ) {
489 this.r = Math.min( 255, parseInt( color[ 1 ], 10 ) ) / 255;
490 this.g = Math.min( 255, parseInt( color[ 2 ], 10 ) ) / 255;
491 this.b = Math.min( 255, parseInt( color[ 3 ], 10 ) ) / 255;
493 handleAlpha( color[ 5 ] );
499 if ( color = /^(\d+)\%\s*,\s*(\d+)\%\s*,\s*(\d+)\%\s*(,\s*([0-9]*\.?[0-9]+)\s*)?$/.exec( components ) ) {
502 this.r = Math.min( 100, parseInt( color[ 1 ], 10 ) ) / 100;
503 this.g = Math.min( 100, parseInt( color[ 2 ], 10 ) ) / 100;
504 this.b = Math.min( 100, parseInt( color[ 3 ], 10 ) ) / 100;
506 handleAlpha( color[ 5 ] );
517 if ( color = /^([0-9]*\.?[0-9]+)\s*,\s*(\d+)\%\s*,\s*(\d+)\%\s*(,\s*([0-9]*\.?[0-9]+)\s*)?$/.exec( components ) ) {
520 var h = parseFloat( color[ 1 ] ) / 360;
521 var s = parseInt( color[ 2 ], 10 ) / 100;
522 var l = parseInt( color[ 3 ], 10 ) / 100;
524 handleAlpha( color[ 5 ] );
526 return this.setHSL( h, s, l );
534 }
else if ( m = /^\#([A-Fa-f0-9]+)$/.exec( style ) ) {
539 var size = hex.length;
544 this.r = parseInt( hex.charAt( 0 ) + hex.charAt( 0 ), 16 ) / 255;
545 this.g = parseInt( hex.charAt( 1 ) + hex.charAt( 1 ), 16 ) / 255;
546 this.b = parseInt( hex.charAt( 2 ) + hex.charAt( 2 ), 16 ) / 255;
550 }
else if ( size === 6 ) {
553 this.r = parseInt( hex.charAt( 0 ) + hex.charAt( 1 ), 16 ) / 255;
554 this.g = parseInt( hex.charAt( 2 ) + hex.charAt( 3 ), 16 ) / 255;
555 this.b = parseInt( hex.charAt( 4 ) + hex.charAt( 5 ), 16 ) / 255;
563 if ( style && style.length > 0 ) {
566 var hex = THREE.ColorKeywords[ style ];
568 if ( hex !== undefined ) {
576 console.warn(
'THREE.Color: Unknown color ' + style );
588 return new this.constructor( this.r, this.g, this.b );
592 copy:
function ( color ) {
602 copyGammaToLinear:
function ( color, gammaFactor ) {
604 if ( gammaFactor === undefined ) gammaFactor = 2.0;
606 this.r = Math.pow( color.r, gammaFactor );
607 this.g = Math.pow( color.g, gammaFactor );
608 this.b = Math.pow( color.b, gammaFactor );
614 copyLinearToGamma:
function ( color, gammaFactor ) {
616 if ( gammaFactor === undefined ) gammaFactor = 2.0;
618 var safeInverse = ( gammaFactor > 0 ) ? ( 1.0 / gammaFactor ) : 1.0;
620 this.r = Math.pow( color.r, safeInverse );
621 this.g = Math.pow( color.g, safeInverse );
622 this.b = Math.pow( color.b, safeInverse );
628 convertGammaToLinear:
function () {
630 var r = this.r, g = this.g, b = this.b;
640 convertLinearToGamma:
function () {
642 this.r = Math.sqrt( this.r );
643 this.g = Math.sqrt( this.g );
644 this.b = Math.sqrt( this.b );
650 getHex:
function () {
652 return ( this.r * 255 ) << 16 ^ ( this.g * 255 ) << 8 ^ ( this.b * 255 ) << 0;
656 getHexString:
function () {
658 return (
'000000' + this.getHex().toString( 16 ) ).slice( - 6 );
662 getHSL:
function ( optionalTarget ) {
666 var hsl = optionalTarget || { h: 0, s: 0, l: 0 };
668 var r = this.r, g = this.g, b = this.b;
670 var max = Math.max( r, g, b );
671 var min = Math.min( r, g, b );
674 var lightness = ( min + max ) / 2.0;
683 var delta = max - min;
685 saturation = lightness <= 0.5 ? delta / ( max + min ) : delta / ( 2 - max - min );
689 case r: hue = ( g - b ) / delta + ( g < b ? 6 : 0 );
break;
690 case g: hue = ( b - r ) / delta + 2;
break;
691 case b: hue = ( r - g ) / delta + 4;
break;
707 getStyle:
function () {
709 return 'rgb(' + ( ( this.r * 255 ) | 0 ) +
',' + ( ( this.g * 255 ) | 0 ) +
',' + ( ( this.b * 255 ) | 0 ) +
')';
713 offsetHSL:
function ( h, s, l ) {
715 var hsl = this.getHSL();
717 hsl.h += h; hsl.s += s; hsl.l += l;
719 this.setHSL( hsl.h, hsl.s, hsl.l );
725 add:
function ( color ) {
735 addColors:
function ( color1, color2 ) {
737 this.r = color1.r + color2.r;
738 this.g = color1.g + color2.g;
739 this.b = color1.b + color2.b;
745 addScalar:
function ( s ) {
755 multiply:
function ( color ) {
765 multiplyScalar:
function ( s ) {
775 lerp:
function ( color, alpha ) {
777 this.r += ( color.r - this.r ) * alpha;
778 this.g += ( color.g - this.g ) * alpha;
779 this.b += ( color.b - this.b ) * alpha;
785 equals:
function ( c ) {
787 return ( c.r ===
this.r ) && ( c.g === this.g ) && ( c.b ===
this.b );
791 fromArray:
function ( array, offset ) {
793 if ( offset === undefined ) offset = 0;
795 this.r = array[ offset ];
796 this.g = array[ offset + 1 ];
797 this.b = array[ offset + 2 ];
803 toArray:
function ( array, offset ) {
805 if ( array === undefined ) array = [];
806 if ( offset === undefined ) offset = 0;
808 array[ offset ] = this.r;
809 array[ offset + 1 ] = this.g;
810 array[ offset + 2 ] = this.b;
818 THREE.ColorKeywords = {
'aliceblue': 0xF0F8FF,
'antiquewhite': 0xFAEBD7,
'aqua': 0x00FFFF,
'aquamarine': 0x7FFFD4,
'azure': 0xF0FFFF,
819 'beige': 0xF5F5DC,
'bisque': 0xFFE4C4,
'black': 0x000000,
'blanchedalmond': 0xFFEBCD,
'blue': 0x0000FF,
'blueviolet': 0x8A2BE2,
820 'brown': 0xA52A2A,
'burlywood': 0xDEB887,
'cadetblue': 0x5F9EA0,
'chartreuse': 0x7FFF00,
'chocolate': 0xD2691E,
'coral': 0xFF7F50,
821 'cornflowerblue': 0x6495ED,
'cornsilk': 0xFFF8DC,
'crimson': 0xDC143C,
'cyan': 0x00FFFF,
'darkblue': 0x00008B,
'darkcyan': 0x008B8B,
822 'darkgoldenrod': 0xB8860B,
'darkgray': 0xA9A9A9,
'darkgreen': 0x006400,
'darkgrey': 0xA9A9A9,
'darkkhaki': 0xBDB76B,
'darkmagenta': 0x8B008B,
823 'darkolivegreen': 0x556B2F,
'darkorange': 0xFF8C00,
'darkorchid': 0x9932CC,
'darkred': 0x8B0000,
'darksalmon': 0xE9967A,
'darkseagreen': 0x8FBC8F,
824 'darkslateblue': 0x483D8B,
'darkslategray': 0x2F4F4F,
'darkslategrey': 0x2F4F4F,
'darkturquoise': 0x00CED1,
'darkviolet': 0x9400D3,
825 'deeppink': 0xFF1493,
'deepskyblue': 0x00BFFF,
'dimgray': 0x696969,
'dimgrey': 0x696969,
'dodgerblue': 0x1E90FF,
'firebrick': 0xB22222,
826 'floralwhite': 0xFFFAF0,
'forestgreen': 0x228B22,
'fuchsia': 0xFF00FF,
'gainsboro': 0xDCDCDC,
'ghostwhite': 0xF8F8FF,
'gold': 0xFFD700,
827 'goldenrod': 0xDAA520,
'gray': 0x808080,
'green': 0x008000,
'greenyellow': 0xADFF2F,
'grey': 0x808080,
'honeydew': 0xF0FFF0,
'hotpink': 0xFF69B4,
828 'indianred': 0xCD5C5C,
'indigo': 0x4B0082,
'ivory': 0xFFFFF0,
'khaki': 0xF0E68C,
'lavender': 0xE6E6FA,
'lavenderblush': 0xFFF0F5,
'lawngreen': 0x7CFC00,
829 'lemonchiffon': 0xFFFACD,
'lightblue': 0xADD8E6,
'lightcoral': 0xF08080,
'lightcyan': 0xE0FFFF,
'lightgoldenrodyellow': 0xFAFAD2,
'lightgray': 0xD3D3D3,
830 'lightgreen': 0x90EE90,
'lightgrey': 0xD3D3D3,
'lightpink': 0xFFB6C1,
'lightsalmon': 0xFFA07A,
'lightseagreen': 0x20B2AA,
'lightskyblue': 0x87CEFA,
831 'lightslategray': 0x778899,
'lightslategrey': 0x778899,
'lightsteelblue': 0xB0C4DE,
'lightyellow': 0xFFFFE0,
'lime': 0x00FF00,
'limegreen': 0x32CD32,
832 'linen': 0xFAF0E6,
'magenta': 0xFF00FF,
'maroon': 0x800000,
'mediumaquamarine': 0x66CDAA,
'mediumblue': 0x0000CD,
'mediumorchid': 0xBA55D3,
833 'mediumpurple': 0x9370DB,
'mediumseagreen': 0x3CB371,
'mediumslateblue': 0x7B68EE,
'mediumspringgreen': 0x00FA9A,
'mediumturquoise': 0x48D1CC,
834 'mediumvioletred': 0xC71585,
'midnightblue': 0x191970,
'mintcream': 0xF5FFFA,
'mistyrose': 0xFFE4E1,
'moccasin': 0xFFE4B5,
'navajowhite': 0xFFDEAD,
835 'navy': 0x000080,
'oldlace': 0xFDF5E6,
'olive': 0x808000,
'olivedrab': 0x6B8E23,
'orange': 0xFFA500,
'orangered': 0xFF4500,
'orchid': 0xDA70D6,
836 'palegoldenrod': 0xEEE8AA,
'palegreen': 0x98FB98,
'paleturquoise': 0xAFEEEE,
'palevioletred': 0xDB7093,
'papayawhip': 0xFFEFD5,
'peachpuff': 0xFFDAB9,
837 'peru': 0xCD853F,
'pink': 0xFFC0CB,
'plum': 0xDDA0DD,
'powderblue': 0xB0E0E6,
'purple': 0x800080,
'red': 0xFF0000,
'rosybrown': 0xBC8F8F,
838 'royalblue': 0x4169E1,
'saddlebrown': 0x8B4513,
'salmon': 0xFA8072,
'sandybrown': 0xF4A460,
'seagreen': 0x2E8B57,
'seashell': 0xFFF5EE,
839 'sienna': 0xA0522D,
'silver': 0xC0C0C0,
'skyblue': 0x87CEEB,
'slateblue': 0x6A5ACD,
'slategray': 0x708090,
'slategrey': 0x708090,
'snow': 0xFFFAFA,
840 'springgreen': 0x00FF7F,
'steelblue': 0x4682B4,
'tan': 0xD2B48C,
'teal': 0x008080,
'thistle': 0xD8BFD8,
'tomato': 0xFF6347,
'turquoise': 0x40E0D0,
841 'violet': 0xEE82EE,
'wheat': 0xF5DEB3,
'white': 0xFFFFFF,
'whitesmoke': 0xF5F5F5,
'yellow': 0xFFFF00,
'yellowgreen': 0x9ACD32 };
852 THREE.Quaternion =
function ( x, y, z, w ) {
857 this._w = ( w !== undefined ) ? w : 1;
861 THREE.Quaternion.prototype = {
863 constructor: THREE.Quaternion,
874 this.onChangeCallback();
887 this.onChangeCallback();
900 this.onChangeCallback();
913 this.onChangeCallback();
917 set:
function ( x, y, z, w ) {
924 this.onChangeCallback();
932 return new this.constructor( this._x, this._y, this._z, this._w );
936 copy:
function ( quaternion ) {
938 this._x = quaternion.x;
939 this._y = quaternion.y;
940 this._z = quaternion.z;
941 this._w = quaternion.w;
943 this.onChangeCallback();
949 setFromEuler:
function ( euler, update ) {
951 if ( euler instanceof THREE.Euler ===
false ) {
953 throw new Error(
'THREE.Quaternion: .setFromEuler() now expects a Euler rotation rather than a Vector3 and order.' );
961 var c1 = Math.cos( euler._x / 2 );
962 var c2 = Math.cos( euler._y / 2 );
963 var c3 = Math.cos( euler._z / 2 );
964 var s1 = Math.sin( euler._x / 2 );
965 var s2 = Math.sin( euler._y / 2 );
966 var s3 = Math.sin( euler._z / 2 );
968 var order = euler.order;
970 if ( order ===
'XYZ' ) {
972 this._x = s1 * c2 * c3 + c1 * s2 * s3;
973 this._y = c1 * s2 * c3 - s1 * c2 * s3;
974 this._z = c1 * c2 * s3 + s1 * s2 * c3;
975 this._w = c1 * c2 * c3 - s1 * s2 * s3;
977 }
else if ( order ===
'YXZ' ) {
979 this._x = s1 * c2 * c3 + c1 * s2 * s3;
980 this._y = c1 * s2 * c3 - s1 * c2 * s3;
981 this._z = c1 * c2 * s3 - s1 * s2 * c3;
982 this._w = c1 * c2 * c3 + s1 * s2 * s3;
984 }
else if ( order ===
'ZXY' ) {
986 this._x = s1 * c2 * c3 - c1 * s2 * s3;
987 this._y = c1 * s2 * c3 + s1 * c2 * s3;
988 this._z = c1 * c2 * s3 + s1 * s2 * c3;
989 this._w = c1 * c2 * c3 - s1 * s2 * s3;
991 }
else if ( order ===
'ZYX' ) {
993 this._x = s1 * c2 * c3 - c1 * s2 * s3;
994 this._y = c1 * s2 * c3 + s1 * c2 * s3;
995 this._z = c1 * c2 * s3 - s1 * s2 * c3;
996 this._w = c1 * c2 * c3 + s1 * s2 * s3;
998 }
else if ( order ===
'YZX' ) {
1000 this._x = s1 * c2 * c3 + c1 * s2 * s3;
1001 this._y = c1 * s2 * c3 + s1 * c2 * s3;
1002 this._z = c1 * c2 * s3 - s1 * s2 * c3;
1003 this._w = c1 * c2 * c3 - s1 * s2 * s3;
1005 }
else if ( order ===
'XZY' ) {
1007 this._x = s1 * c2 * c3 - c1 * s2 * s3;
1008 this._y = c1 * s2 * c3 - s1 * c2 * s3;
1009 this._z = c1 * c2 * s3 + s1 * s2 * c3;
1010 this._w = c1 * c2 * c3 + s1 * s2 * s3;
1014 if ( update !==
false ) this.onChangeCallback();
1020 setFromAxisAngle:
function ( axis, angle ) {
1026 var halfAngle = angle / 2, s = Math.sin( halfAngle );
1028 this._x = axis.x * s;
1029 this._y = axis.y * s;
1030 this._z = axis.z * s;
1031 this._w = Math.cos( halfAngle );
1033 this.onChangeCallback();
1039 setFromRotationMatrix:
function ( m ) {
1045 var te = m.elements,
1047 m11 = te[ 0 ], m12 = te[ 4 ], m13 = te[ 8 ],
1048 m21 = te[ 1 ], m22 = te[ 5 ], m23 = te[ 9 ],
1049 m31 = te[ 2 ], m32 = te[ 6 ], m33 = te[ 10 ],
1051 trace = m11 + m22 + m33,
1056 s = 0.5 / Math.sqrt( trace + 1.0 );
1059 this._x = ( m32 - m23 ) * s;
1060 this._y = ( m13 - m31 ) * s;
1061 this._z = ( m21 - m12 ) * s;
1063 }
else if ( m11 > m22 && m11 > m33 ) {
1065 s = 2.0 * Math.sqrt( 1.0 + m11 - m22 - m33 );
1067 this._w = ( m32 - m23 ) / s;
1069 this._y = ( m12 + m21 ) / s;
1070 this._z = ( m13 + m31 ) / s;
1072 }
else if ( m22 > m33 ) {
1074 s = 2.0 * Math.sqrt( 1.0 + m22 - m11 - m33 );
1076 this._w = ( m13 - m31 ) / s;
1077 this._x = ( m12 + m21 ) / s;
1079 this._z = ( m23 + m32 ) / s;
1083 s = 2.0 * Math.sqrt( 1.0 + m33 - m11 - m22 );
1085 this._w = ( m21 - m12 ) / s;
1086 this._x = ( m13 + m31 ) / s;
1087 this._y = ( m23 + m32 ) / s;
1092 this.onChangeCallback();
1098 setFromUnitVectors:
function () {
1108 return function ( vFrom, vTo ) {
1110 if ( v1 === undefined ) v1 =
new THREE.Vector3();
1112 r = vFrom.dot( vTo ) + 1;
1118 if ( Math.abs( vFrom.x ) > Math.abs( vFrom.z ) ) {
1120 v1.set( - vFrom.y, vFrom.x, 0 );
1124 v1.set( 0, - vFrom.z, vFrom.y );
1130 v1.crossVectors( vFrom, vTo );
1147 inverse:
function () {
1149 this.conjugate().normalize();
1155 conjugate:
function () {
1161 this.onChangeCallback();
1167 dot:
function ( v ) {
1169 return this._x * v._x + this._y * v._y + this._z * v._z + this._w * v._w;
1173 lengthSq:
function () {
1175 return this._x * this._x + this._y * this._y + this._z * this._z + this._w * this._w;
1179 length:
function () {
1181 return Math.sqrt( this._x * this._x + this._y * this._y + this._z * this._z + this._w * this._w );
1185 normalize:
function () {
1187 var l = this.length();
1200 this._x = this._x * l;
1201 this._y = this._y * l;
1202 this._z = this._z * l;
1203 this._w = this._w * l;
1207 this.onChangeCallback();
1213 multiply:
function ( q, p ) {
1215 if ( p !== undefined ) {
1217 console.warn(
'THREE.Quaternion: .multiply() now only accepts one argument. Use .multiplyQuaternions( a, b ) instead.' );
1218 return this.multiplyQuaternions( q, p );
1222 return this.multiplyQuaternions(
this, q );
1226 multiplyQuaternions:
function ( a, b ) {
1230 var qax = a._x, qay = a._y, qaz = a._z, qaw = a._w;
1231 var qbx = b._x, qby = b._y, qbz = b._z, qbw = b._w;
1233 this._x = qax * qbw + qaw * qbx + qay * qbz - qaz * qby;
1234 this._y = qay * qbw + qaw * qby + qaz * qbx - qax * qbz;
1235 this._z = qaz * qbw + qaw * qbz + qax * qby - qay * qbx;
1236 this._w = qaw * qbw - qax * qbx - qay * qby - qaz * qbz;
1238 this.onChangeCallback();
1244 multiplyVector3:
function ( vector ) {
1246 console.warn(
'THREE.Quaternion: .multiplyVector3() has been removed. Use is now vector.applyQuaternion( quaternion ) instead.' );
1247 return vector.applyQuaternion(
this );
1251 slerp:
function ( qb, t ) {
1253 if ( t === 0 )
return this;
1254 if ( t === 1 )
return this.copy( qb );
1256 var x = this._x, y = this._y, z = this._z, w = this._w;
1260 var cosHalfTheta = w * qb._w + x * qb._x + y * qb._y + z * qb._z;
1262 if ( cosHalfTheta < 0 ) {
1269 cosHalfTheta = - cosHalfTheta;
1277 if ( cosHalfTheta >= 1.0 ) {
1288 var halfTheta = Math.acos( cosHalfTheta );
1289 var sinHalfTheta = Math.sqrt( 1.0 - cosHalfTheta * cosHalfTheta );
1291 if ( Math.abs( sinHalfTheta ) < 0.001 ) {
1293 this._w = 0.5 * ( w + this._w );
1294 this._x = 0.5 * ( x + this._x );
1295 this._y = 0.5 * ( y + this._y );
1296 this._z = 0.5 * ( z + this._z );
1302 var ratioA = Math.sin( ( 1 - t ) * halfTheta ) / sinHalfTheta,
1303 ratioB = Math.sin( t * halfTheta ) / sinHalfTheta;
1305 this._w = ( w * ratioA + this._w * ratioB );
1306 this._x = ( x * ratioA + this._x * ratioB );
1307 this._y = ( y * ratioA + this._y * ratioB );
1308 this._z = ( z * ratioA + this._z * ratioB );
1310 this.onChangeCallback();
1316 equals:
function ( quaternion ) {
1318 return ( quaternion._x ===
this._x ) && ( quaternion._y === this._y ) && ( quaternion._z ===
this._z ) && ( quaternion._w === this._w );
1322 fromArray:
function ( array, offset ) {
1324 if ( offset === undefined ) offset = 0;
1326 this._x = array[ offset ];
1327 this._y = array[ offset + 1 ];
1328 this._z = array[ offset + 2 ];
1329 this._w = array[ offset + 3 ];
1331 this.onChangeCallback();
1337 toArray:
function ( array, offset ) {
1339 if ( array === undefined ) array = [];
1340 if ( offset === undefined ) offset = 0;
1342 array[ offset ] = this._x;
1343 array[ offset + 1 ] = this._y;
1344 array[ offset + 2 ] = this._z;
1345 array[ offset + 3 ] = this._w;
1351 onChange:
function ( callback ) {
1353 this.onChangeCallback = callback;
1359 onChangeCallback:
function () {}
1363 THREE.Quaternion.slerp =
function ( qa, qb, qm, t ) {
1365 return qm.copy( qa ).slerp( qb, t );
1378 THREE.Vector2 =
function ( x, y ) {
1385 THREE.Vector2.prototype = {
1387 constructor: THREE.Vector2,
1389 get width() {
return this.x },
1390 set width( value ) { this.x = value },
1392 get height() {
return this.y },
1393 set height( value ) { this.y = value },
1397 set:
function ( x, y ) {
1406 setX:
function ( x ) {
1414 setY:
function ( y ) {
1422 setComponent:
function ( index, value ) {
1426 case 0: this.x = value;
break;
1427 case 1: this.y = value;
break;
1428 default:
throw new Error(
'index is out of range: ' + index );
1434 getComponent:
function ( index ) {
1438 case 0:
return this.x;
1439 case 1:
return this.y;
1440 default:
throw new Error(
'index is out of range: ' + index );
1446 clone:
function () {
1448 return new this.constructor( this.x, this.y );
1452 copy:
function ( v ) {
1461 add:
function ( v, w ) {
1463 if ( w !== undefined ) {
1465 console.warn(
'THREE.Vector2: .add() now only accepts one argument. Use .addVectors( a, b ) instead.' );
1466 return this.addVectors( v, w );
1477 addScalar:
function ( s ) {
1486 addVectors:
function ( a, b ) {
1495 addScaledVector:
function ( v, s ) {
1504 sub:
function ( v, w ) {
1506 if ( w !== undefined ) {
1508 console.warn(
'THREE.Vector2: .sub() now only accepts one argument. Use .subVectors( a, b ) instead.' );
1509 return this.subVectors( v, w );
1520 subScalar:
function ( s ) {
1529 subVectors:
function ( a, b ) {
1538 multiply:
function ( v ) {
1547 multiplyScalar:
function ( scalar ) {
1549 if ( isFinite( scalar ) ) {
1561 divide:
function ( v ) {
1570 divideScalar:
function ( scalar ) {
1572 return this.multiplyScalar( 1 / scalar );
1576 min:
function ( v ) {
1578 this.x = Math.min( this.x, v.x );
1579 this.y = Math.min( this.y, v.y );
1585 max:
function ( v ) {
1587 this.x = Math.max( this.x, v.x );
1588 this.y = Math.max( this.y, v.y );
1594 clamp:
function ( min, max ) {
1598 this.x = Math.max( min.x, Math.min( max.x,
this.x ) );
1599 this.y = Math.max( min.y, Math.min( max.y,
this.y ) );
1605 clampScalar:
function () {
1609 return function clampScalar( minVal, maxVal ) {
1611 if ( min === undefined ) {
1613 min =
new THREE.Vector2();
1614 max =
new THREE.Vector2();
1618 min.set( minVal, minVal );
1619 max.set( maxVal, maxVal );
1621 return this.clamp( min, max );
1627 clampLength:
function ( min, max ) {
1629 var length = this.length();
1631 this.multiplyScalar( Math.max( min, Math.min( max, length ) ) / length );
1637 floor:
function () {
1639 this.x = Math.floor( this.x );
1640 this.y = Math.floor( this.y );
1648 this.x = Math.ceil( this.x );
1649 this.y = Math.ceil( this.y );
1655 round:
function () {
1657 this.x = Math.round( this.x );
1658 this.y = Math.round( this.y );
1664 roundToZero:
function () {
1666 this.x = ( this.x < 0 ) ? Math.ceil(
this.x ) : Math.floor( this.x );
1667 this.y = ( this.y < 0 ) ? Math.ceil(
this.y ) : Math.floor( this.y );
1673 negate:
function () {
1682 dot:
function ( v ) {
1684 return this.x * v.x + this.y * v.y;
1688 lengthSq:
function () {
1690 return this.x * this.x + this.y * this.y;
1694 length:
function () {
1696 return Math.sqrt( this.x * this.x + this.y * this.y );
1700 lengthManhattan:
function() {
1702 return Math.abs( this.x ) + Math.abs( this.y );
1706 normalize:
function () {
1708 return this.divideScalar( this.length() );
1712 distanceTo:
function ( v ) {
1714 return Math.sqrt( this.distanceToSquared( v ) );
1718 distanceToSquared:
function ( v ) {
1720 var dx = this.x - v.x, dy = this.y - v.y;
1721 return dx * dx + dy * dy;
1725 setLength:
function ( length ) {
1727 return this.multiplyScalar( length / this.length() );
1731 lerp:
function ( v, alpha ) {
1733 this.x += ( v.x - this.x ) * alpha;
1734 this.y += ( v.y - this.y ) * alpha;
1740 lerpVectors:
function ( v1, v2, alpha ) {
1742 this.subVectors( v2, v1 ).multiplyScalar( alpha ).add( v1 );
1748 equals:
function ( v ) {
1750 return ( ( v.x ===
this.x ) && ( v.y === this.y ) );
1754 fromArray:
function ( array, offset ) {
1756 if ( offset === undefined ) offset = 0;
1758 this.x = array[ offset ];
1759 this.y = array[ offset + 1 ];
1765 toArray:
function ( array, offset ) {
1767 if ( array === undefined ) array = [];
1768 if ( offset === undefined ) offset = 0;
1770 array[ offset ] = this.x;
1771 array[ offset + 1 ] = this.y;
1777 fromAttribute:
function ( attribute, index, offset ) {
1779 if ( offset === undefined ) offset = 0;
1781 index = index * attribute.itemSize + offset;
1783 this.x = attribute.array[ index ];
1784 this.y = attribute.array[ index + 1 ];
1790 rotateAround:
function ( center, angle ) {
1792 var c = Math.cos( angle ), s = Math.sin( angle );
1794 var x = this.x - center.x;
1795 var y = this.y - center.y;
1797 this.x = x * c - y * s + center.x;
1798 this.y = x * s + y * c + center.y;
1817 THREE.Vector3 =
function ( x, y, z ) {
1825 THREE.Vector3.prototype = {
1827 constructor: THREE.Vector3,
1829 set:
function ( x, y, z ) {
1839 setX:
function ( x ) {
1847 setY:
function ( y ) {
1855 setZ:
function ( z ) {
1863 setComponent:
function ( index, value ) {
1867 case 0: this.x = value;
break;
1868 case 1: this.y = value;
break;
1869 case 2: this.z = value;
break;
1870 default:
throw new Error(
'index is out of range: ' + index );
1876 getComponent:
function ( index ) {
1880 case 0:
return this.x;
1881 case 1:
return this.y;
1882 case 2:
return this.z;
1883 default:
throw new Error(
'index is out of range: ' + index );
1889 clone:
function () {
1891 return new this.constructor( this.x, this.y, this.z );
1895 copy:
function ( v ) {
1905 add:
function ( v, w ) {
1907 if ( w !== undefined ) {
1909 console.warn(
'THREE.Vector3: .add() now only accepts one argument. Use .addVectors( a, b ) instead.' );
1910 return this.addVectors( v, w );
1922 addScalar:
function ( s ) {
1932 addVectors:
function ( a, b ) {
1942 addScaledVector:
function ( v, s ) {
1952 sub:
function ( v, w ) {
1954 if ( w !== undefined ) {
1956 console.warn(
'THREE.Vector3: .sub() now only accepts one argument. Use .subVectors( a, b ) instead.' );
1957 return this.subVectors( v, w );
1969 subScalar:
function ( s ) {
1979 subVectors:
function ( a, b ) {
1989 multiply:
function ( v, w ) {
1991 if ( w !== undefined ) {
1993 console.warn(
'THREE.Vector3: .multiply() now only accepts one argument. Use .multiplyVectors( a, b ) instead.' );
1994 return this.multiplyVectors( v, w );
2006 multiplyScalar:
function ( scalar ) {
2008 if ( isFinite( scalar ) ) {
2022 multiplyVectors:
function ( a, b ) {
2032 applyEuler:
function () {
2036 return function applyEuler( euler ) {
2038 if ( euler instanceof THREE.Euler ===
false ) {
2040 console.error(
'THREE.Vector3: .applyEuler() now expects a Euler rotation rather than a Vector3 and order.' );
2044 if ( quaternion === undefined ) quaternion =
new THREE.Quaternion();
2046 this.applyQuaternion( quaternion.setFromEuler( euler ) );
2054 applyAxisAngle:
function () {
2058 return function applyAxisAngle( axis, angle ) {
2060 if ( quaternion === undefined ) quaternion =
new THREE.Quaternion();
2062 this.applyQuaternion( quaternion.setFromAxisAngle( axis, angle ) );
2070 applyMatrix3:
function ( m ) {
2078 this.x = e[ 0 ] * x + e[ 3 ] * y + e[ 6 ] * z;
2079 this.y = e[ 1 ] * x + e[ 4 ] * y + e[ 7 ] * z;
2080 this.z = e[ 2 ] * x + e[ 5 ] * y + e[ 8 ] * z;
2086 applyMatrix4:
function ( m ) {
2090 var x = this.x, y = this.y, z = this.z;
2094 this.x = e[ 0 ] * x + e[ 4 ] * y + e[ 8 ] * z + e[ 12 ];
2095 this.y = e[ 1 ] * x + e[ 5 ] * y + e[ 9 ] * z + e[ 13 ];
2096 this.z = e[ 2 ] * x + e[ 6 ] * y + e[ 10 ] * z + e[ 14 ];
2102 applyProjection:
function ( m ) {
2106 var x = this.x, y = this.y, z = this.z;
2109 var d = 1 / ( e[ 3 ] * x + e[ 7 ] * y + e[ 11 ] * z + e[ 15 ] );
2111 this.x = ( e[ 0 ] * x + e[ 4 ] * y + e[ 8 ] * z + e[ 12 ] ) * d;
2112 this.y = ( e[ 1 ] * x + e[ 5 ] * y + e[ 9 ] * z + e[ 13 ] ) * d;
2113 this.z = ( e[ 2 ] * x + e[ 6 ] * y + e[ 10 ] * z + e[ 14 ] ) * d;
2119 applyQuaternion:
function ( q ) {
2132 var ix = qw * x + qy * z - qz * y;
2133 var iy = qw * y + qz * x - qx * z;
2134 var iz = qw * z + qx * y - qy * x;
2135 var iw = - qx * x - qy * y - qz * z;
2139 this.x = ix * qw + iw * - qx + iy * - qz - iz * - qy;
2140 this.y = iy * qw + iw * - qy + iz * - qx - ix * - qz;
2141 this.z = iz * qw + iw * - qz + ix * - qy - iy * - qx;
2147 project:
function () {
2151 return function project( camera ) {
2153 if ( matrix === undefined ) matrix =
new THREE.Matrix4();
2155 matrix.multiplyMatrices( camera.projectionMatrix, matrix.getInverse( camera.matrixWorld ) );
2156 return this.applyProjection( matrix );
2162 unproject:
function () {
2166 return function unproject( camera ) {
2168 if ( matrix === undefined ) matrix =
new THREE.Matrix4();
2170 matrix.multiplyMatrices( camera.matrixWorld, matrix.getInverse( camera.projectionMatrix ) );
2171 return this.applyProjection( matrix );
2177 transformDirection:
function ( m ) {
2182 var x = this.x, y = this.y, z = this.z;
2186 this.x = e[ 0 ] * x + e[ 4 ] * y + e[ 8 ] * z;
2187 this.y = e[ 1 ] * x + e[ 5 ] * y + e[ 9 ] * z;
2188 this.z = e[ 2 ] * x + e[ 6 ] * y + e[ 10 ] * z;
2196 divide:
function ( v ) {
2206 divideScalar:
function ( scalar ) {
2208 return this.multiplyScalar( 1 / scalar );
2212 min:
function ( v ) {
2214 this.x = Math.min( this.x, v.x );
2215 this.y = Math.min( this.y, v.y );
2216 this.z = Math.min( this.z, v.z );
2222 max:
function ( v ) {
2224 this.x = Math.max( this.x, v.x );
2225 this.y = Math.max( this.y, v.y );
2226 this.z = Math.max( this.z, v.z );
2232 clamp:
function ( min, max ) {
2236 this.x = Math.max( min.x, Math.min( max.x,
this.x ) );
2237 this.y = Math.max( min.y, Math.min( max.y,
this.y ) );
2238 this.z = Math.max( min.z, Math.min( max.z,
this.z ) );
2244 clampScalar:
function () {
2248 return function clampScalar( minVal, maxVal ) {
2250 if ( min === undefined ) {
2252 min =
new THREE.Vector3();
2253 max =
new THREE.Vector3();
2257 min.set( minVal, minVal, minVal );
2258 max.set( maxVal, maxVal, maxVal );
2260 return this.clamp( min, max );
2266 clampLength:
function ( min, max ) {
2268 var length = this.length();
2270 this.multiplyScalar( Math.max( min, Math.min( max, length ) ) / length );
2276 floor:
function () {
2278 this.x = Math.floor( this.x );
2279 this.y = Math.floor( this.y );
2280 this.z = Math.floor( this.z );
2288 this.x = Math.ceil( this.x );
2289 this.y = Math.ceil( this.y );
2290 this.z = Math.ceil( this.z );
2296 round:
function () {
2298 this.x = Math.round( this.x );
2299 this.y = Math.round( this.y );
2300 this.z = Math.round( this.z );
2306 roundToZero:
function () {
2308 this.x = ( this.x < 0 ) ? Math.ceil(
this.x ) : Math.floor( this.x );
2309 this.y = ( this.y < 0 ) ? Math.ceil(
this.y ) : Math.floor( this.y );
2310 this.z = ( this.z < 0 ) ? Math.ceil(
this.z ) : Math.floor( this.z );
2316 negate:
function () {
2326 dot:
function ( v ) {
2328 return this.x * v.x + this.y * v.y + this.z * v.z;
2332 lengthSq:
function () {
2334 return this.x * this.x + this.y * this.y + this.z * this.z;
2338 length:
function () {
2340 return Math.sqrt( this.x * this.x + this.y * this.y + this.z * this.z );
2344 lengthManhattan:
function () {
2346 return Math.abs( this.x ) + Math.abs( this.y ) + Math.abs( this.z );
2350 normalize:
function () {
2352 return this.divideScalar( this.length() );
2356 setLength:
function ( length ) {
2358 return this.multiplyScalar( length / this.length() );
2362 lerp:
function ( v, alpha ) {
2364 this.x += ( v.x - this.x ) * alpha;
2365 this.y += ( v.y - this.y ) * alpha;
2366 this.z += ( v.z - this.z ) * alpha;
2372 lerpVectors:
function ( v1, v2, alpha ) {
2374 this.subVectors( v2, v1 ).multiplyScalar( alpha ).add( v1 );
2380 cross:
function ( v, w ) {
2382 if ( w !== undefined ) {
2384 console.warn(
'THREE.Vector3: .cross() now only accepts one argument. Use .crossVectors( a, b ) instead.' );
2385 return this.crossVectors( v, w );
2389 var x = this.x, y = this.y, z = this.z;
2391 this.x = y * v.z - z * v.y;
2392 this.y = z * v.x - x * v.z;
2393 this.z = x * v.y - y * v.x;
2399 crossVectors:
function ( a, b ) {
2401 var ax = a.x, ay = a.y, az = a.z;
2402 var bx = b.x, by = b.y, bz = b.z;
2404 this.x = ay * bz - az * by;
2405 this.y = az * bx - ax * bz;
2406 this.z = ax * by - ay * bx;
2412 projectOnVector:
function () {
2416 return function projectOnVector( vector ) {
2418 if ( v1 === undefined ) v1 =
new THREE.Vector3();
2420 v1.copy( vector ).normalize();
2422 dot = this.dot( v1 );
2424 return this.copy( v1 ).multiplyScalar( dot );
2430 projectOnPlane:
function () {
2434 return function projectOnPlane( planeNormal ) {
2436 if ( v1 === undefined ) v1 =
new THREE.Vector3();
2438 v1.copy(
this ).projectOnVector( planeNormal );
2440 return this.sub( v1 );
2446 reflect:
function () {
2453 return function reflect( normal ) {
2455 if ( v1 === undefined ) v1 =
new THREE.Vector3();
2457 return this.sub( v1.copy( normal ).multiplyScalar( 2 * this.dot( normal ) ) );
2463 angleTo:
function ( v ) {
2465 var theta = this.dot( v ) / ( this.length() * v.length() );
2469 return Math.acos( THREE.Math.clamp( theta, - 1, 1 ) );
2473 distanceTo:
function ( v ) {
2475 return Math.sqrt( this.distanceToSquared( v ) );
2479 distanceToSquared:
function ( v ) {
2481 var dx = this.x - v.x;
2482 var dy = this.y - v.y;
2483 var dz = this.z - v.z;
2485 return dx * dx + dy * dy + dz * dz;
2489 setEulerFromRotationMatrix:
function ( m, order ) {
2491 console.error(
'THREE.Vector3: .setEulerFromRotationMatrix() has been removed. Use Euler.setFromRotationMatrix() instead.' );
2495 setEulerFromQuaternion:
function ( q, order ) {
2497 console.error(
'THREE.Vector3: .setEulerFromQuaternion() has been removed. Use Euler.setFromQuaternion() instead.' );
2501 getPositionFromMatrix:
function ( m ) {
2503 console.warn(
'THREE.Vector3: .getPositionFromMatrix() has been renamed to .setFromMatrixPosition().' );
2505 return this.setFromMatrixPosition( m );
2509 getScaleFromMatrix:
function ( m ) {
2511 console.warn(
'THREE.Vector3: .getScaleFromMatrix() has been renamed to .setFromMatrixScale().' );
2513 return this.setFromMatrixScale( m );
2517 getColumnFromMatrix:
function ( index, matrix ) {
2519 console.warn(
'THREE.Vector3: .getColumnFromMatrix() has been renamed to .setFromMatrixColumn().' );
2521 return this.setFromMatrixColumn( index, matrix );
2525 setFromMatrixPosition:
function ( m ) {
2527 this.x = m.elements[ 12 ];
2528 this.y = m.elements[ 13 ];
2529 this.z = m.elements[ 14 ];
2535 setFromMatrixScale:
function ( m ) {
2537 var sx = this.set( m.elements[ 0 ], m.elements[ 1 ], m.elements[ 2 ] ).length();
2538 var sy = this.set( m.elements[ 4 ], m.elements[ 5 ], m.elements[ 6 ] ).length();
2539 var sz = this.set( m.elements[ 8 ], m.elements[ 9 ], m.elements[ 10 ] ).length();
2549 setFromMatrixColumn:
function ( index, matrix ) {
2551 var offset = index * 4;
2553 var me = matrix.elements;
2555 this.x = me[ offset ];
2556 this.y = me[ offset + 1 ];
2557 this.z = me[ offset + 2 ];
2563 equals:
function ( v ) {
2565 return ( ( v.x ===
this.x ) && ( v.y === this.y ) && ( v.z ===
this.z ) );
2569 fromArray:
function ( array, offset ) {
2571 if ( offset === undefined ) offset = 0;
2573 this.x = array[ offset ];
2574 this.y = array[ offset + 1 ];
2575 this.z = array[ offset + 2 ];
2581 toArray:
function ( array, offset ) {
2583 if ( array === undefined ) array = [];
2584 if ( offset === undefined ) offset = 0;
2586 array[ offset ] = this.x;
2587 array[ offset + 1 ] = this.y;
2588 array[ offset + 2 ] = this.z;
2594 fromAttribute:
function ( attribute, index, offset ) {
2596 if ( offset === undefined ) offset = 0;
2598 index = index * attribute.itemSize + offset;
2600 this.x = attribute.array[ index ];
2601 this.y = attribute.array[ index + 1 ];
2602 this.z = attribute.array[ index + 2 ];
2620 THREE.Vector4 =
function ( x, y, z, w ) {
2625 this.w = ( w !== undefined ) ? w : 1;
2629 THREE.Vector4.prototype = {
2631 constructor: THREE.Vector4,
2633 set:
function ( x, y, z, w ) {
2644 setX:
function ( x ) {
2652 setY:
function ( y ) {
2660 setZ:
function ( z ) {
2668 setW:
function ( w ) {
2676 setComponent:
function ( index, value ) {
2680 case 0: this.x = value;
break;
2681 case 1: this.y = value;
break;
2682 case 2: this.z = value;
break;
2683 case 3: this.w = value;
break;
2684 default:
throw new Error(
'index is out of range: ' + index );
2690 getComponent:
function ( index ) {
2694 case 0:
return this.x;
2695 case 1:
return this.y;
2696 case 2:
return this.z;
2697 case 3:
return this.w;
2698 default:
throw new Error(
'index is out of range: ' + index );
2704 clone:
function () {
2706 return new this.constructor( this.x, this.y, this.z, this.w );
2710 copy:
function ( v ) {
2715 this.w = ( v.w !== undefined ) ? v.w : 1;
2721 add:
function ( v, w ) {
2723 if ( w !== undefined ) {
2725 console.warn(
'THREE.Vector4: .add() now only accepts one argument. Use .addVectors( a, b ) instead.' );
2726 return this.addVectors( v, w );
2739 addScalar:
function ( s ) {
2750 addVectors:
function ( a, b ) {
2761 addScaledVector:
function ( v, s ) {
2772 sub:
function ( v, w ) {
2774 if ( w !== undefined ) {
2776 console.warn(
'THREE.Vector4: .sub() now only accepts one argument. Use .subVectors( a, b ) instead.' );
2777 return this.subVectors( v, w );
2790 subScalar:
function ( s ) {
2801 subVectors:
function ( a, b ) {
2812 multiplyScalar:
function ( scalar ) {
2814 if ( isFinite( scalar ) ) {
2830 applyMatrix4:
function ( m ) {
2839 this.x = e[ 0 ] * x + e[ 4 ] * y + e[ 8 ] * z + e[ 12 ] * w;
2840 this.y = e[ 1 ] * x + e[ 5 ] * y + e[ 9 ] * z + e[ 13 ] * w;
2841 this.z = e[ 2 ] * x + e[ 6 ] * y + e[ 10 ] * z + e[ 14 ] * w;
2842 this.w = e[ 3 ] * x + e[ 7 ] * y + e[ 11 ] * z + e[ 15 ] * w;
2848 divideScalar:
function ( scalar ) {
2850 return this.multiplyScalar( 1 / scalar );
2854 setAxisAngleFromQuaternion:
function ( q ) {
2860 this.w = 2 * Math.acos( q.w );
2862 var s = Math.sqrt( 1 - q.w * q.w );
2882 setAxisAngleFromRotationMatrix:
function ( m ) {
2894 m11 = te[ 0 ], m12 = te[ 4 ], m13 = te[ 8 ],
2895 m21 = te[ 1 ], m22 = te[ 5 ], m23 = te[ 9 ],
2896 m31 = te[ 2 ], m32 = te[ 6 ], m33 = te[ 10 ];
2898 if ( ( Math.abs( m12 - m21 ) < epsilon )
2899 && ( Math.abs( m13 - m31 ) < epsilon )
2900 && ( Math.abs( m23 - m32 ) < epsilon ) ) {
2906 if ( ( Math.abs( m12 + m21 ) < epsilon2 )
2907 && ( Math.abs( m13 + m31 ) < epsilon2 )
2908 && ( Math.abs( m23 + m32 ) < epsilon2 )
2909 && ( Math.abs( m11 + m22 + m33 - 3 ) < epsilon2 ) ) {
2913 this.set( 1, 0, 0, 0 );
2923 var xx = ( m11 + 1 ) / 2;
2924 var yy = ( m22 + 1 ) / 2;
2925 var zz = ( m33 + 1 ) / 2;
2926 var xy = ( m12 + m21 ) / 4;
2927 var xz = ( m13 + m31 ) / 4;
2928 var yz = ( m23 + m32 ) / 4;
2930 if ( ( xx > yy ) && ( xx > zz ) ) {
2934 if ( xx < epsilon ) {
2942 x = Math.sqrt( xx );
2948 }
else if ( yy > zz ) {
2952 if ( yy < epsilon ) {
2960 y = Math.sqrt( yy );
2970 if ( zz < epsilon ) {
2978 z = Math.sqrt( zz );
2986 this.set( x, y, z, angle );
2994 var s = Math.sqrt( ( m32 - m23 ) * ( m32 - m23 )
2995 + ( m13 - m31 ) * ( m13 - m31 )
2996 + ( m21 - m12 ) * ( m21 - m12 ) );
2998 if ( Math.abs( s ) < 0.001 ) s = 1;
3003 this.x = ( m32 - m23 ) / s;
3004 this.y = ( m13 - m31 ) / s;
3005 this.z = ( m21 - m12 ) / s;
3006 this.w = Math.acos( ( m11 + m22 + m33 - 1 ) / 2 );
3012 min:
function ( v ) {
3014 this.x = Math.min( this.x, v.x );
3015 this.y = Math.min( this.y, v.y );
3016 this.z = Math.min( this.z, v.z );
3017 this.w = Math.min( this.w, v.w );
3023 max:
function ( v ) {
3025 this.x = Math.max( this.x, v.x );
3026 this.y = Math.max( this.y, v.y );
3027 this.z = Math.max( this.z, v.z );
3028 this.w = Math.max( this.w, v.w );
3034 clamp:
function ( min, max ) {
3038 this.x = Math.max( min.x, Math.min( max.x,
this.x ) );
3039 this.y = Math.max( min.y, Math.min( max.y,
this.y ) );
3040 this.z = Math.max( min.z, Math.min( max.z,
this.z ) );
3041 this.w = Math.max( min.w, Math.min( max.w,
this.w ) );
3047 clampScalar:
function () {
3051 return function clampScalar( minVal, maxVal ) {
3053 if ( min === undefined ) {
3055 min =
new THREE.Vector4();
3056 max =
new THREE.Vector4();
3060 min.set( minVal, minVal, minVal, minVal );
3061 max.set( maxVal, maxVal, maxVal, maxVal );
3063 return this.clamp( min, max );
3069 floor:
function () {
3071 this.x = Math.floor( this.x );
3072 this.y = Math.floor( this.y );
3073 this.z = Math.floor( this.z );
3074 this.w = Math.floor( this.w );
3082 this.x = Math.ceil( this.x );
3083 this.y = Math.ceil( this.y );
3084 this.z = Math.ceil( this.z );
3085 this.w = Math.ceil( this.w );
3091 round:
function () {
3093 this.x = Math.round( this.x );
3094 this.y = Math.round( this.y );
3095 this.z = Math.round( this.z );
3096 this.w = Math.round( this.w );
3102 roundToZero:
function () {
3104 this.x = ( this.x < 0 ) ? Math.ceil(
this.x ) : Math.floor( this.x );
3105 this.y = ( this.y < 0 ) ? Math.ceil(
this.y ) : Math.floor( this.y );
3106 this.z = ( this.z < 0 ) ? Math.ceil(
this.z ) : Math.floor( this.z );
3107 this.w = ( this.w < 0 ) ? Math.ceil(
this.w ) : Math.floor( this.w );
3113 negate:
function () {
3124 dot:
function ( v ) {
3126 return this.x * v.x + this.y * v.y + this.z * v.z + this.w * v.w;
3130 lengthSq:
function () {
3132 return this.x * this.x + this.y * this.y + this.z * this.z + this.w * this.w;
3136 length:
function () {
3138 return Math.sqrt( this.x * this.x + this.y * this.y + this.z * this.z + this.w * this.w );
3142 lengthManhattan:
function () {
3144 return Math.abs( this.x ) + Math.abs( this.y ) + Math.abs( this.z ) + Math.abs( this.w );
3148 normalize:
function () {
3150 return this.divideScalar( this.length() );
3154 setLength:
function ( length ) {
3156 return this.multiplyScalar( length / this.length() );
3160 lerp:
function ( v, alpha ) {
3162 this.x += ( v.x - this.x ) * alpha;
3163 this.y += ( v.y - this.y ) * alpha;
3164 this.z += ( v.z - this.z ) * alpha;
3165 this.w += ( v.w - this.w ) * alpha;
3171 lerpVectors:
function ( v1, v2, alpha ) {
3173 this.subVectors( v2, v1 ).multiplyScalar( alpha ).add( v1 );
3179 equals:
function ( v ) {
3181 return ( ( v.x ===
this.x ) && ( v.y === this.y ) && ( v.z ===
this.z ) && ( v.w === this.w ) );
3185 fromArray:
function ( array, offset ) {
3187 if ( offset === undefined ) offset = 0;
3189 this.x = array[ offset ];
3190 this.y = array[ offset + 1 ];
3191 this.z = array[ offset + 2 ];
3192 this.w = array[ offset + 3 ];
3198 toArray:
function ( array, offset ) {
3200 if ( array === undefined ) array = [];
3201 if ( offset === undefined ) offset = 0;
3203 array[ offset ] = this.x;
3204 array[ offset + 1 ] = this.y;
3205 array[ offset + 2 ] = this.z;
3206 array[ offset + 3 ] = this.w;
3212 fromAttribute:
function ( attribute, index, offset ) {
3214 if ( offset === undefined ) offset = 0;
3216 index = index * attribute.itemSize + offset;
3218 this.x = attribute.array[ index ];
3219 this.y = attribute.array[ index + 1 ];
3220 this.z = attribute.array[ index + 2 ];
3221 this.w = attribute.array[ index + 3 ];
3237 THREE.Euler =
function ( x, y, z, order ) {
3242 this._order = order || THREE.Euler.DefaultOrder;
3246 THREE.Euler.RotationOrders = [
'XYZ',
'YZX',
'ZXY',
'XZY',
'YXZ',
'ZYX' ];
3248 THREE.Euler.DefaultOrder =
'XYZ';
3250 THREE.Euler.prototype = {
3252 constructor: THREE.Euler,
3263 this.onChangeCallback();
3276 this.onChangeCallback();
3289 this.onChangeCallback();
3299 set order ( value ) {
3301 this._order = value;
3302 this.onChangeCallback();
3306 set:
function ( x, y, z, order ) {
3311 this._order = order || this._order;
3313 this.onChangeCallback();
3319 clone:
function () {
3321 return new this.constructor( this._x, this._y, this._z, this._order);
3325 copy:
function ( euler ) {
3330 this._order = euler._order;
3332 this.onChangeCallback();
3338 setFromRotationMatrix:
function ( m, order, update ) {
3340 var clamp = THREE.Math.clamp;
3344 var te = m.elements;
3345 var m11 = te[ 0 ], m12 = te[ 4 ], m13 = te[ 8 ];
3346 var m21 = te[ 1 ], m22 = te[ 5 ], m23 = te[ 9 ];
3347 var m31 = te[ 2 ], m32 = te[ 6 ], m33 = te[ 10 ];
3349 order = order || this._order;
3351 if ( order ===
'XYZ' ) {
3353 this._y = Math.asin( clamp( m13, - 1, 1 ) );
3355 if ( Math.abs( m13 ) < 0.99999 ) {
3357 this._x = Math.atan2( - m23, m33 );
3358 this._z = Math.atan2( - m12, m11 );
3362 this._x = Math.atan2( m32, m22 );
3367 }
else if ( order ===
'YXZ' ) {
3369 this._x = Math.asin( - clamp( m23, - 1, 1 ) );
3371 if ( Math.abs( m23 ) < 0.99999 ) {
3373 this._y = Math.atan2( m13, m33 );
3374 this._z = Math.atan2( m21, m22 );
3378 this._y = Math.atan2( - m31, m11 );
3383 }
else if ( order ===
'ZXY' ) {
3385 this._x = Math.asin( clamp( m32, - 1, 1 ) );
3387 if ( Math.abs( m32 ) < 0.99999 ) {
3389 this._y = Math.atan2( - m31, m33 );
3390 this._z = Math.atan2( - m12, m22 );
3395 this._z = Math.atan2( m21, m11 );
3399 }
else if ( order ===
'ZYX' ) {
3401 this._y = Math.asin( - clamp( m31, - 1, 1 ) );
3403 if ( Math.abs( m31 ) < 0.99999 ) {
3405 this._x = Math.atan2( m32, m33 );
3406 this._z = Math.atan2( m21, m11 );
3411 this._z = Math.atan2( - m12, m22 );
3415 }
else if ( order ===
'YZX' ) {
3417 this._z = Math.asin( clamp( m21, - 1, 1 ) );
3419 if ( Math.abs( m21 ) < 0.99999 ) {
3421 this._x = Math.atan2( - m23, m22 );
3422 this._y = Math.atan2( - m31, m11 );
3427 this._y = Math.atan2( m13, m33 );
3431 }
else if ( order ===
'XZY' ) {
3433 this._z = Math.asin( - clamp( m12, - 1, 1 ) );
3435 if ( Math.abs( m12 ) < 0.99999 ) {
3437 this._x = Math.atan2( m32, m22 );
3438 this._y = Math.atan2( m13, m11 );
3442 this._x = Math.atan2( - m23, m33 );
3449 console.warn(
'THREE.Euler: .setFromRotationMatrix() given unsupported order: ' + order )
3453 this._order = order;
3455 if ( update !==
false ) this.onChangeCallback();
3461 setFromQuaternion:
function () {
3465 return function ( q, order, update ) {
3467 if ( matrix === undefined ) matrix =
new THREE.Matrix4();
3468 matrix.makeRotationFromQuaternion( q );
3469 this.setFromRotationMatrix( matrix, order, update );
3477 setFromVector3:
function ( v, order ) {
3479 return this.set( v.x, v.y, v.z, order ||
this._order );
3483 reorder:
function () {
3487 var q =
new THREE.Quaternion();
3489 return function ( newOrder ) {
3491 q.setFromEuler(
this );
3492 this.setFromQuaternion( q, newOrder );
3498 equals:
function ( euler ) {
3500 return ( euler._x ===
this._x ) && ( euler._y === this._y ) && ( euler._z ===
this._z ) && ( euler._order === this._order );
3504 fromArray:
function ( array ) {
3506 this._x = array[ 0 ];
3507 this._y = array[ 1 ];
3508 this._z = array[ 2 ];
3509 if ( array[ 3 ] !== undefined ) this._order = array[ 3 ];
3511 this.onChangeCallback();
3517 toArray:
function ( array, offset ) {
3519 if ( array === undefined ) array = [];
3520 if ( offset === undefined ) offset = 0;
3522 array[ offset ] = this._x;
3523 array[ offset + 1 ] = this._y;
3524 array[ offset + 2 ] = this._z;
3525 array[ offset + 3 ] = this._order;
3531 toVector3:
function ( optionalResult ) {
3533 if ( optionalResult ) {
3535 return optionalResult.set( this._x, this._y, this._z );
3539 return new THREE.Vector3( this._x, this._y, this._z );
3545 onChange:
function ( callback ) {
3547 this.onChangeCallback = callback;
3553 onChangeCallback:
function () {}
3563 THREE.Line3 =
function ( start, end ) {
3565 this.start = ( start !== undefined ) ? start :
new THREE.Vector3();
3566 this.end = ( end !== undefined ) ? end :
new THREE.Vector3();
3570 THREE.Line3.prototype = {
3572 constructor: THREE.Line3,
3574 set:
function ( start, end ) {
3576 this.start.copy( start );
3577 this.end.copy( end );
3583 clone:
function () {
3585 return new this.constructor().copy(
this );
3589 copy:
function ( line ) {
3591 this.start.copy( line.start );
3592 this.end.copy( line.end );
3598 center:
function ( optionalTarget ) {
3600 var result = optionalTarget ||
new THREE.Vector3();
3601 return result.addVectors( this.start, this.end ).multiplyScalar( 0.5 );
3605 delta:
function ( optionalTarget ) {
3607 var result = optionalTarget ||
new THREE.Vector3();
3608 return result.subVectors( this.end, this.start );
3612 distanceSq:
function () {
3614 return this.start.distanceToSquared( this.end );
3618 distance:
function () {
3620 return this.start.distanceTo( this.end );
3624 at:
function ( t, optionalTarget ) {
3626 var result = optionalTarget ||
new THREE.Vector3();
3628 return this.delta( result ).multiplyScalar( t ).add( this.start );
3632 closestPointToPointParameter:
function () {
3634 var startP =
new THREE.Vector3();
3635 var startEnd =
new THREE.Vector3();
3637 return function ( point, clampToLine ) {
3639 startP.subVectors( point, this.start );
3640 startEnd.subVectors( this.end, this.start );
3642 var startEnd2 = startEnd.dot( startEnd );
3643 var startEnd_startP = startEnd.dot( startP );
3645 var t = startEnd_startP / startEnd2;
3647 if ( clampToLine ) {
3649 t = THREE.Math.clamp( t, 0, 1 );
3659 closestPointToPoint:
function ( point, clampToLine, optionalTarget ) {
3661 var t = this.closestPointToPointParameter( point, clampToLine );
3663 var result = optionalTarget ||
new THREE.Vector3();
3665 return this.delta( result ).multiplyScalar( t ).add( this.start );
3669 applyMatrix4:
function ( matrix ) {
3671 this.start.applyMatrix4( matrix );
3672 this.end.applyMatrix4( matrix );
3678 equals:
function ( line ) {
3680 return line.start.equals( this.start ) && line.end.equals( this.end );
3692 THREE.Box2 =
function ( min, max ) {
3694 this.min = ( min !== undefined ) ? min :
new THREE.Vector2( Infinity, Infinity );
3695 this.max = ( max !== undefined ) ? max :
new THREE.Vector2( - Infinity, - Infinity );
3699 THREE.Box2.prototype = {
3701 constructor: THREE.Box2,
3703 set:
function ( min, max ) {
3705 this.min.copy( min );
3706 this.max.copy( max );
3712 setFromPoints:
function ( points ) {
3716 for ( var i = 0, il = points.length; i < il; i ++ ) {
3718 this.expandByPoint( points[ i ] )
3726 setFromCenterAndSize:
function () {
3728 var v1 =
new THREE.Vector2();
3730 return function ( center, size ) {
3732 var halfSize = v1.copy( size ).multiplyScalar( 0.5 );
3733 this.min.copy( center ).sub( halfSize );
3734 this.max.copy( center ).add( halfSize );
3742 clone:
function () {
3744 return new this.constructor().copy(
this );
3748 copy:
function ( box ) {
3750 this.min.copy( box.min );
3751 this.max.copy( box.max );
3757 makeEmpty:
function () {
3759 this.min.x = this.min.y = Infinity;
3760 this.max.x = this.max.y = - Infinity;
3766 empty:
function () {
3770 return ( this.max.x <
this.min.x ) || ( this.max.y < this.min.y );
3774 center:
function ( optionalTarget ) {
3776 var result = optionalTarget ||
new THREE.Vector2();
3777 return result.addVectors( this.min, this.max ).multiplyScalar( 0.5 );
3781 size:
function ( optionalTarget ) {
3783 var result = optionalTarget ||
new THREE.Vector2();
3784 return result.subVectors( this.max, this.min );
3788 expandByPoint:
function ( point ) {
3790 this.min.min( point );
3791 this.max.max( point );
3797 expandByVector:
function ( vector ) {
3799 this.min.sub( vector );
3800 this.max.add( vector );
3806 expandByScalar:
function ( scalar ) {
3808 this.min.addScalar( - scalar );
3809 this.max.addScalar( scalar );
3815 containsPoint:
function ( point ) {
3817 if ( point.x <
this.min.x || point.x >
this.max.x ||
3818 point.y <
this.min.y || point.y >
this.max.y ) {
3828 containsBox:
function ( box ) {
3830 if ( ( this.min.x <= box.min.x ) && ( box.max.x <= this.max.x ) &&
3831 ( this.min.y <= box.min.y ) && ( box.max.y <= this.max.y ) ) {
3841 getParameter:
function ( point, optionalTarget ) {
3846 var result = optionalTarget ||
new THREE.Vector2();
3849 ( point.x -
this.min.x ) / (
this.max.x -
this.min.x ),
3850 ( point.y -
this.min.y ) / (
this.max.y -
this.min.y )
3855 isIntersectionBox:
function ( box ) {
3859 if ( box.max.x <
this.min.x || box.min.x >
this.max.x ||
3860 box.max.y <
this.min.y || box.min.y >
this.max.y ) {
3870 clampPoint:
function ( point, optionalTarget ) {
3872 var result = optionalTarget ||
new THREE.Vector2();
3873 return result.copy( point ).clamp( this.min, this.max );
3877 distanceToPoint:
function () {
3879 var v1 =
new THREE.Vector2();
3881 return function ( point ) {
3883 var clampedPoint = v1.copy( point ).clamp( this.min, this.max );
3884 return clampedPoint.sub( point ).length();
3890 intersect:
function ( box ) {
3892 this.min.max( box.min );
3893 this.max.min( box.max );
3899 union:
function ( box ) {
3901 this.min.min( box.min );
3902 this.max.max( box.max );
3908 translate:
function ( offset ) {
3910 this.min.add( offset );
3911 this.max.add( offset );
3917 equals:
function ( box ) {
3919 return box.min.equals( this.min ) && box.max.equals( this.max );
3932 THREE.Box3 =
function ( min, max ) {
3934 this.min = ( min !== undefined ) ? min :
new THREE.Vector3( Infinity, Infinity, Infinity );
3935 this.max = ( max !== undefined ) ? max :
new THREE.Vector3( - Infinity, - Infinity, - Infinity );
3939 THREE.Box3.prototype = {
3941 constructor: THREE.Box3,
3943 set:
function ( min, max ) {
3945 this.min.copy( min );
3946 this.max.copy( max );
3952 setFromPoints:
function ( points ) {
3956 for ( var i = 0, il = points.length; i < il; i ++ ) {
3958 this.expandByPoint( points[ i ] );
3966 setFromCenterAndSize:
function () {
3968 var v1 =
new THREE.Vector3();
3970 return function ( center, size ) {
3972 var halfSize = v1.copy( size ).multiplyScalar( 0.5 );
3974 this.min.copy( center ).sub( halfSize );
3975 this.max.copy( center ).add( halfSize );
3983 setFromObject:
function () {
3988 var v1 =
new THREE.Vector3();
3990 return function ( object ) {
3994 object.updateMatrixWorld(
true );
3998 object.traverse(
function ( node ) {
4000 var geometry = node.geometry;
4002 if ( geometry !== undefined ) {
4004 if ( geometry instanceof THREE.Geometry ) {
4006 var vertices = geometry.vertices;
4008 for ( var i = 0, il = vertices.length; i < il; i ++ ) {
4010 v1.copy( vertices[ i ] );
4012 v1.applyMatrix4( node.matrixWorld );
4014 scope.expandByPoint( v1 );
4018 }
else if ( geometry instanceof THREE.BufferGeometry && geometry.attributes[
'position' ] !== undefined ) {
4020 var positions = geometry.attributes[
'position' ].array;
4022 for ( var i = 0, il = positions.length; i < il; i += 3 ) {
4024 v1.set( positions[ i ], positions[ i + 1 ], positions[ i + 2 ] );
4026 v1.applyMatrix4( node.matrixWorld );
4028 scope.expandByPoint( v1 );
4044 clone:
function () {
4046 return new this.constructor().copy(
this );
4050 copy:
function ( box ) {
4052 this.min.copy( box.min );
4053 this.max.copy( box.max );
4059 makeEmpty:
function () {
4061 this.min.x = this.min.y = this.min.z = Infinity;
4062 this.max.x = this.max.y = this.max.z = - Infinity;
4068 empty:
function () {
4072 return ( this.max.x <
this.min.x ) || ( this.max.y < this.min.y ) || ( this.max.z <
this.min.z );
4076 center:
function ( optionalTarget ) {
4078 var result = optionalTarget ||
new THREE.Vector3();
4079 return result.addVectors( this.min, this.max ).multiplyScalar( 0.5 );
4083 size:
function ( optionalTarget ) {
4085 var result = optionalTarget ||
new THREE.Vector3();
4086 return result.subVectors( this.max, this.min );
4090 expandByPoint:
function ( point ) {
4092 this.min.min( point );
4093 this.max.max( point );
4099 expandByVector:
function ( vector ) {
4101 this.min.sub( vector );
4102 this.max.add( vector );
4108 expandByScalar:
function ( scalar ) {
4110 this.min.addScalar( - scalar );
4111 this.max.addScalar( scalar );
4117 containsPoint:
function ( point ) {
4119 if ( point.x <
this.min.x || point.x >
this.max.x ||
4120 point.y <
this.min.y || point.y >
this.max.y ||
4121 point.z <
this.min.z || point.z >
this.max.z ) {
4131 containsBox:
function ( box ) {
4133 if ( ( this.min.x <= box.min.x ) && ( box.max.x <= this.max.x ) &&
4134 ( this.min.y <= box.min.y ) && ( box.max.y <= this.max.y ) &&
4135 ( this.min.z <= box.min.z ) && ( box.max.z <= this.max.z ) ) {
4145 getParameter:
function ( point, optionalTarget ) {
4150 var result = optionalTarget ||
new THREE.Vector3();
4153 ( point.x -
this.min.x ) / (
this.max.x -
this.min.x ),
4154 ( point.y -
this.min.y ) / (
this.max.y -
this.min.y ),
4155 ( point.z -
this.min.z ) / (
this.max.z -
this.min.z )
4160 isIntersectionBox:
function ( box ) {
4164 if ( box.max.x <
this.min.x || box.min.x >
this.max.x ||
4165 box.max.y <
this.min.y || box.min.y >
this.max.y ||
4166 box.max.z <
this.min.z || box.min.z >
this.max.z ) {
4176 clampPoint:
function ( point, optionalTarget ) {
4178 var result = optionalTarget ||
new THREE.Vector3();
4179 return result.copy( point ).clamp( this.min, this.max );
4183 distanceToPoint:
function () {
4185 var v1 =
new THREE.Vector3();
4187 return function ( point ) {
4189 var clampedPoint = v1.copy( point ).clamp( this.min, this.max );
4190 return clampedPoint.sub( point ).length();
4196 getBoundingSphere:
function () {
4198 var v1 =
new THREE.Vector3();
4200 return function ( optionalTarget ) {
4202 var result = optionalTarget ||
new THREE.Sphere();
4204 result.center = this.center();
4205 result.radius = this.size( v1 ).length() * 0.5;
4213 intersect:
function ( box ) {
4215 this.min.max( box.min );
4216 this.max.min( box.max );
4222 union:
function ( box ) {
4224 this.min.min( box.min );
4225 this.max.max( box.max );
4231 applyMatrix4:
function () {
4234 new THREE.Vector3(),
4235 new THREE.Vector3(),
4236 new THREE.Vector3(),
4237 new THREE.Vector3(),
4238 new THREE.Vector3(),
4239 new THREE.Vector3(),
4240 new THREE.Vector3(),
4244 return function ( matrix ) {
4247 points[ 0 ].set( this.min.x,
this.min.y,
this.min.z ).applyMatrix4( matrix );
4248 points[ 1 ].set( this.min.x,
this.min.y,
this.max.z ).applyMatrix4( matrix );
4249 points[ 2 ].set( this.min.x,
this.max.y,
this.min.z ).applyMatrix4( matrix );
4250 points[ 3 ].set( this.min.x,
this.max.y,
this.max.z ).applyMatrix4( matrix );
4251 points[ 4 ].set( this.max.x,
this.min.y,
this.min.z ).applyMatrix4( matrix );
4252 points[ 5 ].set( this.max.x,
this.min.y,
this.max.z ).applyMatrix4( matrix );
4253 points[ 6 ].set( this.max.x,
this.max.y,
this.min.z ).applyMatrix4( matrix );
4254 points[ 7 ].set( this.max.x,
this.max.y,
this.max.z ).applyMatrix4( matrix );
4257 this.setFromPoints( points );
4265 translate:
function ( offset ) {
4267 this.min.add( offset );
4268 this.max.add( offset );
4274 equals:
function ( box ) {
4276 return box.min.equals( this.min ) && box.max.equals( this.max );
4290 THREE.Matrix3 =
function () {
4292 this.elements =
new Float32Array( [
4300 if ( arguments.length > 0 ) {
4302 console.error(
'THREE.Matrix3: the constructor no longer reads arguments. use .set() instead.' );
4308 THREE.Matrix3.prototype = {
4310 constructor: THREE.Matrix3,
4312 set:
function ( n11, n12, n13, n21, n22, n23, n31, n32, n33 ) {
4314 var te = this.elements;
4316 te[ 0 ] = n11; te[ 3 ] = n12; te[ 6 ] = n13;
4317 te[ 1 ] = n21; te[ 4 ] = n22; te[ 7 ] = n23;
4318 te[ 2 ] = n31; te[ 5 ] = n32; te[ 8 ] = n33;
4324 identity:
function () {
4338 clone:
function () {
4340 return new this.constructor().fromArray( this.elements );
4344 copy:
function ( m ) {
4346 var me = m.elements;
4350 me[ 0 ], me[ 3 ], me[ 6 ],
4351 me[ 1 ], me[ 4 ], me[ 7 ],
4352 me[ 2 ], me[ 5 ], me[ 8 ]
4360 multiplyVector3:
function ( vector ) {
4362 console.warn(
'THREE.Matrix3: .multiplyVector3() has been removed. Use vector.applyMatrix3( matrix ) instead.' );
4363 return vector.applyMatrix3(
this );
4367 multiplyVector3Array:
function ( a ) {
4369 console.warn(
'THREE.Matrix3: .multiplyVector3Array() has been renamed. Use matrix.applyToVector3Array( array ) instead.' );
4370 return this.applyToVector3Array( a );
4374 applyToVector3Array:
function () {
4378 return function ( array, offset, length ) {
4380 if ( v1 === undefined ) v1 =
new THREE.Vector3();
4381 if ( offset === undefined ) offset = 0;
4382 if ( length === undefined ) length = array.length;
4384 for ( var i = 0, j = offset; i < length; i += 3, j += 3 ) {
4386 v1.fromArray( array, j );
4387 v1.applyMatrix3(
this );
4388 v1.toArray( array, j );
4398 applyToBuffer:
function () {
4402 return function applyToBuffer( buffer, offset, length ) {
4404 if ( v1 === undefined ) v1 =
new THREE.Vector3();
4405 if ( offset === undefined ) offset = 0;
4406 if ( length === undefined ) length = buffer.length / buffer.itemSize;
4408 for ( var i = 0, j = offset; i < length; i ++, j ++ ) {
4410 v1.x = buffer.getX( j );
4411 v1.y = buffer.getY( j );
4412 v1.z = buffer.getZ( j );
4414 v1.applyMatrix3(
this );
4416 buffer.setXYZ( v1.x, v1.y, v1.z );
4426 multiplyScalar:
function ( s ) {
4428 var te = this.elements;
4430 te[ 0 ] *= s; te[ 3 ] *= s; te[ 6 ] *= s;
4431 te[ 1 ] *= s; te[ 4 ] *= s; te[ 7 ] *= s;
4432 te[ 2 ] *= s; te[ 5 ] *= s; te[ 8 ] *= s;
4438 determinant:
function () {
4440 var te = this.elements;
4442 var a = te[ 0 ], b = te[ 1 ], c = te[ 2 ],
4443 d = te[ 3 ], e = te[ 4 ], f = te[ 5 ],
4444 g = te[ 6 ], h = te[ 7 ], i = te[ 8 ];
4446 return a * e * i - a * f * h - b * d * i + b * f * g + c * d * h - c * e * g;
4450 getInverse:
function ( matrix, throwOnInvertible ) {
4455 var me = matrix.elements;
4456 var te = this.elements;
4458 te[ 0 ] = me[ 10 ] * me[ 5 ] - me[ 6 ] * me[ 9 ];
4459 te[ 1 ] = - me[ 10 ] * me[ 1 ] + me[ 2 ] * me[ 9 ];
4460 te[ 2 ] = me[ 6 ] * me[ 1 ] - me[ 2 ] * me[ 5 ];
4461 te[ 3 ] = - me[ 10 ] * me[ 4 ] + me[ 6 ] * me[ 8 ];
4462 te[ 4 ] = me[ 10 ] * me[ 0 ] - me[ 2 ] * me[ 8 ];
4463 te[ 5 ] = - me[ 6 ] * me[ 0 ] + me[ 2 ] * me[ 4 ];
4464 te[ 6 ] = me[ 9 ] * me[ 4 ] - me[ 5 ] * me[ 8 ];
4465 te[ 7 ] = - me[ 9 ] * me[ 0 ] + me[ 1 ] * me[ 8 ];
4466 te[ 8 ] = me[ 5 ] * me[ 0 ] - me[ 1 ] * me[ 4 ];
4468 var det = me[ 0 ] * te[ 0 ] + me[ 1 ] * te[ 3 ] + me[ 2 ] * te[ 6 ];
4474 var msg =
"Matrix3.getInverse(): can't invert matrix, determinant is 0";
4476 if ( throwOnInvertible ||
false ) {
4478 throw new Error( msg );
4482 console.warn( msg );
4492 this.multiplyScalar( 1.0 / det );
4498 transpose:
function () {
4500 var tmp, m = this.elements;
4502 tmp = m[ 1 ]; m[ 1 ] = m[ 3 ]; m[ 3 ] = tmp;
4503 tmp = m[ 2 ]; m[ 2 ] = m[ 6 ]; m[ 6 ] = tmp;
4504 tmp = m[ 5 ]; m[ 5 ] = m[ 7 ]; m[ 7 ] = tmp;
4510 flattenToArrayOffset:
function ( array, offset ) {
4512 var te = this.elements;
4514 array[ offset ] = te[ 0 ];
4515 array[ offset + 1 ] = te[ 1 ];
4516 array[ offset + 2 ] = te[ 2 ];
4518 array[ offset + 3 ] = te[ 3 ];
4519 array[ offset + 4 ] = te[ 4 ];
4520 array[ offset + 5 ] = te[ 5 ];
4522 array[ offset + 6 ] = te[ 6 ];
4523 array[ offset + 7 ] = te[ 7 ];
4524 array[ offset + 8 ] = te[ 8 ];
4530 getNormalMatrix:
function ( m ) {
4534 this.getInverse( m ).transpose();
4540 transposeIntoArray:
function ( r ) {
4542 var m = this.elements;
4558 fromArray:
function ( array ) {
4560 this.elements.set( array );
4566 toArray:
function () {
4568 var te = this.elements;
4571 te[ 0 ], te[ 1 ], te[ 2 ],
4572 te[ 3 ], te[ 4 ], te[ 5 ],
4573 te[ 6 ], te[ 7 ], te[ 8 ]
4595 THREE.Matrix4 =
function () {
4597 this.elements =
new Float32Array( [
4606 if ( arguments.length > 0 ) {
4608 console.error(
'THREE.Matrix4: the constructor no longer reads arguments. use .set() instead.' );
4614 THREE.Matrix4.prototype = {
4616 constructor: THREE.Matrix4,
4618 set:
function ( n11, n12, n13, n14, n21, n22, n23, n24, n31, n32, n33, n34, n41, n42, n43, n44 ) {
4620 var te = this.elements;
4622 te[ 0 ] = n11; te[ 4 ] = n12; te[ 8 ] = n13; te[ 12 ] = n14;
4623 te[ 1 ] = n21; te[ 5 ] = n22; te[ 9 ] = n23; te[ 13 ] = n24;
4624 te[ 2 ] = n31; te[ 6 ] = n32; te[ 10 ] = n33; te[ 14 ] = n34;
4625 te[ 3 ] = n41; te[ 7 ] = n42; te[ 11 ] = n43; te[ 15 ] = n44;
4631 identity:
function () {
4646 clone:
function () {
4648 return new THREE.Matrix4().fromArray( this.elements );
4652 copy:
function ( m ) {
4654 this.elements.set( m.elements );
4660 extractPosition:
function ( m ) {
4662 console.warn(
'THREE.Matrix4: .extractPosition() has been renamed to .copyPosition().' );
4663 return this.copyPosition( m );
4667 copyPosition:
function ( m ) {
4669 var te = this.elements;
4670 var me = m.elements;
4672 te[ 12 ] = me[ 12 ];
4673 te[ 13 ] = me[ 13 ];
4674 te[ 14 ] = me[ 14 ];
4680 extractBasis:
function ( xAxis, yAxis, zAxis ) {
4682 var te = this.elements;
4684 xAxis.set( te[ 0 ], te[ 1 ], te[ 2 ] );
4685 yAxis.set( te[ 4 ], te[ 5 ], te[ 6 ] );
4686 zAxis.set( te[ 8 ], te[ 9 ], te[ 10 ] );
4692 makeBasis:
function ( xAxis, yAxis, zAxis ) {
4695 xAxis.x, yAxis.x, zAxis.x, 0,
4696 xAxis.y, yAxis.y, zAxis.y, 0,
4697 xAxis.z, yAxis.z, zAxis.z, 0,
4705 extractRotation:
function () {
4709 return function ( m ) {
4711 if ( v1 === undefined ) v1 =
new THREE.Vector3();
4713 var te = this.elements;
4714 var me = m.elements;
4716 var scaleX = 1 / v1.set( me[ 0 ], me[ 1 ], me[ 2 ] ).length();
4717 var scaleY = 1 / v1.set( me[ 4 ], me[ 5 ], me[ 6 ] ).length();
4718 var scaleZ = 1 / v1.set( me[ 8 ], me[ 9 ], me[ 10 ] ).length();
4720 te[ 0 ] = me[ 0 ] * scaleX;
4721 te[ 1 ] = me[ 1 ] * scaleX;
4722 te[ 2 ] = me[ 2 ] * scaleX;
4724 te[ 4 ] = me[ 4 ] * scaleY;
4725 te[ 5 ] = me[ 5 ] * scaleY;
4726 te[ 6 ] = me[ 6 ] * scaleY;
4728 te[ 8 ] = me[ 8 ] * scaleZ;
4729 te[ 9 ] = me[ 9 ] * scaleZ;
4730 te[ 10 ] = me[ 10 ] * scaleZ;
4738 makeRotationFromEuler:
function ( euler ) {
4740 if ( euler instanceof THREE.Euler ===
false ) {
4742 console.error(
'THREE.Matrix: .makeRotationFromEuler() now expects a Euler rotation rather than a Vector3 and order.' );
4746 var te = this.elements;
4748 var x = euler.x, y = euler.y, z = euler.z;
4749 var a = Math.cos( x ), b = Math.sin( x );
4750 var c = Math.cos( y ), d = Math.sin( y );
4751 var e = Math.cos( z ), f = Math.sin( z );
4753 if ( euler.order ===
'XYZ' ) {
4755 var ae = a * e, af = a * f, be = b * e, bf = b * f;
4761 te[ 1 ] = af + be * d;
4762 te[ 5 ] = ae - bf * d;
4765 te[ 2 ] = bf - ae * d;
4766 te[ 6 ] = be + af * d;
4769 }
else if ( euler.order ===
'YXZ' ) {
4771 var ce = c * e, cf = c * f, de = d * e, df = d * f;
4773 te[ 0 ] = ce + df * b;
4774 te[ 4 ] = de * b - cf;
4781 te[ 2 ] = cf * b - de;
4782 te[ 6 ] = df + ce * b;
4785 }
else if ( euler.order ===
'ZXY' ) {
4787 var ce = c * e, cf = c * f, de = d * e, df = d * f;
4789 te[ 0 ] = ce - df * b;
4791 te[ 8 ] = de + cf * b;
4793 te[ 1 ] = cf + de * b;
4795 te[ 9 ] = df - ce * b;
4801 }
else if ( euler.order ===
'ZYX' ) {
4803 var ae = a * e, af = a * f, be = b * e, bf = b * f;
4806 te[ 4 ] = be * d - af;
4807 te[ 8 ] = ae * d + bf;
4810 te[ 5 ] = bf * d + ae;
4811 te[ 9 ] = af * d - be;
4817 }
else if ( euler.order ===
'YZX' ) {
4819 var ac = a * c, ad = a * d, bc = b * c, bd = b * d;
4822 te[ 4 ] = bd - ac * f;
4823 te[ 8 ] = bc * f + ad;
4830 te[ 6 ] = ad * f + bc;
4831 te[ 10 ] = ac - bd * f;
4833 }
else if ( euler.order ===
'XZY' ) {
4835 var ac = a * c, ad = a * d, bc = b * c, bd = b * d;
4841 te[ 1 ] = ac * f + bd;
4843 te[ 9 ] = ad * f - bc;
4845 te[ 2 ] = bc * f - ad;
4847 te[ 10 ] = bd * f + ac;
4866 setRotationFromQuaternion:
function ( q ) {
4868 console.warn(
'THREE.Matrix4: .setRotationFromQuaternion() has been renamed to .makeRotationFromQuaternion().' );
4870 return this.makeRotationFromQuaternion( q );
4874 makeRotationFromQuaternion:
function ( q ) {
4876 var te = this.elements;
4878 var x = q.x, y = q.y, z = q.z, w = q.w;
4879 var x2 = x + x, y2 = y + y, z2 = z + z;
4880 var xx = x * x2, xy = x * y2, xz = x * z2;
4881 var yy = y * y2, yz = y * z2, zz = z * z2;
4882 var wx = w * x2, wy = w * y2, wz = w * z2;
4884 te[ 0 ] = 1 - ( yy + zz );
4889 te[ 5 ] = 1 - ( xx + zz );
4894 te[ 10 ] = 1 - ( xx + yy );
4911 lookAt:
function () {
4915 return function ( eye, target, up ) {
4917 if ( x === undefined ) x =
new THREE.Vector3();
4918 if ( y === undefined ) y =
new THREE.Vector3();
4919 if ( z === undefined ) z =
new THREE.Vector3();
4921 var te = this.elements;
4923 z.subVectors( eye, target ).normalize();
4925 if ( z.lengthSq() === 0 ) {
4931 x.crossVectors( up, z ).normalize();
4933 if ( x.lengthSq() === 0 ) {
4936 x.crossVectors( up, z ).normalize();
4940 y.crossVectors( z, x );
4943 te[ 0 ] = x.x; te[ 4 ] = y.x; te[ 8 ] = z.x;
4944 te[ 1 ] = x.y; te[ 5 ] = y.y; te[ 9 ] = z.y;
4945 te[ 2 ] = x.z; te[ 6 ] = y.z; te[ 10 ] = z.z;
4953 multiply:
function ( m, n ) {
4955 if ( n !== undefined ) {
4957 console.warn(
'THREE.Matrix4: .multiply() now only accepts one argument. Use .multiplyMatrices( a, b ) instead.' );
4958 return this.multiplyMatrices( m, n );
4962 return this.multiplyMatrices(
this, m );
4966 multiplyMatrices:
function ( a, b ) {
4968 var ae = a.elements;
4969 var be = b.elements;
4970 var te = this.elements;
4972 var a11 = ae[ 0 ], a12 = ae[ 4 ], a13 = ae[ 8 ], a14 = ae[ 12 ];
4973 var a21 = ae[ 1 ], a22 = ae[ 5 ], a23 = ae[ 9 ], a24 = ae[ 13 ];
4974 var a31 = ae[ 2 ], a32 = ae[ 6 ], a33 = ae[ 10 ], a34 = ae[ 14 ];
4975 var a41 = ae[ 3 ], a42 = ae[ 7 ], a43 = ae[ 11 ], a44 = ae[ 15 ];
4977 var b11 = be[ 0 ], b12 = be[ 4 ], b13 = be[ 8 ], b14 = be[ 12 ];
4978 var b21 = be[ 1 ], b22 = be[ 5 ], b23 = be[ 9 ], b24 = be[ 13 ];
4979 var b31 = be[ 2 ], b32 = be[ 6 ], b33 = be[ 10 ], b34 = be[ 14 ];
4980 var b41 = be[ 3 ], b42 = be[ 7 ], b43 = be[ 11 ], b44 = be[ 15 ];
4982 te[ 0 ] = a11 * b11 + a12 * b21 + a13 * b31 + a14 * b41;
4983 te[ 4 ] = a11 * b12 + a12 * b22 + a13 * b32 + a14 * b42;
4984 te[ 8 ] = a11 * b13 + a12 * b23 + a13 * b33 + a14 * b43;
4985 te[ 12 ] = a11 * b14 + a12 * b24 + a13 * b34 + a14 * b44;
4987 te[ 1 ] = a21 * b11 + a22 * b21 + a23 * b31 + a24 * b41;
4988 te[ 5 ] = a21 * b12 + a22 * b22 + a23 * b32 + a24 * b42;
4989 te[ 9 ] = a21 * b13 + a22 * b23 + a23 * b33 + a24 * b43;
4990 te[ 13 ] = a21 * b14 + a22 * b24 + a23 * b34 + a24 * b44;
4992 te[ 2 ] = a31 * b11 + a32 * b21 + a33 * b31 + a34 * b41;
4993 te[ 6 ] = a31 * b12 + a32 * b22 + a33 * b32 + a34 * b42;
4994 te[ 10 ] = a31 * b13 + a32 * b23 + a33 * b33 + a34 * b43;
4995 te[ 14 ] = a31 * b14 + a32 * b24 + a33 * b34 + a34 * b44;
4997 te[ 3 ] = a41 * b11 + a42 * b21 + a43 * b31 + a44 * b41;
4998 te[ 7 ] = a41 * b12 + a42 * b22 + a43 * b32 + a44 * b42;
4999 te[ 11 ] = a41 * b13 + a42 * b23 + a43 * b33 + a44 * b43;
5000 te[ 15 ] = a41 * b14 + a42 * b24 + a43 * b34 + a44 * b44;
5006 multiplyToArray:
function ( a, b, r ) {
5008 var te = this.elements;
5010 this.multiplyMatrices( a, b );
5012 r[ 0 ] = te[ 0 ]; r[ 1 ] = te[ 1 ]; r[ 2 ] = te[ 2 ]; r[ 3 ] = te[ 3 ];
5013 r[ 4 ] = te[ 4 ]; r[ 5 ] = te[ 5 ]; r[ 6 ] = te[ 6 ]; r[ 7 ] = te[ 7 ];
5014 r[ 8 ] = te[ 8 ]; r[ 9 ] = te[ 9 ]; r[ 10 ] = te[ 10 ]; r[ 11 ] = te[ 11 ];
5015 r[ 12 ] = te[ 12 ]; r[ 13 ] = te[ 13 ]; r[ 14 ] = te[ 14 ]; r[ 15 ] = te[ 15 ];
5021 multiplyScalar:
function ( s ) {
5023 var te = this.elements;
5025 te[ 0 ] *= s; te[ 4 ] *= s; te[ 8 ] *= s; te[ 12 ] *= s;
5026 te[ 1 ] *= s; te[ 5 ] *= s; te[ 9 ] *= s; te[ 13 ] *= s;
5027 te[ 2 ] *= s; te[ 6 ] *= s; te[ 10 ] *= s; te[ 14 ] *= s;
5028 te[ 3 ] *= s; te[ 7 ] *= s; te[ 11 ] *= s; te[ 15 ] *= s;
5034 multiplyVector3:
function ( vector ) {
5036 console.warn(
'THREE.Matrix4: .multiplyVector3() has been removed. Use vector.applyMatrix4( matrix ) or vector.applyProjection( matrix ) instead.' );
5037 return vector.applyProjection(
this );
5041 multiplyVector4:
function ( vector ) {
5043 console.warn(
'THREE.Matrix4: .multiplyVector4() has been removed. Use vector.applyMatrix4( matrix ) instead.' );
5044 return vector.applyMatrix4(
this );
5048 multiplyVector3Array:
function ( a ) {
5050 console.warn(
'THREE.Matrix4: .multiplyVector3Array() has been renamed. Use matrix.applyToVector3Array( array ) instead.' );
5051 return this.applyToVector3Array( a );
5055 applyToVector3Array:
function () {
5059 return function ( array, offset, length ) {
5061 if ( v1 === undefined ) v1 =
new THREE.Vector3();
5062 if ( offset === undefined ) offset = 0;
5063 if ( length === undefined ) length = array.length;
5065 for ( var i = 0, j = offset; i < length; i += 3, j += 3 ) {
5067 v1.fromArray( array, j );
5068 v1.applyMatrix4(
this );
5069 v1.toArray( array, j );
5079 applyToBuffer:
function () {
5083 return function applyToBuffer( buffer, offset, length ) {
5085 if ( v1 === undefined ) v1 =
new THREE.Vector3();
5086 if ( offset === undefined ) offset = 0;
5087 if ( length === undefined ) length = buffer.length / buffer.itemSize;
5089 for ( var i = 0, j = offset; i < length; i ++, j ++ ) {
5091 v1.x = buffer.getX( j );
5092 v1.y = buffer.getY( j );
5093 v1.z = buffer.getZ( j );
5095 v1.applyMatrix4(
this );
5097 buffer.setXYZ( v1.x, v1.y, v1.z );
5107 rotateAxis:
function ( v ) {
5109 console.warn(
'THREE.Matrix4: .rotateAxis() has been removed. Use Vector3.transformDirection( matrix ) instead.' );
5111 v.transformDirection(
this );
5115 crossVector:
function ( vector ) {
5117 console.warn(
'THREE.Matrix4: .crossVector() has been removed. Use vector.applyMatrix4( matrix ) instead.' );
5118 return vector.applyMatrix4(
this );
5122 determinant:
function () {
5124 var te = this.elements;
5126 var n11 = te[ 0 ], n12 = te[ 4 ], n13 = te[ 8 ], n14 = te[ 12 ];
5127 var n21 = te[ 1 ], n22 = te[ 5 ], n23 = te[ 9 ], n24 = te[ 13 ];
5128 var n31 = te[ 2 ], n32 = te[ 6 ], n33 = te[ 10 ], n34 = te[ 14 ];
5129 var n41 = te[ 3 ], n42 = te[ 7 ], n43 = te[ 11 ], n44 = te[ 15 ];
5172 transpose:
function () {
5174 var te = this.elements;
5177 tmp = te[ 1 ]; te[ 1 ] = te[ 4 ]; te[ 4 ] = tmp;
5178 tmp = te[ 2 ]; te[ 2 ] = te[ 8 ]; te[ 8 ] = tmp;
5179 tmp = te[ 6 ]; te[ 6 ] = te[ 9 ]; te[ 9 ] = tmp;
5181 tmp = te[ 3 ]; te[ 3 ] = te[ 12 ]; te[ 12 ] = tmp;
5182 tmp = te[ 7 ]; te[ 7 ] = te[ 13 ]; te[ 13 ] = tmp;
5183 tmp = te[ 11 ]; te[ 11 ] = te[ 14 ]; te[ 14 ] = tmp;
5189 flattenToArrayOffset:
function ( array, offset ) {
5191 var te = this.elements;
5193 array[ offset ] = te[ 0 ];
5194 array[ offset + 1 ] = te[ 1 ];
5195 array[ offset + 2 ] = te[ 2 ];
5196 array[ offset + 3 ] = te[ 3 ];
5198 array[ offset + 4 ] = te[ 4 ];
5199 array[ offset + 5 ] = te[ 5 ];
5200 array[ offset + 6 ] = te[ 6 ];
5201 array[ offset + 7 ] = te[ 7 ];
5203 array[ offset + 8 ] = te[ 8 ];
5204 array[ offset + 9 ] = te[ 9 ];
5205 array[ offset + 10 ] = te[ 10 ];
5206 array[ offset + 11 ] = te[ 11 ];
5208 array[ offset + 12 ] = te[ 12 ];
5209 array[ offset + 13 ] = te[ 13 ];
5210 array[ offset + 14 ] = te[ 14 ];
5211 array[ offset + 15 ] = te[ 15 ];
5217 getPosition:
function () {
5221 return function () {
5223 if ( v1 === undefined ) v1 =
new THREE.Vector3();
5224 console.warn(
'THREE.Matrix4: .getPosition() has been removed. Use Vector3.setFromMatrixPosition( matrix ) instead.' );
5226 var te = this.elements;
5227 return v1.set( te[ 12 ], te[ 13 ], te[ 14 ] );
5233 setPosition:
function ( v ) {
5235 var te = this.elements;
5245 getInverse:
function ( m, throwOnInvertible ) {
5248 var te = this.elements;
5249 var me = m.elements;
5251 var n11 = me[ 0 ], n12 = me[ 4 ], n13 = me[ 8 ], n14 = me[ 12 ];
5252 var n21 = me[ 1 ], n22 = me[ 5 ], n23 = me[ 9 ], n24 = me[ 13 ];
5253 var n31 = me[ 2 ], n32 = me[ 6 ], n33 = me[ 10 ], n34 = me[ 14 ];
5254 var n41 = me[ 3 ], n42 = me[ 7 ], n43 = me[ 11 ], n44 = me[ 15 ];
5256 te[ 0 ] = n23 * n34 * n42 - n24 * n33 * n42 + n24 * n32 * n43 - n22 * n34 * n43 - n23 * n32 * n44 + n22 * n33 * n44;
5257 te[ 4 ] = n14 * n33 * n42 - n13 * n34 * n42 - n14 * n32 * n43 + n12 * n34 * n43 + n13 * n32 * n44 - n12 * n33 * n44;
5258 te[ 8 ] = n13 * n24 * n42 - n14 * n23 * n42 + n14 * n22 * n43 - n12 * n24 * n43 - n13 * n22 * n44 + n12 * n23 * n44;
5259 te[ 12 ] = n14 * n23 * n32 - n13 * n24 * n32 - n14 * n22 * n33 + n12 * n24 * n33 + n13 * n22 * n34 - n12 * n23 * n34;
5260 te[ 1 ] = n24 * n33 * n41 - n23 * n34 * n41 - n24 * n31 * n43 + n21 * n34 * n43 + n23 * n31 * n44 - n21 * n33 * n44;
5261 te[ 5 ] = n13 * n34 * n41 - n14 * n33 * n41 + n14 * n31 * n43 - n11 * n34 * n43 - n13 * n31 * n44 + n11 * n33 * n44;
5262 te[ 9 ] = n14 * n23 * n41 - n13 * n24 * n41 - n14 * n21 * n43 + n11 * n24 * n43 + n13 * n21 * n44 - n11 * n23 * n44;
5263 te[ 13 ] = n13 * n24 * n31 - n14 * n23 * n31 + n14 * n21 * n33 - n11 * n24 * n33 - n13 * n21 * n34 + n11 * n23 * n34;
5264 te[ 2 ] = n22 * n34 * n41 - n24 * n32 * n41 + n24 * n31 * n42 - n21 * n34 * n42 - n22 * n31 * n44 + n21 * n32 * n44;
5265 te[ 6 ] = n14 * n32 * n41 - n12 * n34 * n41 - n14 * n31 * n42 + n11 * n34 * n42 + n12 * n31 * n44 - n11 * n32 * n44;
5266 te[ 10 ] = n12 * n24 * n41 - n14 * n22 * n41 + n14 * n21 * n42 - n11 * n24 * n42 - n12 * n21 * n44 + n11 * n22 * n44;
5267 te[ 14 ] = n14 * n22 * n31 - n12 * n24 * n31 - n14 * n21 * n32 + n11 * n24 * n32 + n12 * n21 * n34 - n11 * n22 * n34;
5268 te[ 3 ] = n23 * n32 * n41 - n22 * n33 * n41 - n23 * n31 * n42 + n21 * n33 * n42 + n22 * n31 * n43 - n21 * n32 * n43;
5269 te[ 7 ] = n12 * n33 * n41 - n13 * n32 * n41 + n13 * n31 * n42 - n11 * n33 * n42 - n12 * n31 * n43 + n11 * n32 * n43;
5270 te[ 11 ] = n13 * n22 * n41 - n12 * n23 * n41 - n13 * n21 * n42 + n11 * n23 * n42 + n12 * n21 * n43 - n11 * n22 * n43;
5271 te[ 15 ] = n12 * n23 * n31 - n13 * n22 * n31 + n13 * n21 * n32 - n11 * n23 * n32 - n12 * n21 * n33 + n11 * n22 * n33;
5273 var det = n11 * te[ 0 ] + n21 * te[ 4 ] + n31 * te[ 8 ] + n41 * te[ 12 ];
5277 var msg =
"THREE.Matrix4.getInverse(): can't invert matrix, determinant is 0";
5279 if ( throwOnInvertible ||
false ) {
5281 throw new Error( msg );
5285 console.warn( msg );
5295 this.multiplyScalar( 1 / det );
5301 translate:
function ( v ) {
5303 console.error(
'THREE.Matrix4: .translate() has been removed.' );
5307 rotateX:
function ( angle ) {
5309 console.error(
'THREE.Matrix4: .rotateX() has been removed.' );
5313 rotateY:
function ( angle ) {
5315 console.error(
'THREE.Matrix4: .rotateY() has been removed.' );
5319 rotateZ:
function ( angle ) {
5321 console.error(
'THREE.Matrix4: .rotateZ() has been removed.' );
5325 rotateByAxis:
function ( axis, angle ) {
5327 console.error(
'THREE.Matrix4: .rotateByAxis() has been removed.' );
5331 scale:
function ( v ) {
5333 var te = this.elements;
5334 var x = v.x, y = v.y, z = v.z;
5336 te[ 0 ] *= x; te[ 4 ] *= y; te[ 8 ] *= z;
5337 te[ 1 ] *= x; te[ 5 ] *= y; te[ 9 ] *= z;
5338 te[ 2 ] *= x; te[ 6 ] *= y; te[ 10 ] *= z;
5339 te[ 3 ] *= x; te[ 7 ] *= y; te[ 11 ] *= z;
5345 getMaxScaleOnAxis:
function () {
5347 var te = this.elements;
5349 var scaleXSq = te[ 0 ] * te[ 0 ] + te[ 1 ] * te[ 1 ] + te[ 2 ] * te[ 2 ];
5350 var scaleYSq = te[ 4 ] * te[ 4 ] + te[ 5 ] * te[ 5 ] + te[ 6 ] * te[ 6 ];
5351 var scaleZSq = te[ 8 ] * te[ 8 ] + te[ 9 ] * te[ 9 ] + te[ 10 ] * te[ 10 ];
5353 return Math.sqrt( Math.max( scaleXSq, scaleYSq, scaleZSq ) );
5357 makeTranslation:
function ( x, y, z ) {
5372 makeRotationX:
function ( theta ) {
5374 var c = Math.cos( theta ), s = Math.sin( theta );
5389 makeRotationY:
function ( theta ) {
5391 var c = Math.cos( theta ), s = Math.sin( theta );
5406 makeRotationZ:
function ( theta ) {
5408 var c = Math.cos( theta ), s = Math.sin( theta );
5423 makeRotationAxis:
function ( axis, angle ) {
5427 var c = Math.cos( angle );
5428 var s = Math.sin( angle );
5430 var x = axis.x, y = axis.y, z = axis.z;
5431 var tx = t * x, ty = t * y;
5435 tx * x + c, tx * y - s * z, tx * z + s * y, 0,
5436 tx * y + s * z, ty * y + c, ty * z - s * x, 0,
5437 tx * z - s * y, ty * z + s * x, t * z * z + c, 0,
5446 makeScale:
function ( x, y, z ) {
5461 compose:
function ( position, quaternion, scale ) {
5463 this.makeRotationFromQuaternion( quaternion );
5464 this.scale( scale );
5465 this.setPosition( position );
5471 decompose:
function () {
5475 return function ( position, quaternion, scale ) {
5477 if ( vector === undefined ) vector =
new THREE.Vector3();
5478 if ( matrix === undefined ) matrix =
new THREE.Matrix4();
5480 var te = this.elements;
5482 var sx = vector.set( te[ 0 ], te[ 1 ], te[ 2 ] ).length();
5483 var sy = vector.set( te[ 4 ], te[ 5 ], te[ 6 ] ).length();
5484 var sz = vector.set( te[ 8 ], te[ 9 ], te[ 10 ] ).length();
5487 var det = this.determinant();
5494 position.x = te[ 12 ];
5495 position.y = te[ 13 ];
5496 position.z = te[ 14 ];
5500 matrix.elements.set( this.elements );
5506 matrix.elements[ 0 ] *= invSX;
5507 matrix.elements[ 1 ] *= invSX;
5508 matrix.elements[ 2 ] *= invSX;
5510 matrix.elements[ 4 ] *= invSY;
5511 matrix.elements[ 5 ] *= invSY;
5512 matrix.elements[ 6 ] *= invSY;
5514 matrix.elements[ 8 ] *= invSZ;
5515 matrix.elements[ 9 ] *= invSZ;
5516 matrix.elements[ 10 ] *= invSZ;
5518 quaternion.setFromRotationMatrix( matrix );
5530 makeFrustum:
function ( left, right, bottom, top, near, far ) {
5532 var te = this.elements;
5533 var x = 2 * near / ( right - left );
5534 var y = 2 * near / ( top - bottom );
5536 var a = ( right + left ) / ( right - left );
5537 var b = ( top + bottom ) / ( top - bottom );
5538 var c = - ( far + near ) / ( far - near );
5539 var d = - 2 * far * near / ( far - near );
5541 te[ 0 ] = x; te[ 4 ] = 0; te[ 8 ] = a; te[ 12 ] = 0;
5542 te[ 1 ] = 0; te[ 5 ] = y; te[ 9 ] = b; te[ 13 ] = 0;
5543 te[ 2 ] = 0; te[ 6 ] = 0; te[ 10 ] = c; te[ 14 ] = d;
5544 te[ 3 ] = 0; te[ 7 ] = 0; te[ 11 ] = - 1; te[ 15 ] = 0;
5550 makePerspective:
function ( fov, aspect, near, far ) {
5552 var ymax = near * Math.tan( THREE.Math.degToRad( fov * 0.5 ) );
5554 var xmin = ymin * aspect;
5555 var xmax = ymax * aspect;
5557 return this.makeFrustum( xmin, xmax, ymin, ymax, near, far );
5561 makeOrthographic:
function ( left, right, top, bottom, near, far ) {
5563 var te = this.elements;
5564 var w = right - left;
5565 var h = top - bottom;
5568 var x = ( right + left ) / w;
5569 var y = ( top + bottom ) / h;
5570 var z = ( far + near ) / p;
5572 te[ 0 ] = 2 / w; te[ 4 ] = 0; te[ 8 ] = 0; te[ 12 ] = - x;
5573 te[ 1 ] = 0; te[ 5 ] = 2 / h; te[ 9 ] = 0; te[ 13 ] = - y;
5574 te[ 2 ] = 0; te[ 6 ] = 0; te[ 10 ] = - 2 / p; te[ 14 ] = - z;
5575 te[ 3 ] = 0; te[ 7 ] = 0; te[ 11 ] = 0; te[ 15 ] = 1;
5581 equals:
function ( matrix ) {
5583 var te = this.elements;
5584 var me = matrix.elements;
5586 for ( var i = 0; i < 16; i ++ ) {
5588 if ( te[ i ] !== me[ i ] )
return false;
5596 fromArray:
function ( array ) {
5598 this.elements.set( array );
5604 toArray:
function () {
5606 var te = this.elements;
5609 te[ 0 ], te[ 1 ], te[ 2 ], te[ 3 ],
5610 te[ 4 ], te[ 5 ], te[ 6 ], te[ 7 ],
5611 te[ 8 ], te[ 9 ], te[ 10 ], te[ 11 ],
5612 te[ 12 ], te[ 13 ], te[ 14 ], te[ 15 ]
5625 THREE.Ray =
function ( origin, direction ) {
5627 this.origin = ( origin !== undefined ) ? origin :
new THREE.Vector3();
5628 this.direction = ( direction !== undefined ) ? direction :
new THREE.Vector3();
5632 THREE.Ray.prototype = {
5634 constructor: THREE.Ray,
5636 set:
function ( origin, direction ) {
5638 this.origin.copy( origin );
5639 this.direction.copy( direction );
5645 clone:
function () {
5647 return new this.constructor().copy(
this );
5651 copy:
function ( ray ) {
5653 this.origin.copy( ray.origin );
5654 this.direction.copy( ray.direction );
5660 at:
function ( t, optionalTarget ) {
5662 var result = optionalTarget ||
new THREE.Vector3();
5664 return result.copy( this.direction ).multiplyScalar( t ).add( this.origin );
5668 recast:
function () {
5670 var v1 =
new THREE.Vector3();
5672 return function ( t ) {
5674 this.origin.copy( this.at( t, v1 ) );
5682 closestPointToPoint:
function ( point, optionalTarget ) {
5684 var result = optionalTarget ||
new THREE.Vector3();
5685 result.subVectors( point, this.origin );
5686 var directionDistance = result.dot( this.direction );
5688 if ( directionDistance < 0 ) {
5690 return result.copy( this.origin );
5694 return result.copy( this.direction ).multiplyScalar( directionDistance ).add( this.origin );
5698 distanceToPoint:
function ( point ) {
5700 return Math.sqrt( this.distanceSqToPoint( point ) );
5704 distanceSqToPoint:
function () {
5706 var v1 =
new THREE.Vector3();
5708 return function ( point ) {
5710 var directionDistance = v1.subVectors( point, this.origin ).dot( this.direction );
5714 if ( directionDistance < 0 ) {
5716 return this.origin.distanceToSquared( point );
5720 v1.copy( this.direction ).multiplyScalar( directionDistance ).add( this.origin );
5722 return v1.distanceToSquared( point );
5728 distanceSqToSegment:
function () {
5730 var segCenter =
new THREE.Vector3();
5731 var segDir =
new THREE.Vector3();
5732 var diff =
new THREE.Vector3();
5734 return function ( v0, v1, optionalPointOnRay, optionalPointOnSegment ) {
5743 segCenter.copy( v0 ).add( v1 ).multiplyScalar( 0.5 );
5744 segDir.copy( v1 ).sub( v0 ).normalize();
5745 diff.copy( this.origin ).sub( segCenter );
5747 var segExtent = v0.distanceTo( v1 ) * 0.5;
5748 var a01 = - this.direction.dot( segDir );
5749 var b0 = diff.dot( this.direction );
5750 var b1 = - diff.dot( segDir );
5751 var c = diff.lengthSq();
5752 var det = Math.abs( 1 - a01 * a01 );
5753 var s0, s1, sqrDist, extDet;
5761 extDet = segExtent * det;
5765 if ( s1 >= - extDet ) {
5767 if ( s1 <= extDet ) {
5772 var invDet = 1 / det;
5775 sqrDist = s0 * ( s0 + a01 * s1 + 2 * b0 ) + s1 * ( a01 * s0 + s1 + 2 * b1 ) + c;
5782 s0 = Math.max( 0, - ( a01 * s1 + b0 ) );
5783 sqrDist = - s0 * s0 + s1 * ( s1 + 2 * b1 ) + c;
5792 s0 = Math.max( 0, - ( a01 * s1 + b0 ) );
5793 sqrDist = - s0 * s0 + s1 * ( s1 + 2 * b1 ) + c;
5799 if ( s1 <= - extDet ) {
5803 s0 = Math.max( 0, - ( - a01 * segExtent + b0 ) );
5804 s1 = ( s0 > 0 ) ? - segExtent : Math.min( Math.max( - segExtent, - b1 ), segExtent );
5805 sqrDist = - s0 * s0 + s1 * ( s1 + 2 * b1 ) + c;
5807 }
else if ( s1 <= extDet ) {
5812 s1 = Math.min( Math.max( - segExtent, - b1 ), segExtent );
5813 sqrDist = s1 * ( s1 + 2 * b1 ) + c;
5819 s0 = Math.max( 0, - ( a01 * segExtent + b0 ) );
5820 s1 = ( s0 > 0 ) ? segExtent : Math.min( Math.max( - segExtent, - b1 ), segExtent );
5821 sqrDist = - s0 * s0 + s1 * ( s1 + 2 * b1 ) + c;
5831 s1 = ( a01 > 0 ) ? - segExtent : segExtent;
5832 s0 = Math.max( 0, - ( a01 * s1 + b0 ) );
5833 sqrDist = - s0 * s0 + s1 * ( s1 + 2 * b1 ) + c;
5837 if ( optionalPointOnRay ) {
5839 optionalPointOnRay.copy( this.direction ).multiplyScalar( s0 ).add( this.origin );
5843 if ( optionalPointOnSegment ) {
5845 optionalPointOnSegment.copy( segDir ).multiplyScalar( s1 ).add( segCenter );
5856 isIntersectionSphere:
function ( sphere ) {
5858 return this.distanceToPoint( sphere.center ) <= sphere.radius;
5862 intersectSphere:
function () {
5866 var v1 =
new THREE.Vector3();
5868 return function ( sphere, optionalTarget ) {
5870 v1.subVectors( sphere.center,
this.origin );
5872 var tca = v1.dot( this.direction );
5874 var d2 = v1.dot( v1 ) - tca * tca;
5876 var radius2 = sphere.radius * sphere.radius;
5878 if ( d2 > radius2 )
return null;
5880 var thc = Math.sqrt( radius2 - d2 );
5889 if ( t0 < 0 && t1 < 0 )
return null;
5894 if ( t0 < 0 )
return this.at( t1, optionalTarget );
5897 return this.at( t0, optionalTarget );
5903 isIntersectionPlane:
function ( plane ) {
5907 var distToPoint = plane.distanceToPoint( this.origin );
5909 if ( distToPoint === 0 ) {
5915 var denominator = plane.normal.dot( this.direction );
5917 if ( denominator * distToPoint < 0 ) {
5929 distanceToPlane:
function ( plane ) {
5931 var denominator = plane.normal.dot( this.direction );
5932 if ( denominator === 0 ) {
5935 if ( plane.distanceToPoint(
this.origin ) === 0 ) {
5947 var t = - ( this.origin.dot( plane.normal ) + plane.constant ) / denominator;
5951 return t >= 0 ? t : null;
5955 intersectPlane:
function ( plane, optionalTarget ) {
5957 var t = this.distanceToPlane( plane );
5965 return this.at( t, optionalTarget );
5969 isIntersectionBox:
function () {
5971 var v =
new THREE.Vector3();
5973 return function ( box ) {
5975 return this.intersectBox( box, v ) !== null;
5981 intersectBox:
function ( box, optionalTarget ) {
5985 var tmin, tmax, tymin, tymax, tzmin, tzmax;
5987 var invdirx = 1 / this.direction.x,
5988 invdiry = 1 / this.direction.y,
5989 invdirz = 1 / this.direction.z;
5991 var origin = this.origin;
5993 if ( invdirx >= 0 ) {
5995 tmin = ( box.min.x - origin.x ) * invdirx;
5996 tmax = ( box.max.x - origin.x ) * invdirx;
6000 tmin = ( box.max.x - origin.x ) * invdirx;
6001 tmax = ( box.min.x - origin.x ) * invdirx;
6005 if ( invdiry >= 0 ) {
6007 tymin = ( box.min.y - origin.y ) * invdiry;
6008 tymax = ( box.max.y - origin.y ) * invdiry;
6012 tymin = ( box.max.y - origin.y ) * invdiry;
6013 tymax = ( box.min.y - origin.y ) * invdiry;
6017 if ( ( tmin > tymax ) || ( tymin > tmax ) )
return null;
6022 if ( tymin > tmin || tmin !== tmin ) tmin = tymin;
6024 if ( tymax < tmax || tmax !== tmax ) tmax = tymax;
6026 if ( invdirz >= 0 ) {
6028 tzmin = ( box.min.z - origin.z ) * invdirz;
6029 tzmax = ( box.max.z - origin.z ) * invdirz;
6033 tzmin = ( box.max.z - origin.z ) * invdirz;
6034 tzmax = ( box.min.z - origin.z ) * invdirz;
6038 if ( ( tmin > tzmax ) || ( tzmin > tmax ) )
return null;
6040 if ( tzmin > tmin || tmin !== tmin ) tmin = tzmin;
6042 if ( tzmax < tmax || tmax !== tmax ) tmax = tzmax;
6046 if ( tmax < 0 )
return null;
6048 return this.at( tmin >= 0 ? tmin : tmax, optionalTarget );
6052 intersectTriangle:
function () {
6055 var diff =
new THREE.Vector3();
6056 var edge1 =
new THREE.Vector3();
6057 var edge2 =
new THREE.Vector3();
6058 var normal =
new THREE.Vector3();
6060 return function ( a, b, c, backfaceCulling, optionalTarget ) {
6064 edge1.subVectors( b, a );
6065 edge2.subVectors( c, a );
6066 normal.crossVectors( edge1, edge2 );
6073 var DdN = this.direction.dot( normal );
6078 if ( backfaceCulling )
return null;
6081 }
else if ( DdN < 0 ) {
6092 diff.subVectors( this.origin, a );
6093 var DdQxE2 = sign * this.direction.dot( edge2.crossVectors( diff, edge2 ) );
6102 var DdE1xQ = sign * this.direction.dot( edge1.cross( diff ) );
6112 if ( DdQxE2 + DdE1xQ > DdN ) {
6119 var QdN = - sign * diff.dot( normal );
6129 return this.at( QdN / DdN, optionalTarget );
6135 applyMatrix4:
function ( matrix4 ) {
6137 this.direction.add( this.origin ).applyMatrix4( matrix4 );
6138 this.origin.applyMatrix4( matrix4 );
6139 this.direction.sub( this.origin );
6140 this.direction.normalize();
6146 equals:
function ( ray ) {
6148 return ray.origin.equals( this.origin ) && ray.direction.equals( this.direction );
6161 THREE.Sphere =
function ( center, radius ) {
6163 this.center = ( center !== undefined ) ? center :
new THREE.Vector3();
6164 this.radius = ( radius !== undefined ) ? radius : 0;
6168 THREE.Sphere.prototype = {
6170 constructor: THREE.Sphere,
6172 set:
function ( center, radius ) {
6174 this.center.copy( center );
6175 this.radius = radius;
6181 setFromPoints:
function () {
6183 var box =
new THREE.Box3();
6185 return function ( points, optionalCenter ) {
6187 var center = this.center;
6189 if ( optionalCenter !== undefined ) {
6191 center.copy( optionalCenter );
6195 box.setFromPoints( points ).center( center );
6199 var maxRadiusSq = 0;
6201 for ( var i = 0, il = points.length; i < il; i ++ ) {
6203 maxRadiusSq = Math.max( maxRadiusSq, center.distanceToSquared( points[ i ] ) );
6207 this.radius = Math.sqrt( maxRadiusSq );
6215 clone:
function () {
6217 return new this.constructor().copy(
this );
6221 copy:
function ( sphere ) {
6223 this.center.copy( sphere.center );
6224 this.radius = sphere.radius;
6230 empty:
function () {
6232 return ( this.radius <= 0 );
6236 containsPoint:
function ( point ) {
6238 return ( point.distanceToSquared(
this.center ) <= ( this.radius * this.radius ) );
6242 distanceToPoint:
function ( point ) {
6244 return ( point.distanceTo(
this.center ) - this.radius );
6248 intersectsSphere:
function ( sphere ) {
6250 var radiusSum = this.radius + sphere.radius;
6252 return sphere.center.distanceToSquared( this.center ) <= ( radiusSum * radiusSum );
6256 clampPoint:
function ( point, optionalTarget ) {
6258 var deltaLengthSq = this.center.distanceToSquared( point );
6260 var result = optionalTarget ||
new THREE.Vector3();
6261 result.copy( point );
6263 if ( deltaLengthSq > ( this.radius * this.radius ) ) {
6265 result.sub( this.center ).normalize();
6266 result.multiplyScalar( this.radius ).add( this.center );
6274 getBoundingBox:
function ( optionalTarget ) {
6276 var box = optionalTarget ||
new THREE.Box3();
6278 box.set( this.center, this.center );
6279 box.expandByScalar( this.radius );
6285 applyMatrix4:
function ( matrix ) {
6287 this.center.applyMatrix4( matrix );
6288 this.radius = this.radius * matrix.getMaxScaleOnAxis();
6294 translate:
function ( offset ) {
6296 this.center.add( offset );
6302 equals:
function ( sphere ) {
6304 return sphere.center.equals( this.center ) && ( sphere.radius === this.radius );
6318 THREE.Frustum =
function ( p0, p1, p2, p3, p4, p5 ) {
6322 ( p0 !== undefined ) ? p0 :
new THREE.Plane(),
6323 ( p1 !== undefined ) ? p1 :
new THREE.Plane(),
6324 ( p2 !== undefined ) ? p2 :
new THREE.Plane(),
6325 ( p3 !== undefined ) ? p3 :
new THREE.Plane(),
6326 ( p4 !== undefined ) ? p4 :
new THREE.Plane(),
6327 ( p5 !== undefined ) ? p5 :
new THREE.Plane()
6333 THREE.Frustum.prototype = {
6335 constructor: THREE.Frustum,
6337 set:
function ( p0, p1, p2, p3, p4, p5 ) {
6339 var planes = this.planes;
6341 planes[ 0 ].copy( p0 );
6342 planes[ 1 ].copy( p1 );
6343 planes[ 2 ].copy( p2 );
6344 planes[ 3 ].copy( p3 );
6345 planes[ 4 ].copy( p4 );
6346 planes[ 5 ].copy( p5 );
6352 clone:
function () {
6354 return new this.constructor().copy(
this );
6358 copy:
function ( frustum ) {
6360 var planes = this.planes;
6362 for ( var i = 0; i < 6; i ++ ) {
6364 planes[ i ].copy( frustum.planes[ i ] );
6372 setFromMatrix:
function ( m ) {
6374 var planes = this.planes;
6375 var me = m.elements;
6376 var me0 = me[ 0 ], me1 = me[ 1 ], me2 = me[ 2 ], me3 = me[ 3 ];
6377 var me4 = me[ 4 ], me5 = me[ 5 ], me6 = me[ 6 ], me7 = me[ 7 ];
6378 var me8 = me[ 8 ], me9 = me[ 9 ], me10 = me[ 10 ], me11 = me[ 11 ];
6379 var me12 = me[ 12 ], me13 = me[ 13 ], me14 = me[ 14 ], me15 = me[ 15 ];
6381 planes[ 0 ].setComponents( me3 - me0, me7 - me4, me11 - me8, me15 - me12 ).normalize();
6382 planes[ 1 ].setComponents( me3 + me0, me7 + me4, me11 + me8, me15 + me12 ).normalize();
6383 planes[ 2 ].setComponents( me3 + me1, me7 + me5, me11 + me9, me15 + me13 ).normalize();
6384 planes[ 3 ].setComponents( me3 - me1, me7 - me5, me11 - me9, me15 - me13 ).normalize();
6385 planes[ 4 ].setComponents( me3 - me2, me7 - me6, me11 - me10, me15 - me14 ).normalize();
6386 planes[ 5 ].setComponents( me3 + me2, me7 + me6, me11 + me10, me15 + me14 ).normalize();
6392 intersectsObject:
function () {
6394 var sphere =
new THREE.Sphere();
6396 return function ( object ) {
6398 var geometry =
object.geometry;
6400 if ( geometry.boundingSphere === null ) geometry.computeBoundingSphere();
6402 sphere.copy( geometry.boundingSphere );
6403 sphere.applyMatrix4(
object.matrixWorld );
6405 return this.intersectsSphere( sphere );
6411 intersectsSphere:
function ( sphere ) {
6413 var planes = this.planes;
6414 var center = sphere.center;
6415 var negRadius = - sphere.radius;
6417 for ( var i = 0; i < 6; i ++ ) {
6419 var distance = planes[ i ].distanceToPoint( center );
6421 if ( distance < negRadius ) {
6433 intersectsBox:
function () {
6435 var p1 =
new THREE.Vector3(),
6436 p2 =
new THREE.Vector3();
6438 return function ( box ) {
6440 var planes = this.planes;
6442 for ( var i = 0; i < 6 ; i ++ ) {
6444 var plane = planes[ i ];
6446 p1.x = plane.normal.x > 0 ? box.min.x : box.max.x;
6447 p2.x = plane.normal.x > 0 ? box.max.x : box.min.x;
6448 p1.y = plane.normal.y > 0 ? box.min.y : box.max.y;
6449 p2.y = plane.normal.y > 0 ? box.max.y : box.min.y;
6450 p1.z = plane.normal.z > 0 ? box.min.z : box.max.z;
6451 p2.z = plane.normal.z > 0 ? box.max.z : box.min.z;
6453 var d1 = plane.distanceToPoint( p1 );
6454 var d2 = plane.distanceToPoint( p2 );
6458 if ( d1 < 0 && d2 < 0 ) {
6473 containsPoint:
function ( point ) {
6475 var planes = this.planes;
6477 for ( var i = 0; i < 6; i ++ ) {
6479 if ( planes[ i ].distanceToPoint( point ) < 0 ) {
6499 THREE.Plane =
function ( normal, constant ) {
6501 this.normal = ( normal !== undefined ) ? normal :
new THREE.Vector3( 1, 0, 0 );
6502 this.constant = ( constant !== undefined ) ? constant : 0;
6506 THREE.Plane.prototype = {
6508 constructor: THREE.Plane,
6510 set:
function ( normal, constant ) {
6512 this.normal.copy( normal );
6513 this.constant = constant;
6519 setComponents:
function ( x, y, z, w ) {
6521 this.normal.set( x, y, z );
6528 setFromNormalAndCoplanarPoint:
function ( normal, point ) {
6530 this.normal.copy( normal );
6531 this.constant = - point.dot( this.normal );
6537 setFromCoplanarPoints:
function () {
6539 var v1 =
new THREE.Vector3();
6540 var v2 =
new THREE.Vector3();
6542 return function ( a, b, c ) {
6544 var normal = v1.subVectors( c, b ).cross( v2.subVectors( a, b ) ).normalize();
6548 this.setFromNormalAndCoplanarPoint( normal, a );
6556 clone:
function () {
6558 return new this.constructor().copy(
this );
6562 copy:
function ( plane ) {
6564 this.normal.copy( plane.normal );
6565 this.constant = plane.constant;
6571 normalize:
function () {
6575 var inverseNormalLength = 1.0 / this.normal.length();
6576 this.normal.multiplyScalar( inverseNormalLength );
6577 this.constant *= inverseNormalLength;
6583 negate:
function () {
6585 this.constant *= - 1;
6586 this.normal.negate();
6592 distanceToPoint:
function ( point ) {
6594 return this.normal.dot( point ) + this.constant;
6598 distanceToSphere:
function ( sphere ) {
6600 return this.distanceToPoint( sphere.center ) - sphere.radius;
6604 projectPoint:
function ( point, optionalTarget ) {
6606 return this.orthoPoint( point, optionalTarget ).sub( point ).negate();
6610 orthoPoint:
function ( point, optionalTarget ) {
6612 var perpendicularMagnitude = this.distanceToPoint( point );
6614 var result = optionalTarget ||
new THREE.Vector3();
6615 return result.copy( this.normal ).multiplyScalar( perpendicularMagnitude );
6619 isIntersectionLine:
function ( line ) {
6623 var startSign = this.distanceToPoint( line.start );
6624 var endSign = this.distanceToPoint( line.end );
6626 return ( startSign < 0 && endSign > 0 ) || ( endSign < 0 && startSign > 0 );
6630 intersectLine:
function () {
6632 var v1 =
new THREE.Vector3();
6634 return function ( line, optionalTarget ) {
6636 var result = optionalTarget ||
new THREE.Vector3();
6638 var direction = line.delta( v1 );
6640 var denominator = this.normal.dot( direction );
6642 if ( denominator === 0 ) {
6645 if ( this.distanceToPoint( line.start ) === 0 ) {
6647 return result.copy( line.start );
6656 var t = - ( line.start.dot( this.normal ) + this.constant ) / denominator;
6658 if ( t < 0 || t > 1 ) {
6664 return result.copy( direction ).multiplyScalar( t ).add( line.start );
6671 coplanarPoint:
function ( optionalTarget ) {
6673 var result = optionalTarget ||
new THREE.Vector3();
6674 return result.copy( this.normal ).multiplyScalar( - this.constant );
6678 applyMatrix4:
function () {
6680 var v1 =
new THREE.Vector3();
6681 var v2 =
new THREE.Vector3();
6682 var m1 =
new THREE.Matrix3();
6684 return function ( matrix, optionalNormalMatrix ) {
6688 var normalMatrix = optionalNormalMatrix || m1.getNormalMatrix( matrix );
6689 var newNormal = v1.copy( this.normal ).applyMatrix3( normalMatrix );
6691 var newCoplanarPoint = this.coplanarPoint( v2 );
6692 newCoplanarPoint.applyMatrix4( matrix );
6694 this.setFromNormalAndCoplanarPoint( newNormal, newCoplanarPoint );
6702 translate:
function ( offset ) {
6704 this.constant = this.constant - offset.dot( this.normal );
6710 equals:
function ( plane ) {
6712 return plane.normal.equals( this.normal ) && ( plane.constant === this.constant );
6727 generateUUID:
function () {
6731 var chars =
'0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'.split(
'' );
6732 var uuid =
new Array( 36 );
6735 return function () {
6737 for ( var i = 0; i < 36; i ++ ) {
6739 if ( i === 8 || i === 13 || i === 18 || i === 23 ) {
6743 }
else if ( i === 14 ) {
6749 if ( rnd <= 0x02 ) rnd = 0x2000000 + ( Math.random() * 0x1000000 ) | 0;
6752 uuid[ i ] = chars[ ( i === 19 ) ? ( r & 0x3 ) | 0x8 : r ];
6758 return uuid.join(
'' );
6764 clamp:
function ( value, min, max ) {
6766 return Math.max( min, Math.min( max, value ) );
6773 euclideanModulo:
function ( n, m ) {
6775 return ( ( n % m ) + m ) % m;
6781 mapLinear:
function ( x, a1, a2, b1, b2 ) {
6783 return b1 + ( x - a1 ) * ( b2 - b1 ) / ( a2 - a1 );
6789 smoothstep:
function ( x, min, max ) {
6791 if ( x <= min )
return 0;
6792 if ( x >= max )
return 1;
6794 x = ( x - min ) / ( max - min );
6796 return x * x * ( 3 - 2 * x );
6800 smootherstep:
function ( x, min, max ) {
6802 if ( x <= min )
return 0;
6803 if ( x >= max )
return 1;
6805 x = ( x - min ) / ( max - min );
6807 return x * x * x * ( x * ( x * 6 - 15 ) + 10 );
6814 random16:
function () {
6816 return ( 65280 * Math.random() + 255 * Math.random() ) / 65535;
6822 randInt:
function ( low, high ) {
6824 return low + Math.floor( Math.random() * ( high - low + 1 ) );
6830 randFloat:
function ( low, high ) {
6832 return low + Math.random() * ( high - low );
6838 randFloatSpread:
function ( range ) {
6840 return range * ( 0.5 - Math.random() );
6844 degToRad:
function () {
6846 var degreeToRadiansFactor = Math.PI / 180;
6848 return function ( degrees ) {
6850 return degrees * degreeToRadiansFactor;
6856 radToDeg:
function () {
6858 var radianToDegreesFactor = 180 / Math.PI;
6860 return function ( radians ) {
6862 return radians * radianToDegreesFactor;
6868 isPowerOfTwo:
function ( value ) {
6870 return ( value & ( value - 1 ) ) === 0 && value !== 0;
6874 nearestPowerOfTwo:
function ( value ) {
6876 return Math.pow( 2, Math.round( Math.log( value ) / Math.LN2 ) );
6880 nextPowerOfTwo:
function ( value ) {
6883 value |= value >> 1;
6884 value |= value >> 2;
6885 value |= value >> 4;
6886 value |= value >> 8;
6887 value |= value >> 16;
6906 THREE.Spline =
function ( points ) {
6908 this.points = points;
6910 var c = [], v3 = { x: 0, y: 0, z: 0 },
6911 point, intPoint, weight, w2, w3,
6914 this.initFromArray =
function ( a ) {
6918 for ( var i = 0; i < a.length; i ++ ) {
6920 this.points[ i ] = { x: a[ i ][ 0 ], y: a[ i ][ 1 ], z: a[ i ][ 2 ] };
6926 this.getPoint =
function ( k ) {
6928 point = ( this.points.length - 1 ) * k;
6929 intPoint = Math.floor( point );
6930 weight = point - intPoint;
6932 c[ 0 ] = intPoint === 0 ? intPoint : intPoint - 1;
6934 c[ 2 ] = intPoint > this.points.length - 2 ? this.points.length - 1 : intPoint + 1;
6935 c[ 3 ] = intPoint > this.points.length - 3 ? this.points.length - 1 : intPoint + 2;
6937 pa = this.points[ c[ 0 ] ];
6938 pb = this.points[ c[ 1 ] ];
6939 pc = this.points[ c[ 2 ] ];
6940 pd = this.points[ c[ 3 ] ];
6942 w2 = weight * weight;
6945 v3.x = interpolate( pa.x, pb.x, pc.x, pd.x, weight, w2, w3 );
6946 v3.y = interpolate( pa.y, pb.y, pc.y, pd.y, weight, w2, w3 );
6947 v3.z = interpolate( pa.z, pb.z, pc.z, pd.z, weight, w2, w3 );
6953 this.getControlPointsArray =
function () {
6955 var i, p, l = this.points.length,
6958 for ( i = 0; i < l; i ++ ) {
6960 p = this.points[ i ];
6961 coords[ i ] = [ p.x, p.y, p.z ];
6971 this.getLength =
function ( nSubDivisions ) {
6973 var i, index, nSamples, position,
6974 point = 0, intPoint = 0, oldIntPoint = 0,
6975 oldPosition =
new THREE.Vector3(),
6976 tmpVec =
new THREE.Vector3(),
6982 chunkLengths[ 0 ] = 0;
6984 if ( ! nSubDivisions ) nSubDivisions = 100;
6986 nSamples = this.points.length * nSubDivisions;
6988 oldPosition.copy( this.points[ 0 ] );
6990 for ( i = 1; i < nSamples; i ++ ) {
6992 index = i / nSamples;
6994 position = this.getPoint( index );
6995 tmpVec.copy( position );
6997 totalLength += tmpVec.distanceTo( oldPosition );
6999 oldPosition.copy( position );
7001 point = ( this.points.length - 1 ) * index;
7002 intPoint = Math.floor( point );
7004 if ( intPoint !== oldIntPoint ) {
7006 chunkLengths[ intPoint ] = totalLength;
7007 oldIntPoint = intPoint;
7015 chunkLengths[ chunkLengths.length ] = totalLength;
7017 return { chunks: chunkLengths, total: totalLength };
7021 this.reparametrizeByArcLength =
function ( samplingCoef ) {
7024 index, indexCurrent, indexNext,
7028 tmpVec =
new THREE.Vector3(),
7029 sl = this.getLength();
7031 newpoints.push( tmpVec.copy(
this.points[ 0 ] ).clone() );
7033 for ( i = 1; i < this.points.length; i ++ ) {
7038 realDistance = sl.chunks[ i ] - sl.chunks[ i - 1 ];
7040 sampling = Math.ceil( samplingCoef * realDistance / sl.total );
7042 indexCurrent = ( i - 1 ) / ( this.points.length - 1 );
7043 indexNext = i / ( this.points.length - 1 );
7045 for ( j = 1; j < sampling - 1; j ++ ) {
7047 index = indexCurrent + j * ( 1 / sampling ) * ( indexNext - indexCurrent );
7049 position = this.getPoint( index );
7050 newpoints.push( tmpVec.copy( position ).clone() );
7054 newpoints.push( tmpVec.copy(
this.points[ i ] ).clone() );
7058 this.points = newpoints;
7064 function interpolate( p0, p1, p2, p3, t, t2, t3 ) {
7066 var v0 = ( p2 - p0 ) * 0.5,
7067 v1 = ( p3 - p1 ) * 0.5;
7069 return ( 2 * ( p1 - p2 ) + v0 + v1 ) * t3 + ( - 3 * ( p1 - p2 ) - 2 * v0 - v1 ) * t2 + v0 * t + p1;
7082 THREE.Triangle =
function ( a, b, c ) {
7084 this.a = ( a !== undefined ) ? a :
new THREE.Vector3();
7085 this.b = ( b !== undefined ) ? b :
new THREE.Vector3();
7086 this.c = ( c !== undefined ) ? c :
new THREE.Vector3();
7090 THREE.Triangle.normal =
function () {
7092 var v0 =
new THREE.Vector3();
7094 return function ( a, b, c, optionalTarget ) {
7096 var result = optionalTarget ||
new THREE.Vector3();
7098 result.subVectors( c, b );
7099 v0.subVectors( a, b );
7102 var resultLengthSq = result.lengthSq();
7103 if ( resultLengthSq > 0 ) {
7105 return result.multiplyScalar( 1 / Math.sqrt( resultLengthSq ) );
7109 return result.set( 0, 0, 0 );
7117 THREE.Triangle.barycoordFromPoint =
function () {
7119 var v0 =
new THREE.Vector3();
7120 var v1 =
new THREE.Vector3();
7121 var v2 =
new THREE.Vector3();
7123 return function ( point, a, b, c, optionalTarget ) {
7125 v0.subVectors( c, a );
7126 v1.subVectors( b, a );
7127 v2.subVectors( point, a );
7129 var dot00 = v0.dot( v0 );
7130 var dot01 = v0.dot( v1 );
7131 var dot02 = v0.dot( v2 );
7132 var dot11 = v1.dot( v1 );
7133 var dot12 = v1.dot( v2 );
7135 var denom = ( dot00 * dot11 - dot01 * dot01 );
7137 var result = optionalTarget ||
new THREE.Vector3();
7140 if ( denom === 0 ) {
7144 return result.set( - 2, - 1, - 1 );
7148 var invDenom = 1 / denom;
7149 var u = ( dot11 * dot02 - dot01 * dot12 ) * invDenom;
7150 var v = ( dot00 * dot12 - dot01 * dot02 ) * invDenom;
7153 return result.set( 1 - u - v, v, u );
7159 THREE.Triangle.containsPoint =
function () {
7161 var v1 =
new THREE.Vector3();
7163 return function ( point, a, b, c ) {
7165 var result = THREE.Triangle.barycoordFromPoint( point, a, b, c, v1 );
7167 return ( result.x >= 0 ) && ( result.y >= 0 ) && ( ( result.x + result.y ) <= 1 );
7173 THREE.Triangle.prototype = {
7175 constructor: THREE.Triangle,
7177 set:
function ( a, b, c ) {
7187 setFromPointsAndIndices:
function ( points, i0, i1, i2 ) {
7189 this.a.copy( points[ i0 ] );
7190 this.b.copy( points[ i1 ] );
7191 this.c.copy( points[ i2 ] );
7197 clone:
function () {
7199 return new this.constructor().copy(
this );
7203 copy:
function ( triangle ) {
7205 this.a.copy( triangle.a );
7206 this.b.copy( triangle.b );
7207 this.c.copy( triangle.c );
7215 var v0 =
new THREE.Vector3();
7216 var v1 =
new THREE.Vector3();
7218 return function () {
7220 v0.subVectors( this.c, this.b );
7221 v1.subVectors( this.a, this.b );
7223 return v0.cross( v1 ).length() * 0.5;
7229 midpoint:
function ( optionalTarget ) {
7231 var result = optionalTarget ||
new THREE.Vector3();
7232 return result.addVectors( this.a, this.b ).add( this.c ).multiplyScalar( 1 / 3 );
7236 normal:
function ( optionalTarget ) {
7238 return THREE.Triangle.normal( this.a, this.b, this.c, optionalTarget );
7242 plane:
function ( optionalTarget ) {
7244 var result = optionalTarget ||
new THREE.Plane();
7246 return result.setFromCoplanarPoints( this.a, this.b, this.c );
7250 barycoordFromPoint:
function ( point, optionalTarget ) {
7252 return THREE.Triangle.barycoordFromPoint( point, this.a, this.b, this.c, optionalTarget );
7256 containsPoint:
function ( point ) {
7258 return THREE.Triangle.containsPoint( point, this.a, this.b, this.c );
7262 equals:
function ( triangle ) {
7264 return triangle.a.equals( this.a ) && triangle.b.equals( this.b ) && triangle.c.equals( this.c );
7276 THREE.Channels =
function () {
7282 THREE.Channels.prototype = {
7284 constructor: THREE.Channels,
7286 set:
function ( channel ) {
7288 this.mask = 1 << channel;
7292 enable:
function ( channel ) {
7294 this.mask |= 1 << channel;
7298 toggle:
function ( channel ) {
7300 this.mask ^= 1 << channel;
7304 disable:
function ( channel ) {
7306 this.mask &= ~ ( 1 << channel );
7318 THREE.Clock =
function ( autoStart ) {
7320 this.autoStart = ( autoStart !== undefined ) ? autoStart :
true;
7324 this.elapsedTime = 0;
7326 this.running =
false;
7330 THREE.Clock.prototype = {
7332 constructor: THREE.Clock,
7334 start:
function () {
7336 this.startTime =
self.performance.now();
7338 this.oldTime = this.startTime;
7339 this.running =
true;
7345 this.getElapsedTime();
7346 this.running =
false;
7350 getElapsedTime:
function () {
7353 return this.elapsedTime;
7357 getDelta:
function () {
7361 if ( this.autoStart && ! this.running ) {
7367 if ( this.running ) {
7369 var newTime =
self.performance.now();
7371 diff = 0.001 * ( newTime - this.oldTime );
7372 this.oldTime = newTime;
7374 this.elapsedTime += diff;
7390 THREE.EventDispatcher =
function () {};
7392 THREE.EventDispatcher.prototype = {
7394 constructor: THREE.EventDispatcher,
7396 apply:
function ( object ) {
7398 object.addEventListener = THREE.EventDispatcher.prototype.addEventListener;
7399 object.hasEventListener = THREE.EventDispatcher.prototype.hasEventListener;
7400 object.removeEventListener = THREE.EventDispatcher.prototype.removeEventListener;
7401 object.dispatchEvent = THREE.EventDispatcher.prototype.dispatchEvent;
7405 addEventListener:
function ( type, listener ) {
7407 if ( this._listeners === undefined ) this._listeners = {};
7409 var listeners = this._listeners;
7411 if ( listeners[ type ] === undefined ) {
7413 listeners[ type ] = [];
7417 if ( listeners[ type ].indexOf( listener ) === - 1 ) {
7419 listeners[ type ].push( listener );
7425 hasEventListener:
function ( type, listener ) {
7427 if ( this._listeners === undefined )
return false;
7429 var listeners = this._listeners;
7431 if ( listeners[ type ] !== undefined && listeners[ type ].indexOf( listener ) !== - 1 ) {
7441 removeEventListener:
function ( type, listener ) {
7443 if ( this._listeners === undefined )
return;
7445 var listeners = this._listeners;
7446 var listenerArray = listeners[ type ];
7448 if ( listenerArray !== undefined ) {
7450 var index = listenerArray.indexOf( listener );
7452 if ( index !== - 1 ) {
7454 listenerArray.splice( index, 1 );
7462 dispatchEvent:
function ( event ) {
7464 if ( this._listeners === undefined )
return;
7466 var listeners = this._listeners;
7467 var listenerArray = listeners[
event.type ];
7469 if ( listenerArray !== undefined ) {
7471 event.target =
this;
7474 var length = listenerArray.length;
7476 for ( var i = 0; i < length; i ++ ) {
7478 array[ i ] = listenerArray[ i ];
7482 for ( var i = 0; i < length; i ++ ) {
7484 array[ i ].call(
this, event );
7502 (
function ( THREE ) {
7504 THREE.Raycaster =
function ( origin, direction, near, far ) {
7506 this.ray =
new THREE.Ray( origin, direction );
7509 this.near = near || 0;
7510 this.far = far || Infinity;
7516 Points: { threshold: 1 },
7520 Object.defineProperties( this.params, {
7523 console.warn(
'THREE.Raycaster: params.PointCloud has been renamed to params.Points.' );
7531 function descSort( a, b ) {
7533 return a.distance - b.distance;
7537 function intersectObject(
object, raycaster, intersects, recursive ) {
7539 if (
object.visible ===
false )
return;
7541 object.raycast( raycaster, intersects );
7543 if ( recursive ===
true ) {
7545 var children =
object.children;
7547 for ( var i = 0, l = children.length; i < l; i ++ ) {
7549 intersectObject( children[ i ], raycaster, intersects,
true );
7559 THREE.Raycaster.prototype = {
7561 constructor: THREE.Raycaster,
7565 set:
function ( origin, direction ) {
7569 this.ray.set( origin, direction );
7573 setFromCamera:
function ( coords, camera ) {
7575 if ( camera instanceof THREE.PerspectiveCamera ) {
7577 this.ray.origin.setFromMatrixPosition( camera.matrixWorld );
7578 this.ray.direction.set( coords.x, coords.y, 0.5 ).unproject( camera ).sub( this.ray.origin ).normalize();
7580 }
else if ( camera instanceof THREE.OrthographicCamera ) {
7582 this.ray.origin.set( coords.x, coords.y, - 1 ).unproject( camera );
7583 this.ray.direction.set( 0, 0, - 1 ).transformDirection( camera.matrixWorld );
7587 console.error(
'THREE.Raycaster: Unsupported camera type.' );
7593 intersectObject:
function ( object, recursive ) {
7595 var intersects = [];
7597 intersectObject(
object,
this, intersects, recursive );
7599 intersects.sort( descSort );
7605 intersectObjects:
function ( objects, recursive ) {
7607 var intersects = [];
7609 if ( Array.isArray( objects ) === false ) {
7611 console.warn(
'THREE.Raycaster.intersectObjects: objects is not an Array.' );
7616 for ( var i = 0, l = objects.length; i < l; i ++ ) {
7618 intersectObject( objects[ i ],
this, intersects, recursive );
7622 intersects.sort( descSort );
7642 THREE.Object3D =
function () {
7644 Object.defineProperty(
this,
'id', { value: THREE.Object3DIdCount ++ } );
7646 this.uuid = THREE.Math.generateUUID();
7649 this.type =
'Object3D';
7652 this.channels =
new THREE.Channels();
7655 this.up = THREE.Object3D.DefaultUp.clone();
7657 var position =
new THREE.Vector3();
7658 var rotation =
new THREE.Euler();
7659 var quaternion =
new THREE.Quaternion();
7660 var scale =
new THREE.Vector3( 1, 1, 1 );
7662 function onRotationChange() {
7664 quaternion.setFromEuler( rotation,
false );
7668 function onQuaternionChange() {
7670 rotation.setFromQuaternion( quaternion, undefined,
false );
7674 rotation.onChange( onRotationChange );
7675 quaternion.onChange( onQuaternionChange );
7677 Object.defineProperties(
this, {
7695 value:
new THREE.Matrix4()
7698 value:
new THREE.Matrix3()
7702 this.rotationAutoUpdate =
true;
7704 this.matrix =
new THREE.Matrix4();
7705 this.matrixWorld =
new THREE.Matrix4();
7707 this.matrixAutoUpdate = THREE.Object3D.DefaultMatrixAutoUpdate;
7708 this.matrixWorldNeedsUpdate =
false;
7710 this.visible =
true;
7712 this.castShadow =
false;
7713 this.receiveShadow =
false;
7715 this.frustumCulled =
true;
7716 this.renderOrder = 0;
7722 THREE.Object3D.DefaultUp =
new THREE.Vector3( 0, 1, 0 );
7723 THREE.Object3D.DefaultMatrixAutoUpdate =
true;
7725 THREE.Object3D.prototype = {
7727 constructor: THREE.Object3D,
7731 console.warn(
'THREE.Object3D: .eulerOrder is now .rotation.order.' );
7733 return this.rotation.order;
7737 set eulerOrder ( value ) {
7739 console.warn(
'THREE.Object3D: .eulerOrder is now .rotation.order.' );
7741 this.rotation.order = value;
7745 get useQuaternion () {
7747 console.warn(
'THREE.Object3D: .useQuaternion has been removed. The library now uses quaternions by default.' );
7751 set useQuaternion ( value ) {
7753 console.warn(
'THREE.Object3D: .useQuaternion has been removed. The library now uses quaternions by default.' );
7757 set renderDepth ( value ) {
7759 console.warn(
'THREE.Object3D: .renderDepth has been removed. Use .renderOrder, instead.' );
7765 applyMatrix:
function ( matrix ) {
7767 this.matrix.multiplyMatrices( matrix, this.matrix );
7769 this.matrix.decompose( this.position, this.quaternion, this.scale );
7773 setRotationFromAxisAngle:
function ( axis, angle ) {
7777 this.quaternion.setFromAxisAngle( axis, angle );
7781 setRotationFromEuler:
function ( euler ) {
7783 this.quaternion.setFromEuler( euler,
true );
7787 setRotationFromMatrix:
function ( m ) {
7791 this.quaternion.setFromRotationMatrix( m );
7795 setRotationFromQuaternion:
function ( q ) {
7799 this.quaternion.copy( q );
7803 rotateOnAxis:
function () {
7808 var q1 =
new THREE.Quaternion();
7810 return function ( axis, angle ) {
7812 q1.setFromAxisAngle( axis, angle );
7814 this.quaternion.multiply( q1 );
7822 rotateX:
function () {
7824 var v1 =
new THREE.Vector3( 1, 0, 0 );
7826 return function ( angle ) {
7828 return this.rotateOnAxis( v1, angle );
7834 rotateY:
function () {
7836 var v1 =
new THREE.Vector3( 0, 1, 0 );
7838 return function ( angle ) {
7840 return this.rotateOnAxis( v1, angle );
7846 rotateZ:
function () {
7848 var v1 =
new THREE.Vector3( 0, 0, 1 );
7850 return function ( angle ) {
7852 return this.rotateOnAxis( v1, angle );
7858 translateOnAxis:
function () {
7863 var v1 =
new THREE.Vector3();
7865 return function ( axis, distance ) {
7867 v1.copy( axis ).applyQuaternion( this.quaternion );
7869 this.position.add( v1.multiplyScalar( distance ) );
7877 translate:
function ( distance, axis ) {
7879 console.warn(
'THREE.Object3D: .translate() has been removed. Use .translateOnAxis( axis, distance ) instead.' );
7880 return this.translateOnAxis( axis, distance );
7884 translateX:
function () {
7886 var v1 =
new THREE.Vector3( 1, 0, 0 );
7888 return function ( distance ) {
7890 return this.translateOnAxis( v1, distance );
7896 translateY:
function () {
7898 var v1 =
new THREE.Vector3( 0, 1, 0 );
7900 return function ( distance ) {
7902 return this.translateOnAxis( v1, distance );
7908 translateZ:
function () {
7910 var v1 =
new THREE.Vector3( 0, 0, 1 );
7912 return function ( distance ) {
7914 return this.translateOnAxis( v1, distance );
7920 localToWorld:
function ( vector ) {
7922 return vector.applyMatrix4( this.matrixWorld );
7926 worldToLocal:
function () {
7928 var m1 =
new THREE.Matrix4();
7930 return function ( vector ) {
7932 return vector.applyMatrix4( m1.getInverse(
this.matrixWorld ) );
7938 lookAt:
function () {
7942 var m1 =
new THREE.Matrix4();
7944 return function ( vector ) {
7946 m1.lookAt( vector, this.position, this.up );
7948 this.quaternion.setFromRotationMatrix( m1 );
7954 add:
function (
object ) {
7956 if ( arguments.length > 1 ) {
7958 for ( var i = 0; i < arguments.length; i ++ ) {
7960 this.add( arguments[ i ] );
7968 if (
object ===
this ) {
7970 console.error(
"THREE.Object3D.add: object can't be added as a child of itself.",
object );
7975 if (
object instanceof THREE.Object3D ) {
7977 if (
object.parent !== null ) {
7979 object.parent.remove(
object );
7983 object.parent =
this;
7984 object.dispatchEvent( { type:
'added' } );
7986 this.children.push(
object );
7990 console.error(
"THREE.Object3D.add: object not an instance of THREE.Object3D.",
object );
7998 remove:
function ( object ) {
8000 if ( arguments.length > 1 ) {
8002 for ( var i = 0; i < arguments.length; i ++ ) {
8004 this.
remove( arguments[ i ] );
8010 var index = this.children.indexOf(
object );
8012 if ( index !== - 1 ) {
8014 object.parent = null;
8016 object.dispatchEvent( { type:
'removed' } );
8018 this.children.splice( index, 1 );
8024 getChildByName:
function ( name ) {
8026 console.warn(
'THREE.Object3D: .getChildByName() has been renamed to .getObjectByName().' );
8027 return this.getObjectByName( name );
8031 getObjectById:
function ( id ) {
8033 return this.getObjectByProperty(
'id',
id );
8037 getObjectByName:
function ( name ) {
8039 return this.getObjectByProperty(
'name', name );
8043 getObjectByProperty:
function ( name, value ) {
8045 if (
this[ name ] === value )
return this;
8047 for ( var i = 0, l = this.children.length; i < l; i ++ ) {
8049 var child = this.children[ i ];
8050 var
object = child.getObjectByProperty( name, value );
8052 if (
object !== undefined ) {
8064 getWorldPosition:
function ( optionalTarget ) {
8066 var result = optionalTarget ||
new THREE.Vector3();
8068 this.updateMatrixWorld(
true );
8070 return result.setFromMatrixPosition( this.matrixWorld );
8074 getWorldQuaternion:
function () {
8076 var position =
new THREE.Vector3();
8077 var scale =
new THREE.Vector3();
8079 return function ( optionalTarget ) {
8081 var result = optionalTarget ||
new THREE.Quaternion();
8083 this.updateMatrixWorld(
true );
8085 this.matrixWorld.decompose( position, result, scale );
8093 getWorldRotation:
function () {
8095 var quaternion =
new THREE.Quaternion();
8097 return function ( optionalTarget ) {
8099 var result = optionalTarget ||
new THREE.Euler();
8101 this.getWorldQuaternion( quaternion );
8103 return result.setFromQuaternion( quaternion, this.rotation.order,
false );
8109 getWorldScale:
function () {
8111 var position =
new THREE.Vector3();
8112 var quaternion =
new THREE.Quaternion();
8114 return function ( optionalTarget ) {
8116 var result = optionalTarget ||
new THREE.Vector3();
8118 this.updateMatrixWorld(
true );
8120 this.matrixWorld.decompose( position, quaternion, result );
8128 getWorldDirection:
function () {
8130 var quaternion =
new THREE.Quaternion();
8132 return function ( optionalTarget ) {
8134 var result = optionalTarget ||
new THREE.Vector3();
8136 this.getWorldQuaternion( quaternion );
8138 return result.set( 0, 0, 1 ).applyQuaternion( quaternion );
8144 raycast:
function () {},
8146 traverse:
function ( callback ) {
8150 var children = this.children;
8152 for ( var i = 0, l = children.length; i < l; i ++ ) {
8154 children[ i ].traverse( callback );
8160 traverseVisible:
function ( callback ) {
8162 if ( this.visible ===
false )
return;
8166 var children = this.children;
8168 for ( var i = 0, l = children.length; i < l; i ++ ) {
8170 children[ i ].traverseVisible( callback );
8176 traverseAncestors:
function ( callback ) {
8178 var parent = this.parent;
8180 if ( parent !== null ) {
8184 parent.traverseAncestors( callback );
8190 updateMatrix:
function () {
8192 this.matrix.compose( this.position, this.quaternion, this.scale );
8194 this.matrixWorldNeedsUpdate =
true;
8198 updateMatrixWorld:
function ( force ) {
8200 if ( this.matrixAutoUpdate ===
true ) this.updateMatrix();
8202 if ( this.matrixWorldNeedsUpdate ===
true || force ===
true ) {
8204 if ( this.parent === null ) {
8206 this.matrixWorld.copy( this.matrix );
8210 this.matrixWorld.multiplyMatrices( this.parent.matrixWorld,
this.matrix );
8214 this.matrixWorldNeedsUpdate =
false;
8222 for ( var i = 0, l = this.children.length; i < l; i ++ ) {
8224 this.children[ i ].updateMatrixWorld( force );
8230 toJSON:
function ( meta ) {
8232 var isRootObject = ( meta === undefined );
8239 if ( isRootObject ) {
8252 generator:
'Object3D.toJSON'
8261 object.uuid = this.uuid;
8262 object.type = this.type;
8264 if ( this.name !==
'' )
object.name = this.name;
8265 if ( JSON.stringify(
this.userData ) !==
'{}' )
object.userData = this.userData;
8266 if ( this.castShadow ===
true )
object.castShadow =
true;
8267 if ( this.receiveShadow ===
true )
object.receiveShadow =
true;
8268 if ( this.visible ===
false )
object.visible =
false;
8270 object.matrix = this.matrix.toArray();
8274 if ( this.geometry !== undefined ) {
8276 if ( meta.geometries[
this.geometry.uuid ] === undefined ) {
8278 meta.geometries[ this.geometry.uuid ] = this.geometry.toJSON( meta );
8282 object.geometry = this.geometry.uuid;
8286 if ( this.material !== undefined ) {
8288 if ( meta.materials[
this.material.uuid ] === undefined ) {
8290 meta.materials[ this.material.uuid ] = this.material.toJSON( meta );
8294 object.material = this.material.uuid;
8300 if ( this.children.length > 0 ) {
8302 object.children = [];
8304 for ( var i = 0; i < this.children.length; i ++ ) {
8306 object.children.push( this.children[ i ].toJSON( meta ).
object );
8312 if ( isRootObject ) {
8314 var geometries = extractFromCache( meta.geometries );
8315 var materials = extractFromCache( meta.materials );
8316 var textures = extractFromCache( meta.textures );
8317 var images = extractFromCache( meta.images );
8319 if ( geometries.length > 0 ) output.geometries = geometries;
8320 if ( materials.length > 0 ) output.materials = materials;
8321 if ( textures.length > 0 ) output.textures = textures;
8322 if ( images.length > 0 ) output.images = images;
8326 output.object = object;
8333 function extractFromCache ( cache ) {
8336 for ( var key in cache ) {
8338 var data = cache[ key ];
8339 delete data.metadata;
8340 values.push( data );
8349 clone:
function ( recursive ) {
8351 return new this.constructor().copy(
this, recursive );
8355 copy:
function ( source, recursive ) {
8357 if ( recursive === undefined ) recursive =
true;
8359 this.name = source.name;
8361 this.up.copy( source.up );
8363 this.position.copy( source.position );
8364 this.quaternion.copy( source.quaternion );
8365 this.scale.copy( source.scale );
8367 this.rotationAutoUpdate = source.rotationAutoUpdate;
8369 this.matrix.copy( source.matrix );
8370 this.matrixWorld.copy( source.matrixWorld );
8372 this.matrixAutoUpdate = source.matrixAutoUpdate;
8373 this.matrixWorldNeedsUpdate = source.matrixWorldNeedsUpdate;
8375 this.visible = source.visible;
8377 this.castShadow = source.castShadow;
8378 this.receiveShadow = source.receiveShadow;
8380 this.frustumCulled = source.frustumCulled;
8381 this.renderOrder = source.renderOrder;
8383 this.userData = JSON.parse( JSON.stringify( source.userData ) );
8385 if ( recursive ===
true ) {
8387 for ( var i = 0; i < source.children.length; i ++ ) {
8389 var child = source.children[ i ];
8390 this.add( child.clone() );
8402 THREE.EventDispatcher.prototype.apply( THREE.Object3D.prototype );
8404 THREE.Object3DIdCount = 0;
8413 THREE.Face3 =
function ( a, b, c, normal, color, materialIndex ) {
8419 this.normal = normal instanceof THREE.Vector3 ? normal :
new THREE.Vector3();
8420 this.vertexNormals = Array.isArray( normal ) ? normal : [];
8422 this.color = color instanceof THREE.Color ? color :
new THREE.Color();
8423 this.vertexColors = Array.isArray( color ) ? color : [];
8425 this.materialIndex = materialIndex !== undefined ? materialIndex : 0;
8429 THREE.Face3.prototype = {
8431 constructor: THREE.Face3,
8433 clone:
function () {
8435 return new this.constructor().copy(
this );
8439 copy:
function ( source ) {
8445 this.normal.copy( source.normal );
8446 this.color.copy( source.color );
8448 this.materialIndex = source.materialIndex;
8450 for ( var i = 0, il = source.vertexNormals.length; i < il; i ++ ) {
8452 this.vertexNormals[ i ] = source.vertexNormals[ i ].clone();
8456 for ( var i = 0, il = source.vertexColors.length; i < il; i ++ ) {
8458 this.vertexColors[ i ] = source.vertexColors[ i ].clone();
8474 THREE.Face4 =
function ( a, b, c, d, normal, color, materialIndex ) {
8476 console.warn(
'THREE.Face4 has been removed. A THREE.Face3 will be created instead.' );
8477 return new THREE.Face3( a, b, c, normal, color, materialIndex );
8487 THREE.BufferAttribute =
function ( array, itemSize ) {
8489 this.uuid = THREE.Math.generateUUID();
8492 this.itemSize = itemSize;
8494 this.dynamic =
false;
8495 this.updateRange = { offset: 0, count: - 1 };
8501 THREE.BufferAttribute.prototype = {
8503 constructor: THREE.BufferAttribute,
8507 console.warn(
'THREE.BufferAttribute: .length has been deprecated. Please use .count.' );
8508 return this.array.length;
8514 return this.array.length / this.itemSize;
8518 set needsUpdate( value ) {
8520 if ( value ===
true ) this.version ++;
8524 setDynamic:
function ( value ) {
8526 this.dynamic = value;
8532 copy:
function ( source ) {
8534 this.array =
new source.array.constructor( source.array );
8535 this.itemSize = source.itemSize;
8537 this.dynamic = source.dynamic;
8543 copyAt:
function ( index1, attribute, index2 ) {
8545 index1 *= this.itemSize;
8546 index2 *= attribute.itemSize;
8548 for ( var i = 0, l = this.itemSize; i < l; i ++ ) {
8550 this.array[ index1 + i ] = attribute.array[ index2 + i ];
8558 copyArray:
function ( array ) {
8560 this.array.set( array );
8566 copyColorsArray:
function ( colors ) {
8568 var array = this.array, offset = 0;
8570 for ( var i = 0, l = colors.length; i < l; i ++ ) {
8572 var color = colors[ i ];
8574 if ( color === undefined ) {
8576 console.warn(
'THREE.BufferAttribute.copyColorsArray(): color is undefined', i );
8577 color =
new THREE.Color();
8581 array[ offset ++ ] = color.r;
8582 array[ offset ++ ] = color.g;
8583 array[ offset ++ ] = color.b;
8591 copyIndicesArray:
function ( indices ) {
8593 var array = this.array, offset = 0;
8595 for ( var i = 0, l = indices.length; i < l; i ++ ) {
8597 var index = indices[ i ];
8599 array[ offset ++ ] = index.a;
8600 array[ offset ++ ] = index.b;
8601 array[ offset ++ ] = index.c;
8609 copyVector2sArray:
function ( vectors ) {
8611 var array = this.array, offset = 0;
8613 for ( var i = 0, l = vectors.length; i < l; i ++ ) {
8615 var vector = vectors[ i ];
8617 if ( vector === undefined ) {
8619 console.warn(
'THREE.BufferAttribute.copyVector2sArray(): vector is undefined', i );
8620 vector =
new THREE.Vector2();
8624 array[ offset ++ ] = vector.x;
8625 array[ offset ++ ] = vector.y;
8633 copyVector3sArray:
function ( vectors ) {
8635 var array = this.array, offset = 0;
8637 for ( var i = 0, l = vectors.length; i < l; i ++ ) {
8639 var vector = vectors[ i ];
8641 if ( vector === undefined ) {
8643 console.warn(
'THREE.BufferAttribute.copyVector3sArray(): vector is undefined', i );
8644 vector =
new THREE.Vector3();
8648 array[ offset ++ ] = vector.x;
8649 array[ offset ++ ] = vector.y;
8650 array[ offset ++ ] = vector.z;
8658 copyVector4sArray:
function ( vectors ) {
8660 var array = this.array, offset = 0;
8662 for ( var i = 0, l = vectors.length; i < l; i ++ ) {
8664 var vector = vectors[ i ];
8666 if ( vector === undefined ) {
8668 console.warn(
'THREE.BufferAttribute.copyVector4sArray(): vector is undefined', i );
8669 vector =
new THREE.Vector4();
8673 array[ offset ++ ] = vector.x;
8674 array[ offset ++ ] = vector.y;
8675 array[ offset ++ ] = vector.z;
8676 array[ offset ++ ] = vector.w;
8684 set:
function ( value, offset ) {
8686 if ( offset === undefined ) offset = 0;
8688 this.array.set( value, offset );
8694 getX:
function ( index ) {
8696 return this.array[ index * this.itemSize ];
8700 setX:
function ( index, x ) {
8702 this.array[ index * this.itemSize ] = x;
8708 getY:
function ( index ) {
8710 return this.array[ index * this.itemSize + 1 ];
8714 setY:
function ( index, y ) {
8716 this.array[ index * this.itemSize + 1 ] = y;
8722 getZ:
function ( index ) {
8724 return this.array[ index * this.itemSize + 2 ];
8728 setZ:
function ( index, z ) {
8730 this.array[ index * this.itemSize + 2 ] = z;
8736 getW:
function ( index ) {
8738 return this.array[ index * this.itemSize + 3 ];
8742 setW:
function ( index, w ) {
8744 this.array[ index * this.itemSize + 3 ] = w;
8750 setXY:
function ( index, x, y ) {
8752 index *= this.itemSize;
8754 this.array[ index + 0 ] = x;
8755 this.array[ index + 1 ] = y;
8761 setXYZ:
function ( index, x, y, z ) {
8763 index *= this.itemSize;
8765 this.array[ index + 0 ] = x;
8766 this.array[ index + 1 ] = y;
8767 this.array[ index + 2 ] = z;
8773 setXYZW:
function ( index, x, y, z, w ) {
8775 index *= this.itemSize;
8777 this.array[ index + 0 ] = x;
8778 this.array[ index + 1 ] = y;
8779 this.array[ index + 2 ] = z;
8780 this.array[ index + 3 ] = w;
8786 clone:
function () {
8788 return new this.constructor().copy(
this );
8796 THREE.Int8Attribute =
function ( array, itemSize ) {
8798 return new THREE.BufferAttribute(
new Int8Array( array ), itemSize );
8802 THREE.Uint8Attribute =
function ( array, itemSize ) {
8804 return new THREE.BufferAttribute(
new Uint8Array( array ), itemSize );
8808 THREE.Uint8ClampedAttribute =
function ( array, itemSize ) {
8810 return new THREE.BufferAttribute(
new Uint8ClampedArray( array ), itemSize );
8814 THREE.Int16Attribute =
function ( array, itemSize ) {
8816 return new THREE.BufferAttribute(
new Int16Array( array ), itemSize );
8820 THREE.Uint16Attribute =
function ( array, itemSize ) {
8822 return new THREE.BufferAttribute(
new Uint16Array( array ), itemSize );
8826 THREE.Int32Attribute =
function ( array, itemSize ) {
8828 return new THREE.BufferAttribute(
new Int32Array( array ), itemSize );
8832 THREE.Uint32Attribute =
function ( array, itemSize ) {
8834 return new THREE.BufferAttribute(
new Uint32Array( array ), itemSize );
8838 THREE.Float32Attribute =
function ( array, itemSize ) {
8840 return new THREE.BufferAttribute(
new Float32Array( array ), itemSize );
8844 THREE.Float64Attribute =
function ( array, itemSize ) {
8846 return new THREE.BufferAttribute(
new Float64Array( array ), itemSize );
8853 THREE.DynamicBufferAttribute =
function ( array, itemSize ) {
8855 console.warn(
'THREE.DynamicBufferAttribute has been removed. Use new THREE.BufferAttribute().setDynamic( true ) instead.' );
8856 return new THREE.BufferAttribute( array, itemSize ).setDynamic(
true );
8866 THREE.InstancedBufferAttribute =
function ( array, itemSize, meshPerAttribute ) {
8868 THREE.BufferAttribute.call(
this, array, itemSize );
8870 this.meshPerAttribute = meshPerAttribute || 1;
8874 THREE.InstancedBufferAttribute.prototype = Object.create( THREE.BufferAttribute.prototype );
8875 THREE.InstancedBufferAttribute.prototype.constructor = THREE.InstancedBufferAttribute;
8877 THREE.InstancedBufferAttribute.prototype.copy =
function ( source ) {
8879 THREE.BufferAttribute.prototype.copy.call(
this, source );
8881 this.meshPerAttribute = source.meshPerAttribute;
8893 THREE.InterleavedBuffer =
function ( array, stride ) {
8895 this.uuid = THREE.Math.generateUUID();
8898 this.stride = stride;
8900 this.dynamic =
false;
8901 this.updateRange = { offset: 0, count: - 1 };
8907 THREE.InterleavedBuffer.prototype = {
8909 constructor: THREE.InterleavedBuffer,
8913 return this.array.length;
8919 return this.array.length / this.stride;
8923 set needsUpdate( value ) {
8925 if ( value ===
true ) this.version ++;
8929 setDynamic:
function ( value ) {
8931 this.dynamic = value;
8937 copy:
function ( source ) {
8939 this.array =
new source.array.constructor( source.array );
8940 this.stride = source.stride;
8941 this.dynamic = source.dynamic;
8945 copyAt:
function ( index1, attribute, index2 ) {
8947 index1 *= this.stride;
8948 index2 *= attribute.stride;
8950 for ( var i = 0, l = this.stride; i < l; i ++ ) {
8952 this.array[ index1 + i ] = attribute.array[ index2 + i ];
8960 set:
function ( value, offset ) {
8962 if ( offset === undefined ) offset = 0;
8964 this.array.set( value, offset );
8970 clone:
function () {
8972 return new this.constructor().copy(
this );
8984 THREE.InstancedInterleavedBuffer =
function ( array, stride, meshPerAttribute ) {
8986 THREE.InterleavedBuffer.call(
this, array, stride );
8988 this.meshPerAttribute = meshPerAttribute || 1;
8992 THREE.InstancedInterleavedBuffer.prototype = Object.create( THREE.InterleavedBuffer.prototype );
8993 THREE.InstancedInterleavedBuffer.prototype.constructor = THREE.InstancedInterleavedBuffer;
8995 THREE.InstancedInterleavedBuffer.prototype.copy =
function ( source ) {
8997 THREE.InterleavedBuffer.prototype.copy.call(
this, source );
8999 this.meshPerAttribute = source.meshPerAttribute;
9011 THREE.InterleavedBufferAttribute =
function ( interleavedBuffer, itemSize, offset ) {
9013 this.uuid = THREE.Math.generateUUID();
9015 this.data = interleavedBuffer;
9016 this.itemSize = itemSize;
9017 this.offset = offset;
9022 THREE.InterleavedBufferAttribute.prototype = {
9024 constructor: THREE.InterleavedBufferAttribute,
9028 console.warn(
'THREE.BufferAttribute: .length has been deprecated. Please use .count.' );
9029 return this.array.length;
9035 return this.data.array.length / this.data.stride;
9039 setX:
function ( index, x ) {
9041 this.data.array[ index * this.data.stride + this.offset ] = x;
9047 setY:
function ( index, y ) {
9049 this.data.array[ index * this.data.stride + this.offset + 1 ] = y;
9055 setZ:
function ( index, z ) {
9057 this.data.array[ index * this.data.stride + this.offset + 2 ] = z;
9063 setW:
function ( index, w ) {
9065 this.data.array[ index * this.data.stride + this.offset + 3 ] = w;
9071 getX:
function ( index ) {
9073 return this.data.array[ index * this.data.stride + this.offset ];
9077 getY:
function ( index ) {
9079 return this.data.array[ index * this.data.stride + this.offset + 1 ];
9083 getZ:
function ( index ) {
9085 return this.data.array[ index * this.data.stride + this.offset + 2 ];
9089 getW:
function ( index ) {
9091 return this.data.array[ index * this.data.stride + this.offset + 3 ];
9095 setXY:
function ( index, x, y ) {
9097 index = index * this.data.stride + this.offset;
9099 this.data.array[ index + 0 ] = x;
9100 this.data.array[ index + 1 ] = y;
9106 setXYZ:
function ( index, x, y, z ) {
9108 index = index * this.data.stride + this.offset;
9110 this.data.array[ index + 0 ] = x;
9111 this.data.array[ index + 1 ] = y;
9112 this.data.array[ index + 2 ] = z;
9118 setXYZW:
function ( index, x, y, z, w ) {
9120 index = index * this.data.stride + this.offset;
9122 this.data.array[ index + 0 ] = x;
9123 this.data.array[ index + 1 ] = y;
9124 this.data.array[ index + 2 ] = z;
9125 this.data.array[ index + 3 ] = w;
9144 THREE.Geometry =
function () {
9146 Object.defineProperty(
this,
'id', { value: THREE.GeometryIdCount ++ } );
9148 this.uuid = THREE.Math.generateUUID();
9151 this.type =
'Geometry';
9156 this.faceVertexUvs = [ [] ];
9158 this.morphTargets = [];
9159 this.morphNormals = [];
9161 this.skinWeights = [];
9162 this.skinIndices = [];
9164 this.lineDistances = [];
9166 this.boundingBox = null;
9167 this.boundingSphere = null;
9171 this.verticesNeedUpdate =
false;
9172 this.elementsNeedUpdate =
false;
9173 this.uvsNeedUpdate =
false;
9174 this.normalsNeedUpdate =
false;
9175 this.colorsNeedUpdate =
false;
9176 this.lineDistancesNeedUpdate =
false;
9177 this.groupsNeedUpdate =
false;
9181 THREE.Geometry.prototype = {
9183 constructor: THREE.Geometry,
9185 applyMatrix:
function ( matrix ) {
9187 var normalMatrix =
new THREE.Matrix3().getNormalMatrix( matrix );
9189 for ( var i = 0, il = this.vertices.length; i < il; i ++ ) {
9191 var vertex = this.vertices[ i ];
9192 vertex.applyMatrix4( matrix );
9196 for ( var i = 0, il = this.faces.length; i < il; i ++ ) {
9198 var face = this.faces[ i ];
9199 face.normal.applyMatrix3( normalMatrix ).normalize();
9201 for ( var j = 0, jl = face.vertexNormals.length; j < jl; j ++ ) {
9203 face.vertexNormals[ j ].applyMatrix3( normalMatrix ).normalize();
9209 if ( this.boundingBox !== null ) {
9211 this.computeBoundingBox();
9215 if ( this.boundingSphere !== null ) {
9217 this.computeBoundingSphere();
9221 this.verticesNeedUpdate =
true;
9222 this.normalsNeedUpdate =
true;
9226 rotateX:
function () {
9232 return function rotateX( angle ) {
9234 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
9236 m1.makeRotationX( angle );
9238 this.applyMatrix( m1 );
9246 rotateY:
function () {
9252 return function rotateY( angle ) {
9254 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
9256 m1.makeRotationY( angle );
9258 this.applyMatrix( m1 );
9266 rotateZ:
function () {
9272 return function rotateZ( angle ) {
9274 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
9276 m1.makeRotationZ( angle );
9278 this.applyMatrix( m1 );
9286 translate:
function () {
9292 return function translate( x, y, z ) {
9294 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
9296 m1.makeTranslation( x, y, z );
9298 this.applyMatrix( m1 );
9306 scale:
function () {
9312 return function scale( x, y, z ) {
9314 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
9316 m1.makeScale( x, y, z );
9318 this.applyMatrix( m1 );
9326 lookAt:
function () {
9330 return function lookAt( vector ) {
9332 if ( obj === undefined ) obj =
new THREE.Object3D();
9334 obj.lookAt( vector );
9338 this.applyMatrix( obj.matrix );
9344 fromBufferGeometry:
function ( geometry ) {
9348 var indices = geometry.index !== null ? geometry.index.array : undefined;
9349 var attributes = geometry.attributes;
9351 var vertices = attributes.position.array;
9352 var normals = attributes.normal !== undefined ? attributes.normal.array : undefined;
9353 var colors = attributes.color !== undefined ? attributes.color.array : undefined;
9354 var uvs = attributes.uv !== undefined ? attributes.uv.array : undefined;
9355 var uvs2 = attributes.uv2 !== undefined ? attributes.uv2.array : undefined;
9357 if ( uvs2 !== undefined ) this.faceVertexUvs[ 1 ] = [];
9359 var tempNormals = [];
9363 for ( var i = 0, j = 0, k = 0; i < vertices.length; i += 3, j += 2, k += 4 ) {
9365 scope.vertices.push(
new THREE.Vector3( vertices[ i ], vertices[ i + 1 ], vertices[ i + 2 ] ) );
9367 if ( normals !== undefined ) {
9369 tempNormals.push(
new THREE.Vector3( normals[ i ], normals[ i + 1 ], normals[ i + 2 ] ) );
9373 if ( colors !== undefined ) {
9375 scope.colors.push(
new THREE.Color( colors[ i ], colors[ i + 1 ], colors[ i + 2 ] ) );
9379 if ( uvs !== undefined ) {
9381 tempUVs.push(
new THREE.Vector2( uvs[ j ], uvs[ j + 1 ] ) );
9385 if ( uvs2 !== undefined ) {
9387 tempUVs2.push(
new THREE.Vector2( uvs2[ j ], uvs2[ j + 1 ] ) );
9393 function addFace( a, b, c ) {
9395 var vertexNormals = normals !== undefined ? [ tempNormals[ a ].clone(), tempNormals[ b ].clone(), tempNormals[ c ].clone() ] : [];
9396 var vertexColors = colors !== undefined ? [ scope.colors[ a ].clone(), scope.colors[ b ].clone(), scope.colors[ c ].clone() ] : [];
9398 var face =
new THREE.Face3( a, b, c, vertexNormals, vertexColors );
9400 scope.faces.push( face );
9402 if ( uvs !== undefined ) {
9404 scope.faceVertexUvs[ 0 ].push( [ tempUVs[ a ].clone(), tempUVs[ b ].clone(), tempUVs[ c ].clone() ] );
9408 if ( uvs2 !== undefined ) {
9410 scope.faceVertexUvs[ 1 ].push( [ tempUVs2[ a ].clone(), tempUVs2[ b ].clone(), tempUVs2[ c ].clone() ] );
9416 if ( indices !== undefined ) {
9418 var groups = geometry.groups;
9420 if ( groups.length > 0 ) {
9422 for ( var i = 0; i < groups.length; i ++ ) {
9424 var group = groups[ i ];
9426 var start = group.start;
9427 var count = group.count;
9429 for ( var j = start, jl = start + count; j < jl; j += 3 ) {
9431 addFace( indices[ j ], indices[ j + 1 ], indices[ j + 2 ] );
9439 for ( var i = 0; i < indices.length; i += 3 ) {
9441 addFace( indices[ i ], indices[ i + 1 ], indices[ i + 2 ] );
9449 for ( var i = 0; i < vertices.length / 3; i += 3 ) {
9451 addFace( i, i + 1, i + 2 );
9457 this.computeFaceNormals();
9459 if ( geometry.boundingBox !== null ) {
9461 this.boundingBox = geometry.boundingBox.clone();
9465 if ( geometry.boundingSphere !== null ) {
9467 this.boundingSphere = geometry.boundingSphere.clone();
9475 center:
function () {
9477 this.computeBoundingBox();
9479 var offset = this.boundingBox.center().negate();
9481 this.translate( offset.x, offset.y, offset.z );
9487 normalize:
function () {
9489 this.computeBoundingSphere();
9491 var center = this.boundingSphere.center;
9492 var radius = this.boundingSphere.radius;
9494 var s = radius === 0 ? 1 : 1.0 / radius;
9496 var matrix =
new THREE.Matrix4();
9498 s, 0, 0, - s * center.x,
9499 0, s, 0, - s * center.y,
9500 0, 0, s, - s * center.z,
9504 this.applyMatrix( matrix );
9510 computeFaceNormals:
function () {
9512 var cb =
new THREE.Vector3(), ab =
new THREE.Vector3();
9514 for ( var f = 0, fl = this.faces.length; f < fl; f ++ ) {
9516 var face = this.faces[ f ];
9518 var vA = this.vertices[ face.a ];
9519 var vB = this.vertices[ face.b ];
9520 var vC = this.vertices[ face.c ];
9522 cb.subVectors( vC, vB );
9523 ab.subVectors( vA, vB );
9528 face.normal.copy( cb );
9534 computeVertexNormals:
function ( areaWeighted ) {
9536 var v, vl, f, fl, face, vertices;
9538 vertices =
new Array( this.vertices.length );
9540 for ( v = 0, vl = this.vertices.length; v < vl; v ++ ) {
9542 vertices[ v ] =
new THREE.Vector3();
9546 if ( areaWeighted ) {
9552 var cb =
new THREE.Vector3(), ab =
new THREE.Vector3();
9554 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9556 face = this.faces[ f ];
9558 vA = this.vertices[ face.a ];
9559 vB = this.vertices[ face.b ];
9560 vC = this.vertices[ face.c ];
9562 cb.subVectors( vC, vB );
9563 ab.subVectors( vA, vB );
9566 vertices[ face.a ].add( cb );
9567 vertices[ face.b ].add( cb );
9568 vertices[ face.c ].add( cb );
9574 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9576 face = this.faces[ f ];
9578 vertices[ face.a ].add( face.normal );
9579 vertices[ face.b ].add( face.normal );
9580 vertices[ face.c ].add( face.normal );
9586 for ( v = 0, vl = this.vertices.length; v < vl; v ++ ) {
9588 vertices[ v ].normalize();
9592 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9594 face = this.faces[ f ];
9596 var vertexNormals = face.vertexNormals;
9598 if ( vertexNormals.length === 3 ) {
9600 vertexNormals[ 0 ].copy( vertices[ face.a ] );
9601 vertexNormals[ 1 ].copy( vertices[ face.b ] );
9602 vertexNormals[ 2 ].copy( vertices[ face.c ] );
9606 vertexNormals[ 0 ] = vertices[ face.a ].clone();
9607 vertexNormals[ 1 ] = vertices[ face.b ].clone();
9608 vertexNormals[ 2 ] = vertices[ face.c ].clone();
9616 computeMorphNormals:
function () {
9618 var i, il, f, fl, face;
9624 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9626 face = this.faces[ f ];
9628 if ( ! face.__originalFaceNormal ) {
9630 face.__originalFaceNormal = face.normal.clone();
9634 face.__originalFaceNormal.copy( face.normal );
9638 if ( ! face.__originalVertexNormals ) face.__originalVertexNormals = [];
9640 for ( i = 0, il = face.vertexNormals.length; i < il; i ++ ) {
9642 if ( ! face.__originalVertexNormals[ i ] ) {
9644 face.__originalVertexNormals[ i ] = face.vertexNormals[ i ].clone();
9648 face.__originalVertexNormals[ i ].copy( face.vertexNormals[ i ] );
9658 var tmpGeo =
new THREE.Geometry();
9659 tmpGeo.faces = this.faces;
9661 for ( i = 0, il = this.morphTargets.length; i < il; i ++ ) {
9665 if ( ! this.morphNormals[ i ] ) {
9667 this.morphNormals[ i ] = {};
9668 this.morphNormals[ i ].faceNormals = [];
9669 this.morphNormals[ i ].vertexNormals = [];
9671 var dstNormalsFace = this.morphNormals[ i ].faceNormals;
9672 var dstNormalsVertex = this.morphNormals[ i ].vertexNormals;
9674 var faceNormal, vertexNormals;
9676 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9678 faceNormal =
new THREE.Vector3();
9679 vertexNormals = { a:
new THREE.Vector3(), b:
new THREE.Vector3(), c:
new THREE.Vector3() };
9681 dstNormalsFace.push( faceNormal );
9682 dstNormalsVertex.push( vertexNormals );
9688 var morphNormals = this.morphNormals[ i ];
9692 tmpGeo.vertices = this.morphTargets[ i ].vertices;
9696 tmpGeo.computeFaceNormals();
9697 tmpGeo.computeVertexNormals();
9701 var faceNormal, vertexNormals;
9703 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9705 face = this.faces[ f ];
9707 faceNormal = morphNormals.faceNormals[ f ];
9708 vertexNormals = morphNormals.vertexNormals[ f ];
9710 faceNormal.copy( face.normal );
9712 vertexNormals.a.copy( face.vertexNormals[ 0 ] );
9713 vertexNormals.b.copy( face.vertexNormals[ 1 ] );
9714 vertexNormals.c.copy( face.vertexNormals[ 2 ] );
9722 for ( f = 0, fl = this.faces.length; f < fl; f ++ ) {
9724 face = this.faces[ f ];
9726 face.normal = face.__originalFaceNormal;
9727 face.vertexNormals = face.__originalVertexNormals;
9733 computeTangents:
function () {
9735 console.warn(
'THREE.Geometry: .computeTangents() has been removed.' );
9739 computeLineDistances:
function () {
9742 var vertices = this.vertices;
9744 for ( var i = 0, il = vertices.length; i < il; i ++ ) {
9748 d += vertices[ i ].distanceTo( vertices[ i - 1 ] );
9752 this.lineDistances[ i ] = d;
9758 computeBoundingBox:
function () {
9760 if ( this.boundingBox === null ) {
9762 this.boundingBox =
new THREE.Box3();
9766 this.boundingBox.setFromPoints( this.vertices );
9770 computeBoundingSphere:
function () {
9772 if ( this.boundingSphere === null ) {
9774 this.boundingSphere =
new THREE.Sphere();
9778 this.boundingSphere.setFromPoints( this.vertices );
9782 merge:
function ( geometry, matrix, materialIndexOffset ) {
9784 if ( geometry instanceof THREE.Geometry ===
false ) {
9786 console.error(
'THREE.Geometry.merge(): geometry not an instance of THREE.Geometry.', geometry );
9792 vertexOffset = this.vertices.length,
9793 vertices1 = this.vertices,
9794 vertices2 = geometry.vertices,
9795 faces1 = this.faces,
9796 faces2 = geometry.faces,
9797 uvs1 = this.faceVertexUvs[ 0 ],
9798 uvs2 = geometry.faceVertexUvs[ 0 ];
9800 if ( materialIndexOffset === undefined ) materialIndexOffset = 0;
9802 if ( matrix !== undefined ) {
9804 normalMatrix =
new THREE.Matrix3().getNormalMatrix( matrix );
9810 for ( var i = 0, il = vertices2.length; i < il; i ++ ) {
9812 var vertex = vertices2[ i ];
9814 var vertexCopy = vertex.clone();
9816 if ( matrix !== undefined ) vertexCopy.applyMatrix4( matrix );
9818 vertices1.push( vertexCopy );
9824 for ( i = 0, il = faces2.length; i < il; i ++ ) {
9826 var face = faces2[ i ], faceCopy, normal, color,
9827 faceVertexNormals = face.vertexNormals,
9828 faceVertexColors = face.vertexColors;
9830 faceCopy =
new THREE.Face3( face.a + vertexOffset, face.b + vertexOffset, face.c + vertexOffset );
9831 faceCopy.normal.copy( face.normal );
9833 if ( normalMatrix !== undefined ) {
9835 faceCopy.normal.applyMatrix3( normalMatrix ).normalize();
9839 for ( var j = 0, jl = faceVertexNormals.length; j < jl; j ++ ) {
9841 normal = faceVertexNormals[ j ].clone();
9843 if ( normalMatrix !== undefined ) {
9845 normal.applyMatrix3( normalMatrix ).normalize();
9849 faceCopy.vertexNormals.push( normal );
9853 faceCopy.color.copy( face.color );
9855 for ( var j = 0, jl = faceVertexColors.length; j < jl; j ++ ) {
9857 color = faceVertexColors[ j ];
9858 faceCopy.vertexColors.push( color.clone() );
9862 faceCopy.materialIndex = face.materialIndex + materialIndexOffset;
9864 faces1.push( faceCopy );
9870 for ( i = 0, il = uvs2.length; i < il; i ++ ) {
9872 var uv = uvs2[ i ], uvCopy = [];
9874 if ( uv === undefined ) {
9880 for ( var j = 0, jl = uv.length; j < jl; j ++ ) {
9882 uvCopy.push( uv[ j ].clone() );
9886 uvs1.push( uvCopy );
9892 mergeMesh:
function ( mesh ) {
9894 if ( mesh instanceof THREE.Mesh ===
false ) {
9896 console.error(
'THREE.Geometry.mergeMesh(): mesh not an instance of THREE.Mesh.', mesh );
9901 mesh.matrixAutoUpdate && mesh.updateMatrix();
9903 this.merge( mesh.geometry, mesh.matrix );
9913 mergeVertices:
function () {
9915 var verticesMap = {};
9916 var unique = [], changes = [];
9919 var precisionPoints = 4;
9920 var precision = Math.pow( 10, precisionPoints );
9924 for ( i = 0, il = this.vertices.length; i < il; i ++ ) {
9926 v = this.vertices[ i ];
9927 key = Math.round( v.x * precision ) +
'_' + Math.round( v.y * precision ) +
'_' + Math.round( v.z * precision );
9929 if ( verticesMap[ key ] === undefined ) {
9931 verticesMap[ key ] = i;
9932 unique.push( this.vertices[ i ] );
9933 changes[ i ] = unique.length - 1;
9938 changes[ i ] = changes[ verticesMap[ key ] ];
9947 var faceIndicesToRemove = [];
9949 for ( i = 0, il = this.faces.length; i < il; i ++ ) {
9951 face = this.faces[ i ];
9953 face.a = changes[ face.a ];
9954 face.b = changes[ face.b ];
9955 face.c = changes[ face.c ];
9957 indices = [ face.a, face.b, face.c ];
9963 for ( var n = 0; n < 3; n ++ ) {
9965 if ( indices[ n ] === indices[ ( n + 1 ) % 3 ] ) {
9968 faceIndicesToRemove.push( i );
9977 for ( i = faceIndicesToRemove.length - 1; i >= 0; i -- ) {
9979 var idx = faceIndicesToRemove[ i ];
9981 this.faces.splice( idx, 1 );
9983 for ( j = 0, jl = this.faceVertexUvs.length; j < jl; j ++ ) {
9985 this.faceVertexUvs[ j ].splice( idx, 1 );
9993 var diff = this.vertices.length - unique.length;
9994 this.vertices = unique;
9999 sortFacesByMaterialIndex:
function () {
10001 var faces = this.faces;
10002 var length = faces.length;
10006 for ( var i = 0; i < length; i ++ ) {
10008 faces[ i ]._id = i;
10014 function materialIndexSort( a, b ) {
10016 return a.materialIndex - b.materialIndex;
10020 faces.sort( materialIndexSort );
10024 var uvs1 = this.faceVertexUvs[ 0 ];
10025 var uvs2 = this.faceVertexUvs[ 1 ];
10027 var newUvs1, newUvs2;
10029 if ( uvs1 && uvs1.length === length ) newUvs1 = [];
10030 if ( uvs2 && uvs2.length === length ) newUvs2 = [];
10032 for ( var i = 0; i < length; i ++ ) {
10034 var
id = faces[ i ]._id;
10036 if ( newUvs1 ) newUvs1.push( uvs1[
id ] );
10037 if ( newUvs2 ) newUvs2.push( uvs2[
id ] );
10041 if ( newUvs1 ) this.faceVertexUvs[ 0 ] = newUvs1;
10042 if ( newUvs2 ) this.faceVertexUvs[ 1 ] = newUvs2;
10046 toJSON:
function () {
10052 generator:
'Geometry.toJSON'
10058 data.uuid = this.uuid;
10059 data.type = this.type;
10060 if ( this.name !==
'' ) data.name = this.name;
10062 if ( this.parameters !== undefined ) {
10064 var parameters = this.parameters;
10066 for ( var key in parameters ) {
10068 if ( parameters[ key ] !== undefined ) data[ key ] = parameters[ key ];
10078 for ( var i = 0; i < this.vertices.length; i ++ ) {
10080 var vertex = this.vertices[ i ];
10081 vertices.push( vertex.x, vertex.y, vertex.z );
10087 var normalsHash = {};
10089 var colorsHash = {};
10093 for ( var i = 0; i < this.faces.length; i ++ ) {
10095 var face = this.faces[ i ];
10097 var hasMaterial =
false;
10098 var hasFaceUv =
false;
10099 var hasFaceVertexUv = this.faceVertexUvs[ 0 ][ i ] !== undefined;
10100 var hasFaceNormal = face.normal.length() > 0;
10101 var hasFaceVertexNormal = face.vertexNormals.length > 0;
10102 var hasFaceColor = face.color.r !== 1 || face.color.g !== 1 || face.color.b !== 1;
10103 var hasFaceVertexColor = face.vertexColors.length > 0;
10107 faceType = setBit( faceType, 0, 0 );
10108 faceType = setBit( faceType, 1, hasMaterial );
10109 faceType = setBit( faceType, 2, hasFaceUv );
10110 faceType = setBit( faceType, 3, hasFaceVertexUv );
10111 faceType = setBit( faceType, 4, hasFaceNormal );
10112 faceType = setBit( faceType, 5, hasFaceVertexNormal );
10113 faceType = setBit( faceType, 6, hasFaceColor );
10114 faceType = setBit( faceType, 7, hasFaceVertexColor );
10116 faces.push( faceType );
10117 faces.push( face.a, face.b, face.c );
10119 if ( hasFaceVertexUv ) {
10121 var faceVertexUvs = this.faceVertexUvs[ 0 ][ i ];
10124 getUvIndex( faceVertexUvs[ 0 ] ),
10125 getUvIndex( faceVertexUvs[ 1 ] ),
10126 getUvIndex( faceVertexUvs[ 2 ] )
10131 if ( hasFaceNormal ) {
10133 faces.push( getNormalIndex( face.normal ) );
10137 if ( hasFaceVertexNormal ) {
10139 var vertexNormals = face.vertexNormals;
10142 getNormalIndex( vertexNormals[ 0 ] ),
10143 getNormalIndex( vertexNormals[ 1 ] ),
10144 getNormalIndex( vertexNormals[ 2 ] )
10149 if ( hasFaceColor ) {
10151 faces.push( getColorIndex( face.color ) );
10155 if ( hasFaceVertexColor ) {
10157 var vertexColors = face.vertexColors;
10160 getColorIndex( vertexColors[ 0 ] ),
10161 getColorIndex( vertexColors[ 1 ] ),
10162 getColorIndex( vertexColors[ 2 ] )
10169 function setBit( value, position, enabled ) {
10171 return enabled ? value | ( 1 << position ) : value & ( ~ ( 1 << position ) );
10175 function getNormalIndex( normal ) {
10177 var hash = normal.x.toString() + normal.y.toString() + normal.z.toString();
10179 if ( normalsHash[ hash ] !== undefined ) {
10181 return normalsHash[ hash ];
10185 normalsHash[ hash ] = normals.length / 3;
10186 normals.push( normal.x, normal.y, normal.z );
10188 return normalsHash[ hash ];
10192 function getColorIndex( color ) {
10194 var hash = color.r.toString() + color.g.toString() + color.b.toString();
10196 if ( colorsHash[ hash ] !== undefined ) {
10198 return colorsHash[ hash ];
10202 colorsHash[ hash ] = colors.length;
10203 colors.push( color.getHex() );
10205 return colorsHash[ hash ];
10209 function getUvIndex( uv ) {
10211 var hash = uv.x.toString() + uv.y.toString();
10213 if ( uvsHash[ hash ] !== undefined ) {
10215 return uvsHash[ hash ];
10219 uvsHash[ hash ] = uvs.length / 2;
10220 uvs.push( uv.x, uv.y );
10222 return uvsHash[ hash ];
10228 data.data.vertices = vertices;
10229 data.data.normals = normals;
10230 if ( colors.length > 0 ) data.data.colors = colors;
10231 if ( uvs.length > 0 ) data.data.uvs = [ uvs ];
10232 data.data.faces = faces;
10238 clone:
function () {
10240 return new this.constructor().copy(
this );
10244 copy:
function ( source ) {
10246 this.vertices = [];
10248 this.faceVertexUvs = [ [] ];
10250 var vertices = source.vertices;
10252 for ( var i = 0, il = vertices.length; i < il; i ++ ) {
10254 this.vertices.push( vertices[ i ].clone() );
10258 var faces = source.faces;
10260 for ( var i = 0, il = faces.length; i < il; i ++ ) {
10262 this.faces.push( faces[ i ].clone() );
10266 for ( var i = 0, il = source.faceVertexUvs.length; i < il; i ++ ) {
10268 var faceVertexUvs = source.faceVertexUvs[ i ];
10270 if ( this.faceVertexUvs[ i ] === undefined ) {
10272 this.faceVertexUvs[ i ] = [];
10276 for ( var j = 0, jl = faceVertexUvs.length; j < jl; j ++ ) {
10278 var uvs = faceVertexUvs[ j ], uvsCopy = [];
10280 for ( var k = 0, kl = uvs.length; k < kl; k ++ ) {
10284 uvsCopy.push( uv.clone() );
10288 this.faceVertexUvs[ i ].push( uvsCopy );
10298 dispose:
function () {
10300 this.dispatchEvent( { type:
'dispose' } );
10306 THREE.EventDispatcher.prototype.apply( THREE.Geometry.prototype );
10308 THREE.GeometryIdCount = 0;
10316 THREE.DirectGeometry =
function () {
10318 Object.defineProperty(
this,
'id', { value: THREE.GeometryIdCount ++ } );
10320 this.uuid = THREE.Math.generateUUID();
10323 this.type =
'DirectGeometry';
10326 this.vertices = [];
10334 this.morphTargets = {};
10336 this.skinWeights = [];
10337 this.skinIndices = [];
10341 this.boundingBox = null;
10342 this.boundingSphere = null;
10346 this.verticesNeedUpdate =
false;
10347 this.normalsNeedUpdate =
false;
10348 this.colorsNeedUpdate =
false;
10349 this.uvsNeedUpdate =
false;
10350 this.groupsNeedUpdate =
false;
10354 THREE.DirectGeometry.prototype = {
10356 constructor: THREE.DirectGeometry,
10358 computeBoundingBox: THREE.Geometry.prototype.computeBoundingBox,
10359 computeBoundingSphere: THREE.Geometry.prototype.computeBoundingSphere,
10361 computeFaceNormals:
function () {
10363 console.warn(
'THREE.DirectGeometry: computeFaceNormals() is not a method of this type of geometry.' );
10367 computeVertexNormals:
function () {
10369 console.warn(
'THREE.DirectGeometry: computeVertexNormals() is not a method of this type of geometry.' );
10373 computeGroups:
function ( geometry ) {
10379 var faces = geometry.faces;
10381 for ( var i = 0; i < faces.length; i ++ ) {
10383 var face = faces[ i ];
10387 if ( face.materialIndex !== materialIndex ) {
10389 materialIndex = face.materialIndex;
10391 if ( group !== undefined ) {
10393 group.count = ( i * 3 ) - group.start;
10394 groups.push( group );
10400 materialIndex: materialIndex
10407 if ( group !== undefined ) {
10409 group.count = ( i * 3 ) - group.start;
10410 groups.push( group );
10414 this.groups = groups;
10418 fromGeometry:
function ( geometry ) {
10420 var faces = geometry.faces;
10421 var vertices = geometry.vertices;
10422 var faceVertexUvs = geometry.faceVertexUvs;
10424 var hasFaceVertexUv = faceVertexUvs[ 0 ] && faceVertexUvs[ 0 ].length > 0;
10425 var hasFaceVertexUv2 = faceVertexUvs[ 1 ] && faceVertexUvs[ 1 ].length > 0;
10429 var morphTargets = geometry.morphTargets;
10430 var morphTargetsLength = morphTargets.length;
10432 if ( morphTargetsLength > 0 ) {
10434 var morphTargetsPosition = [];
10436 for ( var i = 0; i < morphTargetsLength; i ++ ) {
10438 morphTargetsPosition[ i ] = [];
10442 this.morphTargets.position = morphTargetsPosition;
10446 var morphNormals = geometry.morphNormals;
10447 var morphNormalsLength = morphNormals.length;
10449 if ( morphNormalsLength > 0 ) {
10451 var morphTargetsNormal = [];
10453 for ( var i = 0; i < morphNormalsLength; i ++ ) {
10455 morphTargetsNormal[ i ] = [];
10459 this.morphTargets.normal = morphTargetsNormal;
10465 var skinIndices = geometry.skinIndices;
10466 var skinWeights = geometry.skinWeights;
10468 var hasSkinIndices = skinIndices.length === vertices.length;
10469 var hasSkinWeights = skinWeights.length === vertices.length;
10473 for ( var i = 0; i < faces.length; i ++ ) {
10475 var face = faces[ i ];
10477 this.vertices.push( vertices[ face.a ], vertices[ face.b ], vertices[ face.c ] );
10479 var vertexNormals = face.vertexNormals;
10481 if ( vertexNormals.length === 3 ) {
10483 this.normals.push( vertexNormals[ 0 ], vertexNormals[ 1 ], vertexNormals[ 2 ] );
10487 var normal = face.normal;
10489 this.normals.push( normal, normal, normal );
10493 var vertexColors = face.vertexColors;
10495 if ( vertexColors.length === 3 ) {
10497 this.colors.push( vertexColors[ 0 ], vertexColors[ 1 ], vertexColors[ 2 ] );
10501 var color = face.color;
10503 this.colors.push( color, color, color );
10507 if ( hasFaceVertexUv ===
true ) {
10509 var vertexUvs = faceVertexUvs[ 0 ][ i ];
10511 if ( vertexUvs !== undefined ) {
10513 this.uvs.push( vertexUvs[ 0 ], vertexUvs[ 1 ], vertexUvs[ 2 ] );
10517 console.warn(
'THREE.DirectGeometry.fromGeometry(): Undefined vertexUv ', i );
10519 this.uvs.push(
new THREE.Vector2(),
new THREE.Vector2(),
new THREE.Vector2() );
10525 if ( hasFaceVertexUv2 ===
true ) {
10527 var vertexUvs = faceVertexUvs[ 1 ][ i ];
10529 if ( vertexUvs !== undefined ) {
10531 this.uvs2.push( vertexUvs[ 0 ], vertexUvs[ 1 ], vertexUvs[ 2 ] );
10535 console.warn(
'THREE.DirectGeometry.fromGeometry(): Undefined vertexUv2 ', i );
10537 this.uvs2.push(
new THREE.Vector2(),
new THREE.Vector2(),
new THREE.Vector2() );
10545 for ( var j = 0; j < morphTargetsLength; j ++ ) {
10547 var morphTarget = morphTargets[ j ].vertices;
10549 morphTargetsPosition[ j ].push( morphTarget[ face.a ], morphTarget[ face.b ], morphTarget[ face.c ] );
10553 for ( var j = 0; j < morphNormalsLength; j ++ ) {
10555 var morphNormal = morphNormals[ j ].vertexNormals[ i ];
10557 morphTargetsNormal[ j ].push( morphNormal.a, morphNormal.b, morphNormal.c );
10563 if ( hasSkinIndices ) {
10565 this.skinIndices.push( skinIndices[ face.a ], skinIndices[ face.b ], skinIndices[ face.c ] );
10569 if ( hasSkinWeights ) {
10571 this.skinWeights.push( skinWeights[ face.a ], skinWeights[ face.b ], skinWeights[ face.c ] );
10577 this.computeGroups( geometry );
10579 this.verticesNeedUpdate = geometry.verticesNeedUpdate;
10580 this.normalsNeedUpdate = geometry.normalsNeedUpdate;
10581 this.colorsNeedUpdate = geometry.colorsNeedUpdate;
10582 this.uvsNeedUpdate = geometry.uvsNeedUpdate;
10583 this.groupsNeedUpdate = geometry.groupsNeedUpdate;
10589 dispose:
function () {
10591 this.dispatchEvent( { type:
'dispose' } );
10597 THREE.EventDispatcher.prototype.apply( THREE.DirectGeometry.prototype );
10606 THREE.BufferGeometry =
function () {
10608 Object.defineProperty(
this,
'id', { value: THREE.GeometryIdCount ++ } );
10610 this.uuid = THREE.Math.generateUUID();
10613 this.type =
'BufferGeometry';
10616 this.attributes = {};
10618 this.morphAttributes = {};
10622 this.boundingBox = null;
10623 this.boundingSphere = null;
10625 this.drawRange = { start: 0, count: Infinity };
10629 THREE.BufferGeometry.prototype = {
10631 constructor: THREE.BufferGeometry,
10633 addIndex:
function ( index ) {
10635 console.warn(
'THREE.BufferGeometry: .addIndex() has been renamed to .setIndex().' );
10636 this.setIndex( index );
10640 getIndex:
function () {
10646 setIndex:
function ( index ) {
10648 this.index = index;
10652 addAttribute:
function ( name, attribute ) {
10654 if ( attribute instanceof THREE.BufferAttribute ===
false && attribute instanceof THREE.InterleavedBufferAttribute ===
false ) {
10656 console.warn(
'THREE.BufferGeometry: .addAttribute() now expects ( name, attribute ).' );
10658 this.addAttribute( name,
new THREE.BufferAttribute( arguments[ 1 ], arguments[ 2 ] ) );
10664 if ( name ===
'index' ) {
10666 console.warn(
'THREE.BufferGeometry.addAttribute: Use .setIndex() for index attribute.' );
10667 this.setIndex( attribute );
10673 this.attributes[ name ] = attribute;
10677 getAttribute:
function ( name ) {
10679 return this.attributes[ name ];
10683 removeAttribute:
function ( name ) {
10685 delete this.attributes[ name ];
10691 console.error(
'THREE.BufferGeometry: .drawcalls has been renamed to .groups.' );
10692 return this.groups;
10698 console.warn(
'THREE.BufferGeometry: .offsets has been renamed to .groups.' );
10699 return this.groups;
10703 addDrawCall:
function ( start, count, indexOffset ) {
10705 if ( indexOffset !== undefined ) {
10707 console.warn(
'THREE.BufferGeometry: .addDrawCall() no longer supports indexOffset.' );
10711 console.warn(
'THREE.BufferGeometry: .addDrawCall() is now .addGroup().' );
10712 this.addGroup( start, count );
10716 clearDrawCalls:
function () {
10718 console.warn(
'THREE.BufferGeometry: .clearDrawCalls() is now .clearGroups().' );
10719 this.clearGroups();
10723 addGroup:
function ( start, count, materialIndex ) {
10725 this.groups.push( {
10729 materialIndex: materialIndex !== undefined ? materialIndex : 0
10735 clearGroups:
function () {
10741 setDrawRange:
function ( start, count ) {
10743 this.drawRange.start = start;
10744 this.drawRange.count = count;
10748 applyMatrix:
function ( matrix ) {
10750 var position = this.attributes.position;
10752 if ( position !== undefined ) {
10754 matrix.applyToVector3Array( position.array );
10755 position.needsUpdate =
true;
10759 var normal = this.attributes.normal;
10761 if ( normal !== undefined ) {
10763 var normalMatrix =
new THREE.Matrix3().getNormalMatrix( matrix );
10765 normalMatrix.applyToVector3Array( normal.array );
10766 normal.needsUpdate =
true;
10770 if ( this.boundingBox !== null ) {
10772 this.computeBoundingBox();
10776 if ( this.boundingSphere !== null ) {
10778 this.computeBoundingSphere();
10784 rotateX:
function () {
10790 return function rotateX( angle ) {
10792 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
10794 m1.makeRotationX( angle );
10796 this.applyMatrix( m1 );
10804 rotateY:
function () {
10810 return function rotateY( angle ) {
10812 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
10814 m1.makeRotationY( angle );
10816 this.applyMatrix( m1 );
10824 rotateZ:
function () {
10830 return function rotateZ( angle ) {
10832 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
10834 m1.makeRotationZ( angle );
10836 this.applyMatrix( m1 );
10844 translate:
function () {
10850 return function translate( x, y, z ) {
10852 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
10854 m1.makeTranslation( x, y, z );
10856 this.applyMatrix( m1 );
10864 scale:
function () {
10870 return function scale( x, y, z ) {
10872 if ( m1 === undefined ) m1 =
new THREE.Matrix4();
10874 m1.makeScale( x, y, z );
10876 this.applyMatrix( m1 );
10884 lookAt:
function () {
10888 return function lookAt( vector ) {
10890 if ( obj === undefined ) obj =
new THREE.Object3D();
10892 obj.lookAt( vector );
10894 obj.updateMatrix();
10896 this.applyMatrix( obj.matrix );
10902 center:
function () {
10904 this.computeBoundingBox();
10906 var offset = this.boundingBox.center().negate();
10908 this.translate( offset.x, offset.y, offset.z );
10914 setFromObject:
function ( object ) {
10918 var geometry =
object.geometry;
10920 if (
object instanceof THREE.Points ||
object instanceof THREE.Line ) {
10922 var positions =
new THREE.Float32Attribute( geometry.vertices.length * 3, 3 );
10923 var colors =
new THREE.Float32Attribute( geometry.colors.length * 3, 3 );
10925 this.addAttribute(
'position', positions.copyVector3sArray( geometry.vertices ) );
10926 this.addAttribute(
'color', colors.copyColorsArray( geometry.colors ) );
10928 if ( geometry.lineDistances && geometry.lineDistances.length === geometry.vertices.length ) {
10930 var lineDistances =
new THREE.Float32Attribute( geometry.lineDistances.length, 1 );
10932 this.addAttribute(
'lineDistance', lineDistances.copyArray( geometry.lineDistances ) );
10936 if ( geometry.boundingSphere !== null ) {
10938 this.boundingSphere = geometry.boundingSphere.clone();
10942 if ( geometry.boundingBox !== null ) {
10944 this.boundingBox = geometry.boundingBox.clone();
10948 }
else if (
object instanceof THREE.Mesh ) {
10950 if ( geometry instanceof THREE.Geometry ) {
10952 this.fromGeometry( geometry );
10962 updateFromObject:
function ( object ) {
10964 var geometry =
object.geometry;
10966 if (
object instanceof THREE.Mesh ) {
10968 var direct = geometry.__directGeometry;
10970 if ( direct === undefined ) {
10972 return this.fromGeometry( geometry );
10976 direct.verticesNeedUpdate = geometry.verticesNeedUpdate;
10977 direct.normalsNeedUpdate = geometry.normalsNeedUpdate;
10978 direct.colorsNeedUpdate = geometry.colorsNeedUpdate;
10979 direct.uvsNeedUpdate = geometry.uvsNeedUpdate;
10980 direct.groupsNeedUpdate = geometry.groupsNeedUpdate;
10982 geometry.verticesNeedUpdate =
false;
10983 geometry.normalsNeedUpdate =
false;
10984 geometry.colorsNeedUpdate =
false;
10985 geometry.uvsNeedUpdate =
false;
10986 geometry.groupsNeedUpdate =
false;
10992 if ( geometry.verticesNeedUpdate ===
true ) {
10994 var attribute = this.attributes.position;
10996 if ( attribute !== undefined ) {
10998 attribute.copyVector3sArray( geometry.vertices );
10999 attribute.needsUpdate =
true;
11003 geometry.verticesNeedUpdate =
false;
11007 if ( geometry.normalsNeedUpdate ===
true ) {
11009 var attribute = this.attributes.normal;
11011 if ( attribute !== undefined ) {
11013 attribute.copyVector3sArray( geometry.normals );
11014 attribute.needsUpdate =
true;
11018 geometry.normalsNeedUpdate =
false;
11022 if ( geometry.colorsNeedUpdate ===
true ) {
11024 var attribute = this.attributes.color;
11026 if ( attribute !== undefined ) {
11028 attribute.copyColorsArray( geometry.colors );
11029 attribute.needsUpdate =
true;
11033 geometry.colorsNeedUpdate =
false;
11037 if ( geometry.uvsNeedUpdate ) {
11039 var attribute = this.attributes.uv;
11041 if ( attribute !== undefined ) {
11043 attribute.copyVector2sArray( geometry.uvs );
11044 attribute.needsUpdate =
true;
11048 geometry.uvsNeedUpdate =
false;
11052 if ( geometry.lineDistancesNeedUpdate ) {
11054 var attribute = this.attributes.lineDistance;
11056 if ( attribute !== undefined ) {
11058 attribute.copyArray( geometry.lineDistances );
11059 attribute.needsUpdate =
true;
11063 geometry.lineDistancesNeedUpdate =
false;
11067 if ( geometry.groupsNeedUpdate ) {
11069 geometry.computeGroups(
object.geometry );
11070 this.groups = geometry.groups;
11072 geometry.groupsNeedUpdate =
false;
11080 fromGeometry:
function ( geometry ) {
11082 geometry.__directGeometry =
new THREE.DirectGeometry().fromGeometry( geometry );
11084 return this.fromDirectGeometry( geometry.__directGeometry );
11088 fromDirectGeometry:
function ( geometry ) {
11090 var positions =
new Float32Array( geometry.vertices.length * 3 );
11091 this.addAttribute(
'position',
new THREE.BufferAttribute( positions, 3 ).copyVector3sArray( geometry.vertices ) );
11093 if ( geometry.normals.length > 0 ) {
11095 var normals =
new Float32Array( geometry.normals.length * 3 );
11096 this.addAttribute(
'normal',
new THREE.BufferAttribute( normals, 3 ).copyVector3sArray( geometry.normals ) );
11100 if ( geometry.colors.length > 0 ) {
11102 var colors =
new Float32Array( geometry.colors.length * 3 );
11103 this.addAttribute(
'color',
new THREE.BufferAttribute( colors, 3 ).copyColorsArray( geometry.colors ) );
11107 if ( geometry.uvs.length > 0 ) {
11109 var uvs =
new Float32Array( geometry.uvs.length * 2 );
11110 this.addAttribute(
'uv',
new THREE.BufferAttribute( uvs, 2 ).copyVector2sArray( geometry.uvs ) );
11114 if ( geometry.uvs2.length > 0 ) {
11116 var uvs2 =
new Float32Array( geometry.uvs2.length * 2 );
11117 this.addAttribute(
'uv2',
new THREE.BufferAttribute( uvs2, 2 ).copyVector2sArray( geometry.uvs2 ) );
11121 if ( geometry.indices.length > 0 ) {
11123 var TypeArray = geometry.vertices.length > 65535 ? Uint32Array : Uint16Array;
11124 var indices =
new TypeArray( geometry.indices.length * 3 );
11125 this.setIndex(
new THREE.BufferAttribute( indices, 1 ).copyIndicesArray( geometry.indices ) );
11131 this.groups = geometry.groups;
11135 for ( var name in geometry.morphTargets ) {
11138 var morphTargets = geometry.morphTargets[ name ];
11140 for ( var i = 0, l = morphTargets.length; i < l; i ++ ) {
11142 var morphTarget = morphTargets[ i ];
11144 var attribute =
new THREE.Float32Attribute( morphTarget.length * 3, 3 );
11146 array.push( attribute.copyVector3sArray( morphTarget ) );
11150 this.morphAttributes[ name ] = array;
11156 if ( geometry.skinIndices.length > 0 ) {
11158 var skinIndices =
new THREE.Float32Attribute( geometry.skinIndices.length * 4, 4 );
11159 this.addAttribute(
'skinIndex', skinIndices.copyVector4sArray( geometry.skinIndices ) );
11163 if ( geometry.skinWeights.length > 0 ) {
11165 var skinWeights =
new THREE.Float32Attribute( geometry.skinWeights.length * 4, 4 );
11166 this.addAttribute(
'skinWeight', skinWeights.copyVector4sArray( geometry.skinWeights ) );
11172 if ( geometry.boundingSphere !== null ) {
11174 this.boundingSphere = geometry.boundingSphere.clone();
11178 if ( geometry.boundingBox !== null ) {
11180 this.boundingBox = geometry.boundingBox.clone();
11188 computeBoundingBox:
function () {
11190 var vector =
new THREE.Vector3();
11192 return function () {
11194 if ( this.boundingBox === null ) {
11196 this.boundingBox =
new THREE.Box3();
11200 var positions = this.attributes.position.array;
11204 var bb = this.boundingBox;
11207 for ( var i = 0, il = positions.length; i < il; i += 3 ) {
11209 vector.fromArray( positions, i );
11210 bb.expandByPoint( vector );
11216 if ( positions === undefined || positions.length === 0 ) {
11218 this.boundingBox.min.set( 0, 0, 0 );
11219 this.boundingBox.max.set( 0, 0, 0 );
11223 if ( isNaN( this.boundingBox.min.x ) || isNaN( this.boundingBox.min.y ) || isNaN( this.boundingBox.min.z ) ) {
11225 console.error(
'THREE.BufferGeometry.computeBoundingBox: Computed min/max have NaN values. The "position" attribute is likely to have NaN values.',
this );
11233 computeBoundingSphere:
function () {
11235 var box =
new THREE.Box3();
11236 var vector =
new THREE.Vector3();
11238 return function () {
11240 if ( this.boundingSphere === null ) {
11242 this.boundingSphere =
new THREE.Sphere();
11246 var positions = this.attributes.position.array;
11252 var center = this.boundingSphere.center;
11254 for ( var i = 0, il = positions.length; i < il; i += 3 ) {
11256 vector.fromArray( positions, i );
11257 box.expandByPoint( vector );
11261 box.center( center );
11266 var maxRadiusSq = 0;
11268 for ( var i = 0, il = positions.length; i < il; i += 3 ) {
11270 vector.fromArray( positions, i );
11271 maxRadiusSq = Math.max( maxRadiusSq, center.distanceToSquared( vector ) );
11275 this.boundingSphere.radius = Math.sqrt( maxRadiusSq );
11277 if ( isNaN( this.boundingSphere.radius ) ) {
11279 console.error(
'THREE.BufferGeometry.computeBoundingSphere(): Computed radius is NaN. The "position" attribute is likely to have NaN values.',
this );
11289 computeFaceNormals:
function () {
11295 computeVertexNormals:
function () {
11297 var index = this.index;
11298 var attributes = this.attributes;
11299 var groups = this.groups;
11301 if ( attributes.position ) {
11303 var positions = attributes.position.array;
11305 if ( attributes.normal === undefined ) {
11307 this.addAttribute(
'normal',
new THREE.BufferAttribute(
new Float32Array( positions.length ), 3 ) );
11313 var normals = attributes.normal.array;
11315 for ( var i = 0, il = normals.length; i < il; i ++ ) {
11323 var normals = attributes.normal.array;
11327 pA =
new THREE.Vector3(),
11328 pB =
new THREE.Vector3(),
11329 pC =
new THREE.Vector3(),
11331 cb =
new THREE.Vector3(),
11332 ab =
new THREE.Vector3();
11338 var indices = index.array;
11340 if ( groups.length === 0 ) {
11342 this.addGroup( 0, indices.length );
11346 for ( var j = 0, jl = groups.length; j < jl; ++ j ) {
11348 var group = groups[ j ];
11350 var start = group.start;
11351 var count = group.count;
11353 for ( var i = start, il = start + count; i < il; i += 3 ) {
11355 vA = indices[ i + 0 ] * 3;
11356 vB = indices[ i + 1 ] * 3;
11357 vC = indices[ i + 2 ] * 3;
11359 pA.fromArray( positions, vA );
11360 pB.fromArray( positions, vB );
11361 pC.fromArray( positions, vC );
11363 cb.subVectors( pC, pB );
11364 ab.subVectors( pA, pB );
11367 normals[ vA ] += cb.x;
11368 normals[ vA + 1 ] += cb.y;
11369 normals[ vA + 2 ] += cb.z;
11371 normals[ vB ] += cb.x;
11372 normals[ vB + 1 ] += cb.y;
11373 normals[ vB + 2 ] += cb.z;
11375 normals[ vC ] += cb.x;
11376 normals[ vC + 1 ] += cb.y;
11377 normals[ vC + 2 ] += cb.z;
11387 for ( var i = 0, il = positions.length; i < il; i += 9 ) {
11389 pA.fromArray( positions, i );
11390 pB.fromArray( positions, i + 3 );
11391 pC.fromArray( positions, i + 6 );
11393 cb.subVectors( pC, pB );
11394 ab.subVectors( pA, pB );
11397 normals[ i ] = cb.x;
11398 normals[ i + 1 ] = cb.y;
11399 normals[ i + 2 ] = cb.z;
11401 normals[ i + 3 ] = cb.x;
11402 normals[ i + 4 ] = cb.y;
11403 normals[ i + 5 ] = cb.z;
11405 normals[ i + 6 ] = cb.x;
11406 normals[ i + 7 ] = cb.y;
11407 normals[ i + 8 ] = cb.z;
11413 this.normalizeNormals();
11415 attributes.normal.needsUpdate =
true;
11421 computeTangents:
function () {
11423 console.warn(
'THREE.BufferGeometry: .computeTangents() has been removed.' );
11427 computeOffsets:
function ( size ) {
11429 console.warn(
'THREE.BufferGeometry: .computeOffsets() has been removed.')
11433 merge:
function ( geometry, offset ) {
11435 if ( geometry instanceof THREE.BufferGeometry ===
false ) {
11437 console.error(
'THREE.BufferGeometry.merge(): geometry not an instance of THREE.BufferGeometry.', geometry );
11442 if ( offset === undefined ) offset = 0;
11444 var attributes = this.attributes;
11446 for ( var key in attributes ) {
11448 if ( geometry.attributes[ key ] === undefined )
continue;
11450 var attribute1 = attributes[ key ];
11451 var attributeArray1 = attribute1.array;
11453 var attribute2 = geometry.attributes[ key ];
11454 var attributeArray2 = attribute2.array;
11456 var attributeSize = attribute2.itemSize;
11458 for ( var i = 0, j = attributeSize * offset; i < attributeArray2.length; i ++, j ++ ) {
11460 attributeArray1[ j ] = attributeArray2[ i ];
11470 normalizeNormals:
function () {
11472 var normals = this.attributes.normal.array;
11476 for ( var i = 0, il = normals.length; i < il; i += 3 ) {
11479 y = normals[ i + 1 ];
11480 z = normals[ i + 2 ];
11482 n = 1.0 / Math.sqrt( x * x + y * y + z * z );
11485 normals[ i + 1 ] *= n;
11486 normals[ i + 2 ] *= n;
11492 toJSON:
function () {
11497 type:
'BufferGeometry',
11498 generator:
'BufferGeometry.toJSON'
11504 data.uuid = this.uuid;
11505 data.type = this.type;
11506 if ( this.name !==
'' ) data.name = this.name;
11508 if ( this.parameters !== undefined ) {
11510 var parameters = this.parameters;
11512 for ( var key in parameters ) {
11514 if ( parameters[ key ] !== undefined ) data[ key ] = parameters[ key ];
11522 data.data = { attributes: {} };
11524 var index = this.index;
11526 if ( index !== null ) {
11528 var array = Array.prototype.slice.call( index.array );
11530 data.data.index = {
11531 type: index.array.constructor.name,
11537 var attributes = this.attributes;
11539 for ( var key in attributes ) {
11541 var attribute = attributes[ key ];
11543 var array = Array.prototype.slice.call( attribute.array );
11545 data.data.attributes[ key ] = {
11546 itemSize: attribute.itemSize,
11547 type: attribute.array.constructor.name,
11553 var groups = this.groups;
11555 if ( groups.length > 0 ) {
11557 data.data.groups = JSON.parse( JSON.stringify( groups ) );
11561 var boundingSphere = this.boundingSphere;
11563 if ( boundingSphere !== null ) {
11565 data.data.boundingSphere = {
11566 center: boundingSphere.center.toArray(),
11567 radius: boundingSphere.radius
11576 clone:
function () {
11578 return new this.constructor().copy(
this );
11582 copy:
function ( source ) {
11584 var index = source.index;
11586 if ( index !== null ) {
11588 this.setIndex( index.clone() );
11592 var attributes = source.attributes;
11594 for ( var name in attributes ) {
11596 var attribute = attributes[ name ];
11597 this.addAttribute( name, attribute.clone() );
11601 var groups = source.groups;
11603 for ( var i = 0, l = groups.length; i < l; i ++ ) {
11605 var group = groups[ i ];
11606 this.addGroup( group.start, group.count );
11614 dispose:
function () {
11616 this.dispatchEvent( { type:
'dispose' } );
11622 THREE.EventDispatcher.prototype.apply( THREE.BufferGeometry.prototype );
11624 THREE.BufferGeometry.MaxIndex = 65535;
11632 THREE.InstancedBufferGeometry =
function () {
11634 THREE.BufferGeometry.call(
this );
11636 this.type =
'InstancedBufferGeometry';
11637 this.maxInstancedCount = undefined;
11641 THREE.InstancedBufferGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
11642 THREE.InstancedBufferGeometry.prototype.constructor = THREE.InstancedBufferGeometry;
11644 THREE.InstancedBufferGeometry.prototype.addGroup =
function ( start, count, instances ) {
11646 this.groups.push( {
11650 instances: instances
11656 THREE.InstancedBufferGeometry.prototype.copy =
function ( source ) {
11658 var index = source.index;
11660 if ( index !== null ) {
11662 this.setIndex( index.clone() );
11666 var attributes = source.attributes;
11668 for ( var name in attributes ) {
11670 var attribute = attributes[ name ];
11671 this.addAttribute( name, attribute.clone() );
11675 var groups = source.groups;
11677 for ( var i = 0, l = groups.length; i < l; i ++ ) {
11679 var group = groups[ i ];
11680 this.addGroup( group.start, group.count, group.instances );
11688 THREE.EventDispatcher.prototype.apply( THREE.InstancedBufferGeometry.prototype );
11700 THREE.AnimationAction =
function ( clip, startTime, timeScale, weight, loop ) {
11702 if ( clip === undefined )
throw new Error(
'clip is null' );
11704 this.localRoot = null;
11705 this.startTime = startTime || 0;
11706 this.timeScale = timeScale || 1;
11707 this.weight = weight || 1;
11708 this.loop = loop || THREE.LoopRepeat;
11709 this.loopCount = 0;
11710 this.enabled =
true;
11712 this.actionTime = - this.startTime;
11715 this.propertyBindings = [];
11724 THREE.AnimationAction.prototype = {
11726 constructor: THREE.AnimationAction,
11728 setLocalRoot:
function( localRoot ) {
11730 this.localRoot = localRoot;
11736 updateTime:
function( clipDeltaTime ) {
11738 var previousClipTime = this.clipTime;
11739 var previousLoopCount = this.loopCount;
11740 var previousActionTime = this.actionTime;
11742 var duration = this.clip.duration;
11744 this.actionTime = this.actionTime + clipDeltaTime;
11746 if ( this.loop === THREE.LoopOnce ) {
11748 this.loopCount = 0;
11749 this.clipTime = Math.min( Math.max(
this.actionTime, 0 ), duration );
11752 if ( this.clipTime !== previousClipTime ) {
11754 if ( this.clipTime === duration ) {
11756 this.mixer.dispatchEvent( { type:
'finished', action:
this, direction: 1 } );
11758 }
else if ( this.clipTime === 0 ) {
11760 this.mixer.dispatchEvent( { type:
'finished', action:
this, direction: -1 } );
11767 return this.clipTime;
11771 this.loopCount = Math.floor( this.actionTime / duration );
11773 var newClipTime = this.actionTime - this.loopCount * duration;
11774 newClipTime = newClipTime % duration;
11777 if ( this.loop == THREE.LoopPingPong ) {
11779 if ( Math.abs(
this.loopCount % 2 ) === 1 ) {
11781 newClipTime = duration - newClipTime;
11787 this.clipTime = newClipTime;
11789 if ( this.loopCount !== previousLoopCount ) {
11791 this.mixer.dispatchEvent( { type:
'loop', action:
this, loopDelta: ( this.loopCount - this.loopCount ) } );
11795 return this.clipTime;
11799 syncWith:
function( action ) {
11801 this.actionTime = action.actionTime;
11802 this.timeScale = action.timeScale;
11807 warpToDuration:
function( duration ) {
11809 this.timeScale = this.clip.duration / duration;
11814 init:
function( time ) {
11816 this.clipTime = time - this.startTime;
11822 update:
function( clipDeltaTime ) {
11824 this.updateTime( clipDeltaTime );
11826 var clipResults = this.clip.getAt( this.clipTime );
11828 return clipResults;
11832 getTimeScaleAt:
function( time ) {
11834 if ( this.timeScale.getAt ) {
11836 return this.timeScale.getAt( time );
11840 return this.timeScale;
11844 getWeightAt:
function( time ) {
11846 if ( this.weight.getAt ) {
11848 return this.weight.getAt( time );
11852 return this.weight;
11868 THREE.AnimationClip =
function ( name, duration, tracks ) {
11871 this.tracks = tracks;
11872 this.duration = ( duration !== undefined ) ? duration : -1;
11875 if ( this.duration < 0 ) {
11876 for ( var i = 0; i < this.tracks.length; i ++ ) {
11877 var track = this.tracks[i];
11878 this.duration = Math.max( track.keys[ track.keys.length - 1 ].time );
11891 THREE.AnimationClip.prototype = {
11893 constructor: THREE.AnimationClip,
11895 getAt:
function( clipTime ) {
11897 clipTime = Math.max( 0, Math.min( clipTime,
this.duration ) );
11899 for ( var i = 0; i < this.tracks.length; i ++ ) {
11901 var track = this.tracks[ i ];
11903 this.results[ i ] = track.getAt( clipTime );
11907 return this.results;
11912 for ( var i = 0; i < this.tracks.length; i ++ ) {
11914 this.tracks[ i ].trim( 0, this.duration );
11922 optimize:
function() {
11924 for ( var i = 0; i < this.tracks.length; i ++ ) {
11926 this.tracks[ i ].optimize();
11937 THREE.AnimationClip.CreateFromMorphTargetSequence =
function( name, morphTargetSequence, fps ) {
11940 var numMorphTargets = morphTargetSequence.length;
11943 for ( var i = 0; i < numMorphTargets; i ++ ) {
11947 keys.push( { time: ( i + numMorphTargets - 1 ) % numMorphTargets, value: 0 } );
11948 keys.push( { time: i, value: 1 } );
11949 keys.push( { time: ( i + 1 ) % numMorphTargets, value: 0 } );
11951 keys.sort( THREE.KeyframeTrack.keyComparer );
11954 if ( keys[0].time === 0 ) {
11956 time: numMorphTargets,
11957 value: keys[0].value
11961 tracks.push(
new THREE.NumberKeyframeTrack(
'.morphTargetInfluences[' + morphTargetSequence[i].name +
']', keys ).scale( 1.0 / fps ) );
11964 return new THREE.AnimationClip( name, -1, tracks );
11968 THREE.AnimationClip.findByName =
function( clipArray, name ) {
11970 for ( var i = 0; i < clipArray.length; i ++ ) {
11972 if ( clipArray[i].name === name ) {
11974 return clipArray[i];
11983 THREE.AnimationClip.CreateClipsFromMorphTargetSequences =
function( morphTargets, fps ) {
11985 var animationToMorphTargets = {};
11988 var pattern = /^([\w-]*?)([\d]+)$/;
11991 for ( var i = 0, il = morphTargets.length; i < il; i ++ ) {
11993 var morphTarget = morphTargets[ i ];
11994 var parts = morphTarget.name.match( pattern );
11996 if ( parts && parts.length > 1 ) {
11998 var name = parts[ 1 ];
12000 var animationMorphTargets = animationToMorphTargets[ name ];
12001 if ( ! animationMorphTargets ) {
12002 animationToMorphTargets[ name ] = animationMorphTargets = [];
12005 animationMorphTargets.push( morphTarget );
12013 for ( var name in animationToMorphTargets ) {
12015 clips.push( THREE.AnimationClip.CreateFromMorphTargetSequence( name, animationToMorphTargets[ name ], fps ) );
12023 THREE.AnimationClip.parse =
function( json ) {
12027 for ( var i = 0; i < json.tracks.length; i ++ ) {
12029 tracks.push( THREE.KeyframeTrack.parse( json.tracks[i] ).scale( 1.0 / json.fps ) );
12033 return new THREE.AnimationClip( json.name, json.duration, tracks );
12039 THREE.AnimationClip.parseAnimation =
function( animation, bones, nodeName ) {
12041 if ( ! animation ) {
12042 console.error(
" no animation in JSONLoader data" );
12046 var convertTrack =
function( trackName, animationKeys, propertyName, trackType, animationKeyToValueFunc ) {
12050 for ( var k = 0; k < animationKeys.length; k ++ ) {
12052 var animationKey = animationKeys[k];
12054 if ( animationKey[propertyName] !== undefined ) {
12056 keys.push( { time: animationKey.time, value: animationKeyToValueFunc( animationKey ) } );
12062 if ( keys.length > 0 ) {
12064 return new trackType( trackName, keys );
12074 var clipName = animation.name ||
'default';
12075 var duration = animation.length || -1;
12076 var fps = animation.fps || 30;
12078 var hierarchyTracks = animation.hierarchy || [];
12080 for ( var h = 0; h < hierarchyTracks.length; h ++ ) {
12082 var animationKeys = hierarchyTracks[ h ].keys;
12085 if ( ! animationKeys || animationKeys.length == 0 ) {
12090 if ( animationKeys[0].morphTargets ) {
12093 var morphTargetNames = {};
12094 for ( var k = 0; k < animationKeys.length; k ++ ) {
12096 if ( animationKeys[k].morphTargets ) {
12097 for ( var m = 0; m < animationKeys[k].morphTargets.length; m ++ ) {
12099 morphTargetNames[ animationKeys[k].morphTargets[m] ] = -1;
12106 for ( var morphTargetName in morphTargetNames ) {
12110 for ( var m = 0; m < animationKeys[k].morphTargets.length; m ++ ) {
12112 var animationKey = animationKeys[k];
12115 time: animationKey.time,
12116 value: (( animationKey.morphTarget === morphTargetName ) ? 1 : 0 )
12121 tracks.push(
new THREE.NumberKeyframeTrack( nodeName +
'.morphTargetInfluence[' + morphTargetName +
']', keys ) );
12125 duration = morphTargetNames.length * ( fps || 1.0 );
12129 var boneName = nodeName +
'.bones[' + bones[ h ].name +
']';
12132 var positionTrack = convertTrack( boneName +
'.position', animationKeys,
'pos', THREE.VectorKeyframeTrack,
function( animationKey ) {
12133 return new THREE.Vector3().fromArray( animationKey.pos )
12136 if ( positionTrack ) tracks.push( positionTrack );
12139 var quaternionTrack = convertTrack( boneName +
'.quaternion', animationKeys,
'rot', THREE.QuaternionKeyframeTrack,
function( animationKey ) {
12140 if ( animationKey.rot.slerp ) {
12141 return animationKey.rot.clone();
12143 return new THREE.Quaternion().fromArray( animationKey.rot );
12147 if ( quaternionTrack ) tracks.push( quaternionTrack );
12150 var scaleTrack = convertTrack( boneName +
'.scale', animationKeys,
'scl', THREE.VectorKeyframeTrack,
function( animationKey ) {
12151 return new THREE.Vector3().fromArray( animationKey.scl )
12154 if ( scaleTrack ) tracks.push( scaleTrack );
12159 if ( tracks.length === 0 ) {
12165 var clip =
new THREE.AnimationClip( clipName, duration, tracks );
12182 THREE.AnimationMixer =
function( root ) {
12186 this.timeScale = 1.0;
12188 this.propertyBindingMap = {};
12192 THREE.AnimationMixer.prototype = {
12194 constructor: THREE.AnimationMixer,
12196 addAction:
function( action ) {
12200 this.actions.push( action );
12201 action.init( this.time );
12202 action.mixer =
this;
12204 var tracks = action.clip.tracks;
12206 var root = action.localRoot || this.root;
12208 for ( var i = 0; i < tracks.length; i ++ ) {
12210 var track = tracks[ i ];
12212 var propertyBindingKey = root.uuid +
'-' + track.name;
12213 var propertyBinding = this.propertyBindingMap[ propertyBindingKey ];
12215 if ( propertyBinding === undefined ) {
12217 propertyBinding =
new THREE.PropertyBinding( root, track.name );
12218 this.propertyBindingMap[ propertyBindingKey ] = propertyBinding;
12223 action.propertyBindings.push( propertyBinding );
12226 propertyBinding.referenceCount += 1;
12232 removeAllActions:
function() {
12234 for ( var i = 0; i < this.actions.length; i ++ ) {
12236 this.actions[i].mixer = null;
12241 for ( var properyBindingKey in this.propertyBindingMap ) {
12243 this.propertyBindingMap[ properyBindingKey ].unbind();
12248 this.propertyBindingMap = {};
12254 removeAction:
function( action ) {
12256 var index = this.actions.indexOf( action );
12258 if ( index !== - 1 ) {
12260 this.actions.splice( index, 1 );
12261 action.mixer = null;
12267 var root = action.localRoot || this.root;
12268 var tracks = action.clip.tracks;
12270 for ( var i = 0; i < tracks.length; i ++ ) {
12272 var track = tracks[ i ];
12274 var propertyBindingKey = root.uuid +
'-' + track.name;
12275 var propertyBinding = this.propertyBindingMap[ propertyBindingKey ];
12277 propertyBinding.referenceCount -= 1;
12279 if ( propertyBinding.referenceCount <= 0 ) {
12281 propertyBinding.unbind();
12283 delete this.propertyBindingMap[ propertyBindingKey ];
12293 findActionByName:
function( name ) {
12295 for ( var i = 0; i < this.actions.length; i ++ ) {
12297 if ( this.actions[i].name === name )
return this.actions[i];
12305 play:
function( action, optionalFadeInDuration ) {
12307 action.startTime = this.time;
12308 this.addAction( action );
12314 fadeOut:
function( action, duration ) {
12318 keys.push( { time: this.time, value: 1 } );
12319 keys.push( { time: this.time + duration, value: 0 } );
12321 action.weight =
new THREE.NumberKeyframeTrack(
"weight", keys );
12327 fadeIn:
function( action, duration ) {
12331 keys.push( { time: this.time, value: 0 } );
12332 keys.push( { time: this.time + duration, value: 1 } );
12334 action.weight =
new THREE.NumberKeyframeTrack(
"weight", keys );
12340 warp:
function( action, startTimeScale, endTimeScale, duration ) {
12344 keys.push( { time: this.time, value: startTimeScale } );
12345 keys.push( { time: this.time + duration, value: endTimeScale } );
12347 action.timeScale =
new THREE.NumberKeyframeTrack(
"timeScale", keys );
12353 crossFade:
function( fadeOutAction, fadeInAction, duration, warp ) {
12355 this.fadeOut( fadeOutAction, duration );
12356 this.fadeIn( fadeInAction, duration );
12360 var startEndRatio = fadeOutAction.clip.duration / fadeInAction.clip.duration;
12361 var endStartRatio = 1.0 / startEndRatio;
12363 this.warp( fadeOutAction, 1.0, startEndRatio, duration );
12364 this.warp( fadeInAction, endStartRatio, 1.0, duration );
12372 update:
function( deltaTime ) {
12374 var mixerDeltaTime = deltaTime * this.timeScale;
12375 this.time += mixerDeltaTime;
12377 for ( var i = 0; i < this.actions.length; i ++ ) {
12379 var action = this.actions[i];
12381 var weight = action.getWeightAt( this.time );
12383 var actionTimeScale = action.getTimeScaleAt( this.time );
12384 var actionDeltaTime = mixerDeltaTime * actionTimeScale;
12386 var actionResults = action.update( actionDeltaTime );
12388 if ( action.weight <= 0 || ! action.enabled )
continue;
12390 for ( var j = 0; j < actionResults.length; j ++ ) {
12392 var name = action.clip.tracks[j].name;
12394 action.propertyBindings[ j ].accumulate( actionResults[j], weight );
12401 for ( var propertyBindingKey in this.propertyBindingMap ) {
12403 this.propertyBindingMap[ propertyBindingKey ].apply();
12413 THREE.EventDispatcher.prototype.apply( THREE.AnimationMixer.prototype );
12422 THREE.AnimationUtils = {
12424 getEqualsFunc:
function( exemplarValue ) {
12426 if ( exemplarValue.equals ) {
12427 return function equals_object( a, b ) {
12428 return a.equals( b );
12432 return function equals_primitive( a, b ) {
12433 return ( a === b );
12438 clone:
function( exemplarValue ) {
12440 var typeName = typeof exemplarValue;
12441 if ( typeName ===
"object" ) {
12442 if ( exemplarValue.clone ) {
12443 return exemplarValue.clone();
12445 console.error(
"can not figure out how to copy exemplarValue", exemplarValue );
12448 return exemplarValue;
12452 lerp:
function( a, b, alpha, interTrack ) {
12454 var lerpFunc = THREE.AnimationUtils.getLerpFunc( a, interTrack );
12456 return lerpFunc( a, b, alpha );
12460 lerp_object:
function( a, b, alpha ) {
12461 return a.lerp( b, alpha );
12464 slerp_object:
function( a, b, alpha ) {
12465 return a.slerp( b, alpha );
12468 lerp_number:
function( a, b, alpha ) {
12469 return a * ( 1 - alpha ) + b * alpha;
12472 lerp_boolean:
function( a, b, alpha ) {
12473 return ( alpha < 0.5 ) ? a : b;
12476 lerp_boolean_immediate:
function( a, b, alpha ) {
12480 lerp_string:
function( a, b, alpha ) {
12481 return ( alpha < 0.5 ) ? a : b;
12484 lerp_string_immediate:
function( a, b, alpha ) {
12489 getLerpFunc:
function( exemplarValue, interTrack ) {
12491 if ( exemplarValue === undefined || exemplarValue === null )
throw new Error(
"examplarValue is null" );
12493 var typeName = typeof exemplarValue;
12495 switch( typeName ) {
12498 if ( exemplarValue.lerp ) {
12499 return THREE.AnimationUtils.lerp_object;
12502 if ( exemplarValue.slerp ) {
12503 return THREE.AnimationUtils.slerp_object;
12508 return THREE.AnimationUtils.lerp_number;
12511 if ( interTrack ) {
12512 return THREE.AnimationUtils.lerp_boolean;
12514 return THREE.AnimationUtils.lerp_boolean_immediate;
12518 if ( interTrack ) {
12519 return THREE.AnimationUtils.lerp_string;
12521 return THREE.AnimationUtils.lerp_string_immediate;
12540 THREE.KeyframeTrack =
function ( name, keys ) {
12542 if ( name === undefined )
throw new Error(
"track name is undefined" );
12543 if ( keys === undefined || keys.length === 0 )
throw new Error(
"no keys in track named " + name );
12549 this.lastIndex = 0;
12556 THREE.KeyframeTrack.prototype = {
12558 constructor: THREE.KeyframeTrack,
12560 getAt:
function( time ) {
12564 while( ( this.lastIndex < this.keys.length ) && ( time >= this.keys[this.lastIndex].time ) ) {
12569 while( ( this.lastIndex > 0 ) && ( time < this.keys[this.lastIndex - 1].time ) ) {
12573 if ( this.lastIndex >= this.keys.length ) {
12575 this.setResult( this.keys[ this.keys.length - 1 ].value );
12577 return this.result;
12581 if ( this.lastIndex === 0 ) {
12583 this.setResult( this.keys[ 0 ].value );
12585 return this.result;
12589 var prevKey = this.keys[ this.lastIndex - 1 ];
12590 this.setResult( prevKey.value );
12593 if ( prevKey.constantToNext ) {
12595 return this.result;
12600 var currentKey = this.keys[ this.lastIndex ];
12601 var alpha = ( time - prevKey.time ) / ( currentKey.time - prevKey.time );
12602 this.result = this.lerpValues( this.result, currentKey.value, alpha );
12604 return this.result;
12609 shift:
function( timeOffset ) {
12611 if ( timeOffset !== 0.0 ) {
12613 for ( var i = 0; i < this.keys.length; i ++ ) {
12614 this.keys[i].time += timeOffset;
12624 scale:
function( timeScale ) {
12626 if ( timeScale !== 1.0 ) {
12628 for ( var i = 0; i < this.keys.length; i ++ ) {
12629 this.keys[i].time *= timeScale;
12640 trim:
function( startTime, endTime ) {
12642 var firstKeysToRemove = 0;
12643 for ( var i = 1; i < this.keys.length; i ++ ) {
12644 if ( this.keys[i] <= startTime ) {
12645 firstKeysToRemove ++;
12649 var lastKeysToRemove = 0;
12650 for ( var i = this.keys.length - 2; i > 0; i ++ ) {
12651 if ( this.keys[i] >= endTime ) {
12652 lastKeysToRemove ++;
12659 if ( ( firstKeysToRemove + lastKeysToRemove ) > 0 ) {
12660 this.keys = this.keys.splice( firstKeysToRemove, this.keys.length - lastKeysToRemove - firstKeysToRemove );;
12679 validate:
function() {
12681 var prevKey = null;
12683 if ( this.keys.length === 0 ) {
12684 console.error(
" track is empty, no keys",
this );
12688 for ( var i = 0; i < this.keys.length; i ++ ) {
12690 var currKey = this.keys[i];
12693 console.error(
" key is null in track",
this, i );
12697 if ( ( typeof currKey.time ) !==
'number' || isNaN( currKey.time ) ) {
12698 console.error(
" key.time is not a valid number",
this, i, currKey );
12702 if ( currKey.value === undefined || currKey.value === null) {
12703 console.error(
" key.value is null in track",
this, i, currKey );
12707 if ( prevKey && prevKey.time > currKey.time ) {
12708 console.error(
" key.time is less than previous key time, out of order keys",
this, i, currKey, prevKey );
12721 optimize:
function() {
12724 var prevKey = this.keys[0];
12725 newKeys.push( prevKey );
12727 var equalsFunc = THREE.AnimationUtils.getEqualsFunc( prevKey.value );
12729 for ( var i = 1; i < this.keys.length - 1; i ++ ) {
12730 var currKey = this.keys[i];
12731 var nextKey = this.keys[i+1];
12735 if ( ( prevKey.time === currKey.time ) ) {
12742 if ( this.compareValues( prevKey.value, currKey.value ) &&
this.compareValues( currKey.value, nextKey.value ) ) {
12749 prevKey.constantToNext = this.compareValues( prevKey.value, currKey.value );
12751 newKeys.push( currKey );
12754 newKeys.push( this.keys[ this.keys.length - 1 ] );
12756 this.keys = newKeys;
12764 THREE.KeyframeTrack.keyComparer =
function keyComparator(key0, key1) {
12765 return key0.time - key1.time;
12768 THREE.KeyframeTrack.parse =
function( json ) {
12770 if ( json.type === undefined )
throw new Error(
"track type undefined, can not parse" );
12772 var trackType = THREE.KeyframeTrack.GetTrackTypeForTypeName( json.type );
12774 return trackType.parse( json );
12778 THREE.KeyframeTrack.GetTrackTypeForTypeName =
function( typeName ) {
12779 switch( typeName.toLowerCase() ) {
12784 return THREE.VectorKeyframeTrack;
12787 return THREE.QuaternionKeyframeTrack;
12794 return THREE.NumberKeyframeTrack;
12798 return THREE.BooleanKeyframeTrack;
12801 return THREE.StringKeyframeTrack;
12804 throw new Error(
"Unsupported typeName: " + typeName );
12817 THREE.PropertyBinding =
function ( rootNode, trackName ) {
12819 this.rootNode = rootNode;
12820 this.trackName = trackName;
12821 this.referenceCount = 0;
12822 this.originalValue = null;
12824 var parseResults = THREE.PropertyBinding.parseTrackName( trackName );
12826 this.directoryName = parseResults.directoryName;
12827 this.nodeName = parseResults.nodeName;
12828 this.objectName = parseResults.objectName;
12829 this.objectIndex = parseResults.objectIndex;
12830 this.propertyName = parseResults.propertyName;
12831 this.propertyIndex = parseResults.propertyIndex;
12833 this.node = THREE.PropertyBinding.findNode( rootNode, this.nodeName ) || rootNode;
12835 this.cumulativeValue = null;
12836 this.cumulativeWeight = 0;
12839 THREE.PropertyBinding.prototype = {
12841 constructor: THREE.PropertyBinding,
12843 reset:
function() {
12845 this.cumulativeValue = null;
12846 this.cumulativeWeight = 0;
12850 accumulate:
function( value, weight ) {
12852 if ( ! this.isBound ) this.bind();
12854 if ( this.cumulativeWeight === 0 ) {
12856 if ( weight > 0 ) {
12858 if ( this.cumulativeValue === null ) {
12859 this.cumulativeValue = THREE.AnimationUtils.clone( value );
12861 this.cumulativeWeight = weight;
12867 var lerpAlpha = weight / ( this.cumulativeWeight + weight );
12868 this.cumulativeValue = this.lerpValue( this.cumulativeValue, value, lerpAlpha );
12869 this.cumulativeWeight += weight;
12875 unbind:
function() {
12877 if ( ! this.isBound )
return;
12879 this.setValue( this.originalValue );
12881 this.setValue = null;
12882 this.getValue = null;
12883 this.lerpValue = null;
12884 this.equalsValue = null;
12885 this.triggerDirty = null;
12886 this.isBound =
false;
12893 if ( this.isBound )
return;
12895 var targetObject = this.node;
12898 if ( ! targetObject ) {
12899 console.error(
" trying to update node for track: " + this.trackName +
" but it wasn't found." );
12903 if ( this.objectName ) {
12905 if ( this.objectName ===
"materials" ) {
12906 if ( ! targetObject.material ) {
12907 console.error(
' can not bind to material as node does not have a material',
this );
12910 if ( ! targetObject.material.materials ) {
12911 console.error(
' can not bind to material.materials as node.material does not have a materials array',
this );
12914 targetObject = targetObject.material.materials;
12915 }
else if ( this.objectName ===
"bones" ) {
12916 if ( ! targetObject.skeleton ) {
12917 console.error(
' can not bind to bones as node does not have a skeleton',
this );
12922 targetObject = targetObject.skeleton.bones;
12925 for ( var i = 0; i < targetObject.length; i ++ ) {
12926 if ( targetObject[i].name === this.objectIndex ) {
12927 this.objectIndex = i;
12933 if ( targetObject[ this.objectName ] === undefined ) {
12934 console.error(
' can not bind to objectName of node, undefined',
this );
12937 targetObject = targetObject[ this.objectName ];
12940 if ( this.objectIndex !== undefined ) {
12941 if ( targetObject[ this.objectIndex ] === undefined ) {
12942 console.error(
" trying to bind to objectIndex of objectName, but is undefined:",
this, targetObject );
12946 targetObject = targetObject[ this.objectIndex ];
12952 var nodeProperty = targetObject[ this.propertyName ];
12953 if ( ! nodeProperty ) {
12954 console.error(
" trying to update property for track: " + this.nodeName +
'.' + this.propertyName +
" but it wasn't found.", targetObject );
12959 if ( this.propertyIndex !== undefined ) {
12961 if ( this.propertyName ===
"morphTargetInfluences" ) {
12965 if ( ! targetObject.geometry ) {
12966 console.error(
' can not bind to morphTargetInfluences becasuse node does not have a geometry',
this );
12968 if ( ! targetObject.geometry.morphTargets ) {
12969 console.error(
' can not bind to morphTargetInfluences becasuse node does not have a geometry.morphTargets',
this );
12972 for ( var i = 0; i < this.node.geometry.morphTargets.length; i ++ ) {
12973 if ( targetObject.geometry.morphTargets[i].name ===
this.propertyIndex ) {
12974 this.propertyIndex = i;
12980 this.setValue =
function setValue_propertyIndexed( value ) {
12981 if ( ! this.equalsValue( nodeProperty[ this.propertyIndex ], value ) ) {
12982 nodeProperty[ this.propertyIndex ] = value;
12988 this.getValue =
function getValue_propertyIndexed() {
12989 return nodeProperty[ this.propertyIndex ];
12994 else if ( nodeProperty.copy ) {
12996 this.setValue =
function setValue_propertyObject( value ) {
12997 if ( ! this.equalsValue( nodeProperty, value ) ) {
12998 nodeProperty.copy( value );
13004 this.getValue =
function getValue_propertyObject() {
13005 return nodeProperty;
13012 this.setValue =
function setValue_property( value ) {
13013 if ( ! this.equalsValue( targetObject[ this.propertyName ], value ) ) {
13014 targetObject[ this.propertyName ] = value;
13020 this.getValue =
function getValue_property() {
13021 return targetObject[ this.propertyName ];
13027 if ( targetObject.needsUpdate !== undefined ) {
13029 this.triggerDirty =
function triggerDirty_needsUpdate() {
13030 this.node.needsUpdate =
true;
13033 }
else if ( targetObject.matrixWorldNeedsUpdate !== undefined ) {
13035 this.triggerDirty =
function triggerDirty_matrixWorldNeedsUpdate() {
13036 targetObject.matrixWorldNeedsUpdate =
true;
13041 this.originalValue = this.getValue();
13043 this.equalsValue = THREE.AnimationUtils.getEqualsFunc( this.originalValue );
13044 this.lerpValue = THREE.AnimationUtils.getLerpFunc( this.originalValue,
true );
13046 this.isBound =
true;
13050 apply:
function() {
13053 if ( ! this.isBound ) this.bind();
13056 if ( this.cumulativeWeight > 0 ) {
13059 if ( this.cumulativeWeight < 1 ) {
13061 var remainingWeight = 1 - this.cumulativeWeight;
13062 var lerpAlpha = remainingWeight / ( this.cumulativeWeight + remainingWeight );
13063 this.cumulativeValue = this.lerpValue( this.cumulativeValue, this.originalValue, lerpAlpha );
13067 var valueChanged = this.setValue( this.cumulativeValue );
13069 if ( valueChanged && this.triggerDirty ) {
13070 this.triggerDirty();
13074 this.cumulativeValue = null;
13075 this.cumulativeWeight = 0;
13083 THREE.PropertyBinding.parseTrackName =
function( trackName ) {
13096 var re = /^(([\w]+\/)*)([\w-\d]+)?(\.([\w]+)(\[([\w\d\[\]\_. ]+)\])?)?(\.([\w.]+)(\[([\w\d\[\]\_. ]+)\])?)$/;
13097 var matches = re.exec(trackName);
13100 throw new Error(
"cannot parse trackName at all: " + trackName );
13103 if (matches.index === re.lastIndex) {
13108 directoryName: matches[1],
13109 nodeName: matches[3],
13110 objectName: matches[5],
13111 objectIndex: matches[7],
13112 propertyName: matches[9],
13113 propertyIndex: matches[11]
13116 if ( results.propertyName === null || results.propertyName.length === 0 ) {
13117 throw new Error(
"can not parse propertyName from trackName: " + trackName );
13124 THREE.PropertyBinding.findNode =
function( root, nodeName ) {
13126 function searchSkeleton( skeleton ) {
13128 for ( var i = 0; i < skeleton.bones.length; i ++ ) {
13130 var bone = skeleton.bones[i];
13132 if ( bone.name === nodeName ) {
13143 function searchNodeSubtree( children ) {
13145 for ( var i = 0; i < children.length; i ++ ) {
13147 var childNode = children[i];
13149 if ( childNode.name === nodeName || childNode.uuid === nodeName ) {
13155 var result = searchNodeSubtree( childNode.children );
13157 if ( result )
return result;
13167 if ( ! nodeName || nodeName ===
"" || nodeName ===
"root" || nodeName ===
"." || nodeName === -1 || nodeName === root.name || nodeName === root.uuid ) {
13174 if ( root.skeleton ) {
13176 var bone = searchSkeleton( root.skeleton );
13186 if ( root.children ) {
13188 var subTreeNode = searchNodeSubtree( root.children );
13190 if ( subTreeNode ) {
13192 return subTreeNode;
13211 THREE.VectorKeyframeTrack =
function ( name, keys ) {
13213 THREE.KeyframeTrack.call(
this, name, keys );
13216 this.result = this.keys[0].value.clone();
13220 THREE.VectorKeyframeTrack.prototype = Object.create( THREE.KeyframeTrack.prototype );
13222 THREE.VectorKeyframeTrack.prototype.constructor = THREE.VectorKeyframeTrack;
13224 THREE.VectorKeyframeTrack.prototype.setResult =
function( value ) {
13226 this.result.copy( value );
13232 THREE.VectorKeyframeTrack.prototype.lerpValues =
function( value0, value1, alpha ) {
13234 return value0.lerp( value1, alpha );
13238 THREE.VectorKeyframeTrack.prototype.compareValues =
function( value0, value1 ) {
13240 return value0.equals( value1 );
13244 THREE.VectorKeyframeTrack.prototype.clone =
function() {
13246 var clonedKeys = [];
13248 for ( var i = 0; i < this.keys.length; i ++ ) {
13250 var key = this.keys[i];
13253 value: key.value.clone()
13257 return new THREE.VectorKeyframeTrack( this.name, clonedKeys );
13261 THREE.VectorKeyframeTrack.parse =
function( json ) {
13263 var elementCount = json.keys[0].value.length;
13264 var valueType = THREE[
'Vector' + elementCount ];
13268 for ( var i = 0; i < json.keys.length; i ++ ) {
13269 var jsonKey = json.keys[i];
13271 value:
new valueType().fromArray( jsonKey.value ),
13276 return new THREE.VectorKeyframeTrack( json.name, keys );
13290 THREE.QuaternionKeyframeTrack =
function ( name, keys ) {
13292 THREE.KeyframeTrack.call(
this, name, keys );
13295 this.result = this.keys[0].value.clone();
13299 THREE.QuaternionKeyframeTrack.prototype = Object.create( THREE.KeyframeTrack.prototype );
13301 THREE.QuaternionKeyframeTrack.prototype.constructor = THREE.QuaternionKeyframeTrack;
13303 THREE.QuaternionKeyframeTrack.prototype.setResult =
function( value ) {
13305 this.result.copy( value );
13311 THREE.QuaternionKeyframeTrack.prototype.lerpValues =
function( value0, value1, alpha ) {
13313 return value0.slerp( value1, alpha );
13317 THREE.QuaternionKeyframeTrack.prototype.compareValues =
function( value0, value1 ) {
13319 return value0.equals( value1 );
13323 THREE.QuaternionKeyframeTrack.prototype.multiply =
function( quat ) {
13325 for ( var i = 0; i < this.keys.length; i ++ ) {
13327 this.keys[i].value.multiply( quat );
13335 THREE.QuaternionKeyframeTrack.prototype.clone =
function() {
13337 var clonedKeys = [];
13339 for ( var i = 0; i < this.keys.length; i ++ ) {
13341 var key = this.keys[i];
13344 value: key.value.clone()
13348 return new THREE.QuaternionKeyframeTrack( this.name, clonedKeys );
13352 THREE.QuaternionKeyframeTrack.parse =
function( json ) {
13356 for ( var i = 0; i < json.keys.length; i ++ ) {
13357 var jsonKey = json.keys[i];
13359 value:
new THREE.Quaternion().fromArray( jsonKey.value ),
13364 return new THREE.QuaternionKeyframeTrack( json.name, keys );
13378 THREE.StringKeyframeTrack =
function ( name, keys ) {
13380 THREE.KeyframeTrack.call(
this, name, keys );
13383 this.result = this.keys[0].value;
13387 THREE.StringKeyframeTrack.prototype = Object.create( THREE.KeyframeTrack.prototype );
13389 THREE.StringKeyframeTrack.prototype.constructor = THREE.StringKeyframeTrack;
13391 THREE.StringKeyframeTrack.prototype.setResult =
function( value ) {
13393 this.result = value;
13399 THREE.StringKeyframeTrack.prototype.lerpValues =
function( value0, value1, alpha ) {
13401 return ( alpha < 1.0 ) ? value0 : value1;
13405 THREE.StringKeyframeTrack.prototype.compareValues =
function( value0, value1 ) {
13407 return ( value0 === value1 );
13411 THREE.StringKeyframeTrack.prototype.clone =
function() {
13413 var clonedKeys = [];
13415 for ( var i = 0; i < this.keys.length; i ++ ) {
13417 var key = this.keys[i];
13424 return new THREE.StringKeyframeTrack( this.name, clonedKeys );
13428 THREE.StringKeyframeTrack.parse =
function( json ) {
13430 return new THREE.StringKeyframeTrack( json.name, json.keys );
13444 THREE.BooleanKeyframeTrack =
function ( name, keys ) {
13446 THREE.KeyframeTrack.call(
this, name, keys );
13449 this.result = this.keys[0].value;
13453 THREE.BooleanKeyframeTrack.prototype = Object.create( THREE.KeyframeTrack.prototype );
13455 THREE.BooleanKeyframeTrack.prototype.constructor = THREE.BooleanKeyframeTrack;
13457 THREE.BooleanKeyframeTrack.prototype.setResult =
function( value ) {
13459 this.result = value;
13465 THREE.BooleanKeyframeTrack.prototype.lerpValues =
function( value0, value1, alpha ) {
13467 return ( alpha < 1.0 ) ? value0 : value1;
13471 THREE.BooleanKeyframeTrack.prototype.compareValues =
function( value0, value1 ) {
13473 return ( value0 === value1 );
13477 THREE.BooleanKeyframeTrack.prototype.clone =
function() {
13479 var clonedKeys = [];
13481 for ( var i = 0; i < this.keys.length; i ++ ) {
13483 var key = this.keys[i];
13490 return new THREE.BooleanKeyframeTrack( this.name, clonedKeys );
13494 THREE.BooleanKeyframeTrack.parse =
function( json ) {
13496 return new THREE.BooleanKeyframeTrack( json.name, json.keys );
13510 THREE.NumberKeyframeTrack =
function ( name, keys ) {
13512 THREE.KeyframeTrack.call(
this, name, keys );
13515 this.result = this.keys[0].value;
13519 THREE.NumberKeyframeTrack.prototype = Object.create( THREE.KeyframeTrack.prototype );
13521 THREE.NumberKeyframeTrack.prototype.constructor = THREE.NumberKeyframeTrack;
13523 THREE.NumberKeyframeTrack.prototype.setResult =
function( value ) {
13525 this.result = value;
13531 THREE.NumberKeyframeTrack.prototype.lerpValues =
function( value0, value1, alpha ) {
13533 return value0 * ( 1 - alpha ) + value1 * alpha;
13537 THREE.NumberKeyframeTrack.prototype.compareValues =
function( value0, value1 ) {
13539 return ( value0 === value1 );
13543 THREE.NumberKeyframeTrack.prototype.clone =
function() {
13545 var clonedKeys = [];
13547 for ( var i = 0; i < this.keys.length; i ++ ) {
13549 var key = this.keys[i];
13556 return new THREE.NumberKeyframeTrack( this.name, clonedKeys );
13560 THREE.NumberKeyframeTrack.parse =
function( json ) {
13562 return new THREE.NumberKeyframeTrack( json.name, json.keys );
13574 THREE.Camera =
function () {
13576 THREE.Object3D.call(
this );
13578 this.type =
'Camera';
13580 this.matrixWorldInverse =
new THREE.Matrix4();
13581 this.projectionMatrix =
new THREE.Matrix4();
13585 THREE.Camera.prototype = Object.create( THREE.Object3D.prototype );
13586 THREE.Camera.prototype.constructor = THREE.Camera;
13588 THREE.Camera.prototype.getWorldDirection =
function () {
13590 var quaternion =
new THREE.Quaternion();
13592 return function ( optionalTarget ) {
13594 var result = optionalTarget ||
new THREE.Vector3();
13596 this.getWorldQuaternion( quaternion );
13598 return result.set( 0, 0, - 1 ).applyQuaternion( quaternion );
13604 THREE.Camera.prototype.lookAt =
function () {
13608 var m1 =
new THREE.Matrix4();
13610 return function ( vector ) {
13612 m1.lookAt( this.position, vector, this.up );
13614 this.quaternion.setFromRotationMatrix( m1 );
13620 THREE.Camera.prototype.clone =
function () {
13622 return new this.constructor().copy(
this );
13626 THREE.Camera.prototype.copy =
function ( source ) {
13628 THREE.Object3D.prototype.copy.call(
this, source );
13630 this.matrixWorldInverse.copy( source.matrixWorldInverse );
13631 this.projectionMatrix.copy( source.projectionMatrix );
13646 THREE.CubeCamera =
function ( near, far, cubeResolution ) {
13648 THREE.Object3D.call(
this );
13650 this.type =
'CubeCamera';
13652 var fov = 90, aspect = 1;
13654 var cameraPX =
new THREE.PerspectiveCamera( fov, aspect, near, far );
13655 cameraPX.up.set( 0, - 1, 0 );
13656 cameraPX.lookAt(
new THREE.Vector3( 1, 0, 0 ) );
13657 this.add( cameraPX );
13659 var cameraNX =
new THREE.PerspectiveCamera( fov, aspect, near, far );
13660 cameraNX.up.set( 0, - 1, 0 );
13661 cameraNX.lookAt(
new THREE.Vector3( - 1, 0, 0 ) );
13662 this.add( cameraNX );
13664 var cameraPY =
new THREE.PerspectiveCamera( fov, aspect, near, far );
13665 cameraPY.up.set( 0, 0, 1 );
13666 cameraPY.lookAt(
new THREE.Vector3( 0, 1, 0 ) );
13667 this.add( cameraPY );
13669 var cameraNY =
new THREE.PerspectiveCamera( fov, aspect, near, far );
13670 cameraNY.up.set( 0, 0, - 1 );
13671 cameraNY.lookAt(
new THREE.Vector3( 0, - 1, 0 ) );
13672 this.add( cameraNY );
13674 var cameraPZ =
new THREE.PerspectiveCamera( fov, aspect, near, far );
13675 cameraPZ.up.set( 0, - 1, 0 );
13676 cameraPZ.lookAt(
new THREE.Vector3( 0, 0, 1 ) );
13677 this.add( cameraPZ );
13679 var cameraNZ =
new THREE.PerspectiveCamera( fov, aspect, near, far );
13680 cameraNZ.up.set( 0, - 1, 0 );
13681 cameraNZ.lookAt(
new THREE.Vector3( 0, 0, - 1 ) );
13682 this.add( cameraNZ );
13684 this.renderTarget =
new THREE.WebGLRenderTargetCube( cubeResolution, cubeResolution, { format: THREE.RGBFormat, magFilter: THREE.LinearFilter, minFilter: THREE.LinearFilter } );
13686 this.updateCubeMap =
function ( renderer, scene ) {
13688 if ( this.parent === null ) this.updateMatrixWorld();
13690 var renderTarget = this.renderTarget;
13691 var generateMipmaps = renderTarget.texture.generateMipmaps;
13693 renderTarget.texture.generateMipmaps =
false;
13695 renderTarget.activeCubeFace = 0;
13696 renderer.render( scene, cameraPX, renderTarget );
13698 renderTarget.activeCubeFace = 1;
13699 renderer.render( scene, cameraNX, renderTarget );
13701 renderTarget.activeCubeFace = 2;
13702 renderer.render( scene, cameraPY, renderTarget );
13704 renderTarget.activeCubeFace = 3;
13705 renderer.render( scene, cameraNY, renderTarget );
13707 renderTarget.activeCubeFace = 4;
13708 renderer.render( scene, cameraPZ, renderTarget );
13710 renderTarget.texture.generateMipmaps = generateMipmaps;
13712 renderTarget.activeCubeFace = 5;
13713 renderer.render( scene, cameraNZ, renderTarget );
13715 renderer.setRenderTarget( null );
13721 THREE.CubeCamera.prototype = Object.create( THREE.Object3D.prototype );
13722 THREE.CubeCamera.prototype.constructor = THREE.CubeCamera;
13730 THREE.OrthographicCamera =
function ( left, right, top, bottom, near, far ) {
13732 THREE.Camera.call(
this );
13734 this.type =
'OrthographicCamera';
13739 this.right = right;
13741 this.bottom = bottom;
13743 this.near = ( near !== undefined ) ? near : 0.1;
13744 this.far = ( far !== undefined ) ? far : 2000;
13746 this.updateProjectionMatrix();
13750 THREE.OrthographicCamera.prototype = Object.create( THREE.Camera.prototype );
13751 THREE.OrthographicCamera.prototype.constructor = THREE.OrthographicCamera;
13753 THREE.OrthographicCamera.prototype.updateProjectionMatrix =
function () {
13755 var dx = ( this.right - this.left ) / ( 2 * this.zoom );
13756 var dy = ( this.top - this.bottom ) / ( 2 * this.zoom );
13757 var cx = ( this.right + this.left ) / 2;
13758 var cy = ( this.top + this.bottom ) / 2;
13760 this.projectionMatrix.makeOrthographic( cx - dx, cx + dx, cy + dy, cy - dy, this.near, this.far );
13764 THREE.OrthographicCamera.prototype.copy =
function ( source ) {
13766 THREE.Camera.prototype.copy.call(
this, source );
13768 this.left = source.left;
13769 this.right = source.right;
13770 this.top = source.top;
13771 this.bottom = source.bottom;
13772 this.near = source.near;
13773 this.far = source.far;
13775 this.zoom = source.zoom;
13781 THREE.OrthographicCamera.prototype.toJSON =
function ( meta ) {
13783 var data = THREE.Object3D.prototype.toJSON.call(
this, meta );
13785 data.object.zoom = this.zoom;
13786 data.object.left = this.left;
13787 data.object.right = this.right;
13788 data.object.top = this.top;
13789 data.object.bottom = this.bottom;
13790 data.object.near = this.near;
13791 data.object.far = this.far;
13805 THREE.PerspectiveCamera =
function ( fov, aspect, near, far ) {
13807 THREE.Camera.call(
this );
13809 this.type =
'PerspectiveCamera';
13813 this.fov = fov !== undefined ? fov : 50;
13814 this.aspect = aspect !== undefined ? aspect : 1;
13815 this.near = near !== undefined ? near : 0.1;
13816 this.far = far !== undefined ? far : 2000;
13818 this.updateProjectionMatrix();
13822 THREE.PerspectiveCamera.prototype = Object.create( THREE.Camera.prototype );
13823 THREE.PerspectiveCamera.prototype.constructor = THREE.PerspectiveCamera;
13832 THREE.PerspectiveCamera.prototype.setLens =
function ( focalLength, frameHeight ) {
13834 if ( frameHeight === undefined ) frameHeight = 24;
13836 this.fov = 2 * THREE.Math.radToDeg( Math.atan( frameHeight / ( focalLength * 2 ) ) );
13837 this.updateProjectionMatrix();
13878 THREE.PerspectiveCamera.prototype.setViewOffset =
function ( fullWidth, fullHeight, x, y, width, height ) {
13880 this.fullWidth = fullWidth;
13881 this.fullHeight = fullHeight;
13884 this.width = width;
13885 this.height = height;
13887 this.updateProjectionMatrix();
13892 THREE.PerspectiveCamera.prototype.updateProjectionMatrix =
function () {
13894 var fov = THREE.Math.radToDeg( 2 * Math.atan( Math.tan( THREE.Math.degToRad(
this.fov ) * 0.5 ) / this.zoom ) );
13896 if ( this.fullWidth ) {
13898 var aspect = this.fullWidth / this.fullHeight;
13899 var top = Math.tan( THREE.Math.degToRad( fov * 0.5 ) ) * this.near;
13900 var bottom = - top;
13901 var left = aspect * bottom;
13902 var right = aspect * top;
13903 var width = Math.abs( right - left );
13904 var height = Math.abs( top - bottom );
13906 this.projectionMatrix.makeFrustum(
13907 left + this.x * width / this.fullWidth,
13908 left + ( this.x + this.width ) * width / this.fullWidth,
13909 top - ( this.y + this.height ) * height / this.fullHeight,
13910 top - this.y * height / this.fullHeight,
13917 this.projectionMatrix.makePerspective( fov, this.aspect, this.near, this.far );
13923 THREE.PerspectiveCamera.prototype.copy =
function ( source ) {
13925 THREE.Camera.prototype.copy.call(
this, source );
13927 this.fov = source.fov;
13928 this.aspect = source.aspect;
13929 this.near = source.near;
13930 this.far = source.far;
13932 this.zoom = source.zoom;
13938 THREE.PerspectiveCamera.prototype.toJSON =
function ( meta ) {
13940 var data = THREE.Object3D.prototype.toJSON.call(
this, meta );
13942 data.object.zoom = this.zoom;
13943 data.object.fov = this.fov;
13944 data.object.aspect = this.aspect;
13945 data.object.near = this.near;
13946 data.object.far = this.far;
13959 THREE.Light =
function ( color ) {
13961 THREE.Object3D.call(
this );
13963 this.type =
'Light';
13965 this.color =
new THREE.Color( color );
13967 this.receiveShadow = undefined;
13971 THREE.Light.prototype = Object.create( THREE.Object3D.prototype );
13972 THREE.Light.prototype.constructor = THREE.Light;
13974 Object.defineProperties( THREE.Light.prototype, {
13976 set: function ( value ) {
13977 console.warn(
'THREE.Light: .onlyShadow has been removed.' );
13981 set:
function ( value ) {
13982 this.shadow.camera.fov = value;
13985 shadowCameraLeft: {
13986 set:
function ( value ) {
13987 this.shadow.camera.left = value;
13990 shadowCameraRight: {
13991 set:
function ( value ) {
13992 this.shadow.camera.right = value;
13996 set:
function ( value ) {
13997 this.shadow.camera.top = value;
14000 shadowCameraBottom: {
14001 set:
function ( value ) {
14002 this.shadow.camera.bottom = value;
14005 shadowCameraNear: {
14006 set:
function ( value ) {
14007 this.shadow.camera.near = value;
14011 set:
function ( value ) {
14012 this.shadow.camera.far = value;
14015 shadowCameraVisible: {
14016 set:
function ( value ) {
14017 console.warn(
'THREE.Light: .shadowCameraVisible has been removed. Use new THREE.CameraHelper( light.shadow ) instead.' );
14021 set:
function ( value ) {
14022 this.shadow.bias = value;
14026 set:
function ( value ) {
14027 this.shadow.darkness = value;
14031 set:
function ( value ) {
14032 this.shadow.mapSize.width = value;
14036 set:
function ( value ) {
14037 this.shadow.mapSize.height = value;
14042 THREE.Light.prototype.copy =
function ( source ) {
14044 THREE.Object3D.prototype.copy.call(
this, source );
14046 this.color.copy( source.color );
14052 THREE.Light.prototype.toJSON =
function ( meta ) {
14054 var data = THREE.Object3D.prototype.toJSON.call(
this, meta );
14056 data.object.color = this.color.getHex();
14057 if ( this.groundColor !== undefined ) data.object.groundColor = this.groundColor.getHex();
14059 if ( this.intensity !== undefined ) data.object.intensity = this.intensity;
14060 if ( this.distance !== undefined ) data.object.distance = this.distance;
14061 if ( this.angle !== undefined ) data.object.angle = this.angle;
14062 if ( this.decay !== undefined ) data.object.decay = this.decay;
14063 if ( this.exponent !== undefined ) data.object.exponent = this.exponent;
14075 THREE.LightShadow =
function ( camera ) {
14077 this.camera = camera;
14082 this.mapSize =
new THREE.Vector2( 512, 512 );
14085 this.matrix = null;
14089 THREE.LightShadow.prototype = {
14091 constructor: THREE.LightShadow,
14093 copy:
function ( source ) {
14095 this.camera = source.camera.clone();
14097 this.bias = source.bias;
14098 this.darkness = source.darkness;
14100 this.mapSize.copy( source.mapSize );
14104 clone:
function () {
14106 return new this.constructor().copy(
this );
14118 THREE.AmbientLight =
function ( color ) {
14120 THREE.Light.call(
this, color );
14122 this.type =
'AmbientLight';
14124 this.castShadow = undefined;
14128 THREE.AmbientLight.prototype = Object.create( THREE.Light.prototype );
14129 THREE.AmbientLight.prototype.constructor = THREE.AmbientLight;
14138 THREE.DirectionalLight =
function ( color, intensity ) {
14140 THREE.Light.call(
this, color );
14142 this.type =
'DirectionalLight';
14144 this.position.set( 0, 1, 0 );
14145 this.updateMatrix();
14147 this.target =
new THREE.Object3D();
14149 this.intensity = ( intensity !== undefined ) ? intensity : 1;
14151 this.shadow =
new THREE.LightShadow(
new THREE.OrthographicCamera( - 500, 500, 500, - 500, 50, 5000 ) );
14155 THREE.DirectionalLight.prototype = Object.create( THREE.Light.prototype );
14156 THREE.DirectionalLight.prototype.constructor = THREE.DirectionalLight;
14158 THREE.DirectionalLight.prototype.copy =
function ( source ) {
14160 THREE.Light.prototype.copy.call(
this, source );
14162 this.intensity = source.intensity;
14163 this.target = source.target.clone();
14165 this.shadow = source.shadow.clone();
14177 THREE.HemisphereLight =
function ( skyColor, groundColor, intensity ) {
14179 THREE.Light.call(
this, skyColor );
14181 this.type =
'HemisphereLight';
14183 this.castShadow = undefined;
14185 this.position.set( 0, 1, 0 );
14186 this.updateMatrix();
14188 this.groundColor =
new THREE.Color( groundColor );
14189 this.intensity = ( intensity !== undefined ) ? intensity : 1;
14193 THREE.HemisphereLight.prototype = Object.create( THREE.Light.prototype );
14194 THREE.HemisphereLight.prototype.constructor = THREE.HemisphereLight;
14196 THREE.HemisphereLight.prototype.copy =
function ( source ) {
14198 THREE.Light.prototype.copy.call(
this, source );
14200 this.groundColor.copy( source.groundColor );
14201 this.intensity = source.intensity;
14214 THREE.PointLight =
function ( color, intensity, distance, decay ) {
14216 THREE.Light.call(
this, color );
14218 this.type =
'PointLight';
14220 this.intensity = ( intensity !== undefined ) ? intensity : 1;
14221 this.distance = ( distance !== undefined ) ? distance : 0;
14222 this.decay = ( decay !== undefined ) ? decay : 1;
14224 this.shadow =
new THREE.LightShadow(
new THREE.PerspectiveCamera( 90, 1, 1, 500 ) );
14228 THREE.PointLight.prototype = Object.create( THREE.Light.prototype );
14229 THREE.PointLight.prototype.constructor = THREE.PointLight;
14231 THREE.PointLight.prototype.copy =
function ( source ) {
14233 THREE.Light.prototype.copy.call(
this, source );
14235 this.intensity = source.intensity;
14236 this.distance = source.distance;
14237 this.decay = source.decay;
14239 this.shadow = source.shadow.clone();
14251 THREE.SpotLight =
function ( color, intensity, distance, angle, exponent, decay ) {
14253 THREE.Light.call(
this, color );
14255 this.type =
'SpotLight';
14257 this.position.set( 0, 1, 0 );
14258 this.updateMatrix();
14260 this.target =
new THREE.Object3D();
14262 this.intensity = ( intensity !== undefined ) ? intensity : 1;
14263 this.distance = ( distance !== undefined ) ? distance : 0;
14264 this.angle = ( angle !== undefined ) ? angle : Math.PI / 3;
14265 this.exponent = ( exponent !== undefined ) ? exponent : 10;
14266 this.decay = ( decay !== undefined ) ? decay : 1;
14268 this.shadow =
new THREE.LightShadow(
new THREE.PerspectiveCamera( 50, 1, 50, 5000 ) );
14272 THREE.SpotLight.prototype = Object.create( THREE.Light.prototype );
14273 THREE.SpotLight.prototype.constructor = THREE.SpotLight;
14275 THREE.SpotLight.prototype.copy =
function ( source ) {
14277 THREE.Light.prototype.copy.call(
this, source );
14279 this.intensity = source.intensity;
14280 this.distance = source.distance;
14281 this.angle = source.angle;
14282 this.exponent = source.exponent;
14283 this.decay = source.decay;
14285 this.target = source.target.clone();
14287 this.shadow = source.shadow.clone();
14305 add:
function ( key, file ) {
14307 if ( this.enabled ===
false )
return;
14311 this.files[ key ] = file;
14315 get:
function ( key ) {
14317 if ( this.enabled ===
false )
return;
14321 return this.files[ key ];
14325 remove:
function ( key ) {
14327 delete this.files[ key ];
14331 clear:
function () {
14345 THREE.Loader =
function () {
14347 this.onLoadStart =
function () {};
14348 this.onLoadProgress =
function () {};
14349 this.onLoadComplete =
function () {};
14353 THREE.Loader.prototype = {
14355 constructor: THREE.Loader,
14357 crossOrigin: undefined,
14359 extractUrlBase:
function ( url ) {
14361 var parts = url.split(
'/' );
14363 if ( parts.length === 1 )
return './';
14367 return parts.join(
'/' ) +
'/';
14371 initMaterials:
function ( materials, texturePath, crossOrigin ) {
14375 for ( var i = 0; i < materials.length; ++ i ) {
14377 array[ i ] = this.createMaterial( materials[ i ], texturePath, crossOrigin );
14385 createMaterial: (
function () {
14387 var color, textureLoader, materialLoader;
14389 return function ( m, texturePath, crossOrigin ) {
14391 if ( color === undefined ) color =
new THREE.Color();
14392 if ( textureLoader === undefined ) textureLoader =
new THREE.TextureLoader();
14393 if ( materialLoader === undefined ) materialLoader =
new THREE.MaterialLoader();
14399 function loadTexture( path, repeat, offset, wrap, anisotropy ) {
14401 var fullPath = texturePath + path;
14402 var loader = THREE.Loader.Handlers.get( fullPath );
14406 if ( loader !== null ) {
14408 texture = loader.load( fullPath );
14412 textureLoader.setCrossOrigin( crossOrigin );
14413 texture = textureLoader.load( fullPath );
14417 if ( repeat !== undefined ) {
14419 texture.repeat.fromArray( repeat );
14421 if ( repeat[ 0 ] !== 1 ) texture.wrapS = THREE.RepeatWrapping;
14422 if ( repeat[ 1 ] !== 1 ) texture.wrapT = THREE.RepeatWrapping;
14426 if ( offset !== undefined ) {
14428 texture.offset.fromArray( offset );
14432 if ( wrap !== undefined ) {
14434 if ( wrap[ 0 ] ===
'repeat' ) texture.wrapS = THREE.RepeatWrapping;
14435 if ( wrap[ 0 ] ===
'mirror' ) texture.wrapS = THREE.MirroredRepeatWrapping;
14437 if ( wrap[ 1 ] ===
'repeat' ) texture.wrapT = THREE.RepeatWrapping;
14438 if ( wrap[ 1 ] ===
'mirror' ) texture.wrapT = THREE.MirroredRepeatWrapping;
14442 if ( anisotropy !== undefined ) {
14444 texture.anisotropy = anisotropy;
14448 var uuid = THREE.Math.generateUUID();
14450 textures[ uuid ] = texture;
14459 uuid: THREE.Math.generateUUID(),
14460 type:
'MeshLambertMaterial'
14463 for ( var name in m ) {
14465 var value = m[ name ];
14469 json.color = value;
14472 case 'opticalDensity':
14473 case 'illumination':
14480 json.blending = THREE[ value ];
14482 case 'colorDiffuse':
14483 json.color = color.fromArray( value ).getHex();
14485 case 'colorSpecular':
14486 json.specular = color.fromArray( value ).getHex();
14488 case 'colorEmissive':
14489 json.emissive = color.fromArray( value ).getHex();
14491 case 'specularCoef':
14492 json.shininess = value;
14495 if ( value.toLowerCase() ===
'basic' ) json.type =
'MeshBasicMaterial';
14496 if ( value.toLowerCase() ===
'phong' ) json.type =
'MeshPhongMaterial';
14499 json.map = loadTexture( value, m.mapDiffuseRepeat, m.mapDiffuseOffset, m.mapDiffuseWrap, m.mapDiffuseAnisotropy );
14501 case 'mapDiffuseRepeat':
14502 case 'mapDiffuseOffset':
14503 case 'mapDiffuseWrap':
14504 case 'mapDiffuseAnisotropy':
14507 json.lightMap = loadTexture( value, m.mapLightRepeat, m.mapLightOffset, m.mapLightWrap, m.mapLightAnisotropy );
14509 case 'mapLightRepeat':
14510 case 'mapLightOffset':
14511 case 'mapLightWrap':
14512 case 'mapLightAnisotropy':
14515 json.aoMap = loadTexture( value, m.mapAORepeat, m.mapAOOffset, m.mapAOWrap, m.mapAOAnisotropy );
14517 case 'mapAORepeat':
14518 case 'mapAOOffset':
14520 case 'mapAOAnisotropy':
14523 json.bumpMap = loadTexture( value, m.mapBumpRepeat, m.mapBumpOffset, m.mapBumpWrap, m.mapBumpAnisotropy );
14525 case 'mapBumpScale':
14526 json.bumpScale = value;
14528 case 'mapBumpRepeat':
14529 case 'mapBumpOffset':
14530 case 'mapBumpWrap':
14531 case 'mapBumpAnisotropy':
14534 json.normalMap = loadTexture( value, m.mapNormalRepeat, m.mapNormalOffset, m.mapNormalWrap, m.mapNormalAnisotropy );
14536 case 'mapNormalFactor':
14537 json.normalScale = [ value, value ];
14539 case 'mapNormalRepeat':
14540 case 'mapNormalOffset':
14541 case 'mapNormalWrap':
14542 case 'mapNormalAnisotropy':
14544 case 'mapSpecular':
14545 json.specularMap = loadTexture( value, m.mapSpecularRepeat, m.mapSpecularOffset, m.mapSpecularWrap, m.mapSpecularAnisotropy );
14547 case 'mapSpecularRepeat':
14548 case 'mapSpecularOffset':
14549 case 'mapSpecularWrap':
14550 case 'mapSpecularAnisotropy':
14553 json.alphaMap = loadTexture( value, m.mapAlphaRepeat, m.mapAlphaOffset, m.mapAlphaWrap, m.mapAlphaAnisotropy );
14555 case 'mapAlphaRepeat':
14556 case 'mapAlphaOffset':
14557 case 'mapAlphaWrap':
14558 case 'mapAlphaAnisotropy':
14561 json.side = THREE.BackSide;
14563 case 'doubleSided':
14564 json.side = THREE.DoubleSide;
14566 case 'transparency':
14567 console.warn(
'THREE.Loader: transparency has been renamed to opacity' );
14568 json.opacity = value;
14571 case 'transparent':
14574 case 'transparent':
14577 json[ name ] = value;
14579 case 'vertexColors':
14580 if ( value ===
true ) json.vertexColors = THREE.VertexColors;
14581 if ( value ===
'face' ) json.vertexColors = THREE.FaceColors;
14584 console.error(
'Loader.createMaterial: Unsupported', name, value );
14590 if ( json.type !==
'MeshPhongMaterial' )
delete json.specular;
14591 if ( json.opacity < 1 ) json.transparent =
true;
14593 materialLoader.setTextures( textures );
14595 return materialLoader.parse( json );
14603 THREE.Loader.Handlers = {
14607 add:
function ( regex, loader ) {
14609 this.handlers.push( regex, loader );
14613 get:
function ( file ) {
14615 var handlers = this.handlers;
14617 for ( var i = 0, l = handlers.length; i < l; i += 2 ) {
14619 var regex = handlers[ i ];
14620 var loader = handlers[ i + 1 ];
14622 if ( regex.test( file ) ) {
14642 THREE.XHRLoader =
function ( manager ) {
14644 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
14648 THREE.XHRLoader.prototype = {
14650 constructor: THREE.XHRLoader,
14652 load:
function ( url, onLoad, onProgress, onError ) {
14656 var cached = THREE.Cache.get( url );
14658 if ( cached !== undefined ) {
14662 setTimeout(
function () {
14674 var request =
new XMLHttpRequest();
14675 request.open(
'GET', url,
true );
14677 request.addEventListener(
'load',
function ( event ) {
14679 var response =
event.target.response;
14681 THREE.Cache.add( url, response );
14683 if ( onLoad ) onLoad( response );
14685 scope.manager.itemEnd( url );
14689 if ( onProgress !== undefined ) {
14691 request.addEventListener(
'progress',
function ( event ) {
14693 onProgress( event );
14699 request.addEventListener(
'error',
function ( event ) {
14701 if ( onError ) onError( event );
14703 scope.manager.itemError( url );
14707 if ( this.crossOrigin !== undefined ) request.crossOrigin = this.crossOrigin;
14708 if ( this.responseType !== undefined ) request.responseType = this.responseType;
14709 if ( this.withCredentials !== undefined ) request.withCredentials = this.withCredentials;
14711 request.send( null );
14713 scope.manager.itemStart( url );
14719 setResponseType:
function ( value ) {
14721 this.responseType = value;
14725 setCrossOrigin:
function ( value ) {
14727 this.crossOrigin = value;
14731 setWithCredentials:
function ( value ) {
14733 this.withCredentials = value;
14745 THREE.ImageLoader =
function ( manager ) {
14747 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
14751 THREE.ImageLoader.prototype = {
14753 constructor: THREE.ImageLoader,
14755 load:
function ( url, onLoad, onProgress, onError ) {
14759 var cached = THREE.Cache.get( url );
14761 if ( cached !== undefined ) {
14763 scope.manager.itemStart( url );
14767 setTimeout(
function () {
14771 scope.manager.itemEnd( url );
14777 scope.manager.itemEnd( url );
14785 var image = document.createElement(
'img' );
14787 image.addEventListener(
'load',
function ( event ) {
14789 THREE.Cache.add( url,
this );
14791 if ( onLoad ) onLoad(
this );
14793 scope.manager.itemEnd( url );
14797 if ( onProgress !== undefined ) {
14799 image.addEventListener(
'progress',
function ( event ) {
14801 onProgress( event );
14807 image.addEventListener(
'error',
function ( event ) {
14809 if ( onError ) onError( event );
14811 scope.manager.itemError( url );
14815 if ( this.crossOrigin !== undefined ) image.crossOrigin = this.crossOrigin;
14817 scope.manager.itemStart( url );
14825 setCrossOrigin:
function ( value ) {
14827 this.crossOrigin = value;
14840 THREE.JSONLoader =
function ( manager ) {
14842 if ( typeof manager ===
'boolean' ) {
14844 console.warn(
'THREE.JSONLoader: showStatus parameter has been removed from constructor.' );
14845 manager = undefined;
14849 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
14851 this.withCredentials =
false;
14855 THREE.JSONLoader.prototype = {
14857 constructor: THREE.JSONLoader,
14861 get statusDomElement () {
14863 if ( this._statusDomElement === undefined ) {
14865 this._statusDomElement = document.createElement(
'div' );
14869 console.warn(
'THREE.JSONLoader: .statusDomElement has been removed.' );
14870 return this._statusDomElement;
14874 load:
function( url, onLoad, onProgress, onError ) {
14878 var texturePath = this.texturePath && ( typeof this.texturePath ===
"string" ) ? this.texturePath : THREE.Loader.prototype.extractUrlBase( url );
14880 var loader =
new THREE.XHRLoader( this.manager );
14881 loader.setCrossOrigin( this.crossOrigin );
14882 loader.setWithCredentials( this.withCredentials );
14883 loader.load( url,
function ( text ) {
14885 var json = JSON.parse( text );
14886 var metadata = json.metadata;
14888 if ( metadata !== undefined ) {
14890 if ( metadata.type ===
'object' ) {
14892 console.error(
'THREE.JSONLoader: ' + url +
' should be loaded with THREE.ObjectLoader instead.' );
14897 if ( metadata.type ===
'scene' ) {
14899 console.error(
'THREE.JSONLoader: ' + url +
' should be loaded with THREE.SceneLoader instead.' );
14906 var
object = scope.parse( json, texturePath );
14907 onLoad(
object.geometry,
object.materials );
14913 setCrossOrigin:
function ( value ) {
14915 this.crossOrigin = value;
14919 setTexturePath:
function ( value ) {
14921 this.texturePath = value;
14925 parse:
function ( json, texturePath ) {
14927 var geometry =
new THREE.Geometry(),
14928 scale = ( json.scale !== undefined ) ? 1.0 / json.scale : 1.0;
14930 parseModel( scale );
14933 parseMorphing( scale );
14936 geometry.computeFaceNormals();
14937 geometry.computeBoundingSphere();
14939 function parseModel( scale ) {
14941 function isBitSet( value, position ) {
14943 return value & ( 1 << position );
14951 colorIndex, normalIndex, uvIndex, materialIndex,
14957 hasFaceNormal, hasFaceVertexNormal,
14958 hasFaceColor, hasFaceVertexColor,
14960 vertex, face, faceA, faceB, hex, normal,
14964 faces = json.faces,
14965 vertices = json.vertices,
14966 normals = json.normals,
14967 colors = json.colors,
14971 if ( json.uvs !== undefined ) {
14975 for ( i = 0; i < json.uvs.length; i ++ ) {
14977 if ( json.uvs[ i ].length ) nUvLayers ++;
14981 for ( i = 0; i < nUvLayers; i ++ ) {
14983 geometry.faceVertexUvs[ i ] = [];
14990 zLength = vertices.length;
14992 while ( offset < zLength ) {
14994 vertex =
new THREE.Vector3();
14996 vertex.x = vertices[ offset ++ ] * scale;
14997 vertex.y = vertices[ offset ++ ] * scale;
14998 vertex.z = vertices[ offset ++ ] * scale;
15000 geometry.vertices.push( vertex );
15005 zLength = faces.length;
15007 while ( offset < zLength ) {
15009 type = faces[ offset ++ ];
15012 isQuad = isBitSet( type, 0 );
15013 hasMaterial = isBitSet( type, 1 );
15014 hasFaceVertexUv = isBitSet( type, 3 );
15015 hasFaceNormal = isBitSet( type, 4 );
15016 hasFaceVertexNormal = isBitSet( type, 5 );
15017 hasFaceColor = isBitSet( type, 6 );
15018 hasFaceVertexColor = isBitSet( type, 7 );
15024 faceA =
new THREE.Face3();
15025 faceA.a = faces[ offset ];
15026 faceA.b = faces[ offset + 1 ];
15027 faceA.c = faces[ offset + 3 ];
15029 faceB =
new THREE.Face3();
15030 faceB.a = faces[ offset + 1 ];
15031 faceB.b = faces[ offset + 2 ];
15032 faceB.c = faces[ offset + 3 ];
15036 if ( hasMaterial ) {
15038 materialIndex = faces[ offset ++ ];
15039 faceA.materialIndex = materialIndex;
15040 faceB.materialIndex = materialIndex;
15046 fi = geometry.faces.length;
15048 if ( hasFaceVertexUv ) {
15050 for ( i = 0; i < nUvLayers; i ++ ) {
15052 uvLayer = json.uvs[ i ];
15054 geometry.faceVertexUvs[ i ][ fi ] = [];
15055 geometry.faceVertexUvs[ i ][ fi + 1 ] = [];
15057 for ( j = 0; j < 4; j ++ ) {
15059 uvIndex = faces[ offset ++ ];
15061 u = uvLayer[ uvIndex * 2 ];
15062 v = uvLayer[ uvIndex * 2 + 1 ];
15064 uv =
new THREE.Vector2( u, v );
15066 if ( j !== 2 ) geometry.faceVertexUvs[ i ][ fi ].push( uv );
15067 if ( j !== 0 ) geometry.faceVertexUvs[ i ][ fi + 1 ].push( uv );
15075 if ( hasFaceNormal ) {
15077 normalIndex = faces[ offset ++ ] * 3;
15080 normals[ normalIndex ++ ],
15081 normals[ normalIndex ++ ],
15082 normals[ normalIndex ]
15085 faceB.normal.copy( faceA.normal );
15089 if ( hasFaceVertexNormal ) {
15091 for ( i = 0; i < 4; i ++ ) {
15093 normalIndex = faces[ offset ++ ] * 3;
15095 normal =
new THREE.Vector3(
15096 normals[ normalIndex ++ ],
15097 normals[ normalIndex ++ ],
15098 normals[ normalIndex ]
15102 if ( i !== 2 ) faceA.vertexNormals.push( normal );
15103 if ( i !== 0 ) faceB.vertexNormals.push( normal );
15110 if ( hasFaceColor ) {
15112 colorIndex = faces[ offset ++ ];
15113 hex = colors[ colorIndex ];
15115 faceA.color.setHex( hex );
15116 faceB.color.setHex( hex );
15121 if ( hasFaceVertexColor ) {
15123 for ( i = 0; i < 4; i ++ ) {
15125 colorIndex = faces[ offset ++ ];
15126 hex = colors[ colorIndex ];
15128 if ( i !== 2 ) faceA.vertexColors.push(
new THREE.Color( hex ) );
15129 if ( i !== 0 ) faceB.vertexColors.push(
new THREE.Color( hex ) );
15135 geometry.faces.push( faceA );
15136 geometry.faces.push( faceB );
15140 face =
new THREE.Face3();
15141 face.a = faces[ offset ++ ];
15142 face.b = faces[ offset ++ ];
15143 face.c = faces[ offset ++ ];
15145 if ( hasMaterial ) {
15147 materialIndex = faces[ offset ++ ];
15148 face.materialIndex = materialIndex;
15154 fi = geometry.faces.length;
15156 if ( hasFaceVertexUv ) {
15158 for ( i = 0; i < nUvLayers; i ++ ) {
15160 uvLayer = json.uvs[ i ];
15162 geometry.faceVertexUvs[ i ][ fi ] = [];
15164 for ( j = 0; j < 3; j ++ ) {
15166 uvIndex = faces[ offset ++ ];
15168 u = uvLayer[ uvIndex * 2 ];
15169 v = uvLayer[ uvIndex * 2 + 1 ];
15171 uv =
new THREE.Vector2( u, v );
15173 geometry.faceVertexUvs[ i ][ fi ].push( uv );
15181 if ( hasFaceNormal ) {
15183 normalIndex = faces[ offset ++ ] * 3;
15186 normals[ normalIndex ++ ],
15187 normals[ normalIndex ++ ],
15188 normals[ normalIndex ]
15193 if ( hasFaceVertexNormal ) {
15195 for ( i = 0; i < 3; i ++ ) {
15197 normalIndex = faces[ offset ++ ] * 3;
15199 normal =
new THREE.Vector3(
15200 normals[ normalIndex ++ ],
15201 normals[ normalIndex ++ ],
15202 normals[ normalIndex ]
15205 face.vertexNormals.push( normal );
15212 if ( hasFaceColor ) {
15214 colorIndex = faces[ offset ++ ];
15215 face.color.setHex( colors[ colorIndex ] );
15220 if ( hasFaceVertexColor ) {
15222 for ( i = 0; i < 3; i ++ ) {
15224 colorIndex = faces[ offset ++ ];
15225 face.vertexColors.push(
new THREE.Color( colors[ colorIndex ] ) );
15231 geometry.faces.push( face );
15239 function parseSkin() {
15241 var influencesPerVertex = ( json.influencesPerVertex !== undefined ) ? json.influencesPerVertex : 2;
15243 if ( json.skinWeights ) {
15245 for ( var i = 0, l = json.skinWeights.length; i < l; i += influencesPerVertex ) {
15247 var x = json.skinWeights[ i ];
15248 var y = ( influencesPerVertex > 1 ) ? json.skinWeights[ i + 1 ] : 0;
15249 var z = ( influencesPerVertex > 2 ) ? json.skinWeights[ i + 2 ] : 0;
15250 var w = ( influencesPerVertex > 3 ) ? json.skinWeights[ i + 3 ] : 0;
15252 geometry.skinWeights.push(
new THREE.Vector4( x, y, z, w ) );
15258 if ( json.skinIndices ) {
15260 for ( var i = 0, l = json.skinIndices.length; i < l; i += influencesPerVertex ) {
15262 var a = json.skinIndices[ i ];
15263 var b = ( influencesPerVertex > 1 ) ? json.skinIndices[ i + 1 ] : 0;
15264 var c = ( influencesPerVertex > 2 ) ? json.skinIndices[ i + 2 ] : 0;
15265 var d = ( influencesPerVertex > 3 ) ? json.skinIndices[ i + 3 ] : 0;
15267 geometry.skinIndices.push(
new THREE.Vector4( a, b, c, d ) );
15273 geometry.bones = json.bones;
15275 if ( geometry.bones && geometry.bones.length > 0 && ( geometry.skinWeights.length !== geometry.skinIndices.length || geometry.skinIndices.length !== geometry.vertices.length ) ) {
15277 console.warn(
'When skinning, number of vertices (' + geometry.vertices.length +
'), skinIndices (' +
15278 geometry.skinIndices.length +
'), and skinWeights (' + geometry.skinWeights.length +
') should match.' );
15284 function parseMorphing( scale ) {
15286 if ( json.morphTargets !== undefined ) {
15288 for ( var i = 0, l = json.morphTargets.length; i < l; i ++ ) {
15290 geometry.morphTargets[ i ] = {};
15291 geometry.morphTargets[ i ].name = json.morphTargets[ i ].name;
15292 geometry.morphTargets[ i ].vertices = [];
15294 var dstVertices = geometry.morphTargets[ i ].vertices;
15295 var srcVertices = json.morphTargets[ i ].vertices;
15297 for ( var v = 0, vl = srcVertices.length; v < vl; v += 3 ) {
15299 var vertex =
new THREE.Vector3();
15300 vertex.x = srcVertices[ v ] * scale;
15301 vertex.y = srcVertices[ v + 1 ] * scale;
15302 vertex.z = srcVertices[ v + 2 ] * scale;
15304 dstVertices.push( vertex );
15312 if ( json.morphColors !== undefined && json.morphColors.length > 0 ) {
15314 console.warn(
'THREE.JSONLoader: "morphColors" no longer supported. Using them as face colors.' );
15316 var faces = geometry.faces;
15317 var morphColors = json.morphColors[ 0 ].colors;
15319 for ( var i = 0, l = faces.length; i < l; i ++ ) {
15321 faces[ i ].color.fromArray( morphColors, i * 3 );
15329 function parseAnimations() {
15331 var outputAnimations = [];
15334 var animations = [];
15335 if ( json.animation !== undefined ) {
15336 animations.push( json.animation );
15338 if ( json.animations !== undefined ) {
15339 if ( json.animations.length ) {
15340 animations = animations.concat( json.animations );
15342 animations.push( json.animations );
15346 for ( var i = 0; i < animations.length; i ++ ) {
15348 var clip = THREE.AnimationClip.parseAnimation( animations[i], geometry.bones );
15349 if ( clip ) outputAnimations.push( clip );
15354 if ( geometry.morphTargets ) {
15357 var morphAnimationClips = THREE.AnimationClip.CreateClipsFromMorphTargetSequences( geometry.morphTargets, 10 );
15358 outputAnimations = outputAnimations.concat( morphAnimationClips );
15362 if ( outputAnimations.length > 0 ) geometry.animations = outputAnimations;
15366 if ( json.materials === undefined || json.materials.length === 0 ) {
15368 return { geometry: geometry };
15372 var materials = THREE.Loader.prototype.initMaterials( json.materials, texturePath,
this.crossOrigin );
15374 return { geometry: geometry, materials: materials };
15388 THREE.LoadingManager =
function ( onLoad, onProgress, onError ) {
15392 var isLoading =
false, itemsLoaded = 0, itemsTotal = 0;
15394 this.onStart = undefined;
15395 this.onLoad = onLoad;
15396 this.onProgress = onProgress;
15397 this.onError = onError;
15399 this.itemStart =
function ( url ) {
15403 if ( isLoading ===
false ) {
15405 if ( scope.onStart !== undefined ) {
15407 scope.onStart( url, itemsLoaded, itemsTotal );
15417 this.itemEnd =
function ( url ) {
15421 if ( scope.onProgress !== undefined ) {
15423 scope.onProgress( url, itemsLoaded, itemsTotal );
15427 if ( itemsLoaded === itemsTotal ) {
15431 if ( scope.onLoad !== undefined ) {
15441 this.itemError =
function ( url ) {
15443 if ( scope.onError !== undefined ) {
15445 scope.onError( url );
15453 THREE.DefaultLoadingManager =
new THREE.LoadingManager();
15461 THREE.BufferGeometryLoader =
function ( manager ) {
15463 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
15467 THREE.BufferGeometryLoader.prototype = {
15469 constructor: THREE.BufferGeometryLoader,
15471 load:
function ( url, onLoad, onProgress, onError ) {
15475 var loader =
new THREE.XHRLoader( scope.manager );
15476 loader.setCrossOrigin( this.crossOrigin );
15477 loader.load( url,
function ( text ) {
15479 onLoad( scope.parse( JSON.parse( text ) ) );
15481 }, onProgress, onError );
15485 setCrossOrigin:
function ( value ) {
15487 this.crossOrigin = value;
15491 parse:
function ( json ) {
15493 var geometry =
new THREE.BufferGeometry();
15495 var index = json.data.index;
15497 if ( index !== undefined ) {
15499 var typedArray =
new self[ index.type ]( index.array );
15500 geometry.setIndex(
new THREE.BufferAttribute( typedArray, 1 ) );
15504 var attributes = json.data.attributes;
15506 for ( var key in attributes ) {
15508 var attribute = attributes[ key ];
15509 var typedArray =
new self[ attribute.type ]( attribute.array );
15511 geometry.addAttribute( key,
new THREE.BufferAttribute( typedArray, attribute.itemSize ) );
15515 var groups = json.data.groups || json.data.drawcalls || json.data.offsets;
15517 if ( groups !== undefined ) {
15519 for ( var i = 0, n = groups.length; i !== n; ++ i ) {
15521 var group = groups[ i ];
15523 geometry.addGroup( group.start, group.count );
15529 var boundingSphere = json.data.boundingSphere;
15531 if ( boundingSphere !== undefined ) {
15533 var center =
new THREE.Vector3();
15535 if ( boundingSphere.center !== undefined ) {
15537 center.fromArray( boundingSphere.center );
15541 geometry.boundingSphere =
new THREE.Sphere( center, boundingSphere.radius );
15557 THREE.MaterialLoader =
function ( manager ) {
15559 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
15560 this.textures = {};
15564 THREE.MaterialLoader.prototype = {
15566 constructor: THREE.MaterialLoader,
15568 load:
function ( url, onLoad, onProgress, onError ) {
15572 var loader =
new THREE.XHRLoader( scope.manager );
15573 loader.setCrossOrigin( this.crossOrigin );
15574 loader.load( url,
function ( text ) {
15576 onLoad( scope.parse( JSON.parse( text ) ) );
15578 }, onProgress, onError );
15582 setCrossOrigin:
function ( value ) {
15584 this.crossOrigin = value;
15588 setTextures:
function ( value ) {
15590 this.textures = value;
15594 getTexture:
function ( name ) {
15596 var textures = this.textures;
15598 if ( textures[ name ] === undefined ) {
15600 console.warn(
'THREE.MaterialLoader: Undefined texture', name );
15604 return textures[ name ];
15608 parse:
function ( json ) {
15610 var material =
new THREE[ json.type ];
15611 material.uuid = json.uuid;
15613 if ( json.name !== undefined ) material.name = json.name;
15614 if ( json.color !== undefined ) material.color.setHex( json.color );
15615 if ( json.emissive !== undefined ) material.emissive.setHex( json.emissive );
15616 if ( json.specular !== undefined ) material.specular.setHex( json.specular );
15617 if ( json.shininess !== undefined ) material.shininess = json.shininess;
15618 if ( json.uniforms !== undefined ) material.uniforms = json.uniforms;
15619 if ( json.vertexShader !== undefined ) material.vertexShader = json.vertexShader;
15620 if ( json.fragmentShader !== undefined ) material.fragmentShader = json.fragmentShader;
15621 if ( json.vertexColors !== undefined ) material.vertexColors = json.vertexColors;
15622 if ( json.shading !== undefined ) material.shading = json.shading;
15623 if ( json.blending !== undefined ) material.blending = json.blending;
15624 if ( json.side !== undefined ) material.side = json.side;
15625 if ( json.opacity !== undefined ) material.opacity = json.opacity;
15626 if ( json.transparent !== undefined ) material.transparent = json.transparent;
15627 if ( json.alphaTest !== undefined ) material.alphaTest = json.alphaTest;
15628 if ( json.depthTest !== undefined ) material.depthTest = json.depthTest;
15629 if ( json.depthWrite !== undefined ) material.depthWrite = json.depthWrite;
15630 if ( json.wireframe !== undefined ) material.wireframe = json.wireframe;
15631 if ( json.wireframeLinewidth !== undefined ) material.wireframeLinewidth = json.wireframeLinewidth;
15634 if ( json.size !== undefined ) material.size = json.size;
15635 if ( json.sizeAttenuation !== undefined ) material.sizeAttenuation = json.sizeAttenuation;
15639 if ( json.map !== undefined ) material.map = this.getTexture( json.map );
15641 if ( json.alphaMap !== undefined ) {
15643 material.alphaMap = this.getTexture( json.alphaMap );
15644 material.transparent =
true;
15648 if ( json.bumpMap !== undefined ) material.bumpMap = this.getTexture( json.bumpMap );
15649 if ( json.bumpScale !== undefined ) material.bumpScale = json.bumpScale;
15651 if ( json.normalMap !== undefined ) material.normalMap = this.getTexture( json.normalMap );
15652 if ( json.normalScale ) material.normalScale =
new THREE.Vector2( json.normalScale, json.normalScale );
15654 if ( json.displacementMap !== undefined ) material.displacementMap = this.getTexture( json.displacementMap );
15655 if ( json.displacementScale !== undefined ) material.displacementScale = json.displacementScale;
15656 if ( json.displacementBias !== undefined ) material.displacementBias = json.displacementBias;
15658 if ( json.specularMap !== undefined ) material.specularMap = this.getTexture( json.specularMap );
15660 if ( json.envMap !== undefined ) {
15662 material.envMap = this.getTexture( json.envMap );
15663 material.combine = THREE.MultiplyOperation;
15667 if ( json.reflectivity ) material.reflectivity = json.reflectivity;
15669 if ( json.lightMap !== undefined ) material.lightMap = this.getTexture( json.lightMap );
15670 if ( json.lightMapIntensity !== undefined ) material.lightMapIntensity = json.lightMapIntensity;
15672 if ( json.aoMap !== undefined ) material.aoMap = this.getTexture( json.aoMap );
15673 if ( json.aoMapIntensity !== undefined ) material.aoMapIntensity = json.aoMapIntensity;
15677 if ( json.materials !== undefined ) {
15679 for ( var i = 0, l = json.materials.length; i < l; i ++ ) {
15681 material.materials.push( this.parse( json.materials[ i ] ) );
15699 THREE.ObjectLoader =
function ( manager ) {
15701 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
15702 this.texturePath =
'';
15706 THREE.ObjectLoader.prototype = {
15708 constructor: THREE.ObjectLoader,
15710 load:
function ( url, onLoad, onProgress, onError ) {
15712 if ( this.texturePath ===
'' ) {
15714 this.texturePath = url.substring( 0, url.lastIndexOf(
'/' ) + 1 );
15720 var loader =
new THREE.XHRLoader( scope.manager );
15721 loader.setCrossOrigin( this.crossOrigin );
15722 loader.load( url,
function ( text ) {
15724 scope.parse( JSON.parse( text ), onLoad );
15726 }, onProgress, onError );
15730 setTexturePath:
function ( value ) {
15732 this.texturePath = value;
15736 setCrossOrigin:
function ( value ) {
15738 this.crossOrigin = value;
15742 parse:
function ( json, onLoad ) {
15744 var geometries = this.parseGeometries( json.geometries );
15746 var images = this.parseImages( json.images, function () {
15748 if ( onLoad !== undefined ) onLoad(
object );
15752 var textures = this.parseTextures( json.textures, images );
15753 var materials = this.parseMaterials( json.materials, textures );
15755 var
object = this.parseObject( json.object, geometries, materials );
15757 if ( json.animations ) {
15759 object.animations = this.parseAnimations( json.animations );
15763 if ( json.images === undefined || json.images.length === 0 ) {
15765 if ( onLoad !== undefined ) onLoad(
object );
15773 parseGeometries:
function ( json ) {
15775 var geometries = {};
15777 if ( json !== undefined ) {
15779 var geometryLoader =
new THREE.JSONLoader();
15780 var bufferGeometryLoader =
new THREE.BufferGeometryLoader();
15782 for ( var i = 0, l = json.length; i < l; i ++ ) {
15785 var data = json[ i ];
15787 switch ( data.type ) {
15789 case 'PlaneGeometry':
15790 case 'PlaneBufferGeometry':
15792 geometry =
new THREE[ data.type ](
15795 data.widthSegments,
15796 data.heightSegments
15801 case 'BoxGeometry':
15802 case 'CubeGeometry':
15804 geometry =
new THREE.BoxGeometry(
15808 data.widthSegments,
15809 data.heightSegments,
15815 case 'CircleBufferGeometry':
15817 geometry =
new THREE.CircleBufferGeometry(
15826 case 'CircleGeometry':
15828 geometry =
new THREE.CircleGeometry(
15837 case 'CylinderGeometry':
15839 geometry =
new THREE.CylinderGeometry(
15843 data.radialSegments,
15844 data.heightSegments,
15852 case 'SphereGeometry':
15854 geometry =
new THREE.SphereGeometry(
15856 data.widthSegments,
15857 data.heightSegments,
15866 case 'SphereBufferGeometry':
15868 geometry =
new THREE.SphereBufferGeometry(
15870 data.widthSegments,
15871 data.heightSegments,
15880 case 'DodecahedronGeometry':
15882 geometry =
new THREE.DodecahedronGeometry(
15889 case 'IcosahedronGeometry':
15891 geometry =
new THREE.IcosahedronGeometry(
15898 case 'OctahedronGeometry':
15900 geometry =
new THREE.OctahedronGeometry(
15907 case 'TetrahedronGeometry':
15909 geometry =
new THREE.TetrahedronGeometry(
15916 case 'RingGeometry':
15918 geometry =
new THREE.RingGeometry(
15921 data.thetaSegments,
15929 case 'TorusGeometry':
15931 geometry =
new THREE.TorusGeometry(
15934 data.radialSegments,
15935 data.tubularSegments,
15941 case 'TorusKnotGeometry':
15943 geometry =
new THREE.TorusKnotGeometry(
15946 data.radialSegments,
15947 data.tubularSegments,
15955 case 'BufferGeometry':
15957 geometry = bufferGeometryLoader.parse( data );
15963 geometry = geometryLoader.parse( data.data,
this.texturePath ).geometry;
15969 console.warn(
'THREE.ObjectLoader: Unsupported geometry type "' + data.type +
'"' );
15975 geometry.uuid = data.uuid;
15977 if ( data.name !== undefined ) geometry.name = data.name;
15979 geometries[ data.uuid ] = geometry;
15989 parseMaterials:
function ( json, textures ) {
15991 var materials = {};
15993 if ( json !== undefined ) {
15995 var loader =
new THREE.MaterialLoader();
15996 loader.setTextures( textures );
15998 for ( var i = 0, l = json.length; i < l; i ++ ) {
16000 var material = loader.parse( json[ i ] );
16001 materials[ material.uuid ] = material;
16011 parseAnimations:
function ( json ) {
16013 var animations = [];
16015 for ( var i = 0; i < json.length; i ++ ) {
16017 var clip = THREE.AnimationClip.parse( json[i] );
16019 animations.push( clip );
16027 parseImages:
function ( json, onLoad ) {
16032 function loadImage( url ) {
16034 scope.manager.itemStart( url );
16036 return loader.load( url,
function () {
16038 scope.manager.itemEnd( url );
16044 if ( json !== undefined && json.length > 0 ) {
16046 var manager =
new THREE.LoadingManager( onLoad );
16048 var loader =
new THREE.ImageLoader( manager );
16049 loader.setCrossOrigin( this.crossOrigin );
16051 for ( var i = 0, l = json.length; i < l; i ++ ) {
16053 var image = json[ i ];
16054 var path = /^(\/\/)|([a-z]+:(\/\/)?)/i.test( image.url ) ? image.url : scope.texturePath + image.url;
16056 images[ image.uuid ] = loadImage( path );
16066 parseTextures:
function ( json, images ) {
16068 function parseConstant( value ) {
16070 if ( typeof( value ) ===
'number' )
return value;
16072 console.warn(
'THREE.ObjectLoader.parseTexture: Constant should be in numeric form.', value );
16074 return THREE[ value ];
16080 if ( json !== undefined ) {
16082 for ( var i = 0, l = json.length; i < l; i ++ ) {
16084 var data = json[ i ];
16086 if ( data.image === undefined ) {
16088 console.warn(
'THREE.ObjectLoader: No "image" specified for', data.uuid );
16092 if ( images[ data.image ] === undefined ) {
16094 console.warn(
'THREE.ObjectLoader: Undefined image', data.image );
16098 var texture =
new THREE.Texture( images[ data.image ] );
16099 texture.needsUpdate =
true;
16101 texture.uuid = data.uuid;
16103 if ( data.name !== undefined ) texture.name = data.name;
16104 if ( data.mapping !== undefined ) texture.mapping = parseConstant( data.mapping );
16105 if ( data.offset !== undefined ) texture.offset =
new THREE.Vector2( data.offset[ 0 ], data.offset[ 1 ] );
16106 if ( data.repeat !== undefined ) texture.repeat =
new THREE.Vector2( data.repeat[ 0 ], data.repeat[ 1 ] );
16107 if ( data.minFilter !== undefined ) texture.minFilter = parseConstant( data.minFilter );
16108 if ( data.magFilter !== undefined ) texture.magFilter = parseConstant( data.magFilter );
16109 if ( data.anisotropy !== undefined ) texture.anisotropy = data.anisotropy;
16110 if ( Array.isArray( data.wrap ) ) {
16112 texture.wrapS = parseConstant( data.wrap[ 0 ] );
16113 texture.wrapT = parseConstant( data.wrap[ 1 ] );
16117 textures[ data.uuid ] = texture;
16127 parseObject:
function () {
16129 var matrix =
new THREE.Matrix4();
16131 return function ( data, geometries, materials ) {
16135 function getGeometry( name ) {
16137 if ( geometries[ name ] === undefined ) {
16139 console.warn(
'THREE.ObjectLoader: Undefined geometry', name );
16143 return geometries[ name ];
16147 function getMaterial( name ) {
16149 if ( name === undefined )
return undefined;
16151 if ( materials[ name ] === undefined ) {
16153 console.warn(
'THREE.ObjectLoader: Undefined material', name );
16157 return materials[ name ];
16161 switch ( data.type ) {
16165 object =
new THREE.Scene();
16169 case 'PerspectiveCamera':
16171 object =
new THREE.PerspectiveCamera( data.fov, data.aspect, data.near, data.far );
16175 case 'OrthographicCamera':
16177 object =
new THREE.OrthographicCamera( data.left, data.right, data.top, data.bottom, data.near, data.far );
16181 case 'AmbientLight':
16183 object =
new THREE.AmbientLight( data.color );
16187 case 'DirectionalLight':
16189 object =
new THREE.DirectionalLight( data.color, data.intensity );
16195 object =
new THREE.PointLight( data.color, data.intensity, data.distance, data.decay );
16201 object =
new THREE.SpotLight( data.color, data.intensity, data.distance, data.angle, data.exponent, data.decay );
16205 case 'HemisphereLight':
16207 object =
new THREE.HemisphereLight( data.color, data.groundColor, data.intensity );
16213 object =
new THREE.Mesh( getGeometry( data.geometry ), getMaterial( data.material ) );
16219 object =
new THREE.LOD();
16225 object =
new THREE.Line( getGeometry( data.geometry ), getMaterial( data.material ), data.mode );
16232 object =
new THREE.Points( getGeometry( data.geometry ), getMaterial( data.material ) );
16238 object =
new THREE.Sprite( getMaterial( data.material ) );
16244 object =
new THREE.Group();
16250 object =
new THREE.Object3D();
16254 object.uuid = data.uuid;
16256 if ( data.name !== undefined )
object.name = data.name;
16257 if ( data.matrix !== undefined ) {
16259 matrix.fromArray( data.matrix );
16260 matrix.decompose(
object.position,
object.quaternion,
object.scale );
16264 if ( data.position !== undefined )
object.position.fromArray( data.position );
16265 if ( data.rotation !== undefined )
object.rotation.fromArray( data.rotation );
16266 if ( data.scale !== undefined )
object.scale.fromArray( data.scale );
16270 if ( data.castShadow !== undefined )
object.castShadow = data.castShadow;
16271 if ( data.receiveShadow !== undefined )
object.receiveShadow = data.receiveShadow;
16273 if ( data.visible !== undefined )
object.visible = data.visible;
16274 if ( data.userData !== undefined )
object.userData = data.userData;
16276 if ( data.children !== undefined ) {
16278 for ( var child in data.children ) {
16280 object.add( this.parseObject( data.children[ child ], geometries, materials ) );
16286 if ( data.type ===
'LOD' ) {
16288 var levels = data.levels;
16290 for ( var l = 0; l < levels.length; l ++ ) {
16292 var level = levels[ l ];
16293 var child =
object.getObjectByProperty(
'uuid', level.object );
16295 if ( child !== undefined ) {
16297 object.addLevel( child, level.distance );
16319 THREE.TextureLoader =
function ( manager ) {
16321 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
16325 THREE.TextureLoader.prototype = {
16327 constructor: THREE.TextureLoader,
16329 load:
function ( url, onLoad, onProgress, onError ) {
16331 var texture =
new THREE.Texture();
16333 var loader =
new THREE.ImageLoader( this.manager );
16334 loader.setCrossOrigin( this.crossOrigin );
16335 loader.load( url,
function ( image ) {
16337 texture.image = image;
16338 texture.needsUpdate =
true;
16340 if ( onLoad !== undefined ) {
16346 }, onProgress, onError );
16352 setCrossOrigin:
function ( value ) {
16354 this.crossOrigin = value;
16366 THREE.CubeTextureLoader =
function ( manager ) {
16368 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
16372 THREE.CubeTextureLoader.prototype = {
16374 constructor: THREE.CubeTextureLoader,
16376 load:
function ( urls, onLoad, onProgress, onError ) {
16378 var texture =
new THREE.CubeTexture( [] );
16380 var loader =
new THREE.ImageLoader();
16381 loader.setCrossOrigin( this.crossOrigin );
16385 function loadTexture( i ) {
16387 loader.load( urls[ i ],
function ( image ) {
16389 texture.images[ i ] = image;
16393 if ( loaded === 6 ) {
16395 texture.needsUpdate =
true;
16397 if ( onLoad ) onLoad( texture );
16401 }, undefined, onError );
16405 for ( var i = 0; i < urls.length; ++ i ) {
16415 setCrossOrigin:
function ( value ) {
16417 this.crossOrigin = value;
16431 THREE.DataTextureLoader = THREE.BinaryTextureLoader =
function ( manager ) {
16433 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
16436 this._parser = null;
16440 THREE.BinaryTextureLoader.prototype = {
16442 constructor: THREE.BinaryTextureLoader,
16444 load:
function ( url, onLoad, onProgress, onError ) {
16448 var texture =
new THREE.DataTexture();
16450 var loader =
new THREE.XHRLoader( this.manager );
16451 loader.setCrossOrigin( this.crossOrigin );
16452 loader.setResponseType(
'arraybuffer' );
16454 loader.load( url,
function ( buffer ) {
16456 var texData = scope._parser( buffer );
16458 if ( ! texData )
return;
16460 if ( undefined !== texData.image ) {
16462 texture.image = texData.image;
16464 }
else if ( undefined !== texData.data ) {
16466 texture.image.width = texData.width;
16467 texture.image.height = texData.height;
16468 texture.image.data = texData.data;
16472 texture.wrapS = undefined !== texData.wrapS ? texData.wrapS : THREE.ClampToEdgeWrapping;
16473 texture.wrapT = undefined !== texData.wrapT ? texData.wrapT : THREE.ClampToEdgeWrapping;
16475 texture.magFilter = undefined !== texData.magFilter ? texData.magFilter : THREE.LinearFilter;
16476 texture.minFilter = undefined !== texData.minFilter ? texData.minFilter : THREE.LinearMipMapLinearFilter;
16478 texture.anisotropy = undefined !== texData.anisotropy ? texData.anisotropy : 1;
16480 if ( undefined !== texData.format ) {
16482 texture.format = texData.format;
16485 if ( undefined !== texData.type ) {
16487 texture.type = texData.type;
16491 if ( undefined !== texData.mipmaps ) {
16493 texture.mipmaps = texData.mipmaps;
16497 if ( 1 === texData.mipmapCount ) {
16499 texture.minFilter = THREE.LinearFilter;
16503 texture.needsUpdate =
true;
16505 if ( onLoad ) onLoad( texture, texData );
16507 }, onProgress, onError );
16514 setCrossOrigin:
function ( value ) {
16516 this.crossOrigin = value;
16530 THREE.CompressedTextureLoader =
function ( manager ) {
16532 this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
16535 this._parser = null;
16540 THREE.CompressedTextureLoader.prototype = {
16542 constructor: THREE.CompressedTextureLoader,
16544 load:
function ( url, onLoad, onProgress, onError ) {
16550 var texture =
new THREE.CompressedTexture();
16551 texture.image = images;
16553 var loader =
new THREE.XHRLoader( this.manager );
16554 loader.setCrossOrigin( this.crossOrigin );
16555 loader.setResponseType(
'arraybuffer' );
16557 if ( Array.isArray( url ) ) {
16561 var loadTexture =
function ( i ) {
16563 loader.load( url[ i ],
function ( buffer ) {
16565 var texDatas = scope._parser( buffer,
true );
16568 width: texDatas.width,
16569 height: texDatas.height,
16570 format: texDatas.format,
16571 mipmaps: texDatas.mipmaps
16576 if ( loaded === 6 ) {
16578 if ( texDatas.mipmapCount === 1 )
16579 texture.minFilter = THREE.LinearFilter;
16581 texture.format = texDatas.format;
16582 texture.needsUpdate =
true;
16584 if ( onLoad ) onLoad( texture );
16588 }, onProgress, onError );
16592 for ( var i = 0, il = url.length; i < il; ++ i ) {
16602 loader.load( url,
function ( buffer ) {
16604 var texDatas = scope._parser( buffer,
true );
16606 if ( texDatas.isCubemap ) {
16608 var faces = texDatas.mipmaps.length / texDatas.mipmapCount;
16610 for ( var f = 0; f < faces; f ++ ) {
16612 images[ f ] = { mipmaps : [] };
16614 for ( var i = 0; i < texDatas.mipmapCount; i ++ ) {
16616 images[ f ].mipmaps.push( texDatas.mipmaps[ f * texDatas.mipmapCount + i ] );
16617 images[ f ].format = texDatas.format;
16618 images[ f ].width = texDatas.width;
16619 images[ f ].height = texDatas.height;
16627 texture.image.width = texDatas.width;
16628 texture.image.height = texDatas.height;
16629 texture.mipmaps = texDatas.mipmaps;
16633 if ( texDatas.mipmapCount === 1 ) {
16635 texture.minFilter = THREE.LinearFilter;
16639 texture.format = texDatas.format;
16640 texture.needsUpdate =
true;
16642 if ( onLoad ) onLoad( texture );
16644 }, onProgress, onError );
16652 setCrossOrigin:
function ( value ) {
16654 this.crossOrigin = value;
16667 THREE.Material =
function () {
16669 Object.defineProperty(
this,
'id', { value: THREE.MaterialIdCount ++ } );
16671 this.uuid = THREE.Math.generateUUID();
16674 this.type =
'Material';
16676 this.side = THREE.FrontSide;
16679 this.transparent =
false;
16681 this.blending = THREE.NormalBlending;
16683 this.blendSrc = THREE.SrcAlphaFactor;
16684 this.blendDst = THREE.OneMinusSrcAlphaFactor;
16685 this.blendEquation = THREE.AddEquation;
16686 this.blendSrcAlpha = null;
16687 this.blendDstAlpha = null;
16688 this.blendEquationAlpha = null;
16690 this.depthFunc = THREE.LessEqualDepth;
16691 this.depthTest =
true;
16692 this.depthWrite =
true;
16694 this.colorWrite =
true;
16696 this.precision = null;
16698 this.polygonOffset =
false;
16699 this.polygonOffsetFactor = 0;
16700 this.polygonOffsetUnits = 0;
16702 this.alphaTest = 0;
16706 this.visible =
true;
16708 this._needsUpdate =
true;
16712 THREE.Material.prototype = {
16714 constructor: THREE.Material,
16716 get needsUpdate () {
16718 return this._needsUpdate;
16722 set needsUpdate ( value ) {
16724 if ( value ===
true ) this.update();
16726 this._needsUpdate = value;
16730 setValues:
function ( values ) {
16732 if ( values === undefined )
return;
16734 for ( var key in values ) {
16736 var newValue = values[ key ];
16738 if ( newValue === undefined ) {
16740 console.warn(
"THREE.Material: '" + key +
"' parameter is undefined." );
16745 var currentValue =
this[ key ];
16747 if ( currentValue === undefined ) {
16749 console.warn(
"THREE." + this.type +
": '" + key +
"' is not a property of this material." );
16754 if ( currentValue instanceof THREE.Color ) {
16756 currentValue.set( newValue );
16758 }
else if ( currentValue instanceof THREE.Vector3 && newValue instanceof THREE.Vector3 ) {
16760 currentValue.copy( newValue );
16762 }
else if ( key ===
'overdraw' ) {
16765 this[ key ] = Number( newValue );
16769 this[ key ] = newValue;
16777 toJSON:
function ( meta ) {
16783 generator:
'Material.toJSON'
16788 data.uuid = this.uuid;
16789 data.type = this.type;
16790 if ( this.name !==
'' ) data.name = this.name;
16792 if ( this.color instanceof THREE.Color ) data.color = this.color.getHex();
16793 if ( this.emissive instanceof THREE.Color ) data.emissive = this.emissive.getHex();
16794 if ( this.specular instanceof THREE.Color ) data.specular = this.specular.getHex();
16795 if ( this.shininess !== undefined ) data.shininess = this.shininess;
16797 if ( this.map instanceof THREE.Texture ) data.map = this.map.toJSON( meta ).uuid;
16798 if ( this.alphaMap instanceof THREE.Texture ) data.alphaMap = this.alphaMap.toJSON( meta ).uuid;
16799 if ( this.lightMap instanceof THREE.Texture ) data.lightMap = this.lightMap.toJSON( meta ).uuid;
16800 if ( this.bumpMap instanceof THREE.Texture ) {
16802 data.bumpMap = this.bumpMap.toJSON( meta ).uuid;
16803 data.bumpScale = this.bumpScale;
16806 if ( this.normalMap instanceof THREE.Texture ) {
16808 data.normalMap = this.normalMap.toJSON( meta ).uuid;
16809 data.normalScale = this.normalScale;
16812 if ( this.displacementMap instanceof THREE.Texture ) {
16814 data.displacementMap = this.displacementMap.toJSON( meta ).uuid;
16815 data.displacementScale = this.displacementScale;
16816 data.displacementBias = this.displacementBias;
16819 if ( this.specularMap instanceof THREE.Texture ) data.specularMap = this.specularMap.toJSON( meta ).uuid;
16820 if ( this.envMap instanceof THREE.Texture ) {
16822 data.envMap = this.envMap.toJSON( meta ).uuid;
16823 data.reflectivity = this.reflectivity;
16827 if ( this.size !== undefined ) data.size = this.size;
16828 if ( this.sizeAttenuation !== undefined ) data.sizeAttenuation = this.sizeAttenuation;
16830 if ( this.vertexColors !== undefined && this.vertexColors !== THREE.NoColors ) data.vertexColors = this.vertexColors;
16831 if ( this.shading !== undefined && this.shading !== THREE.SmoothShading ) data.shading = this.shading;
16832 if ( this.blending !== undefined && this.blending !== THREE.NormalBlending ) data.blending = this.blending;
16833 if ( this.side !== undefined && this.side !== THREE.FrontSide ) data.side = this.side;
16835 if ( this.opacity < 1 ) data.opacity = this.opacity;
16836 if ( this.transparent ===
true ) data.transparent = this.transparent;
16837 if ( this.alphaTest > 0 ) data.alphaTest = this.alphaTest;
16838 if ( this.wireframe ===
true ) data.wireframe = this.wireframe;
16839 if ( this.wireframeLinewidth > 1 ) data.wireframeLinewidth = this.wireframeLinewidth;
16845 clone:
function () {
16847 return new this.constructor().copy(
this );
16851 copy:
function ( source ) {
16853 this.name = source.name;
16855 this.side = source.side;
16857 this.opacity = source.opacity;
16858 this.transparent = source.transparent;
16860 this.blending = source.blending;
16862 this.blendSrc = source.blendSrc;
16863 this.blendDst = source.blendDst;
16864 this.blendEquation = source.blendEquation;
16865 this.blendSrcAlpha = source.blendSrcAlpha;
16866 this.blendDstAlpha = source.blendDstAlpha;
16867 this.blendEquationAlpha = source.blendEquationAlpha;
16869 this.depthFunc = source.depthFunc;
16870 this.depthTest = source.depthTest;
16871 this.depthWrite = source.depthWrite;
16873 this.precision = source.precision;
16875 this.polygonOffset = source.polygonOffset;
16876 this.polygonOffsetFactor = source.polygonOffsetFactor;
16877 this.polygonOffsetUnits = source.polygonOffsetUnits;
16879 this.alphaTest = source.alphaTest;
16881 this.overdraw = source.overdraw;
16883 this.visible = source.visible;
16889 update:
function () {
16891 this.dispatchEvent( { type:
'update' } );
16895 dispose:
function () {
16897 this.dispatchEvent( { type:
'dispose' } );
16903 get wrapAround () {
16905 console.warn(
'THREE.' + this.type +
': .wrapAround has been removed.' );
16909 set wrapAround (
boolean ) {
16911 console.warn(
'THREE.' + this.type +
': .wrapAround has been removed.' );
16917 console.warn(
'THREE.' + this.type +
': .wrapRGB has been removed.' );
16918 return new THREE.Color();
16924 THREE.EventDispatcher.prototype.apply( THREE.Material.prototype );
16926 THREE.MaterialIdCount = 0;
16952 THREE.LineBasicMaterial =
function ( parameters ) {
16954 THREE.Material.call(
this );
16956 this.type =
'LineBasicMaterial';
16958 this.color =
new THREE.Color( 0xffffff );
16960 this.linewidth = 1;
16961 this.linecap =
'round';
16962 this.linejoin =
'round';
16964 this.vertexColors = THREE.NoColors;
16968 this.setValues( parameters );
16972 THREE.LineBasicMaterial.prototype = Object.create( THREE.Material.prototype );
16973 THREE.LineBasicMaterial.prototype.constructor = THREE.LineBasicMaterial;
16975 THREE.LineBasicMaterial.prototype.copy =
function ( source ) {
16977 THREE.Material.prototype.copy.call(
this, source );
16979 this.color.copy( source.color );
16981 this.linewidth = source.linewidth;
16982 this.linecap = source.linecap;
16983 this.linejoin = source.linejoin;
16985 this.vertexColors = source.vertexColors;
16987 this.fog = source.fog;
17018 THREE.LineDashedMaterial =
function ( parameters ) {
17020 THREE.Material.call(
this );
17022 this.type =
'LineDashedMaterial';
17024 this.color =
new THREE.Color( 0xffffff );
17026 this.linewidth = 1;
17032 this.vertexColors =
false;
17036 this.setValues( parameters );
17040 THREE.LineDashedMaterial.prototype = Object.create( THREE.Material.prototype );
17041 THREE.LineDashedMaterial.prototype.constructor = THREE.LineDashedMaterial;
17043 THREE.LineDashedMaterial.prototype.copy =
function ( source ) {
17045 THREE.Material.prototype.copy.call(
this, source );
17047 this.color.copy( source.color );
17049 this.linewidth = source.linewidth;
17051 this.scale = source.scale;
17052 this.dashSize = source.dashSize;
17053 this.gapSize = source.gapSize;
17055 this.vertexColors = source.vertexColors;
17057 this.fog = source.fog;
17103 THREE.MeshBasicMaterial =
function ( parameters ) {
17105 THREE.Material.call(
this );
17107 this.type =
'MeshBasicMaterial';
17109 this.color =
new THREE.Color( 0xffffff );
17114 this.aoMapIntensity = 1.0;
17116 this.specularMap = null;
17118 this.alphaMap = null;
17120 this.envMap = null;
17121 this.combine = THREE.MultiplyOperation;
17122 this.reflectivity = 1;
17123 this.refractionRatio = 0.98;
17127 this.shading = THREE.SmoothShading;
17129 this.wireframe =
false;
17130 this.wireframeLinewidth = 1;
17131 this.wireframeLinecap =
'round';
17132 this.wireframeLinejoin =
'round';
17134 this.vertexColors = THREE.NoColors;
17136 this.skinning =
false;
17137 this.morphTargets =
false;
17139 this.setValues( parameters );
17143 THREE.MeshBasicMaterial.prototype = Object.create( THREE.Material.prototype );
17144 THREE.MeshBasicMaterial.prototype.constructor = THREE.MeshBasicMaterial;
17146 THREE.MeshBasicMaterial.prototype.copy =
function ( source ) {
17148 THREE.Material.prototype.copy.call(
this, source );
17150 this.color.copy( source.color );
17152 this.map = source.map;
17154 this.aoMap = source.aoMap;
17155 this.aoMapIntensity = source.aoMapIntensity;
17157 this.specularMap = source.specularMap;
17159 this.alphaMap = source.alphaMap;
17161 this.envMap = source.envMap;
17162 this.combine = source.combine;
17163 this.reflectivity = source.reflectivity;
17164 this.refractionRatio = source.refractionRatio;
17166 this.fog = source.fog;
17168 this.shading = source.shading;
17170 this.wireframe = source.wireframe;
17171 this.wireframeLinewidth = source.wireframeLinewidth;
17172 this.wireframeLinecap = source.wireframeLinecap;
17173 this.wireframeLinejoin = source.wireframeLinejoin;
17175 this.vertexColors = source.vertexColors;
17177 this.skinning = source.skinning;
17178 this.morphTargets = source.morphTargets;
17223 THREE.MeshLambertMaterial =
function ( parameters ) {
17225 THREE.Material.call(
this );
17227 this.type =
'MeshLambertMaterial';
17229 this.color =
new THREE.Color( 0xffffff );
17230 this.emissive =
new THREE.Color( 0x000000 );
17234 this.specularMap = null;
17236 this.alphaMap = null;
17238 this.envMap = null;
17239 this.combine = THREE.MultiplyOperation;
17240 this.reflectivity = 1;
17241 this.refractionRatio = 0.98;
17245 this.wireframe =
false;
17246 this.wireframeLinewidth = 1;
17247 this.wireframeLinecap =
'round';
17248 this.wireframeLinejoin =
'round';
17250 this.vertexColors = THREE.NoColors;
17252 this.skinning =
false;
17253 this.morphTargets =
false;
17254 this.morphNormals =
false;
17256 this.setValues( parameters );
17260 THREE.MeshLambertMaterial.prototype = Object.create( THREE.Material.prototype );
17261 THREE.MeshLambertMaterial.prototype.constructor = THREE.MeshLambertMaterial;
17263 THREE.MeshLambertMaterial.prototype.copy =
function ( source ) {
17265 THREE.Material.prototype.copy.call(
this, source );
17267 this.color.copy( source.color );
17268 this.emissive.copy( source.emissive );
17270 this.map = source.map;
17272 this.specularMap = source.specularMap;
17274 this.alphaMap = source.alphaMap;
17276 this.envMap = source.envMap;
17277 this.combine = source.combine;
17278 this.reflectivity = source.reflectivity;
17279 this.refractionRatio = source.refractionRatio;
17281 this.fog = source.fog;
17283 this.wireframe = source.wireframe;
17284 this.wireframeLinewidth = source.wireframeLinewidth;
17285 this.wireframeLinecap = source.wireframeLinecap;
17286 this.wireframeLinejoin = source.wireframeLinejoin;
17288 this.vertexColors = source.vertexColors;
17290 this.skinning = source.skinning;
17291 this.morphTargets = source.morphTargets;
17292 this.morphNormals = source.morphNormals;
17358 THREE.MeshPhongMaterial =
function ( parameters ) {
17360 THREE.Material.call(
this );
17362 this.type =
'MeshPhongMaterial';
17364 this.color =
new THREE.Color( 0xffffff );
17365 this.emissive =
new THREE.Color( 0x000000 );
17366 this.specular =
new THREE.Color( 0x111111 );
17367 this.shininess = 30;
17369 this.metal =
false;
17373 this.lightMap = null;
17374 this.lightMapIntensity = 1.0;
17377 this.aoMapIntensity = 1.0;
17379 this.emissiveMap = null;
17381 this.bumpMap = null;
17382 this.bumpScale = 1;
17384 this.normalMap = null;
17385 this.normalScale =
new THREE.Vector2( 1, 1 );
17387 this.displacementMap = null;
17388 this.displacementScale = 1;
17389 this.displacementBias = 0;
17391 this.specularMap = null;
17393 this.alphaMap = null;
17395 this.envMap = null;
17396 this.combine = THREE.MultiplyOperation;
17397 this.reflectivity = 1;
17398 this.refractionRatio = 0.98;
17402 this.shading = THREE.SmoothShading;
17404 this.wireframe =
false;
17405 this.wireframeLinewidth = 1;
17406 this.wireframeLinecap =
'round';
17407 this.wireframeLinejoin =
'round';
17409 this.vertexColors = THREE.NoColors;
17411 this.skinning =
false;
17412 this.morphTargets =
false;
17413 this.morphNormals =
false;
17415 this.setValues( parameters );
17419 THREE.MeshPhongMaterial.prototype = Object.create( THREE.Material.prototype );
17420 THREE.MeshPhongMaterial.prototype.constructor = THREE.MeshPhongMaterial;
17422 THREE.MeshPhongMaterial.prototype.copy =
function ( source ) {
17424 THREE.Material.prototype.copy.call(
this, source );
17426 this.color.copy( source.color );
17427 this.emissive.copy( source.emissive );
17428 this.specular.copy( source.specular );
17429 this.shininess = source.shininess;
17431 this.metal = source.metal;
17433 this.map = source.map;
17435 this.lightMap = source.lightMap;
17436 this.lightMapIntensity = source.lightMapIntensity;
17438 this.aoMap = source.aoMap;
17439 this.aoMapIntensity = source.aoMapIntensity;
17441 this.emissiveMap = source.emissiveMap;
17443 this.bumpMap = source.bumpMap;
17444 this.bumpScale = source.bumpScale;
17446 this.normalMap = source.normalMap;
17447 this.normalScale.copy( source.normalScale );
17449 this.displacementMap = source.displacementMap;
17450 this.displacementScale = source.displacementScale;
17451 this.displacementBias = source.displacementBias;
17453 this.specularMap = source.specularMap;
17455 this.alphaMap = source.alphaMap;
17457 this.envMap = source.envMap;
17458 this.combine = source.combine;
17459 this.reflectivity = source.reflectivity;
17460 this.refractionRatio = source.refractionRatio;
17462 this.fog = source.fog;
17464 this.shading = source.shading;
17466 this.wireframe = source.wireframe;
17467 this.wireframeLinewidth = source.wireframeLinewidth;
17468 this.wireframeLinecap = source.wireframeLinecap;
17469 this.wireframeLinejoin = source.wireframeLinejoin;
17471 this.vertexColors = source.vertexColors;
17473 this.skinning = source.skinning;
17474 this.morphTargets = source.morphTargets;
17475 this.morphNormals = source.morphNormals;
17499 THREE.MeshDepthMaterial =
function ( parameters ) {
17501 THREE.Material.call(
this );
17503 this.type =
'MeshDepthMaterial';
17505 this.morphTargets =
false;
17506 this.wireframe =
false;
17507 this.wireframeLinewidth = 1;
17509 this.setValues( parameters );
17513 THREE.MeshDepthMaterial.prototype = Object.create( THREE.Material.prototype );
17514 THREE.MeshDepthMaterial.prototype.constructor = THREE.MeshDepthMaterial;
17516 THREE.MeshDepthMaterial.prototype.copy =
function ( source ) {
17518 THREE.Material.prototype.copy.call(
this, source );
17520 this.wireframe = source.wireframe;
17521 this.wireframeLinewidth = source.wireframeLinewidth;
17545 THREE.MeshNormalMaterial =
function ( parameters ) {
17547 THREE.Material.call(
this, parameters );
17549 this.type =
'MeshNormalMaterial';
17551 this.wireframe =
false;
17552 this.wireframeLinewidth = 1;
17554 this.morphTargets =
false;
17556 this.setValues( parameters );
17560 THREE.MeshNormalMaterial.prototype = Object.create( THREE.Material.prototype );
17561 THREE.MeshNormalMaterial.prototype.constructor = THREE.MeshNormalMaterial;
17563 THREE.MeshNormalMaterial.prototype.copy =
function ( source ) {
17565 THREE.Material.prototype.copy.call(
this, source );
17567 this.wireframe = source.wireframe;
17568 this.wireframeLinewidth = source.wireframeLinewidth;
17580 THREE.MultiMaterial =
function ( materials ) {
17582 this.uuid = THREE.Math.generateUUID();
17584 this.type =
'MultiMaterial';
17586 this.materials = materials instanceof Array ? materials : [];
17588 this.visible =
true;
17592 THREE.MultiMaterial.prototype = {
17594 constructor: THREE.MultiMaterial,
17596 toJSON:
function () {
17602 generator:
'MaterialExporter'
17609 for ( var i = 0, l = this.materials.length; i < l; i ++ ) {
17611 output.materials.push( this.materials[ i ].toJSON() );
17615 output.visible = this.visible;
17621 clone:
function () {
17623 var material =
new this.constructor();
17625 for ( var i = 0; i < this.materials.length; i ++ ) {
17627 material.materials.push( this.materials[ i ].clone() );
17631 material.visible = this.visible;
17641 THREE.MeshFaceMaterial = THREE.MultiMaterial;
17667 THREE.PointsMaterial =
function ( parameters ) {
17669 THREE.Material.call(
this );
17671 this.type =
'PointsMaterial';
17673 this.color =
new THREE.Color( 0xffffff );
17678 this.sizeAttenuation =
true;
17680 this.vertexColors = THREE.NoColors;
17684 this.setValues( parameters );
17688 THREE.PointsMaterial.prototype = Object.create( THREE.Material.prototype );
17689 THREE.PointsMaterial.prototype.constructor = THREE.PointsMaterial;
17691 THREE.PointsMaterial.prototype.copy =
function ( source ) {
17693 THREE.Material.prototype.copy.call(
this, source );
17695 this.color.copy( source.color );
17697 this.map = source.map;
17699 this.size = source.size;
17700 this.sizeAttenuation = source.sizeAttenuation;
17702 this.vertexColors = source.vertexColors;
17704 this.fog = source.fog;
17712 THREE.PointCloudMaterial =
function ( parameters ) {
17714 console.warn(
'THREE.PointCloudMaterial has been renamed to THREE.PointsMaterial.' );
17715 return new THREE.PointsMaterial( parameters );
17719 THREE.ParticleBasicMaterial =
function ( parameters ) {
17721 console.warn(
'THREE.ParticleBasicMaterial has been renamed to THREE.PointsMaterial.' );
17722 return new THREE.PointsMaterial( parameters );
17726 THREE.ParticleSystemMaterial =
function ( parameters ) {
17728 console.warn(
'THREE.ParticleSystemMaterial has been renamed to THREE.PointsMaterial.' );
17729 return new THREE.PointsMaterial( parameters );
17765 THREE.ShaderMaterial =
function ( parameters ) {
17767 THREE.Material.call(
this );
17769 this.type =
'ShaderMaterial';
17772 this.uniforms = {};
17774 this.vertexShader =
'void main() {\n\tgl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );\n}';
17775 this.fragmentShader =
'void main() {\n\tgl_FragColor = vec4( 1.0, 0.0, 0.0, 1.0 );\n}';
17777 this.shading = THREE.SmoothShading;
17779 this.linewidth = 1;
17781 this.wireframe =
false;
17782 this.wireframeLinewidth = 1;
17786 this.lights =
false;
17788 this.vertexColors = THREE.NoColors;
17790 this.skinning =
false;
17792 this.morphTargets =
false;
17793 this.morphNormals =
false;
17795 this.derivatives =
false;
17799 this.defaultAttributeValues = {
17800 'color': [ 1, 1, 1 ],
17805 this.index0AttributeName = undefined;
17807 if ( parameters !== undefined ) {
17809 if ( parameters.attributes !== undefined ) {
17811 console.error(
'THREE.ShaderMaterial: attributes should now be defined in THREE.BufferGeometry instead.' );
17815 this.setValues( parameters );
17821 THREE.ShaderMaterial.prototype = Object.create( THREE.Material.prototype );
17822 THREE.ShaderMaterial.prototype.constructor = THREE.ShaderMaterial;
17824 THREE.ShaderMaterial.prototype.copy =
function ( source ) {
17826 THREE.Material.prototype.copy.call(
this, source );
17828 this.fragmentShader = source.fragmentShader;
17829 this.vertexShader = source.vertexShader;
17831 this.uniforms = THREE.UniformsUtils.clone( source.uniforms );
17833 this.attributes = source.attributes;
17834 this.defines = source.defines;
17836 this.shading = source.shading;
17838 this.wireframe = source.wireframe;
17839 this.wireframeLinewidth = source.wireframeLinewidth;
17841 this.fog = source.fog;
17843 this.lights = source.lights;
17845 this.vertexColors = source.vertexColors;
17847 this.skinning = source.skinning;
17849 this.morphTargets = source.morphTargets;
17850 this.morphNormals = source.morphNormals;
17852 this.derivatives = source.derivatives;
17858 THREE.ShaderMaterial.prototype.toJSON =
function ( meta ) {
17860 var data = THREE.Material.prototype.toJSON.call(
this, meta );
17862 data.uniforms = this.uniforms;
17863 data.attributes = this.attributes;
17864 data.vertexShader = this.vertexShader;
17865 data.fragmentShader = this.fragmentShader;
17877 THREE.RawShaderMaterial =
function ( parameters ) {
17879 THREE.ShaderMaterial.call(
this, parameters );
17881 this.type =
'RawShaderMaterial';
17885 THREE.RawShaderMaterial.prototype = Object.create( THREE.ShaderMaterial.prototype );
17886 THREE.RawShaderMaterial.prototype.constructor = THREE.RawShaderMaterial;
17908 THREE.SpriteMaterial =
function ( parameters ) {
17910 THREE.Material.call(
this );
17912 this.type =
'SpriteMaterial';
17914 this.color =
new THREE.Color( 0xffffff );
17923 this.setValues( parameters );
17927 THREE.SpriteMaterial.prototype = Object.create( THREE.Material.prototype );
17928 THREE.SpriteMaterial.prototype.constructor = THREE.SpriteMaterial;
17930 THREE.SpriteMaterial.prototype.copy =
function ( source ) {
17932 THREE.Material.prototype.copy.call(
this, source );
17934 this.color.copy( source.color );
17935 this.map = source.map;
17937 this.rotation = source.rotation;
17939 this.fog = source.fog;
17953 THREE.Texture =
function ( image, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy ) {
17955 Object.defineProperty(
this,
'id', { value: THREE.TextureIdCount ++ } );
17957 this.uuid = THREE.Math.generateUUID();
17960 this.sourceFile =
'';
17962 this.image = image !== undefined ? image : THREE.Texture.DEFAULT_IMAGE;
17965 this.mapping = mapping !== undefined ? mapping : THREE.Texture.DEFAULT_MAPPING;
17967 this.wrapS = wrapS !== undefined ? wrapS : THREE.ClampToEdgeWrapping;
17968 this.wrapT = wrapT !== undefined ? wrapT : THREE.ClampToEdgeWrapping;
17970 this.magFilter = magFilter !== undefined ? magFilter : THREE.LinearFilter;
17971 this.minFilter = minFilter !== undefined ? minFilter : THREE.LinearMipMapLinearFilter;
17973 this.anisotropy = anisotropy !== undefined ? anisotropy : 1;
17975 this.format = format !== undefined ? format : THREE.RGBAFormat;
17976 this.type = type !== undefined ? type : THREE.UnsignedByteType;
17978 this.offset =
new THREE.Vector2( 0, 0 );
17979 this.repeat =
new THREE.Vector2( 1, 1 );
17981 this.generateMipmaps =
true;
17982 this.premultiplyAlpha =
false;
17984 this.unpackAlignment = 4;
17987 this.onUpdate = null;
17991 THREE.Texture.DEFAULT_IMAGE = undefined;
17992 THREE.Texture.DEFAULT_MAPPING = THREE.UVMapping;
17994 THREE.Texture.prototype = {
17996 constructor: THREE.Texture,
17998 set needsUpdate ( value ) {
18000 if ( value ===
true ) this.version ++;
18004 clone:
function () {
18006 return new this.constructor().copy(
this );
18010 copy:
function ( source ) {
18012 this.image = source.image;
18013 this.mipmaps = source.mipmaps.slice( 0 );
18015 this.mapping = source.mapping;
18017 this.wrapS = source.wrapS;
18018 this.wrapT = source.wrapT;
18020 this.magFilter = source.magFilter;
18021 this.minFilter = source.minFilter;
18023 this.anisotropy = source.anisotropy;
18025 this.format = source.format;
18026 this.type = source.type;
18028 this.offset.copy( source.offset );
18029 this.repeat.copy( source.repeat );
18031 this.generateMipmaps = source.generateMipmaps;
18032 this.premultiplyAlpha = source.premultiplyAlpha;
18033 this.flipY = source.flipY;
18034 this.unpackAlignment = source.unpackAlignment;
18040 toJSON:
function ( meta ) {
18042 if ( meta.textures[
this.uuid ] !== undefined ) {
18044 return meta.textures[ this.uuid ];
18048 function getDataURL( image ) {
18052 if ( image.toDataURL !== undefined ) {
18058 canvas = document.createElement(
'canvas' );
18059 canvas.width = image.width;
18060 canvas.height = image.height;
18062 canvas.getContext(
'2d' ).drawImage( image, 0, 0, image.width, image.height );
18066 if ( canvas.width > 2048 || canvas.height > 2048 ) {
18068 return canvas.toDataURL(
'image/jpeg', 0.6 );
18072 return canvas.toDataURL(
'image/png' );
18082 generator:
'Texture.toJSON'
18088 mapping: this.mapping,
18090 repeat: [ this.repeat.x, this.repeat.y ],
18091 offset: [ this.offset.x, this.offset.y ],
18092 wrap: [ this.wrapS, this.wrapT ],
18094 minFilter: this.minFilter,
18095 magFilter: this.magFilter,
18096 anisotropy: this.anisotropy
18099 if ( this.image !== undefined ) {
18103 var image = this.image;
18105 if ( image.uuid === undefined ) {
18107 image.uuid = THREE.Math.generateUUID();
18111 if ( meta.images[ image.uuid ] === undefined ) {
18113 meta.images[ image.uuid ] = {
18115 url: getDataURL( image )
18120 output.image = image.uuid;
18124 meta.textures[ this.uuid ] = output;
18130 dispose:
function () {
18132 this.dispatchEvent( { type:
'dispose' } );
18136 transformUv:
function ( uv ) {
18138 if ( this.mapping !== THREE.UVMapping )
return;
18140 uv.multiply( this.repeat );
18141 uv.add( this.offset );
18143 if ( uv.x < 0 || uv.x > 1 ) {
18145 switch ( this.wrapS ) {
18147 case THREE.RepeatWrapping:
18149 uv.x = uv.x - Math.floor( uv.x );
18152 case THREE.ClampToEdgeWrapping:
18154 uv.x = uv.x < 0 ? 0 : 1;
18157 case THREE.MirroredRepeatWrapping:
18159 if ( Math.abs( Math.floor( uv.x ) % 2 ) === 1 ) {
18161 uv.x = Math.ceil( uv.x ) - uv.x;
18165 uv.x = uv.x - Math.floor( uv.x );
18174 if ( uv.y < 0 || uv.y > 1 ) {
18176 switch ( this.wrapT ) {
18178 case THREE.RepeatWrapping:
18180 uv.y = uv.y - Math.floor( uv.y );
18183 case THREE.ClampToEdgeWrapping:
18185 uv.y = uv.y < 0 ? 0 : 1;
18188 case THREE.MirroredRepeatWrapping:
18190 if ( Math.abs( Math.floor( uv.y ) % 2 ) === 1 ) {
18192 uv.y = Math.ceil( uv.y ) - uv.y;
18196 uv.y = uv.y - Math.floor( uv.y );
18205 if ( this.flipY ) {
18215 THREE.EventDispatcher.prototype.apply( THREE.Texture.prototype );
18217 THREE.TextureIdCount = 0;
18225 THREE.CanvasTexture =
function ( canvas, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy ) {
18227 THREE.Texture.call(
this, canvas, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy );
18229 this.needsUpdate =
true;
18233 THREE.CanvasTexture.prototype = Object.create( THREE.Texture.prototype );
18234 THREE.CanvasTexture.prototype.constructor = THREE.CanvasTexture;
18242 THREE.CubeTexture =
function ( images, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy ) {
18244 mapping = mapping !== undefined ? mapping : THREE.CubeReflectionMapping;
18246 THREE.Texture.call(
this, images, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy );
18248 this.images = images;
18249 this.flipY =
false;
18253 THREE.CubeTexture.prototype = Object.create( THREE.Texture.prototype );
18254 THREE.CubeTexture.prototype.constructor = THREE.CubeTexture;
18256 THREE.CubeTexture.prototype.copy =
function ( source ) {
18258 THREE.Texture.prototype.copy.call(
this, source );
18260 this.images = source.images;
18271 THREE.CompressedTexture =
function ( mipmaps, width, height, format, type, mapping, wrapS, wrapT, magFilter, minFilter, anisotropy ) {
18273 THREE.Texture.call(
this, null, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy );
18275 this.image = { width: width, height: height };
18276 this.mipmaps = mipmaps;
18281 this.flipY =
false;
18286 this.generateMipmaps =
false;
18290 THREE.CompressedTexture.prototype = Object.create( THREE.Texture.prototype );
18291 THREE.CompressedTexture.prototype.constructor = THREE.CompressedTexture;
18299 THREE.DataTexture =
function ( data, width, height, format, type, mapping, wrapS, wrapT, magFilter, minFilter, anisotropy ) {
18301 THREE.Texture.call(
this, null, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy );
18303 this.image = { data: data, width: width, height: height };
18305 this.magFilter = magFilter !== undefined ? magFilter : THREE.NearestFilter;
18306 this.minFilter = minFilter !== undefined ? minFilter : THREE.NearestFilter;
18308 this.flipY =
false;
18309 this.generateMipmaps =
false;
18313 THREE.DataTexture.prototype = Object.create( THREE.Texture.prototype );
18314 THREE.DataTexture.prototype.constructor = THREE.DataTexture;
18322 THREE.VideoTexture =
function ( video, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy ) {
18324 THREE.Texture.call(
this, video, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy );
18326 this.generateMipmaps =
false;
18330 function update() {
18332 requestAnimationFrame( update );
18334 if ( video.readyState === video.HAVE_ENOUGH_DATA ) {
18336 scope.needsUpdate =
true;
18346 THREE.VideoTexture.prototype = Object.create( THREE.Texture.prototype );
18347 THREE.VideoTexture.prototype.constructor = THREE.VideoTexture;
18355 THREE.Group =
function () {
18357 THREE.Object3D.call(
this );
18359 this.type =
'Group';
18363 THREE.Group.prototype = Object.create( THREE.Object3D.prototype );
18364 THREE.Group.prototype.constructor = THREE.Group;
18371 THREE.Points =
function ( geometry, material ) {
18373 THREE.Object3D.call(
this );
18375 this.type =
'Points';
18377 this.geometry = geometry !== undefined ? geometry :
new THREE.Geometry();
18378 this.material = material !== undefined ? material :
new THREE.PointsMaterial( { color: Math.random() * 0xffffff } );
18382 THREE.Points.prototype = Object.create( THREE.Object3D.prototype );
18383 THREE.Points.prototype.constructor = THREE.Points;
18385 THREE.Points.prototype.raycast = (
function () {
18387 var inverseMatrix =
new THREE.Matrix4();
18388 var ray =
new THREE.Ray();
18390 return function raycast( raycaster, intersects ) {
18393 var geometry =
object.geometry;
18394 var threshold = raycaster.params.Points.threshold;
18396 inverseMatrix.getInverse( this.matrixWorld );
18397 ray.copy( raycaster.ray ).applyMatrix4( inverseMatrix );
18399 if ( geometry.boundingBox !== null ) {
18401 if ( ray.isIntersectionBox( geometry.boundingBox ) === false ) {
18409 var localThreshold = threshold / ( ( this.scale.x + this.scale.y + this.scale.z ) / 3 );
18410 var localThresholdSq = localThreshold * localThreshold;
18411 var position =
new THREE.Vector3();
18413 function testPoint( point, index ) {
18415 var rayPointDistanceSq = ray.distanceSqToPoint( point );
18417 if ( rayPointDistanceSq < localThresholdSq ) {
18419 var intersectPoint = ray.closestPointToPoint( point );
18420 intersectPoint.applyMatrix4(
object.matrixWorld );
18422 var distance = raycaster.ray.origin.distanceTo( intersectPoint );
18424 if ( distance < raycaster.near || distance > raycaster.far )
return;
18428 distance: distance,
18429 distanceToRay: Math.sqrt( rayPointDistanceSq ),
18430 point: intersectPoint.clone(),
18441 if ( geometry instanceof THREE.BufferGeometry ) {
18443 var index = geometry.index;
18444 var attributes = geometry.attributes;
18445 var positions = attributes.position.array;
18447 if ( index !== null ) {
18449 var indices = index.array;
18451 for ( var i = 0, il = indices.length; i < il; i ++ ) {
18453 var a = indices[ i ];
18455 position.fromArray( positions, a * 3 );
18457 testPoint( position, a );
18463 for ( var i = 0, l = positions.length / 3; i < l; i ++ ) {
18465 position.fromArray( positions, i * 3 );
18467 testPoint( position, i );
18475 var vertices = geometry.vertices;
18477 for ( var i = 0, l = vertices.length; i < l; i ++ ) {
18479 testPoint( vertices[ i ], i );
18489 THREE.Points.prototype.clone =
function () {
18491 return new this.constructor( this.geometry, this.material ).copy(
this );
18497 THREE.PointCloud =
function ( geometry, material ) {
18499 console.warn(
'THREE.PointCloud has been renamed to THREE.Points.' );
18500 return new THREE.Points( geometry, material );
18504 THREE.ParticleSystem =
function ( geometry, material ) {
18506 console.warn(
'THREE.ParticleSystem has been renamed to THREE.Points.' );
18507 return new THREE.Points( geometry, material );
18517 THREE.Line =
function ( geometry, material, mode ) {
18519 if ( mode === 1 ) {
18521 console.warn(
'THREE.Line: parameter THREE.LinePieces no longer supported. Created THREE.LineSegments instead.' );
18522 return new THREE.LineSegments( geometry, material );
18526 THREE.Object3D.call(
this );
18528 this.type =
'Line';
18530 this.geometry = geometry !== undefined ? geometry :
new THREE.Geometry();
18531 this.material = material !== undefined ? material :
new THREE.LineBasicMaterial( { color: Math.random() * 0xffffff } );
18535 THREE.Line.prototype = Object.create( THREE.Object3D.prototype );
18536 THREE.Line.prototype.constructor = THREE.Line;
18538 THREE.Line.prototype.raycast = (
function () {
18540 var inverseMatrix =
new THREE.Matrix4();
18541 var ray =
new THREE.Ray();
18542 var sphere =
new THREE.Sphere();
18544 return function raycast( raycaster, intersects ) {
18546 var precision = raycaster.linePrecision;
18547 var precisionSq = precision * precision;
18549 var geometry = this.geometry;
18551 if ( geometry.boundingSphere === null ) geometry.computeBoundingSphere();
18555 sphere.copy( geometry.boundingSphere );
18556 sphere.applyMatrix4( this.matrixWorld );
18558 if ( raycaster.ray.isIntersectionSphere( sphere ) === false ) {
18564 inverseMatrix.getInverse( this.matrixWorld );
18565 ray.copy( raycaster.ray ).applyMatrix4( inverseMatrix );
18567 var vStart =
new THREE.Vector3();
18568 var vEnd =
new THREE.Vector3();
18569 var interSegment =
new THREE.Vector3();
18570 var interRay =
new THREE.Vector3();
18571 var step =
this instanceof THREE.LineSegments ? 2 : 1;
18573 if ( geometry instanceof THREE.BufferGeometry ) {
18575 var index = geometry.index;
18576 var attributes = geometry.attributes;
18578 if ( index !== null ) {
18580 var indices = index.array;
18581 var positions = attributes.position.array;
18583 for ( var i = 0, l = indices.length - 1; i < l; i += step ) {
18585 var a = indices[ i ];
18586 var b = indices[ i + 1 ];
18588 vStart.fromArray( positions, a * 3 );
18589 vEnd.fromArray( positions, b * 3 );
18591 var distSq = ray.distanceSqToSegment( vStart, vEnd, interRay, interSegment );
18593 if ( distSq > precisionSq )
continue;
18595 interRay.applyMatrix4( this.matrixWorld );
18597 var distance = raycaster.ray.origin.distanceTo( interRay );
18599 if ( distance < raycaster.near || distance > raycaster.far )
continue;
18603 distance: distance,
18606 point: interSegment.clone().applyMatrix4( this.matrixWorld ),
18618 var positions = attributes.position.array;
18620 for ( var i = 0, l = positions.length / 3 - 1; i < l; i += step ) {
18622 vStart.fromArray( positions, 3 * i );
18623 vEnd.fromArray( positions, 3 * i + 3 );
18625 var distSq = ray.distanceSqToSegment( vStart, vEnd, interRay, interSegment );
18627 if ( distSq > precisionSq )
continue;
18629 interRay.applyMatrix4( this.matrixWorld );
18631 var distance = raycaster.ray.origin.distanceTo( interRay );
18633 if ( distance < raycaster.near || distance > raycaster.far )
continue;
18637 distance: distance,
18640 point: interSegment.clone().applyMatrix4( this.matrixWorld ),
18652 }
else if ( geometry instanceof THREE.Geometry ) {
18654 var vertices = geometry.vertices;
18655 var nbVertices = vertices.length;
18657 for ( var i = 0; i < nbVertices - 1; i += step ) {
18659 var distSq = ray.distanceSqToSegment( vertices[ i ], vertices[ i + 1 ], interRay, interSegment );
18661 if ( distSq > precisionSq )
continue;
18663 interRay.applyMatrix4( this.matrixWorld );
18665 var distance = raycaster.ray.origin.distanceTo( interRay );
18667 if ( distance < raycaster.near || distance > raycaster.far )
continue;
18671 distance: distance,
18674 point: interSegment.clone().applyMatrix4( this.matrixWorld ),
18690 THREE.Line.prototype.clone =
function () {
18692 return new this.constructor( this.geometry, this.material ).copy(
this );
18698 THREE.LineStrip = 0;
18699 THREE.LinePieces = 1;
18707 THREE.LineSegments =
function ( geometry, material ) {
18709 THREE.Line.call(
this, geometry, material );
18711 this.type =
'LineSegments';
18715 THREE.LineSegments.prototype = Object.create( THREE.Line.prototype );
18716 THREE.LineSegments.prototype.constructor = THREE.LineSegments;
18727 THREE.Mesh =
function ( geometry, material ) {
18729 THREE.Object3D.call(
this );
18731 this.type =
'Mesh';
18733 this.geometry = geometry !== undefined ? geometry :
new THREE.Geometry();
18734 this.material = material !== undefined ? material :
new THREE.MeshBasicMaterial( { color: Math.random() * 0xffffff } );
18736 this.updateMorphTargets();
18740 THREE.Mesh.prototype = Object.create( THREE.Object3D.prototype );
18741 THREE.Mesh.prototype.constructor = THREE.Mesh;
18743 THREE.Mesh.prototype.updateMorphTargets =
function () {
18745 if ( this.geometry.morphTargets !== undefined &&
this.geometry.morphTargets.length > 0 ) {
18747 this.morphTargetBase = - 1;
18748 this.morphTargetInfluences = [];
18749 this.morphTargetDictionary = {};
18751 for ( var m = 0, ml = this.geometry.morphTargets.length; m < ml; m ++ ) {
18753 this.morphTargetInfluences.push( 0 );
18754 this.morphTargetDictionary[ this.geometry.morphTargets[ m ].name ] = m;
18762 THREE.Mesh.prototype.getMorphTargetIndexByName =
function ( name ) {
18764 if ( this.morphTargetDictionary[ name ] !== undefined ) {
18766 return this.morphTargetDictionary[ name ];
18770 console.warn(
'THREE.Mesh.getMorphTargetIndexByName: morph target ' + name +
' does not exist. Returning 0.' );
18777 THREE.Mesh.prototype.raycast = (
function () {
18779 var inverseMatrix =
new THREE.Matrix4();
18780 var ray =
new THREE.Ray();
18781 var sphere =
new THREE.Sphere();
18783 var vA =
new THREE.Vector3();
18784 var vB =
new THREE.Vector3();
18785 var vC =
new THREE.Vector3();
18787 var tempA =
new THREE.Vector3();
18788 var tempB =
new THREE.Vector3();
18789 var tempC =
new THREE.Vector3();
18791 var uvA =
new THREE.Vector2();
18792 var uvB =
new THREE.Vector2();
18793 var uvC =
new THREE.Vector2();
18795 var barycoord =
new THREE.Vector3();
18797 var intersectionPoint =
new THREE.Vector3();
18798 var intersectionPointWorld =
new THREE.Vector3();
18800 function uvIntersection( point, p1, p2, p3, uv1, uv2, uv3 ) {
18802 THREE.Triangle.barycoordFromPoint( point, p1, p2, p3, barycoord );
18804 uv1.multiplyScalar( barycoord.x );
18805 uv2.multiplyScalar( barycoord.y );
18806 uv3.multiplyScalar( barycoord.z );
18808 uv1.add( uv2 ).add( uv3 );
18810 return uv1.clone();
18814 function checkIntersection(
object, raycaster, ray, pA, pB, pC, point ){
18817 var material =
object.material;
18819 if ( material.side === THREE.BackSide ) {
18821 intersect = ray.intersectTriangle( pC, pB, pA,
true, point );
18825 intersect = ray.intersectTriangle( pA, pB, pC, material.side !== THREE.DoubleSide, point );
18829 if ( intersect === null )
return null;
18831 intersectionPointWorld.copy( point );
18832 intersectionPointWorld.applyMatrix4(
object.matrixWorld );
18834 var distance = raycaster.ray.origin.distanceTo( intersectionPointWorld );
18836 if ( distance < raycaster.near || distance > raycaster.far )
return null;
18839 distance: distance,
18840 point: intersectionPointWorld.clone(),
18846 function checkBufferGeometryIntersection(
object, raycaster, ray, positions, uvs, a, b, c ) {
18848 vA.fromArray( positions, a * 3 );
18849 vB.fromArray( positions, b * 3 );
18850 vC.fromArray( positions, c * 3 );
18852 var intersection = checkIntersection(
object, raycaster, ray, vA, vB, vC, intersectionPoint );
18854 if ( intersection ) {
18858 uvA.fromArray( uvs, a * 2 );
18859 uvB.fromArray( uvs, b * 2 );
18860 uvC.fromArray( uvs, c * 2 );
18862 intersection.uv = uvIntersection( intersectionPoint, vA, vB, vC, uvA, uvB, uvC );
18866 intersection.face =
new THREE.Face3( a, b, c, THREE.Triangle.normal( vA, vB, vC ) );
18867 intersection.faceIndex = a;
18871 return intersection;
18875 return function raycast( raycaster, intersects ) {
18877 var geometry = this.geometry;
18878 var material = this.material;
18880 if ( material === undefined )
return;
18884 if ( geometry.boundingSphere === null ) geometry.computeBoundingSphere();
18886 var matrixWorld = this.matrixWorld;
18888 sphere.copy( geometry.boundingSphere );
18889 sphere.applyMatrix4( matrixWorld );
18891 if ( raycaster.ray.isIntersectionSphere( sphere ) === false )
return;
18895 inverseMatrix.getInverse( matrixWorld );
18896 ray.copy( raycaster.ray ).applyMatrix4( inverseMatrix );
18898 if ( geometry.boundingBox !== null ) {
18900 if ( ray.isIntersectionBox( geometry.boundingBox ) === false )
return;
18904 var uvs, intersection;
18906 if ( geometry instanceof THREE.BufferGeometry ) {
18909 var index = geometry.index;
18910 var attributes = geometry.attributes;
18911 var positions = attributes.position.array;
18913 if ( attributes.uv !== undefined ){
18915 uvs = attributes.uv.array;
18919 if ( index !== null ) {
18921 var indices = index.array;
18923 for ( var i = 0, l = indices.length; i < l; i += 3 ) {
18926 b = indices[ i + 1 ];
18927 c = indices[ i + 2 ];
18929 intersection = checkBufferGeometryIntersection(
this, raycaster, ray, positions, uvs, a, b, c );
18931 if ( intersection ) {
18933 intersection.faceIndex = Math.floor( i / 3 );
18934 intersects.push( intersection );
18943 for ( var i = 0, l = positions.length; i < l; i += 9 ) {
18949 intersection = checkBufferGeometryIntersection(
this, raycaster, ray, positions, uvs, a, b, c );
18951 if ( intersection ) {
18953 intersection.index = a;
18954 intersects.push( intersection );
18962 }
else if ( geometry instanceof THREE.Geometry ) {
18965 var isFaceMaterial = material instanceof THREE.MeshFaceMaterial;
18966 var materials = isFaceMaterial ===
true ? material.materials : null;
18968 var vertices = geometry.vertices;
18969 var faces = geometry.faces;
18970 var faceVertexUvs = geometry.faceVertexUvs[ 0 ];
18971 if ( faceVertexUvs.length > 0 ) uvs = faceVertexUvs;
18973 for ( var f = 0, fl = faces.length; f < fl; f ++ ) {
18975 var face = faces[ f ];
18976 var faceMaterial = isFaceMaterial ===
true ? materials[ face.materialIndex ] : material;
18978 if ( faceMaterial === undefined )
continue;
18980 fvA = vertices[ face.a ];
18981 fvB = vertices[ face.b ];
18982 fvC = vertices[ face.c ];
18984 if ( faceMaterial.morphTargets ===
true ) {
18986 var morphTargets = geometry.morphTargets;
18987 var morphInfluences = this.morphTargetInfluences;
18993 for ( var t = 0, tl = morphTargets.length; t < tl; t ++ ) {
18995 var influence = morphInfluences[ t ];
18997 if ( influence === 0 )
continue;
18999 var targets = morphTargets[ t ].vertices;
19001 vA.addScaledVector( tempA.subVectors( targets[ face.a ], fvA ), influence );
19002 vB.addScaledVector( tempB.subVectors( targets[ face.b ], fvB ), influence );
19003 vC.addScaledVector( tempC.subVectors( targets[ face.c ], fvC ), influence );
19017 intersection = checkIntersection(
this, raycaster, ray, fvA, fvB, fvC, intersectionPoint );
19019 if ( intersection ) {
19023 var uvs_f = uvs[ f ];
19024 uvA.copy( uvs_f[ 0 ] );
19025 uvB.copy( uvs_f[ 1 ] );
19026 uvC.copy( uvs_f[ 2 ] );
19028 intersection.uv = uvIntersection( intersectionPoint, fvA, fvB, fvC, uvA, uvB, uvC );
19032 intersection.face = face;
19033 intersection.faceIndex = f;
19034 intersects.push( intersection );
19046 THREE.Mesh.prototype.clone =
function () {
19048 return new this.constructor( this.geometry, this.material ).copy(
this );
19060 THREE.Bone =
function ( skin ) {
19062 THREE.Object3D.call(
this );
19064 this.type =
'Bone';
19070 THREE.Bone.prototype = Object.create( THREE.Object3D.prototype );
19071 THREE.Bone.prototype.constructor = THREE.Bone;
19073 THREE.Bone.prototype.copy =
function ( source ) {
19075 THREE.Object3D.prototype.copy.call(
this, source );
19077 this.skin = source.skin;
19092 THREE.Skeleton =
function ( bones, boneInverses, useVertexTexture ) {
19094 this.useVertexTexture = useVertexTexture !== undefined ? useVertexTexture :
true;
19096 this.identityMatrix =
new THREE.Matrix4();
19100 bones = bones || [];
19102 this.bones = bones.slice( 0 );
19106 if ( this.useVertexTexture ) {
19116 var size = Math.sqrt( this.bones.length * 4 );
19117 size = THREE.Math.nextPowerOfTwo( Math.ceil( size ) );
19118 size = Math.max( size, 4 );
19120 this.boneTextureWidth = size;
19121 this.boneTextureHeight = size;
19123 this.boneMatrices =
new Float32Array( this.boneTextureWidth * this.boneTextureHeight * 4 );
19124 this.boneTexture =
new THREE.DataTexture( this.boneMatrices, this.boneTextureWidth, this.boneTextureHeight, THREE.RGBAFormat, THREE.FloatType );
19128 this.boneMatrices =
new Float32Array( 16 * this.bones.length );
19134 if ( boneInverses === undefined ) {
19136 this.calculateInverses();
19140 if ( this.bones.length === boneInverses.length ) {
19142 this.boneInverses = boneInverses.slice( 0 );
19146 console.warn(
'THREE.Skeleton bonInverses is the wrong length.' );
19148 this.boneInverses = [];
19150 for ( var b = 0, bl = this.bones.length; b < bl; b ++ ) {
19152 this.boneInverses.push(
new THREE.Matrix4() );
19162 THREE.Skeleton.prototype.calculateInverses =
function () {
19164 this.boneInverses = [];
19166 for ( var b = 0, bl = this.bones.length; b < bl; b ++ ) {
19168 var inverse =
new THREE.Matrix4();
19170 if ( this.bones[ b ] ) {
19172 inverse.getInverse( this.bones[ b ].matrixWorld );
19176 this.boneInverses.push( inverse );
19182 THREE.Skeleton.prototype.pose =
function () {
19188 for ( var b = 0, bl = this.bones.length; b < bl; b ++ ) {
19190 bone = this.bones[ b ];
19194 bone.matrixWorld.getInverse( this.boneInverses[ b ] );
19202 for ( var b = 0, bl = this.bones.length; b < bl; b ++ ) {
19204 bone = this.bones[ b ];
19208 if ( bone.parent ) {
19210 bone.matrix.getInverse( bone.parent.matrixWorld );
19211 bone.matrix.multiply( bone.matrixWorld );
19215 bone.matrix.copy( bone.matrixWorld );
19219 bone.matrix.decompose( bone.position, bone.quaternion, bone.scale );
19227 THREE.Skeleton.prototype.update = (
function () {
19229 var offsetMatrix =
new THREE.Matrix4();
19231 return function update() {
19235 for ( var b = 0, bl = this.bones.length; b < bl; b ++ ) {
19239 var matrix = this.bones[ b ] ? this.bones[ b ].matrixWorld : this.identityMatrix;
19241 offsetMatrix.multiplyMatrices( matrix, this.boneInverses[ b ] );
19242 offsetMatrix.flattenToArrayOffset( this.boneMatrices, b * 16 );
19246 if ( this.useVertexTexture ) {
19248 this.boneTexture.needsUpdate =
true;
19256 THREE.Skeleton.prototype.clone =
function () {
19258 return new THREE.Skeleton( this.bones, this.boneInverses, this.useVertexTexture );
19270 THREE.SkinnedMesh =
function ( geometry, material, useVertexTexture ) {
19272 THREE.Mesh.call(
this, geometry, material );
19274 this.type =
'SkinnedMesh';
19276 this.bindMode =
"attached";
19277 this.bindMatrix =
new THREE.Matrix4();
19278 this.bindMatrixInverse =
new THREE.Matrix4();
19287 if ( this.geometry && this.geometry.bones !== undefined ) {
19291 for ( var b = 0, bl = this.geometry.bones.length; b < bl; ++ b ) {
19293 gbone = this.geometry.bones[ b ];
19295 bone =
new THREE.Bone(
this );
19296 bones.push( bone );
19298 bone.name = gbone.name;
19299 bone.position.fromArray( gbone.pos );
19300 bone.quaternion.fromArray( gbone.rotq );
19301 if ( gbone.scl !== undefined ) bone.scale.fromArray( gbone.scl );
19305 for ( var b = 0, bl = this.geometry.bones.length; b < bl; ++ b ) {
19307 gbone = this.geometry.bones[ b ];
19309 if ( gbone.parent !== - 1 && gbone.parent !== null) {
19311 bones[ gbone.parent ].add( bones[ b ] );
19315 this.add( bones[ b ] );
19323 this.normalizeSkinWeights();
19325 this.updateMatrixWorld(
true );
19326 this.bind(
new THREE.Skeleton( bones, undefined, useVertexTexture ), this.matrixWorld );
19331 THREE.SkinnedMesh.prototype = Object.create( THREE.Mesh.prototype );
19332 THREE.SkinnedMesh.prototype.constructor = THREE.SkinnedMesh;
19334 THREE.SkinnedMesh.prototype.bind =
function( skeleton, bindMatrix ) {
19336 this.skeleton = skeleton;
19338 if ( bindMatrix === undefined ) {
19340 this.updateMatrixWorld(
true );
19342 this.skeleton.calculateInverses();
19344 bindMatrix = this.matrixWorld;
19348 this.bindMatrix.copy( bindMatrix );
19349 this.bindMatrixInverse.getInverse( bindMatrix );
19353 THREE.SkinnedMesh.prototype.pose =
function () {
19355 this.skeleton.pose();
19359 THREE.SkinnedMesh.prototype.normalizeSkinWeights =
function () {
19361 if ( this.geometry instanceof THREE.Geometry ) {
19363 for ( var i = 0; i < this.geometry.skinIndices.length; i ++ ) {
19365 var sw = this.geometry.skinWeights[ i ];
19367 var scale = 1.0 / sw.lengthManhattan();
19369 if ( scale !== Infinity ) {
19371 sw.multiplyScalar( scale );
19389 THREE.SkinnedMesh.prototype.updateMatrixWorld =
function( force ) {
19391 THREE.Mesh.prototype.updateMatrixWorld.call(
this,
true );
19393 if ( this.bindMode ===
"attached" ) {
19395 this.bindMatrixInverse.getInverse( this.matrixWorld );
19397 }
else if ( this.bindMode ===
"detached" ) {
19399 this.bindMatrixInverse.getInverse( this.bindMatrix );
19403 console.warn(
'THREE.SkinnedMesh unrecognized bindMode: ' + this.bindMode );
19409 THREE.SkinnedMesh.prototype.clone =
function() {
19411 return new this.constructor( this.geometry, this.material, this.useVertexTexture ).copy(
this );
19423 THREE.LOD =
function () {
19425 THREE.Object3D.call(
this );
19429 Object.defineProperties(
this, {
19437 console.warn(
'THREE.LOD: .objects has been renamed to .levels.' );
19438 return this.levels;
19447 THREE.LOD.prototype = Object.create( THREE.Object3D.prototype );
19448 THREE.LOD.prototype.constructor = THREE.LOD;
19450 THREE.LOD.prototype.addLevel =
function ( object, distance ) {
19452 if ( distance === undefined ) distance = 0;
19454 distance = Math.abs( distance );
19456 var levels = this.levels;
19458 for ( var l = 0; l < levels.length; l ++ ) {
19460 if ( distance < levels[ l ].distance ) {
19468 levels.splice( l, 0, { distance: distance,
object:
object } );
19470 this.add(
object );
19474 THREE.LOD.prototype.getObjectForDistance =
function ( distance ) {
19476 var levels = this.levels;
19478 for ( var i = 1, l = levels.length; i < l; i ++ ) {
19480 if ( distance < levels[ i ].distance ) {
19488 return levels[ i - 1 ].object;
19492 THREE.LOD.prototype.raycast = (
function () {
19494 var matrixPosition =
new THREE.Vector3();
19496 return function raycast( raycaster, intersects ) {
19498 matrixPosition.setFromMatrixPosition( this.matrixWorld );
19500 var distance = raycaster.ray.origin.distanceTo( matrixPosition );
19502 this.getObjectForDistance( distance ).raycast( raycaster, intersects );
19508 THREE.LOD.prototype.update =
function () {
19510 var v1 =
new THREE.Vector3();
19511 var v2 =
new THREE.Vector3();
19513 return function update( camera ) {
19515 var levels = this.levels;
19517 if ( levels.length > 1 ) {
19519 v1.setFromMatrixPosition( camera.matrixWorld );
19520 v2.setFromMatrixPosition( this.matrixWorld );
19522 var distance = v1.distanceTo( v2 );
19524 levels[ 0 ].object.visible =
true;
19526 for ( var i = 1, l = levels.length; i < l; i ++ ) {
19528 if ( distance >= levels[ i ].distance ) {
19530 levels[ i - 1 ].object.visible =
false;
19531 levels[ i ].object.visible =
true;
19541 for ( ; i < l; i ++ ) {
19543 levels[ i ].object.visible =
false;
19553 THREE.LOD.prototype.copy =
function ( source ) {
19555 THREE.Object3D.prototype.copy.call(
this, source,
false );
19557 var levels = source.levels;
19559 for ( var i = 0, l = levels.length; i < l; i ++ ) {
19561 var level = levels[ i ];
19563 this.addLevel( level.object.clone(), level.distance );
19571 THREE.LOD.prototype.toJSON =
function ( meta ) {
19573 var data = THREE.Object3D.prototype.toJSON.call(
this, meta );
19575 data.object.levels = [];
19577 var levels = this.levels;
19579 for ( var i = 0, l = levels.length; i < l; i ++ ) {
19581 var level = levels[ i ];
19583 data.object.levels.push( {
19584 object: level.object.uuid,
19585 distance: level.distance
19601 THREE.Sprite = (
function () {
19603 var indices =
new Uint16Array( [ 0, 1, 2, 0, 2, 3 ] );
19604 var vertices =
new Float32Array( [ - 0.5, - 0.5, 0, 0.5, - 0.5, 0, 0.5, 0.5, 0, - 0.5, 0.5, 0 ] );
19605 var uvs =
new Float32Array( [ 0, 0, 1, 0, 1, 1, 0, 1 ] );
19607 var geometry =
new THREE.BufferGeometry();
19608 geometry.setIndex(
new THREE.BufferAttribute( indices, 1 ) );
19609 geometry.addAttribute(
'position',
new THREE.BufferAttribute( vertices, 3 ) );
19610 geometry.addAttribute(
'uv',
new THREE.BufferAttribute( uvs, 2 ) );
19612 return function Sprite( material ) {
19614 THREE.Object3D.call(
this );
19616 this.type =
'Sprite';
19618 this.geometry = geometry;
19619 this.material = ( material !== undefined ) ? material :
new THREE.SpriteMaterial();
19625 THREE.Sprite.prototype = Object.create( THREE.Object3D.prototype );
19626 THREE.Sprite.prototype.constructor = THREE.Sprite;
19628 THREE.Sprite.prototype.raycast = (
function () {
19630 var matrixPosition =
new THREE.Vector3();
19632 return function raycast( raycaster, intersects ) {
19634 matrixPosition.setFromMatrixPosition( this.matrixWorld );
19636 var distanceSq = raycaster.ray.distanceSqToPoint( matrixPosition );
19637 var guessSizeSq = this.scale.x * this.scale.y;
19639 if ( distanceSq > guessSizeSq ) {
19647 distance: Math.sqrt( distanceSq ),
19648 point: this.position,
19658 THREE.Sprite.prototype.clone =
function () {
19660 return new this.constructor( this.material ).copy(
this );
19666 THREE.Particle = THREE.Sprite;
19675 THREE.LensFlare =
function ( texture, size, distance, blending, color ) {
19677 THREE.Object3D.call(
this );
19679 this.lensFlares = [];
19681 this.positionScreen =
new THREE.Vector3();
19682 this.customUpdateCallback = undefined;
19684 if ( texture !== undefined ) {
19686 this.add( texture, size, distance, blending, color );
19692 THREE.LensFlare.prototype = Object.create( THREE.Object3D.prototype );
19693 THREE.LensFlare.prototype.constructor = THREE.LensFlare;
19700 THREE.LensFlare.prototype.add =
function ( texture, size, distance, blending, color, opacity ) {
19702 if ( size === undefined ) size = - 1;
19703 if ( distance === undefined ) distance = 0;
19704 if ( opacity === undefined ) opacity = 1;
19705 if ( color === undefined ) color =
new THREE.Color( 0xffffff );
19706 if ( blending === undefined ) blending = THREE.NormalBlending;
19708 distance = Math.min( distance, Math.max( 0, distance ) );
19710 this.lensFlares.push( {
19713 distance: distance,
19729 THREE.LensFlare.prototype.updateLensFlares =
function () {
19731 var f, fl = this.lensFlares.length;
19733 var vecX = - this.positionScreen.x * 2;
19734 var vecY = - this.positionScreen.y * 2;
19736 for ( f = 0; f < fl; f ++ ) {
19738 flare = this.lensFlares[ f ];
19740 flare.x = this.positionScreen.x + vecX * flare.distance;
19741 flare.y = this.positionScreen.y + vecY * flare.distance;
19743 flare.wantedRotation = flare.x * Math.PI * 0.25;
19744 flare.rotation += ( flare.wantedRotation - flare.rotation ) * 0.25;
19750 THREE.LensFlare.prototype.copy =
function ( source ) {
19752 THREE.Object3D.prototype.copy.call(
this, source );
19754 this.positionScreen.copy( source.positionScreen );
19755 this.customUpdateCallback = source.customUpdateCallback;
19757 for ( var i = 0, l = source.lensFlares.length; i < l; i ++ ) {
19759 this.lensFlares.push( source.lensFlares[ i ] );
19773 THREE.Scene =
function () {
19775 THREE.Object3D.call(
this );
19777 this.type =
'Scene';
19780 this.overrideMaterial = null;
19782 this.autoUpdate =
true;
19786 THREE.Scene.prototype = Object.create( THREE.Object3D.prototype );
19787 THREE.Scene.prototype.constructor = THREE.Scene;
19789 THREE.Scene.prototype.copy =
function ( source ) {
19791 THREE.Object3D.prototype.copy.call(
this, source );
19793 if ( source.fog !== null ) this.fog = source.fog.clone();
19794 if ( source.overrideMaterial !== null ) this.overrideMaterial = source.overrideMaterial.clone();
19796 this.autoUpdate = source.autoUpdate;
19797 this.matrixAutoUpdate = source.matrixAutoUpdate;
19810 THREE.Fog =
function ( color, near, far ) {
19814 this.color =
new THREE.Color( color );
19816 this.near = ( near !== undefined ) ? near : 1;
19817 this.far = ( far !== undefined ) ? far : 1000;
19821 THREE.Fog.prototype.clone =
function () {
19823 return new THREE.Fog( this.color.getHex(), this.near, this.far );
19834 THREE.FogExp2 =
function ( color, density ) {
19838 this.color =
new THREE.Color( color );
19839 this.density = ( density !== undefined ) ? density : 0.00025;
19843 THREE.FogExp2.prototype.clone =
function () {
19845 return new THREE.FogExp2( this.color.getHex(), this.density );
19851 THREE.ShaderChunk = {};
19855 THREE.ShaderChunk[
'alphamap_fragment'] =
"#ifdef USE_ALPHAMAP\n\n diffuseColor.a *= texture2D( alphaMap, vUv ).g;\n\n#endif\n";
19859 THREE.ShaderChunk[
'alphamap_pars_fragment'] =
"#ifdef USE_ALPHAMAP\n\n uniform sampler2D alphaMap;\n\n#endif\n";
19863 THREE.ShaderChunk[
'alphatest_fragment'] =
"#ifdef ALPHATEST\n\n if ( diffuseColor.a < ALPHATEST ) discard;\n\n#endif\n";
19867 THREE.ShaderChunk[
'aomap_fragment'] =
"#ifdef USE_AOMAP\n\n totalAmbientLight *= ( texture2D( aoMap, vUv2 ).r - 1.0 ) * aoMapIntensity + 1.0;\n\n#endif\n";
19871 THREE.ShaderChunk[
'aomap_pars_fragment'] =
"#ifdef USE_AOMAP\n\n uniform sampler2D aoMap;\n uniform float aoMapIntensity;\n\n#endif";
19875 THREE.ShaderChunk[
'begin_vertex'] =
"\nvec3 transformed = vec3( position );\n";
19879 THREE.ShaderChunk[
'beginnormal_vertex'] =
"\nvec3 objectNormal = vec3( normal );\n";
19883 THREE.ShaderChunk[
'bumpmap_pars_fragment'] =
"#ifdef USE_BUMPMAP\n\n uniform sampler2D bumpMap;\n uniform float bumpScale;\n\n\n\n vec2 dHdxy_fwd() {\n\n vec2 dSTdx = dFdx( vUv );\n vec2 dSTdy = dFdy( vUv );\n\n float Hll = bumpScale * texture2D( bumpMap, vUv ).x;\n float dBx = bumpScale * texture2D( bumpMap, vUv + dSTdx ).x - Hll;\n float dBy = bumpScale * texture2D( bumpMap, vUv + dSTdy ).x - Hll;\n\n return vec2( dBx, dBy );\n\n }\n\n vec3 perturbNormalArb( vec3 surf_pos, vec3 surf_norm, vec2 dHdxy ) {\n\n vec3 vSigmaX = dFdx( surf_pos );\n vec3 vSigmaY = dFdy( surf_pos );\n vec3 vN = surf_norm;\n vec3 R1 = cross( vSigmaY, vN );\n vec3 R2 = cross( vN, vSigmaX );\n\n float fDet = dot( vSigmaX, R1 );\n\n vec3 vGrad = sign( fDet ) * ( dHdxy.x * R1 + dHdxy.y * R2 );\n return normalize( abs( fDet ) * surf_norm - vGrad );\n\n }\n\n#endif\n";
19887 THREE.ShaderChunk[
'color_fragment'] =
"#ifdef USE_COLOR\n\n diffuseColor.rgb *= vColor;\n\n#endif";
19891 THREE.ShaderChunk[
'color_pars_fragment'] =
"#ifdef USE_COLOR\n\n varying vec3 vColor;\n\n#endif\n";
19895 THREE.ShaderChunk[
'color_pars_vertex'] =
"#ifdef USE_COLOR\n\n varying vec3 vColor;\n\n#endif";
19899 THREE.ShaderChunk[
'color_vertex'] =
"#ifdef USE_COLOR\n\n vColor.xyz = color.xyz;\n\n#endif";
19903 THREE.ShaderChunk[
'common'] =
"#define PI 3.14159\n#define PI2 6.28318\n#define RECIPROCAL_PI2 0.15915494\n#define LOG2 1.442695\n#define EPSILON 1e-6\n\n#define saturate(a) clamp( a, 0.0, 1.0 )\n#define whiteCompliment(a) ( 1.0 - saturate( a ) )\n\nvec3 transformDirection( in vec3 normal, in mat4 matrix ) {\n\n return normalize( ( matrix * vec4( normal, 0.0 ) ).xyz );\n\n}\n\nvec3 inverseTransformDirection( in vec3 normal, in mat4 matrix ) {\n\n return normalize( ( vec4( normal, 0.0 ) * matrix ).xyz );\n\n}\n\nvec3 projectOnPlane(in vec3 point, in vec3 pointOnPlane, in vec3 planeNormal ) {\n\n float distance = dot( planeNormal, point - pointOnPlane );\n\n return - distance * planeNormal + point;\n\n}\n\nfloat sideOfPlane( in vec3 point, in vec3 pointOnPlane, in vec3 planeNormal ) {\n\n return sign( dot( point - pointOnPlane, planeNormal ) );\n\n}\n\nvec3 linePlaneIntersect( in vec3 pointOnLine, in vec3 lineDirection, in vec3 pointOnPlane, in vec3 planeNormal ) {\n\n return lineDirection * ( dot( planeNormal, pointOnPlane - pointOnLine ) / dot( planeNormal, lineDirection ) ) + pointOnLine;\n\n}\n\nfloat calcLightAttenuation( float lightDistance, float cutoffDistance, float decayExponent ) {\n\n if ( decayExponent > 0.0 ) {\n\n return pow( saturate( -lightDistance / cutoffDistance + 1.0 ), decayExponent );\n\n }\n\n return 1.0;\n\n}\n\nvec3 F_Schlick( in vec3 specularColor, in float dotLH ) {\n\n\n float fresnel = exp2( ( -5.55437 * dotLH - 6.98316 ) * dotLH );\n\n return ( 1.0 - specularColor ) * fresnel + specularColor;\n\n}\n\nfloat G_BlinnPhong_Implicit( /* in float dotNL, in float dotNV */ ) {\n\n\n return 0.25;\n\n}\n\nfloat D_BlinnPhong( in float shininess, in float dotNH ) {\n\n\n return ( shininess * 0.5 + 1.0 ) * pow( dotNH, shininess );\n\n}\n\nvec3 BRDF_BlinnPhong( in vec3 specularColor, in float shininess, in vec3 normal, in vec3 lightDir, in vec3 viewDir ) {\n\n vec3 halfDir = normalize( lightDir + viewDir );\n\n float dotNH = saturate( dot( normal, halfDir ) );\n float dotLH = saturate( dot( lightDir, halfDir ) );\n\n vec3 F = F_Schlick( specularColor, dotLH );\n\n float G = G_BlinnPhong_Implicit( /* dotNL, dotNV */ );\n\n float D = D_BlinnPhong( shininess, dotNH );\n\n return F * G * D;\n\n}\n\nvec3 inputToLinear( in vec3 a ) {\n\n #ifdef GAMMA_INPUT\n\n return pow( a, vec3( float( GAMMA_FACTOR ) ) );\n\n #else\n\n return a;\n\n #endif\n\n}\n\nvec3 linearToOutput( in vec3 a ) {\n\n #ifdef GAMMA_OUTPUT\n\n return pow( a, vec3( 1.0 / float( GAMMA_FACTOR ) ) );\n\n #else\n\n return a;\n\n #endif\n\n}\n";
19907 THREE.ShaderChunk[
'defaultnormal_vertex'] =
"#ifdef FLIP_SIDED\n\n objectNormal = -objectNormal;\n\n#endif\n\nvec3 transformedNormal = normalMatrix * objectNormal;\n";
19911 THREE.ShaderChunk[
'displacementmap_vertex'] =
"#ifdef USE_DISPLACEMENTMAP\n\n transformed += normal * ( texture2D( displacementMap, uv ).x * displacementScale + displacementBias );\n\n#endif\n";
19915 THREE.ShaderChunk[
'displacementmap_pars_vertex'] =
"#ifdef USE_DISPLACEMENTMAP\n\n uniform sampler2D displacementMap;\n uniform float displacementScale;\n uniform float displacementBias;\n\n#endif\n";
19919 THREE.ShaderChunk[
'emissivemap_fragment'] =
"#ifdef USE_EMISSIVEMAP\n\n vec4 emissiveColor = texture2D( emissiveMap, vUv );\n\n emissiveColor.rgb = inputToLinear( emissiveColor.rgb );\n\n totalEmissiveLight *= emissiveColor.rgb;\n\n#endif\n";
19923 THREE.ShaderChunk[
'emissivemap_pars_fragment'] =
"#ifdef USE_EMISSIVEMAP\n\n uniform sampler2D emissiveMap;\n\n#endif\n";
19927 THREE.ShaderChunk[
'envmap_fragment'] =
"#ifdef USE_ENVMAP\n\n #if defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG )\n\n vec3 cameraToVertex = normalize( vWorldPosition - cameraPosition );\n\n vec3 worldNormal = inverseTransformDirection( normal, viewMatrix );\n\n #ifdef ENVMAP_MODE_REFLECTION\n\n vec3 reflectVec = reflect( cameraToVertex, worldNormal );\n\n #else\n\n vec3 reflectVec = refract( cameraToVertex, worldNormal, refractionRatio );\n\n #endif\n\n #else\n\n vec3 reflectVec = vReflect;\n\n #endif\n\n #ifdef DOUBLE_SIDED\n float flipNormal = ( float( gl_FrontFacing ) * 2.0 - 1.0 );\n #else\n float flipNormal = 1.0;\n #endif\n\n #ifdef ENVMAP_TYPE_CUBE\n vec4 envColor = textureCube( envMap, flipNormal * vec3( flipEnvMap * reflectVec.x, reflectVec.yz ) );\n\n #elif defined( ENVMAP_TYPE_EQUIREC )\n vec2 sampleUV;\n sampleUV.y = saturate( flipNormal * reflectVec.y * 0.5 + 0.5 );\n sampleUV.x = atan( flipNormal * reflectVec.z, flipNormal * reflectVec.x ) * RECIPROCAL_PI2 + 0.5;\n vec4 envColor = texture2D( envMap, sampleUV );\n\n #elif defined( ENVMAP_TYPE_SPHERE )\n vec3 reflectView = flipNormal * normalize((viewMatrix * vec4( reflectVec, 0.0 )).xyz + vec3(0.0,0.0,1.0));\n vec4 envColor = texture2D( envMap, reflectView.xy * 0.5 + 0.5 );\n #endif\n\n envColor.xyz = inputToLinear( envColor.xyz );\n\n #ifdef ENVMAP_BLENDING_MULTIPLY\n\n outgoingLight = mix( outgoingLight, outgoingLight * envColor.xyz, specularStrength * reflectivity );\n\n #elif defined( ENVMAP_BLENDING_MIX )\n\n outgoingLight = mix( outgoingLight, envColor.xyz, specularStrength * reflectivity );\n\n #elif defined( ENVMAP_BLENDING_ADD )\n\n outgoingLight += envColor.xyz * specularStrength * reflectivity;\n\n #endif\n\n#endif\n";
19931 THREE.ShaderChunk[
'envmap_pars_fragment'] =
"#ifdef USE_ENVMAP\n\n uniform float reflectivity;\n #ifdef ENVMAP_TYPE_CUBE\n uniform samplerCube envMap;\n #else\n uniform sampler2D envMap;\n #endif\n uniform float flipEnvMap;\n\n #if defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( PHONG )\n\n uniform float refractionRatio;\n\n #else\n\n varying vec3 vReflect;\n\n #endif\n\n#endif\n";
19935 THREE.ShaderChunk[
'envmap_pars_vertex'] =
"#if defined( USE_ENVMAP ) && ! defined( USE_BUMPMAP ) && ! defined( USE_NORMALMAP ) && ! defined( PHONG )\n\n varying vec3 vReflect;\n\n uniform float refractionRatio;\n\n#endif\n";
19939 THREE.ShaderChunk[
'envmap_vertex'] =
"#if defined( USE_ENVMAP ) && ! defined( USE_BUMPMAP ) && ! defined( USE_NORMALMAP ) && ! defined( PHONG )\n\n vec3 cameraToVertex = normalize( worldPosition.xyz - cameraPosition );\n\n vec3 worldNormal = inverseTransformDirection( transformedNormal, viewMatrix );\n\n #ifdef ENVMAP_MODE_REFLECTION\n\n vReflect = reflect( cameraToVertex, worldNormal );\n\n #else\n\n vReflect = refract( cameraToVertex, worldNormal, refractionRatio );\n\n #endif\n\n#endif\n";
19943 THREE.ShaderChunk[
'fog_fragment'] =
"#ifdef USE_FOG\n\n #ifdef USE_LOGDEPTHBUF_EXT\n\n float depth = gl_FragDepthEXT / gl_FragCoord.w;\n\n #else\n\n float depth = gl_FragCoord.z / gl_FragCoord.w;\n\n #endif\n\n #ifdef FOG_EXP2\n\n float fogFactor = whiteCompliment( exp2( - fogDensity * fogDensity * depth * depth * LOG2 ) );\n\n #else\n\n float fogFactor = smoothstep( fogNear, fogFar, depth );\n\n #endif\n \n outgoingLight = mix( outgoingLight, fogColor, fogFactor );\n\n#endif";
19947 THREE.ShaderChunk[
'fog_pars_fragment'] =
"#ifdef USE_FOG\n\n uniform vec3 fogColor;\n\n #ifdef FOG_EXP2\n\n uniform float fogDensity;\n\n #else\n\n uniform float fogNear;\n uniform float fogFar;\n #endif\n\n#endif";
19951 THREE.ShaderChunk[
'hemilight_fragment'] =
"#if MAX_HEMI_LIGHTS > 0\n\n for ( int i = 0; i < MAX_HEMI_LIGHTS; i ++ ) {\n\n vec3 lightDir = hemisphereLightDirection[ i ];\n\n float dotProduct = dot( normal, lightDir );\n\n float hemiDiffuseWeight = 0.5 * dotProduct + 0.5;\n\n vec3 lightColor = mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight );\n\n totalAmbientLight += lightColor;\n\n }\n\n#endif\n\n";
19955 THREE.ShaderChunk[
'lightmap_fragment'] =
"#ifdef USE_LIGHTMAP\n\n totalAmbientLight += texture2D( lightMap, vUv2 ).xyz * lightMapIntensity;\n\n#endif\n";
19959 THREE.ShaderChunk[
'lightmap_pars_fragment'] =
"#ifdef USE_LIGHTMAP\n\n uniform sampler2D lightMap;\n uniform float lightMapIntensity;\n\n#endif";
19963 THREE.ShaderChunk[
'lights_lambert_pars_vertex'] =
"#if MAX_DIR_LIGHTS > 0\n\n uniform vec3 directionalLightColor[ MAX_DIR_LIGHTS ];\n uniform vec3 directionalLightDirection[ MAX_DIR_LIGHTS ];\n\n#endif\n\n#if MAX_HEMI_LIGHTS > 0\n\n uniform vec3 hemisphereLightSkyColor[ MAX_HEMI_LIGHTS ];\n uniform vec3 hemisphereLightGroundColor[ MAX_HEMI_LIGHTS ];\n uniform vec3 hemisphereLightDirection[ MAX_HEMI_LIGHTS ];\n\n#endif\n\n#if MAX_POINT_LIGHTS > 0\n\n uniform vec3 pointLightColor[ MAX_POINT_LIGHTS ];\n uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];\n uniform float pointLightDistance[ MAX_POINT_LIGHTS ];\n uniform float pointLightDecay[ MAX_POINT_LIGHTS ];\n\n#endif\n\n#if MAX_SPOT_LIGHTS > 0\n\n uniform vec3 spotLightColor[ MAX_SPOT_LIGHTS ];\n uniform vec3 spotLightPosition[ MAX_SPOT_LIGHTS ];\n uniform vec3 spotLightDirection[ MAX_SPOT_LIGHTS ];\n uniform float spotLightDistance[ MAX_SPOT_LIGHTS ];\n uniform float spotLightAngleCos[ MAX_SPOT_LIGHTS ];\n uniform float spotLightExponent[ MAX_SPOT_LIGHTS ];\n uniform float spotLightDecay[ MAX_SPOT_LIGHTS ];\n\n#endif\n";
19967 THREE.ShaderChunk[
'lights_lambert_vertex'] =
"vLightFront = vec3( 0.0 );\n\n#ifdef DOUBLE_SIDED\n\n vLightBack = vec3( 0.0 );\n\n#endif\n\nvec3 normal = normalize( transformedNormal );\n\n#if MAX_POINT_LIGHTS > 0\n\n for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {\n\n vec3 lightColor = pointLightColor[ i ];\n\n vec3 lVector = pointLightPosition[ i ] - mvPosition.xyz;\n vec3 lightDir = normalize( lVector );\n\n\n float attenuation = calcLightAttenuation( length( lVector ), pointLightDistance[ i ], pointLightDecay[ i ] );\n\n\n float dotProduct = dot( normal, lightDir );\n\n vLightFront += lightColor * attenuation * saturate( dotProduct );\n\n #ifdef DOUBLE_SIDED\n\n vLightBack += lightColor * attenuation * saturate( - dotProduct );\n\n #endif\n\n }\n\n#endif\n\n#if MAX_SPOT_LIGHTS > 0\n\n for ( int i = 0; i < MAX_SPOT_LIGHTS; i ++ ) {\n\n vec3 lightColor = spotLightColor[ i ];\n\n vec3 lightPosition = spotLightPosition[ i ];\n vec3 lVector = lightPosition - mvPosition.xyz;\n vec3 lightDir = normalize( lVector );\n\n float spotEffect = dot( spotLightDirection[ i ], lightDir );\n\n if ( spotEffect > spotLightAngleCos[ i ] ) {\n\n spotEffect = saturate( pow( saturate( spotEffect ), spotLightExponent[ i ] ) );\n\n\n float attenuation = calcLightAttenuation( length( lVector ), spotLightDistance[ i ], spotLightDecay[ i ] );\n\n attenuation *= spotEffect;\n\n\n float dotProduct = dot( normal, lightDir );\n\n vLightFront += lightColor * attenuation * saturate( dotProduct );\n\n #ifdef DOUBLE_SIDED\n\n vLightBack += lightColor * attenuation * saturate( - dotProduct );\n\n #endif\n\n }\n\n }\n\n#endif\n\n#if MAX_DIR_LIGHTS > 0\n\n for ( int i = 0; i < MAX_DIR_LIGHTS; i ++ ) {\n\n vec3 lightColor = directionalLightColor[ i ];\n\n vec3 lightDir = directionalLightDirection[ i ];\n\n\n float dotProduct = dot( normal, lightDir );\n\n vLightFront += lightColor * saturate( dotProduct );\n\n #ifdef DOUBLE_SIDED\n\n vLightBack += lightColor * saturate( - dotProduct );\n\n #endif\n\n }\n\n#endif\n\n#if MAX_HEMI_LIGHTS > 0\n\n for ( int i = 0; i < MAX_HEMI_LIGHTS; i ++ ) {\n\n vec3 lightDir = hemisphereLightDirection[ i ];\n\n\n float dotProduct = dot( normal, lightDir );\n\n float hemiDiffuseWeight = 0.5 * dotProduct + 0.5;\n\n vLightFront += mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeight );\n\n #ifdef DOUBLE_SIDED\n\n float hemiDiffuseWeightBack = - 0.5 * dotProduct + 0.5;\n\n vLightBack += mix( hemisphereLightGroundColor[ i ], hemisphereLightSkyColor[ i ], hemiDiffuseWeightBack );\n\n #endif\n\n }\n\n#endif\n";
19971 THREE.ShaderChunk[
'lights_phong_fragment'] =
"vec3 viewDir = normalize( vViewPosition );\n\nvec3 totalDiffuseLight = vec3( 0.0 );\nvec3 totalSpecularLight = vec3( 0.0 );\n\n#if MAX_POINT_LIGHTS > 0\n\n for ( int i = 0; i < MAX_POINT_LIGHTS; i ++ ) {\n\n vec3 lightColor = pointLightColor[ i ];\n\n vec3 lightPosition = pointLightPosition[ i ];\n vec3 lVector = lightPosition + vViewPosition.xyz;\n vec3 lightDir = normalize( lVector );\n\n\n float attenuation = calcLightAttenuation( length( lVector ), pointLightDistance[ i ], pointLightDecay[ i ] );\n\n\n float cosineTerm = saturate( dot( normal, lightDir ) );\n\n totalDiffuseLight += lightColor * attenuation * cosineTerm;\n\n\n vec3 brdf = BRDF_BlinnPhong( specular, shininess, normal, lightDir, viewDir );\n\n totalSpecularLight += brdf * specularStrength * lightColor * attenuation * cosineTerm;\n\n\n }\n\n#endif\n\n#if MAX_SPOT_LIGHTS > 0\n\n for ( int i = 0; i < MAX_SPOT_LIGHTS; i ++ ) {\n\n vec3 lightColor = spotLightColor[ i ];\n\n vec3 lightPosition = spotLightPosition[ i ];\n vec3 lVector = lightPosition + vViewPosition.xyz;\n vec3 lightDir = normalize( lVector );\n\n float spotEffect = dot( spotLightDirection[ i ], lightDir );\n\n if ( spotEffect > spotLightAngleCos[ i ] ) {\n\n spotEffect = saturate( pow( saturate( spotEffect ), spotLightExponent[ i ] ) );\n\n\n float attenuation = calcLightAttenuation( length( lVector ), spotLightDistance[ i ], spotLightDecay[ i ] );\n\n attenuation *= spotEffect;\n\n\n float cosineTerm = saturate( dot( normal, lightDir ) );\n\n totalDiffuseLight += lightColor * attenuation * cosineTerm;\n\n\n vec3 brdf = BRDF_BlinnPhong( specular, shininess, normal, lightDir, viewDir );\n\n totalSpecularLight += brdf * specularStrength * lightColor * attenuation * cosineTerm;\n\n }\n\n }\n\n#endif\n\n#if MAX_DIR_LIGHTS > 0\n\n for ( int i = 0; i < MAX_DIR_LIGHTS; i ++ ) {\n\n vec3 lightColor = directionalLightColor[ i ];\n\n vec3 lightDir = directionalLightDirection[ i ];\n\n\n float cosineTerm = saturate( dot( normal, lightDir ) );\n\n totalDiffuseLight += lightColor * cosineTerm;\n\n\n vec3 brdf = BRDF_BlinnPhong( specular, shininess, normal, lightDir, viewDir );\n\n totalSpecularLight += brdf * specularStrength * lightColor * cosineTerm;\n\n }\n\n#endif\n";
19975 THREE.ShaderChunk[
'lights_phong_pars_fragment'] =
"uniform vec3 ambientLightColor;\n\n#if MAX_DIR_LIGHTS > 0\n\n uniform vec3 directionalLightColor[ MAX_DIR_LIGHTS ];\n uniform vec3 directionalLightDirection[ MAX_DIR_LIGHTS ];\n\n#endif\n\n#if MAX_HEMI_LIGHTS > 0\n\n uniform vec3 hemisphereLightSkyColor[ MAX_HEMI_LIGHTS ];\n uniform vec3 hemisphereLightGroundColor[ MAX_HEMI_LIGHTS ];\n uniform vec3 hemisphereLightDirection[ MAX_HEMI_LIGHTS ];\n\n#endif\n\n#if MAX_POINT_LIGHTS > 0\n\n uniform vec3 pointLightColor[ MAX_POINT_LIGHTS ];\n\n uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];\n uniform float pointLightDistance[ MAX_POINT_LIGHTS ];\n uniform float pointLightDecay[ MAX_POINT_LIGHTS ];\n\n#endif\n\n#if MAX_SPOT_LIGHTS > 0\n\n uniform vec3 spotLightColor[ MAX_SPOT_LIGHTS ];\n uniform vec3 spotLightPosition[ MAX_SPOT_LIGHTS ];\n uniform vec3 spotLightDirection[ MAX_SPOT_LIGHTS ];\n uniform float spotLightAngleCos[ MAX_SPOT_LIGHTS ];\n uniform float spotLightExponent[ MAX_SPOT_LIGHTS ];\n uniform float spotLightDistance[ MAX_SPOT_LIGHTS ];\n uniform float spotLightDecay[ MAX_SPOT_LIGHTS ];\n\n#endif\n\n#if MAX_SPOT_LIGHTS > 0 || defined( USE_ENVMAP )\n\n varying vec3 vWorldPosition;\n\n#endif\n\nvarying vec3 vViewPosition;\n\n#ifndef FLAT_SHADED\n\n varying vec3 vNormal;\n\n#endif\n";
19979 THREE.ShaderChunk[
'lights_phong_pars_vertex'] =
"#if MAX_SPOT_LIGHTS > 0 || defined( USE_ENVMAP )\n\n varying vec3 vWorldPosition;\n\n#endif\n\n#if MAX_POINT_LIGHTS > 0\n\n uniform vec3 pointLightPosition[ MAX_POINT_LIGHTS ];\n\n#endif\n";
19983 THREE.ShaderChunk[
'lights_phong_vertex'] =
"#if MAX_SPOT_LIGHTS > 0 || defined( USE_ENVMAP )\n\n vWorldPosition = worldPosition.xyz;\n\n#endif\n";
19987 THREE.ShaderChunk[
'linear_to_gamma_fragment'] =
"\n outgoingLight = linearToOutput( outgoingLight );\n";
19991 THREE.ShaderChunk[
'logdepthbuf_fragment'] =
"#if defined(USE_LOGDEPTHBUF) && defined(USE_LOGDEPTHBUF_EXT)\n\n gl_FragDepthEXT = log2(vFragDepth) * logDepthBufFC * 0.5;\n\n#endif";
19995 THREE.ShaderChunk[
'logdepthbuf_pars_fragment'] =
"#ifdef USE_LOGDEPTHBUF\n\n uniform float logDepthBufFC;\n\n #ifdef USE_LOGDEPTHBUF_EXT\n\n varying float vFragDepth;\n\n #endif\n\n#endif\n";
19999 THREE.ShaderChunk[
'logdepthbuf_pars_vertex'] =
"#ifdef USE_LOGDEPTHBUF\n\n #ifdef USE_LOGDEPTHBUF_EXT\n\n varying float vFragDepth;\n\n #endif\n\n uniform float logDepthBufFC;\n\n#endif";
20003 THREE.ShaderChunk[
'logdepthbuf_vertex'] =
"#ifdef USE_LOGDEPTHBUF\n\n gl_Position.z = log2(max( EPSILON, gl_Position.w + 1.0 )) * logDepthBufFC;\n\n #ifdef USE_LOGDEPTHBUF_EXT\n\n vFragDepth = 1.0 + gl_Position.w;\n\n#else\n\n gl_Position.z = (gl_Position.z - 1.0) * gl_Position.w;\n\n #endif\n\n#endif";
20007 THREE.ShaderChunk[
'map_fragment'] =
"#ifdef USE_MAP\n\n vec4 texelColor = texture2D( map, vUv );\n\n texelColor.xyz = inputToLinear( texelColor.xyz );\n\n diffuseColor *= texelColor;\n\n#endif\n";
20011 THREE.ShaderChunk[
'map_pars_fragment'] =
"#ifdef USE_MAP\n\n uniform sampler2D map;\n\n#endif";
20015 THREE.ShaderChunk[
'map_particle_fragment'] =
"#ifdef USE_MAP\n\n diffuseColor *= texture2D( map, vec2( gl_PointCoord.x, 1.0 - gl_PointCoord.y ) * offsetRepeat.zw + offsetRepeat.xy );\n\n#endif\n";
20019 THREE.ShaderChunk[
'map_particle_pars_fragment'] =
"#ifdef USE_MAP\n\n uniform vec4 offsetRepeat;\n uniform sampler2D map;\n\n#endif\n";
20023 THREE.ShaderChunk[
'morphnormal_vertex'] =
"#ifdef USE_MORPHNORMALS\n\n objectNormal += ( morphNormal0 - normal ) * morphTargetInfluences[ 0 ];\n objectNormal += ( morphNormal1 - normal ) * morphTargetInfluences[ 1 ];\n objectNormal += ( morphNormal2 - normal ) * morphTargetInfluences[ 2 ];\n objectNormal += ( morphNormal3 - normal ) * morphTargetInfluences[ 3 ];\n\n#endif\n";
20027 THREE.ShaderChunk[
'morphtarget_pars_vertex'] =
"#ifdef USE_MORPHTARGETS\n\n #ifndef USE_MORPHNORMALS\n\n uniform float morphTargetInfluences[ 8 ];\n\n #else\n\n uniform float morphTargetInfluences[ 4 ];\n\n #endif\n\n#endif";
20031 THREE.ShaderChunk[
'morphtarget_vertex'] =
"#ifdef USE_MORPHTARGETS\n\n transformed += ( morphTarget0 - position ) * morphTargetInfluences[ 0 ];\n transformed += ( morphTarget1 - position ) * morphTargetInfluences[ 1 ];\n transformed += ( morphTarget2 - position ) * morphTargetInfluences[ 2 ];\n transformed += ( morphTarget3 - position ) * morphTargetInfluences[ 3 ];\n\n #ifndef USE_MORPHNORMALS\n\n transformed += ( morphTarget4 - position ) * morphTargetInfluences[ 4 ];\n transformed += ( morphTarget5 - position ) * morphTargetInfluences[ 5 ];\n transformed += ( morphTarget6 - position ) * morphTargetInfluences[ 6 ];\n transformed += ( morphTarget7 - position ) * morphTargetInfluences[ 7 ];\n\n #endif\n\n#endif\n";
20035 THREE.ShaderChunk[
'normal_phong_fragment'] =
"#ifndef FLAT_SHADED\n\n vec3 normal = normalize( vNormal );\n\n #ifdef DOUBLE_SIDED\n\n normal = normal * ( -1.0 + 2.0 * float( gl_FrontFacing ) );\n\n #endif\n\n#else\n\n vec3 fdx = dFdx( vViewPosition );\n vec3 fdy = dFdy( vViewPosition );\n vec3 normal = normalize( cross( fdx, fdy ) );\n\n#endif\n\n#ifdef USE_NORMALMAP\n\n normal = perturbNormal2Arb( -vViewPosition, normal );\n\n#elif defined( USE_BUMPMAP )\n\n normal = perturbNormalArb( -vViewPosition, normal, dHdxy_fwd() );\n\n#endif\n\n";
20039 THREE.ShaderChunk[
'normalmap_pars_fragment'] =
"#ifdef USE_NORMALMAP\n\n uniform sampler2D normalMap;\n uniform vec2 normalScale;\n\n\n vec3 perturbNormal2Arb( vec3 eye_pos, vec3 surf_norm ) {\n\n vec3 q0 = dFdx( eye_pos.xyz );\n vec3 q1 = dFdy( eye_pos.xyz );\n vec2 st0 = dFdx( vUv.st );\n vec2 st1 = dFdy( vUv.st );\n\n vec3 S = normalize( q0 * st1.t - q1 * st0.t );\n vec3 T = normalize( -q0 * st1.s + q1 * st0.s );\n vec3 N = normalize( surf_norm );\n\n vec3 mapN = texture2D( normalMap, vUv ).xyz * 2.0 - 1.0;\n mapN.xy = normalScale * mapN.xy;\n mat3 tsn = mat3( S, T, N );\n return normalize( tsn * mapN );\n\n }\n\n#endif\n";
20043 THREE.ShaderChunk[
'project_vertex'] =
"#ifdef USE_SKINNING\n\n vec4 mvPosition = modelViewMatrix * skinned;\n\n#else\n\n vec4 mvPosition = modelViewMatrix * vec4( transformed, 1.0 );\n\n#endif\n\ngl_Position = projectionMatrix * mvPosition;\n";
20047 THREE.ShaderChunk[
'shadowmap_fragment'] =
"#ifdef USE_SHADOWMAP\n\n for ( int i = 0; i < MAX_SHADOWS; i ++ ) {\n\n float texelSizeY = 1.0 / shadowMapSize[ i ].y;\n\n float shadow = 0.0;\n\n#if defined( POINT_LIGHT_SHADOWS )\n\n bool isPointLight = shadowDarkness[ i ] < 0.0;\n\n if ( isPointLight ) {\n\n float realShadowDarkness = abs( shadowDarkness[ i ] );\n\n vec3 lightToPosition = vShadowCoord[ i ].xyz;\n\n #if defined( SHADOWMAP_TYPE_PCF ) || defined( SHADOWMAP_TYPE_PCF_SOFT )\n\n vec3 bd3D = normalize( lightToPosition );\n float dp = length( lightToPosition );\n\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D, texelSizeY ) ), shadowBias[ i ], shadow );\n\n\n #if defined( SHADOWMAP_TYPE_PCF )\n const float Dr = 1.25;\n #elif defined( SHADOWMAP_TYPE_PCF_SOFT )\n const float Dr = 2.25;\n #endif\n\n float os = Dr * 2.0 * texelSizeY;\n\n const vec3 Gsd = vec3( - 1, 0, 1 );\n\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zzz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zxz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xxz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xzz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zzx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zxx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xxx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xzx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zzy * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zxy * os, texelSizeY ) ), shadowBias[ i ], shadow );\n\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xxy * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xzy * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zyz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xyz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.zyx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.xyx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.yzz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.yxz * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.yxx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D + Gsd.yzx * os, texelSizeY ) ), shadowBias[ i ], shadow );\n\n shadow *= realShadowDarkness * ( 1.0 / 21.0 );\n\n #else \n vec3 bd3D = normalize( lightToPosition );\n float dp = length( lightToPosition );\n\n adjustShadowValue1K( dp, texture2D( shadowMap[ i ], cubeToUV( bd3D, texelSizeY ) ), shadowBias[ i ], shadow );\n\n shadow *= realShadowDarkness;\n\n #endif\n\n } else {\n\n#endif \n float texelSizeX = 1.0 / shadowMapSize[ i ].x;\n\n vec3 shadowCoord = vShadowCoord[ i ].xyz / vShadowCoord[ i ].w;\n\n\n bvec4 inFrustumVec = bvec4 ( shadowCoord.x >= 0.0, shadowCoord.x <= 1.0, shadowCoord.y >= 0.0, shadowCoord.y <= 1.0 );\n bool inFrustum = all( inFrustumVec );\n\n bvec2 frustumTestVec = bvec2( inFrustum, shadowCoord.z <= 1.0 );\n\n bool frustumTest = all( frustumTestVec );\n\n if ( frustumTest ) {\n\n #if defined( SHADOWMAP_TYPE_PCF )\n\n\n /*\n for ( float y = -1.25; y <= 1.25; y += 1.25 )\n for ( float x = -1.25; x <= 1.25; x += 1.25 ) {\n vec4 rgbaDepth = texture2D( shadowMap[ i ], vec2( x * xPixelOffset, y * yPixelOffset ) + shadowCoord.xy );\n float fDepth = unpackDepth( rgbaDepth );\n if ( fDepth < shadowCoord.z )\n shadow += 1.0;\n }\n shadow /= 9.0;\n */\n\n shadowCoord.z += shadowBias[ i ];\n\n const float ShadowDelta = 1.0 / 9.0;\n\n float xPixelOffset = texelSizeX;\n float yPixelOffset = texelSizeY;\n\n float dx0 = - 1.25 * xPixelOffset;\n float dy0 = - 1.25 * yPixelOffset;\n float dx1 = 1.25 * xPixelOffset;\n float dy1 = 1.25 * yPixelOffset;\n\n float fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx0, dy0 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( 0.0, dy0 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx1, dy0 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx0, 0.0 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx1, 0.0 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx0, dy1 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( 0.0, dy1 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n fDepth = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx1, dy1 ) ) );\n if ( fDepth < shadowCoord.z ) shadow += ShadowDelta;\n\n shadow *= shadowDarkness[ i ];\n\n #elif defined( SHADOWMAP_TYPE_PCF_SOFT )\n\n\n shadowCoord.z += shadowBias[ i ];\n\n float xPixelOffset = texelSizeX;\n float yPixelOffset = texelSizeY;\n\n float dx0 = - 1.0 * xPixelOffset;\n float dy0 = - 1.0 * yPixelOffset;\n float dx1 = 1.0 * xPixelOffset;\n float dy1 = 1.0 * yPixelOffset;\n\n mat3 shadowKernel;\n mat3 depthKernel;\n\n depthKernel[ 0 ][ 0 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx0, dy0 ) ) );\n depthKernel[ 0 ][ 1 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx0, 0.0 ) ) );\n depthKernel[ 0 ][ 2 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx0, dy1 ) ) );\n depthKernel[ 1 ][ 0 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( 0.0, dy0 ) ) );\n depthKernel[ 1 ][ 1 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy ) );\n depthKernel[ 1 ][ 2 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( 0.0, dy1 ) ) );\n depthKernel[ 2 ][ 0 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx1, dy0 ) ) );\n depthKernel[ 2 ][ 1 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx1, 0.0 ) ) );\n depthKernel[ 2 ][ 2 ] = unpackDepth( texture2D( shadowMap[ i ], shadowCoord.xy + vec2( dx1, dy1 ) ) );\n\n vec3 shadowZ = vec3( shadowCoord.z );\n shadowKernel[ 0 ] = vec3( lessThan( depthKernel[ 0 ], shadowZ ) );\n shadowKernel[ 0 ] *= vec3( 0.25 );\n\n shadowKernel[ 1 ] = vec3( lessThan( depthKernel[ 1 ], shadowZ ) );\n shadowKernel[ 1 ] *= vec3( 0.25 );\n\n shadowKernel[ 2 ] = vec3( lessThan( depthKernel[ 2 ], shadowZ ) );\n shadowKernel[ 2 ] *= vec3( 0.25 );\n\n vec2 fractionalCoord = 1.0 - fract( shadowCoord.xy * shadowMapSize[ i ].xy );\n\n shadowKernel[ 0 ] = mix( shadowKernel[ 1 ], shadowKernel[ 0 ], fractionalCoord.x );\n shadowKernel[ 1 ] = mix( shadowKernel[ 2 ], shadowKernel[ 1 ], fractionalCoord.x );\n\n vec4 shadowValues;\n shadowValues.x = mix( shadowKernel[ 0 ][ 1 ], shadowKernel[ 0 ][ 0 ], fractionalCoord.y );\n shadowValues.y = mix( shadowKernel[ 0 ][ 2 ], shadowKernel[ 0 ][ 1 ], fractionalCoord.y );\n shadowValues.z = mix( shadowKernel[ 1 ][ 1 ], shadowKernel[ 1 ][ 0 ], fractionalCoord.y );\n shadowValues.w = mix( shadowKernel[ 1 ][ 2 ], shadowKernel[ 1 ][ 1 ], fractionalCoord.y );\n\n shadow = dot( shadowValues, vec4( 1.0 ) ) * shadowDarkness[ i ];\n\n #else \n shadowCoord.z += shadowBias[ i ];\n\n vec4 rgbaDepth = texture2D( shadowMap[ i ], shadowCoord.xy );\n float fDepth = unpackDepth( rgbaDepth );\n\n if ( fDepth < shadowCoord.z )\n shadow = shadowDarkness[ i ];\n\n #endif\n\n }\n\n#ifdef SHADOWMAP_DEBUG\n\n if ( inFrustum ) {\n\n if ( i == 0 ) {\n\n outgoingLight *= vec3( 1.0, 0.5, 0.0 );\n\n } else if ( i == 1 ) {\n\n outgoingLight *= vec3( 0.0, 1.0, 0.8 );\n\n } else {\n\n outgoingLight *= vec3( 0.0, 0.5, 1.0 );\n\n }\n\n }\n\n#endif\n\n#if defined( POINT_LIGHT_SHADOWS )\n\n }\n\n#endif\n\n shadowMask = shadowMask * vec3( 1.0 - shadow );\n\n }\n\n#endif\n";
20051 THREE.ShaderChunk[
'shadowmap_pars_fragment'] =
"#ifdef USE_SHADOWMAP\n\n uniform sampler2D shadowMap[ MAX_SHADOWS ];\n uniform vec2 shadowMapSize[ MAX_SHADOWS ];\n\n uniform float shadowDarkness[ MAX_SHADOWS ];\n uniform float shadowBias[ MAX_SHADOWS ];\n\n varying vec4 vShadowCoord[ MAX_SHADOWS ];\n\n float unpackDepth( const in vec4 rgba_depth ) {\n\n const vec4 bit_shift = vec4( 1.0 / ( 256.0 * 256.0 * 256.0 ), 1.0 / ( 256.0 * 256.0 ), 1.0 / 256.0, 1.0 );\n float depth = dot( rgba_depth, bit_shift );\n return depth;\n\n }\n\n #if defined(POINT_LIGHT_SHADOWS)\n\n\n void adjustShadowValue1K( const float testDepth, const vec4 textureData, const float bias, inout float shadowValue ) {\n\n const vec4 bitSh = vec4( 1.0 / ( 256.0 * 256.0 * 256.0 ), 1.0 / ( 256.0 * 256.0 ), 1.0 / 256.0, 1.0 );\n if ( testDepth >= dot( textureData, bitSh ) * 1000.0 + bias )\n shadowValue += 1.0;\n\n }\n\n\n vec2 cubeToUV( vec3 v, float texelSizeY ) {\n\n\n vec3 absV = abs( v );\n\n\n float scaleToCube = 1.0 / max( absV.x, max( absV.y, absV.z ) );\n absV *= scaleToCube;\n\n\n v *= scaleToCube * ( 1.0 - 2.0 * texelSizeY );\n\n\n\n vec2 planar = v.xy;\n\n float almostATexel = 1.5 * texelSizeY;\n float almostOne = 1.0 - almostATexel;\n\n if ( absV.z >= almostOne ) {\n\n if ( v.z > 0.0 )\n planar.x = 4.0 - v.x;\n\n } else if ( absV.x >= almostOne ) {\n\n float signX = sign( v.x );\n planar.x = v.z * signX + 2.0 * signX;\n\n } else if ( absV.y >= almostOne ) {\n\n float signY = sign( v.y );\n planar.x = v.x + 2.0 * signY + 2.0;\n planar.y = v.z * signY - 2.0;\n\n }\n\n\n return vec2( 0.125, 0.25 ) * planar + vec2( 0.375, 0.75 );\n\n }\n\n #endif\n\n#endif\n";
20055 THREE.ShaderChunk[
'shadowmap_pars_vertex'] =
"#ifdef USE_SHADOWMAP\n\n uniform float shadowDarkness[ MAX_SHADOWS ];\n uniform mat4 shadowMatrix[ MAX_SHADOWS ];\n varying vec4 vShadowCoord[ MAX_SHADOWS ];\n\n#endif";
20059 THREE.ShaderChunk[
'shadowmap_vertex'] =
"#ifdef USE_SHADOWMAP\n\n for ( int i = 0; i < MAX_SHADOWS; i ++ ) {\n\n vShadowCoord[ i ] = shadowMatrix[ i ] * worldPosition;\n\n }\n\n#endif";
20063 THREE.ShaderChunk[
'skinbase_vertex'] =
"#ifdef USE_SKINNING\n\n mat4 boneMatX = getBoneMatrix( skinIndex.x );\n mat4 boneMatY = getBoneMatrix( skinIndex.y );\n mat4 boneMatZ = getBoneMatrix( skinIndex.z );\n mat4 boneMatW = getBoneMatrix( skinIndex.w );\n\n#endif";
20067 THREE.ShaderChunk[
'skinning_pars_vertex'] =
"#ifdef USE_SKINNING\n\n uniform mat4 bindMatrix;\n uniform mat4 bindMatrixInverse;\n\n #ifdef BONE_TEXTURE\n\n uniform sampler2D boneTexture;\n uniform int boneTextureWidth;\n uniform int boneTextureHeight;\n\n mat4 getBoneMatrix( const in float i ) {\n\n float j = i * 4.0;\n float x = mod( j, float( boneTextureWidth ) );\n float y = floor( j / float( boneTextureWidth ) );\n\n float dx = 1.0 / float( boneTextureWidth );\n float dy = 1.0 / float( boneTextureHeight );\n\n y = dy * ( y + 0.5 );\n\n vec4 v1 = texture2D( boneTexture, vec2( dx * ( x + 0.5 ), y ) );\n vec4 v2 = texture2D( boneTexture, vec2( dx * ( x + 1.5 ), y ) );\n vec4 v3 = texture2D( boneTexture, vec2( dx * ( x + 2.5 ), y ) );\n vec4 v4 = texture2D( boneTexture, vec2( dx * ( x + 3.5 ), y ) );\n\n mat4 bone = mat4( v1, v2, v3, v4 );\n\n return bone;\n\n }\n\n #else\n\n uniform mat4 boneGlobalMatrices[ MAX_BONES ];\n\n mat4 getBoneMatrix( const in float i ) {\n\n mat4 bone = boneGlobalMatrices[ int(i) ];\n return bone;\n\n }\n\n #endif\n\n#endif\n";
20071 THREE.ShaderChunk[
'skinning_vertex'] =
"#ifdef USE_SKINNING\n\n vec4 skinVertex = bindMatrix * vec4( transformed, 1.0 );\n\n vec4 skinned = vec4( 0.0 );\n skinned += boneMatX * skinVertex * skinWeight.x;\n skinned += boneMatY * skinVertex * skinWeight.y;\n skinned += boneMatZ * skinVertex * skinWeight.z;\n skinned += boneMatW * skinVertex * skinWeight.w;\n skinned = bindMatrixInverse * skinned;\n\n#endif\n";
20075 THREE.ShaderChunk[
'skinnormal_vertex'] =
"#ifdef USE_SKINNING\n\n mat4 skinMatrix = mat4( 0.0 );\n skinMatrix += skinWeight.x * boneMatX;\n skinMatrix += skinWeight.y * boneMatY;\n skinMatrix += skinWeight.z * boneMatZ;\n skinMatrix += skinWeight.w * boneMatW;\n skinMatrix = bindMatrixInverse * skinMatrix * bindMatrix;\n\n objectNormal = vec4( skinMatrix * vec4( objectNormal, 0.0 ) ).xyz;\n\n#endif\n";
20079 THREE.ShaderChunk[
'specularmap_fragment'] =
"float specularStrength;\n\n#ifdef USE_SPECULARMAP\n\n vec4 texelSpecular = texture2D( specularMap, vUv );\n specularStrength = texelSpecular.r;\n\n#else\n\n specularStrength = 1.0;\n\n#endif";
20083 THREE.ShaderChunk[
'specularmap_pars_fragment'] =
"#ifdef USE_SPECULARMAP\n\n uniform sampler2D specularMap;\n\n#endif";
20087 THREE.ShaderChunk[
'uv2_pars_fragment'] =
"#if defined( USE_LIGHTMAP ) || defined( USE_AOMAP )\n\n varying vec2 vUv2;\n\n#endif";
20091 THREE.ShaderChunk[
'uv2_pars_vertex'] =
"#if defined( USE_LIGHTMAP ) || defined( USE_AOMAP )\n\n attribute vec2 uv2;\n varying vec2 vUv2;\n\n#endif";
20095 THREE.ShaderChunk[
'uv2_vertex'] =
"#if defined( USE_LIGHTMAP ) || defined( USE_AOMAP )\n\n vUv2 = uv2;\n\n#endif";
20099 THREE.ShaderChunk[
'uv_pars_fragment'] =
"#if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) || defined( USE_EMISSIVEMAP )\n\n varying vec2 vUv;\n\n#endif";
20103 THREE.ShaderChunk[
'uv_pars_vertex'] =
"#if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) || defined( USE_EMISSIVEMAP )\n\n varying vec2 vUv;\n uniform vec4 offsetRepeat;\n\n#endif\n";
20107 THREE.ShaderChunk[
'uv_vertex'] =
"#if defined( USE_MAP ) || defined( USE_BUMPMAP ) || defined( USE_NORMALMAP ) || defined( USE_SPECULARMAP ) || defined( USE_ALPHAMAP ) || defined( USE_EMISSIVEMAP )\n\n vUv = uv * offsetRepeat.zw + offsetRepeat.xy;\n\n#endif";
20111 THREE.ShaderChunk[
'worldpos_vertex'] =
"#if defined( USE_ENVMAP ) || defined( PHONG ) || defined( LAMBERT ) || defined ( USE_SHADOWMAP )\n\n #ifdef USE_SKINNING\n\n vec4 worldPosition = modelMatrix * skinned;\n\n #else\n\n vec4 worldPosition = modelMatrix * vec4( transformed, 1.0 );\n\n #endif\n\n#endif\n";
20119 THREE.UniformsUtils = {
20121 merge:
function ( uniforms ) {
20125 for ( var u = 0; u < uniforms.length; u ++ ) {
20127 var tmp = this.clone( uniforms[ u ] );
20129 for ( var p in tmp ) {
20131 merged[ p ] = tmp[ p ];
20141 clone:
function ( uniforms_src ) {
20143 var uniforms_dst = {};
20145 for ( var u in uniforms_src ) {
20147 uniforms_dst[ u ] = {};
20149 for ( var p in uniforms_src[ u ] ) {
20151 var parameter_src = uniforms_src[ u ][ p ];
20153 if ( parameter_src instanceof THREE.Color ||
20154 parameter_src instanceof THREE.Vector2 ||
20155 parameter_src instanceof THREE.Vector3 ||
20156 parameter_src instanceof THREE.Vector4 ||
20157 parameter_src instanceof THREE.Matrix3 ||
20158 parameter_src instanceof THREE.Matrix4 ||
20159 parameter_src instanceof THREE.Texture ) {
20161 uniforms_dst[ u ][ p ] = parameter_src.clone();
20163 }
else if ( Array.isArray( parameter_src ) ) {
20165 uniforms_dst[ u ][ p ] = parameter_src.slice();
20169 uniforms_dst[ u ][ p ] = parameter_src;
20177 return uniforms_dst;
20189 THREE.UniformsLib = {
20193 "diffuse" : { type:
"c", value:
new THREE.Color( 0xeeeeee ) },
20194 "opacity" : { type:
"f", value: 1.0 },
20196 "map" : { type:
"t", value: null },
20197 "offsetRepeat" : { type:
"v4", value:
new THREE.Vector4( 0, 0, 1, 1 ) },
20199 "specularMap" : { type:
"t", value: null },
20200 "alphaMap" : { type:
"t", value: null },
20202 "envMap" : { type:
"t", value: null },
20203 "flipEnvMap" : { type:
"f", value: - 1 },
20204 "reflectivity" : { type:
"f", value: 1.0 },
20205 "refractionRatio" : { type:
"f", value: 0.98 }
20211 "aoMap" : { type:
"t", value: null },
20212 "aoMapIntensity" : { type:
"f", value: 1 },
20218 "lightMap" : { type:
"t", value: null },
20219 "lightMapIntensity" : { type:
"f", value: 1 },
20225 "emissiveMap" : { type:
"t", value: null },
20231 "bumpMap" : { type:
"t", value: null },
20232 "bumpScale" : { type:
"f", value: 1 }
20238 "normalMap" : { type:
"t", value: null },
20239 "normalScale" : { type:
"v2", value:
new THREE.Vector2( 1, 1 ) }
20245 "displacementMap" : { type:
"t", value: null },
20246 "displacementScale" : { type:
"f", value: 1 },
20247 "displacementBias" : { type:
"f", value: 0 }
20253 "fogDensity" : { type:
"f", value: 0.00025 },
20254 "fogNear" : { type:
"f", value: 1 },
20255 "fogFar" : { type:
"f", value: 2000 },
20256 "fogColor" : { type:
"c", value:
new THREE.Color( 0xffffff ) }
20262 "ambientLightColor" : { type:
"fv", value: [] },
20264 "directionalLightDirection" : { type:
"fv", value: [] },
20265 "directionalLightColor" : { type:
"fv", value: [] },
20267 "hemisphereLightDirection" : { type:
"fv", value: [] },
20268 "hemisphereLightSkyColor" : { type:
"fv", value: [] },
20269 "hemisphereLightGroundColor" : { type:
"fv", value: [] },
20271 "pointLightColor" : { type:
"fv", value: [] },
20272 "pointLightPosition" : { type:
"fv", value: [] },
20273 "pointLightDistance" : { type:
"fv1", value: [] },
20274 "pointLightDecay" : { type:
"fv1", value: [] },
20276 "spotLightColor" : { type:
"fv", value: [] },
20277 "spotLightPosition" : { type:
"fv", value: [] },
20278 "spotLightDirection" : { type:
"fv", value: [] },
20279 "spotLightDistance" : { type:
"fv1", value: [] },
20280 "spotLightAngleCos" : { type:
"fv1", value: [] },
20281 "spotLightExponent" : { type:
"fv1", value: [] },
20282 "spotLightDecay" : { type:
"fv1", value: [] }
20288 "psColor" : { type:
"c", value:
new THREE.Color( 0xeeeeee ) },
20289 "opacity" : { type:
"f", value: 1.0 },
20290 "size" : { type:
"f", value: 1.0 },
20291 "scale" : { type:
"f", value: 1.0 },
20292 "map" : { type:
"t", value: null },
20293 "offsetRepeat" : { type:
"v4", value:
new THREE.Vector4( 0, 0, 1, 1 ) },
20295 "fogDensity" : { type:
"f", value: 0.00025 },
20296 "fogNear" : { type:
"f", value: 1 },
20297 "fogFar" : { type:
"f", value: 2000 },
20298 "fogColor" : { type:
"c", value:
new THREE.Color( 0xffffff ) }
20304 "shadowMap": { type:
"tv", value: [] },
20305 "shadowMapSize": { type:
"v2v", value: [] },
20307 "shadowBias" : { type:
"fv1", value: [] },
20308 "shadowDarkness": { type:
"fv1", value: [] },
20310 "shadowMatrix" : { type:
"m4v", value: [] }
20327 THREE.ShaderLib = {
20331 uniforms: THREE.UniformsUtils.merge( [
20333 THREE.UniformsLib[
"common" ],
20334 THREE.UniformsLib[
"aomap" ],
20335 THREE.UniformsLib[
"fog" ],
20336 THREE.UniformsLib[
"shadowmap" ]
20342 THREE.ShaderChunk[
"common" ],
20343 THREE.ShaderChunk[
"uv_pars_vertex" ],
20344 THREE.ShaderChunk[
"uv2_pars_vertex" ],
20345 THREE.ShaderChunk[
"envmap_pars_vertex" ],
20346 THREE.ShaderChunk[
"color_pars_vertex" ],
20347 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
20348 THREE.ShaderChunk[
"skinning_pars_vertex" ],
20349 THREE.ShaderChunk[
"shadowmap_pars_vertex" ],
20350 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20354 THREE.ShaderChunk[
"uv_vertex" ],
20355 THREE.ShaderChunk[
"uv2_vertex" ],
20356 THREE.ShaderChunk[
"color_vertex" ],
20357 THREE.ShaderChunk[
"skinbase_vertex" ],
20359 " #ifdef USE_ENVMAP",
20361 THREE.ShaderChunk[
"beginnormal_vertex" ],
20362 THREE.ShaderChunk[
"morphnormal_vertex" ],
20363 THREE.ShaderChunk[
"skinnormal_vertex" ],
20364 THREE.ShaderChunk[
"defaultnormal_vertex" ],
20368 THREE.ShaderChunk[
"begin_vertex" ],
20369 THREE.ShaderChunk[
"morphtarget_vertex" ],
20370 THREE.ShaderChunk[
"skinning_vertex" ],
20371 THREE.ShaderChunk[
"project_vertex" ],
20372 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20374 THREE.ShaderChunk[
"worldpos_vertex" ],
20375 THREE.ShaderChunk[
"envmap_vertex" ],
20376 THREE.ShaderChunk[
"shadowmap_vertex" ],
20384 "uniform vec3 diffuse;",
20385 "uniform float opacity;",
20387 THREE.ShaderChunk[
"common" ],
20388 THREE.ShaderChunk[
"color_pars_fragment" ],
20389 THREE.ShaderChunk[
"uv_pars_fragment" ],
20390 THREE.ShaderChunk[
"uv2_pars_fragment" ],
20391 THREE.ShaderChunk[
"map_pars_fragment" ],
20392 THREE.ShaderChunk[
"alphamap_pars_fragment" ],
20393 THREE.ShaderChunk[
"aomap_pars_fragment" ],
20394 THREE.ShaderChunk[
"envmap_pars_fragment" ],
20395 THREE.ShaderChunk[
"fog_pars_fragment" ],
20396 THREE.ShaderChunk[
"shadowmap_pars_fragment" ],
20397 THREE.ShaderChunk[
"specularmap_pars_fragment" ],
20398 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20402 " vec3 outgoingLight = vec3( 0.0 );",
20403 " vec4 diffuseColor = vec4( diffuse, opacity );",
20404 " vec3 totalAmbientLight = vec3( 1.0 );",
20405 " vec3 shadowMask = vec3( 1.0 );",
20407 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
20408 THREE.ShaderChunk[
"map_fragment" ],
20409 THREE.ShaderChunk[
"color_fragment" ],
20410 THREE.ShaderChunk[
"alphamap_fragment" ],
20411 THREE.ShaderChunk[
"alphatest_fragment" ],
20412 THREE.ShaderChunk[
"specularmap_fragment" ],
20413 THREE.ShaderChunk[
"aomap_fragment" ],
20414 THREE.ShaderChunk[
"shadowmap_fragment" ],
20416 " outgoingLight = diffuseColor.rgb * totalAmbientLight * shadowMask;",
20418 THREE.ShaderChunk[
"envmap_fragment" ],
20420 THREE.ShaderChunk[
"linear_to_gamma_fragment" ],
20422 THREE.ShaderChunk[
"fog_fragment" ],
20424 " gl_FragColor = vec4( outgoingLight, diffuseColor.a );",
20434 uniforms: THREE.UniformsUtils.merge( [
20436 THREE.UniformsLib[
"common" ],
20437 THREE.UniformsLib[
"fog" ],
20438 THREE.UniformsLib[
"lights" ],
20439 THREE.UniformsLib[
"shadowmap" ],
20442 "emissive" : { type:
"c", value:
new THREE.Color( 0x000000 ) }
20451 "varying vec3 vLightFront;",
20453 "#ifdef DOUBLE_SIDED",
20455 " varying vec3 vLightBack;",
20459 THREE.ShaderChunk[
"common" ],
20460 THREE.ShaderChunk[
"uv_pars_vertex" ],
20461 THREE.ShaderChunk[
"uv2_pars_vertex" ],
20462 THREE.ShaderChunk[
"envmap_pars_vertex" ],
20463 THREE.ShaderChunk[
"lights_lambert_pars_vertex" ],
20464 THREE.ShaderChunk[
"color_pars_vertex" ],
20465 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
20466 THREE.ShaderChunk[
"skinning_pars_vertex" ],
20467 THREE.ShaderChunk[
"shadowmap_pars_vertex" ],
20468 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20472 THREE.ShaderChunk[
"uv_vertex" ],
20473 THREE.ShaderChunk[
"uv2_vertex" ],
20474 THREE.ShaderChunk[
"color_vertex" ],
20476 THREE.ShaderChunk[
"beginnormal_vertex" ],
20477 THREE.ShaderChunk[
"morphnormal_vertex" ],
20478 THREE.ShaderChunk[
"skinbase_vertex" ],
20479 THREE.ShaderChunk[
"skinnormal_vertex" ],
20480 THREE.ShaderChunk[
"defaultnormal_vertex" ],
20482 THREE.ShaderChunk[
"begin_vertex" ],
20483 THREE.ShaderChunk[
"morphtarget_vertex" ],
20484 THREE.ShaderChunk[
"skinning_vertex" ],
20485 THREE.ShaderChunk[
"project_vertex" ],
20486 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20488 THREE.ShaderChunk[
"worldpos_vertex" ],
20489 THREE.ShaderChunk[
"envmap_vertex" ],
20490 THREE.ShaderChunk[
"lights_lambert_vertex" ],
20491 THREE.ShaderChunk[
"shadowmap_vertex" ],
20499 "uniform vec3 diffuse;",
20500 "uniform vec3 emissive;",
20501 "uniform float opacity;",
20503 "uniform vec3 ambientLightColor;",
20505 "varying vec3 vLightFront;",
20507 "#ifdef DOUBLE_SIDED",
20509 " varying vec3 vLightBack;",
20513 THREE.ShaderChunk[
"common" ],
20514 THREE.ShaderChunk[
"color_pars_fragment" ],
20515 THREE.ShaderChunk[
"uv_pars_fragment" ],
20516 THREE.ShaderChunk[
"uv2_pars_fragment" ],
20517 THREE.ShaderChunk[
"map_pars_fragment" ],
20518 THREE.ShaderChunk[
"alphamap_pars_fragment" ],
20519 THREE.ShaderChunk[
"envmap_pars_fragment" ],
20520 THREE.ShaderChunk[
"fog_pars_fragment" ],
20521 THREE.ShaderChunk[
"shadowmap_pars_fragment" ],
20522 THREE.ShaderChunk[
"specularmap_pars_fragment" ],
20523 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20527 " vec3 outgoingLight = vec3( 0.0 );",
20528 " vec4 diffuseColor = vec4( diffuse, opacity );",
20529 " vec3 totalAmbientLight = ambientLightColor;",
20530 " vec3 shadowMask = vec3( 1.0 );",
20532 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
20533 THREE.ShaderChunk[
"map_fragment" ],
20534 THREE.ShaderChunk[
"color_fragment" ],
20535 THREE.ShaderChunk[
"alphamap_fragment" ],
20536 THREE.ShaderChunk[
"alphatest_fragment" ],
20537 THREE.ShaderChunk[
"specularmap_fragment" ],
20538 THREE.ShaderChunk[
"shadowmap_fragment" ],
20540 " #ifdef DOUBLE_SIDED",
20542 " if ( gl_FrontFacing )",
20543 " outgoingLight += diffuseColor.rgb * ( vLightFront * shadowMask + totalAmbientLight ) + emissive;",
20545 " outgoingLight += diffuseColor.rgb * ( vLightBack * shadowMask + totalAmbientLight ) + emissive;",
20549 " outgoingLight += diffuseColor.rgb * ( vLightFront * shadowMask + totalAmbientLight ) + emissive;",
20553 THREE.ShaderChunk[
"envmap_fragment" ],
20555 THREE.ShaderChunk[
"linear_to_gamma_fragment" ],
20557 THREE.ShaderChunk[
"fog_fragment" ],
20559 " gl_FragColor = vec4( outgoingLight, diffuseColor.a );",
20569 uniforms: THREE.UniformsUtils.merge( [
20571 THREE.UniformsLib[
"common" ],
20572 THREE.UniformsLib[
"aomap" ],
20573 THREE.UniformsLib[
"lightmap" ],
20574 THREE.UniformsLib[
"emissivemap" ],
20575 THREE.UniformsLib[
"bumpmap" ],
20576 THREE.UniformsLib[
"normalmap" ],
20577 THREE.UniformsLib[
"displacementmap" ],
20578 THREE.UniformsLib[
"fog" ],
20579 THREE.UniformsLib[
"lights" ],
20580 THREE.UniformsLib[
"shadowmap" ],
20583 "emissive" : { type:
"c", value:
new THREE.Color( 0x000000 ) },
20584 "specular" : { type:
"c", value:
new THREE.Color( 0x111111 ) },
20585 "shininess": { type:
"f", value: 30 }
20594 "varying vec3 vViewPosition;",
20596 "#ifndef FLAT_SHADED",
20598 " varying vec3 vNormal;",
20602 THREE.ShaderChunk[
"common" ],
20603 THREE.ShaderChunk[
"uv_pars_vertex" ],
20604 THREE.ShaderChunk[
"uv2_pars_vertex" ],
20605 THREE.ShaderChunk[
"displacementmap_pars_vertex" ],
20606 THREE.ShaderChunk[
"envmap_pars_vertex" ],
20607 THREE.ShaderChunk[
"lights_phong_pars_vertex" ],
20608 THREE.ShaderChunk[
"color_pars_vertex" ],
20609 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
20610 THREE.ShaderChunk[
"skinning_pars_vertex" ],
20611 THREE.ShaderChunk[
"shadowmap_pars_vertex" ],
20612 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20616 THREE.ShaderChunk[
"uv_vertex" ],
20617 THREE.ShaderChunk[
"uv2_vertex" ],
20618 THREE.ShaderChunk[
"color_vertex" ],
20620 THREE.ShaderChunk[
"beginnormal_vertex" ],
20621 THREE.ShaderChunk[
"morphnormal_vertex" ],
20622 THREE.ShaderChunk[
"skinbase_vertex" ],
20623 THREE.ShaderChunk[
"skinnormal_vertex" ],
20624 THREE.ShaderChunk[
"defaultnormal_vertex" ],
20626 "#ifndef FLAT_SHADED",
20628 " vNormal = normalize( transformedNormal );",
20632 THREE.ShaderChunk[
"begin_vertex" ],
20633 THREE.ShaderChunk[
"displacementmap_vertex" ],
20634 THREE.ShaderChunk[
"morphtarget_vertex" ],
20635 THREE.ShaderChunk[
"skinning_vertex" ],
20636 THREE.ShaderChunk[
"project_vertex" ],
20637 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20639 " vViewPosition = - mvPosition.xyz;",
20641 THREE.ShaderChunk[
"worldpos_vertex" ],
20642 THREE.ShaderChunk[
"envmap_vertex" ],
20643 THREE.ShaderChunk[
"lights_phong_vertex" ],
20644 THREE.ShaderChunk[
"shadowmap_vertex" ],
20654 "uniform vec3 diffuse;",
20655 "uniform vec3 emissive;",
20656 "uniform vec3 specular;",
20657 "uniform float shininess;",
20658 "uniform float opacity;",
20660 THREE.ShaderChunk[
"common" ],
20661 THREE.ShaderChunk[
"color_pars_fragment" ],
20662 THREE.ShaderChunk[
"uv_pars_fragment" ],
20663 THREE.ShaderChunk[
"uv2_pars_fragment" ],
20664 THREE.ShaderChunk[
"map_pars_fragment" ],
20665 THREE.ShaderChunk[
"alphamap_pars_fragment" ],
20666 THREE.ShaderChunk[
"aomap_pars_fragment" ],
20667 THREE.ShaderChunk[
"lightmap_pars_fragment" ],
20668 THREE.ShaderChunk[
"emissivemap_pars_fragment" ],
20669 THREE.ShaderChunk[
"envmap_pars_fragment" ],
20670 THREE.ShaderChunk[
"fog_pars_fragment" ],
20671 THREE.ShaderChunk[
"lights_phong_pars_fragment" ],
20672 THREE.ShaderChunk[
"shadowmap_pars_fragment" ],
20673 THREE.ShaderChunk[
"bumpmap_pars_fragment" ],
20674 THREE.ShaderChunk[
"normalmap_pars_fragment" ],
20675 THREE.ShaderChunk[
"specularmap_pars_fragment" ],
20676 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20680 " vec3 outgoingLight = vec3( 0.0 );",
20681 " vec4 diffuseColor = vec4( diffuse, opacity );",
20682 " vec3 totalAmbientLight = ambientLightColor;",
20683 " vec3 totalEmissiveLight = emissive;",
20684 " vec3 shadowMask = vec3( 1.0 );",
20686 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
20687 THREE.ShaderChunk[
"map_fragment" ],
20688 THREE.ShaderChunk[
"color_fragment" ],
20689 THREE.ShaderChunk[
"alphamap_fragment" ],
20690 THREE.ShaderChunk[
"alphatest_fragment" ],
20691 THREE.ShaderChunk[
"specularmap_fragment" ],
20692 THREE.ShaderChunk[
"normal_phong_fragment" ],
20693 THREE.ShaderChunk[
"lightmap_fragment" ],
20694 THREE.ShaderChunk[
"hemilight_fragment" ],
20695 THREE.ShaderChunk[
"aomap_fragment" ],
20696 THREE.ShaderChunk[
"emissivemap_fragment" ],
20698 THREE.ShaderChunk[
"lights_phong_fragment" ],
20699 THREE.ShaderChunk[
"shadowmap_fragment" ],
20701 "totalDiffuseLight *= shadowMask;",
20702 "totalSpecularLight *= shadowMask;",
20706 " outgoingLight += diffuseColor.rgb * ( totalDiffuseLight + totalAmbientLight ) * specular + totalSpecularLight + totalEmissiveLight;",
20710 " outgoingLight += diffuseColor.rgb * ( totalDiffuseLight + totalAmbientLight ) + totalSpecularLight + totalEmissiveLight;",
20714 THREE.ShaderChunk[
"envmap_fragment" ],
20716 THREE.ShaderChunk[
"linear_to_gamma_fragment" ],
20718 THREE.ShaderChunk[
"fog_fragment" ],
20720 " gl_FragColor = vec4( outgoingLight, diffuseColor.a );",
20730 uniforms: THREE.UniformsUtils.merge( [
20732 THREE.UniformsLib[
"points" ],
20733 THREE.UniformsLib[
"shadowmap" ]
20739 "uniform float size;",
20740 "uniform float scale;",
20742 THREE.ShaderChunk[
"common" ],
20743 THREE.ShaderChunk[
"color_pars_vertex" ],
20744 THREE.ShaderChunk[
"shadowmap_pars_vertex" ],
20745 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20749 THREE.ShaderChunk[
"color_vertex" ],
20751 " vec4 mvPosition = modelViewMatrix * vec4( position, 1.0 );",
20753 " #ifdef USE_SIZEATTENUATION",
20754 " gl_PointSize = size * ( scale / length( mvPosition.xyz ) );",
20756 " gl_PointSize = size;",
20759 " gl_Position = projectionMatrix * mvPosition;",
20761 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20762 THREE.ShaderChunk[
"worldpos_vertex" ],
20763 THREE.ShaderChunk[
"shadowmap_vertex" ],
20771 "uniform vec3 psColor;",
20772 "uniform float opacity;",
20774 THREE.ShaderChunk[
"common" ],
20775 THREE.ShaderChunk[
"color_pars_fragment" ],
20776 THREE.ShaderChunk[
"map_particle_pars_fragment" ],
20777 THREE.ShaderChunk[
"fog_pars_fragment" ],
20778 THREE.ShaderChunk[
"shadowmap_pars_fragment" ],
20779 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20783 " vec3 outgoingLight = vec3( 0.0 );",
20784 " vec4 diffuseColor = vec4( psColor, opacity );",
20785 " vec3 shadowMask = vec3( 1.0 );",
20787 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
20788 THREE.ShaderChunk[
"map_particle_fragment" ],
20789 THREE.ShaderChunk[
"color_fragment" ],
20790 THREE.ShaderChunk[
"alphatest_fragment" ],
20791 THREE.ShaderChunk[
"shadowmap_fragment" ],
20793 " outgoingLight = diffuseColor.rgb * shadowMask;",
20795 THREE.ShaderChunk[
"fog_fragment" ],
20797 " gl_FragColor = vec4( outgoingLight, diffuseColor.a );",
20807 uniforms: THREE.UniformsUtils.merge( [
20809 THREE.UniformsLib[
"common" ],
20810 THREE.UniformsLib[
"fog" ],
20813 "scale" : { type:
"f", value: 1 },
20814 "dashSize" : { type:
"f", value: 1 },
20815 "totalSize": { type:
"f", value: 2 }
20822 "uniform float scale;",
20823 "attribute float lineDistance;",
20825 "varying float vLineDistance;",
20827 THREE.ShaderChunk[
"common" ],
20828 THREE.ShaderChunk[
"color_pars_vertex" ],
20829 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20833 THREE.ShaderChunk[
"color_vertex" ],
20835 " vLineDistance = scale * lineDistance;",
20837 " vec4 mvPosition = modelViewMatrix * vec4( position, 1.0 );",
20838 " gl_Position = projectionMatrix * mvPosition;",
20840 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20848 "uniform vec3 diffuse;",
20849 "uniform float opacity;",
20851 "uniform float dashSize;",
20852 "uniform float totalSize;",
20854 "varying float vLineDistance;",
20856 THREE.ShaderChunk[
"common" ],
20857 THREE.ShaderChunk[
"color_pars_fragment" ],
20858 THREE.ShaderChunk[
"fog_pars_fragment" ],
20859 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20863 " if ( mod( vLineDistance, totalSize ) > dashSize ) {",
20869 " vec3 outgoingLight = vec3( 0.0 );",
20870 " vec4 diffuseColor = vec4( diffuse, opacity );",
20872 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
20873 THREE.ShaderChunk[
"color_fragment" ],
20875 " outgoingLight = diffuseColor.rgb;",
20877 THREE.ShaderChunk[
"fog_fragment" ],
20879 " gl_FragColor = vec4( outgoingLight, diffuseColor.a );",
20891 "mNear": { type:
"f", value: 1.0 },
20892 "mFar" : { type:
"f", value: 2000.0 },
20893 "opacity" : { type:
"f", value: 1.0 }
20899 THREE.ShaderChunk[
"common" ],
20900 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
20901 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20905 THREE.ShaderChunk[
"begin_vertex" ],
20906 THREE.ShaderChunk[
"morphtarget_vertex" ],
20907 THREE.ShaderChunk[
"project_vertex" ],
20908 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20916 "uniform float mNear;",
20917 "uniform float mFar;",
20918 "uniform float opacity;",
20920 THREE.ShaderChunk[
"common" ],
20921 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20925 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
20927 " #ifdef USE_LOGDEPTHBUF_EXT",
20929 " float depth = gl_FragDepthEXT / gl_FragCoord.w;",
20933 " float depth = gl_FragCoord.z / gl_FragCoord.w;",
20937 " float color = 1.0 - smoothstep( mNear, mFar, depth );",
20938 " gl_FragColor = vec4( vec3( color ), opacity );",
20950 "opacity" : { type:
"f", value: 1.0 }
20956 "varying vec3 vNormal;",
20958 THREE.ShaderChunk[
"common" ],
20959 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
20960 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
20964 " vNormal = normalize( normalMatrix * normal );",
20966 THREE.ShaderChunk[
"begin_vertex" ],
20967 THREE.ShaderChunk[
"morphtarget_vertex" ],
20968 THREE.ShaderChunk[
"project_vertex" ],
20969 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
20977 "uniform float opacity;",
20978 "varying vec3 vNormal;",
20980 THREE.ShaderChunk[
"common" ],
20981 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
20985 " gl_FragColor = vec4( 0.5 * normalize( vNormal ) + 0.5, opacity );",
20987 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
21001 uniforms: {
"tCube": { type:
"t", value: null },
21002 "tFlip": { type:
"f", value: - 1 } },
21006 "varying vec3 vWorldPosition;",
21008 THREE.ShaderChunk[
"common" ],
21009 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
21013 " vWorldPosition = transformDirection( position, modelMatrix );",
21015 " gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );",
21017 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
21025 "uniform samplerCube tCube;",
21026 "uniform float tFlip;",
21028 "varying vec3 vWorldPosition;",
21030 THREE.ShaderChunk[
"common" ],
21031 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
21035 " gl_FragColor = textureCube( tCube, vec3( tFlip * vWorldPosition.x, vWorldPosition.yz ) );",
21037 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
21051 uniforms: {
"tEquirect": { type:
"t", value: null },
21052 "tFlip": { type:
"f", value: - 1 } },
21056 "varying vec3 vWorldPosition;",
21058 THREE.ShaderChunk[
"common" ],
21059 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
21063 " vWorldPosition = transformDirection( position, modelMatrix );",
21065 " gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );",
21067 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
21075 "uniform sampler2D tEquirect;",
21076 "uniform float tFlip;",
21078 "varying vec3 vWorldPosition;",
21080 THREE.ShaderChunk[
"common" ],
21081 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
21086 "vec3 direction = normalize( vWorldPosition );",
21088 "sampleUV.y = saturate( tFlip * direction.y * -0.5 + 0.5 );",
21089 "sampleUV.x = atan( direction.z, direction.x ) * RECIPROCAL_PI2 + 0.5;",
21090 "gl_FragColor = texture2D( tEquirect, sampleUV );",
21092 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
21118 THREE.ShaderChunk[
"common" ],
21119 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
21120 THREE.ShaderChunk[
"skinning_pars_vertex" ],
21121 THREE.ShaderChunk[
"logdepthbuf_pars_vertex" ],
21125 THREE.ShaderChunk[
"skinbase_vertex" ],
21127 THREE.ShaderChunk[
"begin_vertex" ],
21128 THREE.ShaderChunk[
"morphtarget_vertex" ],
21129 THREE.ShaderChunk[
"skinning_vertex" ],
21130 THREE.ShaderChunk[
"project_vertex" ],
21131 THREE.ShaderChunk[
"logdepthbuf_vertex" ],
21139 THREE.ShaderChunk[
"common" ],
21140 THREE.ShaderChunk[
"logdepthbuf_pars_fragment" ],
21142 "vec4 pack_depth( const in float depth ) {",
21144 " const vec4 bit_shift = vec4( 256.0 * 256.0 * 256.0, 256.0 * 256.0, 256.0, 1.0 );",
21145 " const vec4 bit_mask = vec4( 0.0, 1.0 / 256.0, 1.0 / 256.0, 1.0 / 256.0 );",
21146 " vec4 res = mod( depth * bit_shift * vec4( 255 ), vec4( 256 ) ) / vec4( 255 );",
21147 " res -= res.xxyz * bit_mask;",
21154 THREE.ShaderChunk[
"logdepthbuf_fragment" ],
21156 " #ifdef USE_LOGDEPTHBUF_EXT",
21158 " gl_FragData[ 0 ] = pack_depth( gl_FragDepthEXT );",
21162 " gl_FragData[ 0 ] = pack_depth( gl_FragCoord.z );",
21182 "lightPos": { type:
"v3", value:
new THREE.Vector3( 0, 0, 0 ) }
21188 "varying vec4 vWorldPosition;",
21190 THREE.ShaderChunk[
"common" ],
21191 THREE.ShaderChunk[
"morphtarget_pars_vertex" ],
21192 THREE.ShaderChunk[
"skinning_pars_vertex" ],
21196 THREE.ShaderChunk[
"skinbase_vertex" ],
21197 THREE.ShaderChunk[
"begin_vertex" ],
21198 THREE.ShaderChunk[
"morphtarget_vertex" ],
21199 THREE.ShaderChunk[
"skinning_vertex" ],
21200 THREE.ShaderChunk[
"project_vertex" ],
21201 THREE.ShaderChunk[
"worldpos_vertex" ],
21203 "vWorldPosition = worldPosition;",
21211 "uniform vec3 lightPos;",
21212 "varying vec4 vWorldPosition;",
21214 THREE.ShaderChunk[
"common" ],
21216 "vec4 pack1K ( float depth ) {",
21218 " depth /= 1000.0;",
21219 " const vec4 bitSh = vec4( 256.0 * 256.0 * 256.0, 256.0 * 256.0, 256.0, 1.0 );",
21220 " const vec4 bitMsk = vec4( 0.0, 1.0 / 256.0, 1.0 / 256.0, 1.0 / 256.0 );",
21221 " vec4 res = fract( depth * bitSh );",
21222 " res -= res.xxyz * bitMsk;",
21227 "float unpack1K ( vec4 color ) {",
21229 " const vec4 bitSh = vec4( 1.0 / ( 256.0 * 256.0 * 256.0 ), 1.0 / ( 256.0 * 256.0 ), 1.0 / 256.0, 1.0 );",
21230 " return dot( color, bitSh ) * 1000.0;",
21236 " gl_FragColor = pack1K( length( vWorldPosition.xyz - lightPos.xyz ) );",
21255 THREE.WebGLRenderer =
function ( parameters ) {
21257 console.log(
'THREE.WebGLRenderer', THREE.REVISION );
21259 parameters = parameters || {};
21261 var _canvas = parameters.canvas !== undefined ? parameters.canvas : document.createElement(
'canvas' ),
21262 _context = parameters.context !== undefined ? parameters.context : null,
21264 _width = _canvas.width,
21265 _height = _canvas.height,
21269 _alpha = parameters.alpha !== undefined ? parameters.alpha :
false,
21270 _depth = parameters.depth !== undefined ? parameters.depth :
true,
21271 _stencil = parameters.stencil !== undefined ? parameters.stencil :
true,
21272 _antialias = parameters.antialias !== undefined ? parameters.antialias :
false,
21273 _premultipliedAlpha = parameters.premultipliedAlpha !== undefined ? parameters.premultipliedAlpha :
true,
21274 _preserveDrawingBuffer = parameters.preserveDrawingBuffer !== undefined ? parameters.preserveDrawingBuffer :
false,
21276 _clearColor =
new THREE.Color( 0x000000 ),
21281 var opaqueObjects = [];
21282 var opaqueObjectsLastIndex = - 1;
21283 var transparentObjects = [];
21284 var transparentObjectsLastIndex = - 1;
21286 var morphInfluences =
new Float32Array( 8 );
21290 var lensFlares = [];
21294 this.domElement = _canvas;
21295 this.context = null;
21299 this.autoClear =
true;
21300 this.autoClearColor =
true;
21301 this.autoClearDepth =
true;
21302 this.autoClearStencil =
true;
21306 this.sortObjects =
true;
21310 this.gammaFactor = 2.0;
21311 this.gammaInput =
false;
21312 this.gammaOutput =
false;
21316 this.maxMorphTargets = 8;
21317 this.maxMorphNormals = 4;
21321 this.autoScaleCubemaps =
true;
21329 _currentProgram = null,
21330 _currentFramebuffer = null,
21331 _currentMaterialId = - 1,
21332 _currentGeometryProgram =
'',
21333 _currentCamera = null,
21335 _usedTextureUnits = 0,
21339 _viewportWidth = _canvas.width,
21340 _viewportHeight = _canvas.height,
21342 _currentHeight = 0,
21346 _frustum =
new THREE.Frustum(),
21350 _projScreenMatrix =
new THREE.Matrix4(),
21352 _vector3 =
new THREE.Vector3(),
21356 _direction =
new THREE.Vector3(),
21358 _lightsNeedUpdate =
true,
21362 ambient: [ 0, 0, 0 ],
21363 directional: { length: 0, colors: [], positions: [] },
21364 point: { length: 0, colors: [], positions: [], distances: [], decays: [] },
21365 spot: { length: 0, colors: [], positions: [], distances: [], directions: [], anglesCos: [], exponents: [], decays: [] },
21366 hemi: { length: 0, skyColors: [], groundColors: [], positions: [] }
21390 render: _infoRender,
21391 memory: _infoMemory,
21407 antialias: _antialias,
21408 premultipliedAlpha: _premultipliedAlpha,
21409 preserveDrawingBuffer: _preserveDrawingBuffer
21412 _gl = _context || _canvas.getContext(
'webgl', attributes ) || _canvas.getContext(
'experimental-webgl', attributes );
21414 if ( _gl === null ) {
21416 if ( _canvas.getContext(
'webgl' ) !== null ) {
21418 throw 'Error creating WebGL context with your selected attributes.';
21422 throw 'Error creating WebGL context.';
21428 _canvas.addEventListener(
'webglcontextlost', onContextLost,
false );
21430 }
catch ( error ) {
21432 console.error(
'THREE.WebGLRenderer: ' + error );
21436 var extensions =
new THREE.WebGLExtensions( _gl );
21438 extensions.get(
'OES_texture_float' );
21439 extensions.get(
'OES_texture_float_linear' );
21440 extensions.get(
'OES_texture_half_float' );
21441 extensions.get(
'OES_texture_half_float_linear' );
21442 extensions.get(
'OES_standard_derivatives' );
21443 extensions.get(
'ANGLE_instanced_arrays' );
21445 if ( extensions.get(
'OES_element_index_uint' ) ) {
21447 THREE.BufferGeometry.MaxIndex = 4294967296;
21451 var capabilities =
new THREE.WebGLCapabilities( _gl, extensions, parameters );
21453 var state =
new THREE.WebGLState( _gl, extensions, paramThreeToGL );
21454 var properties =
new THREE.WebGLProperties();
21455 var objects =
new THREE.WebGLObjects( _gl, properties, this.info );
21456 var programCache =
new THREE.WebGLPrograms(
this, capabilities );
21458 this.info.programs = programCache.programs;
21460 var bufferRenderer =
new THREE.WebGLBufferRenderer( _gl, extensions, _infoRender );
21461 var indexedBufferRenderer =
new THREE.WebGLIndexedBufferRenderer( _gl, extensions, _infoRender );
21465 function glClearColor( r, g, b, a ) {
21467 if ( _premultipliedAlpha ===
true ) {
21469 r *= a; g *= a; b *= a;
21473 _gl.clearColor( r, g, b, a );
21477 function setDefaultGLState() {
21481 _gl.viewport( _viewportX, _viewportY, _viewportWidth, _viewportHeight );
21483 glClearColor( _clearColor.r, _clearColor.g, _clearColor.b, _clearAlpha );
21487 function resetGLState() {
21489 _currentProgram = null;
21490 _currentCamera = null;
21492 _currentGeometryProgram =
'';
21493 _currentMaterialId = - 1;
21495 _lightsNeedUpdate =
true;
21501 setDefaultGLState();
21503 this.context = _gl;
21504 this.capabilities = capabilities;
21505 this.extensions = extensions;
21506 this.state = state;
21510 var shadowMap =
new THREE.WebGLShadowMap(
this, lights, objects );
21512 this.shadowMap = shadowMap;
21517 var spritePlugin =
new THREE.SpritePlugin(
this, sprites );
21518 var lensFlarePlugin =
new THREE.LensFlarePlugin(
this, lensFlares );
21522 this.getContext =
function () {
21528 this.getContextAttributes =
function () {
21530 return _gl.getContextAttributes();
21534 this.forceContextLoss =
function () {
21536 extensions.get(
'WEBGL_lose_context' ).loseContext();
21540 this.getMaxAnisotropy = (
function () {
21544 return function getMaxAnisotropy() {
21546 if ( value !== undefined )
return value;
21548 var extension = extensions.get(
'EXT_texture_filter_anisotropic' );
21550 if ( extension !== null ) {
21552 value = _gl.getParameter( extension.MAX_TEXTURE_MAX_ANISOTROPY_EXT );
21566 this.getPrecision =
function () {
21568 return capabilities.precision;
21572 this.getPixelRatio =
function () {
21578 this.setPixelRatio =
function ( value ) {
21580 if ( value !== undefined ) pixelRatio = value;
21584 this.getSize =
function () {
21593 this.setSize =
function ( width, height, updateStyle ) {
21598 _canvas.width = width * pixelRatio;
21599 _canvas.height = height * pixelRatio;
21601 if ( updateStyle !==
false ) {
21603 _canvas.style.width = width +
'px';
21604 _canvas.style.height = height +
'px';
21608 this.setViewport( 0, 0, width, height );
21612 this.setViewport =
function ( x, y, width, height ) {
21614 _viewportX = x * pixelRatio;
21615 _viewportY = y * pixelRatio;
21617 _viewportWidth = width * pixelRatio;
21618 _viewportHeight = height * pixelRatio;
21620 _gl.viewport( _viewportX, _viewportY, _viewportWidth, _viewportHeight );
21624 this.getViewport =
function ( dimensions ) {
21626 dimensions.x = _viewportX / pixelRatio;
21627 dimensions.y = _viewportY / pixelRatio;
21629 dimensions.z = _viewportWidth / pixelRatio;
21630 dimensions.w = _viewportHeight / pixelRatio;
21634 this.setScissor =
function ( x, y, width, height ) {
21639 width * pixelRatio,
21640 height * pixelRatio
21645 this.enableScissorTest =
function ( boolean ) {
21647 state.setScissorTest(
boolean );
21653 this.getClearColor =
function () {
21655 return _clearColor;
21659 this.setClearColor =
function ( color, alpha ) {
21661 _clearColor.set( color );
21663 _clearAlpha = alpha !== undefined ? alpha : 1;
21665 glClearColor( _clearColor.r, _clearColor.g, _clearColor.b, _clearAlpha );
21669 this.getClearAlpha =
function () {
21671 return _clearAlpha;
21675 this.setClearAlpha =
function ( alpha ) {
21677 _clearAlpha = alpha;
21679 glClearColor( _clearColor.r, _clearColor.g, _clearColor.b, _clearAlpha );
21683 this.clear =
function ( color, depth, stencil ) {
21687 if ( color === undefined || color ) bits |= _gl.COLOR_BUFFER_BIT;
21688 if ( depth === undefined || depth ) bits |= _gl.DEPTH_BUFFER_BIT;
21689 if ( stencil === undefined || stencil ) bits |= _gl.STENCIL_BUFFER_BIT;
21695 this.clearColor =
function () {
21697 _gl.clear( _gl.COLOR_BUFFER_BIT );
21701 this.clearDepth =
function () {
21703 _gl.clear( _gl.DEPTH_BUFFER_BIT );
21707 this.clearStencil =
function () {
21709 _gl.clear( _gl.STENCIL_BUFFER_BIT );
21713 this.clearTarget =
function ( renderTarget, color, depth, stencil ) {
21715 this.setRenderTarget( renderTarget );
21716 this.clear( color, depth, stencil );
21722 this.resetGLState = resetGLState;
21724 this.dispose =
function() {
21726 _canvas.removeEventListener(
'webglcontextlost', onContextLost,
false );
21732 function onContextLost( event ) {
21734 event.preventDefault();
21737 setDefaultGLState();
21739 properties.clear();
21743 function onTextureDispose( event ) {
21745 var texture =
event.target;
21747 texture.removeEventListener(
'dispose', onTextureDispose );
21749 deallocateTexture( texture );
21751 _infoMemory.textures --;
21756 function onRenderTargetDispose( event ) {
21758 var renderTarget =
event.target;
21760 renderTarget.removeEventListener(
'dispose', onRenderTargetDispose );
21762 deallocateRenderTarget( renderTarget );
21764 _infoMemory.textures --;
21768 function onMaterialDispose( event ) {
21770 var material =
event.target;
21772 material.removeEventListener(
'dispose', onMaterialDispose );
21774 deallocateMaterial( material );
21780 function deallocateTexture( texture ) {
21782 var textureProperties = properties.get( texture );
21784 if ( texture.image && textureProperties.__image__webglTextureCube ) {
21788 _gl.deleteTexture( textureProperties.__image__webglTextureCube );
21794 if ( textureProperties.__webglInit === undefined )
return;
21796 _gl.deleteTexture( textureProperties.__webglTexture );
21801 properties.delete( texture );
21805 function deallocateRenderTarget( renderTarget ) {
21807 var renderTargetProperties = properties.get( renderTarget );
21808 var textureProperties = properties.get( renderTarget.texture );
21810 if ( ! renderTarget || textureProperties.__webglTexture === undefined )
return;
21812 _gl.deleteTexture( textureProperties.__webglTexture );
21814 if ( renderTarget instanceof THREE.WebGLRenderTargetCube ) {
21816 for ( var i = 0; i < 6; i ++ ) {
21818 _gl.deleteFramebuffer( renderTargetProperties.__webglFramebuffer[ i ] );
21819 _gl.deleteRenderbuffer( renderTargetProperties.__webglRenderbuffer[ i ] );
21825 _gl.deleteFramebuffer( renderTargetProperties.__webglFramebuffer );
21826 _gl.deleteRenderbuffer( renderTargetProperties.__webglRenderbuffer );
21830 properties.delete( renderTarget.texture );
21831 properties.delete( renderTarget );
21835 function deallocateMaterial( material ) {
21837 releaseMaterialProgramReference( material );
21839 properties.delete( material );
21844 function releaseMaterialProgramReference( material ) {
21846 var programInfo = properties.get( material ).program;
21848 material.program = undefined;
21850 if ( programInfo !== undefined ) {
21852 programCache.releaseProgram( programInfo );
21860 this.renderBufferImmediate =
function ( object, program, material ) {
21862 state.initAttributes();
21864 var buffers = properties.get(
object );
21866 if (
object.hasPositions && ! buffers.position ) buffers.position = _gl.createBuffer();
21867 if (
object.hasNormals && ! buffers.normal ) buffers.normal = _gl.createBuffer();
21868 if (
object.hasUvs && ! buffers.uv ) buffers.uv = _gl.createBuffer();
21869 if (
object.hasColors && ! buffers.color ) buffers.color = _gl.createBuffer();
21871 var attributes = program.getAttributes();
21873 if (
object.hasPositions ) {
21875 _gl.bindBuffer( _gl.ARRAY_BUFFER, buffers.position );
21876 _gl.bufferData( _gl.ARRAY_BUFFER,
object.positionArray, _gl.DYNAMIC_DRAW );
21878 state.enableAttribute( attributes.position );
21879 _gl.vertexAttribPointer( attributes.position, 3, _gl.FLOAT,
false, 0, 0 );
21883 if (
object.hasNormals ) {
21885 _gl.bindBuffer( _gl.ARRAY_BUFFER, buffers.normal );
21887 if ( material.type !==
'MeshPhongMaterial' && material.shading === THREE.FlatShading ) {
21889 for ( var i = 0, l =
object.count * 3; i < l; i += 9 ) {
21891 var array =
object.normalArray;
21893 var nx = ( array[ i + 0 ] + array[ i + 3 ] + array[ i + 6 ] ) / 3;
21894 var ny = ( array[ i + 1 ] + array[ i + 4 ] + array[ i + 7 ] ) / 3;
21895 var nz = ( array[ i + 2 ] + array[ i + 5 ] + array[ i + 8 ] ) / 3;
21897 array[ i + 0 ] = nx;
21898 array[ i + 1 ] = ny;
21899 array[ i + 2 ] = nz;
21901 array[ i + 3 ] = nx;
21902 array[ i + 4 ] = ny;
21903 array[ i + 5 ] = nz;
21905 array[ i + 6 ] = nx;
21906 array[ i + 7 ] = ny;
21907 array[ i + 8 ] = nz;
21913 _gl.bufferData( _gl.ARRAY_BUFFER,
object.normalArray, _gl.DYNAMIC_DRAW );
21915 state.enableAttribute( attributes.normal );
21917 _gl.vertexAttribPointer( attributes.normal, 3, _gl.FLOAT,
false, 0, 0 );
21921 if (
object.hasUvs && material.map ) {
21923 _gl.bindBuffer( _gl.ARRAY_BUFFER, buffers.uv );
21924 _gl.bufferData( _gl.ARRAY_BUFFER,
object.uvArray, _gl.DYNAMIC_DRAW );
21926 state.enableAttribute( attributes.uv );
21928 _gl.vertexAttribPointer( attributes.uv, 2, _gl.FLOAT,
false, 0, 0 );
21932 if (
object.hasColors && material.vertexColors !== THREE.NoColors ) {
21934 _gl.bindBuffer( _gl.ARRAY_BUFFER, buffers.color );
21935 _gl.bufferData( _gl.ARRAY_BUFFER,
object.colorArray, _gl.DYNAMIC_DRAW );
21937 state.enableAttribute( attributes.color );
21939 _gl.vertexAttribPointer( attributes.color, 3, _gl.FLOAT,
false, 0, 0 );
21943 state.disableUnusedAttributes();
21945 _gl.drawArrays( _gl.TRIANGLES, 0,
object.count );
21951 this.renderBufferDirect =
function ( camera, lights, fog, geometry, material, object, group ) {
21953 setMaterial( material );
21955 var program = setProgram( camera, lights, fog, material,
object );
21957 var updateBuffers =
false;
21958 var geometryProgram = geometry.id +
'_' + program.id +
'_' + material.wireframe;
21960 if ( geometryProgram !== _currentGeometryProgram ) {
21962 _currentGeometryProgram = geometryProgram;
21963 updateBuffers =
true;
21969 var morphTargetInfluences =
object.morphTargetInfluences;
21971 if ( morphTargetInfluences !== undefined ) {
21973 var activeInfluences = [];
21975 for ( var i = 0, l = morphTargetInfluences.length; i < l; i ++ ) {
21977 var influence = morphTargetInfluences[ i ];
21978 activeInfluences.push( [ influence, i ] );
21982 activeInfluences.sort( numericalSort );
21984 if ( activeInfluences.length > 8 ) {
21986 activeInfluences.length = 8;
21990 var morphAttributes = geometry.morphAttributes;
21992 for ( var i = 0, l = activeInfluences.length; i < l; i ++ ) {
21994 var influence = activeInfluences[ i ];
21995 morphInfluences[ i ] = influence[ 0 ];
21997 if ( influence[ 0 ] !== 0 ) {
21999 var index = influence[ 1 ];
22001 if ( material.morphTargets ===
true && morphAttributes.position ) geometry.addAttribute(
'morphTarget' + i, morphAttributes.position[ index ] );
22002 if ( material.morphNormals ===
true && morphAttributes.normal ) geometry.addAttribute(
'morphNormal' + i, morphAttributes.normal[ index ] );
22006 if ( material.morphTargets ===
true ) geometry.removeAttribute(
'morphTarget' + i );
22007 if ( material.morphNormals ===
true ) geometry.removeAttribute(
'morphNormal' + i );
22013 var uniforms = program.getUniforms();
22015 if ( uniforms.morphTargetInfluences !== null ) {
22017 _gl.uniform1fv( uniforms.morphTargetInfluences, morphInfluences );
22021 updateBuffers =
true;
22027 var index = geometry.index;
22028 var position = geometry.attributes.position;
22030 if ( material.wireframe ===
true ) {
22032 index = objects.getWireframeAttribute( geometry );
22038 if ( index !== null ) {
22040 renderer = indexedBufferRenderer;
22041 renderer.setIndex( index );
22045 renderer = bufferRenderer;
22049 if ( updateBuffers ) {
22051 setupVertexAttributes( material, program, geometry );
22053 if ( index !== null ) {
22055 _gl.bindBuffer( _gl.ELEMENT_ARRAY_BUFFER, objects.getAttributeBuffer( index ) );
22064 var dataCount = Infinity;
22066 if ( index !== null ) {
22068 dataCount = index.count
22070 }
else if ( position !== undefined ) {
22072 dataCount = position.count;
22076 var rangeStart = geometry.drawRange.start;
22077 var rangeCount = geometry.drawRange.count;
22079 var groupStart = group !== null ? group.start : 0;
22080 var groupCount = group !== null ? group.count : Infinity;
22082 var drawStart = Math.max( dataStart, rangeStart, groupStart );
22083 var drawEnd = Math.min( dataStart + dataCount, rangeStart + rangeCount, groupStart + groupCount ) - 1;
22085 var drawCount = Math.max( 0, drawEnd - drawStart + 1 );
22089 if (
object instanceof THREE.Mesh ) {
22091 if ( material.wireframe ===
true ) {
22093 state.setLineWidth( material.wireframeLinewidth * pixelRatio );
22094 renderer.setMode( _gl.LINES );
22098 renderer.setMode( _gl.TRIANGLES );
22102 if ( geometry instanceof THREE.InstancedBufferGeometry && geometry.maxInstancedCount > 0 ) {
22104 renderer.renderInstances( geometry );
22108 renderer.render( drawStart, drawCount );
22112 }
else if (
object instanceof THREE.Line ) {
22114 var lineWidth = material.linewidth;
22116 if ( lineWidth === undefined ) lineWidth = 1;
22118 state.setLineWidth( lineWidth * pixelRatio );
22120 if (
object instanceof THREE.LineSegments ) {
22122 renderer.setMode( _gl.LINES );
22126 renderer.setMode( _gl.LINE_STRIP );
22130 renderer.render( drawStart, drawCount );
22132 }
else if (
object instanceof THREE.Points ) {
22134 renderer.setMode( _gl.POINTS );
22135 renderer.render( drawStart, drawCount );
22141 function setupVertexAttributes( material, program, geometry, startIndex ) {
22145 if ( geometry instanceof THREE.InstancedBufferGeometry ) {
22147 extension = extensions.get(
'ANGLE_instanced_arrays' );
22149 if ( extension === null ) {
22151 console.error(
'THREE.WebGLRenderer.setupVertexAttributes: using THREE.InstancedBufferGeometry but hardware does not support extension ANGLE_instanced_arrays.' );
22158 if ( startIndex === undefined ) startIndex = 0;
22160 state.initAttributes();
22162 var geometryAttributes = geometry.attributes;
22164 var programAttributes = program.getAttributes();
22166 var materialDefaultAttributeValues = material.defaultAttributeValues;
22168 for ( var name in programAttributes ) {
22170 var programAttribute = programAttributes[ name ];
22172 if ( programAttribute >= 0 ) {
22174 var geometryAttribute = geometryAttributes[ name ];
22176 if ( geometryAttribute !== undefined ) {
22178 var size = geometryAttribute.itemSize;
22179 var buffer = objects.getAttributeBuffer( geometryAttribute );
22181 if ( geometryAttribute instanceof THREE.InterleavedBufferAttribute ) {
22183 var data = geometryAttribute.data;
22184 var stride = data.stride;
22185 var offset = geometryAttribute.offset;
22187 if ( data instanceof THREE.InstancedInterleavedBuffer ) {
22189 state.enableAttributeAndDivisor( programAttribute, data.meshPerAttribute, extension );
22191 if ( geometry.maxInstancedCount === undefined ) {
22193 geometry.maxInstancedCount = data.meshPerAttribute * data.count;
22199 state.enableAttribute( programAttribute );
22203 _gl.bindBuffer( _gl.ARRAY_BUFFER, buffer );
22204 _gl.vertexAttribPointer( programAttribute, size, _gl.FLOAT,
false, stride * data.array.BYTES_PER_ELEMENT, ( startIndex * stride + offset ) * data.array.BYTES_PER_ELEMENT );
22208 if ( geometryAttribute instanceof THREE.InstancedBufferAttribute ) {
22210 state.enableAttributeAndDivisor( programAttribute, geometryAttribute.meshPerAttribute, extension );
22212 if ( geometry.maxInstancedCount === undefined ) {
22214 geometry.maxInstancedCount = geometryAttribute.meshPerAttribute * geometryAttribute.count;
22220 state.enableAttribute( programAttribute );
22224 _gl.bindBuffer( _gl.ARRAY_BUFFER, buffer );
22225 _gl.vertexAttribPointer( programAttribute, size, _gl.FLOAT,
false, 0, startIndex * size * 4 );
22229 }
else if ( materialDefaultAttributeValues !== undefined ) {
22231 var value = materialDefaultAttributeValues[ name ];
22233 if ( value !== undefined ) {
22235 switch ( value.length ) {
22238 _gl.vertexAttrib2fv( programAttribute, value );
22242 _gl.vertexAttrib3fv( programAttribute, value );
22246 _gl.vertexAttrib4fv( programAttribute, value );
22250 _gl.vertexAttrib1fv( programAttribute, value );
22262 state.disableUnusedAttributes();
22268 function numericalSort ( a, b ) {
22270 return b[ 0 ] - a[ 0 ];
22274 function painterSortStable ( a, b ) {
22276 if ( a.object.renderOrder !== b.object.renderOrder ) {
22278 return a.object.renderOrder - b.object.renderOrder;
22280 }
else if ( a.material.id !== b.material.id ) {
22282 return a.material.id - b.material.id;
22284 }
else if ( a.z !== b.z ) {
22290 return a.id - b.id;
22296 function reversePainterSortStable ( a, b ) {
22298 if ( a.object.renderOrder !== b.object.renderOrder ) {
22300 return a.object.renderOrder - b.object.renderOrder;
22302 }
if ( a.z !== b.z ) {
22308 return a.id - b.id;
22316 this.render =
function ( scene, camera, renderTarget, forceClear ) {
22318 if ( camera instanceof THREE.Camera ===
false ) {
22320 console.error(
'THREE.WebGLRenderer.render: camera is not an instance of THREE.Camera.' );
22325 var fog = scene.fog;
22329 _currentGeometryProgram =
'';
22330 _currentMaterialId = - 1;
22331 _currentCamera = null;
22332 _lightsNeedUpdate =
true;
22336 if ( scene.autoUpdate ===
true ) scene.updateMatrixWorld();
22340 if ( camera.parent === null ) camera.updateMatrixWorld();
22342 camera.matrixWorldInverse.getInverse( camera.matrixWorld );
22344 _projScreenMatrix.multiplyMatrices( camera.projectionMatrix, camera.matrixWorldInverse );
22345 _frustum.setFromMatrix( _projScreenMatrix );
22349 opaqueObjectsLastIndex = - 1;
22350 transparentObjectsLastIndex = - 1;
22352 sprites.length = 0;
22353 lensFlares.length = 0;
22355 projectObject( scene, camera );
22357 opaqueObjects.length = opaqueObjectsLastIndex + 1;
22358 transparentObjects.length = transparentObjectsLastIndex + 1;
22360 if ( _this.sortObjects ===
true ) {
22362 opaqueObjects.sort( painterSortStable );
22363 transparentObjects.sort( reversePainterSortStable );
22369 shadowMap.render( scene );
22373 _infoRender.calls = 0;
22374 _infoRender.vertices = 0;
22375 _infoRender.faces = 0;
22376 _infoRender.points = 0;
22378 this.setRenderTarget( renderTarget );
22380 if ( this.autoClear || forceClear ) {
22382 this.clear( this.autoClearColor, this.autoClearDepth, this.autoClearStencil );
22388 if ( scene.overrideMaterial ) {
22390 var overrideMaterial = scene.overrideMaterial;
22392 renderObjects( opaqueObjects, camera, lights, fog, overrideMaterial );
22393 renderObjects( transparentObjects, camera, lights, fog, overrideMaterial );
22399 state.setBlending( THREE.NoBlending );
22400 renderObjects( opaqueObjects, camera, lights, fog );
22404 renderObjects( transparentObjects, camera, lights, fog );
22410 spritePlugin.render( scene, camera );
22411 lensFlarePlugin.render( scene, camera, _currentWidth, _currentHeight );
22415 if ( renderTarget ) {
22417 var texture = renderTarget.texture;
22418 var isTargetPowerOfTwo = isPowerOfTwo( renderTarget );
22419 if ( texture.generateMipmaps && isTargetPowerOfTwo && texture.minFilter !== THREE.NearestFilter && texture.minFilter !== THREE.LinearFilter ) {
22421 updateRenderTargetMipmap( renderTarget );
22429 state.setDepthTest(
true );
22430 state.setDepthWrite(
true );
22431 state.setColorWrite(
true );
22437 function pushRenderItem(
object, geometry, material, z, group ) {
22443 if ( material.transparent ) {
22445 array = transparentObjects;
22446 index = ++ transparentObjectsLastIndex;
22450 array = opaqueObjects;
22451 index = ++ opaqueObjectsLastIndex;
22457 var renderItem = array[ index ];
22459 if ( renderItem !== undefined ) {
22461 renderItem.id =
object.id;
22462 renderItem.object = object;
22463 renderItem.geometry = geometry;
22464 renderItem.material = material;
22465 renderItem.z = _vector3.z;
22466 renderItem.group = group;
22473 geometry: geometry,
22474 material: material,
22480 array.push( renderItem );
22486 function projectObject(
object, camera ) {
22488 if (
object.visible ===
false )
return;
22490 if ( (
object.channels.mask & camera.channels.mask ) !== 0 ) {
22492 if (
object instanceof THREE.Light ) {
22494 lights.push(
object );
22496 }
else if (
object instanceof THREE.Sprite ) {
22498 sprites.push(
object );
22500 }
else if (
object instanceof THREE.LensFlare ) {
22502 lensFlares.push(
object );
22504 }
else if (
object instanceof THREE.ImmediateRenderObject ) {
22506 if ( _this.sortObjects ===
true ) {
22508 _vector3.setFromMatrixPosition(
object.matrixWorld );
22509 _vector3.applyProjection( _projScreenMatrix );
22513 pushRenderItem(
object, null,
object.material, _vector3.z, null );
22515 }
else if (
object instanceof THREE.Mesh ||
object instanceof THREE.Line ||
object instanceof THREE.Points ) {
22517 if (
object instanceof THREE.SkinnedMesh ) {
22519 object.skeleton.update();
22523 if (
object.frustumCulled ===
false || _frustum.intersectsObject(
object ) === true ) {
22525 var material =
object.material;
22527 if ( material.visible ===
true ) {
22529 if ( _this.sortObjects ===
true ) {
22531 _vector3.setFromMatrixPosition(
object.matrixWorld );
22532 _vector3.applyProjection( _projScreenMatrix );
22536 var geometry = objects.update(
object );
22538 if ( material instanceof THREE.MeshFaceMaterial ) {
22540 var groups = geometry.groups;
22541 var materials = material.materials;
22543 for ( var i = 0, l = groups.length; i < l; i ++ ) {
22545 var group = groups[ i ];
22546 var groupMaterial = materials[ group.materialIndex ];
22548 if ( groupMaterial.visible ===
true ) {
22550 pushRenderItem(
object, geometry, groupMaterial, _vector3.z, group );
22558 pushRenderItem(
object, geometry, material, _vector3.z, null );
22570 var children =
object.children;
22572 for ( var i = 0, l = children.length; i < l; i ++ ) {
22574 projectObject( children[ i ], camera );
22580 function renderObjects( renderList, camera, lights, fog, overrideMaterial ) {
22582 for ( var i = 0, l = renderList.length; i < l; i ++ ) {
22584 var renderItem = renderList[ i ];
22586 var
object = renderItem.object;
22587 var geometry = renderItem.geometry;
22588 var material = overrideMaterial === undefined ? renderItem.material : overrideMaterial;
22589 var group = renderItem.group;
22591 object.modelViewMatrix.multiplyMatrices( camera.matrixWorldInverse,
object.matrixWorld );
22592 object.normalMatrix.getNormalMatrix(
object.modelViewMatrix );
22594 if (
object instanceof THREE.ImmediateRenderObject ) {
22596 setMaterial( material );
22598 var program = setProgram( camera, lights, fog, material,
object );
22600 _currentGeometryProgram =
'';
22602 object.render(
function (
object ) {
22604 _this.renderBufferImmediate(
object, program, material );
22610 _this.renderBufferDirect( camera, lights, fog, geometry, material,
object, group );
22618 function initMaterial( material, lights, fog,
object ) {
22620 var materialProperties = properties.get( material );
22622 var parameters = programCache.getParameters( material, lights, fog,
object );
22623 var code = programCache.getProgramCode( material, parameters );
22625 var program = materialProperties.program;
22626 var programChange =
true;
22628 if ( program === undefined ) {
22631 material.addEventListener(
'dispose', onMaterialDispose );
22633 }
else if ( program.code !== code ) {
22636 releaseMaterialProgramReference( material );
22638 }
else if ( parameters.shaderID !== undefined ) {
22646 programChange =
false;
22650 if ( programChange ) {
22652 if ( parameters.shaderID ) {
22654 var shader = THREE.ShaderLib[ parameters.shaderID ];
22656 materialProperties.__webglShader = {
22657 name: material.type,
22658 uniforms: THREE.UniformsUtils.clone( shader.uniforms ),
22659 vertexShader: shader.vertexShader,
22660 fragmentShader: shader.fragmentShader
22665 materialProperties.__webglShader = {
22666 name: material.type,
22667 uniforms: material.uniforms,
22668 vertexShader: material.vertexShader,
22669 fragmentShader: material.fragmentShader
22674 material.__webglShader = materialProperties.__webglShader;
22676 program = programCache.acquireProgram( material, parameters, code );
22678 materialProperties.program = program;
22679 material.program = program;
22683 var attributes = program.getAttributes();
22685 if ( material.morphTargets ) {
22687 material.numSupportedMorphTargets = 0;
22689 for ( var i = 0; i < _this.maxMorphTargets; i ++ ) {
22691 if ( attributes[
'morphTarget' + i ] >= 0 ) {
22693 material.numSupportedMorphTargets ++;
22701 if ( material.morphNormals ) {
22703 material.numSupportedMorphNormals = 0;
22705 for ( i = 0; i < _this.maxMorphNormals; i ++ ) {
22707 if ( attributes[
'morphNormal' + i ] >= 0 ) {
22709 material.numSupportedMorphNormals ++;
22717 materialProperties.uniformsList = [];
22719 var uniformLocations = materialProperties.program.getUniforms();
22721 for ( var u in materialProperties.__webglShader.uniforms ) {
22723 var location = uniformLocations[ u ];
22727 materialProperties.uniformsList.push( [ materialProperties.__webglShader.uniforms[ u ], location ] );
22735 function setMaterial( material ) {
22737 setMaterialFaces( material );
22739 if ( material.transparent ===
true ) {
22741 state.setBlending( material.blending, material.blendEquation, material.blendSrc, material.blendDst, material.blendEquationAlpha, material.blendSrcAlpha, material.blendDstAlpha );
22745 state.setBlending( THREE.NoBlending );
22749 state.setDepthFunc( material.depthFunc );
22750 state.setDepthTest( material.depthTest );
22751 state.setDepthWrite( material.depthWrite );
22752 state.setColorWrite( material.colorWrite );
22753 state.setPolygonOffset( material.polygonOffset, material.polygonOffsetFactor, material.polygonOffsetUnits );
22757 function setMaterialFaces( material ) {
22759 material.side !== THREE.DoubleSide ? state.enable( _gl.CULL_FACE ) : state.disable( _gl.CULL_FACE );
22760 state.setFlipSided( material.side === THREE.BackSide );
22764 function setProgram( camera, lights, fog, material,
object ) {
22766 _usedTextureUnits = 0;
22768 var materialProperties = properties.get( material );
22770 if ( material.needsUpdate || ! materialProperties.program ) {
22772 initMaterial( material, lights, fog,
object );
22773 material.needsUpdate =
false;
22777 var refreshProgram =
false;
22778 var refreshMaterial =
false;
22779 var refreshLights =
false;
22781 var program = materialProperties.program,
22782 p_uniforms = program.getUniforms(),
22783 m_uniforms = materialProperties.__webglShader.uniforms;
22785 if ( program.id !== _currentProgram ) {
22787 _gl.useProgram( program.program );
22788 _currentProgram = program.id;
22790 refreshProgram =
true;
22791 refreshMaterial =
true;
22792 refreshLights =
true;
22796 if ( material.id !== _currentMaterialId ) {
22798 if ( _currentMaterialId === - 1 ) refreshLights =
true;
22799 _currentMaterialId = material.id;
22801 refreshMaterial =
true;
22805 if ( refreshProgram || camera !== _currentCamera ) {
22807 _gl.uniformMatrix4fv( p_uniforms.projectionMatrix,
false, camera.projectionMatrix.elements );
22809 if ( capabilities.logarithmicDepthBuffer ) {
22811 _gl.uniform1f( p_uniforms.logDepthBufFC, 2.0 / ( Math.log( camera.far + 1.0 ) / Math.LN2 ) );
22816 if ( camera !== _currentCamera ) _currentCamera = camera;
22821 if ( material instanceof THREE.ShaderMaterial ||
22822 material instanceof THREE.MeshPhongMaterial ||
22823 material.envMap ) {
22825 if ( p_uniforms.cameraPosition !== undefined ) {
22827 _vector3.setFromMatrixPosition( camera.matrixWorld );
22828 _gl.uniform3f( p_uniforms.cameraPosition, _vector3.x, _vector3.y, _vector3.z );
22834 if ( material instanceof THREE.MeshPhongMaterial ||
22835 material instanceof THREE.MeshLambertMaterial ||
22836 material instanceof THREE.MeshBasicMaterial ||
22837 material instanceof THREE.ShaderMaterial ||
22838 material.skinning ) {
22840 if ( p_uniforms.viewMatrix !== undefined ) {
22842 _gl.uniformMatrix4fv( p_uniforms.viewMatrix,
false, camera.matrixWorldInverse.elements );
22854 if ( material.skinning ) {
22856 if (
object.bindMatrix && p_uniforms.bindMatrix !== undefined ) {
22858 _gl.uniformMatrix4fv( p_uniforms.bindMatrix,
false,
object.bindMatrix.elements );
22862 if (
object.bindMatrixInverse && p_uniforms.bindMatrixInverse !== undefined ) {
22864 _gl.uniformMatrix4fv( p_uniforms.bindMatrixInverse,
false,
object.bindMatrixInverse.elements );
22868 if ( capabilities.floatVertexTextures &&
object.skeleton &&
object.skeleton.useVertexTexture ) {
22870 if ( p_uniforms.boneTexture !== undefined ) {
22872 var textureUnit = getTextureUnit();
22874 _gl.uniform1i( p_uniforms.boneTexture, textureUnit );
22875 _this.setTexture(
object.skeleton.boneTexture, textureUnit );
22879 if ( p_uniforms.boneTextureWidth !== undefined ) {
22881 _gl.uniform1i( p_uniforms.boneTextureWidth,
object.skeleton.boneTextureWidth );
22885 if ( p_uniforms.boneTextureHeight !== undefined ) {
22887 _gl.uniform1i( p_uniforms.boneTextureHeight,
object.skeleton.boneTextureHeight );
22891 }
else if (
object.skeleton &&
object.skeleton.boneMatrices ) {
22893 if ( p_uniforms.boneGlobalMatrices !== undefined ) {
22895 _gl.uniformMatrix4fv( p_uniforms.boneGlobalMatrices,
false,
object.skeleton.boneMatrices );
22903 if ( refreshMaterial ) {
22907 if ( fog && material.fog ) {
22909 refreshUniformsFog( m_uniforms, fog );
22913 if ( material instanceof THREE.MeshPhongMaterial ||
22914 material instanceof THREE.MeshLambertMaterial ||
22915 material.lights ) {
22917 if ( _lightsNeedUpdate ) {
22919 refreshLights =
true;
22920 setupLights( lights, camera );
22921 _lightsNeedUpdate =
false;
22925 if ( refreshLights ) {
22927 refreshUniformsLights( m_uniforms, _lights );
22928 markUniformsLightsNeedsUpdate( m_uniforms,
true );
22932 markUniformsLightsNeedsUpdate( m_uniforms,
false );
22938 if ( material instanceof THREE.MeshBasicMaterial ||
22939 material instanceof THREE.MeshLambertMaterial ||
22940 material instanceof THREE.MeshPhongMaterial ) {
22942 refreshUniformsCommon( m_uniforms, material );
22948 if ( material instanceof THREE.LineBasicMaterial ) {
22950 refreshUniformsLine( m_uniforms, material );
22952 }
else if ( material instanceof THREE.LineDashedMaterial ) {
22954 refreshUniformsLine( m_uniforms, material );
22955 refreshUniformsDash( m_uniforms, material );
22957 }
else if ( material instanceof THREE.PointsMaterial ) {
22959 refreshUniformsParticle( m_uniforms, material );
22961 }
else if ( material instanceof THREE.MeshPhongMaterial ) {
22963 refreshUniformsPhong( m_uniforms, material );
22965 }
else if ( material instanceof THREE.MeshDepthMaterial ) {
22967 m_uniforms.mNear.value = camera.near;
22968 m_uniforms.mFar.value = camera.far;
22969 m_uniforms.opacity.value = material.opacity;
22971 }
else if ( material instanceof THREE.MeshNormalMaterial ) {
22973 m_uniforms.opacity.value = material.opacity;
22977 if (
object.receiveShadow && ! material._shadowPass ) {
22979 refreshUniformsShadow( m_uniforms, lights, camera );
22985 loadUniformsGeneric( materialProperties.uniformsList );
22989 loadUniformsMatrices( p_uniforms,
object );
22991 if ( p_uniforms.modelMatrix !== undefined ) {
22993 _gl.uniformMatrix4fv( p_uniforms.modelMatrix,
false,
object.matrixWorld.elements );
23003 function refreshUniformsCommon ( uniforms, material ) {
23005 uniforms.opacity.value = material.opacity;
23007 uniforms.diffuse.value = material.color;
23009 if ( material.emissive ) {
23011 uniforms.emissive.value = material.emissive;
23015 uniforms.map.value = material.map;
23016 uniforms.specularMap.value = material.specularMap;
23017 uniforms.alphaMap.value = material.alphaMap;
23019 if ( material.aoMap ) {
23021 uniforms.aoMap.value = material.aoMap;
23022 uniforms.aoMapIntensity.value = material.aoMapIntensity;
23036 if ( material.map ) {
23038 uvScaleMap = material.map;
23040 }
else if ( material.specularMap ) {
23042 uvScaleMap = material.specularMap;
23044 }
else if ( material.displacementMap ) {
23046 uvScaleMap = material.displacementMap;
23048 }
else if ( material.normalMap ) {
23050 uvScaleMap = material.normalMap;
23052 }
else if ( material.bumpMap ) {
23054 uvScaleMap = material.bumpMap;
23056 }
else if ( material.alphaMap ) {
23058 uvScaleMap = material.alphaMap;
23060 }
else if ( material.emissiveMap ) {
23062 uvScaleMap = material.emissiveMap;
23066 if ( uvScaleMap !== undefined ) {
23068 if ( uvScaleMap instanceof THREE.WebGLRenderTarget ) uvScaleMap = uvScaleMap.texture;
23069 var offset = uvScaleMap.offset;
23070 var repeat = uvScaleMap.repeat;
23072 uniforms.offsetRepeat.value.set( offset.x, offset.y, repeat.x, repeat.y );
23076 uniforms.envMap.value = material.envMap;
23077 uniforms.flipEnvMap.value = ( material.envMap instanceof THREE.WebGLRenderTargetCube ) ? 1 : - 1;
23079 uniforms.reflectivity.value = material.reflectivity;
23080 uniforms.refractionRatio.value = material.refractionRatio;
23084 function refreshUniformsLine ( uniforms, material ) {
23086 uniforms.diffuse.value = material.color;
23087 uniforms.opacity.value = material.opacity;
23091 function refreshUniformsDash ( uniforms, material ) {
23093 uniforms.dashSize.value = material.dashSize;
23094 uniforms.totalSize.value = material.dashSize + material.gapSize;
23095 uniforms.scale.value = material.scale;
23099 function refreshUniformsParticle ( uniforms, material ) {
23101 uniforms.psColor.value = material.color;
23102 uniforms.opacity.value = material.opacity;
23103 uniforms.size.value = material.size;
23104 uniforms.scale.value = _canvas.height / 2.0;
23106 uniforms.map.value = material.map;
23108 if ( material.map !== null ) {
23110 var offset = material.map.offset;
23111 var repeat = material.map.repeat;
23113 uniforms.offsetRepeat.value.set( offset.x, offset.y, repeat.x, repeat.y );
23119 function refreshUniformsFog ( uniforms, fog ) {
23121 uniforms.fogColor.value = fog.color;
23123 if ( fog instanceof THREE.Fog ) {
23125 uniforms.fogNear.value = fog.near;
23126 uniforms.fogFar.value = fog.far;
23128 }
else if ( fog instanceof THREE.FogExp2 ) {
23130 uniforms.fogDensity.value = fog.density;
23136 function refreshUniformsPhong ( uniforms, material ) {
23138 uniforms.specular.value = material.specular;
23139 uniforms.shininess.value = Math.max( material.shininess, 1e-4 );
23141 if ( material.lightMap ) {
23143 uniforms.lightMap.value = material.lightMap;
23144 uniforms.lightMapIntensity.value = material.lightMapIntensity;
23148 if ( material.emissiveMap ) {
23150 uniforms.emissiveMap.value = material.emissiveMap;
23154 if ( material.bumpMap ) {
23156 uniforms.bumpMap.value = material.bumpMap;
23157 uniforms.bumpScale.value = material.bumpScale;
23161 if ( material.normalMap ) {
23163 uniforms.normalMap.value = material.normalMap;
23164 uniforms.normalScale.value.copy( material.normalScale );
23168 if ( material.displacementMap ) {
23170 uniforms.displacementMap.value = material.displacementMap;
23171 uniforms.displacementScale.value = material.displacementScale;
23172 uniforms.displacementBias.value = material.displacementBias;
23178 function refreshUniformsLights ( uniforms, lights ) {
23180 uniforms.ambientLightColor.value = lights.ambient;
23182 uniforms.directionalLightColor.value = lights.directional.colors;
23183 uniforms.directionalLightDirection.value = lights.directional.positions;
23185 uniforms.pointLightColor.value = lights.point.colors;
23186 uniforms.pointLightPosition.value = lights.point.positions;
23187 uniforms.pointLightDistance.value = lights.point.distances;
23188 uniforms.pointLightDecay.value = lights.point.decays;
23190 uniforms.spotLightColor.value = lights.spot.colors;
23191 uniforms.spotLightPosition.value = lights.spot.positions;
23192 uniforms.spotLightDistance.value = lights.spot.distances;
23193 uniforms.spotLightDirection.value = lights.spot.directions;
23194 uniforms.spotLightAngleCos.value = lights.spot.anglesCos;
23195 uniforms.spotLightExponent.value = lights.spot.exponents;
23196 uniforms.spotLightDecay.value = lights.spot.decays;
23198 uniforms.hemisphereLightSkyColor.value = lights.hemi.skyColors;
23199 uniforms.hemisphereLightGroundColor.value = lights.hemi.groundColors;
23200 uniforms.hemisphereLightDirection.value = lights.hemi.positions;
23206 function markUniformsLightsNeedsUpdate ( uniforms, value ) {
23208 uniforms.ambientLightColor.needsUpdate = value;
23210 uniforms.directionalLightColor.needsUpdate = value;
23211 uniforms.directionalLightDirection.needsUpdate = value;
23213 uniforms.pointLightColor.needsUpdate = value;
23214 uniforms.pointLightPosition.needsUpdate = value;
23215 uniforms.pointLightDistance.needsUpdate = value;
23216 uniforms.pointLightDecay.needsUpdate = value;
23218 uniforms.spotLightColor.needsUpdate = value;
23219 uniforms.spotLightPosition.needsUpdate = value;
23220 uniforms.spotLightDistance.needsUpdate = value;
23221 uniforms.spotLightDirection.needsUpdate = value;
23222 uniforms.spotLightAngleCos.needsUpdate = value;
23223 uniforms.spotLightExponent.needsUpdate = value;
23224 uniforms.spotLightDecay.needsUpdate = value;
23226 uniforms.hemisphereLightSkyColor.needsUpdate = value;
23227 uniforms.hemisphereLightGroundColor.needsUpdate = value;
23228 uniforms.hemisphereLightDirection.needsUpdate = value;
23232 function refreshUniformsShadow ( uniforms, lights, camera ) {
23234 if ( uniforms.shadowMatrix ) {
23238 for ( var i = 0, il = lights.length; i < il; i ++ ) {
23240 var light = lights[ i ];
23242 if ( light.castShadow ===
true ) {
23244 if ( light instanceof THREE.PointLight || light instanceof THREE.SpotLight || light instanceof THREE.DirectionalLight ) {
23246 var shadow = light.shadow;
23248 if ( light instanceof THREE.PointLight ) {
23252 _vector3.setFromMatrixPosition( light.matrixWorld ).negate();
23253 shadow.matrix.identity().setPosition( _vector3 );
23256 uniforms.shadowDarkness.value[ j ] = - shadow.darkness;
23260 uniforms.shadowDarkness.value[ j ] = shadow.darkness;
23264 uniforms.shadowMatrix.value[ j ] = shadow.matrix;
23265 uniforms.shadowMap.value[ j ] = shadow.map;
23266 uniforms.shadowMapSize.value[ j ] = shadow.mapSize;
23267 uniforms.shadowBias.value[ j ] = shadow.bias;
23283 function loadUniformsMatrices ( uniforms,
object ) {
23285 _gl.uniformMatrix4fv( uniforms.modelViewMatrix,
false,
object.modelViewMatrix.elements );
23287 if ( uniforms.normalMatrix ) {
23289 _gl.uniformMatrix3fv( uniforms.normalMatrix,
false,
object.normalMatrix.elements );
23295 function getTextureUnit() {
23297 var textureUnit = _usedTextureUnits;
23299 if ( textureUnit >= capabilities.maxTextures ) {
23301 console.warn(
'WebGLRenderer: trying to use ' + textureUnit +
' texture units while this GPU supports only ' + capabilities.maxTextures );
23305 _usedTextureUnits += 1;
23307 return textureUnit;
23311 function loadUniformsGeneric ( uniforms ) {
23313 var texture, textureUnit;
23315 for ( var j = 0, jl = uniforms.length; j < jl; j ++ ) {
23317 var uniform = uniforms[ j ][ 0 ];
23320 if ( uniform.needsUpdate ===
false )
continue;
23322 var type = uniform.type;
23323 var value = uniform.value;
23324 var location = uniforms[ j ][ 1 ];
23329 _gl.uniform1i( location, value );
23333 _gl.uniform1f( location, value );
23337 _gl.uniform2f( location, value[ 0 ], value[ 1 ] );
23341 _gl.uniform3f( location, value[ 0 ], value[ 1 ], value[ 2 ] );
23345 _gl.uniform4f( location, value[ 0 ], value[ 1 ], value[ 2 ], value[ 3 ] );
23349 _gl.uniform1iv( location, value );
23353 _gl.uniform3iv( location, value );
23357 _gl.uniform1fv( location, value );
23361 _gl.uniform2fv( location, value );
23365 _gl.uniform3fv( location, value );
23369 _gl.uniform4fv( location, value );
23373 _gl.uniformMatrix3fv( location,
false, value );
23377 _gl.uniformMatrix4fv( location,
false, value );
23385 _gl.uniform1i( location, value );
23392 _gl.uniform1f( location, value );
23399 _gl.uniform2f( location, value.x, value.y );
23406 _gl.uniform3f( location, value.x, value.y, value.z );
23413 _gl.uniform4f( location, value.x, value.y, value.z, value.w );
23420 _gl.uniform3f( location, value.r, value.g, value.b );
23427 _gl.uniform1iv( location, value );
23434 _gl.uniform3iv( location, value );
23441 _gl.uniform1fv( location, value );
23448 _gl.uniform3fv( location, value );
23456 if ( uniform._array === undefined ) {
23458 uniform._array =
new Float32Array( 2 * value.length );
23462 for ( var i = 0, i2 = 0, il = value.length; i < il; i ++, i2 += 2 ) {
23464 uniform._array[ i2 + 0 ] = value[ i ].x;
23465 uniform._array[ i2 + 1 ] = value[ i ].y;
23469 _gl.uniform2fv( location, uniform._array );
23477 if ( uniform._array === undefined ) {
23479 uniform._array =
new Float32Array( 3 * value.length );
23483 for ( var i = 0, i3 = 0, il = value.length; i < il; i ++, i3 += 3 ) {
23485 uniform._array[ i3 + 0 ] = value[ i ].x;
23486 uniform._array[ i3 + 1 ] = value[ i ].y;
23487 uniform._array[ i3 + 2 ] = value[ i ].z;
23491 _gl.uniform3fv( location, uniform._array );
23499 if ( uniform._array === undefined ) {
23501 uniform._array =
new Float32Array( 4 * value.length );
23505 for ( var i = 0, i4 = 0, il = value.length; i < il; i ++, i4 += 4 ) {
23507 uniform._array[ i4 + 0 ] = value[ i ].x;
23508 uniform._array[ i4 + 1 ] = value[ i ].y;
23509 uniform._array[ i4 + 2 ] = value[ i ].z;
23510 uniform._array[ i4 + 3 ] = value[ i ].w;
23514 _gl.uniform4fv( location, uniform._array );
23521 _gl.uniformMatrix3fv( location,
false, value.elements );
23529 if ( uniform._array === undefined ) {
23531 uniform._array =
new Float32Array( 9 * value.length );
23535 for ( var i = 0, il = value.length; i < il; i ++ ) {
23537 value[ i ].flattenToArrayOffset( uniform._array, i * 9 );
23541 _gl.uniformMatrix3fv( location,
false, uniform._array );
23548 _gl.uniformMatrix4fv( location,
false, value.elements );
23556 if ( uniform._array === undefined ) {
23558 uniform._array =
new Float32Array( 16 * value.length );
23562 for ( var i = 0, il = value.length; i < il; i ++ ) {
23564 value[ i ].flattenToArrayOffset( uniform._array, i * 16 );
23568 _gl.uniformMatrix4fv( location,
false, uniform._array );
23577 textureUnit = getTextureUnit();
23579 _gl.uniform1i( location, textureUnit );
23581 if ( ! texture )
continue;
23583 if ( texture instanceof THREE.CubeTexture ||
23584 ( Array.isArray( texture.image ) && texture.image.length === 6 ) ) {
23588 setCubeTexture( texture, textureUnit );
23590 }
else if ( texture instanceof THREE.WebGLRenderTargetCube ) {
23592 setCubeTextureDynamic( texture.texture, textureUnit );
23594 }
else if ( texture instanceof THREE.WebGLRenderTarget ) {
23596 _this.setTexture( texture.texture, textureUnit );
23600 _this.setTexture( texture, textureUnit );
23610 if ( uniform._array === undefined ) {
23612 uniform._array = [];
23616 for ( var i = 0, il = uniform.value.length; i < il; i ++ ) {
23618 uniform._array[ i ] = getTextureUnit();
23622 _gl.uniform1iv( location, uniform._array );
23624 for ( var i = 0, il = uniform.value.length; i < il; i ++ ) {
23626 texture = uniform.value[ i ];
23627 textureUnit = uniform._array[ i ];
23629 if ( ! texture )
continue;
23631 if ( texture instanceof THREE.CubeTexture ||
23632 ( texture.image instanceof Array && texture.image.length === 6 ) ) {
23636 setCubeTexture( texture, textureUnit );
23638 }
else if ( texture instanceof THREE.WebGLRenderTarget ) {
23640 _this.setTexture( texture.texture, textureUnit );
23642 }
else if ( texture instanceof THREE.WebGLRenderTargetCube ) {
23644 setCubeTextureDynamic( texture.texture, textureUnit );
23648 _this.setTexture( texture, textureUnit );
23658 console.warn(
'THREE.WebGLRenderer: Unknown uniform type: ' + type );
23666 function setColorLinear( array, offset, color, intensity ) {
23668 array[ offset + 0 ] = color.r * intensity;
23669 array[ offset + 1 ] = color.g * intensity;
23670 array[ offset + 2 ] = color.b * intensity;
23674 function setupLights ( lights, camera ) {
23677 r = 0, g = 0, b = 0,
23678 color, skyColor, groundColor,
23684 viewMatrix = camera.matrixWorldInverse,
23686 dirColors = zlights.directional.colors,
23687 dirPositions = zlights.directional.positions,
23689 pointColors = zlights.point.colors,
23690 pointPositions = zlights.point.positions,
23691 pointDistances = zlights.point.distances,
23692 pointDecays = zlights.point.decays,
23694 spotColors = zlights.spot.colors,
23695 spotPositions = zlights.spot.positions,
23696 spotDistances = zlights.spot.distances,
23697 spotDirections = zlights.spot.directions,
23698 spotAnglesCos = zlights.spot.anglesCos,
23699 spotExponents = zlights.spot.exponents,
23700 spotDecays = zlights.spot.decays,
23702 hemiSkyColors = zlights.hemi.skyColors,
23703 hemiGroundColors = zlights.hemi.groundColors,
23704 hemiPositions = zlights.hemi.positions,
23721 for ( l = 0, ll = lights.length; l < ll; l ++ ) {
23723 light = lights[ l ];
23725 color = light.color;
23726 intensity = light.intensity;
23727 distance = light.distance;
23729 if ( light instanceof THREE.AmbientLight ) {
23731 if ( ! light.visible )
continue;
23737 }
else if ( light instanceof THREE.DirectionalLight ) {
23741 if ( ! light.visible )
continue;
23743 _direction.setFromMatrixPosition( light.matrixWorld );
23744 _vector3.setFromMatrixPosition( light.target.matrixWorld );
23745 _direction.sub( _vector3 );
23746 _direction.transformDirection( viewMatrix );
23748 dirOffset = dirLength * 3;
23750 dirPositions[ dirOffset + 0 ] = _direction.x;
23751 dirPositions[ dirOffset + 1 ] = _direction.y;
23752 dirPositions[ dirOffset + 2 ] = _direction.z;
23754 setColorLinear( dirColors, dirOffset, color, intensity );
23758 }
else if ( light instanceof THREE.PointLight ) {
23762 if ( ! light.visible )
continue;
23764 pointOffset = pointLength * 3;
23766 setColorLinear( pointColors, pointOffset, color, intensity );
23768 _vector3.setFromMatrixPosition( light.matrixWorld );
23769 _vector3.applyMatrix4( viewMatrix );
23771 pointPositions[ pointOffset + 0 ] = _vector3.x;
23772 pointPositions[ pointOffset + 1 ] = _vector3.y;
23773 pointPositions[ pointOffset + 2 ] = _vector3.z;
23776 pointDistances[ pointLength ] = distance;
23777 pointDecays[ pointLength ] = ( light.distance === 0 ) ? 0.0 : light.decay;
23781 }
else if ( light instanceof THREE.SpotLight ) {
23785 if ( ! light.visible )
continue;
23787 spotOffset = spotLength * 3;
23789 setColorLinear( spotColors, spotOffset, color, intensity );
23791 _direction.setFromMatrixPosition( light.matrixWorld );
23792 _vector3.copy( _direction ).applyMatrix4( viewMatrix );
23794 spotPositions[ spotOffset + 0 ] = _vector3.x;
23795 spotPositions[ spotOffset + 1 ] = _vector3.y;
23796 spotPositions[ spotOffset + 2 ] = _vector3.z;
23798 spotDistances[ spotLength ] = distance;
23800 _vector3.setFromMatrixPosition( light.target.matrixWorld );
23801 _direction.sub( _vector3 );
23802 _direction.transformDirection( viewMatrix );
23804 spotDirections[ spotOffset + 0 ] = _direction.x;
23805 spotDirections[ spotOffset + 1 ] = _direction.y;
23806 spotDirections[ spotOffset + 2 ] = _direction.z;
23808 spotAnglesCos[ spotLength ] = Math.cos( light.angle );
23809 spotExponents[ spotLength ] = light.exponent;
23810 spotDecays[ spotLength ] = ( light.distance === 0 ) ? 0.0 : light.decay;
23814 }
else if ( light instanceof THREE.HemisphereLight ) {
23818 if ( ! light.visible )
continue;
23820 _direction.setFromMatrixPosition( light.matrixWorld );
23821 _direction.transformDirection( viewMatrix );
23823 hemiOffset = hemiLength * 3;
23825 hemiPositions[ hemiOffset + 0 ] = _direction.x;
23826 hemiPositions[ hemiOffset + 1 ] = _direction.y;
23827 hemiPositions[ hemiOffset + 2 ] = _direction.z;
23829 skyColor = light.color;
23830 groundColor = light.groundColor;
23832 setColorLinear( hemiSkyColors, hemiOffset, skyColor, intensity );
23833 setColorLinear( hemiGroundColors, hemiOffset, groundColor, intensity );
23844 for ( l = dirLength * 3, ll = Math.max( dirColors.length, dirCount * 3 ); l < ll; l ++ ) dirColors[ l ] = 0.0;
23845 for ( l = pointLength * 3, ll = Math.max( pointColors.length, pointCount * 3 ); l < ll; l ++ ) pointColors[ l ] = 0.0;
23846 for ( l = spotLength * 3, ll = Math.max( spotColors.length, spotCount * 3 ); l < ll; l ++ ) spotColors[ l ] = 0.0;
23847 for ( l = hemiLength * 3, ll = Math.max( hemiSkyColors.length, hemiCount * 3 ); l < ll; l ++ ) hemiSkyColors[ l ] = 0.0;
23848 for ( l = hemiLength * 3, ll = Math.max( hemiGroundColors.length, hemiCount * 3 ); l < ll; l ++ ) hemiGroundColors[ l ] = 0.0;
23850 zlights.directional.length = dirLength;
23851 zlights.point.length = pointLength;
23852 zlights.spot.length = spotLength;
23853 zlights.hemi.length = hemiLength;
23855 zlights.ambient[ 0 ] = r;
23856 zlights.ambient[ 1 ] = g;
23857 zlights.ambient[ 2 ] = b;
23863 this.setFaceCulling =
function ( cullFace, frontFaceDirection ) {
23865 if ( cullFace === THREE.CullFaceNone ) {
23867 state.disable( _gl.CULL_FACE );
23871 if ( frontFaceDirection === THREE.FrontFaceDirectionCW ) {
23873 _gl.frontFace( _gl.CW );
23877 _gl.frontFace( _gl.CCW );
23881 if ( cullFace === THREE.CullFaceBack ) {
23883 _gl.cullFace( _gl.BACK );
23885 }
else if ( cullFace === THREE.CullFaceFront ) {
23887 _gl.cullFace( _gl.FRONT );
23891 _gl.cullFace( _gl.FRONT_AND_BACK );
23895 state.enable( _gl.CULL_FACE );
23903 function setTextureParameters ( textureType, texture, isImagePowerOfTwo ) {
23907 if ( isImagePowerOfTwo ) {
23909 _gl.texParameteri( textureType, _gl.TEXTURE_WRAP_S, paramThreeToGL( texture.wrapS ) );
23910 _gl.texParameteri( textureType, _gl.TEXTURE_WRAP_T, paramThreeToGL( texture.wrapT ) );
23912 _gl.texParameteri( textureType, _gl.TEXTURE_MAG_FILTER, paramThreeToGL( texture.magFilter ) );
23913 _gl.texParameteri( textureType, _gl.TEXTURE_MIN_FILTER, paramThreeToGL( texture.minFilter ) );
23917 _gl.texParameteri( textureType, _gl.TEXTURE_WRAP_S, _gl.CLAMP_TO_EDGE );
23918 _gl.texParameteri( textureType, _gl.TEXTURE_WRAP_T, _gl.CLAMP_TO_EDGE );
23920 if ( texture.wrapS !== THREE.ClampToEdgeWrapping || texture.wrapT !== THREE.ClampToEdgeWrapping ) {
23922 console.warn(
'THREE.WebGLRenderer: Texture is not power of two. Texture.wrapS and Texture.wrapT should be set to THREE.ClampToEdgeWrapping.', texture );
23926 _gl.texParameteri( textureType, _gl.TEXTURE_MAG_FILTER, filterFallback( texture.magFilter ) );
23927 _gl.texParameteri( textureType, _gl.TEXTURE_MIN_FILTER, filterFallback( texture.minFilter ) );
23929 if ( texture.minFilter !== THREE.NearestFilter && texture.minFilter !== THREE.LinearFilter ) {
23931 console.warn(
'THREE.WebGLRenderer: Texture is not power of two. Texture.minFilter should be set to THREE.NearestFilter or THREE.LinearFilter.', texture );
23937 extension = extensions.get(
'EXT_texture_filter_anisotropic' );
23941 if ( texture.type === THREE.FloatType && extensions.get(
'OES_texture_float_linear' ) === null )
return;
23942 if ( texture.type === THREE.HalfFloatType && extensions.get(
'OES_texture_half_float_linear' ) === null )
return;
23944 if ( texture.anisotropy > 1 || properties.get( texture ).__currentAnisotropy ) {
23946 _gl.texParameterf( textureType, extension.TEXTURE_MAX_ANISOTROPY_EXT, Math.min( texture.anisotropy, _this.getMaxAnisotropy() ) );
23947 properties.get( texture ).__currentAnisotropy = texture.anisotropy;
23955 function uploadTexture( textureProperties, texture, slot ) {
23957 if ( textureProperties.__webglInit === undefined ) {
23959 textureProperties.__webglInit =
true;
23961 texture.addEventListener(
'dispose', onTextureDispose );
23963 textureProperties.__webglTexture = _gl.createTexture();
23965 _infoMemory.textures ++;
23969 state.activeTexture( _gl.TEXTURE0 + slot );
23970 state.bindTexture( _gl.TEXTURE_2D, textureProperties.__webglTexture );
23972 _gl.pixelStorei( _gl.UNPACK_FLIP_Y_WEBGL, texture.flipY );
23973 _gl.pixelStorei( _gl.UNPACK_PREMULTIPLY_ALPHA_WEBGL, texture.premultiplyAlpha );
23974 _gl.pixelStorei( _gl.UNPACK_ALIGNMENT, texture.unpackAlignment );
23976 texture.image = clampToMaxSize( texture.image, capabilities.maxTextureSize );
23978 if ( textureNeedsPowerOfTwo( texture ) && isPowerOfTwo( texture.image ) ===
false ) {
23980 texture.image = makePowerOfTwo( texture.image );
23984 var image = texture.image,
23985 isImagePowerOfTwo = isPowerOfTwo( image ),
23986 glFormat = paramThreeToGL( texture.format ),
23987 glType = paramThreeToGL( texture.type );
23989 setTextureParameters( _gl.TEXTURE_2D, texture, isImagePowerOfTwo );
23991 var mipmap, mipmaps = texture.mipmaps;
23993 if ( texture instanceof THREE.DataTexture ) {
23999 if ( mipmaps.length > 0 && isImagePowerOfTwo ) {
24001 for ( var i = 0, il = mipmaps.length; i < il; i ++ ) {
24003 mipmap = mipmaps[ i ];
24004 state.texImage2D( _gl.TEXTURE_2D, i, glFormat, mipmap.width, mipmap.height, 0, glFormat, glType, mipmap.data );
24008 texture.generateMipmaps =
false;
24012 state.texImage2D( _gl.TEXTURE_2D, 0, glFormat, image.width, image.height, 0, glFormat, glType, image.data );
24016 }
else if ( texture instanceof THREE.CompressedTexture ) {
24018 for ( var i = 0, il = mipmaps.length; i < il; i ++ ) {
24020 mipmap = mipmaps[ i ];
24022 if ( texture.format !== THREE.RGBAFormat && texture.format !== THREE.RGBFormat ) {
24024 if ( state.getCompressedTextureFormats().indexOf( glFormat ) > - 1 ) {
24026 state.compressedTexImage2D( _gl.TEXTURE_2D, i, glFormat, mipmap.width, mipmap.height, 0, mipmap.data );
24030 console.warn(
"THREE.WebGLRenderer: Attempt to load unsupported compressed texture format in .uploadTexture()" );
24036 state.texImage2D( _gl.TEXTURE_2D, i, glFormat, mipmap.width, mipmap.height, 0, glFormat, glType, mipmap.data );
24050 if ( mipmaps.length > 0 && isImagePowerOfTwo ) {
24052 for ( var i = 0, il = mipmaps.length; i < il; i ++ ) {
24054 mipmap = mipmaps[ i ];
24055 state.texImage2D( _gl.TEXTURE_2D, i, glFormat, glFormat, glType, mipmap );
24059 texture.generateMipmaps =
false;
24063 state.texImage2D( _gl.TEXTURE_2D, 0, glFormat, glFormat, glType, texture.image );
24069 if ( texture.generateMipmaps && isImagePowerOfTwo ) _gl.generateMipmap( _gl.TEXTURE_2D );
24071 textureProperties.__version = texture.version;
24073 if ( texture.onUpdate ) texture.onUpdate( texture );
24077 this.setTexture =
function ( texture, slot ) {
24079 var textureProperties = properties.get( texture );
24081 if ( texture.version > 0 && textureProperties.__version !== texture.version ) {
24083 var image = texture.image;
24085 if ( image === undefined ) {
24087 console.warn(
'THREE.WebGLRenderer: Texture marked for update but image is undefined', texture );
24092 if ( image.complete ===
false ) {
24094 console.warn(
'THREE.WebGLRenderer: Texture marked for update but image is incomplete', texture );
24099 uploadTexture( textureProperties, texture, slot );
24105 state.activeTexture( _gl.TEXTURE0 + slot );
24106 state.bindTexture( _gl.TEXTURE_2D, textureProperties.__webglTexture );
24110 function clampToMaxSize ( image, maxSize ) {
24112 if ( image.width > maxSize || image.height > maxSize ) {
24117 var scale = maxSize / Math.max( image.width, image.height );
24119 var canvas = document.createElement(
'canvas' );
24120 canvas.width = Math.floor( image.width * scale );
24121 canvas.height = Math.floor( image.height * scale );
24123 var context = canvas.getContext(
'2d' );
24124 context.drawImage( image, 0, 0, image.width, image.height, 0, 0, canvas.width, canvas.height );
24126 console.warn(
'THREE.WebGLRenderer: image is too big (' + image.width +
'x' + image.height +
'). Resized to ' + canvas.width +
'x' + canvas.height, image );
24136 function isPowerOfTwo( image ) {
24138 return THREE.Math.isPowerOfTwo( image.width ) && THREE.Math.isPowerOfTwo( image.height );
24142 function textureNeedsPowerOfTwo( texture ) {
24144 if ( texture.wrapS !== THREE.ClampToEdgeWrapping || texture.wrapT !== THREE.ClampToEdgeWrapping )
return true;
24145 if ( texture.minFilter !== THREE.NearestFilter && texture.minFilter !== THREE.LinearFilter )
return true;
24151 function makePowerOfTwo( image ) {
24153 if ( image instanceof HTMLImageElement || image instanceof HTMLCanvasElement ) {
24155 var canvas = document.createElement(
'canvas' );
24156 canvas.width = THREE.Math.nearestPowerOfTwo( image.width );
24157 canvas.height = THREE.Math.nearestPowerOfTwo( image.height );
24159 var context = canvas.getContext(
'2d' );
24160 context.drawImage( image, 0, 0, canvas.width, canvas.height );
24162 console.warn(
'THREE.WebGLRenderer: image is not power of two (' + image.width +
'x' + image.height +
'). Resized to ' + canvas.width +
'x' + canvas.height, image );
24172 function setCubeTexture ( texture, slot ) {
24174 var textureProperties = properties.get( texture );
24176 if ( texture.image.length === 6 ) {
24178 if ( texture.version > 0 && textureProperties.__version !== texture.version ) {
24180 if ( ! textureProperties.__image__webglTextureCube ) {
24182 texture.addEventListener(
'dispose', onTextureDispose );
24184 textureProperties.__image__webglTextureCube = _gl.createTexture();
24186 _infoMemory.textures ++;
24190 state.activeTexture( _gl.TEXTURE0 + slot );
24191 state.bindTexture( _gl.TEXTURE_CUBE_MAP, textureProperties.__image__webglTextureCube );
24193 _gl.pixelStorei( _gl.UNPACK_FLIP_Y_WEBGL, texture.flipY );
24195 var isCompressed = texture instanceof THREE.CompressedTexture;
24196 var isDataTexture = texture.image[ 0 ] instanceof THREE.DataTexture;
24198 var cubeImage = [];
24200 for ( var i = 0; i < 6; i ++ ) {
24202 if ( _this.autoScaleCubemaps && ! isCompressed && ! isDataTexture ) {
24204 cubeImage[ i ] = clampToMaxSize( texture.image[ i ], capabilities.maxCubemapSize );
24208 cubeImage[ i ] = isDataTexture ? texture.image[ i ].image : texture.image[ i ];
24214 var image = cubeImage[ 0 ],
24215 isImagePowerOfTwo = isPowerOfTwo( image ),
24216 glFormat = paramThreeToGL( texture.format ),
24217 glType = paramThreeToGL( texture.type );
24219 setTextureParameters( _gl.TEXTURE_CUBE_MAP, texture, isImagePowerOfTwo );
24221 for ( var i = 0; i < 6; i ++ ) {
24223 if ( ! isCompressed ) {
24225 if ( isDataTexture ) {
24227 state.texImage2D( _gl.TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, glFormat, cubeImage[ i ].width, cubeImage[ i ].height, 0, glFormat, glType, cubeImage[ i ].data );
24231 state.texImage2D( _gl.TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, glFormat, glFormat, glType, cubeImage[ i ] );
24237 var mipmap, mipmaps = cubeImage[ i ].mipmaps;
24239 for ( var j = 0, jl = mipmaps.length; j < jl; j ++ ) {
24241 mipmap = mipmaps[ j ];
24243 if ( texture.format !== THREE.RGBAFormat && texture.format !== THREE.RGBFormat ) {
24245 if ( state.getCompressedTextureFormats().indexOf( glFormat ) > - 1 ) {
24247 state.compressedTexImage2D( _gl.TEXTURE_CUBE_MAP_POSITIVE_X + i, j, glFormat, mipmap.width, mipmap.height, 0, mipmap.data );
24251 console.warn(
"THREE.WebGLRenderer: Attempt to load unsupported compressed texture format in .setCubeTexture()" );
24257 state.texImage2D( _gl.TEXTURE_CUBE_MAP_POSITIVE_X + i, j, glFormat, mipmap.width, mipmap.height, 0, glFormat, glType, mipmap.data );
24267 if ( texture.generateMipmaps && isImagePowerOfTwo ) {
24269 _gl.generateMipmap( _gl.TEXTURE_CUBE_MAP );
24273 textureProperties.__version = texture.version;
24275 if ( texture.onUpdate ) texture.onUpdate( texture );
24279 state.activeTexture( _gl.TEXTURE0 + slot );
24280 state.bindTexture( _gl.TEXTURE_CUBE_MAP, textureProperties.__image__webglTextureCube );
24288 function setCubeTextureDynamic ( texture, slot ) {
24290 state.activeTexture( _gl.TEXTURE0 + slot );
24291 state.bindTexture( _gl.TEXTURE_CUBE_MAP, properties.get( texture ).__webglTexture );
24297 function setupFrameBuffer ( framebuffer, renderTarget, textureTarget ) {
24299 _gl.bindFramebuffer( _gl.FRAMEBUFFER, framebuffer );
24300 _gl.framebufferTexture2D( _gl.FRAMEBUFFER, _gl.COLOR_ATTACHMENT0, textureTarget, properties.get( renderTarget.texture ).__webglTexture, 0 );
24304 function setupRenderBuffer ( renderbuffer, renderTarget ) {
24306 _gl.bindRenderbuffer( _gl.RENDERBUFFER, renderbuffer );
24308 if ( renderTarget.depthBuffer && ! renderTarget.stencilBuffer ) {
24310 _gl.renderbufferStorage( _gl.RENDERBUFFER, _gl.DEPTH_COMPONENT16, renderTarget.width, renderTarget.height );
24311 _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.DEPTH_ATTACHMENT, _gl.RENDERBUFFER, renderbuffer );
24320 }
else if ( renderTarget.depthBuffer && renderTarget.stencilBuffer ) {
24322 _gl.renderbufferStorage( _gl.RENDERBUFFER, _gl.DEPTH_STENCIL, renderTarget.width, renderTarget.height );
24323 _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.DEPTH_STENCIL_ATTACHMENT, _gl.RENDERBUFFER, renderbuffer );
24327 _gl.renderbufferStorage( _gl.RENDERBUFFER, _gl.RGBA4, renderTarget.width, renderTarget.height );
24333 this.setRenderTarget =
function ( renderTarget ) {
24335 var isCube = ( renderTarget instanceof THREE.WebGLRenderTargetCube );
24337 if ( renderTarget && properties.get( renderTarget ).__webglFramebuffer === undefined ) {
24339 var renderTargetProperties = properties.get( renderTarget );
24340 var textureProperties = properties.get( renderTarget.texture );
24342 if ( renderTarget.depthBuffer === undefined ) renderTarget.depthBuffer =
true;
24343 if ( renderTarget.stencilBuffer === undefined ) renderTarget.stencilBuffer =
true;
24345 renderTarget.addEventListener(
'dispose', onRenderTargetDispose );
24347 textureProperties.__webglTexture = _gl.createTexture();
24349 _infoMemory.textures ++;
24353 var isTargetPowerOfTwo = isPowerOfTwo( renderTarget ),
24354 glFormat = paramThreeToGL( renderTarget.texture.format ),
24355 glType = paramThreeToGL( renderTarget.texture.type );
24359 renderTargetProperties.__webglFramebuffer = [];
24360 renderTargetProperties.__webglRenderbuffer = [];
24362 state.bindTexture( _gl.TEXTURE_CUBE_MAP, textureProperties.__webglTexture );
24364 setTextureParameters( _gl.TEXTURE_CUBE_MAP, renderTarget.texture, isTargetPowerOfTwo );
24366 for ( var i = 0; i < 6; i ++ ) {
24368 renderTargetProperties.__webglFramebuffer[ i ] = _gl.createFramebuffer();
24369 renderTargetProperties.__webglRenderbuffer[ i ] = _gl.createRenderbuffer();
24370 state.texImage2D( _gl.TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, glFormat, renderTarget.width, renderTarget.height, 0, glFormat, glType, null );
24372 setupFrameBuffer( renderTargetProperties.__webglFramebuffer[ i ], renderTarget, _gl.TEXTURE_CUBE_MAP_POSITIVE_X + i );
24373 setupRenderBuffer( renderTargetProperties.__webglRenderbuffer[ i ], renderTarget );
24377 if ( renderTarget.texture.generateMipmaps && isTargetPowerOfTwo ) _gl.generateMipmap( _gl.TEXTURE_CUBE_MAP );
24381 renderTargetProperties.__webglFramebuffer = _gl.createFramebuffer();
24383 if ( renderTarget.shareDepthFrom ) {
24385 renderTargetProperties.__webglRenderbuffer = renderTarget.shareDepthFrom.__webglRenderbuffer;
24389 renderTargetProperties.__webglRenderbuffer = _gl.createRenderbuffer();
24393 state.bindTexture( _gl.TEXTURE_2D, textureProperties.__webglTexture );
24394 setTextureParameters( _gl.TEXTURE_2D, renderTarget.texture, isTargetPowerOfTwo );
24396 state.texImage2D( _gl.TEXTURE_2D, 0, glFormat, renderTarget.width, renderTarget.height, 0, glFormat, glType, null );
24398 setupFrameBuffer( renderTargetProperties.__webglFramebuffer, renderTarget, _gl.TEXTURE_2D );
24400 if ( renderTarget.shareDepthFrom ) {
24402 if ( renderTarget.depthBuffer && ! renderTarget.stencilBuffer ) {
24404 _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.DEPTH_ATTACHMENT, _gl.RENDERBUFFER, renderTargetProperties.__webglRenderbuffer );
24406 }
else if ( renderTarget.depthBuffer && renderTarget.stencilBuffer ) {
24408 _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.DEPTH_STENCIL_ATTACHMENT, _gl.RENDERBUFFER, renderTargetProperties.__webglRenderbuffer );
24414 setupRenderBuffer( renderTargetProperties.__webglRenderbuffer, renderTarget );
24418 if ( renderTarget.texture.generateMipmaps && isTargetPowerOfTwo ) _gl.generateMipmap( _gl.TEXTURE_2D );
24426 state.bindTexture( _gl.TEXTURE_CUBE_MAP, null );
24430 state.bindTexture( _gl.TEXTURE_2D, null );
24434 _gl.bindRenderbuffer( _gl.RENDERBUFFER, null );
24435 _gl.bindFramebuffer( _gl.FRAMEBUFFER, null );
24439 var framebuffer, width, height, vx, vy;
24441 if ( renderTarget ) {
24443 var renderTargetProperties = properties.get( renderTarget );
24447 framebuffer = renderTargetProperties.__webglFramebuffer[ renderTarget.activeCubeFace ];
24451 framebuffer = renderTargetProperties.__webglFramebuffer;
24455 width = renderTarget.width;
24456 height = renderTarget.height;
24463 framebuffer = null;
24465 width = _viewportWidth;
24466 height = _viewportHeight;
24473 if ( framebuffer !== _currentFramebuffer ) {
24475 _gl.bindFramebuffer( _gl.FRAMEBUFFER, framebuffer );
24476 _gl.viewport( vx, vy, width, height );
24478 _currentFramebuffer = framebuffer;
24484 var textureProperties = properties.get( renderTarget.texture );
24485 _gl.framebufferTexture2D( _gl.FRAMEBUFFER, _gl.COLOR_ATTACHMENT0, _gl.TEXTURE_CUBE_MAP_POSITIVE_X + renderTarget.activeCubeFace, textureProperties.__webglTexture, 0 );
24489 _currentWidth = width;
24490 _currentHeight = height;
24494 this.readRenderTargetPixels =
function ( renderTarget, x, y, width, height, buffer ) {
24496 if ( renderTarget instanceof THREE.WebGLRenderTarget ===
false ) {
24498 console.error(
'THREE.WebGLRenderer.readRenderTargetPixels: renderTarget is not THREE.WebGLRenderTarget.' );
24503 var framebuffer = properties.get( renderTarget ).__webglFramebuffer;
24505 if ( framebuffer ) {
24507 var restore =
false;
24509 if ( framebuffer !== _currentFramebuffer ) {
24511 _gl.bindFramebuffer( _gl.FRAMEBUFFER, framebuffer );
24519 var texture = renderTarget.texture;
24521 if ( texture.format !== THREE.RGBAFormat
24522 && paramThreeToGL( texture.format ) !== _gl.getParameter( _gl.IMPLEMENTATION_COLOR_READ_FORMAT ) ) {
24524 console.error(
'THREE.WebGLRenderer.readRenderTargetPixels: renderTarget is not in RGBA or implementation defined format.' );
24529 if ( texture.type !== THREE.UnsignedByteType
24530 && paramThreeToGL( texture.type ) !== _gl.getParameter( _gl.IMPLEMENTATION_COLOR_READ_TYPE )
24531 && ! ( texture.type === THREE.FloatType && extensions.get(
'WEBGL_color_buffer_float' ) )
24532 && ! ( texture.type === THREE.HalfFloatType && extensions.get(
'EXT_color_buffer_half_float' ) ) ) {
24534 console.error(
'THREE.WebGLRenderer.readRenderTargetPixels: renderTarget is not in UnsignedByteType or implementation defined type.' );
24539 if ( _gl.checkFramebufferStatus( _gl.FRAMEBUFFER ) === _gl.FRAMEBUFFER_COMPLETE ) {
24541 _gl.readPixels( x, y, width, height, paramThreeToGL( texture.format ), paramThreeToGL( texture.type ), buffer );
24545 console.error(
'THREE.WebGLRenderer.readRenderTargetPixels: readPixels from renderTarget failed. Framebuffer not complete.' );
24553 _gl.bindFramebuffer( _gl.FRAMEBUFFER, _currentFramebuffer );
24563 function updateRenderTargetMipmap( renderTarget ) {
24565 var target = renderTarget instanceof THREE.WebGLRenderTargetCube ? _gl.TEXTURE_CUBE_MAP : _gl.TEXTURE_2D;
24566 var texture = properties.get( renderTarget.texture ).__webglTexture;
24568 state.bindTexture( target, texture );
24569 _gl.generateMipmap( target );
24570 state.bindTexture( target, null );
24576 function filterFallback ( f ) {
24578 if ( f === THREE.NearestFilter || f === THREE.NearestMipMapNearestFilter || f === THREE.NearestMipMapLinearFilter ) {
24580 return _gl.NEAREST;
24590 function paramThreeToGL ( p ) {
24594 if ( p === THREE.RepeatWrapping )
return _gl.REPEAT;
24595 if ( p === THREE.ClampToEdgeWrapping )
return _gl.CLAMP_TO_EDGE;
24596 if ( p === THREE.MirroredRepeatWrapping )
return _gl.MIRRORED_REPEAT;
24598 if ( p === THREE.NearestFilter )
return _gl.NEAREST;
24599 if ( p === THREE.NearestMipMapNearestFilter )
return _gl.NEAREST_MIPMAP_NEAREST;
24600 if ( p === THREE.NearestMipMapLinearFilter )
return _gl.NEAREST_MIPMAP_LINEAR;
24602 if ( p === THREE.LinearFilter )
return _gl.LINEAR;
24603 if ( p === THREE.LinearMipMapNearestFilter )
return _gl.LINEAR_MIPMAP_NEAREST;
24604 if ( p === THREE.LinearMipMapLinearFilter )
return _gl.LINEAR_MIPMAP_LINEAR;
24606 if ( p === THREE.UnsignedByteType )
return _gl.UNSIGNED_BYTE;
24607 if ( p === THREE.UnsignedShort4444Type )
return _gl.UNSIGNED_SHORT_4_4_4_4;
24608 if ( p === THREE.UnsignedShort5551Type )
return _gl.UNSIGNED_SHORT_5_5_5_1;
24609 if ( p === THREE.UnsignedShort565Type )
return _gl.UNSIGNED_SHORT_5_6_5;
24611 if ( p === THREE.ByteType )
return _gl.BYTE;
24612 if ( p === THREE.ShortType )
return _gl.SHORT;
24613 if ( p === THREE.UnsignedShortType )
return _gl.UNSIGNED_SHORT;
24614 if ( p === THREE.IntType )
return _gl.INT;
24615 if ( p === THREE.UnsignedIntType )
return _gl.UNSIGNED_INT;
24616 if ( p === THREE.FloatType )
return _gl.FLOAT;
24618 extension = extensions.get(
'OES_texture_half_float' );
24620 if ( extension !== null ) {
24622 if ( p === THREE.HalfFloatType )
return extension.HALF_FLOAT_OES;
24626 if ( p === THREE.AlphaFormat )
return _gl.ALPHA;
24627 if ( p === THREE.RGBFormat )
return _gl.RGB;
24628 if ( p === THREE.RGBAFormat )
return _gl.RGBA;
24629 if ( p === THREE.LuminanceFormat )
return _gl.LUMINANCE;
24630 if ( p === THREE.LuminanceAlphaFormat )
return _gl.LUMINANCE_ALPHA;
24632 if ( p === THREE.AddEquation )
return _gl.FUNC_ADD;
24633 if ( p === THREE.SubtractEquation )
return _gl.FUNC_SUBTRACT;
24634 if ( p === THREE.ReverseSubtractEquation )
return _gl.FUNC_REVERSE_SUBTRACT;
24636 if ( p === THREE.ZeroFactor )
return _gl.ZERO;
24637 if ( p === THREE.OneFactor )
return _gl.ONE;
24638 if ( p === THREE.SrcColorFactor )
return _gl.SRC_COLOR;
24639 if ( p === THREE.OneMinusSrcColorFactor )
return _gl.ONE_MINUS_SRC_COLOR;
24640 if ( p === THREE.SrcAlphaFactor )
return _gl.SRC_ALPHA;
24641 if ( p === THREE.OneMinusSrcAlphaFactor )
return _gl.ONE_MINUS_SRC_ALPHA;
24642 if ( p === THREE.DstAlphaFactor )
return _gl.DST_ALPHA;
24643 if ( p === THREE.OneMinusDstAlphaFactor )
return _gl.ONE_MINUS_DST_ALPHA;
24645 if ( p === THREE.DstColorFactor )
return _gl.DST_COLOR;
24646 if ( p === THREE.OneMinusDstColorFactor )
return _gl.ONE_MINUS_DST_COLOR;
24647 if ( p === THREE.SrcAlphaSaturateFactor )
return _gl.SRC_ALPHA_SATURATE;
24649 extension = extensions.get(
'WEBGL_compressed_texture_s3tc' );
24651 if ( extension !== null ) {
24653 if ( p === THREE.RGB_S3TC_DXT1_Format )
return extension.COMPRESSED_RGB_S3TC_DXT1_EXT;
24654 if ( p === THREE.RGBA_S3TC_DXT1_Format )
return extension.COMPRESSED_RGBA_S3TC_DXT1_EXT;
24655 if ( p === THREE.RGBA_S3TC_DXT3_Format )
return extension.COMPRESSED_RGBA_S3TC_DXT3_EXT;
24656 if ( p === THREE.RGBA_S3TC_DXT5_Format )
return extension.COMPRESSED_RGBA_S3TC_DXT5_EXT;
24660 extension = extensions.get(
'WEBGL_compressed_texture_pvrtc' );
24662 if ( extension !== null ) {
24664 if ( p === THREE.RGB_PVRTC_4BPPV1_Format )
return extension.COMPRESSED_RGB_PVRTC_4BPPV1_IMG;
24665 if ( p === THREE.RGB_PVRTC_2BPPV1_Format )
return extension.COMPRESSED_RGB_PVRTC_2BPPV1_IMG;
24666 if ( p === THREE.RGBA_PVRTC_4BPPV1_Format )
return extension.COMPRESSED_RGBA_PVRTC_4BPPV1_IMG;
24667 if ( p === THREE.RGBA_PVRTC_2BPPV1_Format )
return extension.COMPRESSED_RGBA_PVRTC_2BPPV1_IMG;
24671 extension = extensions.get(
'EXT_blend_minmax' );
24673 if ( extension !== null ) {
24675 if ( p === THREE.MinEquation )
return extension.MIN_EXT;
24676 if ( p === THREE.MaxEquation )
return extension.MAX_EXT;
24686 this.supportsFloatTextures =
function () {
24688 console.warn(
'THREE.WebGLRenderer: .supportsFloatTextures() is now .extensions.get( \'OES_texture_float\' ).' );
24689 return extensions.get(
'OES_texture_float' );
24693 this.supportsHalfFloatTextures =
function () {
24695 console.warn(
'THREE.WebGLRenderer: .supportsHalfFloatTextures() is now .extensions.get( \'OES_texture_half_float\' ).' );
24696 return extensions.get(
'OES_texture_half_float' );
24700 this.supportsStandardDerivatives =
function () {
24702 console.warn(
'THREE.WebGLRenderer: .supportsStandardDerivatives() is now .extensions.get( \'OES_standard_derivatives\' ).' );
24703 return extensions.get(
'OES_standard_derivatives' );
24707 this.supportsCompressedTextureS3TC =
function () {
24709 console.warn(
'THREE.WebGLRenderer: .supportsCompressedTextureS3TC() is now .extensions.get( \'WEBGL_compressed_texture_s3tc\' ).' );
24710 return extensions.get(
'WEBGL_compressed_texture_s3tc' );
24714 this.supportsCompressedTexturePVRTC =
function () {
24716 console.warn(
'THREE.WebGLRenderer: .supportsCompressedTexturePVRTC() is now .extensions.get( \'WEBGL_compressed_texture_pvrtc\' ).' );
24717 return extensions.get(
'WEBGL_compressed_texture_pvrtc' );
24721 this.supportsBlendMinMax =
function () {
24723 console.warn(
'THREE.WebGLRenderer: .supportsBlendMinMax() is now .extensions.get( \'EXT_blend_minmax\' ).' );
24724 return extensions.get(
'EXT_blend_minmax' );
24728 this.supportsVertexTextures =
function () {
24730 return capabilities.vertexTextures;
24734 this.supportsInstancedArrays =
function () {
24736 console.warn(
'THREE.WebGLRenderer: .supportsInstancedArrays() is now .extensions.get( \'ANGLE_instanced_arrays\' ).' );
24737 return extensions.get(
'ANGLE_instanced_arrays' );
24743 this.initMaterial =
function () {
24745 console.warn(
'THREE.WebGLRenderer: .initMaterial() has been removed.' );
24749 this.addPrePlugin =
function () {
24751 console.warn(
'THREE.WebGLRenderer: .addPrePlugin() has been removed.' );
24755 this.addPostPlugin =
function () {
24757 console.warn(
'THREE.WebGLRenderer: .addPostPlugin() has been removed.' );
24761 this.updateShadowMap =
function () {
24763 console.warn(
'THREE.WebGLRenderer: .updateShadowMap() has been removed.' );
24767 Object.defineProperties(
this, {
24768 shadowMapEnabled: {
24771 return shadowMap.enabled;
24774 set:
function ( value ) {
24776 console.warn(
'THREE.WebGLRenderer: .shadowMapEnabled is now .shadowMap.enabled.' );
24777 shadowMap.enabled = value;
24784 return shadowMap.type;
24787 set:
function ( value ) {
24789 console.warn(
'THREE.WebGLRenderer: .shadowMapType is now .shadowMap.type.' );
24790 shadowMap.type = value;
24794 shadowMapCullFace: {
24797 return shadowMap.cullFace;
24800 set:
function ( value ) {
24802 console.warn(
'THREE.WebGLRenderer: .shadowMapCullFace is now .shadowMap.cullFace.' );
24803 shadowMap.cullFace = value;
24810 return shadowMap.debug;
24813 set:
function ( value ) {
24815 console.warn(
'THREE.WebGLRenderer: .shadowMapDebug is now .shadowMap.debug.' );
24816 shadowMap.debug = value;
24831 THREE.WebGLRenderTarget =
function ( width, height, options ) {
24833 this.uuid = THREE.Math.generateUUID();
24835 this.width = width;
24836 this.height = height;
24838 options = options || {};
24840 if ( options.minFilter === undefined ) options.minFilter = THREE.LinearFilter;
24842 this.texture =
new THREE.Texture( undefined, undefined, options.wrapS, options.wrapT, options.magFilter, options.minFilter, options.format, options.type, options.anisotropy );
24844 this.depthBuffer = options.depthBuffer !== undefined ? options.depthBuffer :
true;
24845 this.stencilBuffer = options.stencilBuffer !== undefined ? options.stencilBuffer :
true;
24847 this.shareDepthFrom = options.shareDepthFrom !== undefined ? options.shareDepthFrom : null;
24851 THREE.WebGLRenderTarget.prototype = {
24853 constructor: THREE.WebGLRenderTarget,
24857 console.warn(
'THREE.WebGLRenderTarget: .wrapS is now .texture.wrapS.' );
24859 return this.texture.wrapS;
24863 set wrapS( value ) {
24865 console.warn(
'THREE.WebGLRenderTarget: .wrapS is now .texture.wrapS.' );
24867 this.texture.wrapS = value;
24873 console.warn(
'THREE.WebGLRenderTarget: .wrapT is now .texture.wrapT.' );
24875 return this.texture.wrapT;
24879 set wrapT( value ) {
24881 console.warn(
'THREE.WebGLRenderTarget: .wrapT is now .texture.wrapT.' );
24883 this.texture.wrapT = value;
24889 console.warn(
'THREE.WebGLRenderTarget: .magFilter is now .texture.magFilter.' );
24891 return this.texture.magFilter;
24895 set magFilter( value ) {
24897 console.warn(
'THREE.WebGLRenderTarget: .magFilter is now .texture.magFilter.' );
24899 this.texture.magFilter = value;
24905 console.warn(
'THREE.WebGLRenderTarget: .minFilter is now .texture.minFilter.' );
24907 return this.texture.minFilter;
24911 set minFilter( value ) {
24913 console.warn(
'THREE.WebGLRenderTarget: .minFilter is now .texture.minFilter.' );
24915 this.texture.minFilter = value;
24921 console.warn(
'THREE.WebGLRenderTarget: .anisotropy is now .texture.anisotropy.' );
24923 return this.texture.anisotropy;
24927 set anisotropy( value ) {
24929 console.warn(
'THREE.WebGLRenderTarget: .anisotropy is now .texture.anisotropy.' );
24931 this.texture.anisotropy = value;
24937 console.warn(
'THREE.WebGLRenderTarget: .offset is now .texture.offset.' );
24939 return this.texture.offset;
24943 set offset( value ) {
24945 console.warn(
'THREE.WebGLRenderTarget: .offset is now .texture.offset.' );
24947 this.texture.offset = value;
24953 console.warn(
'THREE.WebGLRenderTarget: .repeat is now .texture.repeat.' );
24955 return this.texture.repeat;
24959 set repeat( value ) {
24961 console.warn(
'THREE.WebGLRenderTarget: .repeat is now .texture.repeat.' );
24963 this.texture.repeat = value;
24969 console.warn(
'THREE.WebGLRenderTarget: .format is now .texture.format.' );
24971 return this.texture.format;
24975 set format( value ) {
24977 console.warn(
'THREE.WebGLRenderTarget: .format is now .texture.format.' );
24979 this.texture.format = value;
24985 console.warn(
'THREE.WebGLRenderTarget: .type is now .texture.type.' );
24987 return this.texture.type;
24991 set type( value ) {
24993 console.warn(
'THREE.WebGLRenderTarget: .type is now .texture.type.' );
24995 this.texture.type = value;
24999 get generateMipmaps() {
25001 console.warn(
'THREE.WebGLRenderTarget: .generateMipmaps is now .texture.generateMipmaps.' );
25003 return this.texture.generateMipmaps;
25007 set generateMipmaps( value ) {
25009 console.warn(
'THREE.WebGLRenderTarget: .generateMipmaps is now .texture.generateMipmaps.' );
25011 this.texture.generateMipmaps = value;
25017 setSize:
function ( width, height ) {
25019 if ( this.width !== width || this.height !== height ) {
25021 this.width = width;
25022 this.height = height;
25030 clone:
function () {
25032 return new this.constructor().copy(
this );
25036 copy:
function ( source ) {
25038 this.width = source.width;
25039 this.height = source.height;
25041 this.texture = source.texture.clone();
25043 this.depthBuffer = source.depthBuffer;
25044 this.stencilBuffer = source.stencilBuffer;
25046 this.shareDepthFrom = source.shareDepthFrom;
25052 dispose:
function () {
25054 this.dispatchEvent( { type:
'dispose' } );
25060 THREE.EventDispatcher.prototype.apply( THREE.WebGLRenderTarget.prototype );
25068 THREE.WebGLRenderTargetCube =
function ( width, height, options ) {
25070 THREE.WebGLRenderTarget.call(
this, width, height, options );
25072 this.activeCubeFace = 0;
25076 THREE.WebGLRenderTargetCube.prototype = Object.create( THREE.WebGLRenderTarget.prototype );
25077 THREE.WebGLRenderTargetCube.prototype.constructor = THREE.WebGLRenderTargetCube;
25085 THREE.WebGLBufferRenderer =
function ( _gl, extensions, _infoRender ) {
25089 function setMode( value ) {
25095 function render( start, count ) {
25097 _gl.drawArrays( mode, start, count );
25099 _infoRender.calls ++;
25100 _infoRender.vertices += count;
25101 if ( mode === _gl.TRIANGLES ) _infoRender.faces += count / 3;
25105 function renderInstances( geometry ) {
25107 var extension = extensions.get(
'ANGLE_instanced_arrays' );
25109 if ( extension === null ) {
25111 console.error(
'THREE.WebGLBufferRenderer: using THREE.InstancedBufferGeometry but hardware does not support extension ANGLE_instanced_arrays.' );
25116 var position = geometry.attributes.position;
25118 if ( position instanceof THREE.InterleavedBufferAttribute ) {
25120 extension.drawArraysInstancedANGLE( mode, 0, position.data.count, geometry.maxInstancedCount );
25124 extension.drawArraysInstancedANGLE( mode, 0, position.count, geometry.maxInstancedCount );
25130 this.setMode = setMode;
25131 this.render = render;
25132 this.renderInstances = renderInstances;
25142 THREE.WebGLIndexedBufferRenderer =
function ( _gl, extensions, _infoRender ) {
25146 function setMode( value ) {
25154 function setIndex( index ) {
25156 if ( index.array instanceof Uint32Array && extensions.get(
'OES_element_index_uint' ) ) {
25158 type = _gl.UNSIGNED_INT;
25163 type = _gl.UNSIGNED_SHORT;
25170 function render( start, count ) {
25172 _gl.drawElements( mode, count, type, start * size );
25174 _infoRender.calls ++;
25175 _infoRender.vertices += count;
25176 if ( mode === _gl.TRIANGLES ) _infoRender.faces += count / 3;
25180 function renderInstances( geometry ) {
25182 var extension = extensions.get(
'ANGLE_instanced_arrays' );
25184 if ( extension === null ) {
25186 console.error(
'THREE.WebGLBufferRenderer: using THREE.InstancedBufferGeometry but hardware does not support extension ANGLE_instanced_arrays.' );
25191 var index = geometry.index;
25193 extension.drawElementsInstancedANGLE( mode, index.array.length, type, 0, geometry.maxInstancedCount );
25197 this.setMode = setMode;
25198 this.setIndex = setIndex;
25199 this.render = render;
25200 this.renderInstances = renderInstances;
25210 THREE.WebGLExtensions =
function ( gl ) {
25212 var extensions = {};
25214 this.
get =
function ( name ) {
25216 if ( extensions[ name ] !== undefined ) {
25218 return extensions[ name ];
25226 case 'EXT_texture_filter_anisotropic':
25227 extension = gl.getExtension(
'EXT_texture_filter_anisotropic' ) || gl.getExtension(
'MOZ_EXT_texture_filter_anisotropic' ) || gl.getExtension(
'WEBKIT_EXT_texture_filter_anisotropic' );
25230 case 'WEBGL_compressed_texture_s3tc':
25231 extension = gl.getExtension(
'WEBGL_compressed_texture_s3tc' ) || gl.getExtension(
'MOZ_WEBGL_compressed_texture_s3tc' ) || gl.getExtension(
'WEBKIT_WEBGL_compressed_texture_s3tc' );
25234 case 'WEBGL_compressed_texture_pvrtc':
25235 extension = gl.getExtension(
'WEBGL_compressed_texture_pvrtc' ) || gl.getExtension(
'WEBKIT_WEBGL_compressed_texture_pvrtc' );
25239 extension = gl.getExtension( name );
25243 if ( extension === null ) {
25245 console.warn(
'THREE.WebGLRenderer: ' + name +
' extension not supported.' );
25249 extensions[ name ] = extension;
25259 THREE.WebGLCapabilities =
function ( gl, extensions, parameters ) {
25261 function getMaxPrecision( precision ) {
25263 if ( precision ===
'highp' ) {
25265 if ( gl.getShaderPrecisionFormat( gl.VERTEX_SHADER, gl.HIGH_FLOAT ).precision > 0 &&
25266 gl.getShaderPrecisionFormat( gl.FRAGMENT_SHADER, gl.HIGH_FLOAT ).precision > 0 ) {
25272 precision =
'mediump';
25276 if ( precision ===
'mediump' ) {
25278 if ( gl.getShaderPrecisionFormat( gl.VERTEX_SHADER, gl.MEDIUM_FLOAT ).precision > 0 &&
25279 gl.getShaderPrecisionFormat( gl.FRAGMENT_SHADER, gl.MEDIUM_FLOAT ).precision > 0 ) {
25291 this.getMaxPrecision = getMaxPrecision;
25293 this.precision = parameters.precision !== undefined ? parameters.precision :
'highp',
25294 this.logarithmicDepthBuffer = parameters.logarithmicDepthBuffer !== undefined ? parameters.logarithmicDepthBuffer :
false;
25296 this.maxTextures = gl.getParameter( gl.MAX_TEXTURE_IMAGE_UNITS );
25297 this.maxVertexTextures = gl.getParameter( gl.MAX_VERTEX_TEXTURE_IMAGE_UNITS );
25298 this.maxTextureSize = gl.getParameter( gl.MAX_TEXTURE_SIZE );
25299 this.maxCubemapSize = gl.getParameter( gl.MAX_CUBE_MAP_TEXTURE_SIZE );
25301 this.maxAttributes = gl.getParameter( gl.MAX_VERTEX_ATTRIBS );
25302 this.maxVertexUniforms = gl.getParameter( gl.MAX_VERTEX_UNIFORM_VECTORS );
25303 this.maxVaryings = gl.getParameter( gl.MAX_VARYING_VECTORS );
25304 this.maxFragmentUniforms = gl.getParameter( gl.MAX_FRAGMENT_UNIFORM_VECTORS );
25306 this.vertexTextures = this.maxVertexTextures > 0;
25307 this.floatFragmentTextures = !! extensions.get(
'OES_texture_float' );
25308 this.floatVertexTextures = this.vertexTextures && this.floatFragmentTextures;
25310 var _maxPrecision = getMaxPrecision( this.precision );
25312 if ( _maxPrecision !== this.precision ) {
25314 console.warn(
'THREE.WebGLRenderer:', this.precision,
'not supported, using', _maxPrecision,
'instead.' );
25315 this.precision = _maxPrecision;
25319 if ( this.logarithmicDepthBuffer ) {
25321 this.logarithmicDepthBuffer = !! extensions.get(
'EXT_frag_depth' );
25333 THREE.WebGLGeometries =
function ( gl, properties, info ) {
25335 var geometries = {};
25337 function get( object ) {
25339 var geometry =
object.geometry;
25341 if ( geometries[ geometry.id ] !== undefined ) {
25343 return geometries[ geometry.id ];
25347 geometry.addEventListener(
'dispose', onGeometryDispose );
25349 var buffergeometry;
25351 if ( geometry instanceof THREE.BufferGeometry ) {
25353 buffergeometry = geometry;
25355 }
else if ( geometry instanceof THREE.Geometry ) {
25357 if ( geometry._bufferGeometry === undefined ) {
25359 geometry._bufferGeometry =
new THREE.BufferGeometry().setFromObject(
object );
25363 buffergeometry = geometry._bufferGeometry;
25367 geometries[ geometry.id ] = buffergeometry;
25369 info.memory.geometries ++;
25371 return buffergeometry;
25375 function onGeometryDispose( event ) {
25377 var geometry =
event.target;
25378 var buffergeometry = geometries[ geometry.id ];
25380 deleteAttributes( buffergeometry.attributes );
25382 geometry.removeEventListener(
'dispose', onGeometryDispose );
25384 delete geometries[ geometry.id ];
25386 var
property = properties.get( geometry );
25387 if ( property.wireframe ) deleteAttribute( property.wireframe );
25389 info.memory.geometries --;
25393 function getAttributeBuffer( attribute ) {
25395 if ( attribute instanceof THREE.InterleavedBufferAttribute ) {
25397 return properties.get( attribute.data ).__webglBuffer;
25401 return properties.get( attribute ).__webglBuffer;
25405 function deleteAttribute( attribute ) {
25407 var buffer = getAttributeBuffer( attribute );
25409 if ( buffer !== undefined ) {
25411 gl.deleteBuffer( buffer );
25412 removeAttributeBuffer( attribute );
25418 function deleteAttributes( attributes ) {
25420 for ( var name in attributes ) {
25422 deleteAttribute( attributes[ name ] );
25428 function removeAttributeBuffer( attribute ) {
25430 if ( attribute instanceof THREE.InterleavedBufferAttribute ) {
25432 properties.delete( attribute.data );
25436 properties.delete( attribute );
25452 THREE.WebGLObjects =
function ( gl, properties, info ) {
25454 var geometries =
new THREE.WebGLGeometries( gl, properties, info );
25458 function update(
object ) {
25462 var geometry = geometries.get(
object );
25464 if (
object.geometry instanceof THREE.Geometry ) {
25466 geometry.updateFromObject(
object );
25470 var index = geometry.index;
25471 var attributes = geometry.attributes;
25473 if ( index !== null ) {
25475 updateAttribute( index, gl.ELEMENT_ARRAY_BUFFER );
25479 for ( var name in attributes ) {
25481 updateAttribute( attributes[ name ], gl.ARRAY_BUFFER );
25487 var morphAttributes = geometry.morphAttributes;
25489 for ( var name in morphAttributes ) {
25491 var array = morphAttributes[ name ];
25493 for ( var i = 0, l = array.length; i < l; i ++ ) {
25495 updateAttribute( array[ i ], gl.ARRAY_BUFFER );
25505 function updateAttribute( attribute, bufferType ) {
25507 var data = ( attribute instanceof THREE.InterleavedBufferAttribute ) ? attribute.data : attribute;
25509 var attributeProperties = properties.get( data );
25511 if ( attributeProperties.__webglBuffer === undefined ) {
25513 createBuffer( attributeProperties, data, bufferType );
25515 }
else if ( attributeProperties.version !== data.version ) {
25517 updateBuffer( attributeProperties, data, bufferType );
25523 function createBuffer( attributeProperties, data, bufferType ) {
25525 attributeProperties.__webglBuffer = gl.createBuffer();
25526 gl.bindBuffer( bufferType, attributeProperties.__webglBuffer );
25528 var usage = data.dynamic ? gl.DYNAMIC_DRAW : gl.STATIC_DRAW;
25530 gl.bufferData( bufferType, data.array, usage );
25532 attributeProperties.version = data.version;
25536 function updateBuffer( attributeProperties, data, bufferType ) {
25538 gl.bindBuffer( bufferType, attributeProperties.__webglBuffer );
25540 if ( data.dynamic ===
false || data.updateRange.count === - 1 ) {
25544 gl.bufferSubData( bufferType, 0, data.array );
25546 }
else if ( data.updateRange.count === 0 ) {
25548 console.error(
'THREE.WebGLObjects.updateBuffer: dynamic THREE.BufferAttribute marked as needsUpdate but updateRange.count is 0, ensure you are using set methods or updating manually.' );
25552 gl.bufferSubData( bufferType, data.updateRange.offset * data.array.BYTES_PER_ELEMENT,
25553 data.array.subarray( data.updateRange.offset, data.updateRange.offset + data.updateRange.count ) );
25555 data.updateRange.count = 0;
25559 attributeProperties.version = data.version;
25563 function getAttributeBuffer( attribute ) {
25565 if ( attribute instanceof THREE.InterleavedBufferAttribute ) {
25567 return properties.get( attribute.data ).__webglBuffer;
25571 return properties.get( attribute ).__webglBuffer;
25575 function getWireframeAttribute( geometry ) {
25577 var
property = properties.get( geometry );
25579 if ( property.wireframe !== undefined ) {
25581 return property.wireframe;
25587 var index = geometry.index;
25588 var attributes = geometry.attributes;
25589 var position = attributes.position;
25593 if ( index !== null ) {
25596 var array = index.array;
25598 for ( var i = 0, l = array.length; i < l; i += 3 ) {
25600 var a = array[ i + 0 ];
25601 var b = array[ i + 1 ];
25602 var c = array[ i + 2 ];
25604 if ( checkEdge( edges, a, b ) ) indices.push( a, b );
25605 if ( checkEdge( edges, b, c ) ) indices.push( b, c );
25606 if ( checkEdge( edges, c, a ) ) indices.push( c, a );
25612 var array = attributes.position.array;
25614 for ( var i = 0, l = ( array.length / 3 ) - 1; i < l; i += 3 ) {
25620 indices.push( a, b, b, c, c, a );
25628 var TypeArray = position.count > 65535 ? Uint32Array : Uint16Array;
25629 var attribute =
new THREE.BufferAttribute(
new TypeArray( indices ), 1 );
25631 updateAttribute( attribute, gl.ELEMENT_ARRAY_BUFFER );
25633 property.wireframe = attribute;
25639 function checkEdge( edges, a, b ) {
25649 var list = edges[ a ];
25651 if ( list === undefined ) {
25653 edges[ a ] = [ b ];
25656 }
else if ( list.indexOf( b ) === -1 ) {
25667 this.getAttributeBuffer = getAttributeBuffer;
25668 this.getWireframeAttribute = getWireframeAttribute;
25670 this.update = update;
25676 THREE.WebGLProgram = (
function () {
25678 var programIdCount = 0;
25680 function generateDefines( defines ) {
25684 for ( var name in defines ) {
25686 var value = defines[ name ];
25688 if ( value ===
false )
continue;
25690 chunks.push(
'#define ' + name +
' ' + value );
25694 return chunks.join(
'\n' );
25698 function fetchUniformLocations( gl, program, identifiers ) {
25702 var n = gl.getProgramParameter( program, gl.ACTIVE_UNIFORMS );
25704 for ( var i = 0; i < n; i ++ ) {
25706 var info = gl.getActiveUniform( program, i );
25707 var name = info.name;
25708 var location = gl.getUniformLocation( program, name );
25712 var suffixPos = name.lastIndexOf(
'[0]' );
25713 if ( suffixPos !== - 1 && suffixPos === name.length - 3 ) {
25715 uniforms[ name.substr( 0, suffixPos ) ] = location;
25719 uniforms[ name ] = location;
25727 function fetchAttributeLocations( gl, program, identifiers ) {
25729 var attributes = {};
25731 var n = gl.getProgramParameter( program, gl.ACTIVE_ATTRIBUTES );
25733 for ( var i = 0; i < n; i ++ ) {
25735 var info = gl.getActiveAttrib( program, i );
25736 var name = info.name;
25740 attributes[ name ] = gl.getAttribLocation( program, name );
25748 function filterEmptyLine(
string ) {
25750 return string !==
'';
25754 return function WebGLProgram( renderer, code, material, parameters ) {
25756 var gl = renderer.context;
25758 var defines = material.defines;
25760 var vertexShader = material.__webglShader.vertexShader;
25761 var fragmentShader = material.__webglShader.fragmentShader;
25763 var shadowMapTypeDefine =
'SHADOWMAP_TYPE_BASIC';
25765 if ( parameters.shadowMapType === THREE.PCFShadowMap ) {
25767 shadowMapTypeDefine =
'SHADOWMAP_TYPE_PCF';
25769 }
else if ( parameters.shadowMapType === THREE.PCFSoftShadowMap ) {
25771 shadowMapTypeDefine =
'SHADOWMAP_TYPE_PCF_SOFT';
25775 var envMapTypeDefine =
'ENVMAP_TYPE_CUBE';
25776 var envMapModeDefine =
'ENVMAP_MODE_REFLECTION';
25777 var envMapBlendingDefine =
'ENVMAP_BLENDING_MULTIPLY';
25779 if ( parameters.envMap ) {
25781 switch ( material.envMap.mapping ) {
25783 case THREE.CubeReflectionMapping:
25784 case THREE.CubeRefractionMapping:
25785 envMapTypeDefine =
'ENVMAP_TYPE_CUBE';
25788 case THREE.EquirectangularReflectionMapping:
25789 case THREE.EquirectangularRefractionMapping:
25790 envMapTypeDefine =
'ENVMAP_TYPE_EQUIREC';
25793 case THREE.SphericalReflectionMapping:
25794 envMapTypeDefine =
'ENVMAP_TYPE_SPHERE';
25799 switch ( material.envMap.mapping ) {
25801 case THREE.CubeRefractionMapping:
25802 case THREE.EquirectangularRefractionMapping:
25803 envMapModeDefine =
'ENVMAP_MODE_REFRACTION';
25808 switch ( material.combine ) {
25810 case THREE.MultiplyOperation:
25811 envMapBlendingDefine =
'ENVMAP_BLENDING_MULTIPLY';
25814 case THREE.MixOperation:
25815 envMapBlendingDefine =
'ENVMAP_BLENDING_MIX';
25818 case THREE.AddOperation:
25819 envMapBlendingDefine =
'ENVMAP_BLENDING_ADD';
25826 var gammaFactorDefine = ( renderer.gammaFactor > 0 ) ? renderer.gammaFactor : 1.0;
25832 var customDefines = generateDefines( defines );
25836 var program = gl.createProgram();
25838 var prefixVertex, prefixFragment;
25840 if ( material instanceof THREE.RawShaderMaterial ) {
25843 prefixFragment =
'';
25849 'precision ' + parameters.precision +
' float;',
25850 'precision ' + parameters.precision +
' int;',
25852 '#define SHADER_NAME ' + material.__webglShader.name,
25856 parameters.supportsVertexTextures ?
'#define VERTEX_TEXTURES' :
'',
25858 renderer.gammaInput ?
'#define GAMMA_INPUT' :
'',
25859 renderer.gammaOutput ?
'#define GAMMA_OUTPUT' :
'',
25860 '#define GAMMA_FACTOR ' + gammaFactorDefine,
25862 '#define MAX_DIR_LIGHTS ' + parameters.maxDirLights,
25863 '#define MAX_POINT_LIGHTS ' + parameters.maxPointLights,
25864 '#define MAX_SPOT_LIGHTS ' + parameters.maxSpotLights,
25865 '#define MAX_HEMI_LIGHTS ' + parameters.maxHemiLights,
25867 '#define MAX_SHADOWS ' + parameters.maxShadows,
25869 '#define MAX_BONES ' + parameters.maxBones,
25871 parameters.map ?
'#define USE_MAP' :
'',
25872 parameters.envMap ?
'#define USE_ENVMAP' :
'',
25873 parameters.envMap ?
'#define ' + envMapModeDefine :
'',
25874 parameters.lightMap ?
'#define USE_LIGHTMAP' :
'',
25875 parameters.aoMap ?
'#define USE_AOMAP' :
'',
25876 parameters.emissiveMap ?
'#define USE_EMISSIVEMAP' :
'',
25877 parameters.bumpMap ?
'#define USE_BUMPMAP' :
'',
25878 parameters.normalMap ?
'#define USE_NORMALMAP' :
'',
25879 parameters.displacementMap && parameters.supportsVertexTextures ?
'#define USE_DISPLACEMENTMAP' :
'',
25880 parameters.specularMap ?
'#define USE_SPECULARMAP' :
'',
25881 parameters.alphaMap ?
'#define USE_ALPHAMAP' :
'',
25882 parameters.vertexColors ?
'#define USE_COLOR' :
'',
25884 parameters.flatShading ?
'#define FLAT_SHADED' :
'',
25886 parameters.skinning ?
'#define USE_SKINNING' :
'',
25887 parameters.useVertexTexture ?
'#define BONE_TEXTURE' :
'',
25889 parameters.morphTargets ?
'#define USE_MORPHTARGETS' :
'',
25890 parameters.morphNormals && parameters.flatShading ===
false ?
'#define USE_MORPHNORMALS' :
'',
25891 parameters.doubleSided ?
'#define DOUBLE_SIDED' :
'',
25892 parameters.flipSided ?
'#define FLIP_SIDED' :
'',
25894 parameters.shadowMapEnabled ?
'#define USE_SHADOWMAP' :
'',
25895 parameters.shadowMapEnabled ?
'#define ' + shadowMapTypeDefine :
'',
25896 parameters.shadowMapDebug ?
'#define SHADOWMAP_DEBUG' :
'',
25897 parameters.pointLightShadows > 0 ?
'#define POINT_LIGHT_SHADOWS' :
'',
25899 parameters.sizeAttenuation ?
'#define USE_SIZEATTENUATION' :
'',
25901 parameters.logarithmicDepthBuffer ?
'#define USE_LOGDEPTHBUF' :
'',
25902 parameters.logarithmicDepthBuffer && renderer.extensions.get(
'EXT_frag_depth' ) ?
'#define USE_LOGDEPTHBUF_EXT' :
'',
25905 'uniform mat4 modelMatrix;',
25906 'uniform mat4 modelViewMatrix;',
25907 'uniform mat4 projectionMatrix;',
25908 'uniform mat4 viewMatrix;',
25909 'uniform mat3 normalMatrix;',
25910 'uniform vec3 cameraPosition;',
25912 'attribute vec3 position;',
25913 'attribute vec3 normal;',
25914 'attribute vec2 uv;',
25916 '#ifdef USE_COLOR',
25918 ' attribute vec3 color;',
25922 '#ifdef USE_MORPHTARGETS',
25924 ' attribute vec3 morphTarget0;',
25925 ' attribute vec3 morphTarget1;',
25926 ' attribute vec3 morphTarget2;',
25927 ' attribute vec3 morphTarget3;',
25929 ' #ifdef USE_MORPHNORMALS',
25931 ' attribute vec3 morphNormal0;',
25932 ' attribute vec3 morphNormal1;',
25933 ' attribute vec3 morphNormal2;',
25934 ' attribute vec3 morphNormal3;',
25938 ' attribute vec3 morphTarget4;',
25939 ' attribute vec3 morphTarget5;',
25940 ' attribute vec3 morphTarget6;',
25941 ' attribute vec3 morphTarget7;',
25947 '#ifdef USE_SKINNING',
25949 ' attribute vec4 skinIndex;',
25950 ' attribute vec4 skinWeight;',
25956 ].filter( filterEmptyLine ).join(
'\n' );
25960 parameters.bumpMap || parameters.normalMap || parameters.flatShading || material.derivatives ?
'#extension GL_OES_standard_derivatives : enable' :
'',
25961 parameters.logarithmicDepthBuffer && renderer.extensions.get(
'EXT_frag_depth' ) ?
'#extension GL_EXT_frag_depth : enable' :
'',
25963 'precision ' + parameters.precision +
' float;',
25964 'precision ' + parameters.precision +
' int;',
25966 '#define SHADER_NAME ' + material.__webglShader.name,
25970 '#define MAX_DIR_LIGHTS ' + parameters.maxDirLights,
25971 '#define MAX_POINT_LIGHTS ' + parameters.maxPointLights,
25972 '#define MAX_SPOT_LIGHTS ' + parameters.maxSpotLights,
25973 '#define MAX_HEMI_LIGHTS ' + parameters.maxHemiLights,
25975 '#define MAX_SHADOWS ' + parameters.maxShadows,
25977 parameters.alphaTest ?
'#define ALPHATEST ' + parameters.alphaTest :
'',
25979 renderer.gammaInput ?
'#define GAMMA_INPUT' :
'',
25980 renderer.gammaOutput ?
'#define GAMMA_OUTPUT' :
'',
25981 '#define GAMMA_FACTOR ' + gammaFactorDefine,
25983 ( parameters.useFog && parameters.fog ) ?
'#define USE_FOG' :
'',
25984 ( parameters.useFog && parameters.fogExp ) ?
'#define FOG_EXP2' :
'',
25986 parameters.map ?
'#define USE_MAP' :
'',
25987 parameters.envMap ?
'#define USE_ENVMAP' :
'',
25988 parameters.envMap ?
'#define ' + envMapTypeDefine :
'',
25989 parameters.envMap ?
'#define ' + envMapModeDefine :
'',
25990 parameters.envMap ?
'#define ' + envMapBlendingDefine :
'',
25991 parameters.lightMap ?
'#define USE_LIGHTMAP' :
'',
25992 parameters.aoMap ?
'#define USE_AOMAP' :
'',
25993 parameters.emissiveMap ?
'#define USE_EMISSIVEMAP' :
'',
25994 parameters.bumpMap ?
'#define USE_BUMPMAP' :
'',
25995 parameters.normalMap ?
'#define USE_NORMALMAP' :
'',
25996 parameters.specularMap ?
'#define USE_SPECULARMAP' :
'',
25997 parameters.alphaMap ?
'#define USE_ALPHAMAP' :
'',
25998 parameters.vertexColors ?
'#define USE_COLOR' :
'',
26000 parameters.flatShading ?
'#define FLAT_SHADED' :
'',
26002 parameters.metal ?
'#define METAL' :
'',
26003 parameters.doubleSided ?
'#define DOUBLE_SIDED' :
'',
26004 parameters.flipSided ?
'#define FLIP_SIDED' :
'',
26006 parameters.shadowMapEnabled ?
'#define USE_SHADOWMAP' :
'',
26007 parameters.shadowMapEnabled ?
'#define ' + shadowMapTypeDefine :
'',
26008 parameters.shadowMapDebug ?
'#define SHADOWMAP_DEBUG' :
'',
26009 parameters.pointLightShadows > 0 ?
'#define POINT_LIGHT_SHADOWS' :
'',
26011 parameters.logarithmicDepthBuffer ?
'#define USE_LOGDEPTHBUF' :
'',
26012 parameters.logarithmicDepthBuffer && renderer.extensions.get(
'EXT_frag_depth' ) ?
'#define USE_LOGDEPTHBUF_EXT' :
'',
26014 'uniform mat4 viewMatrix;',
26015 'uniform vec3 cameraPosition;',
26019 ].filter( filterEmptyLine ).join(
'\n' );
26023 var vertexGlsl = prefixVertex + vertexShader;
26024 var fragmentGlsl = prefixFragment + fragmentShader;
26026 var glVertexShader = THREE.WebGLShader( gl, gl.VERTEX_SHADER, vertexGlsl );
26027 var glFragmentShader = THREE.WebGLShader( gl, gl.FRAGMENT_SHADER, fragmentGlsl );
26029 gl.attachShader( program, glVertexShader );
26030 gl.attachShader( program, glFragmentShader );
26034 if ( material.index0AttributeName !== undefined ) {
26036 gl.bindAttribLocation( program, 0, material.index0AttributeName );
26038 }
else if ( parameters.morphTargets ===
true ) {
26041 gl.bindAttribLocation( program, 0,
'position' );
26045 gl.linkProgram( program );
26047 var programLog = gl.getProgramInfoLog( program );
26048 var vertexLog = gl.getShaderInfoLog( glVertexShader );
26049 var fragmentLog = gl.getShaderInfoLog( glFragmentShader );
26051 var runnable =
true;
26052 var haveDiagnostics =
true;
26054 if ( gl.getProgramParameter( program, gl.LINK_STATUS ) === false ) {
26058 console.error(
'THREE.WebGLProgram: shader error: ', gl.getError(),
'gl.VALIDATE_STATUS', gl.getProgramParameter( program, gl.VALIDATE_STATUS ),
'gl.getProgramInfoLog', programLog, vertexLog, fragmentLog );
26060 }
else if ( programLog !==
'' ) {
26062 console.warn(
'THREE.WebGLProgram: gl.getProgramInfoLog()', programLog );
26064 }
else if ( vertexLog ===
'' || fragmentLog ===
'' ) {
26066 haveDiagnostics =
false;
26070 if ( haveDiagnostics ) {
26072 this.diagnostics = {
26074 runnable: runnable,
26075 material: material,
26077 programLog: programLog,
26082 prefix: prefixVertex
26089 prefix: prefixFragment
26099 gl.deleteShader( glVertexShader );
26100 gl.deleteShader( glFragmentShader );
26104 var cachedUniforms;
26106 this.getUniforms =
function() {
26108 if ( cachedUniforms === undefined ) {
26110 cachedUniforms = fetchUniformLocations( gl, program );
26114 return cachedUniforms;
26120 var cachedAttributes;
26122 this.getAttributes =
function() {
26124 if ( cachedAttributes === undefined ) {
26126 cachedAttributes = fetchAttributeLocations( gl, program );
26130 return cachedAttributes;
26136 this.destroy =
function() {
26138 gl.deleteProgram( program );
26139 this.program = undefined;
26145 Object.defineProperties(
this, {
26150 console.warn(
'THREE.WebGLProgram: .uniforms is now .getUniforms().' );
26151 return this.getUniforms();
26159 console.warn(
'THREE.WebGLProgram: .attributes is now .getAttributes().' );
26160 return this.getAttributes();
26170 this.
id = programIdCount ++;
26172 this.usedTimes = 1;
26173 this.program = program;
26174 this.vertexShader = glVertexShader;
26175 this.fragmentShader = glFragmentShader;
26185 THREE.WebGLPrograms =
function ( renderer, capabilities ) {
26190 MeshDepthMaterial:
'depth',
26191 MeshNormalMaterial:
'normal',
26192 MeshBasicMaterial:
'basic',
26193 MeshLambertMaterial:
'lambert',
26194 MeshPhongMaterial:
'phong',
26195 LineBasicMaterial:
'basic',
26196 LineDashedMaterial:
'dashed',
26197 PointsMaterial:
'points'
26200 var parameterNames = [
26201 "precision",
"supportsVertexTextures",
"map",
"envMap",
"envMapMode",
26202 "lightMap",
"aoMap",
"emissiveMap",
"bumpMap",
"normalMap",
"displacementMap",
"specularMap",
26203 "alphaMap",
"combine",
"vertexColors",
"fog",
"useFog",
"fogExp",
26204 "flatShading",
"sizeAttenuation",
"logarithmicDepthBuffer",
"skinning",
26205 "maxBones",
"useVertexTexture",
"morphTargets",
"morphNormals",
26206 "maxMorphTargets",
"maxMorphNormals",
"maxDirLights",
"maxPointLights",
26207 "maxSpotLights",
"maxHemiLights",
"maxShadows",
"shadowMapEnabled",
"pointLightShadows",
26208 "shadowMapType",
"shadowMapDebug",
"alphaTest",
"metal",
"doubleSided",
26213 function allocateBones (
object ) {
26215 if ( capabilities.floatVertexTextures &&
object &&
object.skeleton &&
object.skeleton.useVertexTexture ) {
26228 var nVertexUniforms = capabilities.maxVertexUniforms;
26229 var nVertexMatrices = Math.floor( ( nVertexUniforms - 20 ) / 4 );
26231 var maxBones = nVertexMatrices;
26233 if (
object !== undefined &&
object instanceof THREE.SkinnedMesh ) {
26235 maxBones = Math.min(
object.skeleton.bones.length, maxBones );
26237 if ( maxBones <
object.skeleton.bones.length ) {
26239 console.warn(
'WebGLRenderer: too many bones - ' +
object.skeleton.bones.length +
', this GPU supports just ' + maxBones +
' (try OpenGL instead of ANGLE)' );
26251 function allocateLights( lights ) {
26254 var pointLights = 0;
26255 var spotLights = 0;
26256 var hemiLights = 0;
26258 for ( var l = 0, ll = lights.length; l < ll; l ++ ) {
26260 var light = lights[ l ];
26262 if ( light.visible ===
false )
continue;
26264 if ( light instanceof THREE.DirectionalLight ) dirLights ++;
26265 if ( light instanceof THREE.PointLight ) pointLights ++;
26266 if ( light instanceof THREE.SpotLight ) spotLights ++;
26267 if ( light instanceof THREE.HemisphereLight ) hemiLights ++;
26271 return {
'directional': dirLights,
'point': pointLights,
'spot': spotLights,
'hemi': hemiLights };
26275 function allocateShadows( lights ) {
26277 var maxShadows = 0;
26278 var pointLightShadows = 0;
26280 for ( var l = 0, ll = lights.length; l < ll; l ++ ) {
26282 var light = lights[ l ];
26284 if ( ! light.castShadow )
continue;
26286 if ( light instanceof THREE.SpotLight || light instanceof THREE.DirectionalLight ) maxShadows ++;
26287 if ( light instanceof THREE.PointLight ) {
26290 pointLightShadows ++;
26296 return {
'maxShadows': maxShadows,
'pointLightShadows': pointLightShadows };
26300 this.getParameters =
function ( material, lights, fog, object ) {
26302 var shaderID = shaderIDs[ material.type ];
26306 var maxLightCount = allocateLights( lights );
26307 var allocatedShadows = allocateShadows( lights );
26308 var maxBones = allocateBones(
object );
26309 var precision = renderer.getPrecision();
26311 if ( material.precision !== null ) {
26313 precision = capabilities.getMaxPrecision( material.precision );
26315 if ( precision !== material.precision ) {
26317 console.warn(
'THREE.WebGLRenderer.initMaterial:', material.precision,
'not supported, using', precision,
'instead.' );
26325 shaderID: shaderID,
26327 precision: precision,
26328 supportsVertexTextures: capabilities.vertexTextures,
26330 map: !! material.map,
26331 envMap: !! material.envMap,
26332 envMapMode: material.envMap && material.envMap.mapping,
26333 lightMap: !! material.lightMap,
26334 aoMap: !! material.aoMap,
26335 emissiveMap: !! material.emissiveMap,
26336 bumpMap: !! material.bumpMap,
26337 normalMap: !! material.normalMap,
26338 displacementMap: !! material.displacementMap,
26339 specularMap: !! material.specularMap,
26340 alphaMap: !! material.alphaMap,
26342 combine: material.combine,
26344 vertexColors: material.vertexColors,
26347 useFog: material.fog,
26348 fogExp: fog instanceof THREE.FogExp2,
26350 flatShading: material.shading === THREE.FlatShading,
26352 sizeAttenuation: material.sizeAttenuation,
26353 logarithmicDepthBuffer: capabilities.logarithmicDepthBuffer,
26355 skinning: material.skinning,
26356 maxBones: maxBones,
26357 useVertexTexture: capabilities.floatVertexTextures &&
object &&
object.skeleton &&
object.skeleton.useVertexTexture,
26359 morphTargets: material.morphTargets,
26360 morphNormals: material.morphNormals,
26361 maxMorphTargets: renderer.maxMorphTargets,
26362 maxMorphNormals: renderer.maxMorphNormals,
26364 maxDirLights: maxLightCount.directional,
26365 maxPointLights: maxLightCount.point,
26366 maxSpotLights: maxLightCount.spot,
26367 maxHemiLights: maxLightCount.hemi,
26369 maxShadows: allocatedShadows.maxShadows,
26370 pointLightShadows: allocatedShadows.pointLightShadows,
26371 shadowMapEnabled: renderer.shadowMap.enabled &&
object.receiveShadow && allocatedShadows.maxShadows > 0,
26372 shadowMapType: renderer.shadowMap.type,
26373 shadowMapDebug: renderer.shadowMap.debug,
26375 alphaTest: material.alphaTest,
26376 metal: material.metal,
26377 doubleSided: material.side === THREE.DoubleSide,
26378 flipSided: material.side === THREE.BackSide
26386 this.getProgramCode =
function ( material, parameters ) {
26390 if ( parameters.shaderID ) {
26392 chunks.push( parameters.shaderID );
26396 chunks.push( material.fragmentShader );
26397 chunks.push( material.vertexShader );
26401 if ( material.defines !== undefined ) {
26403 for ( var name in material.defines ) {
26405 chunks.push( name );
26406 chunks.push( material.defines[ name ] );
26412 for ( var i = 0; i < parameterNames.length; i ++ ) {
26414 var parameterName = parameterNames[ i ];
26415 chunks.push( parameterName );
26416 chunks.push( parameters[ parameterName ] );
26420 return chunks.join();
26424 this.acquireProgram =
function ( material, parameters, code ) {
26429 for ( var p = 0, pl = programs.length; p < pl; p ++ ) {
26431 var programInfo = programs[ p ];
26433 if ( programInfo.code === code ) {
26435 program = programInfo;
26436 ++ program.usedTimes;
26444 if ( program === undefined ) {
26446 program =
new THREE.WebGLProgram( renderer, code, material, parameters );
26447 programs.push( program );
26455 this.releaseProgram =
function( program ) {
26457 if ( -- program.usedTimes === 0 ) {
26460 var i = programs.indexOf( program );
26461 programs[ i ] = programs[ programs.length - 1 ];
26472 this.programs = programs;
26482 THREE.WebGLProperties =
function () {
26484 var properties = {};
26486 this.
get =
function ( object ) {
26488 var uuid =
object.uuid;
26489 var map = properties[ uuid ];
26491 if ( map === undefined ) {
26494 properties[ uuid ] = map;
26502 this.
delete =
function ( object ) {
26504 delete properties[
object.uuid ];
26508 this.clear =
function () {
26518 THREE.WebGLShader = (
function () {
26520 function addLineNumbers(
string ) {
26522 var lines =
string.split(
'\n' );
26524 for ( var i = 0; i < lines.length; i ++ ) {
26526 lines[ i ] = ( i + 1 ) +
': ' + lines[ i ];
26530 return lines.join(
'\n' );
26534 return function WebGLShader( gl, type,
string ) {
26536 var shader = gl.createShader( type );
26538 gl.shaderSource( shader,
string );
26539 gl.compileShader( shader );
26541 if ( gl.getShaderParameter( shader, gl.COMPILE_STATUS ) === false ) {
26543 console.error(
'THREE.WebGLShader: Shader couldn\'t compile.' );
26547 if ( gl.getShaderInfoLog( shader ) !==
'' ) {
26549 console.warn(
'THREE.WebGLShader: gl.getShaderInfoLog()', type === gl.VERTEX_SHADER ?
'vertex' :
'fragment', gl.getShaderInfoLog( shader ), addLineNumbers(
string ) );
26569 THREE.WebGLShadowMap =
function ( _renderer, _lights, _objects ) {
26571 var _gl = _renderer.context,
26572 _state = _renderer.state,
26573 _frustum =
new THREE.Frustum(),
26574 _projScreenMatrix =
new THREE.Matrix4(),
26576 _min =
new THREE.Vector3(),
26577 _max =
new THREE.Vector3(),
26579 _lookTarget =
new THREE.Vector3(),
26580 _lightPositionWorld =
new THREE.Vector3(),
26587 _NumberOfMaterialVariants = ( _MorphingFlag | _SkinningFlag ) + 1,
26589 _depthMaterials =
new Array( _NumberOfMaterialVariants ),
26590 _distanceMaterials =
new Array( _NumberOfMaterialVariants );
26592 var cubeDirections = [
26593 new THREE.Vector3( 1, 0, 0 ),
new THREE.Vector3( - 1, 0, 0 ),
new THREE.Vector3( 0, 0, 1 ),
26594 new THREE.Vector3( 0, 0, - 1 ),
new THREE.Vector3( 0, 1, 0 ),
new THREE.Vector3( 0, - 1, 0 )
26598 new THREE.Vector3( 0, 1, 0 ),
new THREE.Vector3( 0, 1, 0 ),
new THREE.Vector3( 0, 1, 0 ),
26599 new THREE.Vector3( 0, 1, 0 ),
new THREE.Vector3( 0, 0, 1 ),
new THREE.Vector3( 0, 0, - 1 )
26602 var cube2DViewPorts = [
26603 new THREE.Vector4(),
new THREE.Vector4(),
new THREE.Vector4(),
26604 new THREE.Vector4(),
new THREE.Vector4(),
new THREE.Vector4()
26607 var _vector4 =
new THREE.Vector4();
26611 var depthShader = THREE.ShaderLib[
"depthRGBA" ];
26612 var depthUniforms = THREE.UniformsUtils.clone( depthShader.uniforms );
26614 var distanceShader = THREE.ShaderLib[
"distanceRGBA" ];
26615 var distanceUniforms = THREE.UniformsUtils.clone( distanceShader.uniforms );
26617 for ( var i = 0; i !== _NumberOfMaterialVariants; ++ i ) {
26619 var useMorphing = ( i & _MorphingFlag ) !== 0;
26620 var useSkinning = ( i & _SkinningFlag ) !== 0;
26622 var depthMaterial =
new THREE.ShaderMaterial( {
26623 uniforms: depthUniforms,
26624 vertexShader: depthShader.vertexShader,
26625 fragmentShader: depthShader.fragmentShader,
26626 morphTargets: useMorphing,
26627 skinning: useSkinning
26630 depthMaterial._shadowPass =
true;
26632 _depthMaterials[ i ] = depthMaterial;
26634 var distanceMaterial =
new THREE.ShaderMaterial( {
26635 uniforms: distanceUniforms,
26636 vertexShader: distanceShader.vertexShader,
26637 fragmentShader: distanceShader.fragmentShader,
26638 morphTargets: useMorphing,
26639 skinning: useSkinning
26642 distanceMaterial._shadowPass =
true;
26644 _distanceMaterials[ i ] = distanceMaterial;
26652 this.enabled =
false;
26654 this.autoUpdate =
true;
26655 this.needsUpdate =
false;
26657 this.type = THREE.PCFShadowMap;
26658 this.cullFace = THREE.CullFaceFront;
26660 this.render =
function ( scene ) {
26662 var faceCount, isPointLight;
26664 if ( scope.enabled ===
false )
return;
26665 if ( scope.autoUpdate ===
false && scope.needsUpdate ===
false )
return;
26668 _gl.clearColor( 1, 1, 1, 1 );
26669 _state.disable( _gl.BLEND );
26670 _state.enable( _gl.CULL_FACE );
26671 _gl.frontFace( _gl.CCW );
26672 _gl.cullFace( scope.cullFace === THREE.CullFaceFront ? _gl.FRONT : _gl.BACK );
26673 _state.setDepthTest(
true );
26676 _renderer.getViewport( _vector4 );
26680 for ( var i = 0, il = _lights.length; i < il; i ++ ) {
26682 var light = _lights[ i ];
26684 if ( light.castShadow ===
true ) {
26686 var shadow = light.shadow;
26687 var shadowCamera = shadow.camera;
26688 var shadowMapSize = shadow.mapSize;
26690 if ( light instanceof THREE.PointLight ) {
26693 isPointLight =
true;
26695 var vpWidth = shadowMapSize.x / 4.0;
26696 var vpHeight = shadowMapSize.y / 2.0;
26712 cube2DViewPorts[ 0 ].set( vpWidth * 2, vpHeight, vpWidth, vpHeight );
26714 cube2DViewPorts[ 1 ].set( 0, vpHeight, vpWidth, vpHeight );
26716 cube2DViewPorts[ 2 ].set( vpWidth * 3, vpHeight, vpWidth, vpHeight );
26718 cube2DViewPorts[ 3 ].set( vpWidth, vpHeight, vpWidth, vpHeight );
26720 cube2DViewPorts[ 4 ].set( vpWidth * 3, 0, vpWidth, vpHeight );
26722 cube2DViewPorts[ 5 ].set( vpWidth, 0, vpWidth, vpHeight );
26727 isPointLight =
false;
26731 if ( shadow.map === null ) {
26733 var shadowFilter = THREE.LinearFilter;
26735 if ( scope.type === THREE.PCFSoftShadowMap ) {
26737 shadowFilter = THREE.NearestFilter;
26741 var pars = { minFilter: shadowFilter, magFilter: shadowFilter, format: THREE.RGBAFormat };
26743 shadow.map =
new THREE.WebGLRenderTarget( shadowMapSize.x, shadowMapSize.y, pars );
26744 shadow.matrix =
new THREE.Matrix4();
26748 if ( light instanceof THREE.SpotLight ) {
26750 shadowCamera.aspect = shadowMapSize.x / shadowMapSize.y;
26754 shadowCamera.updateProjectionMatrix();
26758 var shadowMap = shadow.map;
26759 var shadowMatrix = shadow.matrix;
26761 _lightPositionWorld.setFromMatrixPosition( light.matrixWorld );
26762 shadowCamera.position.copy( _lightPositionWorld );
26764 _renderer.setRenderTarget( shadowMap );
26770 for ( var face = 0; face < faceCount; face ++ ) {
26772 if ( isPointLight ) {
26774 _lookTarget.copy( shadowCamera.position );
26775 _lookTarget.add( cubeDirections[ face ] );
26776 shadowCamera.up.copy( cubeUps[ face ] );
26777 shadowCamera.lookAt( _lookTarget );
26778 var vpDimensions = cube2DViewPorts[ face ];
26779 _renderer.setViewport( vpDimensions.x, vpDimensions.y, vpDimensions.z, vpDimensions.w );
26783 _lookTarget.setFromMatrixPosition( light.target.matrixWorld );
26784 shadowCamera.lookAt( _lookTarget );
26788 shadowCamera.updateMatrixWorld();
26789 shadowCamera.matrixWorldInverse.getInverse( shadowCamera.matrixWorld );
26794 0.5, 0.0, 0.0, 0.5,
26795 0.0, 0.5, 0.0, 0.5,
26796 0.0, 0.0, 0.5, 0.5,
26800 shadowMatrix.multiply( shadowCamera.projectionMatrix );
26801 shadowMatrix.multiply( shadowCamera.matrixWorldInverse );
26805 _projScreenMatrix.multiplyMatrices( shadowCamera.projectionMatrix, shadowCamera.matrixWorldInverse );
26806 _frustum.setFromMatrix( _projScreenMatrix );
26810 _renderList.length = 0;
26812 projectObject( scene, shadowCamera );
26817 for ( var j = 0, jl = _renderList.length; j < jl; j ++ ) {
26819 var
object = _renderList[ j ];
26820 var geometry = _objects.update(
object );
26821 var material =
object.material;
26823 if ( material instanceof THREE.MeshFaceMaterial ) {
26825 var groups = geometry.groups;
26826 var materials = material.materials;
26828 for ( var k = 0, kl = groups.length; k < kl; k ++ ) {
26830 var group = groups[ k ];
26831 var groupMaterial = materials[ group.materialIndex ];
26833 if ( groupMaterial.visible ===
true ) {
26835 var depthMaterial = getDepthMaterial(
object, groupMaterial, isPointLight, _lightPositionWorld );
26836 _renderer.renderBufferDirect( shadowCamera, _lights, null, geometry, depthMaterial,
object, group );
26844 var depthMaterial = getDepthMaterial(
object, material, isPointLight, _lightPositionWorld );
26845 _renderer.renderBufferDirect( shadowCamera, _lights, null, geometry, depthMaterial,
object, null );
26855 _renderer.resetGLState();
26861 _renderer.setViewport( _vector4.x, _vector4.y, _vector4.z, _vector4.w );
26864 var clearColor = _renderer.getClearColor(),
26865 clearAlpha = _renderer.getClearAlpha();
26866 _renderer.setClearColor( clearColor, clearAlpha );
26867 _state.enable( _gl.BLEND );
26869 if ( scope.cullFace === THREE.CullFaceFront ) {
26871 _gl.cullFace( _gl.BACK );
26875 _renderer.resetGLState();
26877 scope.needsUpdate =
false;
26881 function getDepthMaterial(
object, material, isPointLight, lightPositionWorld ) {
26883 var geometry =
object.geometry;
26885 var newMaterial = null;
26887 var materialVariants = _depthMaterials;
26888 var customMaterial =
object.customDepthMaterial;
26890 if ( isPointLight ) {
26892 materialVariants = _distanceMaterials;
26893 customMaterial =
object.customDistanceMaterial;
26897 if ( ! customMaterial ) {
26899 var useMorphing = geometry.morphTargets !== undefined &&
26900 geometry.morphTargets.length > 0 && material.morphTargets;
26902 var useSkinning =
object instanceof THREE.SkinnedMesh && material.skinning;
26904 var variantIndex = 0;
26906 if ( useMorphing ) variantIndex |= _MorphingFlag;
26907 if ( useSkinning ) variantIndex |= _SkinningFlag;
26909 newMaterial = materialVariants[ variantIndex ];
26913 newMaterial = customMaterial;
26917 newMaterial.visible = material.visible;
26918 newMaterial.wireframe = material.wireframe;
26919 newMaterial.wireframeLinewidth = material.wireframeLinewidth;
26921 if ( isPointLight && newMaterial.uniforms.lightPos !== undefined ) {
26923 newMaterial.uniforms.lightPos.value.copy( lightPositionWorld );
26927 return newMaterial;
26931 function projectObject(
object, camera ) {
26933 if (
object.visible ===
false )
return;
26935 if (
object instanceof THREE.Mesh ||
object instanceof THREE.Line ||
object instanceof THREE.Points ) {
26937 if (
object.castShadow && (
object.frustumCulled ===
false || _frustum.intersectsObject(
object ) === true ) ) {
26939 var material =
object.material;
26941 if ( material.visible ===
true ) {
26943 object.modelViewMatrix.multiplyMatrices( camera.matrixWorldInverse,
object.matrixWorld );
26944 _renderList.push(
object );
26952 var children =
object.children;
26954 for ( var i = 0, l = children.length; i < l; i ++ ) {
26956 projectObject( children[ i ], camera );
26970 THREE.WebGLState =
function ( gl, extensions, paramThreeToGL ) {
26974 var newAttributes =
new Uint8Array( 16 );
26975 var enabledAttributes =
new Uint8Array( 16 );
26976 var attributeDivisors =
new Uint8Array( 16 );
26978 var capabilities = {};
26980 var compressedTextureFormats = null;
26982 var currentBlending = null;
26983 var currentBlendEquation = null;
26984 var currentBlendSrc = null;
26985 var currentBlendDst = null;
26986 var currentBlendEquationAlpha = null;
26987 var currentBlendSrcAlpha = null;
26988 var currentBlendDstAlpha = null;
26990 var currentDepthFunc = null;
26991 var currentDepthWrite = null;
26993 var currentColorWrite = null;
26995 var currentFlipSided = null;
26997 var currentLineWidth = null;
26999 var currentPolygonOffsetFactor = null;
27000 var currentPolygonOffsetUnits = null;
27002 var maxTextures = gl.getParameter( gl.MAX_TEXTURE_IMAGE_UNITS );
27004 var currentTextureSlot = undefined;
27005 var currentBoundTextures = {};
27007 this.init =
function () {
27009 gl.clearColor( 0, 0, 0, 1 );
27010 gl.clearDepth( 1 );
27011 gl.clearStencil( 0 );
27013 this.enable( gl.DEPTH_TEST );
27014 gl.depthFunc( gl.LEQUAL );
27016 gl.frontFace( gl.CCW );
27017 gl.cullFace( gl.BACK );
27018 this.enable( gl.CULL_FACE );
27020 this.enable( gl.BLEND );
27021 gl.blendEquation( gl.FUNC_ADD );
27022 gl.blendFunc( gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA );
27026 this.initAttributes =
function () {
27028 for ( var i = 0, l = newAttributes.length; i < l; i ++ ) {
27030 newAttributes[ i ] = 0;
27036 this.enableAttribute =
function ( attribute ) {
27038 newAttributes[ attribute ] = 1;
27040 if ( enabledAttributes[ attribute ] === 0 ) {
27042 gl.enableVertexAttribArray( attribute );
27043 enabledAttributes[ attribute ] = 1;
27047 if ( attributeDivisors[ attribute ] !== 0 ) {
27049 var extension = extensions.get(
'ANGLE_instanced_arrays' );
27051 extension.vertexAttribDivisorANGLE( attribute, 0 );
27052 attributeDivisors[ attribute ] = 0;
27058 this.enableAttributeAndDivisor =
function ( attribute, meshPerAttribute, extension ) {
27060 newAttributes[ attribute ] = 1;
27062 if ( enabledAttributes[ attribute ] === 0 ) {
27064 gl.enableVertexAttribArray( attribute );
27065 enabledAttributes[ attribute ] = 1;
27069 if ( attributeDivisors[ attribute ] !== meshPerAttribute ) {
27071 extension.vertexAttribDivisorANGLE( attribute, meshPerAttribute );
27072 attributeDivisors[ attribute ] = meshPerAttribute;
27078 this.disableUnusedAttributes =
function () {
27080 for ( var i = 0, l = enabledAttributes.length; i < l; i ++ ) {
27082 if ( enabledAttributes[ i ] !== newAttributes[ i ] ) {
27084 gl.disableVertexAttribArray( i );
27085 enabledAttributes[ i ] = 0;
27093 this.enable =
function ( id ) {
27095 if ( capabilities[
id ] !==
true ) {
27098 capabilities[ id ] =
true;
27104 this.disable =
function ( id ) {
27106 if ( capabilities[
id ] !==
false ) {
27109 capabilities[ id ] =
false;
27115 this.getCompressedTextureFormats =
function () {
27117 if ( compressedTextureFormats === null ) {
27119 compressedTextureFormats = [];
27121 if ( extensions.get(
'WEBGL_compressed_texture_pvrtc' ) ||
27122 extensions.get(
'WEBGL_compressed_texture_s3tc' ) ) {
27124 var formats = gl.getParameter( gl.COMPRESSED_TEXTURE_FORMATS );
27126 for ( var i = 0; i < formats.length; i ++ ) {
27128 compressedTextureFormats.push( formats[ i ] );
27136 return compressedTextureFormats;
27140 this.setBlending =
function ( blending, blendEquation, blendSrc, blendDst, blendEquationAlpha, blendSrcAlpha, blendDstAlpha ) {
27142 if ( blending !== currentBlending ) {
27144 if ( blending === THREE.NoBlending ) {
27146 this.disable( gl.BLEND );
27148 }
else if ( blending === THREE.AdditiveBlending ) {
27150 this.enable( gl.BLEND );
27151 gl.blendEquation( gl.FUNC_ADD );
27152 gl.blendFunc( gl.SRC_ALPHA, gl.ONE );
27154 }
else if ( blending === THREE.SubtractiveBlending ) {
27158 this.enable( gl.BLEND );
27159 gl.blendEquation( gl.FUNC_ADD );
27160 gl.blendFunc( gl.ZERO, gl.ONE_MINUS_SRC_COLOR );
27162 }
else if ( blending === THREE.MultiplyBlending ) {
27166 this.enable( gl.BLEND );
27167 gl.blendEquation( gl.FUNC_ADD );
27168 gl.blendFunc( gl.ZERO, gl.SRC_COLOR );
27170 }
else if ( blending === THREE.CustomBlending ) {
27172 this.enable( gl.BLEND );
27176 this.enable( gl.BLEND );
27177 gl.blendEquationSeparate( gl.FUNC_ADD, gl.FUNC_ADD );
27178 gl.blendFuncSeparate( gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA, gl.ONE, gl.ONE_MINUS_SRC_ALPHA );
27182 currentBlending = blending;
27186 if ( blending === THREE.CustomBlending ) {
27188 blendEquationAlpha = blendEquationAlpha || blendEquation;
27189 blendSrcAlpha = blendSrcAlpha || blendSrc;
27190 blendDstAlpha = blendDstAlpha || blendDst;
27192 if ( blendEquation !== currentBlendEquation || blendEquationAlpha !== currentBlendEquationAlpha ) {
27194 gl.blendEquationSeparate( paramThreeToGL( blendEquation ), paramThreeToGL( blendEquationAlpha ) );
27196 currentBlendEquation = blendEquation;
27197 currentBlendEquationAlpha = blendEquationAlpha;
27201 if ( blendSrc !== currentBlendSrc || blendDst !== currentBlendDst || blendSrcAlpha !== currentBlendSrcAlpha || blendDstAlpha !== currentBlendDstAlpha ) {
27203 gl.blendFuncSeparate( paramThreeToGL( blendSrc ), paramThreeToGL( blendDst ), paramThreeToGL( blendSrcAlpha ), paramThreeToGL( blendDstAlpha ) );
27205 currentBlendSrc = blendSrc;
27206 currentBlendDst = blendDst;
27207 currentBlendSrcAlpha = blendSrcAlpha;
27208 currentBlendDstAlpha = blendDstAlpha;
27214 currentBlendEquation = null;
27215 currentBlendSrc = null;
27216 currentBlendDst = null;
27217 currentBlendEquationAlpha = null;
27218 currentBlendSrcAlpha = null;
27219 currentBlendDstAlpha = null;
27225 this.setDepthFunc =
function ( depthFunc ) {
27227 if ( currentDepthFunc !== depthFunc ) {
27231 switch ( depthFunc ) {
27233 case THREE.NeverDepth:
27235 gl.depthFunc( gl.NEVER );
27238 case THREE.AlwaysDepth:
27240 gl.depthFunc( gl.ALWAYS );
27243 case THREE.LessDepth:
27245 gl.depthFunc( gl.LESS );
27248 case THREE.LessEqualDepth:
27250 gl.depthFunc( gl.LEQUAL );
27253 case THREE.EqualDepth:
27255 gl.depthFunc( gl.EQUAL );
27258 case THREE.GreaterEqualDepth:
27260 gl.depthFunc( gl.GEQUAL );
27263 case THREE.GreaterDepth:
27265 gl.depthFunc( gl.GREATER );
27268 case THREE.NotEqualDepth:
27270 gl.depthFunc( gl.NOTEQUAL );
27275 gl.depthFunc( gl.LEQUAL );
27281 gl.depthFunc( gl.LEQUAL );
27285 currentDepthFunc = depthFunc;
27291 this.setDepthTest =
function ( depthTest ) {
27295 this.enable( gl.DEPTH_TEST );
27299 this.disable( gl.DEPTH_TEST );
27305 this.setDepthWrite =
function ( depthWrite ) {
27307 if ( currentDepthWrite !== depthWrite ) {
27309 gl.depthMask( depthWrite );
27310 currentDepthWrite = depthWrite;
27316 this.setColorWrite =
function ( colorWrite ) {
27318 if ( currentColorWrite !== colorWrite ) {
27320 gl.colorMask( colorWrite, colorWrite, colorWrite, colorWrite );
27321 currentColorWrite = colorWrite;
27327 this.setFlipSided =
function ( flipSided ) {
27329 if ( currentFlipSided !== flipSided ) {
27333 gl.frontFace( gl.CW );
27337 gl.frontFace( gl.CCW );
27341 currentFlipSided = flipSided;
27347 this.setLineWidth =
function ( width ) {
27349 if ( width !== currentLineWidth ) {
27351 gl.lineWidth( width );
27353 currentLineWidth = width;
27359 this.setPolygonOffset =
function ( polygonOffset, factor, units ) {
27361 if ( polygonOffset ) {
27363 this.enable( gl.POLYGON_OFFSET_FILL );
27367 this.disable( gl.POLYGON_OFFSET_FILL );
27371 if ( polygonOffset && ( currentPolygonOffsetFactor !== factor || currentPolygonOffsetUnits !== units ) ) {
27373 gl.polygonOffset( factor, units );
27375 currentPolygonOffsetFactor = factor;
27376 currentPolygonOffsetUnits = units;
27382 this.setScissorTest =
function ( scissorTest ) {
27384 if ( scissorTest ) {
27386 this.enable( gl.SCISSOR_TEST );
27390 this.disable( gl.SCISSOR_TEST );
27398 this.activeTexture =
function ( webglSlot ) {
27400 if ( webglSlot === undefined ) webglSlot = gl.TEXTURE0 + maxTextures - 1;
27402 if ( currentTextureSlot !== webglSlot ) {
27404 gl.activeTexture( webglSlot );
27405 currentTextureSlot = webglSlot;
27411 this.bindTexture =
function ( webglType, webglTexture ) {
27413 if ( currentTextureSlot === undefined ) {
27415 _this.activeTexture();
27419 var boundTexture = currentBoundTextures[ currentTextureSlot ];
27421 if ( boundTexture === undefined ) {
27423 boundTexture = { type: undefined, texture: undefined };
27424 currentBoundTextures[ currentTextureSlot ] = boundTexture;
27428 if ( boundTexture.type !== webglType || boundTexture.texture !== webglTexture ) {
27430 gl.bindTexture( webglType, webglTexture );
27432 boundTexture.type = webglType;
27433 boundTexture.texture = webglTexture;
27439 this.compressedTexImage2D =
function () {
27443 gl.compressedTexImage2D.apply( gl, arguments );
27445 }
catch ( error ) {
27447 console.error( error );
27453 this.texImage2D =
function () {
27457 gl.texImage2D.apply( gl, arguments );
27459 }
catch ( error ) {
27461 console.error( error );
27469 this.reset =
function () {
27471 for ( var i = 0; i < enabledAttributes.length; i ++ ) {
27473 if ( enabledAttributes[ i ] === 1 ) {
27475 gl.disableVertexAttribArray( i );
27476 enabledAttributes[ i ] = 0;
27484 compressedTextureFormats = null;
27486 currentBlending = null;
27488 currentDepthWrite = null;
27489 currentColorWrite = null;
27491 currentFlipSided = null;
27504 THREE.LensFlarePlugin =
function ( renderer, flares ) {
27506 var gl = renderer.context;
27507 var state = renderer.state;
27509 var vertexBuffer, elementBuffer;
27510 var program, attributes, uniforms;
27511 var hasVertexTexture;
27513 var tempTexture, occlusionTexture;
27517 var vertices =
new Float32Array( [
27524 var faces =
new Uint16Array( [
27531 vertexBuffer = gl.createBuffer();
27532 elementBuffer = gl.createBuffer();
27534 gl.bindBuffer( gl.ARRAY_BUFFER, vertexBuffer );
27535 gl.bufferData( gl.ARRAY_BUFFER, vertices, gl.STATIC_DRAW );
27537 gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, elementBuffer );
27538 gl.bufferData( gl.ELEMENT_ARRAY_BUFFER, faces, gl.STATIC_DRAW );
27542 tempTexture = gl.createTexture();
27543 occlusionTexture = gl.createTexture();
27545 state.bindTexture( gl.TEXTURE_2D, tempTexture );
27546 gl.texImage2D( gl.TEXTURE_2D, 0, gl.RGB, 16, 16, 0, gl.RGB, gl.UNSIGNED_BYTE, null );
27547 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE );
27548 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE );
27549 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST );
27550 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST );
27552 state.bindTexture( gl.TEXTURE_2D, occlusionTexture );
27553 gl.texImage2D( gl.TEXTURE_2D, 0, gl.RGBA, 16, 16, 0, gl.RGBA, gl.UNSIGNED_BYTE, null );
27554 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE );
27555 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE );
27556 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST );
27557 gl.texParameteri( gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST );
27559 hasVertexTexture = gl.getParameter( gl.MAX_VERTEX_TEXTURE_IMAGE_UNITS ) > 0;
27563 if ( hasVertexTexture ) {
27569 "uniform lowp int renderType;",
27571 "uniform vec3 screenPosition;",
27572 "uniform vec2 scale;",
27573 "uniform float rotation;",
27575 "uniform sampler2D occlusionMap;",
27577 "attribute vec2 position;",
27578 "attribute vec2 uv;",
27580 "varying vec2 vUV;",
27581 "varying float vVisibility;",
27587 "vec2 pos = position;",
27589 "if ( renderType == 2 ) {",
27591 "vec4 visibility = texture2D( occlusionMap, vec2( 0.1, 0.1 ) );",
27592 "visibility += texture2D( occlusionMap, vec2( 0.5, 0.1 ) );",
27593 "visibility += texture2D( occlusionMap, vec2( 0.9, 0.1 ) );",
27594 "visibility += texture2D( occlusionMap, vec2( 0.9, 0.5 ) );",
27595 "visibility += texture2D( occlusionMap, vec2( 0.9, 0.9 ) );",
27596 "visibility += texture2D( occlusionMap, vec2( 0.5, 0.9 ) );",
27597 "visibility += texture2D( occlusionMap, vec2( 0.1, 0.9 ) );",
27598 "visibility += texture2D( occlusionMap, vec2( 0.1, 0.5 ) );",
27599 "visibility += texture2D( occlusionMap, vec2( 0.5, 0.5 ) );",
27601 "vVisibility = visibility.r / 9.0;",
27602 "vVisibility *= 1.0 - visibility.g / 9.0;",
27603 "vVisibility *= visibility.b / 9.0;",
27604 "vVisibility *= 1.0 - visibility.a / 9.0;",
27606 "pos.x = cos( rotation ) * position.x - sin( rotation ) * position.y;",
27607 "pos.y = sin( rotation ) * position.x + cos( rotation ) * position.y;",
27611 "gl_Position = vec4( ( pos * scale + screenPosition.xy ).xy, screenPosition.z, 1.0 );",
27619 "uniform lowp int renderType;",
27621 "uniform sampler2D map;",
27622 "uniform float opacity;",
27623 "uniform vec3 color;",
27625 "varying vec2 vUV;",
27626 "varying float vVisibility;",
27632 "if ( renderType == 0 ) {",
27634 "gl_FragColor = vec4( 1.0, 0.0, 1.0, 0.0 );",
27638 "} else if ( renderType == 1 ) {",
27640 "gl_FragColor = texture2D( map, vUV );",
27646 "vec4 texture = texture2D( map, vUV );",
27647 "texture.a *= opacity * vVisibility;",
27648 "gl_FragColor = texture;",
27649 "gl_FragColor.rgb *= color;",
27665 "uniform lowp int renderType;",
27667 "uniform vec3 screenPosition;",
27668 "uniform vec2 scale;",
27669 "uniform float rotation;",
27671 "attribute vec2 position;",
27672 "attribute vec2 uv;",
27674 "varying vec2 vUV;",
27680 "vec2 pos = position;",
27682 "if ( renderType == 2 ) {",
27684 "pos.x = cos( rotation ) * position.x - sin( rotation ) * position.y;",
27685 "pos.y = sin( rotation ) * position.x + cos( rotation ) * position.y;",
27689 "gl_Position = vec4( ( pos * scale + screenPosition.xy ).xy, screenPosition.z, 1.0 );",
27697 "precision mediump float;",
27699 "uniform lowp int renderType;",
27701 "uniform sampler2D map;",
27702 "uniform sampler2D occlusionMap;",
27703 "uniform float opacity;",
27704 "uniform vec3 color;",
27706 "varying vec2 vUV;",
27712 "if ( renderType == 0 ) {",
27714 "gl_FragColor = vec4( texture2D( map, vUV ).rgb, 0.0 );",
27718 "} else if ( renderType == 1 ) {",
27720 "gl_FragColor = texture2D( map, vUV );",
27726 "float visibility = texture2D( occlusionMap, vec2( 0.5, 0.1 ) ).a;",
27727 "visibility += texture2D( occlusionMap, vec2( 0.9, 0.5 ) ).a;",
27728 "visibility += texture2D( occlusionMap, vec2( 0.5, 0.9 ) ).a;",
27729 "visibility += texture2D( occlusionMap, vec2( 0.1, 0.5 ) ).a;",
27730 "visibility = ( 1.0 - visibility / 4.0 );",
27732 "vec4 texture = texture2D( map, vUV );",
27733 "texture.a *= opacity * visibility;",
27734 "gl_FragColor = texture;",
27735 "gl_FragColor.rgb *= color;",
27747 program = createProgram( shader );
27750 vertex: gl.getAttribLocation ( program,
"position" ),
27751 uv: gl.getAttribLocation ( program,
"uv" )
27755 renderType: gl.getUniformLocation( program,
"renderType" ),
27756 map: gl.getUniformLocation( program,
"map" ),
27757 occlusionMap: gl.getUniformLocation( program,
"occlusionMap" ),
27758 opacity: gl.getUniformLocation( program,
"opacity" ),
27759 color: gl.getUniformLocation( program,
"color" ),
27760 scale: gl.getUniformLocation( program,
"scale" ),
27761 rotation: gl.getUniformLocation( program,
"rotation" ),
27762 screenPosition: gl.getUniformLocation( program,
"screenPosition" )
27773 this.render =
function ( scene, camera, viewportWidth, viewportHeight ) {
27775 if ( flares.length === 0 )
return;
27777 var tempPosition =
new THREE.Vector3();
27779 var invAspect = viewportHeight / viewportWidth,
27780 halfViewportWidth = viewportWidth * 0.5,
27781 halfViewportHeight = viewportHeight * 0.5;
27783 var size = 16 / viewportHeight,
27784 scale =
new THREE.Vector2( size * invAspect, size );
27786 var screenPosition =
new THREE.Vector3( 1, 1, 0 ),
27787 screenPositionPixels =
new THREE.Vector2( 1, 1 );
27789 if ( program === undefined ) {
27795 gl.useProgram( program );
27797 state.initAttributes();
27798 state.enableAttribute( attributes.vertex );
27799 state.enableAttribute( attributes.uv );
27800 state.disableUnusedAttributes();
27805 gl.uniform1i( uniforms.occlusionMap, 0 );
27806 gl.uniform1i( uniforms.map, 1 );
27808 gl.bindBuffer( gl.ARRAY_BUFFER, vertexBuffer );
27809 gl.vertexAttribPointer( attributes.vertex, 2, gl.FLOAT,
false, 2 * 8, 0 );
27810 gl.vertexAttribPointer( attributes.uv, 2, gl.FLOAT,
false, 2 * 8, 8 );
27812 gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, elementBuffer );
27814 state.disable( gl.CULL_FACE );
27815 gl.depthMask(
false );
27817 for ( var i = 0, l = flares.length; i < l; i ++ ) {
27819 size = 16 / viewportHeight;
27820 scale.set( size * invAspect, size );
27824 var flare = flares[ i ];
27826 tempPosition.set( flare.matrixWorld.elements[ 12 ], flare.matrixWorld.elements[ 13 ], flare.matrixWorld.elements[ 14 ] );
27828 tempPosition.applyMatrix4( camera.matrixWorldInverse );
27829 tempPosition.applyProjection( camera.projectionMatrix );
27833 screenPosition.copy( tempPosition );
27835 screenPositionPixels.x = screenPosition.x * halfViewportWidth + halfViewportWidth;
27836 screenPositionPixels.y = screenPosition.y * halfViewportHeight + halfViewportHeight;
27840 if ( hasVertexTexture || (
27841 screenPositionPixels.x > 0 &&
27842 screenPositionPixels.x < viewportWidth &&
27843 screenPositionPixels.y > 0 &&
27844 screenPositionPixels.y < viewportHeight ) ) {
27848 state.activeTexture( gl.TEXTURE0 );
27849 state.bindTexture( gl.TEXTURE_2D, null );
27850 state.activeTexture( gl.TEXTURE1 );
27851 state.bindTexture( gl.TEXTURE_2D, tempTexture );
27852 gl.copyTexImage2D( gl.TEXTURE_2D, 0, gl.RGB, screenPositionPixels.x - 8, screenPositionPixels.y - 8, 16, 16, 0 );
27857 gl.uniform1i( uniforms.renderType, 0 );
27858 gl.uniform2f( uniforms.scale, scale.x, scale.y );
27859 gl.uniform3f( uniforms.screenPosition, screenPosition.x, screenPosition.y, screenPosition.z );
27861 state.disable( gl.BLEND );
27862 state.enable( gl.DEPTH_TEST );
27864 gl.drawElements( gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0 );
27869 state.activeTexture( gl.TEXTURE0 );
27870 state.bindTexture( gl.TEXTURE_2D, occlusionTexture );
27871 gl.copyTexImage2D( gl.TEXTURE_2D, 0, gl.RGBA, screenPositionPixels.x - 8, screenPositionPixels.y - 8, 16, 16, 0 );
27876 gl.uniform1i( uniforms.renderType, 1 );
27877 state.disable( gl.DEPTH_TEST );
27879 state.activeTexture( gl.TEXTURE1 );
27880 state.bindTexture( gl.TEXTURE_2D, tempTexture );
27881 gl.drawElements( gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0 );
27886 flare.positionScreen.copy( screenPosition );
27888 if ( flare.customUpdateCallback ) {
27890 flare.customUpdateCallback( flare );
27894 flare.updateLensFlares();
27900 gl.uniform1i( uniforms.renderType, 2 );
27901 state.enable( gl.BLEND );
27903 for ( var j = 0, jl = flare.lensFlares.length; j < jl; j ++ ) {
27905 var sprite = flare.lensFlares[ j ];
27907 if ( sprite.opacity > 0.001 && sprite.scale > 0.001 ) {
27909 screenPosition.x = sprite.x;
27910 screenPosition.y = sprite.y;
27911 screenPosition.z = sprite.z;
27913 size = sprite.size * sprite.scale / viewportHeight;
27915 scale.x = size * invAspect;
27918 gl.uniform3f( uniforms.screenPosition, screenPosition.x, screenPosition.y, screenPosition.z );
27919 gl.uniform2f( uniforms.scale, scale.x, scale.y );
27920 gl.uniform1f( uniforms.rotation, sprite.rotation );
27922 gl.uniform1f( uniforms.opacity, sprite.opacity );
27923 gl.uniform3f( uniforms.color, sprite.color.r, sprite.color.g, sprite.color.b );
27925 state.setBlending( sprite.blending, sprite.blendEquation, sprite.blendSrc, sprite.blendDst );
27926 renderer.setTexture( sprite.texture, 1 );
27928 gl.drawElements( gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0 );
27940 state.enable( gl.CULL_FACE );
27941 state.enable( gl.DEPTH_TEST );
27942 gl.depthMask(
true );
27944 renderer.resetGLState();
27948 function createProgram ( shader ) {
27950 var program = gl.createProgram();
27952 var fragmentShader = gl.createShader( gl.FRAGMENT_SHADER );
27953 var vertexShader = gl.createShader( gl.VERTEX_SHADER );
27955 var prefix =
"precision " + renderer.getPrecision() +
" float;\n";
27957 gl.shaderSource( fragmentShader, prefix + shader.fragmentShader );
27958 gl.shaderSource( vertexShader, prefix + shader.vertexShader );
27960 gl.compileShader( fragmentShader );
27961 gl.compileShader( vertexShader );
27963 gl.attachShader( program, fragmentShader );
27964 gl.attachShader( program, vertexShader );
27966 gl.linkProgram( program );
27981 THREE.SpritePlugin =
function ( renderer, sprites ) {
27983 var gl = renderer.context;
27984 var state = renderer.state;
27986 var vertexBuffer, elementBuffer;
27987 var program, attributes, uniforms;
27993 var spritePosition =
new THREE.Vector3();
27994 var spriteRotation =
new THREE.Quaternion();
27995 var spriteScale =
new THREE.Vector3();
27999 var vertices =
new Float32Array( [
28000 - 0.5, - 0.5, 0, 0,
28006 var faces =
new Uint16Array( [
28011 vertexBuffer = gl.createBuffer();
28012 elementBuffer = gl.createBuffer();
28014 gl.bindBuffer( gl.ARRAY_BUFFER, vertexBuffer );
28015 gl.bufferData( gl.ARRAY_BUFFER, vertices, gl.STATIC_DRAW );
28017 gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, elementBuffer );
28018 gl.bufferData( gl.ELEMENT_ARRAY_BUFFER, faces, gl.STATIC_DRAW );
28020 program = createProgram();
28023 position: gl.getAttribLocation ( program,
'position' ),
28024 uv: gl.getAttribLocation ( program,
'uv' )
28028 uvOffset: gl.getUniformLocation( program,
'uvOffset' ),
28029 uvScale: gl.getUniformLocation( program,
'uvScale' ),
28031 rotation: gl.getUniformLocation( program,
'rotation' ),
28032 scale: gl.getUniformLocation( program,
'scale' ),
28034 color: gl.getUniformLocation( program,
'color' ),
28035 map: gl.getUniformLocation( program,
'map' ),
28036 opacity: gl.getUniformLocation( program,
'opacity' ),
28038 modelViewMatrix: gl.getUniformLocation( program,
'modelViewMatrix' ),
28039 projectionMatrix: gl.getUniformLocation( program,
'projectionMatrix' ),
28041 fogType: gl.getUniformLocation( program,
'fogType' ),
28042 fogDensity: gl.getUniformLocation( program,
'fogDensity' ),
28043 fogNear: gl.getUniformLocation( program,
'fogNear' ),
28044 fogFar: gl.getUniformLocation( program,
'fogFar' ),
28045 fogColor: gl.getUniformLocation( program,
'fogColor' ),
28047 alphaTest: gl.getUniformLocation( program,
'alphaTest' )
28050 var canvas = document.createElement(
'canvas' );
28054 var context = canvas.getContext(
'2d' );
28055 context.fillStyle =
'white';
28056 context.fillRect( 0, 0, 8, 8 );
28058 texture =
new THREE.Texture( canvas );
28059 texture.needsUpdate =
true;
28063 this.render =
function ( scene, camera ) {
28065 if ( sprites.length === 0 )
return;
28069 if ( program === undefined ) {
28075 gl.useProgram( program );
28077 state.initAttributes();
28078 state.enableAttribute( attributes.position );
28079 state.enableAttribute( attributes.uv );
28080 state.disableUnusedAttributes();
28082 state.disable( gl.CULL_FACE );
28083 state.enable( gl.BLEND );
28085 gl.bindBuffer( gl.ARRAY_BUFFER, vertexBuffer );
28086 gl.vertexAttribPointer( attributes.position, 2, gl.FLOAT,
false, 2 * 8, 0 );
28087 gl.vertexAttribPointer( attributes.uv, 2, gl.FLOAT,
false, 2 * 8, 8 );
28089 gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, elementBuffer );
28091 gl.uniformMatrix4fv( uniforms.projectionMatrix,
false, camera.projectionMatrix.elements );
28093 state.activeTexture( gl.TEXTURE0 );
28094 gl.uniform1i( uniforms.map, 0 );
28096 var oldFogType = 0;
28097 var sceneFogType = 0;
28098 var fog = scene.fog;
28102 gl.uniform3f( uniforms.fogColor, fog.color.r, fog.color.g, fog.color.b );
28104 if ( fog instanceof THREE.Fog ) {
28106 gl.uniform1f( uniforms.fogNear, fog.near );
28107 gl.uniform1f( uniforms.fogFar, fog.far );
28109 gl.uniform1i( uniforms.fogType, 1 );
28113 }
else if ( fog instanceof THREE.FogExp2 ) {
28115 gl.uniform1f( uniforms.fogDensity, fog.density );
28117 gl.uniform1i( uniforms.fogType, 2 );
28125 gl.uniform1i( uniforms.fogType, 0 );
28134 for ( var i = 0, l = sprites.length; i < l; i ++ ) {
28136 var sprite = sprites[ i ];
28138 sprite.modelViewMatrix.multiplyMatrices( camera.matrixWorldInverse, sprite.matrixWorld );
28139 sprite.z = - sprite.modelViewMatrix.elements[ 14 ];
28143 sprites.sort( painterSortStable );
28149 for ( var i = 0, l = sprites.length; i < l; i ++ ) {
28151 var sprite = sprites[ i ];
28152 var material = sprite.material;
28154 gl.uniform1f( uniforms.alphaTest, material.alphaTest );
28155 gl.uniformMatrix4fv( uniforms.modelViewMatrix,
false, sprite.modelViewMatrix.elements );
28157 sprite.matrixWorld.decompose( spritePosition, spriteRotation, spriteScale );
28159 scale[ 0 ] = spriteScale.x;
28160 scale[ 1 ] = spriteScale.y;
28164 if ( scene.fog && material.fog ) {
28166 fogType = sceneFogType;
28170 if ( oldFogType !== fogType ) {
28172 gl.uniform1i( uniforms.fogType, fogType );
28173 oldFogType = fogType;
28177 if ( material.map !== null ) {
28179 gl.uniform2f( uniforms.uvOffset, material.map.offset.x, material.map.offset.y );
28180 gl.uniform2f( uniforms.uvScale, material.map.repeat.x, material.map.repeat.y );
28184 gl.uniform2f( uniforms.uvOffset, 0, 0 );
28185 gl.uniform2f( uniforms.uvScale, 1, 1 );
28189 gl.uniform1f( uniforms.opacity, material.opacity );
28190 gl.uniform3f( uniforms.color, material.color.r, material.color.g, material.color.b );
28192 gl.uniform1f( uniforms.rotation, material.rotation );
28193 gl.uniform2fv( uniforms.scale, scale );
28195 state.setBlending( material.blending, material.blendEquation, material.blendSrc, material.blendDst );
28196 state.setDepthTest( material.depthTest );
28197 state.setDepthWrite( material.depthWrite );
28199 if ( material.map && material.map.image && material.map.image.width ) {
28201 renderer.setTexture( material.map, 0 );
28205 renderer.setTexture( texture, 0 );
28209 gl.drawElements( gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0 );
28215 state.enable( gl.CULL_FACE );
28217 renderer.resetGLState();
28221 function createProgram () {
28223 var program = gl.createProgram();
28225 var vertexShader = gl.createShader( gl.VERTEX_SHADER );
28226 var fragmentShader = gl.createShader( gl.FRAGMENT_SHADER );
28228 gl.shaderSource( vertexShader, [
28230 'precision ' + renderer.getPrecision() +
' float;',
28232 'uniform mat4 modelViewMatrix;',
28233 'uniform mat4 projectionMatrix;',
28234 'uniform float rotation;',
28235 'uniform vec2 scale;',
28236 'uniform vec2 uvOffset;',
28237 'uniform vec2 uvScale;',
28239 'attribute vec2 position;',
28240 'attribute vec2 uv;',
28242 'varying vec2 vUV;',
28246 'vUV = uvOffset + uv * uvScale;',
28248 'vec2 alignedPosition = position * scale;',
28250 'vec2 rotatedPosition;',
28251 'rotatedPosition.x = cos( rotation ) * alignedPosition.x - sin( rotation ) * alignedPosition.y;',
28252 'rotatedPosition.y = sin( rotation ) * alignedPosition.x + cos( rotation ) * alignedPosition.y;',
28254 'vec4 finalPosition;',
28256 'finalPosition = modelViewMatrix * vec4( 0.0, 0.0, 0.0, 1.0 );',
28257 'finalPosition.xy += rotatedPosition;',
28258 'finalPosition = projectionMatrix * finalPosition;',
28260 'gl_Position = finalPosition;',
28266 gl.shaderSource( fragmentShader, [
28268 'precision ' + renderer.getPrecision() +
' float;',
28270 'uniform vec3 color;',
28271 'uniform sampler2D map;',
28272 'uniform float opacity;',
28274 'uniform int fogType;',
28275 'uniform vec3 fogColor;',
28276 'uniform float fogDensity;',
28277 'uniform float fogNear;',
28278 'uniform float fogFar;',
28279 'uniform float alphaTest;',
28281 'varying vec2 vUV;',
28285 'vec4 texture = texture2D( map, vUV );',
28287 'if ( texture.a < alphaTest ) discard;',
28289 'gl_FragColor = vec4( color * texture.xyz, texture.a * opacity );',
28291 'if ( fogType > 0 ) {',
28293 'float depth = gl_FragCoord.z / gl_FragCoord.w;',
28294 'float fogFactor = 0.0;',
28296 'if ( fogType == 1 ) {',
28298 'fogFactor = smoothstep( fogNear, fogFar, depth );',
28302 'const float LOG2 = 1.442695;',
28303 'fogFactor = exp2( - fogDensity * fogDensity * depth * depth * LOG2 );',
28304 'fogFactor = 1.0 - clamp( fogFactor, 0.0, 1.0 );',
28308 'gl_FragColor = mix( gl_FragColor, vec4( fogColor, gl_FragColor.w ), fogFactor );',
28316 gl.compileShader( vertexShader );
28317 gl.compileShader( fragmentShader );
28319 gl.attachShader( program, vertexShader );
28320 gl.attachShader( program, fragmentShader );
28322 gl.linkProgram( program );
28328 function painterSortStable ( a, b ) {
28330 if ( a.z !== b.z ) {
28336 return b.id - a.id;
28350 THREE.CurveUtils = {
28352 tangentQuadraticBezier:
function ( t, p0, p1, p2 ) {
28354 return 2 * ( 1 - t ) * ( p1 - p0 ) + 2 * t * ( p2 - p1 );
28360 tangentCubicBezier:
function ( t, p0, p1, p2, p3 ) {
28362 return - 3 * p0 * ( 1 - t ) * ( 1 - t ) +
28363 3 * p1 * ( 1 - t ) * ( 1 - t ) - 6 * t * p1 * ( 1 - t ) +
28364 6 * t * p2 * ( 1 - t ) - 3 * t * t * p2 +
28369 tangentSpline:
function ( t, p0, p1, p2, p3 ) {
28373 var h00 = 6 * t * t - 6 * t;
28374 var h10 = 3 * t * t - 4 * t + 1;
28375 var h01 = - 6 * t * t + 6 * t;
28376 var h11 = 3 * t * t - 2 * t;
28378 return h00 + h10 + h01 + h11;
28384 interpolate:
function( p0, p1, p2, p3, t ) {
28386 var v0 = ( p2 - p0 ) * 0.5;
28387 var v1 = ( p3 - p1 ) * 0.5;
28390 return ( 2 * p1 - 2 * p2 + v0 + v1 ) * t3 + ( - 3 * p1 + 3 * p2 - 2 * v0 - v1 ) * t2 + v0 * t + p1;
28402 THREE.GeometryUtils = {
28404 merge:
function ( geometry1, geometry2, materialIndexOffset ) {
28406 console.warn(
'THREE.GeometryUtils: .merge() has been moved to Geometry. Use geometry.merge( geometry2, matrix, materialIndexOffset ) instead.' );
28410 if ( geometry2 instanceof THREE.Mesh ) {
28412 geometry2.matrixAutoUpdate && geometry2.updateMatrix();
28414 matrix = geometry2.matrix;
28415 geometry2 = geometry2.geometry;
28419 geometry1.merge( geometry2, matrix, materialIndexOffset );
28423 center:
function ( geometry ) {
28425 console.warn(
'THREE.GeometryUtils: .center() has been moved to Geometry. Use geometry.center() instead.' );
28426 return geometry.center();
28440 THREE.ImageUtils = {
28442 crossOrigin: undefined,
28444 loadTexture:
function ( url, mapping, onLoad, onError ) {
28446 console.warn(
'THREE.ImageUtils.loadTexture is being deprecated. Use THREE.TextureLoader() instead.' );
28448 var loader =
new THREE.TextureLoader();
28449 loader.setCrossOrigin( this.crossOrigin );
28451 var texture = loader.load( url, onLoad, undefined, onError );
28453 if ( mapping ) texture.mapping = mapping;
28459 loadTextureCube:
function ( urls, mapping, onLoad, onError ) {
28461 console.warn(
'THREE.ImageUtils.loadTextureCube is being deprecated. Use THREE.CubeTextureLoader() instead.' );
28463 var loader =
new THREE.CubeTextureLoader();
28464 loader.setCrossOrigin( this.crossOrigin );
28466 var texture = loader.load( urls, onLoad, undefined, onError );
28468 if ( mapping ) texture.mapping = mapping;
28474 loadCompressedTexture:
function () {
28476 console.error(
'THREE.ImageUtils.loadCompressedTexture has been removed. Use THREE.DDSLoader instead.' )
28480 loadCompressedTextureCube:
function () {
28482 console.error(
'THREE.ImageUtils.loadCompressedTextureCube has been removed. Use THREE.DDSLoader instead.' )
28494 THREE.SceneUtils = {
28496 createMultiMaterialObject:
function ( geometry, materials ) {
28498 var group =
new THREE.Group();
28500 for ( var i = 0, l = materials.length; i < l; i ++ ) {
28502 group.add(
new THREE.Mesh( geometry, materials[ i ] ) );
28510 detach:
function ( child, parent, scene ) {
28512 child.applyMatrix( parent.matrixWorld );
28513 parent.remove( child );
28514 scene.add( child );
28518 attach:
function ( child, scene, parent ) {
28520 var matrixWorldInverse =
new THREE.Matrix4();
28521 matrixWorldInverse.getInverse( parent.matrixWorld );
28522 child.applyMatrix( matrixWorldInverse );
28524 scene.remove( child );
28525 parent.add( child );
28537 THREE.ShapeUtils = {
28541 area:
function ( contour ) {
28543 var n = contour.length;
28546 for ( var p = n - 1, q = 0; q < n; p = q ++ ) {
28548 a += contour[ p ].x * contour[ q ].y - contour[ q ].x * contour[ p ].y;
28556 triangulate: (
function () {
28572 function snip( contour, u, v, w, n, verts ) {
28575 var ax, ay, bx, by;
28576 var cx, cy, px, py;
28578 ax = contour[ verts[ u ] ].x;
28579 ay = contour[ verts[ u ] ].y;
28581 bx = contour[ verts[ v ] ].x;
28582 by = contour[ verts[ v ] ].y;
28584 cx = contour[ verts[ w ] ].x;
28585 cy = contour[ verts[ w ] ].y;
28587 if ( Number.EPSILON > ( ( ( bx - ax ) * ( cy - ay ) ) - ( ( by - ay ) * ( cx - ax ) ) ) )
return false;
28589 var aX, aY, bX, bY, cX, cY;
28590 var apx, apy, bpx, bpy, cpx, cpy;
28591 var cCROSSap, bCROSScp, aCROSSbp;
28593 aX = cx - bx; aY = cy - by;
28594 bX = ax - cx; bY = ay - cy;
28595 cX = bx - ax; cY = by - ay;
28597 for ( p = 0; p < n; p ++ ) {
28599 px = contour[ verts[ p ] ].x;
28600 py = contour[ verts[ p ] ].y;
28602 if ( ( ( px === ax ) && ( py === ay ) ) ||
28603 ( ( px === bx ) && ( py === by ) ) ||
28604 ( ( px === cx ) && ( py === cy ) ) )
continue;
28606 apx = px - ax; apy = py - ay;
28607 bpx = px - bx; bpy = py - by;
28608 cpx = px - cx; cpy = py - cy;
28612 aCROSSbp = aX * bpy - aY * bpx;
28613 cCROSSap = cX * apy - cY * apx;
28614 bCROSScp = bX * cpy - bY * cpx;
28616 if ( ( aCROSSbp >= - Number.EPSILON ) && ( bCROSScp >= - Number.EPSILON ) && ( cCROSSap >= - Number.EPSILON ) )
return false;
28626 return function ( contour, indices ) {
28628 var n = contour.length;
28630 if ( n < 3 )
return null;
28640 if ( THREE.ShapeUtils.area( contour ) > 0.0 ) {
28642 for ( v = 0; v < n; v ++ ) verts[ v ] = v;
28646 for ( v = 0; v < n; v ++ ) verts[ v ] = ( n - 1 ) - v;
28654 var count = 2 * nv;
28656 for ( v = nv - 1; nv > 2; ) {
28660 if ( ( count -- ) <= 0 ) {
28667 console.warn(
'THREE.ShapeUtils: Unable to triangulate polygon! in triangulate()' );
28669 if ( indices )
return vertIndices;
28676 u = v;
if ( nv <= u ) u = 0;
28677 v = u + 1;
if ( nv <= v ) v = 0;
28678 w = v + 1;
if ( nv <= w ) w = 0;
28680 if ( snip( contour, u, v, w, nv, verts ) ) {
28692 result.push( [ contour[ a ],
28697 vertIndices.push( [ verts[ u ], verts[ v ], verts[ w ] ] );
28701 for ( s = v, t = v + 1; t < nv; s ++, t ++ ) {
28703 verts[ s ] = verts[ t ];
28717 if ( indices )
return vertIndices;
28724 triangulateShape:
function ( contour, holes ) {
28726 function point_in_segment_2D_colin( inSegPt1, inSegPt2, inOtherPt ) {
28729 if ( inSegPt1.x !== inSegPt2.x ) {
28731 if ( inSegPt1.x < inSegPt2.x ) {
28733 return ( ( inSegPt1.x <= inOtherPt.x ) && ( inOtherPt.x <= inSegPt2.x ) );
28737 return ( ( inSegPt2.x <= inOtherPt.x ) && ( inOtherPt.x <= inSegPt1.x ) );
28743 if ( inSegPt1.y < inSegPt2.y ) {
28745 return ( ( inSegPt1.y <= inOtherPt.y ) && ( inOtherPt.y <= inSegPt2.y ) );
28749 return ( ( inSegPt2.y <= inOtherPt.y ) && ( inOtherPt.y <= inSegPt1.y ) );
28757 function intersect_segments_2D( inSeg1Pt1, inSeg1Pt2, inSeg2Pt1, inSeg2Pt2, inExcludeAdjacentSegs ) {
28759 var seg1dx = inSeg1Pt2.x - inSeg1Pt1.x, seg1dy = inSeg1Pt2.y - inSeg1Pt1.y;
28760 var seg2dx = inSeg2Pt2.x - inSeg2Pt1.x, seg2dy = inSeg2Pt2.y - inSeg2Pt1.y;
28762 var seg1seg2dx = inSeg1Pt1.x - inSeg2Pt1.x;
28763 var seg1seg2dy = inSeg1Pt1.y - inSeg2Pt1.y;
28765 var limit = seg1dy * seg2dx - seg1dx * seg2dy;
28766 var perpSeg1 = seg1dy * seg1seg2dx - seg1dx * seg1seg2dy;
28768 if ( Math.abs( limit ) > Number.EPSILON ) {
28775 if ( ( perpSeg1 < 0 ) || ( perpSeg1 > limit ) )
return [];
28776 perpSeg2 = seg2dy * seg1seg2dx - seg2dx * seg1seg2dy;
28777 if ( ( perpSeg2 < 0 ) || ( perpSeg2 > limit ) )
return [];
28781 if ( ( perpSeg1 > 0 ) || ( perpSeg1 < limit ) )
return [];
28782 perpSeg2 = seg2dy * seg1seg2dx - seg2dx * seg1seg2dy;
28783 if ( ( perpSeg2 > 0 ) || ( perpSeg2 < limit ) )
return [];
28789 if ( perpSeg2 === 0 ) {
28791 if ( ( inExcludeAdjacentSegs ) &&
28792 ( ( perpSeg1 === 0 ) || ( perpSeg1 === limit ) ) )
return [];
28793 return [ inSeg1Pt1 ];
28796 if ( perpSeg2 === limit ) {
28798 if ( ( inExcludeAdjacentSegs ) &&
28799 ( ( perpSeg1 === 0 ) || ( perpSeg1 === limit ) ) )
return [];
28800 return [ inSeg1Pt2 ];
28804 if ( perpSeg1 === 0 )
return [ inSeg2Pt1 ];
28805 if ( perpSeg1 === limit )
return [ inSeg2Pt2 ];
28808 var factorSeg1 = perpSeg2 / limit;
28809 return [ { x: inSeg1Pt1.x + factorSeg1 * seg1dx,
28810 y: inSeg1Pt1.y + factorSeg1 * seg1dy } ];
28815 if ( ( perpSeg1 !== 0 ) ||
28816 ( seg2dy * seg1seg2dx !== seg2dx * seg1seg2dy ) )
return [];
28819 var seg1Pt = ( ( seg1dx === 0 ) && ( seg1dy === 0 ) );
28820 var seg2Pt = ( ( seg2dx === 0 ) && ( seg2dy === 0 ) );
28822 if ( seg1Pt && seg2Pt ) {
28824 if ( ( inSeg1Pt1.x !== inSeg2Pt1.x ) ||
28825 ( inSeg1Pt1.y !== inSeg2Pt1.y ) )
return [];
28826 return [ inSeg1Pt1 ];
28832 if ( ! point_in_segment_2D_colin( inSeg2Pt1, inSeg2Pt2, inSeg1Pt1 ) )
return [];
28833 return [ inSeg1Pt1 ];
28839 if ( ! point_in_segment_2D_colin( inSeg1Pt1, inSeg1Pt2, inSeg2Pt1 ) )
return [];
28840 return [ inSeg2Pt1 ];
28845 var seg1min, seg1max, seg1minVal, seg1maxVal;
28846 var seg2min, seg2max, seg2minVal, seg2maxVal;
28847 if ( seg1dx !== 0 ) {
28850 if ( inSeg1Pt1.x < inSeg1Pt2.x ) {
28852 seg1min = inSeg1Pt1; seg1minVal = inSeg1Pt1.x;
28853 seg1max = inSeg1Pt2; seg1maxVal = inSeg1Pt2.x;
28857 seg1min = inSeg1Pt2; seg1minVal = inSeg1Pt2.x;
28858 seg1max = inSeg1Pt1; seg1maxVal = inSeg1Pt1.x;
28861 if ( inSeg2Pt1.x < inSeg2Pt2.x ) {
28863 seg2min = inSeg2Pt1; seg2minVal = inSeg2Pt1.x;
28864 seg2max = inSeg2Pt2; seg2maxVal = inSeg2Pt2.x;
28868 seg2min = inSeg2Pt2; seg2minVal = inSeg2Pt2.x;
28869 seg2max = inSeg2Pt1; seg2maxVal = inSeg2Pt1.x;
28876 if ( inSeg1Pt1.y < inSeg1Pt2.y ) {
28878 seg1min = inSeg1Pt1; seg1minVal = inSeg1Pt1.y;
28879 seg1max = inSeg1Pt2; seg1maxVal = inSeg1Pt2.y;
28883 seg1min = inSeg1Pt2; seg1minVal = inSeg1Pt2.y;
28884 seg1max = inSeg1Pt1; seg1maxVal = inSeg1Pt1.y;
28887 if ( inSeg2Pt1.y < inSeg2Pt2.y ) {
28889 seg2min = inSeg2Pt1; seg2minVal = inSeg2Pt1.y;
28890 seg2max = inSeg2Pt2; seg2maxVal = inSeg2Pt2.y;
28894 seg2min = inSeg2Pt2; seg2minVal = inSeg2Pt2.y;
28895 seg2max = inSeg2Pt1; seg2maxVal = inSeg2Pt1.y;
28900 if ( seg1minVal <= seg2minVal ) {
28902 if ( seg1maxVal < seg2minVal )
return [];
28903 if ( seg1maxVal === seg2minVal ) {
28905 if ( inExcludeAdjacentSegs )
return [];
28906 return [ seg2min ];
28909 if ( seg1maxVal <= seg2maxVal )
return [ seg2min, seg1max ];
28910 return [ seg2min, seg2max ];
28914 if ( seg1minVal > seg2maxVal )
return [];
28915 if ( seg1minVal === seg2maxVal ) {
28917 if ( inExcludeAdjacentSegs )
return [];
28918 return [ seg1min ];
28921 if ( seg1maxVal <= seg2maxVal )
return [ seg1min, seg1max ];
28922 return [ seg1min, seg2max ];
28930 function isPointInsideAngle( inVertex, inLegFromPt, inLegToPt, inOtherPt ) {
28935 var legFromPtX = inLegFromPt.x - inVertex.x, legFromPtY = inLegFromPt.y - inVertex.y;
28936 var legToPtX = inLegToPt.x - inVertex.x, legToPtY = inLegToPt.y - inVertex.y;
28937 var otherPtX = inOtherPt.x - inVertex.x, otherPtY = inOtherPt.y - inVertex.y;
28940 var from2toAngle = legFromPtX * legToPtY - legFromPtY * legToPtX;
28941 var from2otherAngle = legFromPtX * otherPtY - legFromPtY * otherPtX;
28943 if ( Math.abs( from2toAngle ) > Number.EPSILON ) {
28947 var other2toAngle = otherPtX * legToPtY - otherPtY * legToPtX;
28950 if ( from2toAngle > 0 ) {
28953 return ( ( from2otherAngle >= 0 ) && ( other2toAngle >= 0 ) );
28958 return ( ( from2otherAngle >= 0 ) || ( other2toAngle >= 0 ) );
28966 return ( from2otherAngle > 0 );
28973 function removeHoles( contour, holes ) {
28975 var shape = contour.concat();
28978 function isCutLineInsideAngles( inShapeIdx, inHoleIdx ) {
28981 var lastShapeIdx = shape.length - 1;
28983 var prevShapeIdx = inShapeIdx - 1;
28984 if ( prevShapeIdx < 0 ) prevShapeIdx = lastShapeIdx;
28986 var nextShapeIdx = inShapeIdx + 1;
28987 if ( nextShapeIdx > lastShapeIdx ) nextShapeIdx = 0;
28989 var insideAngle = isPointInsideAngle( shape[ inShapeIdx ], shape[ prevShapeIdx ], shape[ nextShapeIdx ], hole[ inHoleIdx ] );
28990 if ( ! insideAngle ) {
28998 var lastHoleIdx = hole.length - 1;
29000 var prevHoleIdx = inHoleIdx - 1;
29001 if ( prevHoleIdx < 0 ) prevHoleIdx = lastHoleIdx;
29003 var nextHoleIdx = inHoleIdx + 1;
29004 if ( nextHoleIdx > lastHoleIdx ) nextHoleIdx = 0;
29006 insideAngle = isPointInsideAngle( hole[ inHoleIdx ], hole[ prevHoleIdx ], hole[ nextHoleIdx ], shape[ inShapeIdx ] );
29007 if ( ! insideAngle ) {
29018 function intersectsShapeEdge( inShapePt, inHolePt ) {
29021 var sIdx, nextIdx, intersection;
29022 for ( sIdx = 0; sIdx < shape.length; sIdx ++ ) {
29024 nextIdx = sIdx + 1; nextIdx %= shape.length;
29025 intersection = intersect_segments_2D( inShapePt, inHolePt, shape[ sIdx ], shape[ nextIdx ],
true );
29026 if ( intersection.length > 0 )
return true;
29034 var indepHoles = [];
29036 function intersectsHoleEdge( inShapePt, inHolePt ) {
29039 var ihIdx, chkHole,
29040 hIdx, nextIdx, intersection;
29041 for ( ihIdx = 0; ihIdx < indepHoles.length; ihIdx ++ ) {
29043 chkHole = holes[ indepHoles[ ihIdx ]];
29044 for ( hIdx = 0; hIdx < chkHole.length; hIdx ++ ) {
29046 nextIdx = hIdx + 1; nextIdx %= chkHole.length;
29047 intersection = intersect_segments_2D( inShapePt, inHolePt, chkHole[ hIdx ], chkHole[ nextIdx ],
true );
29048 if ( intersection.length > 0 )
return true;
29057 var holeIndex, shapeIndex,
29059 holeIdx, cutKey, failedCuts = [],
29060 tmpShape1, tmpShape2,
29061 tmpHole1, tmpHole2;
29063 for ( var h = 0, hl = holes.length; h < hl; h ++ ) {
29065 indepHoles.push( h );
29069 var minShapeIndex = 0;
29070 var counter = indepHoles.length * 2;
29071 while ( indepHoles.length > 0 ) {
29074 if ( counter < 0 ) {
29076 console.log(
"Infinite Loop! Holes left:" + indepHoles.length +
", Probably Hole outside Shape!" );
29083 for ( shapeIndex = minShapeIndex; shapeIndex < shape.length; shapeIndex ++ ) {
29085 shapePt = shape[ shapeIndex ];
29089 for ( var h = 0; h < indepHoles.length; h ++ ) {
29091 holeIdx = indepHoles[ h ];
29094 cutKey = shapePt.x +
":" + shapePt.y +
":" + holeIdx;
29095 if ( failedCuts[ cutKey ] !== undefined )
continue;
29097 hole = holes[ holeIdx ];
29098 for ( var h2 = 0; h2 < hole.length; h2 ++ ) {
29100 holePt = hole[ h2 ];
29101 if ( ! isCutLineInsideAngles( shapeIndex, h2 ) )
continue;
29102 if ( intersectsShapeEdge( shapePt, holePt ) )
continue;
29103 if ( intersectsHoleEdge( shapePt, holePt ) )
continue;
29106 indepHoles.splice( h, 1 );
29108 tmpShape1 = shape.slice( 0, shapeIndex + 1 );
29109 tmpShape2 = shape.slice( shapeIndex );
29110 tmpHole1 = hole.slice( holeIndex );
29111 tmpHole2 = hole.slice( 0, holeIndex + 1 );
29113 shape = tmpShape1.concat( tmpHole1 ).concat( tmpHole2 ).concat( tmpShape2 );
29115 minShapeIndex = shapeIndex;
29123 if ( holeIndex >= 0 )
break;
29125 failedCuts[ cutKey ] =
true;
29128 if ( holeIndex >= 0 )
break;
29139 var i, il, f, face,
29145 var allpoints = contour.concat();
29147 for ( var h = 0, hl = holes.length; h < hl; h ++ ) {
29149 Array.prototype.push.apply( allpoints, holes[ h ] );
29157 for ( i = 0, il = allpoints.length; i < il; i ++ ) {
29159 key = allpoints[ i ].x +
":" + allpoints[ i ].y;
29161 if ( allPointsMap[ key ] !== undefined ) {
29163 console.warn(
"THREE.Shape: Duplicate point", key );
29167 allPointsMap[ key ] = i;
29172 var shapeWithoutHoles = removeHoles( contour, holes );
29174 var triangles = THREE.ShapeUtils.triangulate( shapeWithoutHoles,
false );
29179 for ( i = 0, il = triangles.length; i < il; i ++ ) {
29181 face = triangles[ i ];
29183 for ( f = 0; f < 3; f ++ ) {
29185 key = face[ f ].x +
":" + face[ f ].y;
29187 index = allPointsMap[ key ];
29189 if ( index !== undefined ) {
29199 return triangles.concat();
29203 isClockWise:
function ( pts ) {
29205 return THREE.ShapeUtils.area( pts ) < 0;
29214 b2: (
function () {
29216 function b2p0( t, p ) {
29223 function b2p1( t, p ) {
29225 return 2 * ( 1 - t ) * t * p;
29229 function b2p2( t, p ) {
29235 return function ( t, p0, p1, p2 ) {
29237 return b2p0( t, p0 ) + b2p1( t, p1 ) + b2p2( t, p2 );
29245 b3: (
function () {
29247 function b3p0( t, p ) {
29250 return k * k * k * p;
29254 function b3p1( t, p ) {
29257 return 3 * k * k * t * p;
29261 function b3p2( t, p ) {
29264 return 3 * k * t * t * p;
29268 function b3p3( t, p ) {
29270 return t * t * t * p;
29274 return function ( t, p0, p1, p2, p3 ) {
29276 return b3p0( t, p0 ) + b3p1( t, p1 ) + b3p2( t, p2 ) + b3p3( t, p3 );
29290 THREE.Audio =
function ( listener ) {
29292 THREE.Object3D.call(
this );
29294 this.type =
'Audio';
29296 this.context = listener.context;
29297 this.source = this.context.createBufferSource();
29298 this.source.onended = this.onEnded.bind(
this );
29300 this.gain = this.context.createGain();
29301 this.gain.connect( this.context.destination );
29303 this.panner = this.context.createPanner();
29304 this.panner.connect( this.gain );
29306 this.autoplay =
false;
29308 this.startTime = 0;
29309 this.playbackRate = 1;
29310 this.isPlaying =
false;
29314 THREE.Audio.prototype = Object.create( THREE.Object3D.prototype );
29315 THREE.Audio.prototype.constructor = THREE.Audio;
29317 THREE.Audio.prototype.load =
function ( file ) {
29321 var request =
new XMLHttpRequest();
29322 request.open(
'GET', file,
true );
29323 request.responseType =
'arraybuffer';
29324 request.onload =
function ( e ) {
29326 scope.context.decodeAudioData( this.response,
function ( buffer ) {
29328 scope.source.buffer = buffer;
29330 if ( scope.autoplay ) scope.play();
29341 THREE.Audio.prototype.play =
function () {
29343 if ( this.isPlaying ===
true ) {
29345 console.warn(
'THREE.Audio: Audio is already playing.' );
29350 var source = this.context.createBufferSource();
29352 source.buffer = this.source.buffer;
29353 source.loop = this.source.loop;
29354 source.onended = this.source.onended;
29355 source.start( 0, this.startTime );
29356 source.playbackRate.value = this.playbackRate;
29358 this.isPlaying =
true;
29360 this.source = source;
29366 THREE.Audio.prototype.pause =
function () {
29368 this.source.stop();
29369 this.startTime = this.context.currentTime;
29373 THREE.Audio.prototype.stop =
function () {
29375 this.source.stop();
29376 this.startTime = 0;
29380 THREE.Audio.prototype.connect =
function () {
29382 if ( this.filter !== undefined ) {
29384 this.source.connect( this.filter );
29385 this.filter.connect( this.panner );
29389 this.source.connect( this.panner );
29395 THREE.Audio.prototype.disconnect =
function () {
29397 if ( this.filter !== undefined ) {
29399 this.source.disconnect( this.filter );
29400 this.filter.disconnect( this.panner );
29404 this.source.disconnect( this.panner );
29410 THREE.Audio.prototype.setFilter =
function ( value ) {
29412 if ( this.isPlaying ===
true ) {
29415 this.filter = value;
29420 this.filter = value;
29426 THREE.Audio.prototype.getFilter =
function () {
29428 return this.filter;
29432 THREE.Audio.prototype.setPlaybackRate =
function ( value ) {
29434 this.playbackRate = value;
29436 if ( this.isPlaying ===
true ) {
29438 this.source.playbackRate.value = this.playbackRate;
29444 THREE.Audio.prototype.getPlaybackRate =
function () {
29446 return this.playbackRate;
29450 THREE.Audio.prototype.onEnded =
function() {
29452 this.isPlaying =
false;
29456 THREE.Audio.prototype.setLoop =
function ( value ) {
29458 this.source.loop = value;
29462 THREE.Audio.prototype.getLoop =
function () {
29464 return this.source.loop;
29468 THREE.Audio.prototype.setRefDistance =
function ( value ) {
29470 this.panner.refDistance = value;
29474 THREE.Audio.prototype.getRefDistance =
function () {
29476 return this.panner.refDistance;
29480 THREE.Audio.prototype.setRolloffFactor =
function ( value ) {
29482 this.panner.rolloffFactor = value;
29486 THREE.Audio.prototype.getRolloffFactor =
function () {
29488 return this.panner.rolloffFactor;
29492 THREE.Audio.prototype.setVolume =
function ( value ) {
29494 this.gain.gain.value = value;
29498 THREE.Audio.prototype.getVolume =
function () {
29500 return this.gain.gain.value;
29504 THREE.Audio.prototype.updateMatrixWorld = (
function () {
29506 var position =
new THREE.Vector3();
29508 return function updateMatrixWorld( force ) {
29510 THREE.Object3D.prototype.updateMatrixWorld.call(
this, force );
29512 position.setFromMatrixPosition( this.matrixWorld );
29514 this.panner.setPosition( position.x, position.y, position.z );
29526 THREE.AudioListener =
function () {
29528 THREE.Object3D.call(
this );
29530 this.type =
'AudioListener';
29532 this.context =
new ( window.AudioContext || window.webkitAudioContext )();
29536 THREE.AudioListener.prototype = Object.create( THREE.Object3D.prototype );
29537 THREE.AudioListener.prototype.constructor = THREE.AudioListener;
29539 THREE.AudioListener.prototype.updateMatrixWorld = (
function () {
29541 var position =
new THREE.Vector3();
29542 var quaternion =
new THREE.Quaternion();
29543 var scale =
new THREE.Vector3();
29545 var orientation =
new THREE.Vector3();
29547 return function updateMatrixWorld( force ) {
29549 THREE.Object3D.prototype.updateMatrixWorld.call(
this, force );
29551 var listener = this.context.listener;
29554 this.matrixWorld.decompose( position, quaternion, scale );
29556 orientation.set( 0, 0, - 1 ).applyQuaternion( quaternion );
29558 listener.setPosition( position.x, position.y, position.z );
29559 listener.setOrientation( orientation.x, orientation.y, orientation.z, up.x, up.y, up.z );
29603 THREE.Curve =
function () {
29607 THREE.Curve.prototype = {
29609 constructor: THREE.Curve,
29614 getPoint:
function ( t ) {
29616 console.warn(
"THREE.Curve: Warning, getPoint() not implemented!" );
29624 getPointAt:
function ( u ) {
29626 var t = this.getUtoTmapping( u );
29627 return this.getPoint( t );
29633 getPoints:
function ( divisions ) {
29635 if ( ! divisions ) divisions = 5;
29639 for ( d = 0; d <= divisions; d ++ ) {
29641 pts.push( this.getPoint( d / divisions ) );
29651 getSpacedPoints:
function ( divisions ) {
29653 if ( ! divisions ) divisions = 5;
29657 for ( d = 0; d <= divisions; d ++ ) {
29659 pts.push( this.getPointAt( d / divisions ) );
29669 getLength:
function () {
29671 var lengths = this.getLengths();
29672 return lengths[ lengths.length - 1 ];
29678 getLengths:
function ( divisions ) {
29680 if ( ! divisions ) divisions = ( this.__arcLengthDivisions ) ? ( this.__arcLengthDivisions ) : 200;
29682 if ( this.cacheArcLengths
29683 && ( this.cacheArcLengths.length === divisions + 1 )
29684 && ! this.needsUpdate ) {
29687 return this.cacheArcLengths;
29691 this.needsUpdate =
false;
29694 var current, last = this.getPoint( 0 );
29699 for ( p = 1; p <= divisions; p ++ ) {
29701 current = this.getPoint ( p / divisions );
29702 sum += current.distanceTo( last );
29708 this.cacheArcLengths = cache;
29714 updateArcLengths:
function() {
29716 this.needsUpdate =
true;
29723 getUtoTmapping:
function ( u, distance ) {
29725 var arcLengths = this.getLengths();
29727 var i = 0, il = arcLengths.length;
29729 var targetArcLength;
29733 targetArcLength = distance;
29737 targetArcLength = u * arcLengths[ il - 1 ];
29745 var low = 0, high = il - 1, comparison;
29747 while ( low <= high ) {
29749 i = Math.floor( low + ( high - low ) / 2 );
29751 comparison = arcLengths[ i ] - targetArcLength;
29753 if ( comparison < 0 ) {
29757 }
else if ( comparison > 0 ) {
29776 if ( arcLengths[ i ] === targetArcLength ) {
29778 var t = i / ( il - 1 );
29785 var lengthBefore = arcLengths[ i ];
29786 var lengthAfter = arcLengths[ i + 1 ];
29788 var segmentLength = lengthAfter - lengthBefore;
29792 var segmentFraction = ( targetArcLength - lengthBefore ) / segmentLength;
29796 var t = ( i + segmentFraction ) / ( il - 1 );
29807 getTangent:
function( t ) {
29809 var delta = 0.0001;
29810 var t1 = t - delta;
29811 var t2 = t + delta;
29815 if ( t1 < 0 ) t1 = 0;
29816 if ( t2 > 1 ) t2 = 1;
29818 var pt1 = this.getPoint( t1 );
29819 var pt2 = this.getPoint( t2 );
29821 var vec = pt2.clone().sub( pt1 );
29822 return vec.normalize();
29826 getTangentAt:
function ( u ) {
29828 var t = this.getUtoTmapping( u );
29829 return this.getTangent( t );
29835 THREE.Curve.Utils = THREE.CurveUtils;
29845 THREE.Curve.create =
function ( constructor, getPointFunc ) {
29847 constructor.prototype = Object.create( THREE.Curve.prototype );
29848 constructor.prototype.constructor = constructor;
29849 constructor.prototype.getPoint = getPointFunc;
29851 return constructor;
29867 THREE.CurvePath =
function () {
29871 this.autoClose =
false;
29875 THREE.CurvePath.prototype = Object.create( THREE.Curve.prototype );
29876 THREE.CurvePath.prototype.constructor = THREE.CurvePath;
29878 THREE.CurvePath.prototype.add =
function ( curve ) {
29880 this.curves.push( curve );
29892 THREE.CurvePath.prototype.closePath =
function() {
29897 var startPoint = this.curves[ 0 ].getPoint( 0 );
29898 var endPoint = this.curves[ this.curves.length - 1 ].getPoint( 1 );
29900 if ( ! startPoint.equals( endPoint ) ) {
29902 this.curves.push(
new THREE.LineCurve( endPoint, startPoint ) );
29917 THREE.CurvePath.prototype.getPoint =
function( t ) {
29919 var d = t * this.getLength();
29920 var curveLengths = this.getCurveLengths();
29925 while ( i < curveLengths.length ) {
29927 if ( curveLengths[ i ] >= d ) {
29929 var diff = curveLengths[ i ] - d;
29930 var curve = this.curves[ i ];
29932 var u = 1 - diff / curve.getLength();
29934 return curve.getPointAt( u );
29957 THREE.CurvePath.prototype.getLength =
function() {
29959 var lens = this.getCurveLengths();
29960 return lens[ lens.length - 1 ];
29967 THREE.CurvePath.prototype.getCurveLengths =
function() {
29971 if ( this.cacheLengths && this.cacheLengths.length ===
this.curves.length ) {
29973 return this.cacheLengths;
29980 var lengths = [], sums = 0;
29982 for ( var i = 0, l = this.curves.length; i < l; i ++ ) {
29984 sums += this.curves[ i ].getLength();
29985 lengths.push( sums );
29989 this.cacheLengths = lengths;
30003 THREE.CurvePath.prototype.createPointsGeometry =
function( divisions ) {
30005 var pts = this.getPoints( divisions,
true );
30006 return this.createGeometry( pts );
30012 THREE.CurvePath.prototype.createSpacedPointsGeometry =
function( divisions ) {
30014 var pts = this.getSpacedPoints( divisions,
true );
30015 return this.createGeometry( pts );
30019 THREE.CurvePath.prototype.createGeometry =
function( points ) {
30021 var geometry =
new THREE.Geometry();
30023 for ( var i = 0, l = points.length; i < l; i ++ ) {
30025 var point = points[ i ];
30026 geometry.vertices.push(
new THREE.Vector3( point.x, point.y, point.z || 0 ) );
30042 THREE.Path =
function ( points ) {
30044 THREE.CurvePath.call(
this );
30050 this.fromPoints( points );
30056 THREE.Path.prototype = Object.create( THREE.CurvePath.prototype );
30057 THREE.Path.prototype.constructor = THREE.Path;
30064 THREE.Path.prototype.fromPoints =
function ( vectors ) {
30066 this.moveTo( vectors[ 0 ].x, vectors[ 0 ].y );
30068 for ( var i = 1, l = vectors.length; i < l; i ++ ) {
30070 this.lineTo( vectors[ i ].x, vectors[ i ].y );
30078 THREE.Path.prototype.moveTo =
function ( x, y ) {
30080 this.actions.push( { action:
'moveTo', args: [ x, y ] } );
30084 THREE.Path.prototype.lineTo =
function ( x, y ) {
30086 var lastargs = this.actions[ this.actions.length - 1 ].args;
30088 var x0 = lastargs[ lastargs.length - 2 ];
30089 var y0 = lastargs[ lastargs.length - 1 ];
30091 var curve =
new THREE.LineCurve(
new THREE.Vector2( x0, y0 ),
new THREE.Vector2( x, y ) );
30092 this.curves.push( curve );
30094 this.actions.push( { action:
'lineTo', args: [ x, y ] } );
30098 THREE.Path.prototype.quadraticCurveTo =
function( aCPx, aCPy, aX, aY ) {
30100 var lastargs = this.actions[ this.actions.length - 1 ].args;
30102 var x0 = lastargs[ lastargs.length - 2 ];
30103 var y0 = lastargs[ lastargs.length - 1 ];
30105 var curve =
new THREE.QuadraticBezierCurve(
30106 new THREE.Vector2( x0, y0 ),
30107 new THREE.Vector2( aCPx, aCPy ),
30108 new THREE.Vector2( aX, aY )
30111 this.curves.push( curve );
30113 this.actions.push( { action:
'quadraticCurveTo', args: [ aCPx, aCPy, aX, aY ] } );
30117 THREE.Path.prototype.bezierCurveTo =
function( aCP1x, aCP1y, aCP2x, aCP2y, aX, aY ) {
30119 var lastargs = this.actions[ this.actions.length - 1 ].args;
30121 var x0 = lastargs[ lastargs.length - 2 ];
30122 var y0 = lastargs[ lastargs.length - 1 ];
30124 var curve =
new THREE.CubicBezierCurve(
30125 new THREE.Vector2( x0, y0 ),
30126 new THREE.Vector2( aCP1x, aCP1y ),
30127 new THREE.Vector2( aCP2x, aCP2y ),
30128 new THREE.Vector2( aX, aY )
30131 this.curves.push( curve );
30133 this.actions.push( { action:
'bezierCurveTo', args: [ aCP1x, aCP1y, aCP2x, aCP2y, aX, aY ] } );
30137 THREE.Path.prototype.splineThru =
function( pts ) {
30139 var args = Array.prototype.slice.call( arguments );
30141 var lastargs = this.actions[ this.actions.length - 1 ].args;
30143 var x0 = lastargs[ lastargs.length - 2 ];
30144 var y0 = lastargs[ lastargs.length - 1 ];
30146 var npts = [
new THREE.Vector2( x0, y0 ) ];
30147 Array.prototype.push.apply( npts, pts );
30149 var curve =
new THREE.SplineCurve( npts );
30150 this.curves.push( curve );
30152 this.actions.push( { action:
'splineThru', args: args } );
30158 THREE.Path.prototype.arc =
function ( aX, aY, aRadius, aStartAngle, aEndAngle, aClockwise ) {
30160 var lastargs = this.actions[ this.actions.length - 1 ].args;
30161 var x0 = lastargs[ lastargs.length - 2 ];
30162 var y0 = lastargs[ lastargs.length - 1 ];
30164 this.absarc( aX + x0, aY + y0, aRadius,
30165 aStartAngle, aEndAngle, aClockwise );
30169 THREE.Path.prototype.absarc =
function ( aX, aY, aRadius, aStartAngle, aEndAngle, aClockwise ) {
30171 this.absellipse( aX, aY, aRadius, aRadius, aStartAngle, aEndAngle, aClockwise );
30175 THREE.Path.prototype.ellipse =
function ( aX, aY, xRadius, yRadius, aStartAngle, aEndAngle, aClockwise, aRotation ) {
30177 var lastargs = this.actions[ this.actions.length - 1 ].args;
30178 var x0 = lastargs[ lastargs.length - 2 ];
30179 var y0 = lastargs[ lastargs.length - 1 ];
30181 this.absellipse( aX + x0, aY + y0, xRadius, yRadius, aStartAngle, aEndAngle, aClockwise, aRotation );
30186 THREE.Path.prototype.absellipse =
function ( aX, aY, xRadius, yRadius, aStartAngle, aEndAngle, aClockwise, aRotation ) {
30191 aStartAngle, aEndAngle,
30196 var curve =
new THREE.EllipseCurve( aX, aY, xRadius, yRadius, aStartAngle, aEndAngle, aClockwise, aRotation );
30197 this.curves.push( curve );
30199 var lastPoint = curve.getPoint( 1 );
30200 args.push( lastPoint.x );
30201 args.push( lastPoint.y );
30203 this.actions.push( { action:
'ellipse', args: args } );
30207 THREE.Path.prototype.getSpacedPoints =
function ( divisions, closedPath ) {
30209 if ( ! divisions ) divisions = 40;
30213 for ( var i = 0; i < divisions; i ++ ) {
30215 points.push( this.getPoint( i / divisions ) );
30233 THREE.Path.prototype.getPoints =
function( divisions, closedPath ) {
30235 divisions = divisions || 12;
30237 var b2 = THREE.ShapeUtils.b2;
30238 var b3 = THREE.ShapeUtils.b3;
30242 var cpx, cpy, cpx2, cpy2, cpx1, cpy1, cpx0, cpy0,
30245 for ( var i = 0, l = this.actions.length; i < l; i ++ ) {
30247 var item = this.actions[ i ];
30249 var action = item.action;
30250 var args = item.args;
30252 switch ( action ) {
30256 points.push(
new THREE.Vector2( args[ 0 ], args[ 1 ] ) );
30262 points.push(
new THREE.Vector2( args[ 0 ], args[ 1 ] ) );
30266 case 'quadraticCurveTo':
30274 if ( points.length > 0 ) {
30276 laste = points[ points.length - 1 ];
30283 laste = this.actions[ i - 1 ].args;
30285 cpx0 = laste[ laste.length - 2 ];
30286 cpy0 = laste[ laste.length - 1 ];
30290 for ( var j = 1; j <= divisions; j ++ ) {
30292 var t = j / divisions;
30294 tx = b2( t, cpx0, cpx1, cpx );
30295 ty = b2( t, cpy0, cpy1, cpy );
30297 points.push(
new THREE.Vector2( tx, ty ) );
30303 case 'bezierCurveTo':
30314 if ( points.length > 0 ) {
30316 laste = points[ points.length - 1 ];
30323 laste = this.actions[ i - 1 ].args;
30325 cpx0 = laste[ laste.length - 2 ];
30326 cpy0 = laste[ laste.length - 1 ];
30331 for ( var j = 1; j <= divisions; j ++ ) {
30333 var t = j / divisions;
30335 tx = b3( t, cpx0, cpx1, cpx2, cpx );
30336 ty = b3( t, cpy0, cpy1, cpy2, cpy );
30338 points.push(
new THREE.Vector2( tx, ty ) );
30346 laste = this.actions[ i - 1 ].args;
30348 var last =
new THREE.Vector2( laste[ laste.length - 2 ], laste[ laste.length - 1 ] );
30349 var spts = [ last ];
30351 var n = divisions * args[ 0 ].length;
30353 spts = spts.concat( args[ 0 ] );
30355 var spline =
new THREE.SplineCurve( spts );
30357 for ( var j = 1; j <= n; j ++ ) {
30359 points.push( spline.getPointAt( j / n ) );
30367 var aX = args[ 0 ], aY = args[ 1 ],
30368 aRadius = args[ 2 ],
30369 aStartAngle = args[ 3 ], aEndAngle = args[ 4 ],
30370 aClockwise = !! args[ 5 ];
30372 var deltaAngle = aEndAngle - aStartAngle;
30374 var tdivisions = divisions * 2;
30376 for ( var j = 1; j <= tdivisions; j ++ ) {
30378 var t = j / tdivisions;
30380 if ( ! aClockwise ) {
30386 angle = aStartAngle + t * deltaAngle;
30388 tx = aX + aRadius * Math.cos( angle );
30389 ty = aY + aRadius * Math.sin( angle );
30393 points.push(
new THREE.Vector2( tx, ty ) );
30403 var aX = args[ 0 ], aY = args[ 1 ],
30404 xRadius = args[ 2 ],
30405 yRadius = args[ 3 ],
30406 aStartAngle = args[ 4 ], aEndAngle = args[ 5 ],
30407 aClockwise = !! args[ 6 ],
30408 aRotation = args[ 7 ];
30411 var deltaAngle = aEndAngle - aStartAngle;
30413 var tdivisions = divisions * 2;
30416 if ( aRotation !== 0 ) {
30418 cos = Math.cos( aRotation );
30419 sin = Math.sin( aRotation );
30423 for ( var j = 1; j <= tdivisions; j ++ ) {
30425 var t = j / tdivisions;
30427 if ( ! aClockwise ) {
30433 angle = aStartAngle + t * deltaAngle;
30435 tx = aX + xRadius * Math.cos( angle );
30436 ty = aY + yRadius * Math.sin( angle );
30438 if ( aRotation !== 0 ) {
30440 var x = tx, y = ty;
30443 tx = ( x - aX ) * cos - ( y - aY ) * sin + aX;
30444 ty = ( x - aX ) * sin + ( y - aY ) * cos + aY;
30450 points.push(
new THREE.Vector2( tx, ty ) );
30465 var lastPoint = points[ points.length - 1 ];
30466 if ( Math.abs( lastPoint.x - points[ 0 ].x ) < Number.EPSILON &&
30467 Math.abs( lastPoint.y - points[ 0 ].y ) < Number.EPSILON )
30468 points.splice( points.length - 1, 1 );
30469 if ( closedPath ) {
30471 points.push( points[ 0 ] );
30491 THREE.Path.prototype.toShapes =
function( isCCW, noHoles ) {
30493 function extractSubpaths( inActions ) {
30495 var subPaths = [], lastPath =
new THREE.Path();
30497 for ( var i = 0, l = inActions.length; i < l; i ++ ) {
30499 var item = inActions[ i ];
30501 var args = item.args;
30502 var action = item.action;
30504 if ( action ===
'moveTo' ) {
30506 if ( lastPath.actions.length !== 0 ) {
30508 subPaths.push( lastPath );
30509 lastPath =
new THREE.Path();
30515 lastPath[ action ].apply( lastPath, args );
30519 if ( lastPath.actions.length !== 0 ) {
30521 subPaths.push( lastPath );
30531 function toShapesNoHoles( inSubpaths ) {
30535 for ( var i = 0, l = inSubpaths.length; i < l; i ++ ) {
30537 var tmpPath = inSubpaths[ i ];
30539 var tmpShape =
new THREE.Shape();
30540 tmpShape.actions = tmpPath.actions;
30541 tmpShape.curves = tmpPath.curves;
30543 shapes.push( tmpShape );
30553 function isPointInsidePolygon( inPt, inPolygon ) {
30555 var polyLen = inPolygon.length;
30561 var inside =
false;
30562 for ( var p = polyLen - 1, q = 0; q < polyLen; p = q ++ ) {
30564 var edgeLowPt = inPolygon[ p ];
30565 var edgeHighPt = inPolygon[ q ];
30567 var edgeDx = edgeHighPt.x - edgeLowPt.x;
30568 var edgeDy = edgeHighPt.y - edgeLowPt.y;
30570 if ( Math.abs( edgeDy ) > Number.EPSILON ) {
30573 if ( edgeDy < 0 ) {
30575 edgeLowPt = inPolygon[ q ]; edgeDx = - edgeDx;
30576 edgeHighPt = inPolygon[ p ]; edgeDy = - edgeDy;
30579 if ( ( inPt.y < edgeLowPt.y ) || ( inPt.y > edgeHighPt.y ) )
continue;
30581 if ( inPt.y === edgeLowPt.y ) {
30583 if ( inPt.x === edgeLowPt.x )
return true;
30588 var perpEdge = edgeDy * ( inPt.x - edgeLowPt.x ) - edgeDx * ( inPt.y - edgeLowPt.y );
30589 if ( perpEdge === 0 )
return true;
30590 if ( perpEdge < 0 )
continue;
30598 if ( inPt.y !== edgeLowPt.y )
continue;
30600 if ( ( ( edgeHighPt.x <= inPt.x ) && ( inPt.x <= edgeLowPt.x ) ) ||
30601 ( ( edgeLowPt.x <= inPt.x ) && ( inPt.x <= edgeHighPt.x ) ) )
return true;
30612 var isClockWise = THREE.ShapeUtils.isClockWise;
30614 var subPaths = extractSubpaths( this.actions );
30615 if ( subPaths.length === 0 )
return [];
30617 if ( noHoles ===
true )
return toShapesNoHoles( subPaths );
30620 var solid, tmpPath, tmpShape, shapes = [];
30622 if ( subPaths.length === 1 ) {
30624 tmpPath = subPaths[ 0 ];
30625 tmpShape =
new THREE.Shape();
30626 tmpShape.actions = tmpPath.actions;
30627 tmpShape.curves = tmpPath.curves;
30628 shapes.push( tmpShape );
30633 var holesFirst = ! isClockWise( subPaths[ 0 ].getPoints() );
30634 holesFirst = isCCW ? ! holesFirst : holesFirst;
30638 var betterShapeHoles = [];
30639 var newShapes = [];
30640 var newShapeHoles = [];
30644 newShapes[ mainIdx ] = undefined;
30645 newShapeHoles[ mainIdx ] = [];
30647 for ( var i = 0, l = subPaths.length; i < l; i ++ ) {
30649 tmpPath = subPaths[ i ];
30650 tmpPoints = tmpPath.getPoints();
30651 solid = isClockWise( tmpPoints );
30652 solid = isCCW ? ! solid : solid;
30656 if ( ( ! holesFirst ) && ( newShapes[ mainIdx ] ) ) mainIdx ++;
30658 newShapes[ mainIdx ] = { s:
new THREE.Shape(), p: tmpPoints };
30659 newShapes[ mainIdx ].s.actions = tmpPath.actions;
30660 newShapes[ mainIdx ].s.curves = tmpPath.curves;
30662 if ( holesFirst ) mainIdx ++;
30663 newShapeHoles[ mainIdx ] = [];
30669 newShapeHoles[ mainIdx ].push( { h: tmpPath, p: tmpPoints[ 0 ] } );
30678 if ( ! newShapes[ 0 ] )
return toShapesNoHoles( subPaths );
30681 if ( newShapes.length > 1 ) {
30683 var ambiguous =
false;
30686 for ( var sIdx = 0, sLen = newShapes.length; sIdx < sLen; sIdx ++ ) {
30688 betterShapeHoles[ sIdx ] = [];
30692 for ( var sIdx = 0, sLen = newShapes.length; sIdx < sLen; sIdx ++ ) {
30694 var sho = newShapeHoles[ sIdx ];
30696 for ( var hIdx = 0; hIdx < sho.length; hIdx ++ ) {
30698 var ho = sho[ hIdx ];
30699 var hole_unassigned =
true;
30701 for ( var s2Idx = 0; s2Idx < newShapes.length; s2Idx ++ ) {
30703 if ( isPointInsidePolygon( ho.p, newShapes[ s2Idx ].p ) ) {
30705 if ( sIdx !== s2Idx ) toChange.push( { froms: sIdx, tos: s2Idx, hole: hIdx } );
30706 if ( hole_unassigned ) {
30708 hole_unassigned =
false;
30709 betterShapeHoles[ s2Idx ].push( ho );
30720 if ( hole_unassigned ) {
30722 betterShapeHoles[ sIdx ].push( ho );
30730 if ( toChange.length > 0 ) {
30733 if ( ! ambiguous ) newShapeHoles = betterShapeHoles;
30741 for ( var i = 0, il = newShapes.length; i < il; i ++ ) {
30743 tmpShape = newShapes[ i ].s;
30744 shapes.push( tmpShape );
30745 tmpHoles = newShapeHoles[ i ];
30747 for ( var j = 0, jl = tmpHoles.length; j < jl; j ++ ) {
30749 tmpShape.holes.push( tmpHoles[ j ].h );
30774 THREE.Shape =
function () {
30776 THREE.Path.apply(
this, arguments );
30782 THREE.Shape.prototype = Object.create( THREE.Path.prototype );
30783 THREE.Shape.prototype.constructor = THREE.Shape;
30787 THREE.Shape.prototype.extrude =
function ( options ) {
30789 return new THREE.ExtrudeGeometry(
this, options );
30795 THREE.Shape.prototype.makeGeometry =
function ( options ) {
30797 return new THREE.ShapeGeometry(
this, options );
30803 THREE.Shape.prototype.getPointsHoles =
function ( divisions ) {
30807 for ( var i = 0, l = this.holes.length; i < l; i ++ ) {
30809 holesPts[ i ] = this.holes[ i ].getPoints( divisions );
30820 THREE.Shape.prototype.extractAllPoints =
function ( divisions ) {
30824 shape: this.getPoints( divisions ),
30825 holes: this.getPointsHoles( divisions )
30831 THREE.Shape.prototype.extractPoints =
function ( divisions ) {
30833 return this.extractAllPoints( divisions );
30837 THREE.Shape.Utils = THREE.ShapeUtils;
30845 THREE.LineCurve =
function ( v1, v2 ) {
30852 THREE.LineCurve.prototype = Object.create( THREE.Curve.prototype );
30853 THREE.LineCurve.prototype.constructor = THREE.LineCurve;
30855 THREE.LineCurve.prototype.getPoint =
function ( t ) {
30857 var point = this.v2.clone().sub( this.v1 );
30858 point.multiplyScalar( t ).add( this.v1 );
30866 THREE.LineCurve.prototype.getPointAt =
function ( u ) {
30868 return this.getPoint( u );
30872 THREE.LineCurve.prototype.getTangent =
function( t ) {
30874 var tangent = this.v2.clone().sub( this.v1 );
30876 return tangent.normalize();
30887 THREE.QuadraticBezierCurve =
function ( v0, v1, v2 ) {
30895 THREE.QuadraticBezierCurve.prototype = Object.create( THREE.Curve.prototype );
30896 THREE.QuadraticBezierCurve.prototype.constructor = THREE.QuadraticBezierCurve;
30899 THREE.QuadraticBezierCurve.prototype.getPoint =
function ( t ) {
30901 var b2 = THREE.ShapeUtils.b2;
30903 return new THREE.Vector2(
30904 b2( t, this.v0.x,
this.v1.x,
this.v2.x ),
30905 b2( t, this.v0.y,
this.v1.y,
this.v2.y )
30911 THREE.QuadraticBezierCurve.prototype.getTangent =
function( t ) {
30913 var tangentQuadraticBezier = THREE.CurveUtils.tangentQuadraticBezier;
30915 return new THREE.Vector2(
30916 tangentQuadraticBezier( t, this.v0.x,
this.v1.x,
this.v2.x ),
30917 tangentQuadraticBezier( t, this.v0.y,
this.v1.y,
this.v2.y )
30928 THREE.CubicBezierCurve =
function ( v0, v1, v2, v3 ) {
30937 THREE.CubicBezierCurve.prototype = Object.create( THREE.Curve.prototype );
30938 THREE.CubicBezierCurve.prototype.constructor = THREE.CubicBezierCurve;
30940 THREE.CubicBezierCurve.prototype.getPoint =
function ( t ) {
30942 var b3 = THREE.ShapeUtils.b3;
30944 return new THREE.Vector2(
30945 b3( t, this.v0.x,
this.v1.x,
this.v2.x,
this.v3.x ),
30946 b3( t, this.v0.y,
this.v1.y,
this.v2.y,
this.v3.y )
30951 THREE.CubicBezierCurve.prototype.getTangent =
function( t ) {
30953 var tangentCubicBezier = THREE.CurveUtils.tangentCubicBezier;
30955 return new THREE.Vector2(
30956 tangentCubicBezier( t, this.v0.x,
this.v1.x,
this.v2.x,
this.v3.x ),
30957 tangentCubicBezier( t, this.v0.y,
this.v1.y,
this.v2.y,
this.v3.y )
30968 THREE.SplineCurve =
function ( points ) {
30970 this.points = ( points == undefined ) ? [] : points;
30974 THREE.SplineCurve.prototype = Object.create( THREE.Curve.prototype );
30975 THREE.SplineCurve.prototype.constructor = THREE.SplineCurve;
30977 THREE.SplineCurve.prototype.getPoint =
function ( t ) {
30979 var points = this.points;
30980 var point = ( points.length - 1 ) * t;
30982 var intPoint = Math.floor( point );
30983 var weight = point - intPoint;
30985 var point0 = points[ intPoint === 0 ? intPoint : intPoint - 1 ];
30986 var point1 = points[ intPoint ];
30987 var point2 = points[ intPoint > points.length - 2 ? points.length - 1 : intPoint + 1 ];
30988 var point3 = points[ intPoint > points.length - 3 ? points.length - 1 : intPoint + 2 ];
30990 var interpolate = THREE.CurveUtils.interpolate;
30992 return new THREE.Vector2(
30993 interpolate( point0.x, point1.x, point2.x, point3.x, weight ),
30994 interpolate( point0.y, point1.y, point2.y, point3.y, weight )
31005 THREE.EllipseCurve =
function ( aX, aY, xRadius, yRadius, aStartAngle, aEndAngle, aClockwise, aRotation ) {
31010 this.xRadius = xRadius;
31011 this.yRadius = yRadius;
31013 this.aStartAngle = aStartAngle;
31014 this.aEndAngle = aEndAngle;
31016 this.aClockwise = aClockwise;
31018 this.aRotation = aRotation || 0;
31022 THREE.EllipseCurve.prototype = Object.create( THREE.Curve.prototype );
31023 THREE.EllipseCurve.prototype.constructor = THREE.EllipseCurve;
31025 THREE.EllipseCurve.prototype.getPoint =
function ( t ) {
31027 var deltaAngle = this.aEndAngle - this.aStartAngle;
31029 if ( deltaAngle < 0 ) deltaAngle += Math.PI * 2;
31030 if ( deltaAngle > Math.PI * 2 ) deltaAngle -= Math.PI * 2;
31034 if ( this.aClockwise ===
true ) {
31036 angle = this.aEndAngle + ( 1 - t ) * ( Math.PI * 2 - deltaAngle );
31040 angle = this.aStartAngle + t * deltaAngle;
31044 var x = this.aX + this.xRadius * Math.cos( angle );
31045 var y = this.aY + this.yRadius * Math.sin( angle );
31047 if ( this.aRotation !== 0 ) {
31049 var cos = Math.cos( this.aRotation );
31050 var sin = Math.sin( this.aRotation );
31052 var tx = x, ty = y;
31055 x = ( tx - this.aX ) * cos - ( ty - this.aY ) * sin + this.aX;
31056 y = ( tx - this.aX ) * sin + ( ty - this.aY ) * cos + this.aY;
31060 return new THREE.Vector2( x, y );
31070 THREE.ArcCurve =
function ( aX, aY, aRadius, aStartAngle, aEndAngle, aClockwise ) {
31072 THREE.EllipseCurve.call(
this, aX, aY, aRadius, aRadius, aStartAngle, aEndAngle, aClockwise );
31076 THREE.ArcCurve.prototype = Object.create( THREE.EllipseCurve.prototype );
31077 THREE.ArcCurve.prototype.constructor = THREE.ArcCurve;
31085 THREE.LineCurve3 = THREE.Curve.create(
31087 function ( v1, v2 ) {
31096 var vector =
new THREE.Vector3();
31098 vector.subVectors( this.v2, this.v1 );
31099 vector.multiplyScalar( t );
31100 vector.add( this.v1 );
31114 THREE.QuadraticBezierCurve3 = THREE.Curve.create(
31116 function ( v0, v1, v2 ) {
31126 var b2 = THREE.ShapeUtils.b2;
31128 return new THREE.Vector3(
31129 b2( t, this.v0.x,
this.v1.x,
this.v2.x ),
31130 b2( t, this.v0.y,
this.v1.y,
this.v2.y ),
31131 b2( t, this.v0.z,
this.v1.z,
this.v2.z )
31144 THREE.CubicBezierCurve3 = THREE.Curve.create(
31146 function ( v0, v1, v2, v3 ) {
31157 var b3 = THREE.ShapeUtils.b3;
31159 return new THREE.Vector3(
31160 b3( t, this.v0.x,
this.v1.x,
this.v2.x,
this.v3.x ),
31161 b3( t, this.v0.y,
this.v1.y,
this.v2.y,
this.v3.y ),
31162 b3( t, this.v0.z,
this.v1.z,
this.v2.z,
this.v3.z )
31176 THREE.SplineCurve3 = THREE.Curve.create(
31178 function ( points ) {
31180 console.warn(
'THREE.SplineCurve3 will be deprecated. Please use THREE.CatmullRomCurve3' );
31181 this.points = ( points == undefined ) ? [] : points;
31187 var points = this.points;
31188 var point = ( points.length - 1 ) * t;
31190 var intPoint = Math.floor( point );
31191 var weight = point - intPoint;
31193 var point0 = points[ intPoint == 0 ? intPoint : intPoint - 1 ];
31194 var point1 = points[ intPoint ];
31195 var point2 = points[ intPoint > points.length - 2 ? points.length - 1 : intPoint + 1 ];
31196 var point3 = points[ intPoint > points.length - 3 ? points.length - 1 : intPoint + 2 ];
31198 var interpolate = THREE.CurveUtils.interpolate;
31200 return new THREE.Vector3(
31201 interpolate( point0.x, point1.x, point2.x, point3.x, weight ),
31202 interpolate( point0.y, point1.y, point2.y, point3.y, weight ),
31203 interpolate( point0.z, point1.z, point2.z, point3.z, weight )
31223 THREE.CatmullRomCurve3 = (
function() {
31226 tmp =
new THREE.Vector3(),
31227 px =
new CubicPoly(),
31228 py =
new CubicPoly(),
31229 pz =
new CubicPoly();
31241 function CubicPoly() {
31253 CubicPoly.prototype.init =
function( x0, x1, t0, t1 ) {
31257 this.c2 = - 3 * x0 + 3 * x1 - 2 * t0 - t1;
31258 this.c3 = 2 * x0 - 2 * x1 + t0 + t1;
31262 CubicPoly.prototype.initNonuniformCatmullRom =
function( x0, x1, x2, x3, dt0, dt1, dt2 ) {
31265 var t1 = ( x1 - x0 ) / dt0 - ( x2 - x0 ) / ( dt0 + dt1 ) + ( x2 - x1 ) / dt1;
31266 var t2 = ( x2 - x1 ) / dt1 - ( x3 - x1 ) / ( dt1 + dt2 ) + ( x3 - x2 ) / dt2;
31273 this.init( x1, x2, t1, t2 );
31278 CubicPoly.prototype.initCatmullRom =
function( x0, x1, x2, x3, tension ) {
31280 this.init( x1, x2, tension * ( x2 - x0 ), tension * ( x3 - x1 ) );
31284 CubicPoly.prototype.calc =
function( t ) {
31288 return this.c0 + this.c1 * t + this.c2 * t2 + this.c3 * t3;
31293 return THREE.Curve.create(
31297 this.points = p || [];
31303 var points = this.points,
31304 point, intPoint, weight, l;
31308 if ( l < 2 ) console.log(
'duh, you need at least 2 points' );
31310 point = ( l - 1 ) * t;
31311 intPoint = Math.floor( point );
31312 weight = point - intPoint;
31314 if ( weight === 0 && intPoint === l - 1 ) {
31321 var p0, p1, p2, p3;
31323 if ( intPoint === 0 ) {
31326 tmp.subVectors( points[ 0 ], points[ 1 ] ).add( points[ 0 ] );
31331 p0 = points[ intPoint - 1 ];
31335 p1 = points[ intPoint ];
31336 p2 = points[ intPoint + 1 ];
31338 if ( intPoint + 2 < l ) {
31340 p3 = points[ intPoint + 2 ]
31345 tmp.subVectors( points[ l - 1 ], points[ l - 2 ] ).add( points[ l - 2 ] );
31350 if ( this.type === undefined || this.type ===
'centripetal' || this.type ===
'chordal' ) {
31353 var pow = this.type ===
'chordal' ? 0.5 : 0.25;
31354 var dt0 = Math.pow( p0.distanceToSquared( p1 ), pow );
31355 var dt1 = Math.pow( p1.distanceToSquared( p2 ), pow );
31356 var dt2 = Math.pow( p2.distanceToSquared( p3 ), pow );
31359 if ( dt1 < 1e-4 ) dt1 = 1.0;
31360 if ( dt0 < 1e-4 ) dt0 = dt1;
31361 if ( dt2 < 1e-4 ) dt2 = dt1;
31363 px.initNonuniformCatmullRom( p0.x, p1.x, p2.x, p3.x, dt0, dt1, dt2 );
31364 py.initNonuniformCatmullRom( p0.y, p1.y, p2.y, p3.y, dt0, dt1, dt2 );
31365 pz.initNonuniformCatmullRom( p0.z, p1.z, p2.z, p3.z, dt0, dt1, dt2 );
31367 }
else if ( this.type ===
'catmullrom' ) {
31369 var tension = this.tension !== undefined ? this.tension : 0.5;
31370 px.initCatmullRom( p0.x, p1.x, p2.x, p3.x, tension );
31371 py.initCatmullRom( p0.y, p1.y, p2.y, p3.y, tension );
31372 pz.initCatmullRom( p0.z, p1.z, p2.z, p3.z, tension );
31376 var v =
new THREE.Vector3(
31397 THREE.ClosedSplineCurve3 = THREE.Curve.create(
31399 function ( points ) {
31401 this.points = ( points == undefined ) ? [] : points;
31407 var points = this.points;
31408 var point = ( points.length - 0 ) * t;
31410 var intPoint = Math.floor( point );
31411 var weight = point - intPoint;
31413 intPoint += intPoint > 0 ? 0 : ( Math.floor( Math.abs( intPoint ) / points.length ) + 1 ) * points.length;
31415 var point0 = points[ ( intPoint - 1 ) % points.length ];
31416 var point1 = points[ ( intPoint ) % points.length ];
31417 var point2 = points[ ( intPoint + 1 ) % points.length ];
31418 var point3 = points[ ( intPoint + 2 ) % points.length ];
31420 var interpolate = THREE.CurveUtils.interpolate;
31422 return new THREE.Vector3(
31423 interpolate( point0.x, point1.x, point2.x, point3.x, weight ),
31424 interpolate( point0.y, point1.y, point2.y, point3.y, weight ),
31425 interpolate( point0.z, point1.z, point2.z, point3.z, weight )
31439 THREE.BoxGeometry =
function ( width, height, depth, widthSegments, heightSegments, depthSegments ) {
31441 THREE.Geometry.call(
this );
31443 this.type =
'BoxGeometry';
31445 this.parameters = {
31449 widthSegments: widthSegments,
31450 heightSegments: heightSegments,
31451 depthSegments: depthSegments
31454 this.widthSegments = widthSegments || 1;
31455 this.heightSegments = heightSegments || 1;
31456 this.depthSegments = depthSegments || 1;
31460 var width_half = width / 2;
31461 var height_half = height / 2;
31462 var depth_half = depth / 2;
31464 buildPlane(
'z',
'y', - 1, - 1, depth, height, width_half, 0 );
31465 buildPlane(
'z',
'y', 1, - 1, depth, height, - width_half, 1 );
31466 buildPlane(
'x',
'z', 1, 1, width, depth, height_half, 2 );
31467 buildPlane(
'x',
'z', 1, - 1, width, depth, - height_half, 3 );
31468 buildPlane(
'x',
'y', 1, - 1, width, height, depth_half, 4 );
31469 buildPlane(
'x',
'y', - 1, - 1, width, height, - depth_half, 5 );
31471 function buildPlane( u, v, udir, vdir, width, height, depth, materialIndex ) {
31474 gridX = scope.widthSegments,
31475 gridY = scope.heightSegments,
31476 width_half = width / 2,
31477 height_half = height / 2,
31478 offset = scope.vertices.length;
31480 if ( ( u ===
'x' && v ===
'y' ) || ( u ===
'y' && v ===
'x' ) ) {
31484 }
else if ( ( u ===
'x' && v ===
'z' ) || ( u ===
'z' && v ===
'x' ) ) {
31487 gridY = scope.depthSegments;
31489 }
else if ( ( u ===
'z' && v ===
'y' ) || ( u ===
'y' && v ===
'z' ) ) {
31492 gridX = scope.depthSegments;
31496 var gridX1 = gridX + 1,
31497 gridY1 = gridY + 1,
31498 segment_width = width / gridX,
31499 segment_height = height / gridY,
31500 normal =
new THREE.Vector3();
31502 normal[ w ] = depth > 0 ? 1 : - 1;
31504 for ( iy = 0; iy < gridY1; iy ++ ) {
31506 for ( ix = 0; ix < gridX1; ix ++ ) {
31508 var vector =
new THREE.Vector3();
31509 vector[ u ] = ( ix * segment_width - width_half ) * udir;
31510 vector[ v ] = ( iy * segment_height - height_half ) * vdir;
31511 vector[ w ] = depth;
31513 scope.vertices.push( vector );
31519 for ( iy = 0; iy < gridY; iy ++ ) {
31521 for ( ix = 0; ix < gridX; ix ++ ) {
31523 var a = ix + gridX1 * iy;
31524 var b = ix + gridX1 * ( iy + 1 );
31525 var c = ( ix + 1 ) + gridX1 * ( iy + 1 );
31526 var d = ( ix + 1 ) + gridX1 * iy;
31528 var uva =
new THREE.Vector2( ix / gridX, 1 - iy / gridY );
31529 var uvb =
new THREE.Vector2( ix / gridX, 1 - ( iy + 1 ) / gridY );
31530 var uvc =
new THREE.Vector2( ( ix + 1 ) / gridX, 1 - ( iy + 1 ) / gridY );
31531 var uvd =
new THREE.Vector2( ( ix + 1 ) / gridX, 1 - iy / gridY );
31533 var face =
new THREE.Face3( a + offset, b + offset, d + offset );
31534 face.normal.copy( normal );
31535 face.vertexNormals.push( normal.clone(), normal.clone(), normal.clone() );
31536 face.materialIndex = materialIndex;
31538 scope.faces.push( face );
31539 scope.faceVertexUvs[ 0 ].push( [ uva, uvb, uvd ] );
31541 face =
new THREE.Face3( b + offset, c + offset, d + offset );
31542 face.normal.copy( normal );
31543 face.vertexNormals.push( normal.clone(), normal.clone(), normal.clone() );
31544 face.materialIndex = materialIndex;
31546 scope.faces.push( face );
31547 scope.faceVertexUvs[ 0 ].push( [ uvb.clone(), uvc, uvd.clone() ] );
31555 this.mergeVertices();
31559 THREE.BoxGeometry.prototype = Object.create( THREE.Geometry.prototype );
31560 THREE.BoxGeometry.prototype.constructor = THREE.BoxGeometry;
31562 THREE.BoxGeometry.prototype.clone =
function () {
31564 var parameters = this.parameters;
31566 return new THREE.BoxGeometry(
31570 parameters.widthSegments,
31571 parameters.heightSegments,
31572 parameters.depthSegments
31577 THREE.CubeGeometry = THREE.BoxGeometry;
31585 THREE.CircleGeometry =
function ( radius, segments, thetaStart, thetaLength ) {
31587 THREE.Geometry.call(
this );
31589 this.type =
'CircleGeometry';
31591 this.parameters = {
31593 segments: segments,
31594 thetaStart: thetaStart,
31595 thetaLength: thetaLength
31598 this.fromBufferGeometry(
new THREE.CircleBufferGeometry( radius, segments, thetaStart, thetaLength ) );
31602 THREE.CircleGeometry.prototype = Object.create( THREE.Geometry.prototype );
31603 THREE.CircleGeometry.prototype.constructor = THREE.CircleGeometry;
31605 THREE.CircleGeometry.prototype.clone =
function () {
31607 var parameters = this.parameters;
31609 return new THREE.CircleGeometry(
31611 parameters.segments,
31612 parameters.thetaStart,
31613 parameters.thetaLength
31624 THREE.CircleBufferGeometry =
function ( radius, segments, thetaStart, thetaLength ) {
31626 THREE.BufferGeometry.call(
this );
31628 this.type =
'CircleBufferGeometry';
31630 this.parameters = {
31632 segments: segments,
31633 thetaStart: thetaStart,
31634 thetaLength: thetaLength
31637 radius = radius || 50;
31638 segments = segments !== undefined ? Math.max( 3, segments ) : 8;
31640 thetaStart = thetaStart !== undefined ? thetaStart : 0;
31641 thetaLength = thetaLength !== undefined ? thetaLength : Math.PI * 2;
31643 var vertices = segments + 2;
31645 var positions =
new Float32Array( vertices * 3 );
31646 var normals =
new Float32Array( vertices * 3 );
31647 var uvs =
new Float32Array( vertices * 2 );
31650 normals[ 2 ] = 1.0;
31654 for ( var s = 0, i = 3, ii = 2 ; s <= segments; s ++, i += 3, ii += 2 ) {
31656 var segment = thetaStart + s / segments * thetaLength;
31658 positions[ i ] = radius * Math.cos( segment );
31659 positions[ i + 1 ] = radius * Math.sin( segment );
31661 normals[ i + 2 ] = 1;
31663 uvs[ ii ] = ( positions[ i ] / radius + 1 ) / 2;
31664 uvs[ ii + 1 ] = ( positions[ i + 1 ] / radius + 1 ) / 2;
31670 for ( var i = 1; i <= segments; i ++ ) {
31672 indices.push( i, i + 1, 0 );
31676 this.setIndex(
new THREE.BufferAttribute(
new Uint16Array( indices ), 1 ) );
31677 this.addAttribute(
'position',
new THREE.BufferAttribute( positions, 3 ) );
31678 this.addAttribute(
'normal',
new THREE.BufferAttribute( normals, 3 ) );
31679 this.addAttribute(
'uv',
new THREE.BufferAttribute( uvs, 2 ) );
31681 this.boundingSphere =
new THREE.Sphere(
new THREE.Vector3(), radius );
31685 THREE.CircleBufferGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
31686 THREE.CircleBufferGeometry.prototype.constructor = THREE.CircleBufferGeometry;
31688 THREE.CircleBufferGeometry.prototype.clone =
function () {
31690 var parameters = this.parameters;
31692 return new THREE.CircleBufferGeometry(
31694 parameters.segments,
31695 parameters.thetaStart,
31696 parameters.thetaLength
31707 THREE.CylinderGeometry =
function ( radiusTop, radiusBottom, height, radialSegments, heightSegments, openEnded, thetaStart, thetaLength ) {
31709 THREE.Geometry.call(
this );
31711 this.type =
'CylinderGeometry';
31713 this.parameters = {
31714 radiusTop: radiusTop,
31715 radiusBottom: radiusBottom,
31717 radialSegments: radialSegments,
31718 heightSegments: heightSegments,
31719 openEnded: openEnded,
31720 thetaStart: thetaStart,
31721 thetaLength: thetaLength
31724 radiusTop = radiusTop !== undefined ? radiusTop : 20;
31725 radiusBottom = radiusBottom !== undefined ? radiusBottom : 20;
31726 height = height !== undefined ? height : 100;
31728 radialSegments = radialSegments || 8;
31729 heightSegments = heightSegments || 1;
31731 openEnded = openEnded !== undefined ? openEnded :
false;
31732 thetaStart = thetaStart !== undefined ? thetaStart : 0;
31733 thetaLength = thetaLength !== undefined ? thetaLength : 2 * Math.PI;
31735 var heightHalf = height / 2;
31737 var x, y, vertices = [], uvs = [];
31739 for ( y = 0; y <= heightSegments; y ++ ) {
31741 var verticesRow = [];
31744 var v = y / heightSegments;
31745 var radius = v * ( radiusBottom - radiusTop ) + radiusTop;
31747 for ( x = 0; x <= radialSegments; x ++ ) {
31749 var u = x / radialSegments;
31751 var vertex =
new THREE.Vector3();
31752 vertex.x = radius * Math.sin( u * thetaLength + thetaStart );
31753 vertex.y = - v * height + heightHalf;
31754 vertex.z = radius * Math.cos( u * thetaLength + thetaStart );
31756 this.vertices.push( vertex );
31758 verticesRow.push( this.vertices.length - 1 );
31759 uvsRow.push(
new THREE.Vector2( u, 1 - v ) );
31763 vertices.push( verticesRow );
31764 uvs.push( uvsRow );
31768 var tanTheta = ( radiusBottom - radiusTop ) / height;
31771 for ( x = 0; x < radialSegments; x ++ ) {
31773 if ( radiusTop !== 0 ) {
31775 na = this.vertices[ vertices[ 0 ][ x ] ].clone();
31776 nb = this.vertices[ vertices[ 0 ][ x + 1 ] ].clone();
31780 na = this.vertices[ vertices[ 1 ][ x ] ].clone();
31781 nb = this.vertices[ vertices[ 1 ][ x + 1 ] ].clone();
31785 na.setY( Math.sqrt( na.x * na.x + na.z * na.z ) * tanTheta ).normalize();
31786 nb.setY( Math.sqrt( nb.x * nb.x + nb.z * nb.z ) * tanTheta ).normalize();
31788 for ( y = 0; y < heightSegments; y ++ ) {
31790 var v1 = vertices[ y ][ x ];
31791 var v2 = vertices[ y + 1 ][ x ];
31792 var v3 = vertices[ y + 1 ][ x + 1 ];
31793 var v4 = vertices[ y ][ x + 1 ];
31795 var n1 = na.clone();
31796 var n2 = na.clone();
31797 var n3 = nb.clone();
31798 var n4 = nb.clone();
31800 var uv1 = uvs[ y ][ x ].clone();
31801 var uv2 = uvs[ y + 1 ][ x ].clone();
31802 var uv3 = uvs[ y + 1 ][ x + 1 ].clone();
31803 var uv4 = uvs[ y ][ x + 1 ].clone();
31805 this.faces.push(
new THREE.Face3( v1, v2, v4, [ n1, n2, n4 ] ) );
31806 this.faceVertexUvs[ 0 ].push( [ uv1, uv2, uv4 ] );
31808 this.faces.push(
new THREE.Face3( v2, v3, v4, [ n2.clone(), n3, n4.clone() ] ) );
31809 this.faceVertexUvs[ 0 ].push( [ uv2.clone(), uv3, uv4.clone() ] );
31817 if ( openEnded ===
false && radiusTop > 0 ) {
31819 this.vertices.push(
new THREE.Vector3( 0, heightHalf, 0 ) );
31821 for ( x = 0; x < radialSegments; x ++ ) {
31823 var v1 = vertices[ 0 ][ x ];
31824 var v2 = vertices[ 0 ][ x + 1 ];
31825 var v3 = this.vertices.length - 1;
31827 var n1 =
new THREE.Vector3( 0, 1, 0 );
31828 var n2 =
new THREE.Vector3( 0, 1, 0 );
31829 var n3 =
new THREE.Vector3( 0, 1, 0 );
31831 var uv1 = uvs[ 0 ][ x ].clone();
31832 var uv2 = uvs[ 0 ][ x + 1 ].clone();
31833 var uv3 =
new THREE.Vector2( uv2.x, 0 );
31835 this.faces.push(
new THREE.Face3( v1, v2, v3, [ n1, n2, n3 ], undefined, 1 ) );
31836 this.faceVertexUvs[ 0 ].push( [ uv1, uv2, uv3 ] );
31844 if ( openEnded ===
false && radiusBottom > 0 ) {
31846 this.vertices.push(
new THREE.Vector3( 0, - heightHalf, 0 ) );
31848 for ( x = 0; x < radialSegments; x ++ ) {
31850 var v1 = vertices[ heightSegments ][ x + 1 ];
31851 var v2 = vertices[ heightSegments ][ x ];
31852 var v3 = this.vertices.length - 1;
31854 var n1 =
new THREE.Vector3( 0, - 1, 0 );
31855 var n2 =
new THREE.Vector3( 0, - 1, 0 );
31856 var n3 =
new THREE.Vector3( 0, - 1, 0 );
31858 var uv1 = uvs[ heightSegments ][ x + 1 ].clone();
31859 var uv2 = uvs[ heightSegments ][ x ].clone();
31860 var uv3 =
new THREE.Vector2( uv2.x, 1 );
31862 this.faces.push(
new THREE.Face3( v1, v2, v3, [ n1, n2, n3 ], undefined, 2 ) );
31863 this.faceVertexUvs[ 0 ].push( [ uv1, uv2, uv3 ] );
31869 this.computeFaceNormals();
31873 THREE.CylinderGeometry.prototype = Object.create( THREE.Geometry.prototype );
31874 THREE.CylinderGeometry.prototype.constructor = THREE.CylinderGeometry;
31876 THREE.CylinderGeometry.prototype.clone =
function () {
31878 var parameters = this.parameters;
31880 return new THREE.CylinderGeometry(
31881 parameters.radiusTop,
31882 parameters.radiusBottom,
31884 parameters.radialSegments,
31885 parameters.heightSegments,
31886 parameters.openEnded,
31887 parameters.thetaStart,
31888 parameters.thetaLength
31899 THREE.EdgesGeometry =
function ( geometry, thresholdAngle ) {
31901 THREE.BufferGeometry.call(
this );
31903 thresholdAngle = ( thresholdAngle !== undefined ) ? thresholdAngle : 1;
31905 var thresholdDot = Math.cos( THREE.Math.degToRad( thresholdAngle ) );
31907 var edge = [ 0, 0 ], hash = {};
31909 function sortFunction( a, b ) {
31915 var keys = [
'a',
'b',
'c' ];
31919 if ( geometry instanceof THREE.BufferGeometry ) {
31921 geometry2 =
new THREE.Geometry();
31922 geometry2.fromBufferGeometry( geometry );
31926 geometry2 = geometry.clone();
31930 geometry2.mergeVertices();
31931 geometry2.computeFaceNormals();
31933 var vertices = geometry2.vertices;
31934 var faces = geometry2.faces;
31936 for ( var i = 0, l = faces.length; i < l; i ++ ) {
31938 var face = faces[ i ];
31940 for ( var j = 0; j < 3; j ++ ) {
31942 edge[ 0 ] = face[ keys[ j ] ];
31943 edge[ 1 ] = face[ keys[ ( j + 1 ) % 3 ] ];
31944 edge.sort( sortFunction );
31946 var key = edge.toString();
31948 if ( hash[ key ] === undefined ) {
31950 hash[ key ] = { vert1: edge[ 0 ], vert2: edge[ 1 ], face1: i, face2: undefined };
31954 hash[ key ].face2 = i;
31964 for ( var key in hash ) {
31966 var h = hash[ key ];
31968 if ( h.face2 === undefined || faces[ h.face1 ].normal.dot( faces[ h.face2 ].normal ) <= thresholdDot ) {
31970 var vertex = vertices[ h.vert1 ];
31971 coords.push( vertex.x );
31972 coords.push( vertex.y );
31973 coords.push( vertex.z );
31975 vertex = vertices[ h.vert2 ];
31976 coords.push( vertex.x );
31977 coords.push( vertex.y );
31978 coords.push( vertex.z );
31984 this.addAttribute(
'position',
new THREE.BufferAttribute(
new Float32Array( coords ), 3 ) );
31988 THREE.EdgesGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
31989 THREE.EdgesGeometry.prototype.constructor = THREE.EdgesGeometry;
32017 THREE.ExtrudeGeometry =
function ( shapes, options ) {
32019 if ( typeof( shapes ) ===
"undefined" ) {
32026 THREE.Geometry.call(
this );
32028 this.type =
'ExtrudeGeometry';
32030 shapes = Array.isArray( shapes ) ? shapes : [ shapes ];
32032 this.addShapeList( shapes, options );
32034 this.computeFaceNormals();
32046 THREE.ExtrudeGeometry.prototype = Object.create( THREE.Geometry.prototype );
32047 THREE.ExtrudeGeometry.prototype.constructor = THREE.ExtrudeGeometry;
32049 THREE.ExtrudeGeometry.prototype.addShapeList =
function ( shapes, options ) {
32051 var sl = shapes.length;
32053 for ( var s = 0; s < sl; s ++ ) {
32055 var shape = shapes[ s ];
32056 this.addShape( shape, options );
32062 THREE.ExtrudeGeometry.prototype.addShape =
function ( shape, options ) {
32064 var amount = options.amount !== undefined ? options.amount : 100;
32066 var bevelThickness = options.bevelThickness !== undefined ? options.bevelThickness : 6;
32067 var bevelSize = options.bevelSize !== undefined ? options.bevelSize : bevelThickness - 2;
32068 var bevelSegments = options.bevelSegments !== undefined ? options.bevelSegments : 3;
32070 var bevelEnabled = options.bevelEnabled !== undefined ? options.bevelEnabled :
true;
32072 var curveSegments = options.curveSegments !== undefined ? options.curveSegments : 12;
32074 var steps = options.steps !== undefined ? options.steps : 1;
32076 var extrudePath = options.extrudePath;
32077 var extrudePts, extrudeByPath =
false;
32080 var uvgen = options.UVGenerator !== undefined ? options.UVGenerator : THREE.ExtrudeGeometry.WorldUVGenerator;
32082 var splineTube, binormal, normal, position2;
32083 if ( extrudePath ) {
32085 extrudePts = extrudePath.getSpacedPoints( steps );
32087 extrudeByPath =
true;
32088 bevelEnabled =
false;
32095 splineTube = options.frames !== undefined ? options.frames :
new THREE.TubeGeometry.FrenetFrames( extrudePath, steps,
false );
32099 binormal =
new THREE.Vector3();
32100 normal =
new THREE.Vector3();
32101 position2 =
new THREE.Vector3();
32107 if ( ! bevelEnabled ) {
32110 bevelThickness = 0;
32120 var shapesOffset = this.vertices.length;
32122 var shapePoints = shape.extractPoints( curveSegments );
32124 var vertices = shapePoints.shape;
32125 var holes = shapePoints.holes;
32127 var reverse = ! THREE.ShapeUtils.isClockWise( vertices );
32131 vertices = vertices.reverse();
32135 for ( h = 0, hl = holes.length; h < hl; h ++ ) {
32137 ahole = holes[ h ];
32139 if ( THREE.ShapeUtils.isClockWise( ahole ) ) {
32141 holes[ h ] = ahole.reverse();
32152 var faces = THREE.ShapeUtils.triangulateShape( vertices, holes );
32156 var contour = vertices;
32158 for ( h = 0, hl = holes.length; h < hl; h ++ ) {
32160 ahole = holes[ h ];
32162 vertices = vertices.concat( ahole );
32167 function scalePt2 ( pt, vec, size ) {
32169 if ( ! vec ) console.error(
"THREE.ExtrudeGeometry: vec does not exist" );
32171 return vec.clone().multiplyScalar( size ).add( pt );
32176 vert, vlen = vertices.length,
32177 face, flen = faces.length;
32183 function getBevelVec( inPt, inPrev, inNext ) {
32192 var v_trans_x, v_trans_y, shrink_by = 1;
32197 var v_prev_x = inPt.x - inPrev.x, v_prev_y = inPt.y - inPrev.y;
32198 var v_next_x = inNext.x - inPt.x, v_next_y = inNext.y - inPt.y;
32200 var v_prev_lensq = ( v_prev_x * v_prev_x + v_prev_y * v_prev_y );
32203 var collinear0 = ( v_prev_x * v_next_y - v_prev_y * v_next_x );
32205 if ( Math.abs( collinear0 ) > Number.EPSILON ) {
32211 var v_prev_len = Math.sqrt( v_prev_lensq );
32212 var v_next_len = Math.sqrt( v_next_x * v_next_x + v_next_y * v_next_y );
32216 var ptPrevShift_x = ( inPrev.x - v_prev_y / v_prev_len );
32217 var ptPrevShift_y = ( inPrev.y + v_prev_x / v_prev_len );
32219 var ptNextShift_x = ( inNext.x - v_next_y / v_next_len );
32220 var ptNextShift_y = ( inNext.y + v_next_x / v_next_len );
32224 var sf = ( ( ptNextShift_x - ptPrevShift_x ) * v_next_y -
32225 ( ptNextShift_y - ptPrevShift_y ) * v_next_x ) /
32226 ( v_prev_x * v_next_y - v_prev_y * v_next_x );
32230 v_trans_x = ( ptPrevShift_x + v_prev_x * sf - inPt.x );
32231 v_trans_y = ( ptPrevShift_y + v_prev_y * sf - inPt.y );
32235 var v_trans_lensq = ( v_trans_x * v_trans_x + v_trans_y * v_trans_y );
32236 if ( v_trans_lensq <= 2 ) {
32238 return new THREE.Vector2( v_trans_x, v_trans_y );
32242 shrink_by = Math.sqrt( v_trans_lensq / 2 );
32250 var direction_eq =
false;
32251 if ( v_prev_x > Number.EPSILON ) {
32253 if ( v_next_x > Number.EPSILON ) {
32255 direction_eq =
true;
32261 if ( v_prev_x < - Number.EPSILON ) {
32263 if ( v_next_x < - Number.EPSILON ) {
32265 direction_eq =
true;
32271 if ( Math.sign( v_prev_y ) === Math.sign( v_next_y ) ) {
32273 direction_eq =
true;
32281 if ( direction_eq ) {
32284 v_trans_x = - v_prev_y;
32285 v_trans_y = v_prev_x;
32286 shrink_by = Math.sqrt( v_prev_lensq );
32291 v_trans_x = v_prev_x;
32292 v_trans_y = v_prev_y;
32293 shrink_by = Math.sqrt( v_prev_lensq / 2 );
32299 return new THREE.Vector2( v_trans_x / shrink_by, v_trans_y / shrink_by );
32304 var contourMovements = [];
32306 for ( var i = 0, il = contour.length, j = il - 1, k = i + 1; i < il; i ++, j ++, k ++ ) {
32308 if ( j === il ) j = 0;
32309 if ( k === il ) k = 0;
32314 contourMovements[ i ] = getBevelVec( contour[ i ], contour[ j ], contour[ k ] );
32318 var holesMovements = [], oneHoleMovements, verticesMovements = contourMovements.concat();
32320 for ( h = 0, hl = holes.length; h < hl; h ++ ) {
32322 ahole = holes[ h ];
32324 oneHoleMovements = [];
32326 for ( i = 0, il = ahole.length, j = il - 1, k = i + 1; i < il; i ++, j ++, k ++ ) {
32328 if ( j === il ) j = 0;
32329 if ( k === il ) k = 0;
32332 oneHoleMovements[ i ] = getBevelVec( ahole[ i ], ahole[ j ], ahole[ k ] );
32336 holesMovements.push( oneHoleMovements );
32337 verticesMovements = verticesMovements.concat( oneHoleMovements );
32344 for ( b = 0; b < bevelSegments; b ++ ) {
32348 t = b / bevelSegments;
32349 z = bevelThickness * ( 1 - t );
32352 bs = bevelSize * ( Math.sin ( t * Math.PI / 2 ) );
32357 for ( i = 0, il = contour.length; i < il; i ++ ) {
32359 vert = scalePt2( contour[ i ], contourMovements[ i ], bs );
32361 v( vert.x, vert.y, - z );
32367 for ( h = 0, hl = holes.length; h < hl; h ++ ) {
32369 ahole = holes[ h ];
32370 oneHoleMovements = holesMovements[ h ];
32372 for ( i = 0, il = ahole.length; i < il; i ++ ) {
32374 vert = scalePt2( ahole[ i ], oneHoleMovements[ i ], bs );
32376 v( vert.x, vert.y, - z );
32388 for ( i = 0; i < vlen; i ++ ) {
32390 vert = bevelEnabled ? scalePt2( vertices[ i ], verticesMovements[ i ], bs ) : vertices[ i ];
32392 if ( ! extrudeByPath ) {
32394 v( vert.x, vert.y, 0 );
32400 normal.copy( splineTube.normals[ 0 ] ).multiplyScalar( vert.x );
32401 binormal.copy( splineTube.binormals[ 0 ] ).multiplyScalar( vert.y );
32403 position2.copy( extrudePts[ 0 ] ).add( normal ).add( binormal );
32405 v( position2.x, position2.y, position2.z );
32416 for ( s = 1; s <= steps; s ++ ) {
32418 for ( i = 0; i < vlen; i ++ ) {
32420 vert = bevelEnabled ? scalePt2( vertices[ i ], verticesMovements[ i ], bs ) : vertices[ i ];
32422 if ( ! extrudeByPath ) {
32424 v( vert.x, vert.y, amount / steps * s );
32430 normal.copy( splineTube.normals[ s ] ).multiplyScalar( vert.x );
32431 binormal.copy( splineTube.binormals[ s ] ).multiplyScalar( vert.y );
32433 position2.copy( extrudePts[ s ] ).add( normal ).add( binormal );
32435 v( position2.x, position2.y, position2.z );
32447 for ( b = bevelSegments - 1; b >= 0; b -- ) {
32449 t = b / bevelSegments;
32450 z = bevelThickness * ( 1 - t );
32452 bs = bevelSize * Math.sin ( t * Math.PI / 2 );
32456 for ( i = 0, il = contour.length; i < il; i ++ ) {
32458 vert = scalePt2( contour[ i ], contourMovements[ i ], bs );
32459 v( vert.x, vert.y, amount + z );
32465 for ( h = 0, hl = holes.length; h < hl; h ++ ) {
32467 ahole = holes[ h ];
32468 oneHoleMovements = holesMovements[ h ];
32470 for ( i = 0, il = ahole.length; i < il; i ++ ) {
32472 vert = scalePt2( ahole[ i ], oneHoleMovements[ i ], bs );
32474 if ( ! extrudeByPath ) {
32476 v( vert.x, vert.y, amount + z );
32480 v( vert.x, vert.y + extrudePts[ steps - 1 ].y, extrudePts[ steps - 1 ].x + z );
32503 function buildLidFaces() {
32505 if ( bevelEnabled ) {
32508 var offset = vlen * layer;
32512 for ( i = 0; i < flen; i ++ ) {
32515 f3( face[ 2 ] + offset, face[ 1 ] + offset, face[ 0 ] + offset );
32519 layer = steps + bevelSegments * 2;
32520 offset = vlen * layer;
32524 for ( i = 0; i < flen; i ++ ) {
32527 f3( face[ 0 ] + offset, face[ 1 ] + offset, face[ 2 ] + offset );
32535 for ( i = 0; i < flen; i ++ ) {
32538 f3( face[ 2 ], face[ 1 ], face[ 0 ] );
32544 for ( i = 0; i < flen; i ++ ) {
32547 f3( face[ 0 ] + vlen * steps, face[ 1 ] + vlen * steps, face[ 2 ] + vlen * steps );
32557 function buildSideFaces() {
32559 var layeroffset = 0;
32560 sidewalls( contour, layeroffset );
32561 layeroffset += contour.length;
32563 for ( h = 0, hl = holes.length; h < hl; h ++ ) {
32565 ahole = holes[ h ];
32566 sidewalls( ahole, layeroffset );
32569 layeroffset += ahole.length;
32575 function sidewalls( contour, layeroffset ) {
32578 i = contour.length;
32580 while ( -- i >= 0 ) {
32584 if ( k < 0 ) k = contour.length - 1;
32588 var s = 0, sl = steps + bevelSegments * 2;
32590 for ( s = 0; s < sl; s ++ ) {
32592 var slen1 = vlen * s;
32593 var slen2 = vlen * ( s + 1 );
32595 var a = layeroffset + j + slen1,
32596 b = layeroffset + k + slen1,
32597 c = layeroffset + k + slen2,
32598 d = layeroffset + j + slen2;
32600 f4( a, b, c, d, contour, s, sl, j, k );
32609 function v( x, y, z ) {
32611 scope.vertices.push(
new THREE.Vector3( x, y, z ) );
32615 function f3( a, b, c ) {
32621 scope.faces.push(
new THREE.Face3( a, b, c, null, null, 0 ) );
32623 var uvs = uvgen.generateTopUV( scope, a, b, c );
32625 scope.faceVertexUvs[ 0 ].push( uvs );
32629 function f4( a, b, c, d, wallContour, stepIndex, stepsLength, contourIndex1, contourIndex2 ) {
32636 scope.faces.push(
new THREE.Face3( a, b, d, null, null, 1 ) );
32637 scope.faces.push(
new THREE.Face3( b, c, d, null, null, 1 ) );
32639 var uvs = uvgen.generateSideWallUV( scope, a, b, c, d );
32641 scope.faceVertexUvs[ 0 ].push( [ uvs[ 0 ], uvs[ 1 ], uvs[ 3 ] ] );
32642 scope.faceVertexUvs[ 0 ].push( [ uvs[ 1 ], uvs[ 2 ], uvs[ 3 ] ] );
32648 THREE.ExtrudeGeometry.WorldUVGenerator = {
32650 generateTopUV:
function ( geometry, indexA, indexB, indexC ) {
32652 var vertices = geometry.vertices;
32654 var a = vertices[ indexA ];
32655 var b = vertices[ indexB ];
32656 var c = vertices[ indexC ];
32659 new THREE.Vector2( a.x, a.y ),
32660 new THREE.Vector2( b.x, b.y ),
32661 new THREE.Vector2( c.x, c.y )
32666 generateSideWallUV:
function ( geometry, indexA, indexB, indexC, indexD ) {
32668 var vertices = geometry.vertices;
32670 var a = vertices[ indexA ];
32671 var b = vertices[ indexB ];
32672 var c = vertices[ indexC ];
32673 var d = vertices[ indexD ];
32675 if ( Math.abs( a.y - b.y ) < 0.01 ) {
32678 new THREE.Vector2( a.x, 1 - a.z ),
32679 new THREE.Vector2( b.x, 1 - b.z ),
32680 new THREE.Vector2( c.x, 1 - c.z ),
32681 new THREE.Vector2( d.x, 1 - d.z )
32687 new THREE.Vector2( a.y, 1 - a.z ),
32688 new THREE.Vector2( b.y, 1 - b.z ),
32689 new THREE.Vector2( c.y, 1 - c.z ),
32690 new THREE.Vector2( d.y, 1 - d.z )
32716 THREE.ShapeGeometry =
function ( shapes, options ) {
32718 THREE.Geometry.call(
this );
32720 this.type =
'ShapeGeometry';
32722 if ( Array.isArray( shapes ) === false ) shapes = [ shapes ];
32724 this.addShapeList( shapes, options );
32726 this.computeFaceNormals();
32730 THREE.ShapeGeometry.prototype = Object.create( THREE.Geometry.prototype );
32731 THREE.ShapeGeometry.prototype.constructor = THREE.ShapeGeometry;
32736 THREE.ShapeGeometry.prototype.addShapeList =
function ( shapes, options ) {
32738 for ( var i = 0, l = shapes.length; i < l; i ++ ) {
32740 this.addShape( shapes[ i ], options );
32751 THREE.ShapeGeometry.prototype.addShape =
function ( shape, options ) {
32753 if ( options === undefined ) options = {};
32754 var curveSegments = options.curveSegments !== undefined ? options.curveSegments : 12;
32756 var material = options.material;
32757 var uvgen = options.UVGenerator === undefined ? THREE.ExtrudeGeometry.WorldUVGenerator : options.UVGenerator;
32763 var shapesOffset = this.vertices.length;
32764 var shapePoints = shape.extractPoints( curveSegments );
32766 var vertices = shapePoints.shape;
32767 var holes = shapePoints.holes;
32769 var reverse = ! THREE.ShapeUtils.isClockWise( vertices );
32773 vertices = vertices.reverse();
32777 for ( i = 0, l = holes.length; i < l; i ++ ) {
32781 if ( THREE.ShapeUtils.isClockWise( hole ) ) {
32783 holes[ i ] = hole.reverse();
32793 var faces = THREE.ShapeUtils.triangulateShape( vertices, holes );
32797 for ( i = 0, l = holes.length; i < l; i ++ ) {
32800 vertices = vertices.concat( hole );
32806 var vert, vlen = vertices.length;
32807 var face, flen = faces.length;
32809 for ( i = 0; i < vlen; i ++ ) {
32811 vert = vertices[ i ];
32813 this.vertices.push(
new THREE.Vector3( vert.x, vert.y, 0 ) );
32817 for ( i = 0; i < flen; i ++ ) {
32821 var a = face[ 0 ] + shapesOffset;
32822 var b = face[ 1 ] + shapesOffset;
32823 var c = face[ 2 ] + shapesOffset;
32825 this.faces.push(
new THREE.Face3( a, b, c, null, null, material ) );
32826 this.faceVertexUvs[ 0 ].push( uvgen.generateTopUV(
this, a, b, c ) );
32847 THREE.LatheGeometry =
function ( points, segments, phiStart, phiLength ) {
32849 THREE.Geometry.call(
this );
32851 this.type =
'LatheGeometry';
32853 this.parameters = {
32855 segments: segments,
32856 phiStart: phiStart,
32857 phiLength: phiLength
32860 segments = segments || 12;
32861 phiStart = phiStart || 0;
32862 phiLength = phiLength || 2 * Math.PI;
32864 var inversePointLength = 1.0 / ( points.length - 1 );
32865 var inverseSegments = 1.0 / segments;
32867 for ( var i = 0, il = segments; i <= il; i ++ ) {
32869 var phi = phiStart + i * inverseSegments * phiLength;
32871 var c = Math.cos( phi ),
32872 s = Math.sin( phi );
32874 for ( var j = 0, jl = points.length; j < jl; j ++ ) {
32876 var pt = points[ j ];
32878 var vertex =
new THREE.Vector3();
32880 vertex.x = c * pt.x - s * pt.y;
32881 vertex.y = s * pt.x + c * pt.y;
32884 this.vertices.push( vertex );
32890 var np = points.length;
32892 for ( var i = 0, il = segments; i < il; i ++ ) {
32894 for ( var j = 0, jl = points.length - 1; j < jl; j ++ ) {
32896 var base = j + np * i;
32899 var c = base + 1 + np;
32902 var u0 = i * inverseSegments;
32903 var v0 = j * inversePointLength;
32904 var u1 = u0 + inverseSegments;
32905 var v1 = v0 + inversePointLength;
32907 this.faces.push(
new THREE.Face3( a, b, d ) );
32909 this.faceVertexUvs[ 0 ].push( [
32911 new THREE.Vector2( u0, v0 ),
32912 new THREE.Vector2( u1, v0 ),
32913 new THREE.Vector2( u0, v1 )
32917 this.faces.push(
new THREE.Face3( b, c, d ) );
32919 this.faceVertexUvs[ 0 ].push( [
32921 new THREE.Vector2( u1, v0 ),
32922 new THREE.Vector2( u1, v1 ),
32923 new THREE.Vector2( u0, v1 )
32932 this.mergeVertices();
32933 this.computeFaceNormals();
32934 this.computeVertexNormals();
32938 THREE.LatheGeometry.prototype = Object.create( THREE.Geometry.prototype );
32939 THREE.LatheGeometry.prototype.constructor = THREE.LatheGeometry;
32948 THREE.PlaneGeometry =
function ( width, height, widthSegments, heightSegments ) {
32950 THREE.Geometry.call(
this );
32952 this.type =
'PlaneGeometry';
32954 this.parameters = {
32957 widthSegments: widthSegments,
32958 heightSegments: heightSegments
32961 this.fromBufferGeometry(
new THREE.PlaneBufferGeometry( width, height, widthSegments, heightSegments ) );
32965 THREE.PlaneGeometry.prototype = Object.create( THREE.Geometry.prototype );
32966 THREE.PlaneGeometry.prototype.constructor = THREE.PlaneGeometry;
32968 THREE.PlaneGeometry.prototype.clone =
function () {
32970 var parameters = this.parameters;
32972 return new THREE.PlaneGeometry(
32975 parameters.widthSegments,
32976 parameters.heightSegments
32988 THREE.PlaneBufferGeometry =
function ( width, height, widthSegments, heightSegments ) {
32990 THREE.BufferGeometry.call(
this );
32992 this.type =
'PlaneBufferGeometry';
32994 this.parameters = {
32997 widthSegments: widthSegments,
32998 heightSegments: heightSegments
33001 var width_half = width / 2;
33002 var height_half = height / 2;
33004 var gridX = Math.floor( widthSegments ) || 1;
33005 var gridY = Math.floor( heightSegments ) || 1;
33007 var gridX1 = gridX + 1;
33008 var gridY1 = gridY + 1;
33010 var segment_width = width / gridX;
33011 var segment_height = height / gridY;
33013 var vertices =
new Float32Array( gridX1 * gridY1 * 3 );
33014 var normals =
new Float32Array( gridX1 * gridY1 * 3 );
33015 var uvs =
new Float32Array( gridX1 * gridY1 * 2 );
33020 for ( var iy = 0; iy < gridY1; iy ++ ) {
33022 var y = iy * segment_height - height_half;
33024 for ( var ix = 0; ix < gridX1; ix ++ ) {
33026 var x = ix * segment_width - width_half;
33028 vertices[ offset ] = x;
33029 vertices[ offset + 1 ] = - y;
33031 normals[ offset + 2 ] = 1;
33033 uvs[ offset2 ] = ix / gridX;
33034 uvs[ offset2 + 1 ] = 1 - ( iy / gridY );
33045 var indices =
new ( ( vertices.length / 3 ) > 65535 ? Uint32Array : Uint16Array )( gridX * gridY * 6 );
33047 for ( var iy = 0; iy < gridY; iy ++ ) {
33049 for ( var ix = 0; ix < gridX; ix ++ ) {
33051 var a = ix + gridX1 * iy;
33052 var b = ix + gridX1 * ( iy + 1 );
33053 var c = ( ix + 1 ) + gridX1 * ( iy + 1 );
33054 var d = ( ix + 1 ) + gridX1 * iy;
33056 indices[ offset ] = a;
33057 indices[ offset + 1 ] = b;
33058 indices[ offset + 2 ] = d;
33060 indices[ offset + 3 ] = b;
33061 indices[ offset + 4 ] = c;
33062 indices[ offset + 5 ] = d;
33070 this.setIndex(
new THREE.BufferAttribute( indices, 1 ) );
33071 this.addAttribute(
'position',
new THREE.BufferAttribute( vertices, 3 ) );
33072 this.addAttribute(
'normal',
new THREE.BufferAttribute( normals, 3 ) );
33073 this.addAttribute(
'uv',
new THREE.BufferAttribute( uvs, 2 ) );
33077 THREE.PlaneBufferGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
33078 THREE.PlaneBufferGeometry.prototype.constructor = THREE.PlaneBufferGeometry;
33080 THREE.PlaneBufferGeometry.prototype.clone =
function () {
33082 var parameters = this.parameters;
33084 return new THREE.PlaneBufferGeometry(
33087 parameters.widthSegments,
33088 parameters.heightSegments
33099 THREE.RingGeometry =
function ( innerRadius, outerRadius, thetaSegments, phiSegments, thetaStart, thetaLength ) {
33101 THREE.Geometry.call(
this );
33103 this.type =
'RingGeometry';
33105 this.parameters = {
33106 innerRadius: innerRadius,
33107 outerRadius: outerRadius,
33108 thetaSegments: thetaSegments,
33109 phiSegments: phiSegments,
33110 thetaStart: thetaStart,
33111 thetaLength: thetaLength
33114 innerRadius = innerRadius || 0;
33115 outerRadius = outerRadius || 50;
33117 thetaStart = thetaStart !== undefined ? thetaStart : 0;
33118 thetaLength = thetaLength !== undefined ? thetaLength : Math.PI * 2;
33120 thetaSegments = thetaSegments !== undefined ? Math.max( 3, thetaSegments ) : 8;
33121 phiSegments = phiSegments !== undefined ? Math.max( 1, phiSegments ) : 8;
33123 var i, o, uvs = [], radius = innerRadius, radiusStep = ( ( outerRadius - innerRadius ) / phiSegments );
33125 for ( i = 0; i < phiSegments + 1; i ++ ) {
33129 for ( o = 0; o < thetaSegments + 1; o ++ ) {
33133 var vertex =
new THREE.Vector3();
33134 var segment = thetaStart + o / thetaSegments * thetaLength;
33135 vertex.x = radius * Math.cos( segment );
33136 vertex.y = radius * Math.sin( segment );
33138 this.vertices.push( vertex );
33139 uvs.push(
new THREE.Vector2( ( vertex.x / outerRadius + 1 ) / 2, ( vertex.y / outerRadius + 1 ) / 2 ) );
33143 radius += radiusStep;
33147 var n =
new THREE.Vector3( 0, 0, 1 );
33149 for ( i = 0; i < phiSegments; i ++ ) {
33153 var thetaSegment = i * ( thetaSegments + 1 );
33155 for ( o = 0; o < thetaSegments ; o ++ ) {
33159 var segment = o + thetaSegment;
33162 var v2 = segment + thetaSegments + 1;
33163 var v3 = segment + thetaSegments + 2;
33165 this.faces.push(
new THREE.Face3( v1, v2, v3, [ n.clone(), n.clone(), n.clone() ] ) );
33166 this.faceVertexUvs[ 0 ].push( [ uvs[ v1 ].clone(), uvs[ v2 ].clone(), uvs[ v3 ].clone() ] );
33169 v2 = segment + thetaSegments + 2;
33172 this.faces.push(
new THREE.Face3( v1, v2, v3, [ n.clone(), n.clone(), n.clone() ] ) );
33173 this.faceVertexUvs[ 0 ].push( [ uvs[ v1 ].clone(), uvs[ v2 ].clone(), uvs[ v3 ].clone() ] );
33179 this.computeFaceNormals();
33181 this.boundingSphere =
new THREE.Sphere(
new THREE.Vector3(), radius );
33185 THREE.RingGeometry.prototype = Object.create( THREE.Geometry.prototype );
33186 THREE.RingGeometry.prototype.constructor = THREE.RingGeometry;
33188 THREE.RingGeometry.prototype.clone =
function () {
33190 var parameters = this.parameters;
33192 return new THREE.RingGeometry(
33193 parameters.innerRadius,
33194 parameters.outerRadius,
33195 parameters.thetaSegments,
33196 parameters.phiSegments,
33197 parameters.thetaStart,
33198 parameters.thetaLength
33209 THREE.SphereGeometry =
function ( radius, widthSegments, heightSegments, phiStart, phiLength, thetaStart, thetaLength ) {
33211 THREE.Geometry.call(
this );
33213 this.type =
'SphereGeometry';
33215 this.parameters = {
33217 widthSegments: widthSegments,
33218 heightSegments: heightSegments,
33219 phiStart: phiStart,
33220 phiLength: phiLength,
33221 thetaStart: thetaStart,
33222 thetaLength: thetaLength
33225 this.fromBufferGeometry(
new THREE.SphereBufferGeometry( radius, widthSegments, heightSegments, phiStart, phiLength, thetaStart, thetaLength ) );
33229 THREE.SphereGeometry.prototype = Object.create( THREE.Geometry.prototype );
33230 THREE.SphereGeometry.prototype.constructor = THREE.SphereGeometry;
33232 THREE.SphereGeometry.prototype.clone =
function () {
33234 var parameters = this.parameters;
33236 return new THREE.SphereGeometry(
33238 parameters.widthSegments,
33239 parameters.heightSegments,
33240 parameters.phiStart,
33241 parameters.phiLength,
33242 parameters.thetaStart,
33243 parameters.thetaLength
33255 THREE.SphereBufferGeometry =
function ( radius, widthSegments, heightSegments, phiStart, phiLength, thetaStart, thetaLength ) {
33257 THREE.BufferGeometry.call(
this );
33259 this.type =
'SphereBufferGeometry';
33261 this.parameters = {
33263 widthSegments: widthSegments,
33264 heightSegments: heightSegments,
33265 phiStart: phiStart,
33266 phiLength: phiLength,
33267 thetaStart: thetaStart,
33268 thetaLength: thetaLength
33271 radius = radius || 50;
33273 widthSegments = Math.max( 3, Math.floor( widthSegments ) || 8 );
33274 heightSegments = Math.max( 2, Math.floor( heightSegments ) || 6 );
33276 phiStart = phiStart !== undefined ? phiStart : 0;
33277 phiLength = phiLength !== undefined ? phiLength : Math.PI * 2;
33279 thetaStart = thetaStart !== undefined ? thetaStart : 0;
33280 thetaLength = thetaLength !== undefined ? thetaLength : Math.PI;
33282 var thetaEnd = thetaStart + thetaLength;
33284 var vertexCount = ( ( widthSegments + 1 ) * ( heightSegments + 1 ) );
33286 var positions =
new THREE.BufferAttribute(
new Float32Array( vertexCount * 3 ), 3 );
33287 var normals =
new THREE.BufferAttribute(
new Float32Array( vertexCount * 3 ), 3 );
33288 var uvs =
new THREE.BufferAttribute(
new Float32Array( vertexCount * 2 ), 2 );
33290 var index = 0, vertices = [], normal =
new THREE.Vector3();
33292 for ( var y = 0; y <= heightSegments; y ++ ) {
33294 var verticesRow = [];
33296 var v = y / heightSegments;
33298 for ( var x = 0; x <= widthSegments; x ++ ) {
33300 var u = x / widthSegments;
33302 var px = - radius * Math.cos( phiStart + u * phiLength ) * Math.sin( thetaStart + v * thetaLength );
33303 var py = radius * Math.cos( thetaStart + v * thetaLength );
33304 var pz = radius * Math.sin( phiStart + u * phiLength ) * Math.sin( thetaStart + v * thetaLength );
33306 normal.set( px, py, pz ).normalize();
33308 positions.setXYZ( index, px, py, pz );
33309 normals.setXYZ( index, normal.x, normal.y, normal.z );
33310 uvs.setXY( index, u, 1 - v );
33312 verticesRow.push( index );
33318 vertices.push( verticesRow );
33324 for ( var y = 0; y < heightSegments; y ++ ) {
33326 for ( var x = 0; x < widthSegments; x ++ ) {
33328 var v1 = vertices[ y ][ x + 1 ];
33329 var v2 = vertices[ y ][ x ];
33330 var v3 = vertices[ y + 1 ][ x ];
33331 var v4 = vertices[ y + 1 ][ x + 1 ];
33333 if ( y !== 0 || thetaStart > 0 ) indices.push( v1, v2, v4 );
33334 if ( y !== heightSegments - 1 || thetaEnd < Math.PI ) indices.push( v2, v3, v4 );
33340 this.setIndex(
new ( positions.count > 65535 ? THREE.Uint32Attribute : THREE.Uint16Attribute )( indices, 1 ) );
33341 this.addAttribute(
'position', positions );
33342 this.addAttribute(
'normal', normals );
33343 this.addAttribute(
'uv', uvs );
33345 this.boundingSphere =
new THREE.Sphere(
new THREE.Vector3(), radius );
33349 THREE.SphereBufferGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
33350 THREE.SphereBufferGeometry.prototype.constructor = THREE.SphereBufferGeometry;
33352 THREE.SphereBufferGeometry.prototype.clone =
function () {
33354 var parameters = this.parameters;
33356 return new THREE.SphereBufferGeometry(
33358 parameters.widthSegments,
33359 parameters.heightSegments,
33360 parameters.phiStart,
33361 parameters.phiLength,
33362 parameters.thetaStart,
33363 parameters.thetaLength
33376 THREE.TorusGeometry =
function ( radius, tube, radialSegments, tubularSegments, arc ) {
33378 THREE.Geometry.call(
this );
33380 this.type =
'TorusGeometry';
33382 this.parameters = {
33385 radialSegments: radialSegments,
33386 tubularSegments: tubularSegments,
33390 radius = radius || 100;
33392 radialSegments = radialSegments || 8;
33393 tubularSegments = tubularSegments || 6;
33394 arc = arc || Math.PI * 2;
33396 var center =
new THREE.Vector3(), uvs = [], normals = [];
33398 for ( var j = 0; j <= radialSegments; j ++ ) {
33400 for ( var i = 0; i <= tubularSegments; i ++ ) {
33402 var u = i / tubularSegments * arc;
33403 var v = j / radialSegments * Math.PI * 2;
33405 center.x = radius * Math.cos( u );
33406 center.y = radius * Math.sin( u );
33408 var vertex =
new THREE.Vector3();
33409 vertex.x = ( radius + tube * Math.cos( v ) ) * Math.cos( u );
33410 vertex.y = ( radius + tube * Math.cos( v ) ) * Math.sin( u );
33411 vertex.z = tube * Math.sin( v );
33413 this.vertices.push( vertex );
33415 uvs.push(
new THREE.Vector2( i / tubularSegments, j / radialSegments ) );
33416 normals.push( vertex.clone().sub( center ).normalize() );
33422 for ( var j = 1; j <= radialSegments; j ++ ) {
33424 for ( var i = 1; i <= tubularSegments; i ++ ) {
33426 var a = ( tubularSegments + 1 ) * j + i - 1;
33427 var b = ( tubularSegments + 1 ) * ( j - 1 ) + i - 1;
33428 var c = ( tubularSegments + 1 ) * ( j - 1 ) + i;
33429 var d = ( tubularSegments + 1 ) * j + i;
33431 var face =
new THREE.Face3( a, b, d, [ normals[ a ].clone(), normals[ b ].clone(), normals[ d ].clone() ] );
33432 this.faces.push( face );
33433 this.faceVertexUvs[ 0 ].push( [ uvs[ a ].clone(), uvs[ b ].clone(), uvs[ d ].clone() ] );
33435 face =
new THREE.Face3( b, c, d, [ normals[ b ].clone(), normals[ c ].clone(), normals[ d ].clone() ] );
33436 this.faces.push( face );
33437 this.faceVertexUvs[ 0 ].push( [ uvs[ b ].clone(), uvs[ c ].clone(), uvs[ d ].clone() ] );
33443 this.computeFaceNormals();
33447 THREE.TorusGeometry.prototype = Object.create( THREE.Geometry.prototype );
33448 THREE.TorusGeometry.prototype.constructor = THREE.TorusGeometry;
33450 THREE.TorusGeometry.prototype.clone =
function () {
33452 var parameters = this.parameters;
33454 return new THREE.TorusGeometry(
33457 parameters.radialSegments,
33458 parameters.tubularSegments,
33471 THREE.TorusKnotGeometry =
function ( radius, tube, radialSegments, tubularSegments, p, q, heightScale ) {
33473 THREE.Geometry.call(
this );
33475 this.type =
'TorusKnotGeometry';
33477 this.parameters = {
33480 radialSegments: radialSegments,
33481 tubularSegments: tubularSegments,
33484 heightScale: heightScale
33487 radius = radius || 100;
33489 radialSegments = radialSegments || 64;
33490 tubularSegments = tubularSegments || 8;
33493 heightScale = heightScale || 1;
33495 var grid =
new Array( radialSegments );
33496 var tang =
new THREE.Vector3();
33497 var n =
new THREE.Vector3();
33498 var bitan =
new THREE.Vector3();
33500 for ( var i = 0; i < radialSegments; ++ i ) {
33502 grid[ i ] =
new Array( tubularSegments );
33503 var u = i / radialSegments * 2 * p * Math.PI;
33504 var p1 = getPos( u, q, p, radius, heightScale );
33505 var p2 = getPos( u + 0.01, q, p, radius, heightScale );
33506 tang.subVectors( p2, p1 );
33507 n.addVectors( p2, p1 );
33509 bitan.crossVectors( tang, n );
33510 n.crossVectors( bitan, tang );
33514 for ( var j = 0; j < tubularSegments; ++ j ) {
33516 var v = j / tubularSegments * 2 * Math.PI;
33517 var cx = - tube * Math.cos( v );
33518 var cy = tube * Math.sin( v );
33520 var pos =
new THREE.Vector3();
33521 pos.x = p1.x + cx * n.x + cy * bitan.x;
33522 pos.y = p1.y + cx * n.y + cy * bitan.y;
33523 pos.z = p1.z + cx * n.z + cy * bitan.z;
33525 grid[ i ][ j ] = this.vertices.push( pos ) - 1;
33531 for ( var i = 0; i < radialSegments; ++ i ) {
33533 for ( var j = 0; j < tubularSegments; ++ j ) {
33535 var ip = ( i + 1 ) % radialSegments;
33536 var jp = ( j + 1 ) % tubularSegments;
33538 var a = grid[ i ][ j ];
33539 var b = grid[ ip ][ j ];
33540 var c = grid[ ip ][ jp ];
33541 var d = grid[ i ][ jp ];
33543 var uva =
new THREE.Vector2( i / radialSegments, j / tubularSegments );
33544 var uvb =
new THREE.Vector2( ( i + 1 ) / radialSegments, j / tubularSegments );
33545 var uvc =
new THREE.Vector2( ( i + 1 ) / radialSegments, ( j + 1 ) / tubularSegments );
33546 var uvd =
new THREE.Vector2( i / radialSegments, ( j + 1 ) / tubularSegments );
33548 this.faces.push(
new THREE.Face3( a, b, d ) );
33549 this.faceVertexUvs[ 0 ].push( [ uva, uvb, uvd ] );
33551 this.faces.push(
new THREE.Face3( b, c, d ) );
33552 this.faceVertexUvs[ 0 ].push( [ uvb.clone(), uvc, uvd.clone() ] );
33558 this.computeFaceNormals();
33559 this.computeVertexNormals();
33561 function getPos( u, in_q, in_p, radius, heightScale ) {
33563 var cu = Math.cos( u );
33564 var su = Math.sin( u );
33565 var quOverP = in_q / in_p * u;
33566 var cs = Math.cos( quOverP );
33568 var tx = radius * ( 2 + cs ) * 0.5 * cu;
33569 var ty = radius * ( 2 + cs ) * su * 0.5;
33570 var tz = heightScale * radius * Math.sin( quOverP ) * 0.5;
33572 return new THREE.Vector3( tx, ty, tz );
33578 THREE.TorusKnotGeometry.prototype = Object.create( THREE.Geometry.prototype );
33579 THREE.TorusKnotGeometry.prototype.constructor = THREE.TorusKnotGeometry;
33581 THREE.TorusKnotGeometry.prototype.clone =
function () {
33583 var parameters = this.parameters;
33585 return new THREE.TorusKnotGeometry(
33588 parameters.radialSegments,
33589 parameters.tubularSegments,
33592 parameters.heightScale
33613 THREE.TubeGeometry =
function ( path, segments, radius, radialSegments, closed, taper ) {
33615 THREE.Geometry.call(
this );
33617 this.type =
'TubeGeometry';
33619 this.parameters = {
33621 segments: segments,
33623 radialSegments: radialSegments,
33628 segments = segments || 64;
33629 radius = radius || 1;
33630 radialSegments = radialSegments || 8;
33631 closed = closed ||
false;
33632 taper = taper || THREE.TubeGeometry.NoTaper;
33642 numpoints = segments + 1,
33647 pos, pos2 =
new THREE.Vector3(),
33651 uva, uvb, uvc, uvd;
33653 var frames =
new THREE.TubeGeometry.FrenetFrames( path, segments, closed ),
33654 tangents = frames.tangents,
33655 normals = frames.normals,
33656 binormals = frames.binormals;
33659 this.tangents = tangents;
33660 this.normals = normals;
33661 this.binormals = binormals;
33663 function vert( x, y, z ) {
33665 return scope.vertices.push(
new THREE.Vector3( x, y, z ) ) - 1;
33671 for ( i = 0; i < numpoints; i ++ ) {
33675 u = i / ( numpoints - 1 );
33677 pos = path.getPointAt( u );
33679 tangent = tangents[ i ];
33680 normal = normals[ i ];
33681 binormal = binormals[ i ];
33683 r = radius * taper( u );
33685 for ( j = 0; j < radialSegments; j ++ ) {
33687 v = j / radialSegments * 2 * Math.PI;
33689 cx = - r * Math.cos( v );
33690 cy = r * Math.sin( v );
33693 pos2.x += cx * normal.x + cy * binormal.x;
33694 pos2.y += cx * normal.y + cy * binormal.y;
33695 pos2.z += cx * normal.z + cy * binormal.z;
33697 grid[ i ][ j ] = vert( pos2.x, pos2.y, pos2.z );
33706 for ( i = 0; i < segments; i ++ ) {
33708 for ( j = 0; j < radialSegments; j ++ ) {
33710 ip = ( closed ) ? ( i + 1 ) % segments : i + 1;
33711 jp = ( j + 1 ) % radialSegments;
33713 a = grid[ i ][ j ];
33714 b = grid[ ip ][ j ];
33715 c = grid[ ip ][ jp ];
33716 d = grid[ i ][ jp ];
33718 uva =
new THREE.Vector2( i / segments, j / radialSegments );
33719 uvb =
new THREE.Vector2( ( i + 1 ) / segments, j / radialSegments );
33720 uvc =
new THREE.Vector2( ( i + 1 ) / segments, ( j + 1 ) / radialSegments );
33721 uvd =
new THREE.Vector2( i / segments, ( j + 1 ) / radialSegments );
33723 this.faces.push(
new THREE.Face3( a, b, d ) );
33724 this.faceVertexUvs[ 0 ].push( [ uva, uvb, uvd ] );
33726 this.faces.push(
new THREE.Face3( b, c, d ) );
33727 this.faceVertexUvs[ 0 ].push( [ uvb.clone(), uvc, uvd.clone() ] );
33733 this.computeFaceNormals();
33734 this.computeVertexNormals();
33738 THREE.TubeGeometry.prototype = Object.create( THREE.Geometry.prototype );
33739 THREE.TubeGeometry.prototype.constructor = THREE.TubeGeometry;
33740 THREE.TubeGeometry.prototype.clone =
function() {
33742 return new this.constructor( this.parameters.path,
33743 this.parameters.segments,
this.parameters.radius,
this.parameters.radialSegments,
33744 this.parameters.closed,
this.parameters.taper
33749 THREE.TubeGeometry.NoTaper =
function ( u ) {
33755 THREE.TubeGeometry.SinusoidalTaper =
function ( u ) {
33757 return Math.sin( Math.PI * u );
33762 THREE.TubeGeometry.FrenetFrames =
function ( path, segments, closed ) {
33764 var normal =
new THREE.Vector3(),
33770 vec =
new THREE.Vector3(),
33771 mat =
new THREE.Matrix4(),
33773 numpoints = segments + 1,
33782 this.tangents = tangents;
33783 this.normals = normals;
33784 this.binormals = binormals;
33788 for ( i = 0; i < numpoints; i ++ ) {
33790 u = i / ( numpoints - 1 );
33792 tangents[ i ] = path.getTangentAt( u );
33793 tangents[ i ].normalize();
33823 function initialNormal3() {
33828 normals[ 0 ] =
new THREE.Vector3();
33829 binormals[ 0 ] =
new THREE.Vector3();
33830 smallest = Number.MAX_VALUE;
33831 tx = Math.abs( tangents[ 0 ].x );
33832 ty = Math.abs( tangents[ 0 ].y );
33833 tz = Math.abs( tangents[ 0 ].z );
33835 if ( tx <= smallest ) {
33838 normal.set( 1, 0, 0 );
33842 if ( ty <= smallest ) {
33845 normal.set( 0, 1, 0 );
33849 if ( tz <= smallest ) {
33851 normal.set( 0, 0, 1 );
33855 vec.crossVectors( tangents[ 0 ], normal ).normalize();
33857 normals[ 0 ].crossVectors( tangents[ 0 ], vec );
33858 binormals[ 0 ].crossVectors( tangents[ 0 ], normals[ 0 ] );
33865 for ( i = 1; i < numpoints; i ++ ) {
33867 normals[ i ] = normals[ i - 1 ].clone();
33869 binormals[ i ] = binormals[ i - 1 ].clone();
33871 vec.crossVectors( tangents[ i - 1 ], tangents[ i ] );
33873 if ( vec.length() > Number.EPSILON ) {
33877 theta = Math.acos( THREE.Math.clamp( tangents[ i - 1 ].dot( tangents[ i ] ), - 1, 1 ) );
33879 normals[ i ].applyMatrix4( mat.makeRotationAxis( vec, theta ) );
33883 binormals[ i ].crossVectors( tangents[ i ], normals[ i ] );
33892 theta = Math.acos( THREE.Math.clamp( normals[ 0 ].dot( normals[ numpoints - 1 ] ), - 1, 1 ) );
33893 theta /= ( numpoints - 1 );
33895 if ( tangents[ 0 ].dot( vec.crossVectors( normals[ 0 ], normals[ numpoints - 1 ] ) ) > 0 ) {
33901 for ( i = 1; i < numpoints; i ++ ) {
33904 normals[ i ].applyMatrix4( mat.makeRotationAxis( tangents[ i ], theta * i ) );
33905 binormals[ i ].crossVectors( tangents[ i ], normals[ i ] );
33921 THREE.PolyhedronGeometry =
function ( vertices, indices, radius, detail ) {
33923 THREE.Geometry.call(
this );
33925 this.type =
'PolyhedronGeometry';
33927 this.parameters = {
33928 vertices: vertices,
33934 radius = radius || 1;
33935 detail = detail || 0;
33939 for ( var i = 0, l = vertices.length; i < l; i += 3 ) {
33941 prepare(
new THREE.Vector3( vertices[ i ], vertices[ i + 1 ], vertices[ i + 2 ] ) );
33945 var p = this.vertices;
33949 for ( var i = 0, j = 0, l = indices.length; i < l; i += 3, j ++ ) {
33951 var v1 = p[ indices[ i ] ];
33952 var v2 = p[ indices[ i + 1 ] ];
33953 var v3 = p[ indices[ i + 2 ] ];
33955 faces[ j ] =
new THREE.Face3( v1.index, v2.index, v3.index, [ v1.clone(), v2.clone(), v3.clone() ], undefined, j );
33959 var centroid =
new THREE.Vector3();
33961 for ( var i = 0, l = faces.length; i < l; i ++ ) {
33963 subdivide( faces[ i ], detail );
33970 for ( var i = 0, l = this.faceVertexUvs[ 0 ].length; i < l; i ++ ) {
33972 var uvs = this.faceVertexUvs[ 0 ][ i ];
33974 var x0 = uvs[ 0 ].x;
33975 var x1 = uvs[ 1 ].x;
33976 var x2 = uvs[ 2 ].x;
33978 var max = Math.max( x0, x1, x2 );
33979 var min = Math.min( x0, x1, x2 );
33981 if ( max > 0.9 && min < 0.1 ) {
33985 if ( x0 < 0.2 ) uvs[ 0 ].x += 1;
33986 if ( x1 < 0.2 ) uvs[ 1 ].x += 1;
33987 if ( x2 < 0.2 ) uvs[ 2 ].x += 1;
33996 for ( var i = 0, l = this.vertices.length; i < l; i ++ ) {
33998 this.vertices[ i ].multiplyScalar( radius );
34005 this.mergeVertices();
34007 this.computeFaceNormals();
34009 this.boundingSphere =
new THREE.Sphere(
new THREE.Vector3(), radius );
34014 function prepare( vector ) {
34016 var vertex = vector.normalize().clone();
34017 vertex.index = that.vertices.push( vertex ) - 1;
34021 var u = azimuth( vector ) / 2 / Math.PI + 0.5;
34022 var v = inclination( vector ) / Math.PI + 0.5;
34023 vertex.uv =
new THREE.Vector2( u, 1 - v );
34032 function make( v1, v2, v3, materialIndex ) {
34034 var face =
new THREE.Face3( v1.index, v2.index, v3.index, [ v1.clone(), v2.clone(), v3.clone() ], undefined, materialIndex );
34035 that.faces.push( face );
34037 centroid.copy( v1 ).add( v2 ).add( v3 ).divideScalar( 3 );
34039 var azi = azimuth( centroid );
34041 that.faceVertexUvs[ 0 ].push( [
34042 correctUV( v1.uv, v1, azi ),
34043 correctUV( v2.uv, v2, azi ),
34044 correctUV( v3.uv, v3, azi )
34052 function subdivide( face, detail ) {
34054 var cols = Math.pow( 2, detail );
34055 var a = prepare( that.vertices[ face.a ] );
34056 var b = prepare( that.vertices[ face.b ] );
34057 var c = prepare( that.vertices[ face.c ] );
34060 var materialIndex = face.materialIndex;
34064 for ( var i = 0 ; i <= cols; i ++ ) {
34068 var aj = prepare( a.clone().lerp( c, i / cols ) );
34069 var bj = prepare( b.clone().lerp( c, i / cols ) );
34070 var rows = cols - i;
34072 for ( var j = 0; j <= rows; j ++ ) {
34074 if ( j === 0 && i === cols ) {
34080 v[ i ][ j ] = prepare( aj.clone().lerp( bj, j / rows ) );
34090 for ( var i = 0; i < cols ; i ++ ) {
34092 for ( var j = 0; j < 2 * ( cols - i ) - 1; j ++ ) {
34094 var k = Math.floor( j / 2 );
34096 if ( j % 2 === 0 ) {
34109 v[ i + 1 ][ k + 1 ],
34125 function azimuth( vector ) {
34127 return Math.atan2( vector.z, - vector.x );
34134 function inclination( vector ) {
34136 return Math.atan2( - vector.y, Math.sqrt( ( vector.x * vector.x ) + ( vector.z * vector.z ) ) );
34143 function correctUV( uv, vector, azimuth ) {
34145 if ( ( azimuth < 0 ) && ( uv.x === 1 ) ) uv =
new THREE.Vector2( uv.x - 1, uv.y );
34146 if ( ( vector.x === 0 ) && ( vector.z === 0 ) ) uv =
new THREE.Vector2( azimuth / 2 / Math.PI + 0.5, uv.y );
34154 THREE.PolyhedronGeometry.prototype = Object.create( THREE.Geometry.prototype );
34155 THREE.PolyhedronGeometry.prototype.constructor = THREE.PolyhedronGeometry;
34157 THREE.PolyhedronGeometry.prototype.clone =
function () {
34159 var parameters = this.parameters;
34161 return new THREE.PolyhedronGeometry(
34162 parameters.vertices,
34163 parameters.indices,
34176 THREE.DodecahedronGeometry =
function ( radius, detail ) {
34178 var t = ( 1 + Math.sqrt( 5 ) ) / 2;
34184 - 1, - 1, - 1, - 1, - 1, 1,
34185 - 1, 1, - 1, - 1, 1, 1,
34186 1, - 1, - 1, 1, - 1, 1,
34187 1, 1, - 1, 1, 1, 1,
34190 0, - r, - t, 0, - r, t,
34191 0, r, - t, 0, r, t,
34194 - r, - t, 0, - r, t, 0,
34195 r, - t, 0, r, t, 0,
34198 - t, 0, - r, t, 0, - r,
34203 3, 11, 7, 3, 7, 15, 3, 15, 13,
34204 7, 19, 17, 7, 17, 6, 7, 6, 15,
34205 17, 4, 8, 17, 8, 10, 17, 10, 6,
34206 8, 0, 16, 8, 16, 2, 8, 2, 10,
34207 0, 12, 1, 0, 1, 18, 0, 18, 16,
34208 6, 10, 2, 6, 2, 13, 6, 13, 15,
34209 2, 16, 18, 2, 18, 3, 2, 3, 13,
34210 18, 1, 9, 18, 9, 11, 18, 11, 3,
34211 4, 14, 12, 4, 12, 0, 4, 0, 8,
34212 11, 9, 5, 11, 5, 19, 11, 19, 7,
34213 19, 5, 14, 19, 14, 4, 19, 4, 17,
34214 1, 12, 14, 1, 14, 5, 1, 5, 9
34217 THREE.PolyhedronGeometry.call(
this, vertices, indices, radius, detail );
34219 this.type =
'DodecahedronGeometry';
34221 this.parameters = {
34228 THREE.DodecahedronGeometry.prototype = Object.create( THREE.PolyhedronGeometry.prototype );
34229 THREE.DodecahedronGeometry.prototype.constructor = THREE.DodecahedronGeometry;
34231 THREE.DodecahedronGeometry.prototype.clone =
function () {
34233 var parameters = this.parameters;
34235 return new THREE.DodecahedronGeometry(
34248 THREE.IcosahedronGeometry =
function ( radius, detail ) {
34250 var t = ( 1 + Math.sqrt( 5 ) ) / 2;
34253 - 1, t, 0, 1, t, 0, - 1, - t, 0, 1, - t, 0,
34254 0, - 1, t, 0, 1, t, 0, - 1, - t, 0, 1, - t,
34255 t, 0, - 1, t, 0, 1, - t, 0, - 1, - t, 0, 1
34259 0, 11, 5, 0, 5, 1, 0, 1, 7, 0, 7, 10, 0, 10, 11,
34260 1, 5, 9, 5, 11, 4, 11, 10, 2, 10, 7, 6, 7, 1, 8,
34261 3, 9, 4, 3, 4, 2, 3, 2, 6, 3, 6, 8, 3, 8, 9,
34262 4, 9, 5, 2, 4, 11, 6, 2, 10, 8, 6, 7, 9, 8, 1
34265 THREE.PolyhedronGeometry.call(
this, vertices, indices, radius, detail );
34267 this.type =
'IcosahedronGeometry';
34269 this.parameters = {
34276 THREE.IcosahedronGeometry.prototype = Object.create( THREE.PolyhedronGeometry.prototype );
34277 THREE.IcosahedronGeometry.prototype.constructor = THREE.IcosahedronGeometry;
34279 THREE.IcosahedronGeometry.prototype.clone =
function () {
34281 var parameters = this.parameters;
34283 return new THREE.IcosahedronGeometry(
34296 THREE.OctahedronGeometry =
function ( radius, detail ) {
34299 1, 0, 0, - 1, 0, 0, 0, 1, 0, 0, - 1, 0, 0, 0, 1, 0, 0, - 1
34303 0, 2, 4, 0, 4, 3, 0, 3, 5, 0, 5, 2, 1, 2, 5, 1, 5, 3, 1, 3, 4, 1, 4, 2
34306 THREE.PolyhedronGeometry.call(
this, vertices, indices, radius, detail );
34308 this.type =
'OctahedronGeometry';
34310 this.parameters = {
34317 THREE.OctahedronGeometry.prototype = Object.create( THREE.PolyhedronGeometry.prototype );
34318 THREE.OctahedronGeometry.prototype.constructor = THREE.OctahedronGeometry;
34320 THREE.OctahedronGeometry.prototype.clone =
function () {
34322 var parameters = this.parameters;
34324 return new THREE.OctahedronGeometry(
34337 THREE.TetrahedronGeometry =
function ( radius, detail ) {
34340 1, 1, 1, - 1, - 1, 1, - 1, 1, - 1, 1, - 1, - 1
34344 2, 1, 0, 0, 3, 2, 1, 3, 0, 2, 3, 1
34347 THREE.PolyhedronGeometry.call(
this, vertices, indices, radius, detail );
34349 this.type =
'TetrahedronGeometry';
34351 this.parameters = {
34358 THREE.TetrahedronGeometry.prototype = Object.create( THREE.PolyhedronGeometry.prototype );
34359 THREE.TetrahedronGeometry.prototype.constructor = THREE.TetrahedronGeometry;
34361 THREE.TetrahedronGeometry.prototype.clone =
function () {
34363 var parameters = this.parameters;
34365 return new THREE.TetrahedronGeometry(
34383 THREE.ParametricGeometry =
function ( func, slices, stacks ) {
34385 THREE.Geometry.call(
this );
34387 this.type =
'ParametricGeometry';
34389 this.parameters = {
34395 var verts = this.vertices;
34396 var faces = this.faces;
34397 var uvs = this.faceVertexUvs[ 0 ];
34402 var sliceCount = slices + 1;
34404 for ( i = 0; i <= stacks; i ++ ) {
34408 for ( j = 0; j <= slices; j ++ ) {
34420 var uva, uvb, uvc, uvd;
34422 for ( i = 0; i < stacks; i ++ ) {
34424 for ( j = 0; j < slices; j ++ ) {
34426 a = i * sliceCount + j;
34427 b = i * sliceCount + j + 1;
34428 c = ( i + 1 ) * sliceCount + j + 1;
34429 d = ( i + 1 ) * sliceCount + j;
34431 uva =
new THREE.Vector2( j / slices, i / stacks );
34432 uvb =
new THREE.Vector2( ( j + 1 ) / slices, i / stacks );
34433 uvc =
new THREE.Vector2( ( j + 1 ) / slices, ( i + 1 ) / stacks );
34434 uvd =
new THREE.Vector2( j / slices, ( i + 1 ) / stacks );
34436 faces.push(
new THREE.Face3( a, b, d ) );
34437 uvs.push( [ uva, uvb, uvd ] );
34439 faces.push(
new THREE.Face3( b, c, d ) );
34440 uvs.push( [ uvb.clone(), uvc, uvd.clone() ] );
34452 this.computeFaceNormals();
34453 this.computeVertexNormals();
34457 THREE.ParametricGeometry.prototype = Object.create( THREE.Geometry.prototype );
34458 THREE.ParametricGeometry.prototype.constructor = THREE.ParametricGeometry;
34466 THREE.WireframeGeometry =
function ( geometry ) {
34468 THREE.BufferGeometry.call(
this );
34470 var edge = [ 0, 0 ], hash = {};
34472 function sortFunction( a, b ) {
34478 var keys = [
'a',
'b',
'c' ];
34480 if ( geometry instanceof THREE.Geometry ) {
34482 var vertices = geometry.vertices;
34483 var faces = geometry.faces;
34487 var edges =
new Uint32Array( 6 * faces.length );
34489 for ( var i = 0, l = faces.length; i < l; i ++ ) {
34491 var face = faces[ i ];
34493 for ( var j = 0; j < 3; j ++ ) {
34495 edge[ 0 ] = face[ keys[ j ] ];
34496 edge[ 1 ] = face[ keys[ ( j + 1 ) % 3 ] ];
34497 edge.sort( sortFunction );
34499 var key = edge.toString();
34501 if ( hash[ key ] === undefined ) {
34503 edges[ 2 * numEdges ] = edge[ 0 ];
34504 edges[ 2 * numEdges + 1 ] = edge[ 1 ];
34505 hash[ key ] =
true;
34514 var coords =
new Float32Array( numEdges * 2 * 3 );
34516 for ( var i = 0, l = numEdges; i < l; i ++ ) {
34518 for ( var j = 0; j < 2; j ++ ) {
34520 var vertex = vertices[ edges [ 2 * i + j ] ];
34522 var index = 6 * i + 3 * j;
34523 coords[ index + 0 ] = vertex.x;
34524 coords[ index + 1 ] = vertex.y;
34525 coords[ index + 2 ] = vertex.z;
34531 this.addAttribute(
'position',
new THREE.BufferAttribute( coords, 3 ) );
34533 }
else if ( geometry instanceof THREE.BufferGeometry ) {
34535 if ( geometry.index !== null ) {
34539 var indices = geometry.index.array;
34540 var vertices = geometry.attributes.position;
34541 var drawcalls = geometry.drawcalls;
34544 if ( drawcalls.length === 0 ) {
34546 geometry.addGroup( 0, indices.length );
34551 var edges =
new Uint32Array( 2 * indices.length );
34553 for ( var o = 0, ol = drawcalls.length; o < ol; ++ o ) {
34555 var drawcall = drawcalls[ o ];
34557 var start = drawcall.start;
34558 var count = drawcall.count;
34560 for ( var i = start, il = start + count; i < il; i += 3 ) {
34562 for ( var j = 0; j < 3; j ++ ) {
34564 edge[ 0 ] = indices[ i + j ];
34565 edge[ 1 ] = indices[ i + ( j + 1 ) % 3 ];
34566 edge.sort( sortFunction );
34568 var key = edge.toString();
34570 if ( hash[ key ] === undefined ) {
34572 edges[ 2 * numEdges ] = edge[ 0 ];
34573 edges[ 2 * numEdges + 1 ] = edge[ 1 ];
34574 hash[ key ] =
true;
34585 var coords =
new Float32Array( numEdges * 2 * 3 );
34587 for ( var i = 0, l = numEdges; i < l; i ++ ) {
34589 for ( var j = 0; j < 2; j ++ ) {
34591 var index = 6 * i + 3 * j;
34592 var index2 = edges[ 2 * i + j ];
34594 coords[ index + 0 ] = vertices.getX( index2 );
34595 coords[ index + 1 ] = vertices.getY( index2 );
34596 coords[ index + 2 ] = vertices.getZ( index2 );
34602 this.addAttribute(
'position',
new THREE.BufferAttribute( coords, 3 ) );
34608 var vertices = geometry.attributes.position.array;
34609 var numEdges = vertices.length / 3;
34610 var numTris = numEdges / 3;
34612 var coords =
new Float32Array( numEdges * 2 * 3 );
34614 for ( var i = 0, l = numTris; i < l; i ++ ) {
34616 for ( var j = 0; j < 3; j ++ ) {
34618 var index = 18 * i + 6 * j;
34620 var index1 = 9 * i + 3 * j;
34621 coords[ index + 0 ] = vertices[ index1 ];
34622 coords[ index + 1 ] = vertices[ index1 + 1 ];
34623 coords[ index + 2 ] = vertices[ index1 + 2 ];
34625 var index2 = 9 * i + 3 * ( ( j + 1 ) % 3 );
34626 coords[ index + 3 ] = vertices[ index2 ];
34627 coords[ index + 4 ] = vertices[ index2 + 1 ];
34628 coords[ index + 5 ] = vertices[ index2 + 2 ];
34634 this.addAttribute(
'position',
new THREE.BufferAttribute( coords, 3 ) );
34642 THREE.WireframeGeometry.prototype = Object.create( THREE.BufferGeometry.prototype );
34643 THREE.WireframeGeometry.prototype.constructor = THREE.WireframeGeometry;
34652 THREE.AxisHelper =
function ( size ) {
34656 var vertices =
new Float32Array( [
34657 0, 0, 0, size, 0, 0,
34658 0, 0, 0, 0, size, 0,
34659 0, 0, 0, 0, 0, size
34662 var colors =
new Float32Array( [
34663 1, 0, 0, 1, 0.6, 0,
34664 0, 1, 0, 0.6, 1, 0,
34668 var geometry =
new THREE.BufferGeometry();
34669 geometry.addAttribute(
'position',
new THREE.BufferAttribute( vertices, 3 ) );
34670 geometry.addAttribute(
'color',
new THREE.BufferAttribute( colors, 3 ) );
34672 var material =
new THREE.LineBasicMaterial( { vertexColors: THREE.VertexColors } );
34674 THREE.LineSegments.call(
this, geometry, material );
34678 THREE.AxisHelper.prototype = Object.create( THREE.LineSegments.prototype );
34679 THREE.AxisHelper.prototype.constructor = THREE.AxisHelper;
34699 THREE.ArrowHelper = (
function () {
34701 var lineGeometry =
new THREE.Geometry();
34702 lineGeometry.vertices.push(
new THREE.Vector3( 0, 0, 0 ),
new THREE.Vector3( 0, 1, 0 ) );
34704 var coneGeometry =
new THREE.CylinderGeometry( 0, 0.5, 1, 5, 1 );
34705 coneGeometry.translate( 0, - 0.5, 0 );
34707 return function ArrowHelper( dir, origin, length, color, headLength, headWidth ) {
34711 THREE.Object3D.call(
this );
34713 if ( color === undefined ) color = 0xffff00;
34714 if ( length === undefined ) length = 1;
34715 if ( headLength === undefined ) headLength = 0.2 * length;
34716 if ( headWidth === undefined ) headWidth = 0.2 * headLength;
34718 this.position.copy( origin );
34720 if ( headLength < length ) {
34721 this.line =
new THREE.Line( lineGeometry,
new THREE.LineBasicMaterial( { color: color } ) );
34722 this.line.matrixAutoUpdate =
false;
34723 this.add( this.line );
34726 this.cone =
new THREE.Mesh( coneGeometry,
new THREE.MeshBasicMaterial( { color: color } ) );
34727 this.cone.matrixAutoUpdate =
false;
34728 this.add( this.cone );
34730 this.setDirection( dir );
34731 this.setLength( length, headLength, headWidth );
34737 THREE.ArrowHelper.prototype = Object.create( THREE.Object3D.prototype );
34738 THREE.ArrowHelper.prototype.constructor = THREE.ArrowHelper;
34740 THREE.ArrowHelper.prototype.setDirection = (
function () {
34742 var axis =
new THREE.Vector3();
34745 return function setDirection( dir ) {
34749 if ( dir.y > 0.99999 ) {
34751 this.quaternion.set( 0, 0, 0, 1 );
34753 }
else if ( dir.y < - 0.99999 ) {
34755 this.quaternion.set( 1, 0, 0, 0 );
34759 axis.set( dir.z, 0, - dir.x ).normalize();
34761 radians = Math.acos( dir.y );
34763 this.quaternion.setFromAxisAngle( axis, radians );
34771 THREE.ArrowHelper.prototype.setLength =
function ( length, headLength, headWidth ) {
34773 if ( headLength === undefined ) headLength = 0.2 * length;
34774 if ( headWidth === undefined ) headWidth = 0.2 * headLength;
34776 if ( headLength < length ){
34777 this.line.scale.set( 1, length - headLength, 1 );
34778 this.line.updateMatrix();
34781 this.cone.scale.set( headWidth, headLength, headWidth );
34782 this.cone.position.y = length;
34783 this.cone.updateMatrix();
34787 THREE.ArrowHelper.prototype.setColor =
function ( color ) {
34789 if ( this.line !== undefined ) this.line.material.color.set( color );
34790 this.cone.material.color.set( color );
34800 THREE.BoxHelper =
function ( object ) {
34802 var indices =
new Uint16Array( [ 0, 1, 1, 2, 2, 3, 3, 0, 4, 5, 5, 6, 6, 7, 7, 4, 0, 4, 1, 5, 2, 6, 3, 7 ] );
34803 var positions =
new Float32Array( 8 * 3 );
34805 var geometry =
new THREE.BufferGeometry();
34806 geometry.setIndex(
new THREE.BufferAttribute( indices, 1 ) );
34807 geometry.addAttribute(
'position',
new THREE.BufferAttribute( positions, 3 ) );
34809 THREE.LineSegments.call(
this, geometry,
new THREE.LineBasicMaterial( { color: 0xffff00 } ) );
34811 if (
object !== undefined ) {
34813 this.update(
object );
34819 THREE.BoxHelper.prototype = Object.create( THREE.LineSegments.prototype );
34820 THREE.BoxHelper.prototype.constructor = THREE.BoxHelper;
34822 THREE.BoxHelper.prototype.update = (
function () {
34824 var box =
new THREE.Box3();
34826 return function ( object ) {
34828 box.setFromObject(
object );
34830 if ( box.empty() )
return;
34851 var position = this.geometry.attributes.position;
34852 var array = position.array;
34854 array[ 0 ] = max.x; array[ 1 ] = max.y; array[ 2 ] = max.z;
34855 array[ 3 ] = min.x; array[ 4 ] = max.y; array[ 5 ] = max.z;
34856 array[ 6 ] = min.x; array[ 7 ] = min.y; array[ 8 ] = max.z;
34857 array[ 9 ] = max.x; array[ 10 ] = min.y; array[ 11 ] = max.z;
34858 array[ 12 ] = max.x; array[ 13 ] = max.y; array[ 14 ] = min.z;
34859 array[ 15 ] = min.x; array[ 16 ] = max.y; array[ 17 ] = min.z;
34860 array[ 18 ] = min.x; array[ 19 ] = min.y; array[ 20 ] = min.z;
34861 array[ 21 ] = max.x; array[ 22 ] = min.y; array[ 23 ] = min.z;
34863 position.needsUpdate =
true;
34865 this.geometry.computeBoundingSphere();
34879 THREE.BoundingBoxHelper =
function ( object, hex ) {
34881 var color = ( hex !== undefined ) ? hex : 0x888888;
34883 this.
object = object;
34885 this.box =
new THREE.Box3();
34887 THREE.Mesh.call(
this,
new THREE.BoxGeometry( 1, 1, 1 ),
new THREE.MeshBasicMaterial( { color: color, wireframe:
true } ) );
34891 THREE.BoundingBoxHelper.prototype = Object.create( THREE.Mesh.prototype );
34892 THREE.BoundingBoxHelper.prototype.constructor = THREE.BoundingBoxHelper;
34894 THREE.BoundingBoxHelper.prototype.update =
function () {
34896 this.box.setFromObject( this.
object );
34898 this.box.size( this.scale );
34900 this.box.center( this.position );
34915 THREE.CameraHelper =
function ( camera ) {
34917 var geometry =
new THREE.Geometry();
34918 var material =
new THREE.LineBasicMaterial( { color: 0xffffff, vertexColors: THREE.FaceColors } );
34924 var hexFrustum = 0xffaa00;
34925 var hexCone = 0xff0000;
34926 var hexUp = 0x00aaff;
34927 var hexTarget = 0xffffff;
34928 var hexCross = 0x333333;
34932 addLine(
"n1",
"n2", hexFrustum );
34933 addLine(
"n2",
"n4", hexFrustum );
34934 addLine(
"n4",
"n3", hexFrustum );
34935 addLine(
"n3",
"n1", hexFrustum );
34939 addLine(
"f1",
"f2", hexFrustum );
34940 addLine(
"f2",
"f4", hexFrustum );
34941 addLine(
"f4",
"f3", hexFrustum );
34942 addLine(
"f3",
"f1", hexFrustum );
34946 addLine(
"n1",
"f1", hexFrustum );
34947 addLine(
"n2",
"f2", hexFrustum );
34948 addLine(
"n3",
"f3", hexFrustum );
34949 addLine(
"n4",
"f4", hexFrustum );
34953 addLine(
"p",
"n1", hexCone );
34954 addLine(
"p",
"n2", hexCone );
34955 addLine(
"p",
"n3", hexCone );
34956 addLine(
"p",
"n4", hexCone );
34960 addLine(
"u1",
"u2", hexUp );
34961 addLine(
"u2",
"u3", hexUp );
34962 addLine(
"u3",
"u1", hexUp );
34966 addLine(
"c",
"t", hexTarget );
34967 addLine(
"p",
"c", hexCross );
34971 addLine(
"cn1",
"cn2", hexCross );
34972 addLine(
"cn3",
"cn4", hexCross );
34974 addLine(
"cf1",
"cf2", hexCross );
34975 addLine(
"cf3",
"cf4", hexCross );
34977 function addLine( a, b, hex ) {
34979 addPoint( a, hex );
34980 addPoint( b, hex );
34984 function addPoint(
id, hex ) {
34986 geometry.vertices.push(
new THREE.Vector3() );
34987 geometry.colors.push(
new THREE.Color( hex ) );
34989 if ( pointMap[
id ] === undefined ) {
34991 pointMap[ id ] = [];
34995 pointMap[ id ].push( geometry.vertices.length - 1 );
34999 THREE.LineSegments.call(
this, geometry, material );
35001 this.camera = camera;
35002 this.camera.updateProjectionMatrix();
35004 this.matrix = camera.matrixWorld;
35005 this.matrixAutoUpdate =
false;
35007 this.pointMap = pointMap;
35013 THREE.CameraHelper.prototype = Object.create( THREE.LineSegments.prototype );
35014 THREE.CameraHelper.prototype.constructor = THREE.CameraHelper;
35016 THREE.CameraHelper.prototype.update =
function () {
35018 var geometry, pointMap;
35020 var vector =
new THREE.Vector3();
35021 var camera =
new THREE.Camera();
35023 function setPoint( point, x, y, z ) {
35025 vector.set( x, y, z ).unproject( camera );
35027 var points = pointMap[ point ];
35029 if ( points !== undefined ) {
35031 for ( var i = 0, il = points.length; i < il; i ++ ) {
35033 geometry.vertices[ points[ i ] ].copy( vector );
35041 return function () {
35043 geometry = this.geometry;
35044 pointMap = this.pointMap;
35051 camera.projectionMatrix.copy( this.camera.projectionMatrix );
35055 setPoint(
"c", 0, 0, - 1 );
35056 setPoint(
"t", 0, 0, 1 );
35060 setPoint(
"n1", - w, - h, - 1 );
35061 setPoint(
"n2", w, - h, - 1 );
35062 setPoint(
"n3", - w, h, - 1 );
35063 setPoint(
"n4", w, h, - 1 );
35067 setPoint(
"f1", - w, - h, 1 );
35068 setPoint(
"f2", w, - h, 1 );
35069 setPoint(
"f3", - w, h, 1 );
35070 setPoint(
"f4", w, h, 1 );
35074 setPoint(
"u1", w * 0.7, h * 1.1, - 1 );
35075 setPoint(
"u2", - w * 0.7, h * 1.1, - 1 );
35076 setPoint(
"u3", 0, h * 2, - 1 );
35080 setPoint(
"cf1", - w, 0, 1 );
35081 setPoint(
"cf2", w, 0, 1 );
35082 setPoint(
"cf3", 0, - h, 1 );
35083 setPoint(
"cf4", 0, h, 1 );
35085 setPoint(
"cn1", - w, 0, - 1 );
35086 setPoint(
"cn2", w, 0, - 1 );
35087 setPoint(
"cn3", 0, - h, - 1 );
35088 setPoint(
"cn4", 0, h, - 1 );
35090 geometry.verticesNeedUpdate =
true;
35104 THREE.DirectionalLightHelper =
function ( light, size ) {
35106 THREE.Object3D.call(
this );
35108 this.light = light;
35109 this.light.updateMatrixWorld();
35111 this.matrix = light.matrixWorld;
35112 this.matrixAutoUpdate =
false;
35116 var geometry =
new THREE.Geometry();
35117 geometry.vertices.push(
35118 new THREE.Vector3( - size, size, 0 ),
35119 new THREE.Vector3( size, size, 0 ),
35120 new THREE.Vector3( size, - size, 0 ),
35121 new THREE.Vector3( - size, - size, 0 ),
35122 new THREE.Vector3( - size, size, 0 )
35125 var material =
new THREE.LineBasicMaterial( { fog:
false } );
35126 material.color.copy( this.light.color ).multiplyScalar( this.light.intensity );
35128 this.lightPlane =
new THREE.Line( geometry, material );
35129 this.add( this.lightPlane );
35131 geometry =
new THREE.Geometry();
35132 geometry.vertices.push(
35133 new THREE.Vector3(),
35134 new THREE.Vector3()
35137 material =
new THREE.LineBasicMaterial( { fog:
false } );
35138 material.color.copy( this.light.color ).multiplyScalar( this.light.intensity );
35140 this.targetLine =
new THREE.Line( geometry, material );
35141 this.add( this.targetLine );
35147 THREE.DirectionalLightHelper.prototype = Object.create( THREE.Object3D.prototype );
35148 THREE.DirectionalLightHelper.prototype.constructor = THREE.DirectionalLightHelper;
35150 THREE.DirectionalLightHelper.prototype.dispose =
function () {
35152 this.lightPlane.geometry.dispose();
35153 this.lightPlane.material.dispose();
35154 this.targetLine.geometry.dispose();
35155 this.targetLine.material.dispose();
35159 THREE.DirectionalLightHelper.prototype.update =
function () {
35161 var v1 =
new THREE.Vector3();
35162 var v2 =
new THREE.Vector3();
35163 var v3 =
new THREE.Vector3();
35165 return function () {
35167 v1.setFromMatrixPosition( this.light.matrixWorld );
35168 v2.setFromMatrixPosition( this.light.target.matrixWorld );
35169 v3.subVectors( v2, v1 );
35171 this.lightPlane.lookAt( v3 );
35172 this.lightPlane.material.color.copy( this.light.color ).multiplyScalar( this.light.intensity );
35174 this.targetLine.geometry.vertices[ 1 ].copy( v3 );
35175 this.targetLine.geometry.verticesNeedUpdate =
true;
35176 this.targetLine.material.color.copy( this.lightPlane.material.color );
35194 THREE.EdgesHelper =
function ( object, hex, thresholdAngle ) {
35196 var color = ( hex !== undefined ) ? hex : 0xffffff;
35198 THREE.LineSegments.call(
this,
new THREE.EdgesGeometry(
object.geometry, thresholdAngle ),
new THREE.LineBasicMaterial( { color: color } ) );
35200 this.matrix =
object.matrixWorld;
35201 this.matrixAutoUpdate =
false;
35205 THREE.EdgesHelper.prototype = Object.create( THREE.LineSegments.prototype );
35206 THREE.EdgesHelper.prototype.constructor = THREE.EdgesHelper;
35215 THREE.FaceNormalsHelper =
function ( object, size, hex, linewidth ) {
35219 this.
object = object;
35221 this.size = ( size !== undefined ) ? size : 1;
35223 var color = ( hex !== undefined ) ? hex : 0xffff00;
35225 var width = ( linewidth !== undefined ) ? linewidth : 1;
35231 var objGeometry = this.
object.geometry;
35233 if ( objGeometry instanceof THREE.Geometry ) {
35235 nNormals = objGeometry.faces.length;
35239 console.warn(
'THREE.FaceNormalsHelper: only THREE.Geometry is supported. Use THREE.VertexNormalsHelper, instead.' );
35245 var geometry =
new THREE.BufferGeometry();
35247 var positions =
new THREE.Float32Attribute( nNormals * 2 * 3, 3 );
35249 geometry.addAttribute(
'position', positions );
35251 THREE.LineSegments.call(
this, geometry,
new THREE.LineBasicMaterial( { color: color, linewidth: width } ) );
35255 this.matrixAutoUpdate =
false;
35260 THREE.FaceNormalsHelper.prototype = Object.create( THREE.LineSegments.prototype );
35261 THREE.FaceNormalsHelper.prototype.constructor = THREE.FaceNormalsHelper;
35263 THREE.FaceNormalsHelper.prototype.update = (
function () {
35265 var v1 =
new THREE.Vector3();
35266 var v2 =
new THREE.Vector3();
35267 var normalMatrix =
new THREE.Matrix3();
35269 return function update() {
35271 this.
object.updateMatrixWorld(
true );
35273 normalMatrix.getNormalMatrix( this.
object.matrixWorld );
35275 var matrixWorld = this.
object.matrixWorld;
35277 var position = this.geometry.attributes.position;
35281 var objGeometry = this.
object.geometry;
35283 var vertices = objGeometry.vertices;
35285 var faces = objGeometry.faces;
35289 for ( var i = 0, l = faces.length; i < l; i ++ ) {
35291 var face = faces[ i ];
35293 var normal = face.normal;
35295 v1.copy( vertices[ face.a ] )
35296 .add( vertices[ face.b ] )
35297 .add( vertices[ face.c ] )
35299 .applyMatrix4( matrixWorld );
35301 v2.copy( normal ).applyMatrix3( normalMatrix ).normalize().multiplyScalar( this.size ).add( v1 );
35303 position.setXYZ( idx, v1.x, v1.y, v1.z );
35307 position.setXYZ( idx, v2.x, v2.y, v2.z );
35313 position.needsUpdate =
true;
35327 THREE.GridHelper =
function ( size, step ) {
35329 var geometry =
new THREE.Geometry();
35330 var material =
new THREE.LineBasicMaterial( { vertexColors: THREE.VertexColors } );
35332 this.color1 =
new THREE.Color( 0x444444 );
35333 this.color2 =
new THREE.Color( 0x888888 );
35335 for ( var i = - size; i <= size; i += step ) {
35337 geometry.vertices.push(
35338 new THREE.Vector3( - size, 0, i ),
new THREE.Vector3( size, 0, i ),
35339 new THREE.Vector3( i, 0, - size ),
new THREE.Vector3( i, 0, size )
35342 var color = i === 0 ? this.color1 : this.color2;
35344 geometry.colors.push( color, color, color, color );
35348 THREE.LineSegments.call(
this, geometry, material );
35352 THREE.GridHelper.prototype = Object.create( THREE.LineSegments.prototype );
35353 THREE.GridHelper.prototype.constructor = THREE.GridHelper;
35355 THREE.GridHelper.prototype.setColors =
function( colorCenterLine, colorGrid ) {
35357 this.color1.set( colorCenterLine );
35358 this.color2.set( colorGrid );
35360 this.geometry.colorsNeedUpdate =
true;
35371 THREE.HemisphereLightHelper =
function ( light, sphereSize ) {
35373 THREE.Object3D.call(
this );
35375 this.light = light;
35376 this.light.updateMatrixWorld();
35378 this.matrix = light.matrixWorld;
35379 this.matrixAutoUpdate =
false;
35381 this.colors = [
new THREE.Color(),
new THREE.Color() ];
35383 var geometry =
new THREE.SphereGeometry( sphereSize, 4, 2 );
35384 geometry.rotateX( - Math.PI / 2 );
35386 for ( var i = 0, il = 8; i < il; i ++ ) {
35388 geometry.faces[ i ].color = this.colors[ i < 4 ? 0 : 1 ];
35392 var material =
new THREE.MeshBasicMaterial( { vertexColors: THREE.FaceColors, wireframe:
true } );
35394 this.lightSphere =
new THREE.Mesh( geometry, material );
35395 this.add( this.lightSphere );
35401 THREE.HemisphereLightHelper.prototype = Object.create( THREE.Object3D.prototype );
35402 THREE.HemisphereLightHelper.prototype.constructor = THREE.HemisphereLightHelper;
35404 THREE.HemisphereLightHelper.prototype.dispose =
function () {
35406 this.lightSphere.geometry.dispose();
35407 this.lightSphere.material.dispose();
35411 THREE.HemisphereLightHelper.prototype.update =
function () {
35413 var vector =
new THREE.Vector3();
35415 return function () {
35417 this.colors[ 0 ].copy( this.light.color ).multiplyScalar( this.light.intensity );
35418 this.colors[ 1 ].copy( this.light.groundColor ).multiplyScalar( this.light.intensity );
35420 this.lightSphere.lookAt( vector.setFromMatrixPosition(
this.light.matrixWorld ).negate() );
35421 this.lightSphere.geometry.colorsNeedUpdate =
true;
35434 THREE.PointLightHelper =
function ( light, sphereSize ) {
35436 this.light = light;
35437 this.light.updateMatrixWorld();
35439 var geometry =
new THREE.SphereGeometry( sphereSize, 4, 2 );
35440 var material =
new THREE.MeshBasicMaterial( { wireframe:
true, fog:
false } );
35441 material.color.copy( this.light.color ).multiplyScalar( this.light.intensity );
35443 THREE.Mesh.call(
this, geometry, material );
35445 this.matrix = this.light.matrixWorld;
35446 this.matrixAutoUpdate =
false;
35472 THREE.PointLightHelper.prototype = Object.create( THREE.Mesh.prototype );
35473 THREE.PointLightHelper.prototype.constructor = THREE.PointLightHelper;
35475 THREE.PointLightHelper.prototype.dispose =
function () {
35477 this.geometry.dispose();
35478 this.material.dispose();
35482 THREE.PointLightHelper.prototype.update =
function () {
35484 this.material.color.copy( this.light.color ).multiplyScalar( this.light.intensity );
35512 THREE.SkeletonHelper =
function ( object ) {
35514 this.bones = this.getBoneList(
object );
35516 var geometry =
new THREE.Geometry();
35518 for ( var i = 0; i < this.bones.length; i ++ ) {
35520 var bone = this.bones[ i ];
35522 if ( bone.parent instanceof THREE.Bone ) {
35524 geometry.vertices.push(
new THREE.Vector3() );
35525 geometry.vertices.push(
new THREE.Vector3() );
35526 geometry.colors.push(
new THREE.Color( 0, 0, 1 ) );
35527 geometry.colors.push(
new THREE.Color( 0, 1, 0 ) );
35533 geometry.dynamic =
true;
35535 var material =
new THREE.LineBasicMaterial( { vertexColors: THREE.VertexColors, depthTest:
false, depthWrite:
false, transparent:
true } );
35537 THREE.LineSegments.call(
this, geometry, material );
35539 this.root = object;
35541 this.matrix =
object.matrixWorld;
35542 this.matrixAutoUpdate =
false;
35549 THREE.SkeletonHelper.prototype = Object.create( THREE.LineSegments.prototype );
35550 THREE.SkeletonHelper.prototype.constructor = THREE.SkeletonHelper;
35552 THREE.SkeletonHelper.prototype.getBoneList =
function( object ) {
35556 if (
object instanceof THREE.Bone ) {
35558 boneList.push(
object );
35562 for ( var i = 0; i <
object.children.length; i ++ ) {
35564 boneList.push.apply( boneList, this.getBoneList(
object.children[ i ] ) );
35572 THREE.SkeletonHelper.prototype.update =
function () {
35574 var geometry = this.geometry;
35576 var matrixWorldInv =
new THREE.Matrix4().getInverse( this.root.matrixWorld );
35578 var boneMatrix =
new THREE.Matrix4();
35582 for ( var i = 0; i < this.bones.length; i ++ ) {
35584 var bone = this.bones[ i ];
35586 if ( bone.parent instanceof THREE.Bone ) {
35588 boneMatrix.multiplyMatrices( matrixWorldInv, bone.matrixWorld );
35589 geometry.vertices[ j ].setFromMatrixPosition( boneMatrix );
35591 boneMatrix.multiplyMatrices( matrixWorldInv, bone.parent.matrixWorld );
35592 geometry.vertices[ j + 1 ].setFromMatrixPosition( boneMatrix );
35600 geometry.verticesNeedUpdate =
true;
35602 geometry.computeBoundingSphere();
35614 THREE.SpotLightHelper =
function ( light ) {
35616 THREE.Object3D.call(
this );
35618 this.light = light;
35619 this.light.updateMatrixWorld();
35621 this.matrix = light.matrixWorld;
35622 this.matrixAutoUpdate =
false;
35624 var geometry =
new THREE.CylinderGeometry( 0, 1, 1, 8, 1,
true );
35626 geometry.translate( 0, - 0.5, 0 );
35627 geometry.rotateX( - Math.PI / 2 );
35629 var material =
new THREE.MeshBasicMaterial( { wireframe:
true, fog:
false } );
35631 this.cone =
new THREE.Mesh( geometry, material );
35632 this.add( this.cone );
35638 THREE.SpotLightHelper.prototype = Object.create( THREE.Object3D.prototype );
35639 THREE.SpotLightHelper.prototype.constructor = THREE.SpotLightHelper;
35641 THREE.SpotLightHelper.prototype.dispose =
function () {
35643 this.cone.geometry.dispose();
35644 this.cone.material.dispose();
35648 THREE.SpotLightHelper.prototype.update =
function () {
35650 var vector =
new THREE.Vector3();
35651 var vector2 =
new THREE.Vector3();
35653 return function () {
35655 var coneLength = this.light.distance ? this.light.distance : 10000;
35656 var coneWidth = coneLength * Math.tan( this.light.angle );
35658 this.cone.scale.set( coneWidth, coneWidth, coneLength );
35660 vector.setFromMatrixPosition( this.light.matrixWorld );
35661 vector2.setFromMatrixPosition( this.light.target.matrixWorld );
35663 this.cone.lookAt( vector2.sub( vector ) );
35665 this.cone.material.color.copy( this.light.color ).multiplyScalar( this.light.intensity );
35678 THREE.VertexNormalsHelper =
function ( object, size, hex, linewidth ) {
35680 this.
object = object;
35682 this.size = ( size !== undefined ) ? size : 1;
35684 var color = ( hex !== undefined ) ? hex : 0xff0000;
35686 var width = ( linewidth !== undefined ) ? linewidth : 1;
35692 var objGeometry = this.
object.geometry;
35694 if ( objGeometry instanceof THREE.Geometry ) {
35696 nNormals = objGeometry.faces.length * 3;
35698 }
else if ( objGeometry instanceof THREE.BufferGeometry ) {
35700 nNormals = objGeometry.attributes.normal.count
35706 var geometry =
new THREE.BufferGeometry();
35708 var positions =
new THREE.Float32Attribute( nNormals * 2 * 3, 3 );
35710 geometry.addAttribute(
'position', positions );
35712 THREE.LineSegments.call(
this, geometry,
new THREE.LineBasicMaterial( { color: color, linewidth: width } ) );
35716 this.matrixAutoUpdate =
false;
35722 THREE.VertexNormalsHelper.prototype = Object.create( THREE.LineSegments.prototype );
35723 THREE.VertexNormalsHelper.prototype.constructor = THREE.VertexNormalsHelper;
35725 THREE.VertexNormalsHelper.prototype.update = (
function () {
35727 var v1 =
new THREE.Vector3();
35728 var v2 =
new THREE.Vector3();
35729 var normalMatrix =
new THREE.Matrix3();
35731 return function update() {
35733 var keys = [
'a',
'b',
'c' ];
35735 this.
object.updateMatrixWorld(
true );
35737 normalMatrix.getNormalMatrix( this.
object.matrixWorld );
35739 var matrixWorld = this.
object.matrixWorld;
35741 var position = this.geometry.attributes.position;
35745 var objGeometry = this.
object.geometry;
35747 if ( objGeometry instanceof THREE.Geometry ) {
35749 var vertices = objGeometry.vertices;
35751 var faces = objGeometry.faces;
35755 for ( var i = 0, l = faces.length; i < l; i ++ ) {
35757 var face = faces[ i ];
35759 for ( var j = 0, jl = face.vertexNormals.length; j < jl; j ++ ) {
35761 var vertex = vertices[ face[ keys[ j ] ] ];
35763 var normal = face.vertexNormals[ j ];
35765 v1.copy( vertex ).applyMatrix4( matrixWorld );
35767 v2.copy( normal ).applyMatrix3( normalMatrix ).normalize().multiplyScalar( this.size ).add( v1 );
35769 position.setXYZ( idx, v1.x, v1.y, v1.z );
35773 position.setXYZ( idx, v2.x, v2.y, v2.z );
35781 }
else if ( objGeometry instanceof THREE.BufferGeometry ) {
35783 var objPos = objGeometry.attributes.position;
35785 var objNorm = objGeometry.attributes.normal;
35791 for ( var j = 0, jl = objPos.count; j < jl; j ++ ) {
35793 v1.set( objPos.getX( j ), objPos.getY( j ), objPos.getZ( j ) ).applyMatrix4( matrixWorld );
35795 v2.set( objNorm.getX( j ), objNorm.getY( j ), objNorm.getZ( j ) );
35797 v2.applyMatrix3( normalMatrix ).normalize().multiplyScalar( this.size ).add( v1 );
35799 position.setXYZ( idx, v1.x, v1.y, v1.z );
35803 position.setXYZ( idx, v2.x, v2.y, v2.z );
35811 position.needsUpdate =
true;
35825 THREE.WireframeHelper =
function ( object, hex ) {
35827 var color = ( hex !== undefined ) ? hex : 0xffffff;
35829 THREE.LineSegments.call(
this,
new THREE.WireframeGeometry(
object.geometry ),
new THREE.LineBasicMaterial( { color: color } ) );
35831 this.matrix =
object.matrixWorld;
35832 this.matrixAutoUpdate =
false;
35836 THREE.WireframeHelper.prototype = Object.create( THREE.LineSegments.prototype );
35837 THREE.WireframeHelper.prototype.constructor = THREE.WireframeHelper;
35845 THREE.ImmediateRenderObject =
function ( material ) {
35847 THREE.Object3D.call(
this );
35849 this.material = material;
35850 this.render =
function ( renderCallback ) {};
35854 THREE.ImmediateRenderObject.prototype = Object.create( THREE.Object3D.prototype );
35855 THREE.ImmediateRenderObject.prototype.constructor = THREE.ImmediateRenderObject;
35863 THREE.MorphBlendMesh =
function( geometry, material ) {
35865 THREE.Mesh.call(
this, geometry, material );
35867 this.animationsMap = {};
35868 this.animationsList = [];
35873 var numFrames = this.geometry.morphTargets.length;
35875 var name =
"__default";
35877 var startFrame = 0;
35878 var endFrame = numFrames - 1;
35880 var fps = numFrames / 1;
35882 this.createAnimation( name, startFrame, endFrame, fps );
35883 this.setAnimationWeight( name, 1 );
35887 THREE.MorphBlendMesh.prototype = Object.create( THREE.Mesh.prototype );
35888 THREE.MorphBlendMesh.prototype.constructor = THREE.MorphBlendMesh;
35890 THREE.MorphBlendMesh.prototype.createAnimation =
function ( name, start, end, fps ) {
35897 length: end - start + 1,
35900 duration: ( end - start ) / fps,
35911 directionBackwards:
false,
35912 mirroredLoop:
false
35916 this.animationsMap[ name ] = animation;
35917 this.animationsList.push( animation );
35921 THREE.MorphBlendMesh.prototype.autoCreateAnimations =
function ( fps ) {
35923 var pattern = /([a-z]+)_?(\d+)/;
35925 var firstAnimation, frameRanges = {};
35927 var geometry = this.geometry;
35929 for ( var i = 0, il = geometry.morphTargets.length; i < il; i ++ ) {
35931 var morph = geometry.morphTargets[ i ];
35932 var chunks = morph.name.match( pattern );
35934 if ( chunks && chunks.length > 1 ) {
35936 var name = chunks[ 1 ];
35938 if ( ! frameRanges[ name ] ) frameRanges[ name ] = { start: Infinity, end: - Infinity };
35940 var range = frameRanges[ name ];
35942 if ( i < range.start ) range.start = i;
35943 if ( i > range.end ) range.end = i;
35945 if ( ! firstAnimation ) firstAnimation = name;
35951 for ( var name in frameRanges ) {
35953 var range = frameRanges[ name ];
35954 this.createAnimation( name, range.start, range.end, fps );
35958 this.firstAnimation = firstAnimation;
35962 THREE.MorphBlendMesh.prototype.setAnimationDirectionForward =
function ( name ) {
35964 var animation = this.animationsMap[ name ];
35968 animation.direction = 1;
35969 animation.directionBackwards =
false;
35975 THREE.MorphBlendMesh.prototype.setAnimationDirectionBackward =
function ( name ) {
35977 var animation = this.animationsMap[ name ];
35981 animation.direction = - 1;
35982 animation.directionBackwards =
true;
35988 THREE.MorphBlendMesh.prototype.setAnimationFPS =
function ( name, fps ) {
35990 var animation = this.animationsMap[ name ];
35994 animation.fps = fps;
35995 animation.duration = ( animation.end - animation.start ) / animation.fps;
36001 THREE.MorphBlendMesh.prototype.setAnimationDuration =
function ( name, duration ) {
36003 var animation = this.animationsMap[ name ];
36007 animation.duration = duration;
36008 animation.fps = ( animation.end - animation.start ) / animation.duration;
36014 THREE.MorphBlendMesh.prototype.setAnimationWeight =
function ( name, weight ) {
36016 var animation = this.animationsMap[ name ];
36020 animation.weight = weight;
36026 THREE.MorphBlendMesh.prototype.setAnimationTime =
function ( name, time ) {
36028 var animation = this.animationsMap[ name ];
36032 animation.time = time;
36038 THREE.MorphBlendMesh.prototype.getAnimationTime =
function ( name ) {
36042 var animation = this.animationsMap[ name ];
36046 time = animation.time;
36054 THREE.MorphBlendMesh.prototype.getAnimationDuration =
function ( name ) {
36056 var duration = - 1;
36058 var animation = this.animationsMap[ name ];
36062 duration = animation.duration;
36070 THREE.MorphBlendMesh.prototype.playAnimation =
function ( name ) {
36072 var animation = this.animationsMap[ name ];
36076 animation.time = 0;
36077 animation.active =
true;
36081 console.warn(
"THREE.MorphBlendMesh: animation[" + name +
"] undefined in .playAnimation()" );
36087 THREE.MorphBlendMesh.prototype.stopAnimation =
function ( name ) {
36089 var animation = this.animationsMap[ name ];
36093 animation.active =
false;
36099 THREE.MorphBlendMesh.prototype.update =
function ( delta ) {
36101 for ( var i = 0, il = this.animationsList.length; i < il; i ++ ) {
36103 var animation = this.animationsList[ i ];
36105 if ( ! animation.active )
continue;
36107 var frameTime = animation.duration / animation.length;
36109 animation.time += animation.direction * delta;
36111 if ( animation.mirroredLoop ) {
36113 if ( animation.time > animation.duration || animation.time < 0 ) {
36115 animation.direction *= - 1;
36117 if ( animation.time > animation.duration ) {
36119 animation.time = animation.duration;
36120 animation.directionBackwards =
true;
36124 if ( animation.time < 0 ) {
36126 animation.time = 0;
36127 animation.directionBackwards =
false;
36135 animation.time = animation.time % animation.duration;
36137 if ( animation.time < 0 ) animation.time += animation.duration;
36141 var keyframe = animation.start + THREE.Math.clamp( Math.floor( animation.time / frameTime ), 0, animation.length - 1 );
36142 var weight = animation.weight;
36144 if ( keyframe !== animation.currentFrame ) {
36146 this.morphTargetInfluences[ animation.lastFrame ] = 0;
36147 this.morphTargetInfluences[ animation.currentFrame ] = 1 * weight;
36149 this.morphTargetInfluences[ keyframe ] = 0;
36151 animation.lastFrame = animation.currentFrame;
36152 animation.currentFrame = keyframe;
36156 var mix = ( animation.time % frameTime ) / frameTime;
36158 if ( animation.directionBackwards ) mix = 1 - mix;
36160 if ( animation.currentFrame !== animation.lastFrame ) {
36162 this.morphTargetInfluences[ animation.currentFrame ] = mix * weight;
36163 this.morphTargetInfluences[ animation.lastFrame ] = ( 1 - mix ) * weight;
36167 this.morphTargetInfluences[ animation.currentFrame ] = weight;