WebGL常用API说明
- 1.设置背景色 gl.clearColor()
- 2.清空绘图区 gl.clear()
- 3.绘制操作 gl.drawArrays()
- 4. attribute变量
- 5. uniform变量
- 6. 缓冲区对象(VBO)
- 7. 类型化数组
- 8. 向4*4矩阵传值 gl.uniformMatrix4fv()
- 9. varying变量使用
- 10. 片元着色器的内置变量 gl_FragCoord
- 11. 纹理对象使用
- 12. Matrix4对象的方法和属性
- 13. 隐藏面消除
- 14. 解决深度冲突设置多边形偏移 gl.polygonOffset()
- 15. 通过顶点索引绘制物体 gl.drawElements()
- 16. 着色器对象
- 17. 程序对象
- 18. 读取指定区域的像素颜色 gl.readPixels()
- 19. 指定混合 gl.blendFunc()
- 20. 释放锁定深度缓冲区 gl.depthMask()
- 21. 帧缓冲区对象(FBO)
- 21.1 创建帧缓冲区对象 gl.createFramebuffer()
- 21.2 删除帧缓冲区对象 gl.deleteFramebuffer()
- 21.3 创建渲染缓冲区对象 gl.createRenderbuffer()
- 21.4 删除渲染缓冲区对象 gl.deleteRenderbuffer()
- 21.5 绑定渲染缓冲区 gl.bindRenderbuffer()
- 21.6 设置渲染缓冲区尺寸 gl.renderbufferStorage()
- 21.7 绑定帧缓冲区 gl.bindFramebuffer()
- 21.8 纹理对象关联到帧缓冲区对象 gl.framebufferTexture2D()
- 21.9 将渲染缓冲区对象关联到帧缓冲区对象 gl.framebufferRenderbuffer()
- 21.10 检查帧缓冲区的配置 gl.checkFramebufferStatus()
- 21.11 设置绘图区域 gl.viewport()
1.设置背景色 gl.clearColor()
在清空绘图区之前需要设置背景色。一旦指定了背景色后,背景色就会驻存在WebGL系统中,在下次调用gl.clearColor()方法前不会改变
函数功能:指定绘图区域的背景色
-----------------------------------------------------------
调用示例:gl.clearColor(red, green, blue, alpha)
-----------------------------------------------------------
参数
red 指定红色值(从0.0到1.0)
green 指定绿色值(从0.0到1.0)
blue 指定蓝色值(从0.0到1.0)
alpha 指定透明度值(从0.0到1.0)
小于0.0的值会被截断为0.0,大于1.0的值会被截断为1.0
-----------------------------------------------------------
返回值 无
-----------------------------------------------------------
错 误 无
2.清空绘图区 gl.clear()
清空绘图区实际上是清空颜色缓冲区,在WebGL中缓冲区有三类: 颜色缓冲区、深度缓冲区、模板缓冲区
函数功能:将指定缓冲区设置为预定的值-预定的值指的是gl.clearColor()设置的值
-----------------------------------------------------------------------------------
调用示例:gl.clear(buffer)
-----------------------------------------------------------------------------------
参数
buffer 指定待清空的缓冲区,位操作位|可以用来指定多个缓冲区
gl.COLOR_BUFFER_BIT 代表清空颜色缓冲区
gl.DEPTH_BUFFER_BIT 代表清空深度缓冲区
gl.STENCIL_BUFFER_BIT 代表清空模板缓冲区
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错 误 INVALID_VALUE 缓冲区不是以上三种类型
如果没有指定背景色(没有调用gl.clearColor()函数),直接调用gl.clear(),那么使用的默认值如下所示
缓冲区名称 | 默认值 | 相关函数 |
---|---|---|
颜色缓冲区 | (0.0, 0.0, 0.0, 0.0) | gl.clearColor(red, green, blue, alpha) |
深度缓冲区 | 1.0 | gl.clearDepth(depth) |
模板缓冲区 | 0 | gl.clearStencil(s) |
3.绘制操作 gl.drawArrays()
建立了着色器之后,我们就要进行绘制了,gl.drawArrays()是一个强大的函数,可以用来绘制各种图形,该函数的规范如下所示
函数功能:执行顶点着色器,按照mode参数指定的方式绘制图形
--------------------------------------------------------------------------
调用示例:gl.drawArrays(mode, first, count)
--------------------------------------------------------------------------
参数
mode 指定绘制的方式,可以接收以下常量符号:
gl.POINTS,gl.LINES,gl.LINE_STRIP,gl.LINE_LOOP
gl.TRIANGLES,gl.TRIANGLE_STRIP,gl.TRIANGLE_FAN
first 指定从哪个点开始绘制-整形数
count 指定要绘制多少个顶点-整形数
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错 误 INVALID_ENUM 传入的mode参数不是指定参数
INVALID_VALUE 参数first或count是负数
第一个参数mode说明
gl.drawArray()方法可以绘制各种图形,它的第一个参数可以取众多常量:gl.POINTS,gl.LINES,gl.LINE_STRIP,gl.LINE_LOOP,gl.TRIANGLES,gl.TRIANGLE_STRIP,gl.TRIANGLE_FAN,接下来通过一张图来解释一下每一个值代表的意思
4. attribute变量
4.1 获取attribute变量地址 gl.getAttribLocation()
我们在着色器程序中声明的attribute变量都会有一个自己的存储地址,通过这个地址我们可以在外部程序中给它赋值,gl.getAttribLocation() 方法就是帮我们获取这个地址的利器
函数功能:获取有name指定的着色器中attribute变量的存储地址
--------------------------------------------------------------------------
调用示例:gl.getAttribLocation(program, name)
--------------------------------------------------------------------------
参数
program 指定包含顶点着色器和片元着色器的着色器程序对象
name 指定想要获取其存储地址的attribute变量名称
--------------------------------------------------------------------------
返回值 >=0 attribute变量的存储地址
-1 指定的变量名不存在,或命名具有gl_或webgl_前缀
--------------------------------------------------------------------------
错 误 INVALID_OPERATION 程序对象未能连接成功
INVALID_VALUE name参数的长度大于最大长度,默认256字节
示例代码
//获取着色器attribute变量a_Position的存储地址
var a_Position = gl.getAttribLocation(gl.program, 'a_Position');
4.2 给attribute变量传值 gl.vertexAttrib3f()
gl.getAttribLocation() 方法帮我们获取到了着色器变量的地址,这时就需要请出gl.vertexAttrib3f() 方法了,通过这个方法我们就可以在JavaScript程序中把想要赋的值赋给着色器中的attribute变量
函数功能:将数据v0, v1, v2 传给由location参数指定的着色器的attribute变量
------------------------------------------------------------------------------
调用示例:gl.vertexAttrib3f(location, v0, v1, v2)
------------------------------------------------------------------------------
参数
location 指定将要修改的attribute变量的存储地址
v0 指定填充attribute变量第一个分量的值
v1 指定填充attribute变量第二个分量的值
v2 指定填充attribute变量第三个分量的值
------------------------------------------------------------------------------
返回值 无
------------------------------------------------------------------------------
错 误 INVALID_OPERATION 没有当前的program对象
INVALID_VALUE location大于等于attribute变量的最大数据,默认为8
示例代码
//向着色器attribute变量a_Position传值
gl.vertexAttrib3f(a_Position, 0.0, 0.0, 0.0)
4.3 给attribute变量传值 gl.vertexAttrib3f()的同族函数
gl.vertexAttrib3f() 方法是一系列同族函数中的一个,该系列函数的任务就是从JavaScript程序中向顶点着色器中的attribute变量传值
函数功能:将数据[1~4个分量]传给由location参数指定的着色器的attribute变量
------------------------------------------------------------------------------
gl.vertexAttrib1f(location, v0)
gl.vertexAttrib2f(location, v0, v1)
gl.vertexAttrib3f(location, v0, v1, v2)
gl.vertexAttrib4f(location, v0, v1, v2, v3)
------------------------------------------------------------------------------
参数
location 指定将要修改的attribute变量的存储地址
v0,v1,v2,v3 指定传输给attribute变量的四个分量的值
------------------------------------------------------------------------------
返回值 无
------------------------------------------------------------------------------
错 误 INVALID_VALUE location大于等于attribute变量的最大数据,默认为8
你同样可以使用这些方法的矢量版本,它们的名字以"v"作为结尾。并接受类型化数组作为参数,函数名中数字表示数组中元素的个数
var position = new Float32Array([1.0,2.0,3.0,1.0]);
gl.vertexAttrib4fv(position);
5. uniform变量
5.1 获取uniform变量地址 gl.getUniformLocation()
与attribute变量一样,要在JavaScript程序中使用着色器中的变量,首先要获取该变量的存储地址,attribute变量通过gl.getAttribLocation() 方法获取,uniform变量则通过gl.getUniformLocation() 方法获取
函数功能:获取由name指定的uniform变量的存储地址
--------------------------------------------------------------------------
调用示例:gl.getUniformLocation(program, name)
--------------------------------------------------------------------------
参数
program 指定包含顶点着色器和片元着色器的着色器程序对象
name 指定想要获取其存储地址的uniform变量名称
--------------------------------------------------------------------------
返回值 non-null uniform变量的存储地址
null 指定的uniform变量不存在,或命名具有gl_或webgl_前缀
--------------------------------------------------------------------------
错 误 INVALID_OPERATION 程序对象未能连接成功
INVALID_VALUE name参数的长度大于uniform变量名的最大长度,默认256字节
示例代码
//获取片元着色器uniform变量u_FragColor的存储地址
var u_FragColor = gl.getUniformLocation(gl.program, 'u_FragColor');
5.2 向uniform变量传值 gl.uniform4f()
gl.getUniformLocation() 方法帮我们获取到着色器uniform变量的地址,我们在JavaScript程序中处理完,需要把新的值再传给这个uniform变量。这时就需要用到gl.uniform4f() 方法了
函数功能:将数据v0, v1, v2, v3 传给由location参数指定的uniform变量
---------------------------------------------------------------------------------
调用示例:gl.uniform4f(location, v0, v1, v2, v3)
---------------------------------------------------------------------------------
参数
location 指定将要修改的uniform变量的存储地址
v0 指定填充uniform变量第一个分量的值
v1 指定填充uniform变量第二个分量的值
v2 指定填充uniform变量第三个分量的值
v2 指定填充uniform变量第四个分量的值
---------------------------------------------------------------------------------
返回值 无
---------------------------------------------------------------------------------
错 误 INVALID_OPERATION 没有当前的program对象,或者location是非法的存储位置
示例代码
//向片元着色器uniform变量u_FragColor传值
gl.uniform4f(u_FragColor, 1.0, 0.0, 0.0, 1.0)
5.3 向uniform变量传值 gl.uniform4f()的同族函数
gl.uniform4f() 方法是一系列同族函数中的一个,该系列函数的任务就是从JavaScript程序中向着色器中的uniform变量传值
函数功能:将数据[1~4个分量]传给由location参数指定的uniform变量
------------------------------------------------------------------------------
gl.uniform1f(location, v0)
gl.uniform2f(location, v0, v1)
gl.uniform3f(location, v0, v1, v2)
gl.uniform4f(location, v0, v1, v2, v3)
------------------------------------------------------------------------------
参数
location 指定将要修改的uniform变量的存储地址
v0,v1,v2,v3 指定传输给uniform变量的四个分量的值
------------------------------------------------------------------------------
返回值 无
------------------------------------------------------------------------------
错 误 INVALID_OPERATION 没有当前的program对象,或者location是非法的存储位置
友情提示:
gl.uniform1f()只需要传输一个值,这个值将被填充到uniform变量的第一个分量中,第二、第三个分量将被设置为0.0,第四个分量将被设置为1.0,其他同族函数类推
6. 缓冲区对象(VBO)
6.1 创建缓冲区对象 gl.createBuffer()
6.2 绑定缓冲区 gl.bindBuffer()
6.3 向缓冲区对象写入数据 gl.bufferData()
6.4 将缓冲区对象分配给attribute变量 gl.vertexAttribPointer()
6.5 开启attribute变量 gl.enableVertexAttribArray()
7. 类型化数组
为了优化性能,WebGL引入了一种特殊的数组- 类型化数组 ,我们先来看一下类型化数组的种类
数组类型 | 每个元素所占字节数 | 描述(C语言还在那个的数据类型) |
---|---|---|
Int8Array | 1 | 8位整形数(signed char) |
UInt8Array | 1 | 8位无符号整形数(unsigned char) |
Int16Array | 2 | 16位整形数(signed short) |
UInt16Array | 2 | 16位无符号整形数(unsigned short) |
Int32Array | 4 | 32位整形数(signed int) |
UInt32Array | 4 | 32位无符号整形数(unsigned int) |
Float32Array | 4 | 32位单精度浮点数(float) |
Float64Array | 8 | 64位双精度浮点数(double) |
类型化数组与JavaScript中的数组有所不同,它不支持pus(),pop()等方法,但是它有自己一系列的方法和属性,具体请查阅下表
方法、属性和常量 | 描述 |
---|---|
get(index) | 获取第index个元素的值 |
set(index, value) | 设置第index个元素的值为value |
set(array, offset) | 从第offset个元素开始将数组array中的值填充进去 |
length | 数组的长度 |
BYTES_PER_ELEMENT | 数组中每个元素所占的字节数 |
8. 向4*4矩阵传值 gl.uniformMatrix4fv()
调用示例:gl.uniformMatrix4fv(location, transpose, array)
----------------------------------------------------------------------------------
函数功能:将array表示的4*4矩阵分配给由location指定的uniform变量
----------------------------------------------------------------------------------
参数
location uniform变量的存储地址
transpose 在WebGL中必须指定为false
array 待传输的类型化数组,4*4矩阵按列主序
----------------------------------------------------------------------------------
返回值 无
----------------------------------------------------------------------------------
错误 INVALID_OPERATION 不存在当前程序对象
INVALID_VALUE transpose不为false,或者数组的长度小于16
示例代码
//在 x、y、z轴方向上平移的距离
var Tx = 0.5
var Ty = 0.5
var Tz = 0.0
//创建平移矩阵的类型化数组
var translateMatrix = new Float32Array([
1.0, 0.0, 0.0, 0.0,
0.0, 1.0, 0.0, 0.0,
0.0, 0.0, 1.0, 0.0,
Tx, Ty, Tz, 1.0
])
//获取顶点着色器uniform变量u_TranslateMatrix(平移矩阵)的存储地址
var u_TranslateMatrix = gl.getUniformLocation(gl.program, 'u_TranslateMatrix')
//向顶点着色器uniform变量u_TranslateMatrix传值
gl.uniformMatrix4fv(u_TranslateMatrix, false, translateMatrix)
9. varying变量使用
9.1 顶点着色器中声明varying变量
9.2 片元着色器中声明与使用varying变量
在片元着色器中同样也要先声明varying变量v_Color,这样片元着色器与顶点着色器通过v_Color变量建立了通讯通道,就可以接收顶点着色器传送的片元颜色信息,同时将接受到的颜色信息赋值给片元着色器的内置变量gl_FragColor
9.3 通过缓冲区对象给attribute变量传值
- 创建类型化数组。这里创建的类型化数组用来存放顶点坐标和顶点颜色信息,大家看一下注释,这个数组中有三行,每一行是一个顶点,在以顶点1为例,前两个元素是顶点坐标,后三个元素是顶点颜色信息。
- 创建缓冲区对象并绑定和写入数据。这一步需要创建缓冲区对象,绑定目标,并将创建的存储顶点坐标和颜色信息的类型化数组写入它
- a_Position的分配缓存与开启。在这里我们注意一下函数 gl.vertexAttribPointer() 的第五个参数和第六个参数,第五个参数stride 指的是每一个顶点的大小,传值为FSIZE * 5,其实就是告诉缓存,每取一个点,我要取五个数,第六个参数offset 指的是缓冲区对象中的偏移量,我们设置为0,因为每一个点,它都是从开始取值
- a_Color的分配缓存与开启。在这里我们也注意一下gl.vertexAttribPointer() 的参数,第五个参数stride 与上一次分配a_Position一样,也值为FSIZE * 5,因为每个点五个元素没有改变。 第六个参数offset 这次设置为FSIZE * 2,因为每一个顶点的前两个元素是顶点坐标,后三个元素是颜色信息
10. 片元着色器的内置变量 gl_FragCoord
类型和变量 | 描述 |
---|---|
vec4 gl_FragCoord | 该内置变量的第一参数表示片元在canvas坐标系中的横坐标,第二参数表示片元在canvas坐标系中的纵坐标 |
使用示例
'precision mediump float;\n' + // 设置精度
'uniform float u_Width;\n' + //声明uniform变量u_Width,用来接收canvas画布的宽度
'uniform float u_Height;\n' + //声明uniform变量u_Height,用来接收canvas画布的高度
'void main(){\n' +
//使用内置变量gl_FragCoord计算颜色并赋值给内置变量gl_FragColor
' gl_FragColor = vec4(gl_FragCoord.x/u_Width, 0.0, gl_FragCoord.y/u_Height, 1.0);\n' +
'}\n';
//获取着色器uniform变量u_Width的存储地址,并传值
var u_Width = gl.getUniformLocation(gl.program, 'u_Width');
gl.uniform1f(u_Width, gl.drawingBufferWidth);
//获取着色器uniform变量u_Height的存储地址,并传值
var u_Height = gl.getUniformLocation(gl.program, 'u_Height');
gl.uniform1f(u_Height, gl.drawingBufferHeight);
以上示例中片元的颜色取决于它的坐标位置,片元颜色会随着片元位置的变化而逐渐变化,所以呈现的图形颜色会有平滑的渐变效果
11. 纹理对象使用
11.1 创建纹理对象 gl.createTexture()
11.2 处理加载的纹理图像 gl.pixelStorei()
11.3 激活纹理单元 gl.activeTexture()
11.4 绑定纹理对象 gl.bindTexture()
11.5 设置纹理填充方式 gl.texParameteri()
通过上面的介绍,你会发现纹理参数pname的每个可选值都有一个默认值,如果你不调用gl.texParameteri() 方法,也会使用默认值,需要注意的是 gl.TEXTURE_MIN_FILTER 纹理缩小方法的默认值是 gl.NEAREST_MIPMAP_LINEAR 这个默认值是一个被称为MIPMAP(金字塔)的纹理类型。实际上MIPMAP是一系列的纹理,它们包括:gl.NEAREST_MIPMAP_NEAREST、gl.LINEAR_MIPMAP_NEAREST、gl.NEAREST_MIPMAP_LINEAR、gl.LINEAR_MIPMAP_LINEAR
11.6 纹理图像分配 gl.texImage2D()
12. Matrix4对象的方法和属性
这里我们介绍一下cuon-matrix.js 中的 Matrix4对象的图形变换相关方法和属性
方法/属性名称 | 描述 |
---|---|
Matrix4.setIdentity() | 将Matrix4实例初始化为单位矩阵 |
Matrix4.setTranslate(x,y,z) | 将Matrix4实例设置为平移矩阵,参数x,y,z分别代表在X轴,Y轴,Z轴上平移的距离 |
Matrix4.setRotate(angle,x,y,z) | 将Matrix4实例设置为旋转矩阵,旋转的角度为angle,旋转轴为(x,y,z) |
Matrix4.setScale(x,y,z) | 将Matrix4实例设置为缩放矩阵,在三个轴上的缩放因子分别是x,y,z |
Matrix4.translate(x,y,z) | 将Matrix4实例乘以一个平移矩阵,该平移矩阵在X轴上平移x,Y轴上平移y,Z轴上平移z,相乘的结果还是储存在Matrix4中 |
Matrix4.rotate(angle,x,y,z) | 将Matrix4实例乘以一个旋转矩阵,该旋转矩阵旋转的角度为angle,旋转轴为(x,y,z),相乘的结果还是储存在Matrix4中 |
Matrix4.scale(x,y,z) | 将Matrix4实例乘以一个缩放矩阵,该缩放矩阵在三个轴上的缩放因子分别是x,y,z 。相乘的结果还是储存在Matrix4中 |
Matrix4.set(m) | 将Matrix4实例设置为m,m必须也是一个Matrix4实例 |
Matrix4.elements | 保存了Matrix4实例的矩阵元素的类型化数组,该类型化数组的种类为Float32Array |
Matrix4.setLookAt(eyeX, eyeY, eyeZ, atX, atY, atZ, upX, upY, upZ) | 根据视点(eyeX, eyeY, eyeZ)、观察点(atX, atY, atZ)、上方向(upX, upY, upZ)创建视图矩阵,视图矩阵的类型是Matrix4,观察点映射到的中心点 |
Matrix4.setOrtho(left, right, bottom, top, near, far) | 根据参数top、bottom、left、right、near、far计算正投影矩阵 |
Matrix4.setPerspective(fov, aspect, near, far) | 根据参数fov, aspect, near, far计算透视投影矩阵 |
Matrix4.setInverseOf(m) | 使自身称为矩阵m的逆矩阵 |
Matrix4.transpose() | 对自身进行转置操作,并将自身设置为转置后的结果 |
从上表中发现,包含set前缀的方法会更加参数计算出变换矩阵,并将该矩阵写入到自身中,即你可以通过Matrix4.elements获取该矩阵的内容,而不包含set前缀的方法,会先根据参数计算出变换矩阵,然后将自身和得到的变换矩阵相乘,最后把相乘后的矩阵写入到自身中,也就是说如果你需要对一个图形进行复合变换需要使用没有set前缀的方法。
13. 隐藏面消除
13.1 开启隐藏面消除 gl.enable()
函数功能:开启cap表示的功能
-----------------------------------------------------------------------------------
调用示例:gl.enable(cap)
-----------------------------------------------------------------------------------
参数
cap 指定需要开启的功能,可以是以下几个
gl.DEPTH_TEST 隐藏面消除
gl.BLEND 混合
gl.POLYGON_OFFSET_FILL 多边形位移
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错误 INVALID_ENUM cap的值无效
13.2 关闭隐藏面消除 gl.disable()
函数功能:关闭cap表示的功能
-----------------------------------------------------------------------------------
调用示例:gl.disable(cap)
-----------------------------------------------------------------------------------
参数
cap 指定需要开启的功能,可以是以下几个
gl.DEPTH_TEST 隐藏面消除
gl.BLEND 混合
gl.POLYGON_OFFSET_FILL 多边形位移
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错误 INVALID_ENUM cap的值无效
14. 解决深度冲突设置多边形偏移 gl.polygonOffset()
函数功能:指定加到每个顶点绘制后Z值上的偏移量,偏移量按照公式 m*factor+r*units计算,其中
m表示顶点所在表面相对于视线的角度,r表示硬件能够区分两个Z值之差的最小值
-----------------------------------------------------------------------------------
调用示例:gl.polygonOffset(factor, units)
-----------------------------------------------------------------------------------
参数
factor 指定每个多边形的可变深度偏移的比例因子,默认0
units 指定与顶点所在表面相对于视线的角度相乘的偏移乘数,默认0
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错误 无
15. 通过顶点索引绘制物体 gl.drawElements()
函数功能:执行着色器,按照mode参数指定的方式,根据gl.ELEMENT_ARRAY_BUFFER的缓冲区的顶点索引绘制图形
--------------------------------------------------------------------------
调用示例:gl.drawArrays(mode, count, type, offset)
--------------------------------------------------------------------------
参数
mode 指定绘制的方式,可以接收以下常量符号:
gl.POINTS,gl.LINES,gl.LINE_STRIP,gl.LINE_LOOP
gl.TRIANGLES,gl.TRIANGLE_STRIP,gl.TRIANGLE_FAN
count 指定绘制顶点的个数
type 指定索引值数据类型,可以以下值
gl.UNSIGNED_BYTE
gl.UNSIGNED_SHORT
offset 指定索引数组中开始绘制的位置,以字节为单位
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错 误 INVALID_ENUM 传入的mode参数不是指定参数
INVALID_VALUE 参数count或offset是负数
第一个参数mode说明
gl.drawArray()方法可以绘制各种图形,它的第一个参数可以取众多常量:gl.POINTS,gl.LINES,gl.LINE_STRIP,gl.LINE_LOOP,gl.TRIANGLES,gl.TRIANGLE_STRIP,gl.TRIANGLE_FAN,接下来通过一张图来解释一下每一个值代表的意思
16. 着色器对象
16.1 创建着色器对象 gl.createShader()
在WebGL中所有的着色器对象必须通过调用 gl.createShader() 来创建
gl.createShader()根据传入的type创建顶点着色器或者片元着色器,如果不在需要这个着色器了,可以 像这样 gl.deleteShader(shader)
删除它,
注:删除着色器的时候,如果着色器对象还在使用(使用gl.attachShader()函数使这个着色器附件在了程序对象上),那么调用删除函数后,不会立即删除着色器,要等到不在使用该着色器时才会删除掉
16.2 指定着色器代码 gl.shaderSource()
16.3 编译着色器 gl.compileShader()
GLSL ES 语言与C或C++相似,需要编译成二进制的可执行文件才能使用,对于我们创建的着色器,在向着色器对象传入源代码之后,同样需要进行编译才能使用,WebGL 提供了gl.compileShader()函数,用来编译着色器
注:如果调用gl.shaderSource() 函数时,用新代码替换了旧代码,已编译好的可执行文件不会被自动替换掉,需要手动重新编译,即再次调用gl.compileShader()函数
16.4 获取着色器信息 gl.getShaderParameter()
16.5 获取写入着色器日志 gl.getShaderInfoLog()
通常 gl.getShaderParameter() 函数和 gl.getShaderInfoLog() 函数是配合使用的,一般是将gl.getShaderParameter()函数的参数pname指定为 gl.COMPILE_STATUS 就可以检查着色器是否编译成功,如果编译失败通过 gl.getShaderInfoLog() 函数获取错误信息
示例如下:
17. 程序对象
17.1 创建程序对象 gl.createProgram()
17.2 删除程序对象 gl.deleteProgram()
17.3 为程序对象分配着色器对象 gl.attachShader()
WebGL程序要运行起来,必须要有两个着色器,一个顶点着色器,一个片元着色器,就需要通过gl.attachShader() 函数为程序对象分配这两个着色器
17.4 取消程序对象分配的着色器对象 gl.detachShader()
17.5 连接程序对象 gl.linkProgram()
17.6 检查着色器是否连接成功 gl.getProgramParameter()
如果程序已经连接成功,我们就得到一个二进制的可执行模块供WebGL调用,如果连接失败可以通过 gl.getProgramInfoLog() 函数获取连接出错的信息
17.7 获取程序对象的日志 gl.getProgramInfoLog()
17.8 使用程序对象 gl.useProgram()
18. 读取指定区域的像素颜色 gl.readPixels()
调用示例:gl.readPixels(x, y, width, height, format, type, pixels)
--------------------------------------------------------------------------
函数功能:从颜色缓冲区中读取由x,y,width,height参数确定的矩形中的所有像素值,
并保存在pixels指定的数组中
--------------------------------------------------------------------------
参数
x, y 指定颜色缓冲区中矩形块左上角的坐标
width, height 指定矩形的宽度和高度,以像素为单位
format 指定像素值的颜色格式,必须为gl.RGBA
type 指定像素值的数据格式,必须为gl.UNSIGNED_BYTE
pixels 指定用来接收像素数据的Uint8Array类型化数组
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错误 INVALID_VALUE pixels为null,或者,width或height是负值
INVALID_OPERATION pexels的长度不够存储所有像素值数据
INVALID_ENUM format或type值无效
19. 指定混合 gl.blendFunc()
在进行α混合时要用到两个颜色,即 源颜色 (source color) 和 目标颜色 (destination color),源颜色是待混合进去的颜色,目标颜色是待被混合进去的颜色
函数功能:通过参数src_factor 和 dst_factor指定进行混合操作的函数,混合后的颜色计算如下:
<混合后的颜色> = <源颜色> x src_factor + <目标颜色> x dst_factor
-----------------------------------------------------------------------------------
调用示例:gl.blendFunc(src_factor,dst_factor)
-----------------------------------------------------------------------------------
参数
src_factor 指定源颜色在混合后颜色中的权重一种,如下表所示
dst_factor 指定目标颜色在混合后颜色中的权重一种,如下表所示
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错 误 INVALID_VALUE src_factor或dst_factor的值不在下表中
可以指定给src_factor和dst_factor的常量
常量 | R分量的系数 | G分量的系数 | B分量的系数 |
---|---|---|---|
gl.ZERO | 0.0 | 0.0 | 0.0 |
gl.ONE | 1.0 | 1.0 | 1.0 |
gl.SRC_COLOR | Rs | Gs | Bs |
gl.ONE_MINUS_SRC_COLOR | (1-Rs) | (1-Gs ) | (1-Bs) |
gl.DST_COLOR | Rd | Gd | Bd |
gl.ONE_MINUS_DST_COLOR | (1-Rd) | (1-Gd) | (1-Bd) |
gl.SRC_ALPHA | As | As | As |
gl.ONE_MINUS_SRC_ALPHA | (1-As) | (1-As) | (1-As) |
gl.DST_ALPHA | Ad | Ad | Ad |
gl.ONE_MINUS_DST_ALPHA | (1-Ad) | (1-Ad) | (1-Ad) |
gl.SRC_ALPHA _SATURATE | min(As,Ad) | min(As,Ad) | min(As,Ad) |
上表中(Rs,Gs,Bs,As)表示源颜色的各个分量,(Rd,Gd,Bd,Ad)表示目标颜色的各个分量
接下来以gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA) 为配置说明一下混合过程
假设:源颜色(0.0,1.0,0.0,0.4),目标颜色(1.0,1.0,0.0,1.0)
从假设中得知As=0.4, 依据上表推出参数gl.SRC_ALPHA指定的源颜色的权重因子 src_factor = (0.4,0.4,0.4),推出参数gl.ONE_MINUS_SRC_ALPHA指定的目标颜色的权重因子 dst_factor = (0.6,0.6,0.6)
计算混合颜色的公式
<混合后的颜色> = <源颜色> x src_factor + <目标颜色> x dst_factor
带入以上公式
<混合后的颜色> = (0.0,1.0,0.0) x (0.4,0.4,0.4) + (1.0,1.0,0.0) x (0.6,0.6,0.6)
<混合后的颜色> = (0.0,0.4,0.0) + (0.6,0.6,0.0)
<混合后的颜色> = (0.6,1.0,0.0)
加法混合 src_factor和dst_factor可以指定为上表中的任意常量,有一种比较常用的混合方式叫加法混合 (additive blending),加法混合的设置函数为 gl.blendFunc(gl.SRC_ALPHA, gl.ONE) 由于gl.ONE指定的权重因子的三个分量值都是1,所以加法混合会使被混合的区域更加明亮,通常用来实现爆炸的光照效果,或者一些需要引起注意的物品
20. 释放锁定深度缓冲区 gl.depthMask()
函数功能:锁定或释放深度缓冲区的写入操作
-----------------------------------------------------------------------------------
调用示例:gl.depthMask(mask)
-----------------------------------------------------------------------------------
参数 mask 指定是锁定(false)还是释放(true)深度缓冲区的写入操作
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错 误 无
21. 帧缓冲区对象(FBO)
21.1 创建帧缓冲区对象 gl.createFramebuffer()
调用示例:gl.createFramebuffer()
--------------------------------------------------------------------------
函数功能:创建帧缓冲区对象
--------------------------------------------------------------------------
参数 无
--------------------------------------------------------------------------
返回值 non-null 新创建的帧缓冲区对象
null 创建帧缓冲区对象失败
--------------------------------------------------------------------------
错误 无
21.2 删除帧缓冲区对象 gl.deleteFramebuffer()
调用示例:gl.deleteFramebuffer(framebuffer)
--------------------------------------------------------------------------
函数功能:删除帧缓冲区对象
--------------------------------------------------------------------------
参数 framebuffer 指定要删除的帧缓冲区对象
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错误 无
21.3 创建渲染缓冲区对象 gl.createRenderbuffer()
调用示例:gl.createRenderbuffer()
--------------------------------------------------------------------------
函数功能:创建渲染缓冲区对象
--------------------------------------------------------------------------
参数 无
--------------------------------------------------------------------------
返回值 non-null 新创建的渲染缓冲区对象
null 创建渲染缓冲区对象失败
--------------------------------------------------------------------------
错误 无
21.4 删除渲染缓冲区对象 gl.deleteRenderbuffer()
调用示例:gl.deleteRenderbuffer(renderbuffer)
--------------------------------------------------------------------------
函数功能:删除渲染缓冲区对象
--------------------------------------------------------------------------
参数 renderbuffer 指定要删除的渲染缓冲区对象
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错误 无
21.5 绑定渲染缓冲区 gl.bindRenderbuffer()
在使用创建出的渲染缓冲区之前,还需要先将它绑定到目标上
调用示例:gl.bindRenderbuffer(target, renderbuffer)
--------------------------------------------------------------------------
函数功能:将renderbuffer指定的渲染缓冲区对象绑定在target目标上,
如果renderbuffer为null,则将已经绑定在target目标上的渲染缓冲区对象解除绑定
--------------------------------------------------------------------------
参数
target 必须为 gl.RENDERBUFFER
renderbuffer 指定要绑定的渲染缓冲区对象
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错误 INVALID_ENUM target 不是 gl.RENDERBUFFER
21.6 设置渲染缓冲区尺寸 gl.renderbufferStorage()
渲染缓冲区完成绑定后,就可设置它的格式、宽度、高度等,这里需要注意
作为深度关联对象的渲染缓冲区,宽度和高度必须与作为颜色关联对象的纹理缓冲区一致
调用示例:gl.renderbufferStorage(target, internalforamt, width, height)
-----------------------------------------------------------------------------------
函数功能:创建并初始化渲染缓冲区的数据区
-----------------------------------------------------------------------------------
参数
target 必须为 gl.RENDERBUFFER
internalforamt 指定渲染缓冲区中的数据格式,可以是以下几项参数
gl.EDPTH_COMPONENT16 表示渲染缓冲区将替代深度缓冲区
gl.STENCIL_INDEX8 表示渲染缓冲区将替代模板缓冲区
gl.RGBA4 表示渲染缓冲区将替代颜色缓冲区,RGBA四个分量各占4比特
gl.RGB5_A1 表示渲染缓冲区将替代颜色缓冲区,RGB各占5比特,A占1比特
gl.RGB565 表示渲染缓冲区将替代颜色缓冲区,RGB分别占5、6、5比特
width 和 height 表示渲染缓冲区的宽度和高度,以像素为单位
-----------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------
错误 INVALID_ENUM target 不是 gl.RENDERBUFFER
INVALID_OPERATION target上没有绑定渲染缓冲区
21.7 绑定帧缓冲区 gl.bindFramebuffer()
调用示例:gl.bindFramebuffer(target, framebuffer)
--------------------------------------------------------------------------
函数功能:将framebuffer指定的帧缓冲区对象绑定在target目标上,
如果framebuffer为null,则将已经绑定在target目标上的帧缓冲区对象解除绑定
--------------------------------------------------------------------------
参数
target 必须为 gl.FRAMEBUFFER
framebuffer 指定要绑定的帧缓冲区对象
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错误 INVALID_ENUM target 不是 gl.FRAMEBUFFER
21.8 纹理对象关联到帧缓冲区对象 gl.framebufferTexture2D()
调用示例:gl.framebufferTexture2D(target, attachment, textarget, texture, level)
-----------------------------------------------------------------------------------------
函数功能:将texture指定的纹理对象关联到绑定在target目标上的帧缓冲区对象
-----------------------------------------------------------------------------------------
参数
target 必须为 gl.FRAMEBUFFER
attachment 指定关联的类型
gl.COLOR_ATTACHMENT0 表示texture是颜色关联对象
gl.DEPTH_ATTACHMENT 表示texture是深度关联对象
textarget gl.TEXTURE_2D或gl.TEXTURE_BUVE_MAP分别代表二维纹理和立方体纹理
texture 指定关联的纹理对象
level 指定为0(在使用MIPMAP纹理时指定纹理的层级)
-----------------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------------
错误 INVALID_ENUM target 不是 gl.FRAMEBUFFER 或者attachment或textarget的值无效
INVALID_VALUE level的值无效
INVALID_OPERATION target上没有绑定帧缓冲区
21.9 将渲染缓冲区对象关联到帧缓冲区对象 gl.framebufferRenderbuffer()
调用示例:gl.framebufferRenderbuffer(target, attachment, renderbuffertarget, renderbuffer)
-----------------------------------------------------------------------------------------
函数功能:将renderbuffer指定的渲染缓冲区对象关联到绑定在target目标上的帧缓冲区对象
-----------------------------------------------------------------------------------------
参数
target 必须为 gl.FRAMEBUFFER
attachment 指定关联的类型
gl.COLOR_ATTACHMENT0 表示renderbuffer是颜色关联对象
gl.DEPTH_ATTACHMENT 表示renderbuffer是深度关联对象
gl.STENCIL_ATTACHMENT 表示renderbuffer是模板关联对象
renderbuffertarget 必须是 gl.RENDERBUFFER
renderbuffer 指定要关联的渲染缓冲区对象
-----------------------------------------------------------------------------------------
返回值 无
-----------------------------------------------------------------------------------------
错误 INVALID_ENUM target 不是 gl.FRAMEBUFFER 或者renderbuffer不是gl.RENDERBUFFER,
或者attachment的值无效
21.10 检查帧缓冲区的配置 gl.checkFramebufferStatus()
调用示例:gl.checkFramebufferStatus(target)
-----------------------------------------------------------------------------------------
函数功能:检查绑定在target上的帧缓冲区对象的配置状态
-----------------------------------------------------------------------------------------
参数 target 必须为 gl.FRAMEBUFFER
-----------------------------------------------------------------------------------------
返回值 0 target不是gl.FRAMEBUFFER
其他
gl.FRAMEBUFFER_COMPLETE 帧缓冲区对象已正确配置
gl.FRAMEBUFFER_INCOMPLETE_ATTACHMENT 某一个关联对象为空,或者关联对象不合法
gl.FRAMEBUFFER_INCOMPLETE_DIMENSIONS 颜色关联对象和深度关联对象尺寸不一致
gl.FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT 帧缓冲区未关联任何关联对象
-----------------------------------------------------------------------------------------
错误 INVALID_ENUM target 不是 gl.FRAMEBUFFER
21.11 设置绘图区域 gl.viewport()
在进行离线绘图前还需要做一项工作,设置绘图区域的大小
调用示例:gl.viewport(x, y, width, height)
--------------------------------------------------------------------------
函数功能:设置gl.drawArrays() 和 gl.drawElements() 函数的绘图区域,
在canvas上绘图时,x和y就是canvas中的坐标
--------------------------------------------------------------------------
参数
x,y 指定绘图区域的左上角,以像素为单位
width,height 指定绘图区域的宽度和高度
--------------------------------------------------------------------------
返回值 无
--------------------------------------------------------------------------
错误 无