Javascript 是否可以在WebGL/OpenGL中获得低于特定像素值的像素数?

Javascript 是否可以在WebGL/OpenGL中获得低于特定像素值的像素数?,javascript,webgl,Javascript,Webgl,class-WebGLUtils{ getGLContext=(画布,版本)=>{ canvas.width=window.innerWidth*0.99; canvas.height=window.innerHeight*0.85; var gl=canvas.getContext(版本?'webgl':'webgl2'); 常量ext=gl.getExtension(“ext\u color\u buffer\u float”); 如果(!ext){ log(“抱歉,无法渲染为浮点纹理”);

class-WebGLUtils{
getGLContext=(画布,版本)=>{
canvas.width=window.innerWidth*0.99;
canvas.height=window.innerHeight*0.85;
var gl=canvas.getContext(版本?'webgl':'webgl2');
常量ext=gl.getExtension(“ext\u color\u buffer\u float”);
如果(!ext){
log(“抱歉,无法渲染为浮点纹理”);
}
gl.clearColor(0,0,0,1.0);
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT |);
gl.线宽(0.5);
返回总账;
};
清除=(总帐)=>{
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT |);
};
getShader=(gl、类型、shaderText)=>{
var vfs=gl.createShader(类型);
gl.shaderSource(vfs、shaderText);
总帐编译主管(vfs);
if(!gl.getShaderParameter(vfs,gl.COMPILE_状态)){
console.error(gl.getShaderInfoLog(vfs));
}
返回vfs;
};
getProgram=(gl、vertexShader、fragmentShader)=>{
var program=gl.createProgram();
gl.attachShader(程序,this.getShader(gl,gl.VERTEX_着色器,document.getElementById(vertexShader.text.trim());
gl.attachShader(程序,this.getShader(gl,gl.FRAGMENT_着色器,document.getElementById(fragmentShader.text.trim());
总账链接程序(程序);
if(!gl.getProgramParameter(程序、总账链接状态)){
控制台错误(gl.getProgramInfoLog(程序));
}
返回程序;
};
getPreCompiledProgram=(gl、vertexShader、fragmentShader)=>{
var program=gl.createProgram();
gl.attachShader(程序,this.getShader(gl,gl.VERTEX_着色器,vertexShader));
gl.attachShader(程序,this.getShader(gl,gl.FRAGMENT_着色器,fragmentShader));
总账链接程序(程序);
if(!gl.getProgramParameter(程序、总账链接状态)){
控制台错误(gl.getProgramInfoLog(程序));
}
返回程序;
};
createAndBindBuffer=(gl,相关顶点)=>{
var buffer=gl.createBuffer();
gl.bindBuffer(gl.ARRAY\u BUFFER,BUFFER);
gl.bufferData(gl.ARRAY\u BUFFER、新Float32Array(相关顶点)、gl.STATIC\u DRAW);
gl.bindBuffer(gl.ARRAY\u BUFFER,null);
返回缓冲区;
};
createAndBindTexture=(gl、img、AR)=>{
var texBuffer=gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D,texBuffer);
如果(img.宽度){
gl.texImage2D(gl.TEXTURE_2D,0,gl.RGBA,gl.RGBA,gl.UNSIGNED_BYTE,img);
}否则{
gl.texImage2D(gl.TEXTURE_2D,0,gl.RGBA,AR.width,AR.height,0,gl.RGBA,gl.UNSIGNED_字节,img);
}
//设置筛选,这样我们就不需要mips了
gl.texParameteri(gl.TEXTURE\u 2D,gl.TEXTURE\u MIN\u过滤器,gl.LINEAR);
gl.texParameteri(gl.TEXTURE\u 2D,gl.TEXTURE\u MAG\u过滤器,gl.LINEAR);
gl.texParameteri(gl.TEXTURE_2D、gl.TEXTURE_WRAP_S、gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE\u 2D、gl.TEXTURE\u WRAP\u T、gl.CLAMP\u至边缘);
gl.bindTexture(gl.TEXTURE_2D,空);
返回缓冲区;
};
createTextureAndFramebuffer=(总图、宽度、高度、类型、过滤器)=>{
常量tex=gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D,tex);
if(类型===gl.无符号字节){
gl.texImage2D(gl.TEXTURE_2D,0,gl.RGBA,宽度,高度,0,gl.RGBA,类型,null);
}否则{
const status=gl.checkFramebufferStatus(gl.FRAMEBUFFER);
log(`can${status==gl.FRAMEBUFFER_COMPLETE?“:“NOT”}呈现给R32`);
gl.texImage2D(gl.TEXTURE_2D,0,gl.R32F,宽度,高度,0,gl.RED,类型,空);
}
gl.texParameteri(gl.TEXTURE\u 2D,gl.TEXTURE\u MIN\u过滤器,过滤器);
gl.texParameteri(gl.TEXTURE\u 2D、gl.TEXTURE\u MAG\u过滤器、过滤器);
gl.texParameteri(gl.TEXTURE_2D、gl.TEXTURE_WRAP_S、gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE\u 2D、gl.TEXTURE\u WRAP\u T、gl.CLAMP\u至边缘);
const fb=gl.createFramebuffer();
gl.bindFramebuffer(gl.FRAMEBUFFER,fb);
gl.framebufferTexture2D(gl.FRAMEBUFFER,gl.COLOR_ATTACHMENT0,gl.TEXTURE_2D,tex,0);
返回{tex:tex,fb:fb};
};
linkAndSendDataToGPU=(总账、程序、linkedVariable、缓冲区、维度)=>{
变量顶点=gl.GetAttriblLocation(程序,链接变量);
gl.EnableVertexAttribute数组(顶点);
gl.bindBuffer(gl.ARRAY\u BUFFER,BUFFER);
gl.VertexAttribute指针(顶点、尺寸、gl.FLOAT、gl.FALSE、0、0);
返回顶点;
};
sendDataToGPU=(总图、缓冲区、顶点、尺寸)=>{
gl.bindBuffer(gl.ARRAY\u BUFFER,BUFFER);
gl.VertexAttribute指针(顶点、尺寸、gl.FLOAT、gl.FALSE、0、0);
};
sendTextureToGPU=(总图、纹理、索引)=>{
gl.activeTexture(gl.TEXTURE0+索引);
gl.bindTexture(gl.TEXTURE_2D,tex);
};
activateTextureByIndex=(gl、程序、gpuRef、gpuTextureIndex)=>{
gl.useProgram(程序);
gl.uniform1i(gl.getUniformLocation(program,gpuRef),gpuTextureIndex);
}
};
var gl、utils、伪img、img;
var rectCoords=[-1.0,-1.0,1.0,-1.0,-1.0,1.0,-1.0,-1.0,-1.0,1.0,1.0];
var texCoords=[0.0,0.0,1.0,0.0,0.0,1.0,1.0,0.0,0.0,1.0,1.0];
var-pixelCount=0;
document.addEventListener('DOMContentLoaded',()=>{
utils=新的WebGLUtils();
gl=utils.getGLContext(document.getElementById('canvas');
var showProgram=utils.getProgram(gl,“新vs”,“显示fs”);
var像素计数程序;
var vertexBuffer=utils.createAndBindBuffer(gl,rectCoords);
utils.activateTextureByIndex(gl,showProgram,“u_纹理”,1);
var checkPixels=(myFbi)=>{
总账使用程序(showProgram);
gl.bindFramebuffer(gl.FRAMEBUFFER,null);
总图视口(0,0,总图画布宽度,总图画布高度);
utils.sendTextureToGPU(g
  uniform sampler2D data;
  const int width = ${imageData.width};
  const int height = ${imageData.height};
  void main() {
    float count = 0.0;
    vec2 size = vec2(width, height);
    for (int y = 0; y < height; ++y) {
      for (int x = 0; x < width; ++x) {
        float data = texture2D(data, (vec2(x, y) + 0.5) / size).r;
        if (data < 229.0 / 255.0) {
          count += 1.0;
        }
      }
    }
    gl_FragColor = vec4(
        mod(count, 256.0),
        mod(floor(count / 256.0), 256.0),
        mod(floor(count / 256.0 / 256.0), 256.0),
        floor(count / 256.0 / 256.0 / 256.0)) / 255.0;
  }
}
  const result = new Uint8Array(4);
  gl.readPixels(0, 0, 1, 1, gl.RGBA, gl.UNSIGNED_BYTE, result);
  const count = result[0] + 
                result[1] * 256 + 
                result[2] * 256 * 256 +
                result[3] * 256 * 256 * 256;