在WebGL中通过着色器进行上色
本系列文章翻译自:https://developer.mozilla.org/en/WebGL
本文地址:https://developer.mozilla.org/en/WebGL/Using_shaders_to_apply_color_in_WebGL
翻译说明:水平有限并且不会逐字逐句翻译,只保证符合原文意思。
在上一篇文章中,我们创建了一个方形,下面很明显要给它添加一些颜色了。我们通过修改着色器来实现。
为顶点添加颜色
在GL中,对象是通过顶点集合来构建的,每个顶点包含位置和颜色。其他像素上的颜色(其他属性也如此,包括位置)是通过线性插值计算而得,自动创建一种平滑过度的渐变效果。之前我们没有指定顶点任何颜色,着色器为每个像素设置为白色,整个方形也是白色的。
假设我们希望渲染一种渐变效果,使得方形的四个角的颜色分别为:红色、蓝色、绿色和白色。首先要为4个顶点指定颜色,创建一个顶点的颜色数组,并存储在WebGL缓冲区中,我们需要在initBuffer()函数中添加如下代码:
var colors = [
1.0, 1.0, 1.0, 1.0, // 白色
1.0, 0.0, 0.0, 1.0, // 红色
0.0, 1.0, 0.0, 1.0, // 绿色
0.0, 0.0, 1.0, 1.0 // 蓝色
];
squareVerticesColorBuffer = gl.createBuffer();
gl.bindBuffer(gl.ARRAY_BUFFER, squareVerticesColorBuffer);
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array(colors), gl.STATIC_DRAW);
}
这段代码开始时创建一个JavaScript数组,用来放置四个颜色向量。接着通过一个新的缓冲区来存储这些颜色,数组被转换为WebGL浮点数并存储在缓冲区中。
为了让这些颜色发挥作用,顶点着色器需要进行更新以便从颜色缓冲区中获取正确的颜色。
<script id="shader-vs" type="x-shader/x-vertex">
attribute vec3 aVertexPosition;
attribute vec4 aVertexColor;
uniform mat4 uMVMatrix;
uniform mat4 uPMatrix;
varying lowp vec4 vColor;
void main(void) {
gl_Position = uPMatrix * uMVMatrix * vec4(aVertexPosition, 1.0);
vColor = aVertexColor;
}
</script>
关键的差别在于对每个顶点来说,我们都将其颜色设置为数组中对应的颜色值。
为片段着色
我们的片段着色器之前是这样的:
<script id="shader-fs" type="x-shader/x-fragment">
void main(void) {
gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0);
}
</script>
为了选择颜色,我们修改代码以便从vColor中获取颜色值:
<script id="shader-fs" type="x-shader/x-fragment">
varying lowp vec4 vColor;
void main(void) {
gl_FragColor = vColor;
}
</script>
修改很简单,每个片段根据自己相对顶点的位置会获得某个插值颜色,这个颜色不是固定的。
用颜色绘制
下面,该轮到在initShaders中添加代码来为着色程序初始化颜色属性了。
vertexColorAttribute = gl.getAttribLocation(shaderProgram, "aVertexColor");
gl.enableVertexAttribArray(vertexColorAttribute);
接着修改drawScene方法,以便在绘制方形时上色:
gl.bindBuffer(gl.ARRAY_BUFFER, squareVerticesColorBuffer);
gl.vertexAttribPointer(vertexColorAttribute, 4, gl.FLOAT, false, 0, 0);
此时,如果你在WebGL兼容的浏览器里查看这个示例,你会看到下面的显示效果: