How to improve scene rendering performance when there are a lot of dynamic entities in the scene?

1. A concise explanation of the problem you’re experiencing.

When I add a lot of entities to the scene, the engine renders a low frame rate,even though there are only a few entities in the field of view.It seems to be the frustum culling takes too much time.

2. A minimal code example. If you’ve found a bug, this helps us reproduce and repair it.

var viewer = new Cesium.Viewer(‘cesiumContainer’, {

infoBox : false,

selectionIndicator : false,

shadows : true,

shouldAnimate : true

});

viewer.scene.debugShowFramesPerSecond = true;

//Create a model at the specified location

function createModel(url, lon,lat,height) {

var position = Cesium.Cartesian3.fromDegrees(lon, lat, height);

var heading = Cesium.Math.toRadians(135);

var pitch = 0;

var roll = 0;

var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);

var orientation = Cesium.Transforms.headingPitchRollQuaternion(position, hpr);

var entity = viewer.entities.add({

name : url,

position : position,

orientation : orientation,

model : {

uri : url,

minimumPixelSize : 128,

maximumScale : 20000

}

});

}

//Create a specified number of models with random locations

function addModel(count){

for (var i=0;i<count;i++){

var lon = Math.random()*120.0 - 60.0;//(-60,60)

var lat = Math.random()*120.0 - 60.0;//(60,60)

var url = “…/…/SampleData/models/CesiumAir/Cesium_Air.glb”;

var entity = createModel(url,lon,lat, 50000.0);

}

}

addModel(5000);

var rectangle = new Cesium.Rectangle(Cesium.Math.toRadians(-60),

Cesium.Math.toRadians(-60),

Cesium.Math.toRadians(60),

Cesium.Math.toRadians(60));

viewer.scene.camera.flyTo({destination: rectangle});

``

3. Context. Why do you need to do this? We might know a better way to accomplish your goal.

I want to support more than 10,000 dynamic entities with high performance in my application.

4. The Cesium version you’re using, your operating system and browser.

Cesium 1.5.2,Windows 10 x64,Google Chrome 71.0.3578.98.

I think for this particle case, it might speed things up significantly to hook up the ModelInstanceCollection system to the Entity API. See the discussion on that here:

https://github.com/AnalyticalGraphicsInc/cesium/issues/7062

You can see an example of how the performance looks and using that directly even though the API isn’t public yet:

This only works if they’re the same model though.

Hi Omar,thank you so much for your reply.

I wrote an example comparing the performance of Entity and ModelInstance. After running the example, we can see that the frame rates of the two are almost the same, and ModleInstance has no obvious performance improvement.

var viewer = new Cesium.Viewer(‘cesiumContainer’, {

infoBox : false,

selectionIndicator : false,

shadows : false,

shouldAnimate : false

});

viewer.scene.debugShowFramesPerSecond = true;

viewer._cesiumWidget._creditContainer.style.display=“none”;

var url = “…/…/…/…/Apps/SampleData/models/CesiumAir/Cesium_Air.glb”;

var count = 5000;//entity number

var collection;

var useCollection = false;

var context = viewer.scene.context;

var instancedArraysExtension = context._instancedArrays;

//generate a random number(n,m)

function rd(n,m){

var c = m-n+1;  

return Math.floor(Math.random() * c + n);

}

//Create a model at the specified location

function createModel(url, lon,lat,height) {

var position = Cesium.Cartesian3.fromDegrees(lon, lat, height);

var heading = Cesium.Math.toRadians(135);

var pitch = 0; 

var roll = 0;

var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);

var orientation = Cesium.Transforms.headingPitchRollQuaternion(position, hpr);

var entity = viewer.entities.add({

    name : url,

    position : position,

    orientation : orientation,

    model : {

        uri : url,

        minimumPixelSize : 128,

        maximumScale : 20000

    }

});

}

//Create a specified number of models with random locations

function addModel(){

 for (var i=0;i<count;i++){

    var lon =rd(90,130);//(90,130)

    var lat =rd(20,55);//(20,55)

    var entity = createModel(url,lon,lat, 50000.0);

 }

}

function reset() {

if(collection){

    viewer.scene.primitives.remove(collection);

}else{

    viewer.entities.removeAll();

}

if(useCollection){

    addCollection();

}else{

addModel();

}

}

//Collection

function addCollection() {

var instances = [];

for(var i=0;i<count;++i){

    var lon =rd(90,130);//(90,130)

    var lat =rd(20,55);//(20,55)

    var position = Cesium.Cartesian3.fromDegrees(lon, lat, 50000);

    var heading = Math.random();

    var pitch = Math.random();

    var roll = Math.random();

    var scale = (Math.random() + 1.0)/2.0;

    scale = 20000;

    var modelMatrix = Cesium.Transforms.headingPitchRollToFixedFrame(position, new Cesium.HeadingPitchRoll(heading, pitch, roll));

    Cesium.Matrix4.multiplyByUniformScale(modelMatrix, scale, modelMatrix);

    instances.push({

        modelMatrix : modelMatrix

    });

}

collection = viewer.scene.primitives.add(new Cesium.ModelInstanceCollection({

    url : url,

    instances : instances

}));

}

addModel();

var rectangle = new Cesium.Rectangle(Cesium.Math.toRadians(90),

                                 Cesium.Math.toRadians(20),

                                 Cesium.Math.toRadians(130),

                                 Cesium.Math.toRadians(55));

viewer.scene.camera.flyTo({destination: rectangle});

Sandcastle.addToolbarMenu([ {

text : 'entity',

onselect : function() {

    useCollection = false;

    reset();

}

}, {

text : 'instances',

onselect : function() {

    context._instancedArrays = instancedArraysExtension;

    useCollection = true;

    reset();

}

}]);

``

result:

在 2019年1月23日星期三 UTC+8下午10:04:13,Omar Shehata写道:

I just tried running this on an old machine. The instance is about 3x faster. Have you tried this on other machines? What frame rates/time per frame are you getting for these tests?

I am sorry, you are right, I have only tested it on my laptop before, the graphics card is Intel HD Graphic 620. When I tested on a GTX 550 graphics card, the instance was indeed much faster than the Entity. In addition, when I simplified the model on my laptop, the instance can bring a big performance boost . Perhaps the frame rate is related to memory and graphics speed. Thanks again.

在 2019年1月25日星期五 UTC+8下午11:51:25,Omar Shehata写道: