Move EGL fields to a separate structure for reusability (e.g. upcoming Mesa X11 EGL support)

git-svn-id: https://svn.code.sf.net/p/freeglut/code/trunk@1161 7f0cb862-5218-0410-a997-914c9d46530a
This commit is contained in:
beuc 2012-03-16 23:23:19 +00:00
parent cb3dea2183
commit 31e0027e09
11 changed files with 106 additions and 54 deletions

1
.gitattributes vendored
View File

@ -70,6 +70,7 @@ freeglut/freeglut/src/egl/fg_init_egl.c -text
freeglut/freeglut/src/egl/fg_internal_egl.h -text
freeglut/freeglut/src/egl/fg_structure_egl.c -text
freeglut/freeglut/src/egl/fg_window_egl.c -text
freeglut/freeglut/src/egl/fg_window_egl.h -text
freeglut/freeglut/src/fg_callbacks.c svn_keywords=Author+Date+Id+Revision
freeglut/freeglut/src/fg_cursor.c svn_keywords=Author+Date+Id+Revision
freeglut/freeglut/src/fg_display.c svn_keywords=Author+Date+Id+Revision

View File

@ -100,6 +100,7 @@ ELSEIF(ANDROID)
src/egl/fg_init_egl.c
src/egl/fg_structure_egl.c
src/egl/fg_window_egl.c
src/egl/fg_window_egl.h
src/android/native_app_glue/android_native_app_glue.c
src/android/native_app_glue/android_native_app_glue.h
src/android/fg_runtime_android.c

View File

@ -31,6 +31,23 @@
/* Android OpenGL ES is accessed through EGL */
#include "egl/fg_internal_egl.h"
/* -- GLOBAL TYPE DEFINITIONS ---------------------------------------------- */
/* The structure used by display initialization in freeglut_init.c */
typedef struct tagSFG_PlatformDisplay SFG_PlatformDisplay;
struct tagSFG_PlatformDisplay
{
struct tagSFG_PlatformDisplayEGL egl;
struct tagSFG_Window* single_window;
};
typedef struct tagSFG_PlatformContext SFG_PlatformContext;
/* SFG_PlatformContext is used for SFG_Window.Window */
struct tagSFG_PlatformContext
{
struct tagSFG_PlatformContextEGL egl;
};
/**
* Virtual PAD (spots on touchscreen that simulate keys)
*/

View File

@ -329,7 +329,7 @@ void handle_cmd(struct android_app* app, int32_t cmd) {
break;
case APP_CMD_WINDOW_RESIZED:
LOGI("handle_cmd: APP_CMD_WINDOW_RESIZED");
if (fgDisplay.pDisplay.single_window->Window.pContext.eglSurface != EGL_NO_SURFACE)
if (fgDisplay.pDisplay.single_window->Window.pContext.egl.Surface != EGL_NO_SURFACE)
/* Make ProcessSingleEvent detect the new size, only available
after the next SwapBuffer */
glutPostRedisplay();

View File

@ -29,7 +29,7 @@
#define FREEGLUT_BUILDING_LIB
#include <GL/freeglut.h>
#include "fg_internal.h"
extern EGLSurface fghEGLPlatformOpenWindow( EGLNativeWindowType handle );
#include "egl/fg_window_egl.h"
/*
* Opens a window. Requires a SFG_Window object created and attached
@ -52,6 +52,8 @@ void fgPlatformOpenWindow( SFG_Window* window, const char* title,
return;
}
fghCreateNewContextEGL(window);
/* Wait until window is available and OpenGL context is created */
/* Normally events are processed through glutMainLoop(), but the
user didn't call it yet, and the Android may not have initialized
@ -64,14 +66,23 @@ void fgPlatformOpenWindow( SFG_Window* window, const char* title,
fgPlatformProcessSingleEvent();
}
EGLDisplay display = fgDisplay.pDisplay.eglDisplay;
EGLint format = fgDisplay.pDisplay.eglContextFormat;
EGLDisplay display = fgDisplay.pDisplay.egl.Display;
EGLint format = fgDisplay.pDisplay.single_window->Window.pContext.egl.ContextFormat;
ANativeWindow_setBuffersGeometry(window->Window.Handle, 0, 0, format);
window->Window.pContext.eglSurface = fghEGLPlatformOpenWindow(window->Window.Handle);
fghPlatformOpenWindowEGL(window);
window->State.Visible = GL_TRUE;
}
/*
* Closes a window, destroying the frame and OpenGL context
*/
void fgPlatformCloseWindow( SFG_Window* window )
{
fghPlatformCloseWindowEGL(window);
/* Window pre-created by Android, no way to delete it */
}
void fgPlatformSetWindow ( SFG_Window *window )
{
/* TODO: only a single window possible? */

View File

@ -32,6 +32,6 @@
void fgPlatformGlutSwapBuffers( SFG_PlatformDisplay *pDisplayPtr, SFG_Window* CurrentWindow )
{
/* LOGI("Swap!"); */
if (!eglSwapBuffers(pDisplayPtr->eglDisplay, CurrentWindow->Window.pContext.eglSurface))
if (!eglSwapBuffers(pDisplayPtr->egl.Display, CurrentWindow->Window.pContext.egl.Surface))
fgError("eglSwapBuffers: error %x\n", eglGetError());
}

View File

@ -40,16 +40,13 @@ void fgPlatformInitialize( const char* displayName )
/* CreateDisplay */
/* Using EGL_DEFAULT_DISPLAY, or a specific native display */
EGLNativeDisplayType nativeDisplay = EGL_DEFAULT_DISPLAY;
fgDisplay.pDisplay.eglDisplay = eglGetDisplay(nativeDisplay);
fgDisplay.pDisplay.egl.Display = eglGetDisplay(nativeDisplay);
FREEGLUT_INTERNAL_ERROR_EXIT(fgDisplay.pDisplay.eglDisplay != EGL_NO_DISPLAY,
FREEGLUT_INTERNAL_ERROR_EXIT(fgDisplay.pDisplay.egl.Display != EGL_NO_DISPLAY,
"No display available", "fgPlatformInitialize");
if (!eglInitialize(fgDisplay.pDisplay.eglDisplay, NULL, NULL))
if (!eglInitialize(fgDisplay.pDisplay.egl.Display, NULL, NULL))
fgError("eglInitialize: error %x\n", eglGetError());
/* CreateContext */
fghCreateContext();
// fgDisplay.ScreenWidth = ...;
// fgDisplay.ScreenHeight = ...;
// fgDisplay.ScreenWidthMM = ...;
@ -58,15 +55,9 @@ void fgPlatformInitialize( const char* displayName )
void fgPlatformCloseDisplay ( void )
{
eglMakeCurrent(fgDisplay.pDisplay.eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
if (fgDisplay.pDisplay.eglContext != EGL_NO_CONTEXT) {
eglDestroyContext(fgDisplay.pDisplay.eglDisplay, fgDisplay.pDisplay.eglContext);
fgDisplay.pDisplay.eglContext = EGL_NO_CONTEXT;
}
if (fgDisplay.pDisplay.eglDisplay != EGL_NO_DISPLAY) {
eglTerminate(fgDisplay.pDisplay.eglDisplay);
fgDisplay.pDisplay.eglDisplay = EGL_NO_DISPLAY;
if (fgDisplay.pDisplay.egl.Display != EGL_NO_DISPLAY) {
eglTerminate(fgDisplay.pDisplay.egl.Display);
fgDisplay.pDisplay.egl.Display = EGL_NO_DISPLAY;
}
}
@ -76,5 +67,5 @@ void fgPlatformCloseDisplay ( void )
void fgPlatformDestroyContext ( SFG_PlatformDisplay pDisplay, SFG_WindowContextType MContext )
{
if (MContext != EGL_NO_CONTEXT)
eglDestroyContext(pDisplay.eglDisplay, MContext);
eglDestroyContext(pDisplay.egl.Display, MContext);
}

View File

@ -30,16 +30,11 @@
/* -- GLOBAL TYPE DEFINITIONS ---------------------------------------------- */
/* The structure used by display initialization in freeglut_init.c */
typedef struct tagSFG_PlatformDisplay SFG_PlatformDisplay;
struct tagSFG_Window;
struct tagSFG_PlatformDisplay
struct tagSFG_PlatformDisplayEGL
{
/* Used to initialize and deinitialize EGL */
EGLDisplay eglDisplay;
EGLContext eglContext;
EGLConfig eglContextConfig;
EGLint eglContextFormat;
struct tagSFG_Window* single_window;
EGLDisplay Display;
};
@ -49,11 +44,11 @@ struct tagSFG_PlatformDisplay
*/
typedef EGLNativeWindowType SFG_WindowHandleType ;
typedef EGLContext SFG_WindowContextType ;
typedef struct tagSFG_PlatformContext SFG_PlatformContext;
/* SFG_PlatformContext is used for SFG_Window.Window */
struct tagSFG_PlatformContext
struct tagSFG_PlatformContextEGL
{
EGLSurface eglSurface;
EGLSurface Surface;
EGLConfig ContextConfig;
EGLint ContextFormat;
};

View File

@ -30,5 +30,6 @@ extern SFG_Structure fgStructure;
void fgPlatformCreateWindow ( SFG_Window *window )
{
window->Window.pContext.eglSurface = EGL_NO_SURFACE;
window->Window.pContext.egl.Surface = EGL_NO_SURFACE;
window->Window.pContext.egl.ContextConfig = NULL;
}

View File

@ -29,7 +29,7 @@
/**
* Initialize an EGL context for the current display.
*/
void fghCreateContext( ) {
void fghCreateNewContextEGL( SFG_Window* window ) {
/*
* Here specify the attributes of the desired configuration.
* Below, we select an EGLConfig with at least 8 bits per color
@ -56,10 +56,7 @@ void fghCreateContext( ) {
EGLConfig config;
EGLContext context;
EGLDisplay eglDisplay = fgDisplay.pDisplay.eglDisplay;
/* TODO : apply DisplayMode */
/* (GLUT_DEPTH already applied in attribs[] above) */
EGLDisplay eglDisplay = fgDisplay.pDisplay.egl.Display;
/* Here, the application chooses the configuration it desires. In this
* sample, we have a very simplified selection process, where we pick
@ -86,44 +83,49 @@ void fghCreateContext( ) {
fghContextCreationError();
}
EGLint ver = -1;
eglQueryContext(fgDisplay.pDisplay.eglDisplay, context, EGL_CONTEXT_CLIENT_VERSION, &ver);
eglQueryContext(fgDisplay.pDisplay.egl.Display, context, EGL_CONTEXT_CLIENT_VERSION, &ver);
if (ver != 2)
fgError("Wrong GLES major version: %d\n", ver);
fgDisplay.pDisplay.eglContext = context;
fgDisplay.pDisplay.eglContextConfig = config;
fgDisplay.pDisplay.eglContextFormat = format;
window->Window.Context = context;
window->Window.pContext.egl.ContextConfig = config;
window->Window.pContext.egl.ContextFormat = format;
}
/*
* Really opens a window when handle is available
*/
EGLSurface fghEGLPlatformOpenWindow( EGLNativeWindowType handle )
void fghPlatformOpenWindowEGL( SFG_Window* window )
{
EGLDisplay display = fgDisplay.pDisplay.eglDisplay;
EGLContext context = fgDisplay.pDisplay.eglContext;
EGLConfig config = fgDisplay.pDisplay.eglContextConfig;
EGLDisplay display = fgDisplay.pDisplay.egl.Display;
EGLConfig config = window->Window.pContext.egl.ContextConfig;
EGLSurface surface = eglCreateWindowSurface(display, config, handle, NULL);
EGLSurface surface = eglCreateWindowSurface(display, config, window->Window.Handle, NULL);
if (surface == EGL_NO_SURFACE)
fgError("Cannot create EGL window surface, err=%x\n", eglGetError());
if (eglMakeCurrent(display, surface, surface, context) == EGL_FALSE)
if (eglMakeCurrent(display, surface, surface, window->Window.Context) == EGL_FALSE)
fgError("eglMakeCurrent: err=%x\n", eglGetError());
//EGLint w, h;
//eglQuerySurface(display, surface, EGL_WIDTH, &w);
//eglQuerySurface(display, surface, EGL_HEIGHT, &h);
return surface;
window->Window.pContext.egl.Surface = surface;
}
/*
* Closes a window, destroying the frame and OpenGL context
*/
void fgPlatformCloseWindow( SFG_Window* window )
void fghPlatformCloseWindowEGL( SFG_Window* window )
{
if (window->Window.pContext.eglSurface != EGL_NO_SURFACE) {
eglDestroySurface(fgDisplay.pDisplay.eglDisplay, window->Window.pContext.eglSurface);
window->Window.pContext.eglSurface = EGL_NO_SURFACE;
eglMakeCurrent(fgDisplay.pDisplay.egl.Display, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
if (window->Window.Context != EGL_NO_CONTEXT) {
eglDestroyContext(fgDisplay.pDisplay.egl.Display, window->Window.Context);
window->Window.Context = EGL_NO_CONTEXT;
}
if (window->Window.pContext.egl.Surface != EGL_NO_SURFACE) {
eglDestroySurface(fgDisplay.pDisplay.egl.Display, window->Window.pContext.egl.Surface);
window->Window.pContext.egl.Surface = EGL_NO_SURFACE;
}
}

View File

@ -0,0 +1,33 @@
/*
* freeglut_display_android.c
*
* Window management methods for EGL
*
* Copyright (C) 2012 Sylvain Beucler
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included
* in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* PAWEL W. OLSZTA BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
* IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#ifndef __FG_WINDOW_EGL_H__
#define __FG_WINDOW_EGL_H__
extern void fghPlatformOpenWindowEGL( SFG_Window* window );
extern void fghCreateNewContextEGL( SFG_Window* window );
extern void fghPlatformCloseWindowEGL( SFG_Window* window );
#endif