我基本是看https://learnopengl-cn.github.io/这个教程,
和落影loyinglin的博客https://www.jianshu.com/nb/2135411来学习的
首先要知道OpenGL是什么,以及对iOS开发而言,它可以做点什么?
一般它被认为是一个API(Application Programming Interface, 应用程序编程接口),包含了一系列可以操作图形、图像的函数。然而,OpenGL本身并不是一个API,它仅仅是一个由Khronos组织制定并维护的规范(Specification)。
简单来说,对我们最上层的开发者而言,OpenGL就是一套供我们调用的操作图形、图像的函数。而OpenGL ES是其移动版,在手机端开发中用到的基本就是OpenGL ES。
而关于OpenGL可以做什么,可以从另外的角度解释一下:
GPUImage就是对OpenGL ES 图像处理方面功能的封装;也就是说,GPUImage实现的功能,都可以用OpenGL实现。
而现在市面上绝大部分的直播,相机类的APP,都是基于GPUImage来实现的。
具体的功能来说,实时的滤镜,贴图,水印等都可以用OpenGL实现。
涉及的知识
在iOS上使用OpenGL,基本上会涉及到 OpenGL ES,GPUImage, GLKit 这三块的知识,其中:
OpenGL ES是最基础最底层的;
GPUImage将OpenGL ES封装成完全的Objective-C方法,如果不自己写滤镜或者做什么极其个性化的需求,基本不用写OpenGL的代码;
GLKit是封装了OpenGL的部分内容,使用GLKit的话还要写不少OpenGL的代码。
如果想要弄明白GPUImage的工作原理,或者用GPUImage实现一些个性化的需求,那学习并理解一些OpenGL的知识就是必不可少的,所以要从最基本的OpenGL概念开始学起。
OpenGL自身是一个巨大的状态机(State Machine):一系列的变量描述OpenGL此刻应当如何运行。OpenGL的状态通常被称为OpenGL上下文(Context)。我们通常使用如下途径去更改OpenGL状态:设置选项,操作缓冲。最后,我们使用当前OpenGL上下文来渲染。
OpenGL的工作流程
需要重点理解的就是 OpenGL的工作流程,这一部分https://learnopengl-cn.github.io/01%20Getting%20started/04%20Hello%20Triangle/ 里面解释的很清楚,虽然它写的是PC环境下的,但原理跟移动端是一模一样的。
在OpenGL中,任何事物都存在于3D空间中,而屏幕确是2D的,所以OpenGL的大部分工作都是关于把3D坐标转换为适应屏幕的2D像素。这个过程是由OpenGL的 图形渲染管线(Graphics Pipeline)管理的,可以分为两个主要部分:一是将3D坐标转换为2D坐标,二是将2D坐标转变为实际的有颜色的像素。
这个过程又可以分为好几个阶段,每个阶段把前一个阶段的输出作为输入,所以是一个链式的操作。而且每个阶段都是高度定制化的,可以并行的执行在GPU上,每个阶段的操作都有一小段程序,称之为 着色器(Shader)!有些着色器允许开发者自己写,所以开发者可以更细致的控制这个阶段的操作应该怎样执行。OpenGL的Shader是用 OPenGL着色器语言(OpenGL Shading language, GLSL)写的,这是一门类似C语言的编程语言,很好入门。
重点就是这张图:
上图即是 图形渲染管线 的主要几个阶段。这里直接摘抄教程里面的解释:
1, 图形渲染管线的第一个部分是顶点着色器(Vertex Shader),它把一个单独的顶点作为输入。顶点着色器主要的目的是把3D坐标转为另一种3D坐标(后面会解释),同时顶点着色器允许我们对顶点属性进行一些基本处理。
2, 图元装配(Primitive Assembly)阶段将顶点着色器输出的所有顶点作为输入(如果是GL_POINTS,那么就是一个顶点),并所有的点装配成指定图元的形状;本节例子中是一个三角形。
3, 图元装配阶段的输出会传递给几何着色器(Geometry Shader)。几何着色器把图元形式的一系列顶点的集合作为输入,它可以通过产生新顶点构造出新的(或是其它的)图元来生成其他形状。例子中,它生成了另一个三角形。
4, 几何着色器的输出会被传入光栅化阶段(Rasterization Stage),这里它会把图元映射为最终屏幕上相应的像素,生成供片段着色器(Fragment Shader)使用的片段(Fragment)。在片段着色器运行之前会执行裁切(Clipping)。裁切会丢弃超出你的视图以外的所有像素,用来提升执行效率。
5, 片段着色器的主要目的是计算一个像素的最终颜色,这也是所有OpenGL高级效果产生的地方。通常,片段着色器包含3D场景的数据(比如光照、阴影、光的颜色等等),这些数据可以被用来计算最终像素的颜色。
6, 在所有对应颜色值确定以后,最终的对象将会被传到最后一个阶段,我们叫做Alpha测试和混合(Blending)阶段。这个阶段检测片段的对应的深度(和模板(Stencil))值(后面会讲),用它们来判断这个像素是其它物体的前面还是后面,决定是否应该丢弃。这个阶段也会检查alpha值(alpha值定义了一个物体的透明度)并对物体进行混合(Blend)。所以,即使在片段着色器中计算出来了一个像素输出的颜色,在渲染多个三角形的时候最后的像素颜色也可能完全不同。
可以看到,图形渲染管线非常复杂,它包含很多可配置的部分。然而,对于大多数场合,我们只需要配置顶点和片段着色器就行了。几何着色器是可选的,通常使用它默认的着色器就行了。
在现代OpenGL中,我们必须定义至少一个顶点着色器和一个片段着色器(因为GPU中没有默认的顶点/片段着色器)。
小结
以上是OpenGL的一些基本概念,弄清楚这些非常有助于理解其工作原理,也很有助于理解之后demo里的代码。