iOS 创建OpenGL 环境的思考
关于如何从头开始创建环境,可以参考大神的博文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.
根据官方文档的说明,这个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 环境的思考的更多相关文章
- IOS 中openGL使用教程1(openGL ES 入门篇 | 搭建openGL环境)
OpenGL版本 iOS系统默认支持OpenGl ES1.0.ES2.0以及ES3.0 3个版本,三者之间并不是简单的版本升级,设计理念甚至完全不同,在开发OpenGL项目前,需要根据业务需求选择合适 ...
- iOS-----openGL--openGL ES iOS 入门篇--->搭建openGL环境
OpenGL版本 iOS系统默认支持OpenGl ES1.0.ES2.0以及ES3.0 3个版本,三者之间并不是简单的版本升级,设计理念甚至完全不同,在开发OpenGL项目前,需要根据业务需求选择合适 ...
- IOS 中openGL使用教程2(openGL ES 入门篇 | 绘制一个多边形)
在上一篇我们学习了如何搭建IOS下openGL的开发环境,接下来我们来学习如何绘制一个多边形. 在2.0之前,es的渲染采用的是固定管线,何为固定管线,就是一套固定的模板流程,局部坐标变换 -> ...
- 使用VSTS/TFS搭建iOS持续集成环境
TFS 自2015版开始支持跨平台的持续集成环境,通过提供开源的build agent为 Windows / linux / macOS 提供了统一的持续集成环境管理能力.这篇文章给大家介绍一下如何使 ...
- [转]phonegap 2.9 IOS Xcode 搭建环境
phonegap 2.9 IOS Xcode 搭建环境 一:下载phoneGap2.9和安装Xcode5(目前最新版) 选择2.9是因为3.0以上坑爹版本编译神马的要在有网络情况. 二: 下载ph ...
- OpenGL环境搭建Windows+Mac+Linux
OpenGL环境搭建Windows+Mac+Linux Mac平台下 下载列表:GLFWcmake 下载的GLFW解压缩 然后安装cmake, 安装好cmake之后打开 1.browse source ...
- ios搭建开发环境
ios搭建开发环境 好久就想试水IOS开发了,由于开发环境限制,一直局限于理论和虚拟机,近来入手了MacBook Pro,也来尝尝鲜,笔者也是现学现总结,如果有不足,请指正. IOS开发必备MAC O ...
- IOS开发基础环境搭建
一.目的 本文的目的是windows下IOS开发基础环境搭建做了对应的介绍,大家可根据文档步骤进行mac环境部署: 二.安装虚拟机 下载虚拟机安装文件绿色版,点击如下文件安装 获取安装包: ...
- 创建OpenGL Context(WGL)
创建OpenGL Context(WGL) 创建OpenGL Context是初始化OpenGL的一部分.只有在此之后才能使用OpenGL. 关于platform的注意事项 创建OpenGL cont ...
随机推荐
- iOS校验身份证是否合法
//身份证号验证 1900+/2000+的年份日期的正则表达式经过修改,目前貌似是对的,如果哪位朋友发现错误希望能够给与提示 //返回yes位表示格式正确,否则为错误 -(BOOL)IDCardAut ...
- 关于cin的用法一些小结
在写二叉树的时候遇到if(!cin)那几个标志位弄得并不清楚,还遇到了诸如cin.clear()等函数,感觉C++又白学了,于是打算去网上搜了几篇靠谱的文章,有时候看来,一些事件处理类的工程代码,在A ...
- Laravel邮件发送问题小解
在Laravel中已经有内置了发送邮件的功能,通过 Mail::send 可发送邮件,但要使用这个函数必须先进行相关配置. 在 /app/config/mail.php 中设置你的邮件参数,如下: 1 ...
- IIS Default Web Site : The service did not response to the start or control request in a timely fashion
IIS Default Web Site无法启动,提示错误:The service did not response to the start or control request in a time ...
- Nodejs之使用session
nodejs中使用session的说明. session介绍 为什么使用session: session运行在服务器端,当客户端第一次访问服务器时,可以将客户的登陆信息保存. 当客户访问其他界面时,可 ...
- 普通项目如何转换成Maven项目 --转载自百度知道
右键普通Java项目,在弹出的菜单中选择[Configure]-[Convert to Maven Project]: 2 在弹出的对话框中输入项目的groupId, artifactId和versi ...
- 【转】安卓Fragment不完全介绍
转两篇博客: 1.http://blog.csdn.net/lmj623565791/article/details/37970961 2.http://blog.csdn.net/lmj623565 ...
- BZOJ2318: Spoj4060 game with probability Problem
#include<iostream> #include<algorithm> #include<cstring> #include<cstdio> #i ...
- Java Spring MVC项目搭建(一)——Spring MVC框架集成
1.Java JDK及Tomcat安装 我这里安装的是JDK 1.8 及 Tomcat 8,安装步骤详见:http://www.cnblogs.com/eczhou/p/6285248.html 2. ...
- Mybatis学习(8)逆向工程
什么是逆向工程: mybaits需要程序员自己编写sql语句,mybatis官方提供逆向工程 可以针对单表自动生成mybatis执行所需要的代码(mapper.java,mapper.xml.po.. ...