JavaScript WebGL 使用图片
引子
- 数据
- 顶点着色器
- 片元着色器
- 缓冲纹理坐标数据
- 加载并创建纹理
- 绘制
JavaScript WebGL 设置颜色效果始终有限,这时候就会想到使用图片,这就涉及到 WebGL 中的纹理使用,比预想中要麻烦的多。
- Origin
- My GitHub
绘制矩形的基础上主要有以下几个方面的变化:
- 数据
- 顶点着色器
- 片元着色器
- 缓冲纹理坐标数据
- 加载并创建纹理
- 绘制
createTexture 创建纹理对象,接着使用 bindTexture 并绑定到对应的目标,这里是二维的图片,第一个参数值取 gl.TEXTURE_2D
表示二维纹理,第二个参数是纹理对象,当为 null
时表示取消绑定。绑定之后才能对纹理进行进一步操作。
- 数据
- 顶点着色器
- 片元着色器
- 缓冲纹理坐标数据
- 加载并创建纹理
- 绘制
createTexture 创建纹理对象,接着使用 bindTexture 并绑定到对应的目标,这里是二维的图片,第一个参数值取 gl.TEXTURE_2D
表示二维纹理,第二个参数是纹理对象,当为 null
时表示取消绑定。绑定之后才能对纹理进行进一步操作。
pixelStorei 方法对图像进行反转 Y 方向坐标,这是因为图片的坐标系统和纹理参考的坐标系不一样。
texParameteri 方法设置纹理的各种参数,这里需要特地说明一下,如果希望使用各种尺寸的图片,需要对水平和垂直填充进行上面的设置,否则只能显示特定尺寸的图片。
texImage2D 方法把纹理源赋值给纹理对象,这里就是把图像的像素数据传给纹理对象,这样才能在绘制纹理的时候看到图像。
activeTexture 方法激活指定的纹理,纹理单元的范围是 0 到 gl.MAX_COMBINED_TEXTURE_IMAGE_UNITS - 1
,这里只有一个,取值为 gl.TEXTUREI0
。默认的第一个纹理单元总是激活的,所以这行代码可以去掉。
uniform1i 方法指定对应的值,第二个参数表示纹理单元,这里 0 就是第一个纹理单元。
/**
* 绘制
* @param {*} gl WebGL 上下文
* @param {*} shaderProgram 着色器程序
*/
function draw(gl, shaderProgram) {
// 获取纹理采样器
const samplerUniform = gl.getUniformLocation(shaderProgram, "uSampler");
// 指定全局变量关联的纹理单元
gl.uniform1i(samplerUniform, 0);
gl.drawElements(gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0);
}
示例, 效果如下:
/**
* 绘制
* @param {*} gl WebGL 上下文
* @param {*} shaderProgram 着色器程序
*/
function draw(gl, shaderProgram) {
// 获取纹理采样器
const samplerUniform = gl.getUniformLocation(shaderProgram, "uSampler");
// 指定全局变量关联的纹理单元
gl.uniform1i(samplerUniform, 0);
gl.drawElements(gl.TRIANGLES, 6, gl.UNSIGNED_SHORT, 0);
}
如果对比原图的话,可以发现这张图片变形了,并没有自适应。
Back to top