canvas本身不支持glsl着色器,但通过获取webgl上下文(gl.getcontext('webgl'))可运行顶点和片段着色器实现gpu加速;需编写glsl es代码、编译着色器、绑定纹理与uniform参数,并配合完整渲染管线(vbo、属性指针、drawarrays)才能生效。

核心前提:启用 WebGL 渲染上下文
Canvas 默认使用 2D 上下文(getContext('2d')),它只提供 CPU 绘图 API,无法加载着色器。要使用自定义着色器,必须获取 WebGL 上下文:
- 调用
canvas.getContext('webgl')或getContext('webgl2') - 确保浏览器支持 WebGL(现代主流浏览器均支持)
- 检查返回值是否为
null,避免静默失败
编写与编译着色器代码
你需要分别准备顶点着色器(.vert)和片段着色器(.frag),两者都使用 GLSL ES 语法(WebGL 版本对应 GLSL ES 1.0 / 3.0):
- 顶点着色器负责处理顶点位置、UV 坐标、法线等输入,并输出给片段着色器
- 片段着色器决定每个像素的颜色,是实现滤镜、光照、噪声等效果的关键
- 示例片段着色器(灰度):
#version 300 es
in vec2 v_texcoord;
uniform sampler2D u_texture;
out vec4 fragColor;
void main() {
vec4 color = texture(u_texture, v_texcoord);
float gray = dot(color.rgb, vec3(0.299, 0.587, 0.114));
fragColor = vec4(gray, gray, gray, color.a);
}
着色器需经 WebGL 编译流程:gl.createShader → gl.shaderSource → gl.compileShader → 检查编译状态。
绑定纹理与 uniform 参数
要在着色器中使用图像或动态参数,需将数据上传至 GPU:
- 图像资源需先转为 WebGL 纹理(
gl.createTexture+gl.texImage2D) - 统一变量(uniform)如时间、强度、颜色偏移等,通过
gl.getUniformLocation获取位置后,用gl.uniform1f、gl.uniform4fv等设置 - 常见可动画参数:
u_time(实时秒数)、u_resolution(画布尺寸)、u_mouse(交互坐标)
渲染流程:从几何到像素
着色器不会自动生效,必须配合完整的渲染管线:
- 创建并绑定顶点缓冲区(VBO),传入三角形顶点(如全屏四边形)
- 配置顶点属性指针(
gl.vertexAttribPointer),关联着色器中的in变量 - 激活着色器程序(
gl.useProgram) - 绑定纹理单元、设置 uniform、调用
gl.drawArrays或gl.drawElements
注意:Canvas 尺寸变化时,需同步更新 WebGL 的 viewport 和 u_resolution 值,否则坐标错位。











