关于如何从头开始创建环境,可以参考大神的博文OpenGL ES 3.0 数据可视化 0:Hello world,本文只是补充一些我在实践中的一些思考。

CAEAGLLayer

If you plan to use OpenGL for your rendering, use this class as the backing layer for your views by returning it from your view’s layerClass class method. The returned CAEAGLLayer object is a wrapper for a Core Animation surface that is fully compatible with OpenGL ES function calls.

CAEAGLLayer

根据官方文档的说明,这个layer用于OpenGL与Core Animation库之间的联系。这个layer的内容来自于一个 renderbuffer,而他自己所做的主要工作就是为renderbuffer分配内存,在用户绘制完成后讲renderbuffer送给Core Animation.使用的方法大家都知道,就是override view的layerClass静态方法,返回这个东西。

创建Framebuffer和Renderbuffer

创建这俩buffer相对容易理解,这里没有GLKViewController来替我们创建所需的OpenGL环境所以我们需要自己创建用与绘制的buffer,没有这俩buffer,相当于没有画板。我们用OpenGL做Render to texture这样的事情的时候也需要自己创建framebuffer object,但是那时候往往不用renderbuffer,而使用texture。这两者的区别是这样的,在过去那些美好时光里纹理是framebuffer附件的唯一可用的类型,后来引进的renderbuffer object,那么相比较texture,Renderbuffer的优点是,以OpenGL原生渲染格式储存它的数据,因此在离屏渲染的时候,这些数据就相当于被优化过的了。

渲染缓冲对象将所有渲染数据直接储存到它们的缓冲里,而不会进行针对特定纹理格式的任何转换,这样它们就成了一种快速可写的存储介质了。然而,渲染缓冲对象通常是只写的,不能修改它们(就像获取纹理,不能写入纹理一样)。可以用glReadPixels函数去读取,函数返回一个当前绑定的帧缓冲的特定像素区域,而不是直接返回附件本身。

因为它们的数据已经是原生格式了,在写入或把它们的数据简单地到其他缓冲的时候非常快。当使用渲染缓冲对象时,像切换缓冲这种操作变得异常高速。我们在每个渲染迭代末尾使用的那个glfwSwapBuffers函数,同样以渲染缓冲对象实现:我们简单地写入到一个渲染缓冲图像,最后交换到另一个里。渲染缓冲对象对于这种操作来说很完美。

Renderbuffer

有些离题,回到iOS这边,示例代码如下

GLuint colorRenderbuffer;
glGenRenderbuffers(1, &colorRenderbuffer);
glBindRenderbuffer(GL_RENDERBUFFER, colorRenderbuffer);
[myContext renderbufferStorage:GL_RENDERBUFFER fromDrawable:myEAGLLayer];
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorRenderbuffer);

该说明的地方大神的博文已经说明此处不再赘述,但是需要留心的事情是,因为renderbuffer的尺寸是从EAGLLayer中得到,如果EGLLayer的尺寸不正确,会导致最终的图像大小不如预期。在apple的 Supporting High-Resolution Screens In Views 这篇文章提到,在高分辨率的设备上渲染OpenGL ES, 如果不做设置,那么出现的图像会变得blockly,应该是说是块状的,就是不太清晰,其建议就是使用较大的scale值。可以这样设置:

eaglLayer.contentsScale = [UIScreen mainScreen].scale;

记住,如果将eagl layer 的scale值设置变大了,那么在glviewport() 的时候要使用相应的成倍数的尺寸。

我自己实践了一下,iPhone7 Plus 上,[UIScreen mainScreen].bounds 得到的尺寸为414x736,设置glviewport为这个尺寸,出来的图像正常。然后如下修改:

eaglLayer.contentsScale = [UIScreen mainScreen].scale;

glViewport(0, 0, (GLsizei) (size.width * scale),
(GLsizei) (size.height * scale));

即同时修改layer和viewport,得到的结果粗看起来和原来的差别不大,但是仔细查看细节边缘,前者的锯齿会更明显,后者分辨率更好。所以总的思路就是layer的scale和viewport要保持同步,两个都不改也可,两个都改也可。如果只修改了viewport的值,将其增大了,那就相当于视口变大了,底下的renderbuffer还是那么小,renderbuffer只能留下窗口的一个角落的图像。看起来就是,图像放的很大,然后只能看见角落里面的部分,一看就知道有问题。我们可以用下面的方法来确认renderbuffer的大小对不对。

// Get the renderbuffer size.
GLint width;
GLint height;
glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_WIDTH_OES, &width);
glGetRenderbufferParameterivOES(GL_RENDERBUFFER_OES, GL_RENDERBUFFER_HEIGHT_OES, &height);

好了,就说这么多吧。再见!

iOS 创建OpenGL 环境的思考的更多相关文章

  1. IOS 中openGL使用教程1(openGL ES 入门篇 | 搭建openGL环境)

    OpenGL版本 iOS系统默认支持OpenGl ES1.0.ES2.0以及ES3.0 3个版本,三者之间并不是简单的版本升级,设计理念甚至完全不同,在开发OpenGL项目前,需要根据业务需求选择合适 ...

  2. iOS-----openGL--openGL ES iOS 入门篇--->搭建openGL环境

    OpenGL版本 iOS系统默认支持OpenGl ES1.0.ES2.0以及ES3.0 3个版本,三者之间并不是简单的版本升级,设计理念甚至完全不同,在开发OpenGL项目前,需要根据业务需求选择合适 ...

  3. IOS 中openGL使用教程2(openGL ES 入门篇 | 绘制一个多边形)

    在上一篇我们学习了如何搭建IOS下openGL的开发环境,接下来我们来学习如何绘制一个多边形. 在2.0之前,es的渲染采用的是固定管线,何为固定管线,就是一套固定的模板流程,局部坐标变换 -> ...

  4. 使用VSTS/TFS搭建iOS持续集成环境

    TFS 自2015版开始支持跨平台的持续集成环境,通过提供开源的build agent为 Windows / linux / macOS 提供了统一的持续集成环境管理能力.这篇文章给大家介绍一下如何使 ...

  5. [转]phonegap 2.9 IOS Xcode 搭建环境

    phonegap 2.9 IOS Xcode 搭建环境   一:下载phoneGap2.9和安装Xcode5(目前最新版) 选择2.9是因为3.0以上坑爹版本编译神马的要在有网络情况. 二: 下载ph ...

  6. OpenGL环境搭建Windows+Mac+Linux

    OpenGL环境搭建Windows+Mac+Linux Mac平台下 下载列表:GLFWcmake 下载的GLFW解压缩 然后安装cmake, 安装好cmake之后打开 1.browse source ...

  7. ios搭建开发环境

    ios搭建开发环境 好久就想试水IOS开发了,由于开发环境限制,一直局限于理论和虚拟机,近来入手了MacBook Pro,也来尝尝鲜,笔者也是现学现总结,如果有不足,请指正. IOS开发必备MAC O ...

  8. IOS开发基础环境搭建

    一.目的 本文的目的是windows下IOS开发基础环境搭建做了对应的介绍,大家可根据文档步骤进行mac环境部署: 二.安装虚拟机 下载虚拟机安装文件绿色版,点击如下文件安装 获取安装包:       ...

  9. 创建OpenGL Context(WGL)

    创建OpenGL Context(WGL) 创建OpenGL Context是初始化OpenGL的一部分.只有在此之后才能使用OpenGL. 关于platform的注意事项 创建OpenGL cont ...

随机推荐

  1. jquery 改变变量出现值不同步

    出现问题的代码 var unc = 0; $.get( 'index.php', 'data=1', function(res) { unc=1; } ); alert(nuc); 这样的话,不管aj ...

  2. 友坚恒天.开发板(Cotex-A9 Exynos4412 开发板)

    友坚恒天.开发板 Cotex-A9 Exynos4412 开发板

  3. Android NDK开发及调用标准linux动态库.so文件

    源:Android NDK开发及调用标准linux动态库.so文件 预备知识及环境搭建 1.NDK(native development Kit)原生开发工具包,用来快速开发C.C++动态库,并能自动 ...

  4. 苹果App Store开发者帐户从申请,验证,到发布应用(1)

    app store为开发者提供四种类型的申请: 个人ios开发者计划$99/年 公司ios开发者计划$99/年 企业ios开发者计划$299/年 高校ios开发者计划免费 在这里主要介绍一下公司ios ...

  5. C++中string类的使用方法

    如果所比较的两个string 相等,则返回0: 操作string 大于参数string,返回 正数:操作string 小于参数string,返回负数. (1) 比较操作string 与 _Str 或C ...

  6. bzoj1070 修车&& bzoj2879美食节 【费用流】

    bzoj1070: 把每个工人拆成汽车那么多个点,假如说 工人(i, j) 和 汽车k 连边,那就代表第i个工人倒数第j个修汽车k,那么这条边对以后的贡献就是k*time[i修k]. #include ...

  7. JQueryUI确认框 confirm

    $(function(){ $('#AlertMsg').dialog({ autoOpen: false, width: 300, modal: true, position: 'center', ...

  8. IOS开发-UI学习-UIImageView控件

    在页面上展现本地图片: // 使用本地图片 // 先初始化UIImageView myImageV = [[UIImageView alloc]initWithFrame:CGRectMake(, , ...

  9. Samba匿名用戶仅仅唯读访问

      NAS(Network Attached Storage),网络附加存储需要支持NFS(Network File System)和CIFS(Common Internet File Sysem)一 ...

  10. 10种处理PHP字符串的措施

    PHP有一个海量字符串操作库,提供了大约100个分割.连接.解析和搜索文本的功能.在这一点上,PHP的性能是如此地强大以至于在处理字符串相关问题时,判断哪一个是最好的方法会比较困难.本文中我讲了10个 ...