Accessing Custom Attributes on VBO Mesh from GLSL


#1

I’m trying to revive an ancient work that used OpenGL 2.0, and am just getting my head around the changes to using VBOMeshes. I can access all the standard attributes (ciPosition etc) thanks to this post:

This is really helpful, but how do I access the custom variables (ie CUSTOM_0 - CUSTOM_9)?
I have tried in float ciCustom0 in the shader but just get the following error:

warning void cinder::gl::VboMesh::buildVao(const cinder::gl::GlslProg *, const AttribGlslMap &)[500] Batch GlslProg expected an Attrib of USER_DEFINED, with name ciCustom0 but vertex data doesn’t provide it.

I have set up my Layout as follows:

vector<gl::VboMesh::Layout> bufferLayout = {
            gl::VboMesh::Layout().usage( GL_DYNAMIC_DRAW ).attrib( geom::Attrib::POSITION, 3 ),
            gl::VboMesh::Layout().usage( GL_DYNAMIC_DRAW ).attrib( geom::Attrib::COLOR, 4 ),
            gl::VboMesh::Layout().usage( GL_DYNAMIC_DRAW ).attrib( geom::Attrib::CUSTOM_0, 1 )
        };

So does this not bind to ciCustom0 in the same way as the other inbuilt attributes?

Cheers,
Ben


#2

Have a look at the 3rd argument to the gl::GlslProg constructor. It allows you to provide an AttribMapping which maps a geom::Attrib to a string for the name of the attribute in the shader.

Something like (typed inline and not tested)

auto shader = gl::GlslProg::create ( vert, frag, { { geom::Attrib::CUSTOM_0, "aSomeAttribute" } } );

then in your shader

in vec4 aSomeAttribute; // or whatever the type is

#3

Actually, the attribute mapping is the 3rd parameter of gl::Batch::create(), not gl::GlslProg::create().

Alternatively, you can specify the name as follows:

auto vert = loadAsset("shader.vert");
auto frag = loadAsset("shader.frag");
auto format = gl::GlslProg::Format().vertex( vert )
                                    .fragment( frag )
                                    .attrib( geom::CUSTOM_0, "aSomeAttribute" );
auto shader = gl::GlslProg::create( format );

The custom attributes are often used to pass per instance data when rendering thousands of instances in one draw call. The attribute would then contain a color, position, orientation, scale or a transform matrix. See here for an example.

-Paul


#5

perfect, thanks! this clears it up perfectly.