void GlContext::create(uint32_t _width, uint32_t _height) { # if BX_PLATFORM_RPI bcm_host_init(); # endif // BX_PLATFORM_RPI m_eglLibrary = eglOpen(); if (NULL == g_platformData.context) { # if BX_PLATFORM_RPI g_platformData.ndt = EGL_DEFAULT_DISPLAY; # endif // BX_PLATFORM_RPI BX_UNUSED(_width, _height); EGLNativeDisplayType ndt = (EGLNativeDisplayType)g_platformData.ndt; EGLNativeWindowType nwh = (EGLNativeWindowType )g_platformData.nwh; # if BX_PLATFORM_WINDOWS if (NULL == g_platformData.ndt) { ndt = GetDC( (HWND)g_platformData.nwh); } # endif // BX_PLATFORM_WINDOWS m_display = eglGetDisplay(ndt); BGFX_FATAL(m_display != EGL_NO_DISPLAY, Fatal::UnableToInitialize, "Failed to create display %p", m_display); EGLint major = 0; EGLint minor = 0; EGLBoolean success = eglInitialize(m_display, &major, &minor); BGFX_FATAL(success && major >= 1 && minor >= 3, Fatal::UnableToInitialize, "Failed to initialize %d.%d", major, minor); BX_TRACE("EGL info:"); const char* clientApis = eglQueryString(m_display, EGL_CLIENT_APIS); BX_TRACE(" APIs: %s", clientApis); BX_UNUSED(clientApis); const char* vendor = eglQueryString(m_display, EGL_VENDOR); BX_TRACE(" Vendor: %s", vendor); BX_UNUSED(vendor); const char* version = eglQueryString(m_display, EGL_VERSION); BX_TRACE("Version: %s", version); BX_UNUSED(version); const char* extensions = eglQueryString(m_display, EGL_EXTENSIONS); BX_TRACE("Supported EGL extensions:"); dumpExtensions(extensions); // https://www.khronos.org/registry/EGL/extensions/ANDROID/EGL_ANDROID_recordable.txt const bool hasEglAndroidRecordable = !bx::findIdentifierMatch(extensions, "EGL_ANDROID_recordable").isEmpty(); EGLint attrs[] = { EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, # if BX_PLATFORM_ANDROID EGL_DEPTH_SIZE, 16, # else EGL_DEPTH_SIZE, 24, # endif // BX_PLATFORM_ EGL_STENCIL_SIZE, 8, // Android Recordable surface hasEglAndroidRecordable ? 0x3142 : EGL_NONE, hasEglAndroidRecordable ? 1 : EGL_NONE, EGL_NONE }; EGLint numConfig = 0; success = eglChooseConfig(m_display, attrs, &m_config, 1, &numConfig); BGFX_FATAL(success, Fatal::UnableToInitialize, "eglChooseConfig"); # if BX_PLATFORM_ANDROID EGLint format; eglGetConfigAttrib(m_display, m_config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry( (ANativeWindow*)g_platformData.nwh, _width, _height, format); # elif BX_PLATFORM_RPI DISPMANX_DISPLAY_HANDLE_T dispmanDisplay = vc_dispmanx_display_open(0); DISPMANX_UPDATE_HANDLE_T dispmanUpdate = vc_dispmanx_update_start(0); VC_RECT_T dstRect = { 0, 0, int32_t(_width), int32_t(_height) }; VC_RECT_T srcRect = { 0, 0, int32_t(_width) << 16, int32_t(_height) << 16 }; DISPMANX_ELEMENT_HANDLE_T dispmanElement = vc_dispmanx_element_add(dispmanUpdate , dispmanDisplay , 0 , &dstRect , 0 , &srcRect , DISPMANX_PROTECTION_NONE , NULL , NULL , DISPMANX_NO_ROTATE ); s_dispmanWindow.element = dispmanElement; s_dispmanWindow.width = _width; s_dispmanWindow.height = _height; nwh = &s_dispmanWindow; vc_dispmanx_update_submit_sync(dispmanUpdate); # endif // BX_PLATFORM_ANDROID m_surface = eglCreateWindowSurface(m_display, m_config, nwh, NULL); BGFX_FATAL(m_surface != EGL_NO_SURFACE, Fatal::UnableToInitialize, "Failed to create surface."); const bool hasEglKhrCreateContext = !bx::findIdentifierMatch(extensions, "EGL_KHR_create_context").isEmpty(); const bool hasEglKhrNoError = !bx::findIdentifierMatch(extensions, "EGL_KHR_create_context_no_error").isEmpty(); const uint32_t gles = BGFX_CONFIG_RENDERER_OPENGLES; for (uint32_t ii = 0; ii < 2; ++ii) { bx::StaticMemoryBlockWriter writer(s_contextAttrs, sizeof(s_contextAttrs) ); EGLint flags = 0; # if BX_PLATFORM_RPI BX_UNUSED(hasEglKhrCreateContext, hasEglKhrNoError); # else if (hasEglKhrCreateContext) { bx::write(&writer, EGLint(EGL_CONTEXT_MAJOR_VERSION_KHR) ); bx::write(&writer, EGLint(gles / 10) ); bx::write(&writer, EGLint(EGL_CONTEXT_MINOR_VERSION_KHR) ); bx::write(&writer, EGLint(gles % 10) ); flags |= BGFX_CONFIG_DEBUG && hasEglKhrNoError ? 0 | EGL_CONTEXT_FLAG_NO_ERROR_BIT_KHR : 0 ; if (0 == ii) { flags |= BGFX_CONFIG_DEBUG ? 0 | EGL_CONTEXT_OPENGL_DEBUG_BIT_KHR // | EGL_OPENGL_ES3_BIT_KHR : 0 ; bx::write(&writer, EGLint(EGL_CONTEXT_FLAGS_KHR) ); bx::write(&writer, flags); } } else # endif // BX_PLATFORM_RPI { bx::write(&writer, EGLint(EGL_CONTEXT_CLIENT_VERSION) ); bx::write(&writer, 2); } bx::write(&writer, EGLint(EGL_NONE) ); m_context = eglCreateContext(m_display, m_config, EGL_NO_CONTEXT, s_contextAttrs); if (NULL != m_context) { break; } BX_TRACE("Failed to create EGL context with EGL_CONTEXT_FLAGS_KHR (%08x).", flags); } BGFX_FATAL(m_context != EGL_NO_CONTEXT, Fatal::UnableToInitialize, "Failed to create context."); success = eglMakeCurrent(m_display, m_surface, m_surface, m_context); BGFX_FATAL(success, Fatal::UnableToInitialize, "Failed to set context."); m_current = NULL; eglSwapInterval(m_display, 0); } import(); g_internalData.context = m_context; }
void g_initGles() { const EGLint attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_NONE }; const EGLint attrs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE, }; bwwindow=GetWindow(); bwdisplay=GetDisplay(); LOGE("Got bwdisplay %p", bwdisplay); LOGE("Got bwwindow %p", bwwindow); LOGI("Initializing context"); if (bwdisplay != EGL_NO_DISPLAY) { LOGI("%d", 2222); } if (!eglInitialize(bwdisplay, 0, 0)) { LOGI("eglInitialize() returned error %d", eglGetError()); } eglBindAPI(EGL_OPENGL_ES_API); if (!eglChooseConfig(bwdisplay, attribs, &bwconfig, 1, &bwnumConfigs)) { LOGI("eglChooseConfig() returned error %d", eglGetError()); g_destroyGL(); } if (!eglGetConfigAttrib(bwdisplay, bwconfig, EGL_NATIVE_VISUAL_ID, &bwformat)) { LOGI("eglGetConfigAttrib() returned error %d", eglGetError()); g_destroyGL(); } ANativeWindow_setBuffersGeometry(bwwindow, 0, 0, bwformat); LOGI("**********pgc1************"); if (!(bwsurface_copy = eglCreateWindowSurface(bwdisplay, bwconfig, bwwindow, 0))) { LOGI("eglCreateWindowSurface() returned error %d", eglGetError()); // g_destroyGL(); }else{ bwsurface = bwsurface_copy; } LOGI("**********pgc2************"); if (!(bwcontext_copy = eglCreateContext(bwdisplay, bwconfig, EGL_NO_CONTEXT, attrs))) { LOGI("eglCreateContext() returned error %d", eglGetError()); // g_destroyGL(); }else{ bwcontext = bwcontext_copy; } if (!eglMakeCurrent(bwdisplay, bwsurface, bwsurface, bwcontext)) { LOGI("eglMakeCurrent() returned error %d", eglGetError()); // g_destroyGL(); } if (!eglQuerySurface(bwdisplay, bwsurface, EGL_WIDTH, &bwwidth) || !eglQuerySurface(bwdisplay, bwsurface, EGL_HEIGHT, &bwheight)) { LOGI("eglQuerySurface() returned error %d", eglGetError()); // g_destroyGL(); } printGLString("Version", GL_VERSION); printGLString("Vendor", GL_VENDOR); printGLString("Renderer", GL_RENDERER); printGLString("Extensions", GL_EXTENSIONS); glHint( GL_GENERATE_MIPMAP_HINT, GL_NICEST ); glHint( GL_FRAGMENT_SHADER_DERIVATIVE_HINT_OES, GL_NICEST ); glEnable( GL_DEPTH_TEST ); glEnable( GL_CULL_FACE ); glDisable( GL_DITHER ); glDepthMask( GL_TRUE ); glDepthFunc( GL_LESS ); glDepthRangef( 0.0f, 1.0f ); glClearDepthf( 1.0f ); glCullFace ( GL_BACK ); glFrontFace( GL_CCW ); glClearStencil( 0 ); glStencilMask( 0xFFFFFFFF ); //绘制三角形 // setupGraphics(1232,800); // if (bwdisplay) { // renderFrame(); // if (!eglSwapBuffers(bwdisplay, bwsurface)) { // LOGE("eglSwapBuffers() returned error %d", eglGetError()); // g_destroyGL(); // } // // } }
//Changed the constructor to a member function so that the //native constructor would be called first. This member //function is then called from the native constructor. void EGLPBuffer::initEGLPBuffer() { // These are now initialized in the native constructors. // mGLSupport = glsupport; // mGlDisplay = mGLSupport->getGLDisplay(); mEglDrawable = 0; ::EGLConfig glConfig = 0; bool isFloat = false; int bits = 0; switch (mFormat) { case PCT_BYTE: bits = 8; break; case PCT_SHORT: case PCT_FLOAT16: bits = 16; break; case PCT_FLOAT32: bits = 32; break; default: break; } if (mFormat == PCT_FLOAT16 || mFormat == PCT_FLOAT32) { OGRE_EXCEPT(Exception::ERR_NOT_IMPLEMENTED, "No support for Floating point PBuffers", "EGLRenderTexture::initEGLPBuffer"); } EGLint minAttribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT | EGL_PBUFFER_BIT, EGL_DEPTH_SIZE, 16, EGL_NONE }; EGLint maxAttribs[] = { EGL_RED_SIZE, bits, EGL_GREEN_SIZE, bits, EGL_BLUE_SIZE, bits, EGL_ALPHA_SIZE, bits, EGL_STENCIL_SIZE, INT_MAX, EGL_NONE }; EGLint pBufferAttribs[] = { // First we specify the width of the surface... EGL_WIDTH, mWidth, // ...then the height of the surface... EGL_HEIGHT, mHeight, /* ... then we specifiy the target for the texture that will be created when the pbuffer is created...*/ EGL_TEXTURE_TARGET, EGL_TEXTURE_2D, /*..then the format of the texture that will be created when the pBuffer is bound to a texture...*/ EGL_TEXTURE_FORMAT, EGL_TEXTURE_RGB, // The final thing is EGL_NONE which signifies the end. EGL_NONE }; glConfig = mGLSupport->selectGLConfig(minAttribs, maxAttribs); EGL_CHECK_ERROR; mEglDrawable = eglCreatePbufferSurface(mGlDisplay, glConfig, pBufferAttribs); EGL_CHECK_ERROR; if (!glConfig || !mEglDrawable) { OGRE_EXCEPT(Exception::ERR_RENDERINGAPI_ERROR, "Unable to create Pbuffer", "EGLPBuffer::EGLPBuffer"); } EGLint glConfigID; EGLint iWidth, iHeight; eglGetConfigAttrib(mGlDisplay, glConfig, EGL_CONFIG_ID, &glConfigID); EGL_CHECK_ERROR; eglQuerySurface(mGlDisplay, mEglDrawable, EGL_WIDTH, &iWidth); EGL_CHECK_ERROR; eglQuerySurface(mGlDisplay, mEglDrawable, EGL_HEIGHT, &iHeight); EGL_CHECK_ERROR; mWidth = iWidth; mHeight = iHeight; LogManager::getSingleton().logMessage(LML_NORMAL, "EGLPBuffer::create used final dimensions " + StringConverter::toString(mWidth) + " x " + StringConverter::toString(mHeight)); LogManager::getSingleton().logMessage("EGLPBuffer::create used FBConfigID " + StringConverter::toString(glConfigID)); }
// Returns the specified attribute of the specified EGLConfig // static int getConfigAttrib(EGLConfig config, int attrib) { int value; eglGetConfigAttrib(_glfw.egl.display, config, attrib, &value); return value; }
VisualID QXlibEglIntegration::getCompatibleVisualId(Display *display, EGLDisplay eglDisplay, EGLConfig config) { VisualID visualId = 0; EGLint eglValue = 0; EGLint configRedSize = 0; eglGetConfigAttrib(eglDisplay, config, EGL_RED_SIZE, &configRedSize); EGLint configGreenSize = 0; eglGetConfigAttrib(eglDisplay, config, EGL_GREEN_SIZE, &configGreenSize); EGLint configBlueSize = 0; eglGetConfigAttrib(eglDisplay, config, EGL_BLUE_SIZE, &configBlueSize); EGLint configAlphaSize = 0; eglGetConfigAttrib(eglDisplay, config, EGL_ALPHA_SIZE, &configAlphaSize); eglGetConfigAttrib(eglDisplay, config, EGL_CONFIG_ID, &eglValue); int configId = eglValue; // See if EGL provided a valid VisualID: eglGetConfigAttrib(eglDisplay, config, EGL_NATIVE_VISUAL_ID, &eglValue); visualId = (VisualID)eglValue; if (visualId) { // EGL has suggested a visual id, so get the rest of the visual info for that id: XVisualInfo visualInfoTemplate; memset(&visualInfoTemplate, 0, sizeof(XVisualInfo)); visualInfoTemplate.visualid = visualId; XVisualInfo *chosenVisualInfo; int matchingCount = 0; chosenVisualInfo = XGetVisualInfo(display, VisualIDMask, &visualInfoTemplate, &matchingCount); if (chosenVisualInfo) { // Skip size checks if implementation supports non-matching visual // and config (QTBUG-9444). if (q_hasEglExtension(eglDisplay,"EGL_NV_post_convert_rounding")) { XFree(chosenVisualInfo); return visualId; } int visualRedSize = qPopulationCount(chosenVisualInfo->red_mask); int visualGreenSize = qPopulationCount(chosenVisualInfo->green_mask); int visualBlueSize = qPopulationCount(chosenVisualInfo->blue_mask); int visualAlphaSize = chosenVisualInfo->depth == 32 ? 8 : 0; const bool visualMatchesConfig = visualRedSize == configRedSize && visualGreenSize == configGreenSize && visualBlueSize == configBlueSize && visualAlphaSize == configAlphaSize; // In some cases EGL tends to suggest a 24-bit visual for 8888 // configs. In such a case we have to fall back to XGetVisualInfo. if (!visualMatchesConfig) { visualId = 0; #ifdef QT_DEBUG_X11_VISUAL_SELECTION qWarning("Warning: EGL suggested using X Visual ID %d (%d %d %d depth %d) for EGL config %d (%d %d %d %d), but this is incompatible", (int)visualId, visualRedSize, visualGreenSize, visualBlueSize, chosenVisualInfo->depth, configId, configRedSize, configGreenSize, configBlueSize, configAlphaSize); #endif } } else { qWarning("Warning: EGL suggested using X Visual ID %d for EGL config %d, but that isn't a valid ID", (int)visualId, configId); visualId = 0; } XFree(chosenVisualInfo); } #ifdef QT_DEBUG_X11_VISUAL_SELECTION else qDebug("EGL did not suggest a VisualID (EGL_NATIVE_VISUAL_ID was zero) for EGLConfig %d", configId); #endif if (visualId) { #ifdef QT_DEBUG_X11_VISUAL_SELECTION if (configAlphaSize > 0) qDebug("Using ARGB Visual ID %d provided by EGL for config %d", (int)visualId, configId); else qDebug("Using Opaque Visual ID %d provided by EGL for config %d", (int)visualId, configId); #endif return visualId; } // Finally, try to use XGetVisualInfo and only use the bit depths to match on: if (!visualId) { XVisualInfo visualInfoTemplate; memset(&visualInfoTemplate, 0, sizeof(XVisualInfo)); XVisualInfo *matchingVisuals; int matchingCount = 0; visualInfoTemplate.depth = configRedSize + configGreenSize + configBlueSize + configAlphaSize; matchingVisuals = XGetVisualInfo(display, VisualDepthMask, &visualInfoTemplate, &matchingCount); if (!matchingVisuals) { // Try again without taking the alpha channel into account: visualInfoTemplate.depth = configRedSize + configGreenSize + configBlueSize; matchingVisuals = XGetVisualInfo(display, VisualDepthMask, &visualInfoTemplate, &matchingCount); } if (matchingVisuals) { visualId = matchingVisuals[0].visualid; XFree(matchingVisuals); } } if (visualId) { #ifdef QT_DEBUG_X11_VISUAL_SELECTION qDebug("Using Visual ID %d provided by XGetVisualInfo for EGL config %d", (int)visualId, configId); #endif return visualId; } qWarning("Unable to find an X11 visual which matches EGL config %d", configId); return (VisualID)0; }
static DFBResult InitLocal( AndroidData *android ) { /* * Here specify the attributes of the desired configuration. * Below, we select an EGLConfig with at least 8 bits per color * component compatible with on-screen windows */ const EGLint attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_ALPHA_SIZE, 8, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_NATIVE_VISUAL_ID, HAL_PIXEL_FORMAT_RGBA_8888, // DSPF_ARGB EGL_NONE }; static const EGLint ctx_attribs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; EGLint w, h, dummy, format; EGLint numConfigs; EGLConfig config; EGLSurface surface; EGLContext context; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); eglInitialize(display, 0, 0); /* Here, the application chooses the configuration it desires. In this * sample, we have a very simplified selection process, where we pick * the first EGLConfig that matches our criteria */ eglChooseConfig(display, attribs, &config, 1, &numConfigs); /* EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is * guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). * As soon as we picked a EGLConfig, we can safely reconfigure the * ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. */ eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry( native_data.app->window, 0, 0, format); // ANativeActivity_setWindowFlags( native_data.app->window, AWINDOW_FLAG_FULLSCREEN | AWINDOW_FLAG_KEEP_SCREEN_ON , 0 ); surface = eglCreateWindowSurface(display, config, native_data.app->window, NULL); context = eglCreateContext(display, config, NULL, ctx_attribs); if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { LOGW("Unable to eglMakeCurrent"); return -1; } eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); android->dpy = display; android->ctx = context; android->surface = surface; android->shared->screen_size.w = w; android->shared->screen_size.h = h; if (strstr(glGetString(GL_RENDERER),"SGX")) android->shared->native_pixelformat = HAL_PIXEL_FORMAT_RGBA_8888; //ANativeWindow_getFormat(native_data.app->window); else android->shared->native_pixelformat = ANativeWindow_getFormat(native_data.app->window); // Initialize GL state. // glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST); glEnable(GL_CULL_FACE); // glShadeModel(GL_SMOOTH); glDisable(GL_DEPTH_TEST); // Just fill the screen with a color. glClearColor( .5, .5, .5, 1 ); glClear( GL_COLOR_BUFFER_BIT ); eglSwapBuffers( android->dpy, android->surface ); return DFB_OK; }
void GLESRender::CreateRenderDevice(TngWindow* mainwnd) { render__ = this; mainwnd__ = mainwnd; Log::GetLog()->Printf(Log::DBG_CHN,"pre create gles"); int samples = RenderConfig::GetInstance().multisampling_ ? RenderConfig::GetInstance().multisampling_ : 0; EGLint eglConfigAttrs[] = { EGL_SAMPLE_BUFFERS, samples > 0 ? 1 : 0, EGL_SAMPLES, samples, EGL_DEPTH_SIZE, 24, EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_ALPHA_SIZE, 8, EGL_STENCIL_SIZE, 8, EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_NONE }; __multiSampling = samples > 0; EGLint eglConfigCount; const EGLint eglContextAttrs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; const EGLint eglSurfaceAttrs[] = { EGL_RENDER_BUFFER, EGL_BACK_BUFFER, EGL_NONE }; if (__eglDisplay == EGL_NO_DISPLAY && __eglContext == EGL_NO_CONTEXT) { // Get the EGL display and initialize. __eglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY); if (__eglDisplay == EGL_NO_DISPLAY) { checkErrorEGL("eglGetDisplay"); return; } if (eglInitialize(__eglDisplay, NULL, NULL) != EGL_TRUE) { checkErrorEGL("eglInitialize"); return; } else Log::GetLog()->Printf(Log::DBG_CHN,"egl Initialized"); // Try both 24 and 16-bit depth sizes since some hardware (i.e. Tegra) does not support 24-bit depth bool validConfig = false; EGLint depthSizes[] = { 24, 16 }; for (unsigned int i = 0; i < 2; ++i) { eglConfigAttrs[1] = samples > 0 ? 1 : 0; eglConfigAttrs[3] = samples; eglConfigAttrs[5] = depthSizes[i]; /* Here, the application chooses the configuration it desires. */ if (eglChooseConfig(__eglDisplay, eglConfigAttrs, &__eglConfig, 1, &eglConfigCount) == EGL_TRUE && eglConfigCount > 0) { validConfig = true; break; } if (samples) { // Try lowering the MSAA sample size until we find a supported config int sampleCount = samples; while (sampleCount) { Log::GetLog()->Printf(Log::WARNING_CHN,"No EGL config found for depth_size=%d and samples=%d. Trying samples=%d instead.", depthSizes[i], sampleCount, sampleCount / 2); sampleCount /= 2; eglConfigAttrs[1] = sampleCount > 0 ? 1 : 0; eglConfigAttrs[3] = sampleCount; if (eglChooseConfig(__eglDisplay, eglConfigAttrs, &__eglConfig, 1, &eglConfigCount) == EGL_TRUE && eglConfigCount > 0) { validConfig = true; break; } } __multiSampling = sampleCount > 0; if (validConfig) break; } else { Log::GetLog()->Printf(Log::WARNING_CHN,"No EGL config found for depth_size=%d.", depthSizes[i]); } } if (!validConfig) { checkErrorEGL("eglChooseConfig"); return; }else Log::GetLog()->Printf(Log::DBG_CHN,"eglChooseConfig"); __eglContext = eglCreateContext(__eglDisplay, __eglConfig, EGL_NO_CONTEXT, eglContextAttrs); if (__eglContext == EGL_NO_CONTEXT) { checkErrorEGL("eglCreateContext"); return; } else Log::GetLog()->Printf(Log::DBG_CHN,"eglCreateContext"); } // EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is // guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). // As soon as we picked a EGLConfig, we can safely reconfigure the // ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. EGLint format; eglGetConfigAttrib(__eglDisplay, __eglConfig, EGL_NATIVE_VISUAL_ID, &format); Log::GetLog()->Printf(Log::DBG_CHN,"state addr=%d.",OS::state__); Log::GetLog()->Printf(Log::DBG_CHN,"wnd addr=%d.",OS::state__->window); ANativeWindow_setBuffersGeometry(OS::state__->window, 0, 0, format); __eglSurface = eglCreateWindowSurface(__eglDisplay, __eglConfig, OS::state__->window, eglSurfaceAttrs); if (__eglSurface == EGL_NO_SURFACE) { checkErrorEGL("eglCreateWindowSurface"); return; } else Log::GetLog()->Printf(Log::DBG_CHN,"eglCreateWindowSurface"); if (eglMakeCurrent(__eglDisplay, __eglSurface, __eglSurface, __eglContext) != EGL_TRUE) { checkErrorEGL("eglMakeCurrent"); return; } else Log::GetLog()->Printf(Log::DBG_CHN,"eglMakeCurrent"); EGLint szx = RenderConfig::GetInstance().back_buffer_sizex_; EGLint szy = RenderConfig::GetInstance().back_buffer_sizey_; eglQuerySurface(__eglDisplay, __eglSurface, EGL_WIDTH, &szx); eglQuerySurface(__eglDisplay, __eglSurface, EGL_HEIGHT, &szy); Log::GetLog()->Printf(Log::SYS_CHN, "target device width(%d),heigh(%d)",szx,szy); mainwnd->width_ = szx; mainwnd->height_ = szy; // Set vsync. eglSwapInterval(__eglDisplay, 1); // Initialize OpenGL ES extensions. _loadExtentions(); if (_checkExtention("GL_OES_vertex_array_object") || _checkExtention("GL_ARB_vertex_array_object")) { // Disable VAO extension for now. glBindVertexArray = (PFNGLBINDVERTEXARRAYOESPROC)eglGetProcAddress("glBindVertexArrayOES"); glDeleteVertexArrays = (PFNGLDELETEVERTEXARRAYSOESPROC)eglGetProcAddress("glDeleteVertexArrays"); glGenVertexArrays = (PFNGLGENVERTEXARRAYSOESPROC)eglGetProcAddress("glGenVertexArraysOES"); glIsVertexArray = (PFNGLISVERTEXARRAYOESPROC)eglGetProcAddress("glIsVertexArrayOES"); if (glBindVertexArray) { Log::GetLog()->Printf(Log::SYS_CHN,"using vao"); } } Log::GetLog()->Printf(Log::SYS_CHN, "gles device created"); OS::state__->onAppCmd =engine_handle_cmd; OS::state__->onInputEvent =engine_handle_input; }
/** * Initialize an EGL context for the current display. */ static int engine_init_display(struct engine* engine) { // initialize OpenGL ES and EGL /* * Here specify the attributes of the desired configuration. * Below, we select an EGLConfig with at least 8 bits per color * component compatible with on-screen windows */ const EGLint attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_NONE }; EGLint w, h, dummy, format; EGLint numConfigs; EGLConfig config; EGLSurface surface; EGLContext context; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); eglInitialize(display, 0, 0); /* Here, the application chooses the configuration it desires. In this * sample, we have a very simplified selection process, where we pick * the first EGLConfig that matches our criteria */ eglChooseConfig(display, attribs, &config, 1, &numConfigs); /* EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is * guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). * As soon as we picked a EGLConfig, we can safely reconfigure the * ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. */ eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry(engine->app->window, 0, 0, format); surface = eglCreateWindowSurface(display, config, engine->app->window, NULL); context = eglCreateContext(display, config, NULL, NULL); if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { LOGI("Unable to eglMakeCurrent"); return -1; } eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); engine->display = display; engine->context = context; engine->surface = surface; engine->width = w; engine->height = h; engine->state.angle = 0; // Initialize GL state. glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST); glEnable(GL_CULL_FACE); glShadeModel(GL_SMOOTH); glDisable(GL_DEPTH_TEST); return 0; }
void QEglFSScreen::createAndSetPlatformContext() { QPlatformWindowFormat platformFormat = QPlatformWindowFormat::defaultFormat(); platformFormat.setWindowApi(QPlatformWindowFormat::OpenGL); QByteArray depthString = qgetenv("QT_QPA_EGLFS_DEPTH"); if (depthString.toInt() == 16) { platformFormat.setDepth(16); platformFormat.setRedBufferSize(5); platformFormat.setGreenBufferSize(6); platformFormat.setBlueBufferSize(5); m_depth = 16; m_format = QImage::Format_RGB16; } else { platformFormat.setDepth(32); platformFormat.setRedBufferSize(8); platformFormat.setGreenBufferSize(8); platformFormat.setBlueBufferSize(8); m_depth = 32; m_format = QImage::Format_RGB32; } if (!qgetenv("QT_QPA_EGLFS_MULTISAMPLE").isEmpty()) { platformFormat.setSampleBuffers(true); } EGLConfig config = q_configFromQPlatformWindowFormat(m_dpy, platformFormat); EGLNativeWindowType eglWindow = 0; #ifdef Q_OPENKODE if (kdInitializeNV() == KD_ENOTINITIALIZED) { qFatal("Did not manage to initialize openkode"); } KDWindow *window = kdCreateWindow(m_dpy,config,0); kdRealizeWindow(window,&eglWindow); #endif m_surface = eglCreateWindowSurface(m_dpy, config, eglWindow, NULL); if (m_surface == EGL_NO_SURFACE) { qWarning("Could not create the egl surface: error = 0x%x\n", eglGetError()); eglTerminate(m_dpy); qFatal("EGL error"); } // qWarning("Created surface %dx%d\n", w, h); #ifdef QEGL_EXTRA_DEBUG qWarning("Configuration %d matches requirements\n", (int)config); for (index = 0; attrs[index].attr != -1; ++index) { EGLint value; if (eglGetConfigAttrib(m_dpy, config, attrs[index].attr, &value)) { qWarning("\t%s: %d\n", attrs[index].name, (int)value); } } qWarning("\n"); #endif EGLint temp; EGLint attribList[32]; temp = 0; attribList[temp++] = EGL_CONTEXT_CLIENT_VERSION; attribList[temp++] = 2; // GLES version 2 attribList[temp++] = EGL_NONE; QEGLPlatformContext *platformContext = new QEGLPlatformContext(m_dpy,config,attribList,m_surface,EGL_OPENGL_ES_API); m_platformContext = platformContext; EGLint w,h; // screen size detection eglQuerySurface(m_dpy, m_surface, EGL_WIDTH, &w); eglQuerySurface(m_dpy, m_surface, EGL_HEIGHT, &h); m_geometry = QRect(0,0,w,h); }
bool SkOSWindow::attach(SkBackEndTypes attachType, int /*msaaSampleCount*/, bool /*deepColor*/ AttachmentInfo* info) { static const EGLint kEGLContextAttribsForOpenGL[] = { EGL_NONE }; static const EGLint kEGLContextAttribsForOpenGLES[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; static const struct { const EGLint* fContextAttribs; EGLenum fAPI; EGLint fRenderableTypeBit; } kAPIs[] = { { // OpenGL kEGLContextAttribsForOpenGL, EGL_OPENGL_API, EGL_OPENGL_BIT, }, { // OpenGL ES. This seems to work for both ES2 and 3 (when available). kEGLContextAttribsForOpenGLES, EGL_OPENGL_ES_API, EGL_OPENGL_ES2_BIT, }, }; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); if (EGL_NO_DISPLAY == display) { return false; } EGLint majorVersion; EGLint minorVersion; if (!eglInitialize(display, &majorVersion, &minorVersion)) { return false; } for (size_t api = 0; api < SK_ARRAY_COUNT(kAPIs); ++api) { if (!eglBindAPI(kAPIs[api].fAPI)) { continue; } #if 0 SkDebugf("VENDOR: %s\n", eglQueryString(fDisplay, EGL_VENDOR)); SkDebugf("APIS: %s\n", eglQueryString(fDisplay, EGL_CLIENT_APIS)); SkDebugf("VERSION: %s\n", eglQueryString(fDisplay, EGL_VERSION)); SkDebugf("EXTENSIONS %s\n", eglQueryString(fDisplay, EGL_EXTENSIONS)); #endif const EGLint configAttribs[] = { EGL_SURFACE_TYPE, EGL_PBUFFER_BIT, EGL_RENDERABLE_TYPE, kAPIs[api].fRenderableTypeBit, EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_ALPHA_SIZE, 8, EGL_NONE }; EGLint format; EGLint numConfigs; EGLConfig config; EGLSurface surface; EGLContext context; /* Here, the application chooses the configuration it desires. In this * sample, we have a very simplified selection process, where we pick * the first EGLConfig that matches our criteria */ if (!eglChooseConfig(display, configAttribs, &config, 1, &numConfigs) || numConfigs != 1) { continue; } /* EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is * guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). * As soon as we picked a EGLConfig, we can safely reconfigure the * ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. */ if (!eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format)) { continue; } ANativeWindow_setBuffersGeometry(fNativeWindow, 0, 0, format); surface = eglCreateWindowSurface(display, config, fNativeWindow, nullptr); if (EGL_NO_SURFACE == surface) { SkDebugf("eglCreateWindowSurface failed. EGL Error: 0x%08x\n", eglGetError()); continue; } context = eglCreateContext(display, config, nullptr, kAPIs[api].fContextAttribs); if (EGL_NO_CONTEXT == context) { SkDebugf("eglCreateContext failed. EGL Error: 0x%08x\n", eglGetError()); eglDestroySurface(display, surface); continue; } if (!eglMakeCurrent(display, surface, surface, context)) { SkDebugf("eglMakeCurrent failed. EGL Error: 0x%08x\n", eglGetError()); eglDestroyContext(display, context); eglDestroySurface(display, surface); continue; } fWindow.fDisplay = display; fWindow.fContext = context; fWindow.fSurface = surface; break; } if (fWindow.fDisplay && fWindow.fContext && fWindow.fSurface) { EGLint w, h; eglQuerySurface(fWindow.fDisplay, fWindow.fSurface, EGL_WIDTH, &w); eglQuerySurface(fWindow.fDisplay, fWindow.fSurface, EGL_HEIGHT, &h); glViewport(0, 0, w, h); glClearColor(0.0, 0, 0, 0.0); glClearStencil(0); glClear(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT); // We retrieve the fullscreen width and height this->setSize((SkScalar)w, (SkScalar)h); return true; } else { return false; } }
bool Game::InitDisplay() { /* * Here specify the attributes of the desired configuration. * Below, we select an EGLConfig with at least 8 bits per color * component compatible with on-screen windows */ const EGLint attribs[] = { EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_DEPTH_SIZE, 24, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, //Maybe EGL_CONFORMANT for windows and Android? EGL_NONE }; EGLint attrib_list[]= { EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_RENDERABLE_TYPE, 0, EGL_NONE}; EGLint w, h, format; EGLint numConfigs; EGLConfig config[64]; EGLSurface surface; EGLContext context; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); int maj; int min; eglInitialize(display, &maj, &min); Log::Debug("EGLInitialise", "EGL Major:%d Minor:%d", maj, min); /* Here, the application chooses the configuration it desires. In this * sample, we have a very simplified selection process, where we pick * the first EGLConfig that matches our criteria */ eglChooseConfig(display, attribs, &config[0], 64, &numConfigs); for(int i = 0; i < numConfigs; i++) { int val[1]; eglGetConfigAttrib(display, config[i], EGL_CONFORMANT, &val[0]); Log::Debug("EGLInitialise", "EGL_CONFORMANT: %d", val[0]); Log::Debug("EGLInitialise", "GL2: %d", val[0] & EGL_OPENGL_ES2_BIT); Log::Debug("EGLInitialise", "GL1: %d", val[0] & EGL_OPENGL_ES_BIT); } if(numConfigs == 0) { Log::Error("EGLInitialise", "No EGL configs were returned."); return true; } /* EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is * guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). * As soon as we picked a EGLConfig, we can safely reconfigure the * ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. */ eglGetConfigAttrib(display, config[0], EGL_NATIVE_VISUAL_ID, &format); #ifdef ANDROID ANativeWindow_setBuffersGeometry(mDisplay.app->window, 0, 0, format); //TODO! surface = eglCreateWindowSurface(display, config[0], mDisplay.app->window, NULL); #endif #ifdef _WIN32 mDisplay.WindowHandle = create_window(mDisplay.Width, mDisplay.Height); surface = EGL_CHECK(eglCreateWindowSurface(display, config[0], (EGLNativeWindowType)mDisplay.WindowHandle, NULL)); #endif #ifdef __QNX__ int screen_format = SCREEN_FORMAT_RGBX8888; int usage = SCREEN_USAGE_OPENGL_ES2 | SCREEN_USAGE_ROTATION; int screen_resolution[2]; screen_display_mode_t screen_mode; int size[2]; int angle = std::atoi(std::getenv("ORIENTATION")); screen_create_window(&mDisplay.qnx_screen_win, mDisplay.qnx_screen_context); screen_set_window_property_iv(mDisplay.qnx_screen_win, SCREEN_PROPERTY_FORMAT, &screen_format); screen_set_window_property_iv(mDisplay.qnx_screen_win, SCREEN_PROPERTY_USAGE, &usage); screen_get_window_property_pv(mDisplay.qnx_screen_win, SCREEN_PROPERTY_DISPLAY, (void **)&mDisplay.qnx_screen_disp); screen_get_display_property_iv(mDisplay.qnx_screen_disp, SCREEN_PROPERTY_SIZE, screen_resolution); screen_get_display_property_pv(mDisplay.qnx_screen_disp, SCREEN_PROPERTY_MODE, (void**)&screen_mode); screen_get_window_property_iv(mDisplay.qnx_screen_win, SCREEN_PROPERTY_BUFFER_SIZE, size); int buffer_size[2] = {size[0], size[1]}; if ((angle == 0) || (angle == 180)) { if (((screen_mode.width > screen_mode.height) && (size[0] < size[1])) || ((screen_mode.width < screen_mode.height) && (size[0] > size[1]))) { buffer_size[1] = size[0]; buffer_size[0] = size[1]; } } else if ((angle == 90) || (angle == 270)){ if (((screen_mode.width > screen_mode.height) && (size[0] > size[1])) || ((screen_mode.width < screen_mode.height && size[0] < size[1]))) { buffer_size[1] = size[0]; buffer_size[0] = size[1]; } } else { return true; } screen_set_window_property_iv(mDisplay.qnx_screen_win, SCREEN_PROPERTY_BUFFER_SIZE, buffer_size); screen_set_window_property_iv(mDisplay.qnx_screen_win, SCREEN_PROPERTY_ROTATION, &angle); screen_create_window_buffers(mDisplay.qnx_screen_win, 2); surface = EGL_CHECK(eglCreateWindowSurface(display, config[0], (EGLNativeWindowType)mDisplay.qnx_screen_win, NULL)); #endif if(surface == EGL_NO_SURFACE) { Log::Error("EGLInitialise", "EGL Surface creation failed."); return true; } const EGLint attribs2[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; context = eglCreateContext(display, config[0], NULL, attribs2); if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { Log::Error("EGLInitialise", "Unable to eglMakeCurrent"); return true; } #ifdef __QNX__ eglSwapInterval(display, 1); #endif eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); mDisplay.Display = display; mDisplay.Context = context; mDisplay.Surface = surface; mDisplay.Width = w; mDisplay.Height = h; mTP->camera->SetResolution(Vector2f((float)mDisplay.Width, (float)mDisplay.Height)); // Initialize GL state. GL_CHECK(glViewport(0, 0, w, h)); GL_CHECK(glEnable(GL_DEPTH_TEST)); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); GL_CHECK(glEnable(GL_BLEND)); GL_CHECK(glEnable(GL_ALPHA)); Effect::CacheTick(*mTP, EffectClearLevel::Initialise); Texture::CacheTick(*mTP, TextureClearLevel::Initialise); Font::CacheTick(*mTP, FontClearLevel::Initialise); //Initialise graphics for(std::vector<GameObject*>::iterator it = mGO.begin(); it != mGO.end(); ++it) { (*it)->InitialiseGraphics(*mTP); } return false; }
void startDriver() { x_dpy = XOpenDisplay(NULL); if (!x_dpy) { fprintf(stderr, "XOpenDisplay failed\n"); exit(1); } e_dpy = eglGetDisplay(x_dpy); if (!e_dpy) { fprintf(stderr, "eglGetDisplay failed: %s\n", eglGetErrorStr()); exit(1); } EGLint e_major, e_minor; if (!eglInitialize(e_dpy, &e_major, &e_minor)) { fprintf(stderr, "eglInitialize failed: %s\n", eglGetErrorStr()); exit(1); } if (!eglBindAPI(EGL_OPENGL_ES_API)) { fprintf(stderr, "eglBindAPI failed: %s\n", eglGetErrorStr()); exit(1); } static const EGLint attribs[] = { EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_DEPTH_SIZE, 16, EGL_CONFIG_CAVEAT, EGL_NONE, EGL_NONE }; EGLint num_configs; if (!eglChooseConfig(e_dpy, attribs, &e_config, 1, &num_configs)) { fprintf(stderr, "eglChooseConfig failed: %s\n", eglGetErrorStr()); exit(1); } EGLint vid; if (!eglGetConfigAttrib(e_dpy, e_config, EGL_NATIVE_VISUAL_ID, &vid)) { fprintf(stderr, "eglGetConfigAttrib failed: %s\n", eglGetErrorStr()); exit(1); } XVisualInfo visTemplate; visTemplate.visualid = vid; int num_visuals; x_visual_info = XGetVisualInfo(x_dpy, VisualIDMask, &visTemplate, &num_visuals); if (!x_visual_info) { fprintf(stderr, "XGetVisualInfo failed\n"); exit(1); } x_root = RootWindow(x_dpy, DefaultScreen(x_dpy)); x_colormap = XCreateColormap(x_dpy, x_root, x_visual_info->visual, AllocNone); if (!x_colormap) { fprintf(stderr, "XCreateColormap failed\n"); exit(1); } static const EGLint ctx_attribs[] = { EGL_CONTEXT_CLIENT_VERSION, 3, EGL_NONE }; e_ctx = eglCreateContext(e_dpy, e_config, EGL_NO_CONTEXT, ctx_attribs); if (!e_ctx) { fprintf(stderr, "eglCreateContext failed: %s\n", eglGetErrorStr()); exit(1); } wm_delete_window = XInternAtom(x_dpy, "WM_DELETE_WINDOW", False); wm_protocols = XInternAtom(x_dpy, "WM_PROTOCOLS", False); wm_take_focus= XInternAtom(x_dpy, "WM_TAKE_FOCUS", False); const int key_lo = 8; const int key_hi = 255; int keysyms_per_keycode; KeySym *keysyms = XGetKeyboardMapping(x_dpy, key_lo, key_hi-key_lo+1, &keysyms_per_keycode); if (keysyms_per_keycode < 2) { fprintf(stderr, "XGetKeyboardMapping returned too few keysyms per keycode: %d\n", keysyms_per_keycode); exit(1); } int k; for (k = key_lo; k <= key_hi; k++) { onKeysym(k, keysyms[(k-key_lo)*keysyms_per_keycode + 0], keysyms[(k-key_lo)*keysyms_per_keycode + 1]); } }
// EGL初期化 static int engine_init_display(struct engine* engine) { EGLint w, h, dummy, format; EGLint numConfigs; EGLConfig config; EGLSurface surface; EGLContext context; // 有効にするEGLパラメータ const EGLint attribs[] = { // サーフェイスのタイプを指定(ダブルバッファを利用するのでEGL_WINDOW_BIT) EGL_SURFACE_TYPE, EGL_WINDOW_BIT, // 青が利用する最小フレームサイズ(単位はbit) EGL_BLUE_SIZE, 8, // 緑が利用する最小フレームサイズ(単位はbit) EGL_GREEN_SIZE, 8, // 赤が利用する最小フレームサイズ(単位はbit) EGL_RED_SIZE, 8, // デプスバッファとして確保するサイズ(単位はbit) EGL_DEPTH_SIZE, 16, // 終端 EGL_NONE }; // EGLディスプレイコネクションを取得 EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); // EGLディスプレイコネクション初期化 eglInitialize(display, 0, 0); // 条件に合ったEGLフレームバッファ設定のリストを返す eglChooseConfig(display, attribs, &config, 1, &numConfigs); // EGLフレームバッファ設定の情報を取得 eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); // NativeActivityへバッファを設定 ANativeWindow_setBuffersGeometry(engine->app->window, 0, 0, format); // EGLウィンドウサーフェイスの取得 surface = eglCreateWindowSurface(display, config, engine->app->window, NULL); // EGLレンダリングコンテキストの取得 context = eglCreateContext(display, config, NULL, NULL); // EGLレンダリングコンテキストをEGLサーフェイスにアタッチする if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { LOGW("Unable to eglMakeCurrent"); return -1; } // 画面解像度取得 eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); // EGL関連データの保存 engine->display = display; engine->context = context; engine->surface = surface; // 画面解像度の保存 engine->width = w; engine->height = h; // 初期値設定 int j; for (j = 0; j < 3; j++){ engine->angle[j] = 0; } // 立方体表示の初期化 initCube(engine); return 0; }
bool EGLWindow::initializeGL(OSWindow *osWindow) { PFNEGLGETPLATFORMDISPLAYEXTPROC eglGetPlatformDisplayEXT = reinterpret_cast<PFNEGLGETPLATFORMDISPLAYEXTPROC>(eglGetProcAddress("eglGetPlatformDisplayEXT")); if (!eglGetPlatformDisplayEXT) { return false; } std::vector<EGLint> displayAttributes; displayAttributes.push_back(EGL_PLATFORM_ANGLE_TYPE_ANGLE); displayAttributes.push_back(mPlatform.renderer); displayAttributes.push_back(EGL_PLATFORM_ANGLE_MAX_VERSION_MAJOR_ANGLE); displayAttributes.push_back(mPlatform.majorVersion); displayAttributes.push_back(EGL_PLATFORM_ANGLE_MAX_VERSION_MINOR_ANGLE); displayAttributes.push_back(mPlatform.minorVersion); if (mPlatform.deviceType != EGL_DONT_CARE) { displayAttributes.push_back(EGL_PLATFORM_ANGLE_DEVICE_TYPE_ANGLE); displayAttributes.push_back(mPlatform.deviceType); } displayAttributes.push_back(EGL_NONE); mDisplay = eglGetPlatformDisplayEXT(EGL_PLATFORM_ANGLE_ANGLE, osWindow->getNativeDisplay(), &displayAttributes[0]); if (mDisplay == EGL_NO_DISPLAY) { destroyGL(); return false; } EGLint majorVersion, minorVersion; if (eglInitialize(mDisplay, &majorVersion, &minorVersion) == EGL_FALSE) { destroyGL(); return false; } eglBindAPI(EGL_OPENGL_ES_API); if (eglGetError() != EGL_SUCCESS) { destroyGL(); return false; } const EGLint configAttributes[] = { EGL_RED_SIZE, (mRedBits >= 0) ? mRedBits : EGL_DONT_CARE, EGL_GREEN_SIZE, (mGreenBits >= 0) ? mGreenBits : EGL_DONT_CARE, EGL_BLUE_SIZE, (mBlueBits >= 0) ? mBlueBits : EGL_DONT_CARE, EGL_ALPHA_SIZE, (mAlphaBits >= 0) ? mAlphaBits : EGL_DONT_CARE, EGL_DEPTH_SIZE, (mDepthBits >= 0) ? mDepthBits : EGL_DONT_CARE, EGL_STENCIL_SIZE, (mStencilBits >= 0) ? mStencilBits : EGL_DONT_CARE, EGL_SAMPLE_BUFFERS, mMultisample ? 1 : 0, EGL_NONE }; EGLint configCount; if (!eglChooseConfig(mDisplay, configAttributes, &mConfig, 1, &configCount) || (configCount != 1)) { destroyGL(); return false; } eglGetConfigAttrib(mDisplay, mConfig, EGL_RED_SIZE, &mRedBits); eglGetConfigAttrib(mDisplay, mConfig, EGL_GREEN_SIZE, &mGreenBits); eglGetConfigAttrib(mDisplay, mConfig, EGL_BLUE_SIZE, &mBlueBits); eglGetConfigAttrib(mDisplay, mConfig, EGL_ALPHA_SIZE, &mBlueBits); eglGetConfigAttrib(mDisplay, mConfig, EGL_DEPTH_SIZE, &mDepthBits); eglGetConfigAttrib(mDisplay, mConfig, EGL_STENCIL_SIZE, &mStencilBits); std::vector<EGLint> surfaceAttributes; if (strstr(eglQueryString(mDisplay, EGL_EXTENSIONS), "EGL_NV_post_sub_buffer") != nullptr) { surfaceAttributes.push_back(EGL_POST_SUB_BUFFER_SUPPORTED_NV); surfaceAttributes.push_back(EGL_TRUE); } surfaceAttributes.push_back(EGL_NONE); mSurface = eglCreateWindowSurface(mDisplay, mConfig, osWindow->getNativeWindow(), &surfaceAttributes[0]); if (eglGetError() != EGL_SUCCESS) { destroyGL(); return false; } ASSERT(mSurface != EGL_NO_SURFACE); EGLint contextAttibutes[] = { EGL_CONTEXT_CLIENT_VERSION, mClientVersion, EGL_NONE }; mContext = eglCreateContext(mDisplay, mConfig, NULL, contextAttibutes); if (eglGetError() != EGL_SUCCESS) { destroyGL(); return false; } eglMakeCurrent(mDisplay, mSurface, mSurface, mContext); if (eglGetError() != EGL_SUCCESS) { destroyGL(); return false; } if (mSwapInterval != -1) { eglSwapInterval(mDisplay, mSwapInterval); } return true; }
//============================================================================== void NativeWindowImpl::create(NativeWindowInitInfo& init) { Array<EGLint, 256> attribs; U attr = 0; EGLint configsCount; EGLint format; EGLConfig config; ANKI_LOGI("Creating native window"); ANKI_ASSERT(gAndroidApp); android_app& andApp = *gAndroidApp; loopUntilWindowIsReady(andApp); // EGL init // display = eglGetDisplay(EGL_DEFAULT_DISPLAY); if(display == EGL_NO_DISPLAY) { throw ANKI_EXCEPTION("Failed to create display"); } int major, minor; if(eglInitialize(display, &major, &minor) == EGL_FALSE) { throw ANKI_EXCEPTION("Failed to initialize EGL"); } // // EGL config // attribs[attr++] = EGL_SURFACE_TYPE; attribs[attr++] = EGL_WINDOW_BIT; attribs[attr++] = EGL_RENDERABLE_TYPE; attribs[attr++] = EGL_OPENGL_ES2_BIT; if(init.samplesCount > 1) { attribs[attr++] = EGL_SAMPLES; attribs[attr++] = init.samplesCount; } attribs[attr++] = EGL_RED_SIZE; attribs[attr++] = init.rgbaBits[0]; attribs[attr++] = EGL_GREEN_SIZE; attribs[attr++] = init.rgbaBits[1]; attribs[attr++] = EGL_BLUE_SIZE; attribs[attr++] = init.rgbaBits[2]; attribs[attr++] = EGL_ALPHA_SIZE; attribs[attr++] = init.rgbaBits[3]; attribs[attr++] = EGL_DEPTH_SIZE; attribs[attr++] = init.depthBits; attribs[attr++] = EGL_STENCIL_SIZE; attribs[attr++] = init.stencilBits; attribs[attr++] = EGL_NONE; if(eglChooseConfig(display, &attribs[0], &config, 1, &configsCount) == EGL_FALSE) { throw ANKI_EXCEPTION("Failed to query required EGL configs"); } if(configsCount == 0) { throw ANKI_EXCEPTION("No matching EGL configs found"); } eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); ANKI_ASSERT(andApp.window); ANativeWindow_setBuffersGeometry(andApp.window, 0, 0, format); // Surface // surface = eglCreateWindowSurface(display, config, andApp.window, NULL); if(surface == EGL_NO_SURFACE) { throw ANKI_EXCEPTION("Cannot create surface"); } // Context // EGLint ctxAttribs[] = {EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE}; context = eglCreateContext(display, config, EGL_NO_CONTEXT, ctxAttribs); if(context == EGL_NO_CONTEXT) { throw ANKI_EXCEPTION("Cannot create context"); } if(eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { throw ANKI_EXCEPTION("Cannot make the context current"); } // Query width and height // EGLint w, h; eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); init.width = w; init.height = h; }
bool CEGLWrapper::GetConfigAttrib(EGLDisplay display, EGLConfig config, EGLint attribute, EGLint *value) { if (display == EGL_NO_DISPLAY || !config || !attribute) return eglGetConfigAttrib(display, config, attribute, value); return false; }
QX11GLSharedContexts() : rgbContext(0) , argbContext(0) , sharedQGLContext(0) , sharePixmap(0) { EGLint rgbConfigId; EGLint argbConfigId; do { EGLConfig rgbConfig = QEgl::defaultConfig(QInternal::Pixmap, QEgl::OpenGL, QEgl::Renderable); EGLConfig argbConfig = QEgl::defaultConfig(QInternal::Pixmap, QEgl::OpenGL, QEgl::Renderable | QEgl::Translucent); eglGetConfigAttrib(QEgl::display(), rgbConfig, EGL_CONFIG_ID, &rgbConfigId); eglGetConfigAttrib(QEgl::display(), argbConfig, EGL_CONFIG_ID, &argbConfigId); rgbContext = new QEglContext; rgbContext->setConfig(rgbConfig); rgbContext->createContext(); if (!rgbContext->isValid()) break; // If the RGB & ARGB configs are the same, use the same egl context for both: if (rgbConfig == argbConfig) argbContext = rgbContext; // Otherwise, create a separate context to be used for ARGB pixmaps: if (!argbContext) { argbContext = new QEglContext; argbContext->setConfig(argbConfig); bool success = argbContext->createContext(rgbContext); if (!success) { qWarning("QX11GLPixmapData - RGB & ARGB contexts aren't shared"); success = argbContext->createContext(); if (!success) argbContext = rgbContext; // Might work, worth a shot at least. } } if (!argbContext->isValid()) break; // Create the pixmap which will be used to create the egl surface for the share QGLContext QX11PixmapData *rgbPixmapData = new QX11PixmapData(QPixmapData::PixmapType); rgbPixmapData->resize(8, 8); rgbPixmapData->fill(Qt::red); sharePixmap = new QPixmap(rgbPixmapData); EGLSurface sharePixmapSurface = QEgl::createSurface(sharePixmap, rgbConfig); rgbPixmapData->gl_surface = (void*)sharePixmapSurface; // Create the actual QGLContext which will be used for sharing sharedQGLContext = new QGLContext(QX11GLPixmapData::glFormat()); sharedQGLContext->d_func()->eglContext = rgbContext; sharedQGLContext->d_func()->eglSurface = sharePixmapSurface; sharedQGLContext->d_func()->valid = true; qt_glformat_from_eglconfig(sharedQGLContext->d_func()->glFormat, rgbConfig); valid = rgbContext->makeCurrent(sharePixmapSurface); // If the ARGB & RGB configs are different, check ARGB works too: if (argbConfig != rgbConfig) { QX11PixmapData *argbPixmapData = new QX11PixmapData(QPixmapData::PixmapType); argbPixmapData->resize(8, 8); argbPixmapData->fill(Qt::transparent); // Force ARGB QPixmap argbPixmap(argbPixmapData); // destroys pixmap data when goes out of scope EGLSurface argbPixmapSurface = QEgl::createSurface(&argbPixmap, argbConfig); valid = argbContext->makeCurrent(argbPixmapSurface); argbContext->doneCurrent(); eglDestroySurface(QEgl::display(), argbPixmapSurface); argbPixmapData->gl_surface = 0; } if (!valid) { qWarning() << "Unable to make pixmap surface current:" << QEgl::errorString(); break; } // The pixmap surface destruction hooks are installed by QGLTextureCache, so we // must make sure this is instanciated: QGLTextureCache::instance(); } while(0); if (!valid) cleanup(); else qDebug("Using QX11GLPixmapData with EGL config %d for ARGB and config %d for RGB", argbConfigId, rgbConfigId); }
/** * 初始化当前显示的 EGL 上下文。 */ static int engine_init_display(struct engine* engine) { //初始化 OpenGL ES 和 EGL /* * 此处指定了所需配置的属性。 *下面,我们选择与屏上窗口 * 兼容的至少每个颜色有 8 个位的 EGLConfig */ const EGLint attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_NONE }; const EGLint select_gles2[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; EGLint w, h, format; EGLint numConfigs; EGLConfig config; EGLSurface surface; EGLContext context; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); eglInitialize(display, 0, 0); /*此处,应用程序选择了所需的配置。 在本 *示例中,我们有非常简化的选择流程, *其中我们选取了与我们的标准匹配的第一个 EGLConfig */ eglChooseConfig(display, attribs, &config, 1, &numConfigs); /* EGL_NATIVE_VISUAL_ID 是 *保证会被 ANativeWindow_setBuffersGeometry() 接受的 EGLConfig 的属性。 * 只要我们选取 EGLConfig,就可使用 EGL_NATIVE_VISUAL_ID 安全地重新配置 * ANativeWindow 缓冲区以进行匹配。*/ eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry(engine->app->window, 0, 0, format); surface = eglCreateWindowSurface(display, config, engine->app->window, NULL); context = eglCreateContext(display, config, NULL, select_gles2); if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { LOGW("Unable to eglMakeCurrent"); return -1; } eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); engine->display = display; engine->context = context; engine->surface = surface; engine->width = w; engine->height = h; engine->state.angle = 0; // gl platform helper init gl_helper_init(); fs_assetmanager = engine->app->activity->assetManager; fs_set_write_path(engine->app->activity->externalDataPath); //初始化 GL 状态。 //glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST); //glEnable(GL_CULL_FACE); //glShadeModel(GL_SMOOTH); //glDisable(GL_DEPTH_TEST); struct game* game = seal_load_game_config(); int window_width = GAME->config.design_width; int window_height = GAME->config.design_height; game->config.scale_factor = w / window_width; game->config.fb_width = w; game->config.fb_height = h; seal_init_graphics(GAME->config.design_width, GAME->config.design_height); seal_start_game(); glViewport(0, 0, GAME->config.fb_width, GAME->config.fb_height); return 0; }
/** Creates the EGL context and window surface for the native window * using specified arguments. * @param raspitex_state A pointer to the GL preview state. This contains * the native_window pointer. * @param attribs The config attributes. * @param context_attribs The context attributes. * @return Zero if successful. */ static int raspitexutil_gl_common(RASPITEX_STATE *raspitex_state, const EGLint attribs[], const EGLint context_attribs[]) { EGLConfig config; EGLint num_configs; vcos_log_trace("%s", VCOS_FUNCTION); if (raspitex_state->native_window == NULL) { vcos_log_error("%s: No native window", VCOS_FUNCTION); goto error; } raspitex_state->display = eglGetDisplay(EGL_DEFAULT_DISPLAY); if (raspitex_state->display == EGL_NO_DISPLAY) { vcos_log_error("%s: Failed to get EGL display", VCOS_FUNCTION); goto error; } if (! eglInitialize(raspitex_state->display, 0, 0)) { vcos_log_error("%s: eglInitialize failed", VCOS_FUNCTION); goto error; } if (! eglChooseConfig(raspitex_state->display, attribs, &config, 1, &num_configs)) { vcos_log_error("%s: eglChooseConfig failed", VCOS_FUNCTION); goto error; } int value = -1; eglGetConfigAttrib(raspitex_state->display, config, EGL_MAX_PBUFFER_WIDTH, &value); fprintf(stderr, "max width %d\n", value); eglGetConfigAttrib(raspitex_state->display, config, EGL_MAX_PBUFFER_HEIGHT, &value); fprintf(stderr, "max height %d\n", value); raspitex_state->surface = eglCreateWindowSurface(raspitex_state->display, config, raspitex_state->native_window, NULL); if (raspitex_state->surface == EGL_NO_SURFACE) { vcos_log_error("%s: eglCreateWindowSurface failed", VCOS_FUNCTION); goto error; } raspitex_state->context = eglCreateContext(raspitex_state->display, config, EGL_NO_CONTEXT, context_attribs); if (raspitex_state->context == EGL_NO_CONTEXT) { vcos_log_error("%s: eglCreateContext failed", VCOS_FUNCTION); goto error; } if (!eglMakeCurrent(raspitex_state->display, raspitex_state->surface, raspitex_state->surface, raspitex_state->context)) { vcos_log_error("%s: Failed to activate EGL context", VCOS_FUNCTION); goto error; } return 0; error: vcos_log_error("%s: EGL error 0x%08x", VCOS_FUNCTION, eglGetError()); raspitex_state->ops.gl_term(raspitex_state); return -1; }
void cInterfaceEGL::DetectMode() { if (s_opengl_mode != MODE_DETECT) return; EGLint num_configs; EGLConfig *config = nullptr; bool supportsGL = false, supportsGLES2 = false, supportsGLES3 = false; std::array<int, 3> renderable_types = { EGL_OPENGL_BIT, (1 << 6), /* EGL_OPENGL_ES3_BIT_KHR */ EGL_OPENGL_ES2_BIT, }; for (auto renderable_type : renderable_types) { // attributes for a visual in RGBA format with at least // 8 bits per color int attribs[] = { EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_RENDERABLE_TYPE, renderable_type, EGL_NONE }; // Get how many configs there are if (!eglChooseConfig( egl_dpy, attribs, nullptr, 0, &num_configs)) { INFO_LOG(VIDEO, "Error: couldn't get an EGL visual config\n"); goto err_exit; } config = new EGLConfig[num_configs]; // Get all the configurations if (!eglChooseConfig(egl_dpy, attribs, config, num_configs, &num_configs)) { INFO_LOG(VIDEO, "Error: couldn't get an EGL visual config\n"); goto err_exit; } for (int i = 0; i < num_configs; ++i) { EGLint attribVal; bool ret; ret = eglGetConfigAttrib(egl_dpy, config[i], EGL_RENDERABLE_TYPE, &attribVal); if (ret) { if (attribVal & EGL_OPENGL_BIT) supportsGL = true; if (attribVal & (1 << 6)) /* EGL_OPENGL_ES3_BIT_KHR */ supportsGLES3 = true; if (attribVal & EGL_OPENGL_ES2_BIT) supportsGLES2 = true; } } } if (supportsGL) s_opengl_mode = GLInterfaceMode::MODE_OPENGL; else if (supportsGLES3) s_opengl_mode = GLInterfaceMode::MODE_OPENGLES3; else if (supportsGLES2) s_opengl_mode = GLInterfaceMode::MODE_OPENGLES2; err_exit: if (s_opengl_mode == GLInterfaceMode::MODE_DETECT) // Errored before we found a mode s_opengl_mode = GLInterfaceMode::MODE_OPENGL; // Fall back to OpenGL if (config) delete[] config; }
// Create the OpenGL or OpenGL ES context // int _glfwCreateContext(_GLFWwindow* window, const _GLFWctxconfig* ctxconfig, const _GLFWfbconfig* fbconfig) { int attribs[40]; EGLConfig config; EGLContext share = NULL; if (ctxconfig->share) share = ctxconfig->share->egl.context; if (!chooseFBConfigs(ctxconfig, fbconfig, &config)) { _glfwInputError(GLFW_PLATFORM_ERROR, "EGL: Failed to find a suitable EGLConfig"); return GL_FALSE; } #if defined(_GLFW_X11) // Retrieve the visual corresponding to the chosen EGL config { EGLint count = 0; int mask; EGLint redBits, greenBits, blueBits, alphaBits, visualID = 0; XVisualInfo info; eglGetConfigAttrib(_glfw.egl.display, config, EGL_NATIVE_VISUAL_ID, &visualID); info.screen = _glfw.x11.screen; mask = VisualScreenMask; if (visualID) { // The X window visual must match the EGL config info.visualid = visualID; mask |= VisualIDMask; } else { // some EGL drivers don't implement the EGL_NATIVE_VISUAL_ID // attribute, so attempt to find the closest match. eglGetConfigAttrib(_glfw.egl.display, config, EGL_RED_SIZE, &redBits); eglGetConfigAttrib(_glfw.egl.display, config, EGL_GREEN_SIZE, &greenBits); eglGetConfigAttrib(_glfw.egl.display, config, EGL_BLUE_SIZE, &blueBits); eglGetConfigAttrib(_glfw.egl.display, config, EGL_ALPHA_SIZE, &alphaBits); info.depth = redBits + greenBits + blueBits + alphaBits; mask |= VisualDepthMask; } window->egl.visual = XGetVisualInfo(_glfw.x11.display, mask, &info, &count); if (!window->egl.visual) { _glfwInputError(GLFW_PLATFORM_ERROR, "EGL: Failed to retrieve visual for EGLConfig"); return GL_FALSE; } } #endif // _GLFW_X11 if (ctxconfig->api == GLFW_OPENGL_ES_API) { if (!eglBindAPI(EGL_OPENGL_ES_API)) { _glfwInputError(GLFW_PLATFORM_ERROR, "EGL: Failed to bind OpenGL ES: %s", getErrorString(eglGetError())); return GL_FALSE; } } else { if (!eglBindAPI(EGL_OPENGL_API)) { _glfwInputError(GLFW_PLATFORM_ERROR, "EGL: Failed to bind OpenGL: %s", getErrorString(eglGetError())); return GL_FALSE; } } if (_glfw.egl.KHR_create_context) { int index = 0, mask = 0, flags = 0, strategy = 0; if (ctxconfig->api == GLFW_OPENGL_API) { if (ctxconfig->profile == GLFW_OPENGL_CORE_PROFILE) mask |= EGL_CONTEXT_OPENGL_CORE_PROFILE_BIT_KHR; else if (ctxconfig->profile == GLFW_OPENGL_COMPAT_PROFILE) mask |= EGL_CONTEXT_OPENGL_COMPATIBILITY_PROFILE_BIT_KHR; if (ctxconfig->forward) flags |= EGL_CONTEXT_OPENGL_FORWARD_COMPATIBLE_BIT_KHR; } if (ctxconfig->debug) flags |= EGL_CONTEXT_OPENGL_DEBUG_BIT_KHR; if (ctxconfig->robustness) { if (ctxconfig->robustness == GLFW_NO_RESET_NOTIFICATION) strategy = EGL_NO_RESET_NOTIFICATION_KHR; else if (ctxconfig->robustness == GLFW_LOSE_CONTEXT_ON_RESET) strategy = EGL_LOSE_CONTEXT_ON_RESET_KHR; flags |= EGL_CONTEXT_OPENGL_ROBUST_ACCESS_BIT_KHR; } if (ctxconfig->major != 1 || ctxconfig->minor != 0) { setEGLattrib(EGL_CONTEXT_MAJOR_VERSION_KHR, ctxconfig->major); setEGLattrib(EGL_CONTEXT_MINOR_VERSION_KHR, ctxconfig->minor); } if (mask) setEGLattrib(EGL_CONTEXT_OPENGL_PROFILE_MASK_KHR, mask); if (flags) setEGLattrib(EGL_CONTEXT_FLAGS_KHR, flags); if (strategy) setEGLattrib(EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY_KHR, strategy); setEGLattrib(EGL_NONE, EGL_NONE); } else { int index = 0; if (ctxconfig->api == GLFW_OPENGL_ES_API) setEGLattrib(EGL_CONTEXT_CLIENT_VERSION, ctxconfig->major); setEGLattrib(EGL_NONE, EGL_NONE); } // Context release behaviors (GL_KHR_context_flush_control) are not yet // supported on EGL but are not a hard constraint, so ignore and continue window->egl.context = eglCreateContext(_glfw.egl.display, config, share, attribs); if (window->egl.context == EGL_NO_CONTEXT) { _glfwInputError(GLFW_PLATFORM_ERROR, "EGL: Failed to create context: %s", getErrorString(eglGetError())); return GL_FALSE; } window->egl.config = config; return GL_TRUE; }
static bool gfx_ctx_init(void) { struct android_app *android_app = (struct android_app*)g_android; const EGLint attribs[] = { EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_ALPHA_SIZE, 8, EGL_NONE }; EGLint num_config; EGLint egl_version_major, egl_version_minor; EGLint format; EGLint context_attributes[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; RARCH_LOG("Initializing context\n"); if ((g_egl_dpy = eglGetDisplay(EGL_DEFAULT_DISPLAY)) == EGL_NO_DISPLAY) { RARCH_ERR("eglGetDisplay failed.\n"); goto error; } if (!eglInitialize(g_egl_dpy, &egl_version_major, &egl_version_minor)) { RARCH_ERR("eglInitialize failed.\n"); goto error; } RARCH_LOG("[ANDROID/EGL]: EGL version: %d.%d\n", egl_version_major, egl_version_minor); if (!eglChooseConfig(g_egl_dpy, attribs, &g_config, 1, &num_config)) { RARCH_ERR("eglChooseConfig failed.\n"); goto error; } int var = eglGetConfigAttrib(g_egl_dpy, g_config, EGL_NATIVE_VISUAL_ID, &format); if (!var) { RARCH_ERR("eglGetConfigAttrib failed: %d.\n", var); goto error; } ANativeWindow_setBuffersGeometry(android_app->window, 0, 0, format); if (!(g_egl_surf = eglCreateWindowSurface(g_egl_dpy, g_config, android_app->window, 0))) { RARCH_ERR("eglCreateWindowSurface failed.\n"); goto error; } if (!(g_egl_ctx = eglCreateContext(g_egl_dpy, g_config, 0, context_attributes))) { RARCH_ERR("eglCreateContext failed.\n"); goto error; } if (!eglMakeCurrent(g_egl_dpy, g_egl_surf, g_egl_surf, g_egl_ctx)) { RARCH_ERR("eglMakeCurrent failed.\n"); goto error; } return true; error: RARCH_ERR("EGL error: %d.\n", eglGetError()); gfx_ctx_destroy(); return false; }
EGLConfig choose_config(EGLDisplay eglDisplay, const char* str) { EGLConfig egl_conf = (EGLConfig)0; EGLConfig *egl_configs; EGLint egl_num_configs; EGLint val; EGLBoolean rc; const char *tok; EGLint i; if (str != NULL) { tok = str; while (*tok == ' ' || *tok == ',') { tok++; } while (*tok != '\0') { if (strncmp(tok, "rgba8888", strlen("rgba8888")) == 0) { egl_conf_attr.red_size = 8; egl_conf_attr.green_size = 8; egl_conf_attr.blue_size = 8; egl_conf_attr.alpha_size = 8; tok += strlen("rgba8888"); } else if (strncmp(tok, "rgba5551", strlen("rgba5551")) == 0) { egl_conf_attr.red_size = 5; egl_conf_attr.green_size = 5; egl_conf_attr.blue_size = 5; egl_conf_attr.alpha_size = 1; tok += strlen("rgba5551"); } else if (strncmp(tok, "rgba4444", strlen("rgba4444")) == 0) { egl_conf_attr.red_size = 4; egl_conf_attr.green_size = 4; egl_conf_attr.blue_size = 4; egl_conf_attr.alpha_size = 4; tok += strlen("rgba4444"); } else if (strncmp(tok, "rgb565", strlen("rgb565")) == 0) { egl_conf_attr.red_size = 5; egl_conf_attr.green_size = 6; egl_conf_attr.blue_size = 5; egl_conf_attr.alpha_size = 0; tok += strlen("rgb565"); } else if (isdigit(*tok)) { val = atoi(tok); while (isdigit(*(++tok))); if (*tok == 'x') { egl_conf_attr.samples = val; tok++; } else { egl_conf_attr.config_id = val; } } else { fprintf(stderr, "invalid configuration specifier: "); while (*tok != ' ' && *tok != ',' && *tok != '\0') { fputc(*tok++, stderr); } fputc('\n', stderr); } while (*tok == ' ' || *tok == ',') { tok++; } } } rc = eglGetConfigs(eglDisplay, NULL, 0, &egl_num_configs); if (rc != EGL_TRUE) { Com_Printf("eglGetConfigs"); return egl_conf; } if (egl_num_configs == 0) { Com_Printf("eglGetConfigs: could not find a configuration\n"); return egl_conf; } egl_configs = malloc(egl_num_configs * sizeof(*egl_configs)); if (egl_configs == NULL) { Com_Printf("could not allocate memory for %d EGL configs\n", egl_num_configs); return egl_conf; } rc = eglGetConfigs(eglDisplay, egl_configs, egl_num_configs, &egl_num_configs); if (rc != EGL_TRUE) { Com_Printf("eglGetConfigs"); free(egl_configs); return egl_conf; } for (i = 0; i < egl_num_configs; i++) { if (egl_conf_attr.config_id != EGL_DONT_CARE) { eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_CONFIG_ID, &val); if (val == egl_conf_attr.config_id) { egl_conf = egl_configs[i]; break; } else { continue; } } eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_SURFACE_TYPE, &val); if ((val & egl_conf_attr.surface_type) != egl_conf_attr.surface_type) { continue; } eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_RENDERABLE_TYPE, &val); if (!(val & EGL_OPENGL_ES_BIT)) { continue; } eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_DEPTH_SIZE, &val); if (val == 0) { continue; } if (egl_conf_attr.red_size != EGL_DONT_CARE) { eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_RED_SIZE, &val); if (val != egl_conf_attr.red_size) { continue; } } if (egl_conf_attr.green_size != EGL_DONT_CARE) { eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_GREEN_SIZE, &val); if (val != egl_conf_attr.green_size) { continue; } } if (egl_conf_attr.blue_size != EGL_DONT_CARE) { eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_BLUE_SIZE, &val); if (val != egl_conf_attr.blue_size) { continue; } } if (egl_conf_attr.alpha_size != EGL_DONT_CARE) { eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_ALPHA_SIZE, &val); if (val != egl_conf_attr.alpha_size) { continue; } } if (egl_conf_attr.samples != EGL_DONT_CARE) { eglGetConfigAttrib(eglDisplay, egl_configs[i], EGL_SAMPLES, &val); if (val != egl_conf_attr.samples) { continue; } } egl_conf = egl_configs[i]; break; } free(egl_configs); if (egl_conf == (EGLConfig)0) { Com_Printf("eglChooseConfig: could not find a matching configuration\n"); } return egl_conf; }
/** * Initialize an EGL context for the current display. */ static int engine_init_display(struct engine* engine) { // initialize OpenGL ES and EGL /* * Here specify the attributes of the desired configuration. * Below, we select an EGLConfig with at least 8 bits per color * component compatible with on-screen windows */ const EGLint attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_DEPTH_SIZE, 8, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_NONE }; const EGLint context_attribs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; EGLint w, h, dummy, format; EGLint numConfigs; EGLConfig config; EGLSurface surface; EGLContext context; EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY); eglInitialize(display, 0, 0); /* Here, the application chooses the configuration it desires. In this * sample, we have a very simplified selection process, where we pick * the first EGLConfig that matches our criteria */ eglChooseConfig(display, attribs, &config, 1, &numConfigs); /* EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is * guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). * As soon as we picked a EGLConfig, we can safely reconfigure the * ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. */ eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry(engine->app->window, 0, 0, format); surface = eglCreateWindowSurface(display, config, engine->app->window, NULL); context = eglCreateContext(display, config, NULL, context_attribs); if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { LOGW("Unable to eglMakeCurrent"); return -1; } eglQuerySurface(display, surface, EGL_WIDTH, &w); eglQuerySurface(display, surface, EGL_HEIGHT, &h); engine->display = display; engine->context = context; engine->surface = surface; engine->width = w; engine->height = h; engine->state.angle = 0; engine->state.x0 = 0; engine->state.y0 = 0; engine->state.x1 = 0; engine->state.y1 = 0; engine->state.isTwoTouches = false; vesKiwiPointCloudApp::Ptr kiwiApp = vesKiwiPointCloudApp::Ptr(new vesKiwiPointCloudApp); kiwiApp->initGL(); engine->kiwiApp = kiwiApp; kiwiApp->resizeView(w, h); storageDir = "/mnt/sdcard"; assetManager = engine->app->activity->assetManager; // initialize shaders AAsset* vertex_asset = AAssetManager_open(assetManager, "vesShader_vert.glsl", AASSET_MODE_UNKNOWN); AAsset* fragment_asset = AAssetManager_open(assetManager, "vesShader_frag.glsl", AASSET_MODE_UNKNOWN); std::string vertex_source = std::string(static_cast<const char*>(AAsset_getBuffer(vertex_asset)), AAsset_getLength(vertex_asset)); std::string fragment_source = std::string(static_cast<const char*>(AAsset_getBuffer(fragment_asset)), AAsset_getLength(fragment_asset)); AAsset_close(vertex_asset); AAsset_close(fragment_asset); LOGI("vertex_source: %s\n", vertex_source.c_str()); LOGI("fragment_source: %s\n", fragment_source.c_str()); kiwiApp->initShader(vertex_source, fragment_source); std::string filename = "cturtle.vtp"; filename = copyAssetToExternalStorage(filename); kiwiApp->loadData(filename); kiwiApp->resetView(false); return 0; }
static void init_egl(struct display *display, struct window *window) { static const EGLint context_attribs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; const char *extensions; EGLint config_attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_RED_SIZE, 1, EGL_GREEN_SIZE, 1, EGL_BLUE_SIZE, 1, EGL_ALPHA_SIZE, 1, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_NONE }; EGLint major, minor, n, count, i, size; EGLConfig *configs; EGLBoolean ret; if (window->opaque || window->buffer_size == 16) config_attribs[9] = 0; display->egl.dpy = weston_platform_get_egl_display(EGL_PLATFORM_WAYLAND_KHR, display->display, NULL); assert(display->egl.dpy); ret = eglInitialize(display->egl.dpy, &major, &minor); assert(ret == EGL_TRUE); ret = eglBindAPI(EGL_OPENGL_ES_API); assert(ret == EGL_TRUE); if (!eglGetConfigs(display->egl.dpy, NULL, 0, &count) || count < 1) assert(0); configs = calloc(count, sizeof *configs); assert(configs); ret = eglChooseConfig(display->egl.dpy, config_attribs, configs, count, &n); assert(ret && n >= 1); for (i = 0; i < n; i++) { eglGetConfigAttrib(display->egl.dpy, configs[i], EGL_BUFFER_SIZE, &size); if (window->buffer_size == size) { display->egl.conf = configs[i]; break; } } free(configs); if (display->egl.conf == NULL) { fprintf(stderr, "did not find config with buffer size %d\n", window->buffer_size); exit(EXIT_FAILURE); } display->egl.ctx = eglCreateContext(display->egl.dpy, display->egl.conf, EGL_NO_CONTEXT, context_attribs); assert(display->egl.ctx); display->swap_buffers_with_damage = NULL; extensions = eglQueryString(display->egl.dpy, EGL_EXTENSIONS); if (extensions && strstr(extensions, "EGL_EXT_swap_buffers_with_damage") && strstr(extensions, "EGL_EXT_buffer_age")) display->swap_buffers_with_damage = (PFNEGLSWAPBUFFERSWITHDAMAGEEXTPROC) eglGetProcAddress("eglSwapBuffersWithDamageEXT"); if (display->swap_buffers_with_damage) printf("has EGL_EXT_buffer_age and EGL_EXT_swap_buffers_with_damage\n"); }
bool GlDisplayService::TryBindDisplay(ANativeWindow& window) { EGLint w, h, dummy, format; EGLConfig config; EGLSurface surface; if (!DefaultEGLChooser(m_display, EGL_WINDOW_BIT, config)) { Eegeo_ERROR("unable to find a good display type"); return false; } eglGetConfigAttrib(m_display, config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry(&window, 0, 0, format); static const EGLint contextAttribs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; surface = eglCreateWindowSurface(m_display, config, &window, NULL); if(m_context == EGL_NO_CONTEXT) { m_context = eglCreateContext(m_display, config, NULL, contextAttribs); } if (eglMakeCurrent(m_display, surface, surface, m_context) == EGL_FALSE) { Eegeo_ERROR("Unable to eglMakeCurrent"); return false; } //Eegeo_TTY("printing extensions\n"); //char * extensionsString = (char *) glGetString(GL_EXTENSIONS); //Eegeo_TTY("%s\n",extensionsString); Eegeo_GL(eglQuerySurface(m_display, surface, EGL_WIDTH, &w)); Eegeo_GL(eglQuerySurface(m_display, surface, EGL_HEIGHT, &h)); m_surface = surface; #ifdef EEGEO_DROID_EMULATOR m_sharedSurface = EGL_NO_SURFACE; m_resourceBuildSharedContext = EGL_NO_CONTEXT; #else if(m_resourceBuildSharedContext == EGL_NO_CONTEXT) { m_resourceBuildSharedContext = eglCreateContext(m_display, config, m_context, contextAttribs); } EGLint pBufferAttribs[] = { EGL_WIDTH, 1, EGL_HEIGHT, 1, EGL_TEXTURE_TARGET, EGL_NO_TEXTURE, EGL_TEXTURE_FORMAT, EGL_NO_TEXTURE, EGL_NONE }; EGLConfig sharedSurfaceConfig; if (!DefaultEGLChooser(m_display, EGL_PBUFFER_BIT, sharedSurfaceConfig)) { Eegeo_ERROR("unabled to find a good pbuffer surface type"); } m_sharedSurface = eglCreatePbufferSurface(m_display, sharedSurfaceConfig, pBufferAttribs); #endif w = w/2.0f; m_displayWidth = w; m_displayHeight = h; glViewport(0, 0, m_displayWidth, m_displayHeight); // Initialize GL state. Eegeo_GL(glClearDepthf(1.0f)); Eegeo_GL(glClearColor(0.0f, 0.0f, 0.0f, 1.0f)); // Set up default Depth test. Eegeo_GL(glEnable(GL_DEPTH_TEST)); Eegeo_GL(glDepthMask(GL_TRUE)); Eegeo_GL(glDepthFunc(GL_LEQUAL)); // Set up default culling. Eegeo_GL(glEnable(GL_CULL_FACE)); Eegeo_GL(glFrontFace(GL_CW)); Eegeo_GL(glCullFace(GL_BACK)); // Turn off the stencil test. Eegeo_GL(glDisable(GL_STENCIL_TEST)); Eegeo_GL(glStencilFunc(GL_NEVER, 0, 0xFFFFFFFF)); Eegeo_GL(glStencilOp(GL_KEEP, GL_KEEP, GL_KEEP)); // Set the default blend mode and colour mask. Eegeo_GL(glDisable(GL_BLEND)); Eegeo_GL(glColorMask(true, true, true, true)); Eegeo_GL(glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT)); eglSwapInterval(m_display, 1); m_displayBound = true; return m_displayBound; }
static QEglContext *createContext(QPaintDevice *device) { QEglContext *context; // Create the context object and open the display. context = new QEglContext(); context->setApi(QEgl::OpenVG); // Set the swap interval for the display. QByteArray interval = qgetenv("QT_VG_SWAP_INTERVAL"); if (!interval.isEmpty()) eglSwapInterval(QEgl::display(), interval.toInt()); else eglSwapInterval(QEgl::display(), 1); #ifdef EGL_RENDERABLE_TYPE // Has the user specified an explicit EGL configuration to use? QByteArray configId = qgetenv("QT_VG_EGL_CONFIG"); if (!configId.isEmpty()) { EGLint cfgId = configId.toInt(); EGLint properties[] = { EGL_CONFIG_ID, cfgId, EGL_NONE }; EGLint matching = 0; EGLConfig cfg; if (eglChooseConfig (QEgl::display(), properties, &cfg, 1, &matching) && matching > 0) { // Check that the selected configuration actually supports OpenVG // and then create the context with it. EGLint id = 0; EGLint type = 0; eglGetConfigAttrib (QEgl::display(), cfg, EGL_CONFIG_ID, &id); eglGetConfigAttrib (QEgl::display(), cfg, EGL_RENDERABLE_TYPE, &type); if (cfgId == id && (type & EGL_OPENVG_BIT) != 0) { context->setConfig(cfg); if (!context->createContext()) { delete context; return 0; } return context; } else { qWarning("QT_VG_EGL_CONFIG: %d is not a valid OpenVG configuration", int(cfgId)); } } } #endif // Choose an appropriate configuration for rendering into the device. QEglProperties configProps; configProps.setPaintDeviceFormat(device); int redSize = configProps.value(EGL_RED_SIZE); if (redSize == EGL_DONT_CARE || redSize == 0) configProps.setPixelFormat(QImage::Format_ARGB32); // XXX configProps.setValue(EGL_ALPHA_MASK_SIZE, 1); #ifdef EGL_VG_ALPHA_FORMAT_PRE_BIT configProps.setValue(EGL_SURFACE_TYPE, EGL_WINDOW_BIT | EGL_VG_ALPHA_FORMAT_PRE_BIT); configProps.setRenderableType(QEgl::OpenVG); if (!context->chooseConfig(configProps)) { // Try again without the "pre" bit. configProps.setValue(EGL_SURFACE_TYPE, EGL_WINDOW_BIT); if (!context->chooseConfig(configProps)) { delete context; return 0; } } #else configProps.setValue(EGL_SURFACE_TYPE, EGL_WINDOW_BIT); configProps.setRenderableType(QEgl::OpenVG); if (!context->chooseConfig(configProps)) { delete context; return 0; } #endif // Construct a new EGL context for the selected configuration. if (!context->createContext()) { delete context; return 0; } return context; }
void OpenGLWindowProvider::create(DisplayWindowSite *new_site, const DisplayWindowDescription &desc) { window_handle = desc.get_handle(); if (window_handle.window == nullptr) throw Exception("Window handle must exist in the display description"); ANativeWindow *window = window_handle.window; const EGLint attribs[] = { EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_NONE }; EGLint format; EGLint numConfigs; EGLConfig config; display = eglGetDisplay(EGL_DEFAULT_DISPLAY); eglInitialize(display, 0, 0); /* Here, the application chooses the configuration it desires. In this * sample, we have a very simplified selection process, where we pick * the first EGLConfig that matches our criteria */ if (!eglChooseConfig(display, attribs, &config, 1, &numConfigs)) throw Exception("eglChooseConfig failed"); if (numConfigs < 1) throw Exception("Found configs failed"); /* EGL_NATIVE_VISUAL_ID is an attribute of the EGLConfig that is * guaranteed to be accepted by ANativeWindow_setBuffersGeometry(). * As soon as we picked a EGLConfig, we can safely reconfigure the * ANativeWindow buffers to match, using EGL_NATIVE_VISUAL_ID. */ eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format); ANativeWindow_setBuffersGeometry(window, 0, 0, format); surface = eglCreateWindowSurface(display, config, window, NULL); if (surface == EGL_NO_SURFACE) throw Exception("eglCreateWindowSurface failed"); context = eglCreateContext(display, config, NULL, NULL); if (context == EGL_NO_CONTEXT) throw Exception("eglCreateWindowSurface failed"); if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE) { throw Exception("Unable to eglMakeCurrent"); } bool use_gl3; int desc_version_major = opengl_desc.get_version_major(); int desc_version_minor = opengl_desc.get_version_minor(); // Do not attempt GL3, if not requested that version if (desc_version_major < 3) { use_gl3 = false; } else if (!opengl_desc.get_allow_lower_versions()) // Else, if we do not allow lower versions, only attempt GL3 { use_gl3 = true; } else { // Choose the target depending on the current opengl version int gl_version_major; int gl_version_minor; get_opengl_version(gl_version_major, gl_version_minor); if (gl_version_major < 3) { use_gl3 = false; } else { use_gl3 = true; } } if (use_gl3) { using_gl3 = true; gc = GraphicContext(new GL3GraphicContextProvider(this)); } else { using_gl3 = false; gc = GraphicContext(new GL1GraphicContextProvider(this)); } swap_interval = desc.get_swap_interval(); if (swap_interval != -1) eglSwapInterval(display, swap_interval); }
static gboolean _cogl_winsys_onscreen_init (CoglOnscreen *onscreen, GError **error) { CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen); CoglContext *context = framebuffer->context; CoglDisplay *display = context->display; CoglDisplayEGL *egl_display = display->winsys; CoglRenderer *renderer = display->renderer; CoglRendererEGL *egl_renderer = renderer->winsys; EGLint attributes[MAX_EGL_CONFIG_ATTRIBS]; EGLConfig egl_config; EGLint config_count = 0; EGLBoolean status; gboolean need_stencil = egl_display->stencil_disabled ? FALSE : framebuffer->config.need_stencil; _COGL_RETURN_VAL_IF_FAIL (egl_display->egl_context, FALSE); egl_attributes_from_framebuffer_config (display, &framebuffer->config, need_stencil, attributes); status = eglChooseConfig (egl_renderer->edpy, attributes, &egl_config, 1, &config_count); if (status != EGL_TRUE || config_count == 0) { g_set_error (error, COGL_WINSYS_ERROR, COGL_WINSYS_ERROR_CREATE_ONSCREEN, "Failed to find a suitable EGL configuration"); return FALSE; } /* Update the real number of samples_per_pixel now that we have * found an egl_config... */ if (framebuffer->config.samples_per_pixel) { EGLint samples; status = eglGetConfigAttrib (egl_renderer->edpy, egl_config, EGL_SAMPLES, &samples); g_return_val_if_fail (status == EGL_TRUE, TRUE); framebuffer->samples_per_pixel = samples; } onscreen->winsys = g_slice_new0 (CoglOnscreenEGL); if (egl_renderer->platform_vtable->onscreen_init && !egl_renderer->platform_vtable->onscreen_init (onscreen, egl_config, error)) { g_slice_free (CoglOnscreenEGL, onscreen->winsys); return FALSE; } return TRUE; }
static struct window *window_create(struct display *display, const char *name, unsigned int x, unsigned int y, unsigned int width, unsigned int height) { static const EGLint attribs[] = { EGL_RED_SIZE, 1, EGL_GREEN_SIZE, 1, EGL_BLUE_SIZE, 1, EGL_DEPTH_SIZE, 1, EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_NONE }; static const EGLint attrs[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE }; XSetWindowAttributes attr; struct window *window; unsigned long mask; XVisualInfo visual; EGLint num_configs; XVisualInfo *info; XSizeHints hints; EGLConfig config; int num_visuals; EGLint version; Window root; int screen; EGLint vid; window = calloc(1, sizeof(*window)); if (!window) return NULL; window->display = display; screen = DefaultScreen(display->x11); root = RootWindow(display->x11, screen); if (!eglChooseConfig(display->egl, attribs, &config, 1, &num_configs)) { free(window); return NULL; } if (!eglGetConfigAttrib(display->egl, config, EGL_NATIVE_VISUAL_ID, &vid)) { free(window); return NULL; } visual.visualid = vid; info = XGetVisualInfo(display->x11, VisualIDMask, &visual, &num_visuals); if (!info) { free(window); return NULL; } memset(&attr, 0, sizeof(attr)); attr.background_pixel = 0; attr.border_pixel = 0; attr.colormap = XCreateColormap(display->x11, root, info->visual, AllocNone); attr.event_mask = StructureNotifyMask | ExposureMask | KeyPressMask; mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask; window->x11 = XCreateWindow(display->x11, root, 0, 0, width, height, 0, info->depth, InputOutput, info->visual, mask, &attr); if (!window->x11) { free(window); return NULL; } memset(&hints, 0, sizeof(hints)); hints.x = x; hints.y = y; hints.width = width; hints.height = height; hints.flags = USSize | USPosition; XSetNormalHints(display->x11, window->x11, &hints); XSetStandardProperties(display->x11, window->x11, name, name, None, NULL, 0, &hints); eglBindAPI(EGL_OPENGL_ES_API); window->context = eglCreateContext(display->egl, config, EGL_NO_CONTEXT, attrs); if (window->context == EGL_NO_CONTEXT) { free(window); return NULL; } eglQueryContext(display->egl, window->context, EGL_CONTEXT_CLIENT_VERSION, &version); printf("OpenGL ES: %d\n", version); window->surface = eglCreateWindowSurface(display->egl, config, window->x11, NULL); if (window->surface == EGL_NO_SURFACE) { free(window); return NULL; } XFree(info); window->width = width; window->height = height; return window; }