##########################################
Iterating Over Lights in a Software Shader
##########################################

Contrary to the GPU version, a software shader contained in the ``RED::MTL_LIT`` pass have to loop through the lights in order to cumulate their effect.

Here is a simple code to iterate over the lights and perform sampling when needed:

.. code:: cpp

    // let:
    // - rayctx be the RED::ISoftRayContext.
    // - shaderctx be the RED::ISoftShaderContext.
    // - renderctx be the RED::ISoftRenderingContext.
    double hit[4], normal[4];
    double latt[4];
    double ldir[4], lcolor[4], lshadows[4];
    bool moresamples;

    // Get the ray hit and normal.
    rayctx.GetWCSHit( hit );
    rayctx.GetWCSNormal( normal, shaderctx.GetRenderCode(), RED_VSH_NORMAL );

    // Prepare lights before shading.
    // This call is mandatory before accessing the lights.
    RC_TEST( rayctx.PrepareLights( hit, normal, false, renderctx ) );

    // Iterate over the scene lights.
    for( unsigned int i = 0; i < renderctx.GetLightsCount(); ++i )
    {
       const RED::ISoftLight& light = renderctx.GetLight( i );

        // Perform culling.
        if( !light.GetAttenuation( latt, rayctx.GetThreadID() ) )
            continue;

        // Sampled light.
        if( light.NeedSampling() )
        {
            moresamples = true;
            while( true )
            {
                RC_TEST( light.GetNextWCSSample( moresamples,
                                                 ldir, lcolor, lshadows, 
                                                 hit, normal, 
                                                 rayctx, renderctx ) );
                if( !moresamples )
                  break;

                // Do something with the light sample...
            }
        }
        // Not sampled light.
        else
        {
            // Do something with the light...
        }
    } 