三、OpenGL ES GLSL语言 & 自定义着色器常用API

简介: OpenGL ES GLSL语言 & 自定义着色器常用API

EGL(Embedded Graphics Library)


  • OpenGL ES 命令需要渲染上下⽂绘制表面才能完成图形图像的绘制
  • 渲染上下⽂: 存储相关OpenGL ES状态,是一个状态机
  • 绘制表面:⽤于绘制图元的表面,需要指定渲染的缓存区,例如颜⾊缓、深度和模板
  • OpenGL ES API 并没有提供如何创建渲染上下文或者上下文如何连接到原生窗口系 统. EGL 是Khronos 渲染API(如OpenGL ES) 和原⽣窗⼝系统之间的接⼝. 唯⼀支持 OpenGL ES 却不支持EGL的平台是iOS. Apple 提供⾃己的EGL API的iOS实现,称为EAGL
  • 因为每个窗⼝系统都有不同的定义,所以EGL提供基本的不透明类型—EGLDisplay, 这 个类型封装了所有系统相关性,用于和原生窗⼝系统接⼝


主要功能


  • 和本地窗口系统(native windowing system)通讯
  • 查询可用的配置
  • 创建OpenGL ES 可用的“绘图表面“(drawing surface)
  • 同步不同类别的API之间的渲染,比如在OpenGL ES 和OpenVG之间同步,或者在OpenGL和本地窗口的绘图命令之间
  • 管理”渲染资源“,比如纹理映射(Rendering map)


GLSL语言


  • xcode中不支持GLSL语言对顶点/片元着色器的编译和连接,因此需要在项目中创建两个空文件,分别命名为shader.vshshaderv.fsh
  • 使用vsh、fsh后缀的原因是方便区分着色器,其本质就是一个字符串
  • 是否可以直接使用NSString?并不建议这样做,因为代码结构不清晰,不易读
  • 这两个文件中是否可以加中文注释?不建议加中文注释,会报奇怪的错误,由于在xcode中书写GLSL,完全是纯手写,没有任何提示,排查问题不好排查


下面是一些类型及API的总结


向量数据类型


常用的是vec2、vec3、vec4,默认是浮点类型

微信图片_20220514181829.png

矩阵数据类型


最常用的是mat3、mat4

微信图片_20220514182657.png

变量存储限定符


常用varying、attribute、uniform


  • varying 修饰符:当需要将顶点着色器的数据传递到片元着色器时,两个着色器中一模一样的纹理坐标变量就需要它来修饰
  • attribute:数据只能从客户端中传递到顶点着色器,且只能在顶点着色器中使用
  • 修饰的数据:顶点、纹理、颜色、法线等
  • API通常以glVertex...开头,例如glVertexAttribPointer
  • 其中的纹理坐标,需要顶点着色器间接传递到片元着色器,需要在顶点与片元着色器中定义一个一模一样的纹理坐标,通过这个变量将纹理坐标数据间接传递到片元着色器,varying lowp vec2 varyTextCoord;
  • 顶点着色器计算之后的顶点结果需要赋值给GLSL的内建变量gl_Position
attribute vec4 position;
attribute vec2 textCoordinate;
varying lowp vec2 varyTextCoord;
void main()
{
    varyTextCoord = textCoordinate;
    gl_Position = position;
}


uniform:从app代码传递到vertex、fragment中所用的变量


  • 在vertex,fragment中一般将uniform当成常量
  • uniform可以传的数据:视图矩阵、投影矩阵、投影视图矩阵
  • API通常以glUniform...开头
  • 片元着色器中最终颜色,即拿到纹理对应坐标下的纹素。纹素是纹理对应像素点的颜色值,需要通过内建函数texture2D(纹理,纹理坐标)计算,将最终返回的颜色值赋值给内建变量gl_FragColor
//需要定义精度,否则可能会报错
precsion highp float;
//纹理坐标 必须与顶点着色器中一模一样,通过这个参数获取传递过来的值
varying lowp vec2 varyTextCoord;
//纹理 
uniform sampler2D colorMap;   
void main(){
    //1、拿到纹理对应坐标下的纹素。纹素是纹理对应像素点的颜色值
    lowp vec4 temp = texture2D(colorMap, varyTextCoord);
    //2、非常重要且必须的内建变量:gl_FragColor
    gl_FragColor = temp;
} 

微信图片_20220514183057.png


OpenGL ES 错误处理


如果不正确使用OpenGL ES 命令,应用程序就会产生一个错误编码,且会被记录,可以用glGetError查询,一旦查询到错误代码,当前的错误代码就会复位为GL_NO_ERROR


微信图片_20220514191115.png


OpenGL ES 自定义着色器常用API


自定义着色器


自定义着色器一般有以下步骤:


  • 创建顶点着色器/片元着色器 --glCreateShader
  • 指定shader的source --glShaderSource
  • 编译shader --glCompileShader


以下是创建与编译一个着色器的相关API

微信图片_20220514191332.png


自定义程序


自定义程序一般有以下步骤:


  • 创建一个程序对象 --glCreateProgram
  • 着色器与程序连接/附着 --glAttachShader
  • 链接程序 --glLinkProgram
  • 使用程序 --glUseProgram


以下是创建与链接程序的相关API

微信图片_20220514191516.png


着色器与程序的 编译 & 链接


  • 需要创建2个基本对象才能使用着色器进行传染:着色器对象和程序对象
  • 获取链接后着色器对象一般的编译&链接分为6步:


  • 创建一个顶点着色器对象和一个片元着色器对象
  • 将源代码链接到每个着色器对象
  • 编译着色器对象
  • 创建一个程序对象
  • 将编译后的着色器对象连接到程序对象
  • 链接程序对象


相关文章
|
1月前
|
数据可视化 API 索引
ES常见Index API操作最佳实践!
【10月更文挑战第21天】
69 1
ES常见Index API操作最佳实践!
|
2月前
|
中间件 Go API
使用Go语言构建高性能RESTful API
在现代软件开发中,RESTful API因其简洁和高效而成为构建网络服务的首选。Go语言以其并发处理能力和高性能著称,是开发RESTful API的理想选择。本文将介绍如何使用Go语言构建RESTful API,包括基础的路由设置、中间件的使用、数据验证、错误处理以及性能优化。通过实际代码示例,我们将展示Go语言在API开发中的强大功能和灵活性。
|
2月前
|
JavaScript 前端开发 Java
多种语言请求API接口方法
每种语言和库的选择取决于具体需求、项目环境以及个人偏好。了解这些基本方法,开发者就可以根据项目需求选择合适的语言和库来高效地与API交互。
40 1
|
3月前
|
JSON Go API
使用Go语言和Gin框架构建RESTful API:GET与POST请求示例
使用Go语言和Gin框架构建RESTful API:GET与POST请求示例
|
3月前
|
Go API 开发者
深入探讨:使用Go语言构建高性能RESTful API服务
在本文中,我们将探索Go语言在构建高效、可靠的RESTful API服务中的独特优势。通过实际案例分析,我们将展示Go如何通过其并发模型、简洁的语法和内置的http包,成为现代后端服务开发的有力工具。
|
4月前
|
域名解析 网络协议 API
【API管理 APIM】APIM集成内部VNet时,常遇见的关于自定义DNS服务问题。
【API管理 APIM】APIM集成内部VNet时,常遇见的关于自定义DNS服务问题。
|
4月前
|
SQL Shell API
python Django教程 之 模型(数据库)、自定义Field、数据表更改、QuerySet API
python Django教程 之 模型(数据库)、自定义Field、数据表更改、QuerySet API
|
4月前
|
中间件 API 网络架构
Django后端架构开发:从匿名用户API节流到REST自定义认证
Django后端架构开发:从匿名用户API节流到REST自定义认证
46 0
|
4月前
|
SQL 网络协议 安全
【Azure API 管理】APIM集成内网虚拟网络后,启用自定义路由管理外出流量经过防火墙(Firewall),遇见APIs加载不出来问题
【Azure API 管理】APIM集成内网虚拟网络后,启用自定义路由管理外出流量经过防火墙(Firewall),遇见APIs加载不出来问题
|
4月前
|
SQL 安全 Java

热门文章

最新文章