2
0
Эх сурвалжийг харах

Update VRMLLoader to support normals. #14814

Allows the VRMLLoader to import normals that are defined in the file.

Also fixes a bug where uvs would be an array filled with `undefined` values if model contained no UV coordinates.
Victor Glindås 7 жил өмнө
parent
commit
39f0917673

+ 71 - 10
examples/js/loaders/VRMLLoader.js

@@ -218,6 +218,7 @@ THREE.VRMLLoader.prototype = {
 						break;
 
 					case 'point':
+					case 'vector':
 						scope.recordingFieldname = fieldName;
 						scope.isRecordingPoints = true;
 						scope.points = [];
@@ -303,6 +304,22 @@ THREE.VRMLLoader.prototype = {
 
 					}
 
+					if ( node.nodeType == 'Normal' ) {
+
+  						while ( null !== ( parts = float3_pattern.exec( line ) ) ) {
+
+							point = {
+								x: parseFloat( parts[ 1 ] ),
+								y: parseFloat( parts[ 2 ] ),
+								z: parseFloat( parts[ 3 ] )
+							};
+
+							scope.points.push( point );
+
+						}
+
+					}
+
 					if ( node.nodeType == 'TextureCoordinate' ) {
 
 						while ( null !== ( parts = float2_pattern.exec( line ) ) ) {
@@ -793,9 +810,10 @@ THREE.VRMLLoader.prototype = {
 						var geometry = new THREE.BufferGeometry();
 
 						var positions = [];
+						var normals = [];
 						var uvs = [];
 
-						var position, uv;
+						var position, normal, uv;
 
 						var i, il, j, jl;
 
@@ -820,6 +838,23 @@ THREE.VRMLLoader.prototype = {
 
 							}
 
+							// normals
+
+							if ( child.nodeType === 'Normal' ) {
+
+								if ( child.points ) {
+
+									for ( j = 0, jl = child.points.length; j < jl; j ++ ) {
+
+										normal = child.points[ j ];
+										normals.push( normal.x, normal.y, normal.z );
+
+									}
+
+								}
+
+							}
+
 							// positions
 
 							if ( child.nodeType === 'Coordinate' ) {
@@ -862,9 +897,11 @@ THREE.VRMLLoader.prototype = {
 						if ( data.coordIndex ) {
 
 							var newPositions = [];
+							var newNormals = [];
 							var newUvs = [];
 
 							position = new THREE.Vector3();
+							normal = new THREE.Vector3();
 							uv = new THREE.Vector2();
 
 							for ( i = 0, il = data.coordIndex.length; i < il; i ++ ) {
@@ -886,19 +923,33 @@ THREE.VRMLLoader.prototype = {
 									// create non indexed geometry, necessary for face normal generation
 
 									position.fromArray( positions, i1 * 3 );
-									uv.fromArray( uvs, i1 * 2 );
 									newPositions.push( position.x, position.y, position.z );
-									newUvs.push( uv.x, uv.y );
-
 									position.fromArray( positions, i2 * 3 );
-									uv.fromArray( uvs, i2 * 2 );
 									newPositions.push( position.x, position.y, position.z );
-									newUvs.push( uv.x, uv.y );
-
 									position.fromArray( positions, i3 * 3 );
-									uv.fromArray( uvs, i3 * 2 );
 									newPositions.push( position.x, position.y, position.z );
-									newUvs.push( uv.x, uv.y );
+
+									if ( uvs.length > 0 ) {
+
+										uv.fromArray( uvs, i1 * 2 );
+										newUvs.push( uv.x, uv.y );
+										uv.fromArray( uvs, i2 * 2 );
+										newUvs.push( uv.x, uv.y );
+										uv.fromArray( uvs, i3 * 2 );
+										newUvs.push( uv.x, uv.y );
+
+									}
+
+									if ( normals.length > 0 ) {
+
+										normal.fromArray( normals, i1 * 3 );
+										newNormals.push( normal.x, normal.y, normal.z );
+										normal.fromArray( normals, i2 * 3 );
+										newNormals.push( normal.x, normal.y, normal.z );
+										normal.fromArray( normals, i3 * 3 );
+										newNormals.push( normal.x, normal.y, normal.z );
+
+									}
 
 									skip ++;
 
@@ -907,6 +958,7 @@ THREE.VRMLLoader.prototype = {
 							}
 
 							positions = newPositions;
+							normals = newNormals;
 							uvs = newUvs;
 
 						} else {
@@ -934,7 +986,16 @@ THREE.VRMLLoader.prototype = {
 
 						}
 
-						geometry.computeVertexNormals();
+						if (normals.length > 0) {
+
+							geometry.addAttribute( 'normal', new THREE.Float32BufferAttribute( normals, 3 ) );
+
+						} else {
+
+							geometry.computeVertexNormals();
+
+						}
+
 						geometry.computeBoundingSphere();
 
 						// see if it's a define