iOS --- OpenGLES之着色器(shader)语法介绍
来源:互联网 发布:java 两个时间戳相减 编辑:程序博客网 时间:2024/06/05 16:47
上一篇博客 iOS — OpenGLES之初步认识 中主要介绍了OpenGLES在iOS中的简单使用,包括创建EAGLContext,设置CAEAGLLayer属性,使用renderbuffer和framebuffer等。这一次,我们将主要学习OpenGLES的着色器shader的基本语法。
关于OpenGLES渲染管线,请参考博客 [OpenGL ES 02]OpenGL ES渲染管线与着色器。着色器是可编程管线中的术语,其语法类似C语言,分为顶点着色器(Vertex Shader)和片元着色器(Fragment Shader)。
顶点着色器
Vertex shader – 在你的场景中,每个顶点都需要调用的程序,称为“顶点着色器”。假如你在渲染一个简单的场景:一个长方形,每个角只有一个顶点。于是vertex shader 会被调用四次。它负责执行:诸如灯光、几何变换等等的计算。得出最终的顶点位置后,为下面的片段着色器提供必须的数据。
vertex shader可通过可编程的方式实现对顶点的操作,如坐标空间转换,颜色及纹理坐标。最简单的Vertex shader如下:
attribute vec4 Position;void main(Void) { gl_Position = Position; // must set gl_Position for vertex shader}
- attribute声明vertex shader接收的变量,针对每一个顶点的数据。属性可理解为针对每一个顶点的输入数据,只有在vertex shader中才有,在fragment shader中没有。vec4表示由4部分组成的矢量。这里的Position用来传入顶点vertex的位置数据。
- main是shader脚本的入口。
- gl_Position是vertex shader内建的输出变量,传递给fragment shader,必须设置。这里将Position直接传递给fragment shader。
片元着色器
Fragment shader – 在你的场景中,大概每个像素都会调用的程序,称为“片段着色器”。在一个简单的场景,也是刚刚说到的长方形。这个长方形所覆盖到的每一个像素,都会调用一次fragment shader。片段着色器的责任是计算灯光,以及更重要的是计算出每个像素的最终颜色
Fragment是可以被渲染到屏幕上的像素点,fragment shader即用于计算每个像素的颜色等属性。最简单的Fragment shader如下
precision mediump float;void main(void) { gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0); // must set gl_FragColor for fragment shader}
- precision mediump float设置float的精度为mediump,还可设置为lowp和highp,主要是出于性能考虑。
- gl_FragColor是fragment shader唯一的内建输出变量,设置像素的颜色。这里设置所有像素均为红色。
Vertex shader接收多个参数
上边的vertex shader仅接收顶点的位置信息,因此像素颜色都是在fragment shader中写固定的(红色)。而在下边的vertex shader中,通过SourceColor传递像素颜色。
attribute vec4 Position; // position of vertexattribute vec4 SourceColor; // color of vertexvarying vec4 DestinationColor; // will pass out to fragment shadervoid main(void) { DestinationColor = SourceColor; gl_Position = Position;}
- 未声明为attribute的变量即为输出变量(如DestinationColor),将传递给fragment shader。
- varying表示依据两个顶点的颜色,平滑地计算出顶点之间每个像素的颜色。
对应的fragment shader为:
varying lowp vec4 DestinationColor;void main(void) { gl_FragColor = DestinationColor;}
这里,fragment shader接收来自vertex shader的变量DestinationColor,赋值给gl_FragColor,再输出至OpenGLES。即每个像素的颜色由DestinationColor决定,这样可在代码中精确控制每个像素的颜色。
Vertex shader与Fragment shader的差异
- shader脚本中有三种级别的精度:lowp,mediump,highp。如precision highp float; 。在vertex shader中,int和float都默认为highp级别。而fragment shader中没有默认精度,必须设置精度描述符,一般设为mediump即可。
- attribute只作用于vertex shader中,表示接收的变量。在vertex shader中,若没有attribute则为输出变量(输出至fragment shader)。
- vertex shader的默认输出变量至少应该有gl_Position,另外有两个可选的gl_FrontFacing和gl_PointSize。而fragment shader只有唯一的varying输出变量gl_FragColor。
- Uniform是全局变量,可用于vertex shader和fragment shader。在vertex shader中通常是变换矩阵、光照参数、颜色等,。在fragment shader中通常是雾化参数、纹理参数等。OpenGLES 2.0规定所有实现应该支持的最大vertex shader的uniform变量个数不能少于128个,而最大fragment shader的uniform变量个数不能少于16个。
- simpler是一种特殊的uniform,用于呈现纹理,可用于vertex shader和fragment shader。
Demo地址
本文的一系列demo都可在github中找到,DemoOpenGL,如有不准确的地方,欢迎指正。
参考资料
OpenGL Tutorial for iOS: OpenGL ES 2.0
OpenGL ES渲染管线与着色器
- iOS --- OpenGLES之着色器(shader)语法介绍
- iOS --- OpenGLES之着色器(shader)的编译、链接及使用
- Android着色器Shader介绍
- Unity3d 着色器语法(Shader)
- Unity3d 着色器语法(Shader)
- Unity3d 着色器语法(Shader)
- Unity3d 着色器语法(Shader)
- Unity3d 着色器语法(Shader)
- OpenGL ES 着色器(shader)介绍
- OpenGL ES 着色器(shader)介绍
- [OpenGL]OpenGL ES 着色器(shader)介绍
- OpenGL ES 着色器(shader)介绍
- OpenGL ES 着色器(shader)介绍
- OpenGL ES 着色器(shader)介绍
- Shader(着色器)相关介绍
- OpenGL ES 着色器(shader)介绍(转)
- OpenGL ES 着色器(shader)介绍
- opengles之卡通着色算法
- Android 各大网络http请求库的比较及实战
- distanceto
- MyBatis-Spring事务管理
- 最大公约数
- 延时模块的使用-system generator
- iOS --- OpenGLES之着色器(shader)语法介绍
- IAP - 3
- 软件工程总结(三)
- RabbitMQ基础概念详细介绍及示例
- leetcode刷题日记—— Count Primes
- tomcat ip地址访问项目 映射共享目录
- ||1
- 黑马程序员-OC语言-多态、代理
- 软件开发管理工具--持续集成构建