初识 OpenGL ES

  • OpenGL ES是OpenGL的子集
  • OpenGL ES 是针对嵌入式设备及移动终端设备的高级3D图形应用程序,例如iOS、Android、Windows等
  • OpenGL ES 是跨平台的,不会提供窗口相关方法,需要系统各自提供载体

OpenGL ES渲染流程

图片来自于 OpenGL ES as a Client-Server Architecture

OpenGL ES的渲染主要分为两部分:CPU和GPU

  • CPU部分

    app代码通过OpenGL ES API,会调度OpenGL ES Framework

    通过OpenGL ES client 调度 OpenGL ES server,将顶点数据等传递到GPU

  • GPU部分

    做一些图形硬件的处理,例如光栅化、显示等

OpenGL ES 图形管道

OpenGL ES 图形管道有以下两种图示,其中原理都是一致的,只是描述方式不同:

图一

  • API获得顶点数据,将顶点数据从内存中拷贝至顶点缓冲区(显存)
  • 拿到数据之后,通过attribute通道传递至顶点着色器,同时,纹理坐标通过Texture通道传递到顶点着色器和片元着色器
  • 然后,图元装配,即图元的连接方式,一共有9种,常用的有6种,此步骤将顶点变换为图形
  • 光栅化:确定图形与屏幕对应的位置
  • 片元/片段/像素着色器:处理对应像素点的颜色值
  • 在将处理好的每个像素点的颜色值存储到帧缓存区,然后在显示器中显示
  • API:可以通过API操作顶点缓冲区、顶点着色器、纹理坐标、片段着色器

Apple官方图示

图片来自于 OpenGL ES as a Client-Server Architecture

  • App:提供图元装配顶点信息,图片信息
  • Vertex(顶点着色器):处理顶点 -- 图形变换(旋转、缩放、平移)
  • Geometry(图元装配):图元装配 + 裁剪(超出屏幕部分被裁剪)
  • Fragment(片元着色器):纹理处理 + 雾化处理
  • Framebuffer Operation(帧缓冲区):透明度混合、模板、深度测试;最后在混合,这些操作都是在即将显示时,在帧缓冲区中完成的动作

顶点着色器

顶点着色器处理顶点的着色器程序,顶点着色器的输入输出如下图所示

  • 输入,有3种方式

    1.通过attribute通道输入顶点数据,提供每个顶点的数据

    2.通过uniform通道输入统一变量,即顶点/片元着色器中使用的不变的数据

    3.采样器:表示顶点着色器使用纹理的特殊统一变量类型

  • 输出:经过处理的最终顶点数据,有2种

    1. gl_Position ,是GLSL 的内建变量,是将处理后的最终顶点数据赋值给它

    2. gl_PointSize,是指点的尺寸,即可以在顶点着色器中修改每个点的大小,使用率较低

顶点着色器处理的业务

  • 矩阵变换位置
  • 算光照公式生成逐顶点颜色(也可以片元着色器)
  • 生成/变换纹理坐标:片元着色器是没有办法传入属性即attribute的,可以通过顶点着色器桥接,间接将纹理坐标属性传递到片元着色器

顶点着色器GLSL代码示例

attribute vec4 position;

attribute vec2 textCoordinate;

uniform mat4 rotateMatrix;

varying lowp vec2 varyTextCoord;

void main()

{

varyTextCoord = textCoordinate;

vec4 vPos = position;

vPos = vPos * rotateMatrix;

gl_Position = vPos;

}

  • attribute、uniform 表示client与server之间的通道
  • 其中的vec4、vec2都是向量类型,表示四维向量和二维向量
  • mat4:4*4矩阵
  • varying是修饰符:通过varying将纹理坐标传入到片元着色器
  • lowp:低精度
  • main中的操作:

    1.实现了纹理坐标的桥接;2.实现了顶点旋转矩阵的相乘:列向量 与 列矩阵 相乘,得到旋转后的顶点坐标;3.将上述得到的顶点坐标,赋值给gl_Position

图元装配、光栅化

  • 图元装配:将顶点数据计算成一个个图元
  • 光栅化:将图元转化为一组二维片段的过程,主要是由于屏幕是2D的,所以转换的像素点也是二维的

片元着色器

下图展示了片元着色器的输入和输出。

  • 输入,和顶点着色器一样,也有3种方式

    1.由顶点着色器桥接传递过来的纹理坐标等

    2.通过uniform通道输入统一变量,即顶点/片元着色器中使用的不变的数据

    3.采样器:表示顶点着色器使用纹理的特殊统一变量类型,例如纹理就是通过采样器传递

  • 输出:

    某个像素点经过片元着色器处理后的结果

片元着色器处理的业务

  • 计算颜色
  • 获取纹理值
  • 往像素点中填充颜色值(纹理值/颜色值)

片元着色器GLSL代码示例

varying lowp vec2 varyTextCoord;

uniform sampler2D colorMap;

void main() {

gl_FragColor = texture2D(colorMap, varyTextCoord); }

  • varying:必须和顶点着色器中一模一样,这样才能传递纹理坐标
  • sampler2D 采样器类型
  • texture2D(纹理采样器,纹理坐标):获取对应位置/坐标的颜色值,简称获得纹素
  • gl_FragColor(内建变量):将最终的颜色值赋值给它

总结

  • 顶点着色器、片元着色器都是代码段,类似于iOS中的函数/方法,有返回值.
  • 这两个返回值都属于GLSL中的内建变量,是封装好的,直接将数据赋值给它即可.
  • 顶点着色器的返回值会被复制给gl_Position,它 是顶点着色器中某一个顶点经过一系列处理后得到的结果;片元着色器的结果会赋值给gl_fragColor,它是经过片元着色器对某一个像素点来进行处理之后的结果。

以上是 初识 OpenGL ES 的全部内容, 来源链接: utcz.com/a/36092.html

回到顶部