textrue纹理
纹理可以认为是现实生活中的贴纸,我们将一个图片贴在我们画好的形状上。我们首先要获取到贴纸(纹理的数据),然后把它对准形状的位置贴好(纹理地址)。
纹理一般是用在图片上读取到数据,图片上的数据既有顶点的数据也有颜色的数据,webgl已经提供了API来进行自动处理,我们不需要把它们进行拆分。
我们需要先传给顶点着色器,再传给片断着色器。这是因为webgl只提供了绑定顶点着色器上attribute的方法:

我们来看看简单的着色器代码。
- 顶点着色器
attribute vec2 a_position;
attribute vec2 a_texCoord;
varying vec2 v_texCoord;
void main() {
gl_Position = vec4(a_position , 0, 1);
v_texCoord = a_texCoord;
- 片断着色器
precision mediump float;
uniform sampler2D u_image;
varying vec2 v_texCoord;
void main() {
gl_FragColor = texture2D(u_image, v_texCoord).bgra;
1.读取图片
前面我们绑定的顶点位置的数据不在赘述,我们之间看纹理如何绑定。
引入图片:
laodImage(imgURL) {
return new Promise((resolve) => {
const image = new Image();
image.src = imgURL;
image.onload = function () {
resolve(image);
}).then((res) => res);
const image = await this.laodImage('/img,jpg');
2.创建纹理缓存
var texture = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, texture);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST);
3.把贴纸(纹理数据)递给program
gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, image);
4.图片贴的位置(纹理地址)
很显然,贴的地址和画的形状一样,需要传入一组数据才能进行对应。
所以着色器是通过attribute
来接受。
所以一组数据需要缓存区来保存。
const texCoordLocation = gl.getAttribLocation(program, 'a_texCoord');
var texCoordBuffer = gl.createBuffer();
gl.bindBuffer(gl.ARRAY_BUFFER, texCoordBuffer);
gl.bufferData(gl.ARRAY_BUFFER, new Float32Array([0, 0, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1]), gl.STATIC_DRAW);
gl.enableVertexAttribArray(texCoordLocation);
gl.vertexAttribPointer(texCoordLocation, 2, gl.FLOAT, false, 0, 0);
由于我们画的是正方形,所以一共需要画2次的三角形来进行拼接,同样,也需要一一对应顶点的位置,告诉shader如何把贴纸贴在“正确的地方”。