Home Game Development c++ – Design of a Light class in an OpenGL renderer

c++ – Design of a Light class in an OpenGL renderer

0
c++ – Design of a Light class in an OpenGL renderer

[ad_1]

I am learning how to make an OpenGL renderer / game engine. I created a C++ class Light, which looks roughly like this:

class Light {
    vec3 position;
    vec3 color;
    // additional padding to make Light compatible with std140 layout
};

The Scene class holds a list of Lights. During the rendering pass, the Renderer class receives a const std::vector<Light>& and uploads it to an UBO / SSBO. The fragment shader can then access this UBO/SSBO and iterate over all the lights.

Problem:

Consider implementing shadow mapping. The fragment shader must know which shadow map is attached to each light (via int shadowMapIndex which indexes a samplerCubeArray with the depth cubemaps). Some lights may not be shadow-casting (shadow casting may be turned on/off for each light), there may be additional data the renderer needs to set up for each light etc.

As a result, the Light class needs to become:

class Light {
    vec3 position;
    vec3 color;
    bool castShadow;
    int shadowMapIndex;
    // ... additional data the renderer may need to set up
};

The Renderer class sets up the shadow maps, so during the rendering pass it must assign to each Light object the index of the associated shadow map, hence, modify the Light scene object. I want to avoid this – I want to keep the Light class high-level and not have the renderer modify the state of the scene during the rendering. I would also like the Light class itself not to have to conform to any specific layout (std140) .

The idea (?) for a solution:

Introduce a RendererLight class which contains all the data held by the Light object in addition to any information the renderer sets up itself and passes to the shaders. A RendererLight object is created during the rendering pass for each Light object.

In pseudo-code this approach looks like:

class Light {
    vec3 position;
    vec3 color;
    // no padding etc. - doesn't need to be std140 compatible;
};

class RendererLight {
    vec3 position;
    vec3 color;
    bool castShadow;
    int shadowMapIndex;
    // padding to ensure std140-compatible layout etc.;

    RendererLight(const Light& light){
        // construct the RendererLight object by essentially copying the data
        // from the Light object
        position = light.position;
        // ...
    }
};

void Renderer::render(const Scene& scene){

    const std::vector<Light>& lights = scene.getLights();

    const std::vector<RendererLight> rendererLights;

    for (const auto& light : lights){

        // Create a RendererLight object from a Light object
        RendererLight& rendererLight = rendererLights.emplace_back(light);

        // assign the shadow map information and other render-specific information
        rendererLight.shadowMapIndex = getShadowMapIndex(...);
        rendererLight.otherBitOfInfoTheShaderNeeds = ...;


    }

    // Upload the RendererLight objects to the GPU
    uploadToUBO(rendererLights);

}

Questions:

  1. Is this the right approach, or should I simply allow the Renderer
    class to modify the state of the Light objects directly?
  2. Is it an anti-pattern / wrong to build what is essentially a copy of the Light during the rendering pass (to avoid modifying the original object)?
  3. Is there any better approach to managing lights?

[ad_2]

Previous article Best Black Friday MacBook deals: Get a laptop from just $505
Next article Key things to know before watching the new Hunger Games movie
Hello there! My name is YoleeTeam, and I am thrilled to welcome you to AmazonianGames.com. As the premier destination for all things related to Amazon Games' universe, we are dedicated to providing you with the most exciting and immersive gaming experiences out there. From captivating visuals to exhilarating gameplay, our website is packed with comprehensive insights, updates, and reviews to keep you ahead of the game. Whether you're a seasoned gamer or new to the scene, I am here to guide you through this virtual frontier. If you have any questions or suggestions, feel free to reach out to me at john@yoleesolutions.com. Embark on your Amazon gaming journey today with AmazonianGames.com and let the adventure begin!