Git Product home page Git Product logo

Comments (3)

jo-chemla avatar jo-chemla commented on May 27, 2024

Directions from #496

We'd need a separate error metric on the tile that scales based based on distance to the center of the screen so it can be used to sort the tiles in the download and parse queue "priority callback". Adding something like a "load order" visualization to the DebugTilesRenderer would be helpful for understanding the impact of this kind of change, as well

Dropping some notes around an implementation for potentially drafting a PR

priorityCallback

TilesRendererBase priorityCallback :

const priorityCallback = ( a, b ) => {
if ( a.__depth !== b.__depth ) {
// load shallower tiles first
return a.__depth > b.__depth ? - 1 : 1;
} else if ( a.__inFrustum !== b.__inFrustum ) {
// load tiles that are in the frustum at the current depth
return a.__inFrustum ? 1 : - 1;
} else if ( a.__used !== b.__used ) {
// load tiles that have been used
return a.__used ? 1 : - 1;
} else if ( a.__error !== b.__error ) {
// load the tile with the higher error
return a.__error > b.__error ? 1 : - 1;
} else if ( a.__distanceFromCamera !== b.__distanceFromCamera ) {
// and finally visible tiles which have equal error (ex: if geometricError === 0)
// should prioritize based on distance.
return a.__distanceFromCamera > b.__distanceFromCamera ? - 1 : 1;
}
return 0;
};

Could add something like this as a final check, but the if/else cascade might mean some tests are never tested against.

	} else if ( a.__distanceFromScreenCenter !== b.__distanceFromScreenCenter ) {

		// and finally tiles closest to the center should be prioritized for faster foveated rendering.
		return a.__distanceFromScreenCenter > b.__distanceFromScreenCenter ? - 1 : 1;

	}

Would that make sense to have some hard tests which return +1/-1 like originally, but hten the final tests would return a sum of +1/-1? Something like

if ( a.__depth !== b.__depth ) { ... } 
else if ( a.__inFrustum !== b.__inFrustum ) { ... } 
else if ( a.__used !== b.__used ) { ... } 
else if ( a.__error !== b.__error )
else if (test)  {
  return (a.__distanceFromCamera > b.__distanceFromCamera) + (a.__distanceFromScreenCenter > b.__distanceFromScreenCenter)
}

Compute __distanceFromScreenCenter

Where to compute this __distanceFromScreenCenter ? Should be done in the traverseFunction file, right? Somewhere like

child.__depthFromRenderedParent = depthFromRenderedParent;

or probably better, within

const inFrustum = renderer.tileInView( tile );

Where we could compute the __distanceFromScreenCenter similar to the way the

tileInView( tile ) {

It would probably make sense to simply compute the distance of the tile boundingVolume center, projected onto the screen, and measure that distance to the screen center - rather than for example computing the tile bounding volume projection surface onto the screen, and decide that that metric should be the distance between that projection area and the screen center.

DebugTilesRenderer load order" viz

Probably exactly along the lines of

case DISTANCE: {
// We don't update the distance if the geometric error is 0.0 so
// it will always be black.
const val = Math.min( tile.__distanceFromCamera / maxDistance, 1 );
this.getDebugColor( val, c.material.color );
break;
}

from 3dtilesrendererjs.

gkjohnson avatar gkjohnson commented on May 27, 2024

Could add something like this as a final check, but the if/else cascade might mean some tests are never tested against.

This is ok and it's already the case that most of the time the final conditions are not used.

	} else if ( a.__distanceFromScreenCenter !== b.__distanceFromScreenCenter ) {

  	// and finally tiles closest to the center should be prioritized for faster foveated rendering.
  	return a.__distanceFromScreenCenter > b.__distanceFromScreenCenter ? - 1 : 1;

  }

We should compute some adjustment of screenspace error here based distance to the center so high error tiles are still prioritized - just less so if they're off on the edge of the screen. As just an example, something like screenSpaceError + screenSpaceError * distanceToCenter * 1e-2. This deserves more thought, though. Cesium's implementation might be the approach to reference here.

from 3dtilesrendererjs.

jo-chemla avatar jo-chemla commented on May 27, 2024

This is how the cesiumjs codebase merges into a single priority metric different priorities: They store it on a base10 number which is composed of (from the Cesium3DTile.js code):

preloadFlightDigits(1) | foveatedDeferDigits(1) | foveatedDigits(4) | preloadProgressiveResolutionDigits(1) | preferredSortingDigits(4) . depthDigits(the decimal digits)

It uses two priorities for the foveated rendering, a boolean priorityDeferred (false within the cone, true outside) and a float normalizedFoveatedFactor which is is the actual priority :

The most interesting bit are probably within the function isPriorityDeferred shows that actually, within a cone with radius given in screen space, tiles loading is not deferred, and then linearly increases between that cone limit and the screen limit.

PS: interesting note in the Cesium3DTilesetBaseTraversal.js file

An ancestor will hold the _foveatedFactor and _distanceToCamera for descendants between itself and its highest priority descendant. Siblings of a min children along the way use this ancestor as their priority holder as well.
Priority of all tiles that refer to the _foveatedFactor and _distanceToCamera stored in the common ancestor will be differentiated based on their _depth.

Plus all the foveated parameters on the Cesium3DTileset docs are interesting to understand how it's working under the hood.

from 3dtilesrendererjs.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.