如何从 ArrayBuffer 在 WebGL 中渲染图像

2023-12-20

我正在服务器端读取一张图像,并通过 AJAX 调用推送到 Web 浏览器。我有一个要求,我必须使用 WebGL 逐行渲染它们。

例如:图像为 640X480,其中 640 是宽度,480 是高度。现在像素总数将为 640*480 = 307200 像素。所以,我想使用 WebGL 在循环中以 640(总宽度)间隔渲染整个图像。

现在我在 webgl 中有texture2D(据我所知)可以这样做,但不知道从哪里开始。我还带着 ArrayBuffer,唯一的事情是使用Texture2D,我想缓慢地逐行渲染它。

我准备好使用任何 js 库,如果它们满足要求的话。 因此,要逐行写入图像,我们可以这样做。

顶点着色器

  • attribute vec2 a_position;?
    attribute vec2 a_texCoord;?
    
    void main() {
       ???
    }
    
  • 片段着色器

     #ifdef GL_ES
     precision mediump float;
     #endif
    
    uniform float time;
    uniform vec2 mouse;
    uniform vec2 resolution;
    
    void main( void ) {
      vec2 position = 1.0 - gl_FragCoord.xy / resolution;
      vec3 color = vec3(1.0);
    
      if (time > position.y * 10.0) {
          color = texture2D(uImage0, uv);
      }
    
     gl_FragColor = vec4(color, 1.0);
    
    }
    
  • Javascript 用于逐像素渲染

      function createTextureFromArray(gl, dataArray, type, width, height) {
            var data = new Uint8Array(dataArray);
            var texture = gl.createTexture();
            gl.bindTexture(gl.TEXTURE_2D, texture);
            gl.texImage2D(gl.TEXTURE_2D, 0, type, width, height, 0, type, gl.UNSIGNED_BYTE, data);
            return texture;
     }
    
       var arrayBuffer = new ArrayBuffer(640*480);
       for (var i=0; i < 640; i++) {
           for (var j=0; j < 480; j++) {
               arrayBuffer[i] = Math.floor(Math.random() * 255) + 0;     //filling buffer with random data between 0 and 255 which will be further filled to the texture 
               //NOTE : above data is just dummy data , I will get this data from server pixel by pixel.
           }
       }
       var gl = canvas.getContext('webgl');
       // setup GLSL program
       var program = createProgramFromScripts(gl, ["2d-vertex-shader", "2d-fragment-shader"]);
       gl.useProgram(program);
       //what should I add after this ?
    

    任何人都可以完成代码,我不知道如何编写代码来完成此任务。


OpenGL 并不是为了“逐行”绘制图像而设计的。但是,您可以在软件中实现此效果,方法是写入数组,将其作为纹理上传,并在绘制全屏多边形时在着色器中对其进行采样。

为此,您应该创建一个无符号字节数组。对于图像中的每个像素,您可以拥有红色、绿色、蓝色和 Alpha 通道的某种组合。最简单的情况是 RGB,每个像素 3 个无符号字节。最终数组的大小应根据组件大小 (3) 乘以宽度 (640) 再乘以高度 (480)。您应该根据您想要的背景颜色初始化数组中的值,然后使用 texImage2D 将其上传到 GPU。

“逐行绘制”将是在给定一行的同时更新“宽度”像素。每次更改图像数据时,您都应该将图像重新上传到 GPU,然后绘制全屏多边形。

全屏多边形只是覆盖屏幕整个剪辑空间的两个三角形。屏幕的 x 和 y 维度从 -1 到 1,因此相应地创建一个数组缓冲区,用两个三角形上传它,并在更新纹理时调用 drawArrays。多边形的 UV 应从 0 到 1,因此在顶点着色器中,您应该有一个“变化”的输出变量,该变量将为 0.5 * 位置 + 0.5。这在片段着色器中用于从纹理中采样。

官方文档是最好的学习场所之一。 openGL ES 或 openGL 3 的官方参考页包含相关信息,而参考卡https://www.khronos.org/files/webgl/webgl-reference-card-1_0.pdf https://www.khronos.org/files/webgl/webgl-reference-card-1_0.pdf显示 WebGL 中大致对应于相同 api 的可用函数。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何从 ArrayBuffer 在 WebGL 中渲染图像 的相关文章

随机推荐