Adding new attribute for instancing

It is now possible to set attributes on standard material (in the next release, 1.66 probably). This allows you to provide additional data per each instance. The method is simple - when creating a vertex buffer, instead of the default vertex format, you create your own one and then set the semantics on the material.

Here is an example of passing two pc.Vec3 vectors:

// 16 for TRS matrix and +3 for each additional vector
const data = new Float32Array(instanceCount * (16 + 6));

let index = 0;
for (let i = 0; i < instanceCount; i++) {
    matrix.setTRS(pos, pc.Quat.IDENTITY, pc.Vec3.ONE);

    // add some custom vectorA
    data[index++] = vectorA.x;
    data[index++] = vectorA.y;
    data[index++] = vectorA.z;

    // add vectorB
    data[index++] = vectorB.x;
    data[index++] = vectorB.y;
    data[index++] = vectorB.z;

    for (let m = 0; m < 16; m++) {
        buffer[bufferIndex++] = matrix.data[m];
    }
}

// create vertex format, 10-11 - our vectorA and vectorB, 12-15 - instancing data
const format = new pc.VertexFormat(device, [
    { semantic: pc.SEMANTIC_ATTR10, components: 3, type: pc.TYPE_FLOAT32 },
    { semantic: pc.SEMANTIC_ATTR11, components: 3, type: pc.TYPE_FLOAT32 },
    { semantic: pc.SEMANTIC_ATTR12, components: 4, type: pc.TYPE_FLOAT32 },
    { semantic: pc.SEMANTIC_ATTR13, components: 4, type: pc.TYPE_FLOAT32 },
    { semantic: pc.SEMANTIC_ATTR14, components: 4, type: pc.TYPE_FLOAT32 },
    { semantic: pc.SEMANTIC_ATTR15, components: 4, type: pc.TYPE_FLOAT32 },
]);            

// create vertex buffer
const vertexBuffer = new pc.VertexBuffer(device, format, instanceCount, pc.BUFFER_STATIC, data);

// add attributes on material to map semantics
standardMaterial.setAttribute('vectorA', pc.SEMANTIC_ATTR10);
standardMaterial.setAttribute('vectorB', pc.SEMANTIC_ATTR11);

// create mesh instance, using that material and provide vertex buffer for instancing
const instance = new pc.MeshInstance(mesh, material);
instance.setInstancing(vertexBuffer);

Then in your vertex chunk, e.g. transformVS

attribute vec3 vectorA, vectorB;
vec4 getPosition()
{
    vec4 something = vec4(vectorA, 1.);
}
2 Likes