I want to do off-screen image processing on Android in native code, so I need create the openGL context in native code by EGL.
By EGL, we can create EGLSurface, I can see there are three choices there: * EGL_WINDOW_BIT * EGL_PIXMAP_BIT * EGL_BUFFER_BIT
The first one is for on-screen processing, the second one is for off-screen, so I use EGL_PIXMAP_BIT like this:
// Step 1 - Get the default display.
EGLDisplay eglDisplay = eglGetDisplay((EGLNativeDisplayType) 0);
if ((eglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY)) == EGL_NO_DISPLAY) {
LOGH("eglGetDisplay() returned error %d", eglGetError());
exit(-1);
}
// Step 2 - Initialize EGL.
if (!eglInitialize(eglDisplay, 0, 0)) {
LOGH("eglInitialize() returned error %d", eglGetError());
exit(-1);
}
// Step 3 - Make OpenGL ES the current API.
eglBindAPI(EGL_OPENGL_ES_API);
// Step 4 - Specify the required configuration attributes.
EGLint pi32ConfigAttribs[] = { EGL_SURFACE_TYPE, EGL_PIXMAP_BIT,
EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_NONE,
EGL_BIND_TO_TEXTURE_RGBA, EGL_TRUE };
// Step 5 - Find a config that matches all requirements.
int iConfigs;
EGLConfig eglConfig;
eglChooseConfig(eglDisplay, pi32ConfigAttribs, &eglConfig, 1, &iConfigs);
if (iConfigs != 1) {
LOGH(
"Error: eglChooseConfig(): config not found %d - %d.\n", eglGetError(), iConfigs);
exit(-1);
}
// Step 6 - Create a surface to draw to.
EGLSurface eglSurface = eglCreatePbufferSurface(eglDisplay, eglConfig,
NULL);
// Step 7 - Create a context.
EGLContext eglContext = eglCreateContext(eglDisplay, eglConfig, NULL,
ai32ContextAttribs);
// Step 8 - Bind the context to the current thread
eglMakeCurrent(eglDisplay, eglSurface, eglSurface, eglContext);
The code failed at step 5, it seems Android doesn't support off screen processing? EGL_PIXMAP_BIT type is not supported.!
You are trying to use EGL options that just don't work on Android and pbuffers only work on some GPUs - not Nvidia Tegra.
pi32ConfigAttribs[]
should look like this regardless of whether it will be on-screen or off-screen:Android is very inflexible in how they support off-screen EGLSurfaces. They defined their own pixmap type named
EGL_NATIVE_BUFFER_ANDROID
.To create an EGL surface that is off-screen on Android, construct a
SurfaceTexture
and pass that toeglCreateWindowSurface()
. You should also look at using the EGL Image Extension andEGL_NATIVE_BUFFER_ANDROID
, as discussed here:http://software.intel.com/en-us/articles/using-opengl-es-to-accelerate-apps-with-legacy-2d-guis
http://software.intel.com/en-us/articles/porting-opengl-games-to-android-on-intel-atom-processors-part-1
UPDATE: Here is some sample code that creates an off-screen surface: