Browse Source

LOD: Make methods more robust.

Mugen87 5 years ago
parent
commit
7827bdd5c0
3 changed files with 60 additions and 16 deletions
  1. 1 1
      src/objects/LOD.d.ts
  2. 19 7
      src/objects/LOD.js
  3. 40 8
      test/unit/src/objects/LOD.tests.js

+ 1 - 1
src/objects/LOD.d.ts

@@ -12,7 +12,7 @@ export class LOD extends Object3D {
 	levels: { distance: number; object: Object3D }[];
 
 	addLevel( object: Object3D, distance?: number ): this;
-	getObjectForDistance( distance: number ): Object3D;
+	getObjectForDistance( distance: number ): Object3D | null;
 	raycast( raycaster: Raycaster, intersects: Intersection[] ): void;
 	update( camera: Camera ): void;
 	toJSON( meta: any ): any;

+ 19 - 7
src/objects/LOD.js

@@ -81,27 +81,39 @@ LOD.prototype = Object.assign( Object.create( Object3D.prototype ), {
 
 		var levels = this.levels;
 
-		for ( var i = 1, l = levels.length; i < l; i ++ ) {
+		if ( levels.length > 0 ) {
 
-			if ( distance < levels[ i ].distance ) {
+			for ( var i = 1, l = levels.length; i < l; i ++ ) {
 
-				break;
+				if ( distance < levels[ i ].distance ) {
+
+					break;
+
+				}
 
 			}
 
+			return levels[ i - 1 ].object;
+
 		}
 
-		return levels[ i - 1 ].object;
+		return null;
 
 	},
 
 	raycast: function ( raycaster, intersects ) {
 
-		_v1.setFromMatrixPosition( this.matrixWorld );
+		var levels = this.levels;
+
+		if ( levels.length > 0 ) {
 
-		var distance = raycaster.ray.origin.distanceTo( _v1 );
+			_v1.setFromMatrixPosition( this.matrixWorld );
 
-		this.getObjectForDistance( distance ).raycast( raycaster, intersects );
+			var distance = raycaster.ray.origin.distanceTo( _v1 );
+
+			this.getObjectForDistance( distance ).raycast( raycaster, intersects );
+
+		}
 
 	},
 

+ 40 - 8
test/unit/src/objects/LOD.tests.js

@@ -3,6 +3,8 @@
  */
 /* global QUnit */
 
+import { Object3D } from '../../../../src/core/Object3D';
+import { Raycaster } from '../../../../src/core/Raycaster';
 import { LOD } from '../../../../src/objects/LOD';
 
 export default QUnit.module( 'Objects', () => {
@@ -10,9 +12,11 @@ export default QUnit.module( 'Objects', () => {
 	QUnit.module( 'LOD', () => {
 
 		// INHERITANCE
-		QUnit.todo( "Extending", ( assert ) => {
+		QUnit.test( "Extending", ( assert ) => {
 
-			assert.ok( false, "everything's gonna be alright" );
+			var lod = new LOD();
+
+			assert.strictEqual( ( lod instanceof Object3D ), true, "LOD extends from Object3D" );
 
 		} );
 
@@ -31,9 +35,11 @@ export default QUnit.module( 'Objects', () => {
 		} );
 
 		// PUBLIC STUFF
-		QUnit.todo( "isLOD", ( assert ) => {
+		QUnit.test( "isLOD", ( assert ) => {
 
-			assert.ok( false, "everything's gonna be alright" );
+			var lod = new LOD();
+
+			assert.strictEqual( lod.isLOD, true, ".isLOD property is defined." );
 
 		} );
 		QUnit.todo( "copy", ( assert ) => {
@@ -46,14 +52,40 @@ export default QUnit.module( 'Objects', () => {
 			assert.ok( false, "everything's gonna be alright" );
 
 		} );
-		QUnit.todo( "getObjectForDistance", ( assert ) => {
+		QUnit.test( "getObjectForDistance", ( assert ) => {
 
-			assert.ok( false, "everything's gonna be alright" );
+			var lod = new LOD();
+
+			var high = new Object3D();
+			var mid = new Object3D();
+			var low = new Object3D();
+
+			assert.strictEqual( lod.getObjectForDistance( 5 ), null, "Returns null if no LOD levels are defined." );
+
+			lod.addLevel( high, 5 );
+
+			assert.strictEqual( lod.getObjectForDistance( 0 ), high, "Returns always the same object if only one LOD level is defined." );
+			assert.strictEqual( lod.getObjectForDistance( 10 ), high, "Returns always the same object if only one LOD level is defined." );
+
+			lod.addLevel( mid, 25 );
+			lod.addLevel( low, 50 );
+
+			assert.strictEqual( lod.getObjectForDistance( 0 ), high, "Returns the high resolution object." );
+			assert.strictEqual( lod.getObjectForDistance( 10 ), high, "Returns the high resolution object." );
+			assert.strictEqual( lod.getObjectForDistance( 25 ), mid, "Returns the mid resolution object." );
+			assert.strictEqual( lod.getObjectForDistance( 50 ), low, "Returns the low resolution object." );
+			assert.strictEqual( lod.getObjectForDistance( 60 ), low, "Returns the low resolution object." );
 
 		} );
-		QUnit.todo( "raycast", ( assert ) => {
+		QUnit.test( "raycast", ( assert ) => {
 
-			assert.ok( false, "everything's gonna be alright" );
+			var lod = new LOD();
+			var raycaster = new Raycaster();
+			var intersections = [];
+
+			lod.raycast( raycaster, intersections );
+
+			assert.strictEqual( intersections.length, 0, "Does not fail if raycasting is used with a LOD object without levels." );
 
 		} );
 		QUnit.todo( "update", ( assert ) => {