之前学习OpenGL的时候,基本上都是使用GLSurfaceView来初始化,然后调用OpenGL的API来进行绘制。然而找OpenGL的教程时,发现基本上的教程都是C,这就很尴尬了呀,Android平台虽然也封装了名字类似的Java 的API,但是总感觉怪怪的。大概看了一下GLSurfaceView的源码,其实就是继承SurfaceView,然后开启一个线程来初始化EGL环境,接着也是使用OpenGL的API来绘制。那么EGL是什么呢?
EGL™在Khronos 的图形渲染API比如 OpenGL ES or Open VG与本地系统底层窗口之间的接口。它处理图形上下文管理,表面/缓冲区绑定和渲染同步,并使用其他Khronos API实现高性能,加速,混合模式2D和3D渲染。
下面我们通过分析EglHelper来查看native代码的初始化流程。
EglHelper类中,初始化主要调用了两个方法。
/**
* Initialize EGL for a given configuration spec.
* @param configSpec
*/
public void start() {
if (LOG_EGL) {
Log.w("EglHelper", "start() tid=" + Thread.currentThread().getId());
}
/*
* Get an EGL instance
*/
mEgl = (EGL10) EGLContext.getEGL();
/*
* Get to the default display.
*/
mEglDisplay = mEgl.eglGetDisplay(EGL10.EGL_DEFAULT_DISPLAY);
if (mEglDisplay == EGL10.EGL_NO_DISPLAY) {
throw new RuntimeException("eglGetDisplay failed");
}
/*
* We can now initialize EGL for that display
*/
int[] version = new int[2];
if(!mEgl.eglInitialize(mEglDisplay, version)) {
throw new RuntimeException("eglInitialize failed");
}
GLSurfaceView view = mGLSurfaceViewWeakRef.get();
if (view == null) {
mEglConfig = null;
mEglContext = null;
} else {
mEglConfig = view.mEGLConfigChooser.chooseConfig(mEgl, mEglDisplay);
/*
* Create an EGL context. We want to do this as rarely as we can, because an
* EGL context is a somewhat heavy object.
*/
mEglContext = view.mEGLContextFactory.createContext(mEgl, mEglDisplay, mEglConfig);
}
if (mEglContext == null || mEglContext == EGL10.EGL_NO_CONTEXT) {
mEglContext = null;
throwEglException("createContext");
}
if (LOG_EGL) {
Log.w("EglHelper", "createContext " + mEglContext + " tid=" + Thread.currentThread().getId());
}
mEglSurface = null;
}
/**
* Create an egl surface for the current SurfaceHolder surface. If a surface
* already exists, destroy it before creating the new surface.
*
* @return true if the surface was created successfully.
*/
public boolean createSurface() {
if (LOG_EGL) {
Log.w("EglHelper", "createSurface() tid=" + Thread.currentThread().getId());
}
/*
* Check preconditions.
*/
if (mEgl ==