how to animate custom primitive?

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

I have rendered a simple custom primitive (a triangle). Now I want to animate the triangle.

Firstly I try to change the vertex data of the triangle to see if the triangle will move to the new location.

But it duplicates the triangle, the old triangle doesn’t disappear. As shown below.

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

Here is my code in Sandcastle:

var viewer = new Cesium.Viewer(‘cesiumContainer’);

var TrianglePrimitive = /** @class */ (function () {

function TrianglePrimitive(options) {

    this._dirty = true;

    this._positions = options.positions;

this._vertices = ;

this._colors = ;

    this._show = options.show || true;

    this._material = Cesium.Material.fromType(Cesium.Material.ColorType);

    this._modelMatrix = Cesium.Matrix4.clone(Cesium.Matrix4.IDENTITY);

    this._drawCommand = new Cesium.DrawCommand({ owner: this });

}

Object.defineProperty(TrianglePrimitive.prototype, "positions", {

    get: function () {

        return this._positions;

    },

    set: function (value) {

        if (this._positions !== value) {

            this._positions = value;

            this._dirty = true;

        }

    },

    enumerable: true,

    configurable: true

});

TrianglePrimitive.prototype.update = function (frameState) {

    if (!this._show) {

        return;

    }

    var context = frameState.context;

    this.vertexArray = (this._dirty || !this.vertexArray) ? this.createVertexArray(context) : this.vertexArray;

    this.setupShaderProgram(context);

    this.setupRenderState();

    

    var passes = frameState.passes;

    if(passes.render){

        this.setupDrawCommand();

        frameState.commandList.push(this._drawCommand);

    }

    

};

TrianglePrimitive.prototype.sceneModeChanged = function (mode) {

    return this._lastMode !== mode;

};

TrianglePrimitive.prototype.createVertexArray = function (context) {

    this._dirty = false;

for(var i=0;i<this._positions.length;i++){

var position = this._positions[i];

this._vertices.push(position.x);

this._vertices.push(position.y);

this._vertices.push(position.z);

this._colors.push(Math.random());

this._colors.push(Math.random());

this._colors.push(Math.random());

}

    var positionVertexBuffer = Cesium.Buffer.createVertexBuffer({

        context: context,

        typedArray: new Float32Array(this._vertices),

        usage: Cesium.BufferUsage.STATIC_DRAW

    });

var colorVertexBuffer = Cesium.Buffer.createVertexBuffer({

        context: context,

        typedArray: new Float32Array(this._colors),

        usage: Cesium.BufferUsage.STATIC_DRAW

    });

    var attributes = [

        {

            index: 0,

            enabled: true,

            vertexBuffer: positionVertexBuffer,

            componentsPerAttribute: 3,

            componentDatatype: Cesium.ComponentDatatype.FLOAT,

            normalize: false,

            offsetInBytes: 0,

            strideInBytes: 0

        },

        {

            index: 1,

            enabled: true,

            vertexBuffer: colorVertexBuffer,

            componentsPerAttribute: 3,

            componentDatatype: Cesium.ComponentDatatype.FLOAT,

            normalize: false,

            offsetInBytes: 0,

            strideInBytes: 0

        }

    ];

var vertexArray = new Cesium.VertexArray({

        context: context,

        attributes: attributes,

        indexBuffer: this.createIndexBuffer(context)

    });

    return vertexArray;

};

TrianglePrimitive.prototype.setupShaderProgram = function (context) {

    this._shaderProgram = this._shaderProgram || Cesium.ShaderProgram.replaceCache({

        context: context,

        shaderProgram: this._shaderProgram,

        vertexShaderSource: "attribute vec3 position;\n"+

        "attribute vec3 color;\n"+

        "varying vec4 v_color;\n\n"+

        "void main() {\n"+

            "gl_Position = czm_modelViewProjection * vec4(position, 1.0);\n"+

            "v_color = vec4(color,1.0);\n"+

        "}",

        fragmentShaderSource: "varying vec4 v_color;\n"+

        "void main(){\n"+

            "gl_FragColor = v_color;\n"+

        "}"

    });

};

TrianglePrimitive.prototype.setupRenderState = function () {

    this._renderState = Cesium.RenderState.fromCache({

        cull: {

            enabled: true,

            face: Cesium.CullFace.FRONT

        },

        depthTest: {

            enabled: false

        },

        depthMask: true,

        blending: undefined

    });

};

TrianglePrimitive.prototype.setupDrawCommand = function () {

    this._drawCommand.modelMatrix = this._modelMatrix;

    this._drawCommand.renderState = this._renderState;

    this._drawCommand.primitiveType = Cesium.PrimitiveType.TRIANGLES;

    this._drawCommand.shaderProgram = this._shaderProgram;

    this._drawCommand.vertexArray = this.vertexArray;

    this._drawCommand.pass = Cesium.Pass.OVERLAY;

    this._drawCommand.boundingVolume = this.createBoundingVolume();

    this._drawCommand.debugShowBoundingVolume = false;

};

TrianglePrimitive.prototype.createIndexBuffer = function (context) {

this._indicesArray = TrianglePrimitive.createIndicesArray(this._vertices.length);

    this._indexBufferArray = Cesium.Buffer.createIndexBuffer({

        context: context,

        typedArray: this._indicesArray,

        usage: Cesium.BufferUsage.STATIC_DRAW,

        indexDatatype: Cesium.IndexDatatype.UNSIGNED_SHORT

    });

};

TrianglePrimitive.createIndicesArray = function (size) {

    var indicesArray = [];

    for (var i = 0; i < size / 3; i++) {

        indicesArray.push(i);

    }

    return new Uint16Array(indicesArray);

};

TrianglePrimitive.prototype.createBoundingVolume = function () {

    return Cesium.BoundingSphere.fromPoints(this._positions);

};

return TrianglePrimitive;

}());

var pri = new TrianglePrimitive({

positions:Cesium.Cartesian3.fromDegreesArrayHeights([-111.0, 40.0, 150000.0,-111,45,150000,-100,40.5,150000])

});

viewer.scene.primitives.add(pri);

Sandcastle.addToolbarButton(‘change’, function() {

pri.positions = Cesium.Cartesian3.fromDegreesArrayHeights([-120.0, 40.0, 150000.0,-120,45,150000,-109,40.5,150000]);

});

``

I wonder why the old triangle doesn’t disappear and how to clear the old triangle.

Any help appreciated.

Thanks

Chris

Is there a particular reason you are not extending Geometry.js like all our primitives too? I think you may be creating duplicate code you don’t have to.

What we do when updating a primitive is destroy the old one and create a new one, see DynamicGeometryUpdater.js

Thanks,

Gabby