如“OpenGLES preloading textures in other thread”中所述,有两个单独的步骤:位图创建和位图上传。在大多数情况下,您只需在辅助线程上创建位图就可以了——这相当容易。
如果您在上传纹理时遇到丢帧现象,请从后台线程调用texImage2D。为此,您需要创建一个新的 OpenGL 上下文,该上下文与您的渲染线程共享它的纹理,因为每个线程都需要它自己的 OpenGL 上下文。
EGLContext textureContext = egl.eglCreateContext(display, eglConfig, renderContext, null);
获取eglCreateContext 的参数有点棘手。您需要在您的 SurfaceView 上使用 setEGLContextFactory 来挂钩 EGLContext 创建:
@Override
public EGLContext createContext(final EGL10 egl, final EGLDisplay display, final EGLConfig eglConfig) {
EGLContext renderContext = egl.eglCreateContext(display, eglConfig, EGL10.EGL_NO_CONTEXT, null);
// create your texture context here
return renderContext;
}
然后你就可以开始一个纹理加载线程了:
public void run() {
int pbufferAttribs[] = { EGL10.EGL_WIDTH, 1, EGL10.EGL_HEIGHT, 1, EGL14.EGL_TEXTURE_TARGET,
EGL14.EGL_NO_TEXTURE, EGL14.EGL_TEXTURE_FORMAT, EGL14.EGL_NO_TEXTURE,
EGL10.EGL_NONE };
EGLSurface localSurface = egl.eglCreatePbufferSurface(display, eglConfig, pbufferAttribs);
egl.eglMakeCurrent(display, localSurface, localSurface, textureContext);
int textureId = loadTexture(R.drawable.waterfalls);
// here you can pass the textureId to your
// render thread to be used with glBindTexture
}
我在https://github.com/perpetual-mobile/SharedGLContextsTest 创建了上述代码sn-ps 的工作演示。
此解决方案基于互联网上的许多来源。这三个影响最大的: