|
@@ -0,0 +1,1447 @@
|
|
|
+/**
|
|
|
+* @author mrdoob / http://mrdoob.com/
|
|
|
+*/
|
|
|
+
|
|
|
+THREE.WebGLBuffers = function ( gl, info, extensions, getBufferMaterial ) {
|
|
|
+
|
|
|
+ function initCustomAttributes ( object ) {
|
|
|
+
|
|
|
+ var geometry = object.geometry;
|
|
|
+ var material = object.material;
|
|
|
+
|
|
|
+ var nvertices = geometry.vertices.length;
|
|
|
+
|
|
|
+ if ( material.attributes ) {
|
|
|
+
|
|
|
+ if ( geometry.__webglCustomAttributesList === undefined ) {
|
|
|
+
|
|
|
+ geometry.__webglCustomAttributesList = [];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ for ( var name in material.attributes ) {
|
|
|
+
|
|
|
+ var attribute = material.attributes[ name ];
|
|
|
+
|
|
|
+ if ( ! attribute.__webglInitialized || attribute.createUniqueBuffers ) {
|
|
|
+
|
|
|
+ attribute.__webglInitialized = true;
|
|
|
+
|
|
|
+ var size = 1; // "f" and "i"
|
|
|
+
|
|
|
+ if ( attribute.type === 'v2' ) size = 2;
|
|
|
+ else if ( attribute.type === 'v3' ) size = 3;
|
|
|
+ else if ( attribute.type === 'v4' ) size = 4;
|
|
|
+ else if ( attribute.type === 'c' ) size = 3;
|
|
|
+
|
|
|
+ attribute.size = size;
|
|
|
+
|
|
|
+ attribute.array = new Float32Array( nvertices * size );
|
|
|
+
|
|
|
+ attribute.buffer = gl.createBuffer();
|
|
|
+ attribute.buffer.belongsToAttribute = name;
|
|
|
+
|
|
|
+ attribute.needsUpdate = true;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ geometry.__webglCustomAttributesList.push( attribute );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ };
|
|
|
+
|
|
|
+ this.initParticleBuffers = function ( geometry, object ) {
|
|
|
+
|
|
|
+ geometry.__webglVertexBuffer = gl.createBuffer();
|
|
|
+ geometry.__webglColorBuffer = gl.createBuffer();
|
|
|
+
|
|
|
+ info.memory.geometries ++;
|
|
|
+
|
|
|
+ //
|
|
|
+
|
|
|
+ var nvertices = geometry.vertices.length;
|
|
|
+
|
|
|
+ geometry.__vertexArray = new Float32Array( nvertices * 3 );
|
|
|
+ geometry.__colorArray = new Float32Array( nvertices * 3 );
|
|
|
+
|
|
|
+ geometry.__webglParticleCount = nvertices;
|
|
|
+
|
|
|
+ initCustomAttributes( object );
|
|
|
+
|
|
|
+ };
|
|
|
+
|
|
|
+ this.initLineBuffers = function ( geometry, object ) {
|
|
|
+
|
|
|
+ geometry.__webglVertexBuffer = gl.createBuffer();
|
|
|
+ geometry.__webglColorBuffer = gl.createBuffer();
|
|
|
+ geometry.__webglLineDistanceBuffer = gl.createBuffer();
|
|
|
+
|
|
|
+ info.memory.geometries ++;
|
|
|
+
|
|
|
+ //
|
|
|
+
|
|
|
+ var nvertices = geometry.vertices.length;
|
|
|
+
|
|
|
+ geometry.__vertexArray = new Float32Array( nvertices * 3 );
|
|
|
+ geometry.__colorArray = new Float32Array( nvertices * 3 );
|
|
|
+ geometry.__lineDistanceArray = new Float32Array( nvertices * 1 );
|
|
|
+
|
|
|
+ geometry.__webglLineCount = nvertices;
|
|
|
+
|
|
|
+ initCustomAttributes( object );
|
|
|
+
|
|
|
+ };
|
|
|
+
|
|
|
+ this.initMeshBuffers = function ( geometryGroup, object ) {
|
|
|
+
|
|
|
+ geometryGroup.__webglVertexBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglNormalBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglTangentBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglColorBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglUVBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglUV2Buffer = gl.createBuffer();
|
|
|
+
|
|
|
+ geometryGroup.__webglSkinIndicesBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglSkinWeightsBuffer = gl.createBuffer();
|
|
|
+
|
|
|
+ geometryGroup.__webglFaceBuffer = gl.createBuffer();
|
|
|
+ geometryGroup.__webglLineBuffer = gl.createBuffer();
|
|
|
+
|
|
|
+ var numMorphTargets = geometryGroup.numMorphTargets;
|
|
|
+
|
|
|
+ if ( numMorphTargets ) {
|
|
|
+
|
|
|
+ geometryGroup.__webglMorphTargetsBuffers = [];
|
|
|
+
|
|
|
+ for ( var m = 0, ml = numMorphTargets; m < ml; m ++ ) {
|
|
|
+
|
|
|
+ geometryGroup.__webglMorphTargetsBuffers.push( gl.createBuffer() );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ var numMorphNormals = geometryGroup.numMorphNormals;
|
|
|
+
|
|
|
+ if ( numMorphNormals ) {
|
|
|
+
|
|
|
+ geometryGroup.__webglMorphNormalsBuffers = [];
|
|
|
+
|
|
|
+ for ( var m = 0, ml = numMorphNormals; m < ml; m ++ ) {
|
|
|
+
|
|
|
+ geometryGroup.__webglMorphNormalsBuffers.push( gl.createBuffer() );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ info.memory.geometries ++;
|
|
|
+
|
|
|
+ //
|
|
|
+
|
|
|
+ var geometry = object.geometry,
|
|
|
+ faces3 = geometryGroup.faces3,
|
|
|
+
|
|
|
+ nvertices = faces3.length * 3,
|
|
|
+ ntris = faces3.length * 1,
|
|
|
+ nlines = faces3.length * 3,
|
|
|
+
|
|
|
+ material = getBufferMaterial( object, geometryGroup );
|
|
|
+
|
|
|
+ geometryGroup.__vertexArray = new Float32Array( nvertices * 3 );
|
|
|
+ geometryGroup.__normalArray = new Float32Array( nvertices * 3 );
|
|
|
+ geometryGroup.__colorArray = new Float32Array( nvertices * 3 );
|
|
|
+ geometryGroup.__uvArray = new Float32Array( nvertices * 2 );
|
|
|
+
|
|
|
+ if ( geometry.faceVertexUvs.length > 1 ) {
|
|
|
+
|
|
|
+ geometryGroup.__uv2Array = new Float32Array( nvertices * 2 );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( geometry.hasTangents ) {
|
|
|
+
|
|
|
+ geometryGroup.__tangentArray = new Float32Array( nvertices * 4 );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( object.geometry.skinWeights.length && object.geometry.skinIndices.length ) {
|
|
|
+
|
|
|
+ geometryGroup.__skinIndexArray = new Float32Array( nvertices * 4 );
|
|
|
+ geometryGroup.__skinWeightArray = new Float32Array( nvertices * 4 );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ var UintArray = extensions.get( 'OES_element_index_uint' ) !== null && ntris > 21845 ? Uint32Array : Uint16Array; // 65535 / 3
|
|
|
+
|
|
|
+ geometryGroup.__typeArray = UintArray;
|
|
|
+ geometryGroup.__faceArray = new UintArray( ntris * 3 );
|
|
|
+ geometryGroup.__lineArray = new UintArray( nlines * 2 );
|
|
|
+
|
|
|
+ if ( numMorphTargets ) {
|
|
|
+
|
|
|
+ geometryGroup.__morphTargetsArrays = [];
|
|
|
+
|
|
|
+ for ( var m = 0, ml = numMorphTargets; m < ml; m ++ ) {
|
|
|
+
|
|
|
+ geometryGroup.__morphTargetsArrays.push( new Float32Array( nvertices * 3 ) );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( numMorphNormals ) {
|
|
|
+
|
|
|
+ geometryGroup.__morphNormalsArrays = [];
|
|
|
+
|
|
|
+ for ( var m = 0, ml = numMorphNormals; m < ml; m ++ ) {
|
|
|
+
|
|
|
+ geometryGroup.__morphNormalsArrays.push( new Float32Array( nvertices * 3 ) );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ geometryGroup.__webglFaceCount = ntris * 3;
|
|
|
+ geometryGroup.__webglLineCount = nlines * 2;
|
|
|
+
|
|
|
+
|
|
|
+ // custom attributes
|
|
|
+
|
|
|
+ if ( material.attributes ) {
|
|
|
+
|
|
|
+ if ( geometryGroup.__webglCustomAttributesList === undefined ) {
|
|
|
+
|
|
|
+ geometryGroup.__webglCustomAttributesList = [];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ for ( var name in material.attributes ) {
|
|
|
+
|
|
|
+ // Do a shallow copy of the attribute object so different geometryGroup chunks use different
|
|
|
+ // attribute buffers which are correctly indexed in the setMeshBuffers function
|
|
|
+
|
|
|
+ var originalAttribute = material.attributes[ name ];
|
|
|
+
|
|
|
+ var attribute = {};
|
|
|
+
|
|
|
+ for ( var property in originalAttribute ) {
|
|
|
+
|
|
|
+ attribute[ property ] = originalAttribute[ property ];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( ! attribute.__webglInitialized || attribute.createUniqueBuffers ) {
|
|
|
+
|
|
|
+ attribute.__webglInitialized = true;
|
|
|
+
|
|
|
+ var size = 1; // "f" and "i"
|
|
|
+
|
|
|
+ if ( attribute.type === 'v2' ) size = 2;
|
|
|
+ else if ( attribute.type === 'v3' ) size = 3;
|
|
|
+ else if ( attribute.type === 'v4' ) size = 4;
|
|
|
+ else if ( attribute.type === 'c' ) size = 3;
|
|
|
+
|
|
|
+ attribute.size = size;
|
|
|
+
|
|
|
+ attribute.array = new Float32Array( nvertices * size );
|
|
|
+
|
|
|
+ attribute.buffer = gl.createBuffer();
|
|
|
+ attribute.buffer.belongsToAttribute = name;
|
|
|
+
|
|
|
+ originalAttribute.needsUpdate = true;
|
|
|
+ attribute.__original = originalAttribute;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ geometryGroup.__webglCustomAttributesList.push( attribute );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ geometryGroup.__inittedArrays = true;
|
|
|
+
|
|
|
+ };
|
|
|
+
|
|
|
+ // Buffer setting
|
|
|
+
|
|
|
+ this.setParticleBuffers = function ( geometry, hint, object ) {
|
|
|
+
|
|
|
+ var v, c, vertex, offset, color,
|
|
|
+
|
|
|
+ vertices = geometry.vertices,
|
|
|
+ vl = vertices.length,
|
|
|
+
|
|
|
+ colors = geometry.colors,
|
|
|
+ cl = colors.length,
|
|
|
+
|
|
|
+ vertexArray = geometry.__vertexArray,
|
|
|
+ colorArray = geometry.__colorArray,
|
|
|
+
|
|
|
+ dirtyVertices = geometry.verticesNeedUpdate,
|
|
|
+ dirtyColors = geometry.colorsNeedUpdate,
|
|
|
+
|
|
|
+ customAttributes = geometry.__webglCustomAttributesList,
|
|
|
+ i, il,
|
|
|
+ ca, cal, value,
|
|
|
+ customAttribute;
|
|
|
+
|
|
|
+ if ( dirtyVertices ) {
|
|
|
+
|
|
|
+ for ( v = 0; v < vl; v ++ ) {
|
|
|
+
|
|
|
+ vertex = vertices[ v ];
|
|
|
+
|
|
|
+ offset = v * 3;
|
|
|
+
|
|
|
+ vertexArray[ offset ] = vertex.x;
|
|
|
+ vertexArray[ offset + 1 ] = vertex.y;
|
|
|
+ vertexArray[ offset + 2 ] = vertex.z;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometry.__webglVertexBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, vertexArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyColors ) {
|
|
|
+
|
|
|
+ for ( c = 0; c < cl; c ++ ) {
|
|
|
+
|
|
|
+ color = colors[ c ];
|
|
|
+
|
|
|
+ offset = c * 3;
|
|
|
+
|
|
|
+ colorArray[ offset ] = color.r;
|
|
|
+ colorArray[ offset + 1 ] = color.g;
|
|
|
+ colorArray[ offset + 2 ] = color.b;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometry.__webglColorBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, colorArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( customAttributes ) {
|
|
|
+
|
|
|
+ for ( i = 0, il = customAttributes.length; i < il; i ++ ) {
|
|
|
+
|
|
|
+ customAttribute = customAttributes[ i ];
|
|
|
+
|
|
|
+ if ( customAttribute.needsUpdate && ( customAttribute.boundTo === undefined || customAttribute.boundTo === 'vertices' ) ) {
|
|
|
+
|
|
|
+ cal = customAttribute.value.length;
|
|
|
+
|
|
|
+ offset = 0;
|
|
|
+
|
|
|
+ if ( customAttribute.size === 1 ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ customAttribute.array[ ca ] = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 2 ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.x;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.y;
|
|
|
+
|
|
|
+ offset += 2;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 3 ) {
|
|
|
+
|
|
|
+ if ( customAttribute.type === 'c' ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.r;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.g;
|
|
|
+ customAttribute.array[ offset + 2 ] = value.b;
|
|
|
+
|
|
|
+ offset += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.x;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.y;
|
|
|
+ customAttribute.array[ offset + 2 ] = value.z;
|
|
|
+
|
|
|
+ offset += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 4 ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.x;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.y;
|
|
|
+ customAttribute.array[ offset + 2 ] = value.z;
|
|
|
+ customAttribute.array[ offset + 3 ] = value.w;
|
|
|
+
|
|
|
+ offset += 4;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, customAttribute.buffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, customAttribute.array, hint );
|
|
|
+
|
|
|
+ customAttribute.needsUpdate = false;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ this.setLineBuffers = function ( geometry, hint ) {
|
|
|
+
|
|
|
+ var v, c, d, vertex, offset, color,
|
|
|
+
|
|
|
+ vertices = geometry.vertices,
|
|
|
+ colors = geometry.colors,
|
|
|
+ lineDistances = geometry.lineDistances,
|
|
|
+
|
|
|
+ vl = vertices.length,
|
|
|
+ cl = colors.length,
|
|
|
+ dl = lineDistances.length,
|
|
|
+
|
|
|
+ vertexArray = geometry.__vertexArray,
|
|
|
+ colorArray = geometry.__colorArray,
|
|
|
+ lineDistanceArray = geometry.__lineDistanceArray,
|
|
|
+
|
|
|
+ dirtyVertices = geometry.verticesNeedUpdate,
|
|
|
+ dirtyColors = geometry.colorsNeedUpdate,
|
|
|
+ dirtyLineDistances = geometry.lineDistancesNeedUpdate,
|
|
|
+
|
|
|
+ customAttributes = geometry.__webglCustomAttributesList,
|
|
|
+
|
|
|
+ i, il,
|
|
|
+ ca, cal, value,
|
|
|
+ customAttribute;
|
|
|
+
|
|
|
+ if ( dirtyVertices ) {
|
|
|
+
|
|
|
+ for ( v = 0; v < vl; v ++ ) {
|
|
|
+
|
|
|
+ vertex = vertices[ v ];
|
|
|
+
|
|
|
+ offset = v * 3;
|
|
|
+
|
|
|
+ vertexArray[ offset ] = vertex.x;
|
|
|
+ vertexArray[ offset + 1 ] = vertex.y;
|
|
|
+ vertexArray[ offset + 2 ] = vertex.z;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometry.__webglVertexBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, vertexArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyColors ) {
|
|
|
+
|
|
|
+ for ( c = 0; c < cl; c ++ ) {
|
|
|
+
|
|
|
+ color = colors[ c ];
|
|
|
+
|
|
|
+ offset = c * 3;
|
|
|
+
|
|
|
+ colorArray[ offset ] = color.r;
|
|
|
+ colorArray[ offset + 1 ] = color.g;
|
|
|
+ colorArray[ offset + 2 ] = color.b;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometry.__webglColorBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, colorArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyLineDistances ) {
|
|
|
+
|
|
|
+ for ( d = 0; d < dl; d ++ ) {
|
|
|
+
|
|
|
+ lineDistanceArray[ d ] = lineDistances[ d ];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometry.__webglLineDistanceBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, lineDistanceArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( customAttributes ) {
|
|
|
+
|
|
|
+ for ( i = 0, il = customAttributes.length; i < il; i ++ ) {
|
|
|
+
|
|
|
+ customAttribute = customAttributes[ i ];
|
|
|
+
|
|
|
+ if ( customAttribute.needsUpdate && ( customAttribute.boundTo === undefined || customAttribute.boundTo === 'vertices' ) ) {
|
|
|
+
|
|
|
+ offset = 0;
|
|
|
+
|
|
|
+ cal = customAttribute.value.length;
|
|
|
+
|
|
|
+ if ( customAttribute.size === 1 ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ customAttribute.array[ ca ] = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 2 ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.x;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.y;
|
|
|
+
|
|
|
+ offset += 2;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 3 ) {
|
|
|
+
|
|
|
+ if ( customAttribute.type === 'c' ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.r;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.g;
|
|
|
+ customAttribute.array[ offset + 2 ] = value.b;
|
|
|
+
|
|
|
+ offset += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.x;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.y;
|
|
|
+ customAttribute.array[ offset + 2 ] = value.z;
|
|
|
+
|
|
|
+ offset += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 4 ) {
|
|
|
+
|
|
|
+ for ( ca = 0; ca < cal; ca ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ ca ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset ] = value.x;
|
|
|
+ customAttribute.array[ offset + 1 ] = value.y;
|
|
|
+ customAttribute.array[ offset + 2 ] = value.z;
|
|
|
+ customAttribute.array[ offset + 3 ] = value.w;
|
|
|
+
|
|
|
+ offset += 4;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, customAttribute.buffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, customAttribute.array, hint );
|
|
|
+
|
|
|
+ customAttribute.needsUpdate = false;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ function materialNeedsFaceNormals ( material ) {
|
|
|
+
|
|
|
+ return material instanceof THREE.MeshPhongMaterial === false && material.shading === THREE.FlatShading;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ this.setMeshBuffers = function ( geometryGroup, object, hint, dispose, material ) {
|
|
|
+
|
|
|
+ if ( ! geometryGroup.__inittedArrays ) {
|
|
|
+
|
|
|
+ return;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ var needsFaceNormals = materialNeedsFaceNormals( material );
|
|
|
+
|
|
|
+ var f, fl, fi, face,
|
|
|
+ vertexNormals, faceNormal,
|
|
|
+ vertexColors, faceColor,
|
|
|
+ vertexTangents,
|
|
|
+ uv, uv2, v1, v2, v3, t1, t2, t3, n1, n2, n3,
|
|
|
+ c1, c2, c3,
|
|
|
+ sw1, sw2, sw3,
|
|
|
+ si1, si2, si3,
|
|
|
+ i, il,
|
|
|
+ vn, uvi, uv2i,
|
|
|
+ vk, vkl, vka,
|
|
|
+ nka, chf, faceVertexNormals,
|
|
|
+
|
|
|
+ vertexIndex = 0,
|
|
|
+
|
|
|
+ offset = 0,
|
|
|
+ offset_uv = 0,
|
|
|
+ offset_uv2 = 0,
|
|
|
+ offset_face = 0,
|
|
|
+ offset_normal = 0,
|
|
|
+ offset_tangent = 0,
|
|
|
+ offset_line = 0,
|
|
|
+ offset_color = 0,
|
|
|
+ offset_skin = 0,
|
|
|
+ offset_morphTarget = 0,
|
|
|
+ offset_custom = 0,
|
|
|
+
|
|
|
+ value,
|
|
|
+
|
|
|
+ vertexArray = geometryGroup.__vertexArray,
|
|
|
+ uvArray = geometryGroup.__uvArray,
|
|
|
+ uv2Array = geometryGroup.__uv2Array,
|
|
|
+ normalArray = geometryGroup.__normalArray,
|
|
|
+ tangentArray = geometryGroup.__tangentArray,
|
|
|
+ colorArray = geometryGroup.__colorArray,
|
|
|
+
|
|
|
+ skinIndexArray = geometryGroup.__skinIndexArray,
|
|
|
+ skinWeightArray = geometryGroup.__skinWeightArray,
|
|
|
+
|
|
|
+ morphTargetsArrays = geometryGroup.__morphTargetsArrays,
|
|
|
+ morphNormalsArrays = geometryGroup.__morphNormalsArrays,
|
|
|
+
|
|
|
+ customAttributes = geometryGroup.__webglCustomAttributesList,
|
|
|
+ customAttribute,
|
|
|
+
|
|
|
+ faceArray = geometryGroup.__faceArray,
|
|
|
+ lineArray = geometryGroup.__lineArray,
|
|
|
+
|
|
|
+ geometry = object.geometry, // this is shared for all chunks
|
|
|
+
|
|
|
+ dirtyVertices = geometry.verticesNeedUpdate,
|
|
|
+ dirtyElements = geometry.elementsNeedUpdate,
|
|
|
+ dirtyUvs = geometry.uvsNeedUpdate,
|
|
|
+ dirtyNormals = geometry.normalsNeedUpdate,
|
|
|
+ dirtyTangents = geometry.tangentsNeedUpdate,
|
|
|
+ dirtyColors = geometry.colorsNeedUpdate,
|
|
|
+ dirtyMorphTargets = geometry.morphTargetsNeedUpdate,
|
|
|
+
|
|
|
+ vertices = geometry.vertices,
|
|
|
+ chunk_faces3 = geometryGroup.faces3,
|
|
|
+ obj_faces = geometry.faces,
|
|
|
+
|
|
|
+ obj_uvs = geometry.faceVertexUvs[ 0 ],
|
|
|
+ obj_uvs2 = geometry.faceVertexUvs[ 1 ],
|
|
|
+
|
|
|
+ obj_skinIndices = geometry.skinIndices,
|
|
|
+ obj_skinWeights = geometry.skinWeights,
|
|
|
+
|
|
|
+ morphTargets = geometry.morphTargets,
|
|
|
+ morphNormals = geometry.morphNormals;
|
|
|
+
|
|
|
+ if ( dirtyVertices ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = vertices[ face.a ];
|
|
|
+ v2 = vertices[ face.b ];
|
|
|
+ v3 = vertices[ face.c ];
|
|
|
+
|
|
|
+ vertexArray[ offset ] = v1.x;
|
|
|
+ vertexArray[ offset + 1 ] = v1.y;
|
|
|
+ vertexArray[ offset + 2 ] = v1.z;
|
|
|
+
|
|
|
+ vertexArray[ offset + 3 ] = v2.x;
|
|
|
+ vertexArray[ offset + 4 ] = v2.y;
|
|
|
+ vertexArray[ offset + 5 ] = v2.z;
|
|
|
+
|
|
|
+ vertexArray[ offset + 6 ] = v3.x;
|
|
|
+ vertexArray[ offset + 7 ] = v3.y;
|
|
|
+ vertexArray[ offset + 8 ] = v3.z;
|
|
|
+
|
|
|
+ offset += 9;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglVertexBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, vertexArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyMorphTargets ) {
|
|
|
+
|
|
|
+ for ( vk = 0, vkl = morphTargets.length; vk < vkl; vk ++ ) {
|
|
|
+
|
|
|
+ offset_morphTarget = 0;
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ chf = chunk_faces3[ f ];
|
|
|
+ face = obj_faces[ chf ];
|
|
|
+
|
|
|
+ // morph positions
|
|
|
+
|
|
|
+ v1 = morphTargets[ vk ].vertices[ face.a ];
|
|
|
+ v2 = morphTargets[ vk ].vertices[ face.b ];
|
|
|
+ v3 = morphTargets[ vk ].vertices[ face.c ];
|
|
|
+
|
|
|
+ vka = morphTargetsArrays[ vk ];
|
|
|
+
|
|
|
+ vka[ offset_morphTarget ] = v1.x;
|
|
|
+ vka[ offset_morphTarget + 1 ] = v1.y;
|
|
|
+ vka[ offset_morphTarget + 2 ] = v1.z;
|
|
|
+
|
|
|
+ vka[ offset_morphTarget + 3 ] = v2.x;
|
|
|
+ vka[ offset_morphTarget + 4 ] = v2.y;
|
|
|
+ vka[ offset_morphTarget + 5 ] = v2.z;
|
|
|
+
|
|
|
+ vka[ offset_morphTarget + 6 ] = v3.x;
|
|
|
+ vka[ offset_morphTarget + 7 ] = v3.y;
|
|
|
+ vka[ offset_morphTarget + 8 ] = v3.z;
|
|
|
+
|
|
|
+ // morph normals
|
|
|
+
|
|
|
+ if ( material.morphNormals ) {
|
|
|
+
|
|
|
+ if ( needsFaceNormals ) {
|
|
|
+
|
|
|
+ n1 = morphNormals[ vk ].faceNormals[ chf ];
|
|
|
+ n2 = n1;
|
|
|
+ n3 = n1;
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ faceVertexNormals = morphNormals[ vk ].vertexNormals[ chf ];
|
|
|
+
|
|
|
+ n1 = faceVertexNormals.a;
|
|
|
+ n2 = faceVertexNormals.b;
|
|
|
+ n3 = faceVertexNormals.c;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ nka = morphNormalsArrays[ vk ];
|
|
|
+
|
|
|
+ nka[ offset_morphTarget ] = n1.x;
|
|
|
+ nka[ offset_morphTarget + 1 ] = n1.y;
|
|
|
+ nka[ offset_morphTarget + 2 ] = n1.z;
|
|
|
+
|
|
|
+ nka[ offset_morphTarget + 3 ] = n2.x;
|
|
|
+ nka[ offset_morphTarget + 4 ] = n2.y;
|
|
|
+ nka[ offset_morphTarget + 5 ] = n2.z;
|
|
|
+
|
|
|
+ nka[ offset_morphTarget + 6 ] = n3.x;
|
|
|
+ nka[ offset_morphTarget + 7 ] = n3.y;
|
|
|
+ nka[ offset_morphTarget + 8 ] = n3.z;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ //
|
|
|
+
|
|
|
+ offset_morphTarget += 9;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglMorphTargetsBuffers[ vk ] );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, morphTargetsArrays[ vk ], hint );
|
|
|
+
|
|
|
+ if ( material.morphNormals ) {
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglMorphNormalsBuffers[ vk ] );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, morphNormalsArrays[ vk ], hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( obj_skinWeights.length ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ // weights
|
|
|
+
|
|
|
+ sw1 = obj_skinWeights[ face.a ];
|
|
|
+ sw2 = obj_skinWeights[ face.b ];
|
|
|
+ sw3 = obj_skinWeights[ face.c ];
|
|
|
+
|
|
|
+ skinWeightArray[ offset_skin ] = sw1.x;
|
|
|
+ skinWeightArray[ offset_skin + 1 ] = sw1.y;
|
|
|
+ skinWeightArray[ offset_skin + 2 ] = sw1.z;
|
|
|
+ skinWeightArray[ offset_skin + 3 ] = sw1.w;
|
|
|
+
|
|
|
+ skinWeightArray[ offset_skin + 4 ] = sw2.x;
|
|
|
+ skinWeightArray[ offset_skin + 5 ] = sw2.y;
|
|
|
+ skinWeightArray[ offset_skin + 6 ] = sw2.z;
|
|
|
+ skinWeightArray[ offset_skin + 7 ] = sw2.w;
|
|
|
+
|
|
|
+ skinWeightArray[ offset_skin + 8 ] = sw3.x;
|
|
|
+ skinWeightArray[ offset_skin + 9 ] = sw3.y;
|
|
|
+ skinWeightArray[ offset_skin + 10 ] = sw3.z;
|
|
|
+ skinWeightArray[ offset_skin + 11 ] = sw3.w;
|
|
|
+
|
|
|
+ // indices
|
|
|
+
|
|
|
+ si1 = obj_skinIndices[ face.a ];
|
|
|
+ si2 = obj_skinIndices[ face.b ];
|
|
|
+ si3 = obj_skinIndices[ face.c ];
|
|
|
+
|
|
|
+ skinIndexArray[ offset_skin ] = si1.x;
|
|
|
+ skinIndexArray[ offset_skin + 1 ] = si1.y;
|
|
|
+ skinIndexArray[ offset_skin + 2 ] = si1.z;
|
|
|
+ skinIndexArray[ offset_skin + 3 ] = si1.w;
|
|
|
+
|
|
|
+ skinIndexArray[ offset_skin + 4 ] = si2.x;
|
|
|
+ skinIndexArray[ offset_skin + 5 ] = si2.y;
|
|
|
+ skinIndexArray[ offset_skin + 6 ] = si2.z;
|
|
|
+ skinIndexArray[ offset_skin + 7 ] = si2.w;
|
|
|
+
|
|
|
+ skinIndexArray[ offset_skin + 8 ] = si3.x;
|
|
|
+ skinIndexArray[ offset_skin + 9 ] = si3.y;
|
|
|
+ skinIndexArray[ offset_skin + 10 ] = si3.z;
|
|
|
+ skinIndexArray[ offset_skin + 11 ] = si3.w;
|
|
|
+
|
|
|
+ offset_skin += 12;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( offset_skin > 0 ) {
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglSkinIndicesBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, skinIndexArray, hint );
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglSkinWeightsBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, skinWeightArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyColors ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ vertexColors = face.vertexColors;
|
|
|
+ faceColor = face.color;
|
|
|
+
|
|
|
+ if ( vertexColors.length === 3 && material.vertexColors === THREE.VertexColors ) {
|
|
|
+
|
|
|
+ c1 = vertexColors[ 0 ];
|
|
|
+ c2 = vertexColors[ 1 ];
|
|
|
+ c3 = vertexColors[ 2 ];
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ c1 = faceColor;
|
|
|
+ c2 = faceColor;
|
|
|
+ c3 = faceColor;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ colorArray[ offset_color ] = c1.r;
|
|
|
+ colorArray[ offset_color + 1 ] = c1.g;
|
|
|
+ colorArray[ offset_color + 2 ] = c1.b;
|
|
|
+
|
|
|
+ colorArray[ offset_color + 3 ] = c2.r;
|
|
|
+ colorArray[ offset_color + 4 ] = c2.g;
|
|
|
+ colorArray[ offset_color + 5 ] = c2.b;
|
|
|
+
|
|
|
+ colorArray[ offset_color + 6 ] = c3.r;
|
|
|
+ colorArray[ offset_color + 7 ] = c3.g;
|
|
|
+ colorArray[ offset_color + 8 ] = c3.b;
|
|
|
+
|
|
|
+ offset_color += 9;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( offset_color > 0 ) {
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglColorBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, colorArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyTangents && geometry.hasTangents ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ vertexTangents = face.vertexTangents;
|
|
|
+
|
|
|
+ t1 = vertexTangents[ 0 ];
|
|
|
+ t2 = vertexTangents[ 1 ];
|
|
|
+ t3 = vertexTangents[ 2 ];
|
|
|
+
|
|
|
+ tangentArray[ offset_tangent ] = t1.x;
|
|
|
+ tangentArray[ offset_tangent + 1 ] = t1.y;
|
|
|
+ tangentArray[ offset_tangent + 2 ] = t1.z;
|
|
|
+ tangentArray[ offset_tangent + 3 ] = t1.w;
|
|
|
+
|
|
|
+ tangentArray[ offset_tangent + 4 ] = t2.x;
|
|
|
+ tangentArray[ offset_tangent + 5 ] = t2.y;
|
|
|
+ tangentArray[ offset_tangent + 6 ] = t2.z;
|
|
|
+ tangentArray[ offset_tangent + 7 ] = t2.w;
|
|
|
+
|
|
|
+ tangentArray[ offset_tangent + 8 ] = t3.x;
|
|
|
+ tangentArray[ offset_tangent + 9 ] = t3.y;
|
|
|
+ tangentArray[ offset_tangent + 10 ] = t3.z;
|
|
|
+ tangentArray[ offset_tangent + 11 ] = t3.w;
|
|
|
+
|
|
|
+ offset_tangent += 12;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglTangentBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, tangentArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyNormals ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ vertexNormals = face.vertexNormals;
|
|
|
+ faceNormal = face.normal;
|
|
|
+
|
|
|
+ if ( vertexNormals.length === 3 && needsFaceNormals === false ) {
|
|
|
+
|
|
|
+ for ( i = 0; i < 3; i ++ ) {
|
|
|
+
|
|
|
+ vn = vertexNormals[ i ];
|
|
|
+
|
|
|
+ normalArray[ offset_normal ] = vn.x;
|
|
|
+ normalArray[ offset_normal + 1 ] = vn.y;
|
|
|
+ normalArray[ offset_normal + 2 ] = vn.z;
|
|
|
+
|
|
|
+ offset_normal += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ for ( i = 0; i < 3; i ++ ) {
|
|
|
+
|
|
|
+ normalArray[ offset_normal ] = faceNormal.x;
|
|
|
+ normalArray[ offset_normal + 1 ] = faceNormal.y;
|
|
|
+ normalArray[ offset_normal + 2 ] = faceNormal.z;
|
|
|
+
|
|
|
+ offset_normal += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglNormalBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, normalArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyUvs && obj_uvs ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ fi = chunk_faces3[ f ];
|
|
|
+
|
|
|
+ uv = obj_uvs[ fi ];
|
|
|
+
|
|
|
+ if ( uv === undefined ) continue;
|
|
|
+
|
|
|
+ for ( i = 0; i < 3; i ++ ) {
|
|
|
+
|
|
|
+ uvi = uv[ i ];
|
|
|
+
|
|
|
+ uvArray[ offset_uv ] = uvi.x;
|
|
|
+ uvArray[ offset_uv + 1 ] = uvi.y;
|
|
|
+
|
|
|
+ offset_uv += 2;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( offset_uv > 0 ) {
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglUVBuffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, uvArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyUvs && obj_uvs2 ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ fi = chunk_faces3[ f ];
|
|
|
+
|
|
|
+ uv2 = obj_uvs2[ fi ];
|
|
|
+
|
|
|
+ if ( uv2 === undefined ) continue;
|
|
|
+
|
|
|
+ for ( i = 0; i < 3; i ++ ) {
|
|
|
+
|
|
|
+ uv2i = uv2[ i ];
|
|
|
+
|
|
|
+ uv2Array[ offset_uv2 ] = uv2i.x;
|
|
|
+ uv2Array[ offset_uv2 + 1 ] = uv2i.y;
|
|
|
+
|
|
|
+ offset_uv2 += 2;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( offset_uv2 > 0 ) {
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, geometryGroup.__webglUV2Buffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, uv2Array, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dirtyElements ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ faceArray[ offset_face ] = vertexIndex;
|
|
|
+ faceArray[ offset_face + 1 ] = vertexIndex + 1;
|
|
|
+ faceArray[ offset_face + 2 ] = vertexIndex + 2;
|
|
|
+
|
|
|
+ offset_face += 3;
|
|
|
+
|
|
|
+ lineArray[ offset_line ] = vertexIndex;
|
|
|
+ lineArray[ offset_line + 1 ] = vertexIndex + 1;
|
|
|
+
|
|
|
+ lineArray[ offset_line + 2 ] = vertexIndex;
|
|
|
+ lineArray[ offset_line + 3 ] = vertexIndex + 2;
|
|
|
+
|
|
|
+ lineArray[ offset_line + 4 ] = vertexIndex + 1;
|
|
|
+ lineArray[ offset_line + 5 ] = vertexIndex + 2;
|
|
|
+
|
|
|
+ offset_line += 6;
|
|
|
+
|
|
|
+ vertexIndex += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, geometryGroup.__webglFaceBuffer );
|
|
|
+ gl.bufferData( gl.ELEMENT_ARRAY_BUFFER, faceArray, hint );
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, geometryGroup.__webglLineBuffer );
|
|
|
+ gl.bufferData( gl.ELEMENT_ARRAY_BUFFER, lineArray, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( customAttributes ) {
|
|
|
+
|
|
|
+ for ( i = 0, il = customAttributes.length; i < il; i ++ ) {
|
|
|
+
|
|
|
+ customAttribute = customAttributes[ i ];
|
|
|
+
|
|
|
+ if ( ! customAttribute.__original.needsUpdate ) continue;
|
|
|
+
|
|
|
+ offset_custom = 0;
|
|
|
+
|
|
|
+ if ( customAttribute.size === 1 ) {
|
|
|
+
|
|
|
+ if ( customAttribute.boundTo === undefined || customAttribute.boundTo === 'vertices' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = customAttribute.value[ face.a ];
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = customAttribute.value[ face.b ];
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = customAttribute.value[ face.c ];
|
|
|
+
|
|
|
+ offset_custom += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.boundTo === 'faces' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = value;
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = value;
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = value;
|
|
|
+
|
|
|
+ offset_custom += 3;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 2 ) {
|
|
|
+
|
|
|
+ if ( customAttribute.boundTo === undefined || customAttribute.boundTo === 'vertices' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = customAttribute.value[ face.a ];
|
|
|
+ v2 = customAttribute.value[ face.b ];
|
|
|
+ v3 = customAttribute.value[ face.c ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1.x;
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1.y;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v2.x;
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v2.y;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v3.x;
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v3.y;
|
|
|
+
|
|
|
+ offset_custom += 6;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.boundTo === 'faces' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = value;
|
|
|
+ v2 = value;
|
|
|
+ v3 = value;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1.x;
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1.y;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v2.x;
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v2.y;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v3.x;
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v3.y;
|
|
|
+
|
|
|
+ offset_custom += 6;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 3 ) {
|
|
|
+
|
|
|
+ var pp;
|
|
|
+
|
|
|
+ if ( customAttribute.type === 'c' ) {
|
|
|
+
|
|
|
+ pp = [ 'r', 'g', 'b' ];
|
|
|
+
|
|
|
+ } else {
|
|
|
+
|
|
|
+ pp = [ 'x', 'y', 'z' ];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( customAttribute.boundTo === undefined || customAttribute.boundTo === 'vertices' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = customAttribute.value[ face.a ];
|
|
|
+ v2 = customAttribute.value[ face.b ];
|
|
|
+ v3 = customAttribute.value[ face.c ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v1[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v2[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v2[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v2[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 6 ] = v3[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 7 ] = v3[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 8 ] = v3[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ offset_custom += 9;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.boundTo === 'faces' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = value;
|
|
|
+ v2 = value;
|
|
|
+ v3 = value;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v1[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v2[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v2[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v2[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 6 ] = v3[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 7 ] = v3[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 8 ] = v3[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ offset_custom += 9;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.boundTo === 'faceVertices' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = value[ 0 ];
|
|
|
+ v2 = value[ 1 ];
|
|
|
+ v3 = value[ 2 ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v1[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v2[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v2[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v2[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 6 ] = v3[ pp[ 0 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 7 ] = v3[ pp[ 1 ] ];
|
|
|
+ customAttribute.array[ offset_custom + 8 ] = v3[ pp[ 2 ] ];
|
|
|
+
|
|
|
+ offset_custom += 9;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.size === 4 ) {
|
|
|
+
|
|
|
+ if ( customAttribute.boundTo === undefined || customAttribute.boundTo === 'vertices' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ face = obj_faces[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = customAttribute.value[ face.a ];
|
|
|
+ v2 = customAttribute.value[ face.b ];
|
|
|
+ v3 = customAttribute.value[ face.c ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1.x;
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1.y;
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v1.z;
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v1.w;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v2.x;
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v2.y;
|
|
|
+ customAttribute.array[ offset_custom + 6 ] = v2.z;
|
|
|
+ customAttribute.array[ offset_custom + 7 ] = v2.w;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 8 ] = v3.x;
|
|
|
+ customAttribute.array[ offset_custom + 9 ] = v3.y;
|
|
|
+ customAttribute.array[ offset_custom + 10 ] = v3.z;
|
|
|
+ customAttribute.array[ offset_custom + 11 ] = v3.w;
|
|
|
+
|
|
|
+ offset_custom += 12;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.boundTo === 'faces' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = value;
|
|
|
+ v2 = value;
|
|
|
+ v3 = value;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1.x;
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1.y;
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v1.z;
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v1.w;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v2.x;
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v2.y;
|
|
|
+ customAttribute.array[ offset_custom + 6 ] = v2.z;
|
|
|
+ customAttribute.array[ offset_custom + 7 ] = v2.w;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 8 ] = v3.x;
|
|
|
+ customAttribute.array[ offset_custom + 9 ] = v3.y;
|
|
|
+ customAttribute.array[ offset_custom + 10 ] = v3.z;
|
|
|
+ customAttribute.array[ offset_custom + 11 ] = v3.w;
|
|
|
+
|
|
|
+ offset_custom += 12;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ } else if ( customAttribute.boundTo === 'faceVertices' ) {
|
|
|
+
|
|
|
+ for ( f = 0, fl = chunk_faces3.length; f < fl; f ++ ) {
|
|
|
+
|
|
|
+ value = customAttribute.value[ chunk_faces3[ f ] ];
|
|
|
+
|
|
|
+ v1 = value[ 0 ];
|
|
|
+ v2 = value[ 1 ];
|
|
|
+ v3 = value[ 2 ];
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom ] = v1.x;
|
|
|
+ customAttribute.array[ offset_custom + 1 ] = v1.y;
|
|
|
+ customAttribute.array[ offset_custom + 2 ] = v1.z;
|
|
|
+ customAttribute.array[ offset_custom + 3 ] = v1.w;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 4 ] = v2.x;
|
|
|
+ customAttribute.array[ offset_custom + 5 ] = v2.y;
|
|
|
+ customAttribute.array[ offset_custom + 6 ] = v2.z;
|
|
|
+ customAttribute.array[ offset_custom + 7 ] = v2.w;
|
|
|
+
|
|
|
+ customAttribute.array[ offset_custom + 8 ] = v3.x;
|
|
|
+ customAttribute.array[ offset_custom + 9 ] = v3.y;
|
|
|
+ customAttribute.array[ offset_custom + 10 ] = v3.z;
|
|
|
+ customAttribute.array[ offset_custom + 11 ] = v3.w;
|
|
|
+
|
|
|
+ offset_custom += 12;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ gl.bindBuffer( gl.ARRAY_BUFFER, customAttribute.buffer );
|
|
|
+ gl.bufferData( gl.ARRAY_BUFFER, customAttribute.array, hint );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if ( dispose ) {
|
|
|
+
|
|
|
+ delete geometryGroup.__inittedArrays;
|
|
|
+ delete geometryGroup.__colorArray;
|
|
|
+ delete geometryGroup.__normalArray;
|
|
|
+ delete geometryGroup.__tangentArray;
|
|
|
+ delete geometryGroup.__uvArray;
|
|
|
+ delete geometryGroup.__uv2Array;
|
|
|
+ delete geometryGroup.__faceArray;
|
|
|
+ delete geometryGroup.__vertexArray;
|
|
|
+ delete geometryGroup.__lineArray;
|
|
|
+ delete geometryGroup.__skinIndexArray;
|
|
|
+ delete geometryGroup.__skinWeightArray;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ };
|
|
|
+
|
|
|
+ this.delete = function ( geometry ) {
|
|
|
+
|
|
|
+ var buffers = [
|
|
|
+ '__webglVertexBuffer',
|
|
|
+ '__webglNormalBuffer',
|
|
|
+ '__webglTangentBuffer',
|
|
|
+ '__webglColorBuffer',
|
|
|
+ '__webglUVBuffer',
|
|
|
+ '__webglUV2Buffer',
|
|
|
+
|
|
|
+ '__webglSkinIndicesBuffer',
|
|
|
+ '__webglSkinWeightsBuffer',
|
|
|
+
|
|
|
+ '__webglFaceBuffer',
|
|
|
+ '__webglLineBuffer',
|
|
|
+
|
|
|
+ '__webglLineDistanceBuffer'
|
|
|
+ ];
|
|
|
+
|
|
|
+ for ( var i = 0, l = buffers.length; i < l; i ++ ) {
|
|
|
+
|
|
|
+ var name = buffers[ i ];
|
|
|
+
|
|
|
+ if ( geometry[ name ] !== undefined ) {
|
|
|
+
|
|
|
+ gl.deleteBuffer( geometry[ name ] );
|
|
|
+
|
|
|
+ delete geometry[ name ];
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ // custom attributes
|
|
|
+
|
|
|
+ if ( geometry.__webglCustomAttributesList !== undefined ) {
|
|
|
+
|
|
|
+ for ( var name in geometry.__webglCustomAttributesList ) {
|
|
|
+
|
|
|
+ gl.deleteBuffer( geometry.__webglCustomAttributesList[ name ].buffer );
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ delete geometry.__webglCustomAttributesList;
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ info.memory.geometries --;
|
|
|
+
|
|
|
+ };
|
|
|
+
|
|
|
+};
|