D2D1Renderer + Hieroglyph3 DXGI_FORMAT problem

May 22, 2013 at 9:00 AM
Edited May 22, 2013 at 1:06 PM
Ive seen that there is a problem between the D2D1Renderer color format and
Hieroglyph3 color format.

You have the default color format on DXGI_FORMAT_R8G8B8A8_UNORM_SRGB (seen in SwapChainConfigDX11::SetDefaults).

The result is that the direct2D overlay is too bright.

This is because Direct2D only works with DXGI_FORMAT_R8G8B8A8_UNORM or DXGI_FORMAT_B8G8R8A8_UNORM format. Not with the SRGB format or others.

so ive had to change the color format to have a correct color of the direct2D rendering:

SwapChainConfigDX11 Config;
Config.SetFormat( DXGI_FORMAT_B8G8R8A8_UNORM );

To hack it in without changing anything, i did:
bool App::ConfigureRenderingEngineComponents( UINT width, UINT height, D3D_FEATURE_LEVEL desiredLevel, D3D_DRIVER_TYPE driverType )
{
    // Create the renderer and initialize it for the desired device
    // type and feature level.

    m_pRenderer11 = new RendererDX11();

    if ( !m_pRenderer11->Initialize( driverType, desiredLevel ) )
    {
        Log::Get().Write( L"Could not create hardware device, trying to create the reference device..." );

        if ( !m_pRenderer11->Initialize( D3D_DRIVER_TYPE_REFERENCE, D3D_FEATURE_LEVEL_11_0 ) )
        {
            MessageBox( 0, L"Could not create a hardware or software Direct3D 11 device - the program will now abort!", L"Hieroglyph 3 Rendering", MB_ICONEXCLAMATION | MB_SYSTEMMODAL );
            RequestTermination();           
            return( false );
        }

        // If using the reference device, utilize a fixed time step for any animations.
        m_pTimer->SetFixedTimeStep( 1.0f / 10.0f );
    }

    // Create the window.
    m_iWidth = width;
    m_iHeight = height;

    // Create the window wrapper class instance.
    m_pWindow = CreateRenderWindow();
    m_pWindow->SetPosition( 20, 20 );
    m_pWindow->SetSize( m_iWidth, m_iHeight );
    m_pWindow->SetCaption( GetName() );
    m_pWindow->Initialize( this );

    // Create a swap chain for the window.
    SwapChainConfigDX11 Config;
    Config.SetFormat( DXGI_FORMAT_B8G8R8A8_UNORM );
    Config.SetWidth( m_pWindow->GetWidth() );
    Config.SetHeight( m_pWindow->GetHeight() );
    Config.SetOutputWindow( m_pWindow->GetHandle() );
    m_pWindow->SetSwapChain( m_pRenderer11->CreateSwapChain( &Config ) );

    // We'll keep a copy of the swap chain's render target index to 
    // use later.
    m_BackBuffer = m_pRenderer11->GetSwapChainResource( m_pWindow->GetSwapChain() );

    SetMultiThreadedMode( true );

    return( true );
}
I overwrite the RenderApplication:ConfigureRenderingEngineComponents with a new one.

The only different between the original and the new one is:
Config.SetFormat( DXGI_FORMAT_B8G8R8A8_UNORM );
What do you think about this fact?
Coordinator
May 23, 2013 at 1:35 AM
I am certainly willing to accommodate some type of a solution here. The reason that I use an SRGB format is to allow for gamma correction when the input content to the pipeline (i.e. textures, the Kinect video feed, etc...) are encoded into SRGB too. If you don't use it, then the content in the 3D scene will appear incorrect, probably in a similar manner to what you are seeing on the D2D overlay...

We could probably allow for an option to be set in the RenderApplication prior to this initialization method being called. This could either be a constant in the class itself, or potentially a variable that has to be set before initialization. A good candidate location is in the ::ConfigureEngineComponents method just prior to the call to ConfigureRenderingEngineComponents(...).

Would that work for your use case? Do you need dynamic setting, or do you think this is something that should utilize a constant in your app class?