瀏覽代碼

Merge branch 'master' of https://github.com/NASA-AMMOS/3DTilesRendererJS

Garrett Johnson 5 年之前
父節點
當前提交
e757665c12
共有 3 個文件被更改,包括 80 次插入21 次删除
  1. 10 4
      README.md
  2. 21 4
      example/index.js
  3. 49 13
      src/three/TilesRenderer.js

+ 10 - 4
README.md

@@ -12,9 +12,7 @@ See it in action [here](https://nasa-ammos.github.io/3DTilesRendererJS/example/b
 
 **In Progress Features**
 - Multicamera support
-- Fast raycast support
 - Travis integration
-- ThreeTilesRenderer API
 - Performance
 
 # Use
@@ -24,7 +22,9 @@ import { TilesRenderer } from '3d-tiles-renderer';
 
 // ... initialize three scene ...
 
-const tilesRenderer = new TilesRenderer( './path/to/tileset.json', camera, renderer );
+const tilesRenderer = new TilesRenderer( './path/to/tileset.json' );
+tilesRenderer.camera = camera;
+tilesRenderer.setResolutionFromRenderer( renderer );
 scene.add( tilesRenderer.group );
 
 function renderLoop() {
@@ -81,7 +81,7 @@ loadSiblings = true : Boolean
 ### .constructor
 
 ```js
-constructor( url : String, cameras : Camera | Array<Camera>, renderer : WebGLRenderer )
+constructor( url : String )
 ```
 
 ### .update
@@ -102,6 +102,12 @@ getBounds( box : Box3 ) : void
 raycast( raycaster : Raycaster, intersects : Array ) : void
 ```
 
+### .setResolutionFromRenderer
+
+```js
+setResolutionFromRenderer( renderer : WebGLRenderer )
+```
+
 # LICENSE
 
 The software is available under the [Apache V2.0 license](../LICENSE.txt).

+ 21 - 4
example/index.js

@@ -57,7 +57,10 @@ function reinstantiateTiles() {
 
 	}
 
-	tiles = new TilesRenderer( url, camera, renderer );
+	tiles = new TilesRenderer( url );
+	tiles.camera = camera;
+	tiles.setResolutionFromRenderer( renderer );
+
 	offsetParent.add( tiles.group );
 
 }
@@ -134,9 +137,9 @@ function init() {
 	rayIntersect = new Group();
 
 	const rayIntersectMat = new MeshBasicMaterial( { color: 0xe91e63 } );
-	const rayMesh = new Mesh( new CylinderBufferGeometry( 0.25, 0.25, 10 ), rayIntersectMat );
+	const rayMesh = new Mesh( new CylinderBufferGeometry( 0.25, 0.25, 6 ), rayIntersectMat );
 	rayMesh.rotation.x = Math.PI / 2;
-	rayMesh.position.z += 5;
+	rayMesh.position.z += 3;
 	rayIntersect.add( rayMesh );
 
 	const rayRing = new Mesh( new TorusBufferGeometry( 1.5, 0.2, 16, 100 ), rayIntersectMat );
@@ -230,7 +233,10 @@ function animate() {
 	tiles.loadSiblings = params.loadSiblings;
 	tiles.maxDepth = params.maxDepth;
 	tiles.displayBounds = params.displayBounds;
-	tiles.cameras[ 0 ] = params.orthographic ? orthoCamera : camera;
+	tiles.camera = params.orthographic ? orthoCamera : camera;
+
+	tiles.camera = camera;
+	tiles.setResolutionFromRenderer( renderer );
 
 	// update tiles
 	tiles.update();
@@ -264,6 +270,7 @@ function animate() {
 		if ( closestHit.face ) {
 
 			const normal = closestHit.face.normal;
+			normal.transformDirection( closestHit.object.matrixWorld );
 			rayIntersect.lookAt(
 				point.x + normal.x,
 				point.y + normal.y,
@@ -272,6 +279,16 @@ function animate() {
 
 		}
 
+		if ( params.orthographic ) {
+
+			rayIntersect.scale.setScalar( closestHit.distance / 150 );
+
+		} else {
+
+			rayIntersect.scale.setScalar( closestHit.distance * camera.fov / 6000 );
+
+		}
+
 		rayIntersect.visible = true;
 
 	} else {

+ 49 - 13
src/three/TilesRenderer.js

@@ -19,7 +19,6 @@ const DEG2RAD = MathUtils.DEG2RAD;
 const tempMat = new Matrix4();
 const tempQuaternion = new Quaternion();
 const tempVector = new Vector3();
-const resVector = new Vector2();
 const vecX = new Vector3();
 const vecY = new Vector3();
 const vecZ = new Vector3();
@@ -29,6 +28,20 @@ function emptyRaycast() {}
 
 export class TilesRenderer extends TilesRendererBase {
 
+	get camera() {
+
+		return this.cameras[ 0 ];
+
+	}
+
+	set camera( camera ) {
+
+		const cameras = this.cameras;
+		cameras.length = 1;
+		cameras[ 0 ] = camera;
+
+	}
+
 	get displayBounds() {
 
 		return this._displayBounds;
@@ -65,13 +78,13 @@ export class TilesRenderer extends TilesRendererBase {
 
 	}
 
-	constructor( url, cameras, renderer ) {
+	constructor( ...args ) {
 
-		super( url );
+		super( ...args );
 		this.group = new TilesGroup( this );
-		this.cameras = Array.isArray( cameras ) ? cameras : [ cameras ];
+		this.cameras = [];
+		this.resolution = new Vector2();
 		this.frustums = [];
-		this.renderer = renderer;
 		this.activeSet = new Set();
 		this.visibleSet = new Set();
 
@@ -101,7 +114,11 @@ export class TilesRenderer extends TilesRendererBase {
 
 	raycast( raycaster, intersects ) {
 
-		if ( ! this.root ) return;
+		if ( ! this.root ) {
+
+			return;
+
+		}
 
 		if ( raycaster.firstHitOnly ) {
 
@@ -120,13 +137,35 @@ export class TilesRenderer extends TilesRendererBase {
 
 	}
 
+	setResolutionFromRenderer( renderer ) {
+
+		const resolution = this.resolution;
+		renderer.getSize( resolution );
+		resolution.multiplyScalar( renderer.getPixelRatio() );
+
+	}
+
 	/* Overriden */
 	update() {
 
 		const group = this.group;
-		const renderer = this.renderer;
 		const cameras = this.cameras;
 		const frustums = this.frustums;
+		const resolution = this.resolution;
+
+		if ( cameras.length === 0 ) {
+
+			console.warn( 'TilesRenderer: no cameras to use are defined. Cannot update 3d tiles.' );
+			return;
+
+		}
+
+		if ( resolution.width === 0 || resolution.height === 0 ) {
+
+			console.warn( 'TilesRenderer: resolution for error calculation is not set. Cannot updated 3d tiles.' );
+			return;
+
+		}
 
 		// automatically scale the array of frustums to match the cameras
 		while ( frustums.length > cameras.length ) {
@@ -154,10 +193,6 @@ export class TilesRenderer extends TilesRendererBase {
 
 		}
 
-		// store the resolution of the render
-		renderer.getSize( resVector );
-		resVector.multiplyScalar( renderer.getPixelRatio() );
-
 		super.update();
 
 	}
@@ -437,6 +472,7 @@ export class TilesRenderer extends TilesRendererBase {
 		// TODO: Use the content bounding volume here?
 		const boundingVolume = tile.boundingVolume;
 		const transformMat = cached.transform;
+		const resolution = this.resolution;
 
 		if ( 'box' in boundingVolume ) {
 
@@ -478,7 +514,7 @@ export class TilesRenderer extends TilesRendererBase {
 
 					const w = cam.right - cam.left;
 					const h = cam.top - cam.bottom;
-					const pixelSize = Math.max( h / resVector.height, w / resVector.width );
+					const pixelSize = Math.max( h / resolution.height, w / resolution.width );
 					error = tile.geometricError / ( pixelSize * invScale );
 
 				} else {
@@ -486,7 +522,7 @@ export class TilesRenderer extends TilesRendererBase {
 					const distance = boundingBox.distanceToPoint( tempVector );
 					const scaledDistance = distance * invScale;
 					const sseDenominator = 2 * Math.tan( 0.5 * cam.fov * DEG2RAD );
-					error = ( tile.geometricError * resVector.height ) / ( scaledDistance * sseDenominator );
+					error = ( tile.geometricError * resolution.height ) / ( scaledDistance * sseDenominator );
 
 				}