Please help,
I have created a program that uses OpenGL ES version 3.2 with OpenGL EGL defining the context and surface for headless rendering. I am able to render various images to image files without any problem.
However, I am now attempting to use this setup within the context of Dear ImGui and calling eglMakeCurrent
function fails. When I check the error code via eglGetError()
just after calling 'eglMakeCurrent the value returned is 12288 (
EGL_SUCCESS). So it fails but doesn't have an error via
eglGetError()`.
I have no idea what could be going on, but suspect it might be related to multiple context/threads with OpenGL EGL and Dear ImGui. It seems odd that there is no problem except when I try to use Dear ImGui with OpenGL EGL
If anyone has had any experience with this and found a solution, any help/hints would be greatly appreciated.
Below is snippet of the code (apologies for length):
Thank you in advance for any help/hint/link.
#include <EGL/egl.h>
#include <GLES3/gl32.h>
#include <EGL/eglext.h>
#include <sstream>
EGLint CONFIG_ATTRIBS[] = {
EGL_SURFACE_TYPE, EGL_PBUFFER_BIT,
EGL_RED_SIZE, 8,
EGL_GREEN_SIZE, 8,
EGL_BLUE_SIZE, 8,
EGL_ALPHA_SIZE, 8,
EGL_DEPTH_SIZE, 24,
EGL_STENCIL_SIZE, 8,
EGL_RENDERABLE_TYPE, EGL_OPENGL_ES3_BIT_KHR,
EGL_NONE
};
EGLint CONTEXT_ATTRIBS[] = {
EGL_CONTEXT_MAJOR_VERSION, 3,
EGL_CONTEXT_MINOR_VERSION, 2,
EGL_NONE
};
PFNEGLQUERYDEVICESEXTPROC eglQueryDevicesEXT =
reinterpret_cast<PFNEGLQUERYDEVICESEXTPROC>(eglGetProcAddress("eglQueryDevicesEXT"));
PFNEGLGETPLATFORMDISPLAYEXTPROC eglGetPlatformDisplayEXT =
reinterpret_cast<PFNEGLGETPLATFORMDISPLAYEXTPROC>(eglGetProcAddress("eglGetPlatformDisplayEXT"));
if(!eglQueryDevicesEXT || !eglGetPlatformDisplayEXT) {
throw std::runtime_error("Failed to get function pointers for OpenGL EGL extensions");
}
EGLDeviceEXT devices[MAX_DEVICES];
EGLint num_devices;
eglQueryDevicesEXT(MAX_DEVICES, devices, &num_devices);
if(num_devices < 1) {
throw std::runtime_error("No OpenGL EGL devices found");
}
...
display = eglGetPlatformDisplayEXT(EGL_PLATFORM_DEVICE_EXT, devices[0], 0);
if(display == EGL_NO_DISPLAY) {
std::stringstream ss;
ss << eglGetError();
throw std::runtime_error(std::string("Failed to get OpenGL EGL display: ") + ss.str());
}
EGLint major;
EGLint minor;
if(eglInitialize(display, &major, &minor) != EGL_TRUE) {
std::stringstream ss;
ss << eglGetError();
throw std::runtime_error(std::string("Failed OpenGL EGL initialize: ") + ss.str());
}
EGLint numConfigs;
if(eglChooseConfig(display, CONFIG_ATTRIBS, &configuration, 1, &numConfigs) == EGL_FALSE) {
std::stringstream ss;
ss << eglGetError();
throw std::runtime_error(std::string("OpenGL EGL failed to choose configuration: ") + ss.str());
}
context = eglCreateContext(display, configuration, EGL_NO_CONTEXT, CONTEXT_ATTRIBS);
if(context == EGL_NO_CONTEXT) {
std::stringstream ss;
ss << eglGetError();
throw std::runtime_error(std::string("EGL failed to create context: ") + ss.str());
}
...
// With width = 50, height = 50
EGLint surfaceAttribs[] = {
EGL_WIDTH, width,
EGL_HEIGHT, height,
EGL_NONE
};
EGLSurface surface = eglCreatePbufferSurface(display, configuration, surfaceAttribs);
if(surface == EGL_NO_SURFACE) {
std::cerr << "EGL failed to create buffer surface\n";
std::stringstream ss;
ss << eglGetError();
throw std::runtime_error(std::string("EGL failed to create buffer surface: ") + ss.str());
}
// The following is where the failure occurs
if(eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) {
std::cerr << "EGL failed to make current display\n";
std::stringstream ss;
ss << eglGetError();
throw std::runtime_error(std::string("EGL failed to make current display: ") + ss.str());
}