“只要确保在主线程中只使用OpenGL.”很重要.您不能在游戏引擎(可能在另一个线程中)调用与gl线程不同步的纹理加载功能.设置一个标志来表示您的gl线程加载新的纹理(例如,您可以在OnDrawFrame(GL gl)中放置一个函数,该函数检查是否必须加载新的纹理.
我将修改我的代码,使纹理从GL线程加载.我只是不明白为什么会这样?为什么OpenGL功能不能从另一个线程工作?
我知道如何创建线程,但我不知道什么同步意味着.上面的提取提到,“你不能在你的游戏引擎(可能在另一个线程)中调用一个纹理加载函数,它与gl线程不同步.所以我猜我的游戏线程可能不会与GL线程同步.是否可以创建与GL Thread同步的另一个线程,以便可以从中调用GL函数?要了解这些概念,我应该学习什么?
解决方法
glVertexPointer(... supply vertex positions ...) glTexCoordPointer(... provide texture positions ...) /* and supply a few other pointers,maybe bind a texture */ glDrawArrays(... draw some geometry ...)
所以最后的调用仅在前面的调用的上下文中提供可预测的结果.如果您允许该位代码暂停,例如glVertexPointer,则另一个线程跳入并执行大致相同的序列来绘制其几何,然后该代码继续进行,它将绘制相当错误的几何,甚至可能导致如果某些替换的数组小于原始数据,则会限制存储器访问.
Android提供了EGL,它支持OpenGL共享组的通用概念(虽然隐含地提供了一个现有上下文,您希望新的上下文通过第七个参数到eglCreateContext
).如果两个上下文在共享组中,那么它们中的每一个都具有独立状态,并且可以安全地仅从一个线程调用,但命名的对象(例如纹理或顶点缓冲对象)可用于每个线程.所以使用共享组可以同时在多个线程上执行OpenGL操作,以便能够将结果组合在一个线程上.
因此,将上下文绑定到单个线程不是一个问题.规划OpenGL本身的问题也将是一个非启动因素,因为OpenGL上下文的一个原因是以特定于操作系统的方式创建,管理和处理,因为某些操作系统需要以完全不同的方式处理这些内容给其他人或者通过暴露自己独特的解决方案能够提供更好的解决方案.