Using multiple shaders

This topic contains 6 replies, has 2 voices, and was last updated by  RichardUK 8 years, 7 months ago.

Viewing 7 posts - 1 through 7 (of 7 total)
  • Author
    Posts
  • #29723

    RichardUK
    Member

    Currently I have two shaders, they are almost the same and so use
    uniforms that have the same name and values. The main difference is
    that one shader uses discard for 1 bit alpha. When I change shaders I
    have to upload uniforms that have changed since the shader was last
    used and so there is code to keep track of the current uniform value so
    if it has changed it can be sent again when the shader changes.

    Is there away I can aviod all this extra ‘management’ work for the CPU?

    In
    DX shaders you can have a ‘pool’ of shared varibles (uniforms) that are
    shared between shaders and so for example the projection matrix only
    has to be uploaded once when it changes and not for every shader.

    Anther
    thing you can do in DX shaders is state the constant register a varible
    (uniform) is using so you can get the same effect as the pool code.

    Can we do either in GLES 2.0???

    #32799

    Xmas
    Member

    No, OpenGL ES 2.0 has no way of explicitly sharing uniform values between programs. It should be relatively easy to encapsulate pairs of programs like this in an object that keeps track of the uniform values, though. Alternatively you could simply set the uniform values on both programs at the same time. There is some overhead to this, but it might be insignificant.

    #32800

    RichardUK
    Member

    I did have a thought, instead of doing code to manage this could I just use ‘glGetUniform’ on the uniforms they share to get the current values, activate the new program, then set the uniforms?

    What is the cost of ‘glGetUniform’?

    Thanks,
    Richard e Collins.

    RichardUK2009-03-09 10:48:47

    #32801

    Xmas
    Member

    You could, but it seems to me this would require just as much code as storing the values yourself. The overhead would certainly be higher.

    #32802

    RichardUK
    Member

    Is glGetUniform doing more than just returning a copy of a local store? As the API supports a ‘get’ on uniforms I had thought that it would be coming from an internal local store and not from the chip and so my code would only be unnessarily duplicating this.

    Doing the code my side off the API means every time I set a uniform I need to record it and so increasing memory bandwidth usage. Something i’ve always tried to advoid on mobile chips.

    Using the glGetUniform I only add ‘work’ for the CPU when the shader changes. Read current uniforms, change shader, set uniforms. (last stage has to be done with both methods)

    But if glGetUniform has to do more than just reading a local store then yes not a good idea. In DX using a “Get” function is not a good idea and so i’ve always tried to advoid it with all 3D api’s including GL.

    Seems the lack of shared uniforms in the shader language is bit of an oversight, it’s causing extra work for the CPU.

    #32803

    Xmas
    Member

    glGetUniform needs to at least perform error and type checking, context and program lookup, so that is an overhead comparing to accessing a local variable. But I really think you’re worrying too much about micro-optimizations. The bandwidth required for storing uniforms should be negligible, and putting a wrapper class around your shader pair that keeps those values should require only a few lines of code.

    #32804

    RichardUK
    Member

    That is true. The killer here is the use of discard and so splitting the shader is the bottom line, only want discard in a shader if it’s going to be used.

    I’ve done the code and there is not much to it. I guess coming from the old 8bit days when writing 16 dwords was a big deal I do fall into that trap from time to time. 😉

Viewing 7 posts - 1 through 7 (of 7 total)
You must be logged in to reply to this topic.