WebGL 着色器保存多个 32 位值

安东乙

我需要在每个 WebGL 片段着色器调用中最多保存 8 个 32 位值(包括当没有 OES_texture_float 或 OES_texture_half_float 扩展可用时)。似乎我只能通过将它打包成 4x8bits RGBA gl_FragColor 来存储单个 32 位值。有没有办法存储 8 个值?

在片段着色器中每次调用绘制超过一个 vec4 值的数据的唯一方法是使用WEBGL_draw_buffers它让您将多个颜色附件绑定到帧缓冲区,然后在单个片段着色器调用中使用

gl_FragData[constAttachmentIndex] = result;

如果WEBGL_draw_buffers不可用,我能想到的唯一解决方法是

  1. 在多个绘制调用中渲染。

    调用gl.drawArrays渲染第一个vec4,然后再次使用不同的参数或不同的着色器渲染第二个vec4

  2. 基于 gl_FragCoord 渲染,您可以在其中更改每个像素的输出。

    换句话说,第一个像素得到第一个 vec4,第二个像素得到第二个 vec4,依此类推。例如

    float mode = mod(gl_Fragcoord.x, 2.);
    gl_FragColor = mix(result1, result2, mode);
    

    通过这种方式,结果是这样存储的

    1212121212
    1212121212
    1212121212
    

    成一种质地。对于更多 vec4s,你可以这样做

    float mode = mod(gl_Fragcoord.x, 4.); // 4 vec4s
    if (mode < 0.5) {
      gl_FragColor = result1;
    } else if (mode < 1.5) {
      gl_FragColor = result2;
    } else if (mode < 2.5) {
      gl_FragColor = result3;
    } else {
      gl_FragColor = result4;
    }
    

    这可能比方法#1 快也可能不快。您的着色器更复杂,因为它可能会为每个像素同时计算 result1 和 result2,但根据 GPU 和流水线,您可能会免费获得其中的一些。

至于获得 32 位值,即使没有,OES_texture_float您基本上也将不得不使用上述 3 种技术之一写出更多的 8 位值。

在 WebGL2 中绘制缓冲区是一个必需的功能,而在 WebGL1 中它是可选的。在 WebGL2 中,还有将顶点着色器的输出(变量)写入缓冲区的转换反馈。

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章