Trying to render 1 million geometryInstances, split into 100 primitives that have an appearance

Here is a sandcastle which reproduces my problem: Cesium Sandcastle

Here is a sandcastle demonstrating the expected behavior with only 100k geometries instead of 1 million: Cesium Sandcastle


I have 1 million geometryInstances that look like this:

const myGeometry = new GeometryInstance({
    id = "someId"
    geometry = new EllipseGeometry({
      height: 0,
      center: Cartesian3.fromDegrees( 1, 2),
      semiMinorAxis: 10000.0,
      semiMajorAxis: 10000.0,
      vertexFormat: VertexFormat.POSITION_AND_ST,

for every 10,000 of them, I create a new primitive like this:

myPrimitive = new Primitive({
      geometryInstances: geometryInstances, <-- a geometryInstance[] of length 10,000
      appearance = new EllipsoidSurfaceAppearance({
          aboveGround: true,
          faceForward: true,
          material: new Material({
                translucent: false,
                fabric: {
                    type: "Image",
                    uniforms: {
                        image: "/icons/icn_bullseye.svg",
      show: true,

when the primitive is created, it is added like this:


this process is supposed to happen 100 times, with varying longitude, latitudes, and ids on the geometryInstances.

However, when I reach ~23 primitives being displayed on the globe, I receive one of the following 2 errors:

An error occurred while rendering.  Rendering has stopped.
RangeError: Array buffer allocation failed
RangeError: Array buffer allocation failed
    at new ArrayBuffer (<anonymous>)
    at new Float64Array (<anonymous>)
    at Object.h.packCreateGeometryResults (http://localhost:8080/Workers/PrimitivePipeline-ff0113f1.js:1:5307)
    at http://localhost:8080/Workers/createGeometry.js:1:975
    at n (http://localhost:8080/Workers/when-208fe5b0.js:1:322)
    at a.u [as then] (http://localhost:8080/Workers/when-208fe5b0.js:1:956)
    at Function.i [as all] (http://localhost:8080/Workers/when-208fe5b0.js:1:1522)
    at http://localhost:8080/Workers/createGeometry.js:1:930
    at http://localhost:8080/Workers/createTaskProcessorWorker.js:1:195
    at http://localhost:8080/Workers/createTaskProcessorWorker.js:1:236
CesiumWidget.js:690 An error occurred while rendering.  Rendering has stopped.
RangeError: Array buffer allocation failed
RangeError: Array buffer allocation failed
    at new ArrayBuffer (<anonymous>)
    at new Float32Array (<anonymous>)
    at Object.r.encodeAttribute (http://localhost:8080/Workers/GeometryPipeline-cd170892.js:1:6811)
    at l (http://localhost:8080/Workers/PrimitivePipeline-ff0113f1.js:1:2739)
    at Object.h.combineGeometry (http://localhost:8080/Workers/PrimitivePipeline-ff0113f1.js:1:4327)
    at http://localhost:8080/Workers/combineGeometry.js:1:699
    at http://localhost:8080/Workers/createTaskProcessorWorker.js:1:195
    at http://localhost:8080/Workers/createTaskProcessorWorker.js:1:236

If I set my vertexFormat on my GeometryInstance to VertexFormat.POSITION_ONLY and remove the appearance from my primitive, I don’t receive errors, but I can’t see anything on the globe! So that sort of defeats the purpose.

While it’s not ideal, I’ve tried batching all 1 million GeometryInstances into a single Primitive to no avail. I have also tried adding all my Primitives to the scene, then traversing them within the scene object and adding their appearance there. This did not work either.

In this article: Performance Tips for Visualizing Lots of Points – Cesium, I see that they can render many millions of pointPrimitives with no problem. I’m assuming the pointPrimitive has no appearance attribute, which is why it is not so computationally expensive. While I do not need my Primitives to have svgs, it is very important that I am able to give them custom shapes, even if it’s just in the form of simple geometric shapes.

Thank you very much for your time and suggestions!

UPDATE: I thought the issue might have been that i was crearing a new EllipsoidSurfaceAppearance for each Primitive, so i tried just making one, and passing it to all primitive instantiations. This has not improved the sitation, though.

After further experiementation, it seems like billboards were the correct solution to the problem, with 10 billboard collections, each containing 100k billboards