androidopengl-esopengl-es-3.0

OpenGL sRGB configuration on Android


I am trying to understand how to enable sRGB profile for default frame buffers on Android.Android SDK is not clear about how to do it practically.For example,here a guy states that it is enough to set texture internal format to sRGB. But he is clearly wrong,because I tried that and it changes nothing.

Khronos provides this extension as a part of EGL.I have tried to add these flags to surface configs:

    final int EGL_GL_COLORSPACE_KHR = 0x309D;
    final int EGL_GL_COLORSPACE_SRGB_KHR = 0x3089;
    int attribs[] = {
            EGL10.EGL_LEVEL, 0,
            EGL10.EGL_RENDERABLE_TYPE,EGLExt.EGL_OPENGL_ES3_BIT_KHR,
            EGL10.EGL_COLOR_BUFFER_TYPE, EGL10.EGL_RGB_BUFFER, 
            EGL10.EGL_RED_SIZE, 8,
            EGL10.EGL_GREEN_SIZE, 8,
            EGL10.EGL_BLUE_SIZE, 8,
            EGL10.EGL_DEPTH_SIZE, maxDepth,
            EGL10.EGL_SAMPLE_BUFFERS, 1,
            EGL10.EGL_SAMPLES, 4, 
            EGL_GL_COLORSPACE_KHR ,EGL_GL_COLORSPACE_SRGB_KHR //<--
            EGL10.EGL_NONE
    };

But in this case the devices I am testing on (Google NEXUS 6) crashes the app. Running OpenGL extension viewer I see the device doesn't support

EGL_KHR_gl_colorspace

extension.

In fact,I found here and on other online demos,that this setup is actually used.Also,iOS allows to configure default FBO to be sRGB with a flag :

kEAGLColorFormatSRGBA8

Is there another way to turn on sRGB on a Android device than that extension?(Of course another alternative is to gamma correct in shader,but that's exactly what I don't wanna do)


Solution

  • No, there is unfortunately no other way to create an sRGB default framebuffer.

    What you could do is use a workaround: render to a texture with internal format GL_SRGB8_ALPHA8 and treat that as your framebuffer, then at the end draw a full-screen quad to the default framebuffer, using the aforementioned texture and a gamma correction shader. (You will get values in linear RGB when reading from the texture, so you need to compress them back to sRGB when writing out to the default framebuffer; the framebuffer is ostensibly linear, but the values in it will be interpreted as sRGB by the display.)

    "The other guy" was entirely correct, but the default framebuffer is not a texture and you can't directly set its internal format.