WebGL中的调试

WebGL中的调试,webgl,webgl2,webgl-extensions,Webgl,Webgl2,Webgl Extensions,我正在学习WebGL,我能感觉到我的速度太慢了,因为我在调试代码时遇到了困难。是否有任何扩展或工具可以帮助我了解缓冲区、属性指针、矩阵等的值 我在谷歌上搜索并了解了chrome扩展spector.js,但这对我来说不起作用。我认为它应该显示框架或上下文,但当我单击时,它什么也不显示。 几秒钟后单击红色按钮时,它会显示: 未检测到帧。尝试移动相机或实现requestAnimationFrame。是的,WebGL很难调试,我不确定是否有什么能让它变得简单。大多数bug都不是调试器可以轻易找

我正在学习WebGL,我能感觉到我的速度太慢了,因为我在调试代码时遇到了困难。是否有任何扩展或工具可以帮助我了解缓冲区、属性指针、矩阵等的值

我在谷歌上搜索并了解了chrome扩展spector.js,但这对我来说不起作用。我认为它应该显示框架或上下文,但当我单击时,它什么也不显示。



几秒钟后单击红色按钮时,它会显示:
未检测到帧。尝试移动相机或实现requestAnimationFrame。

是的,WebGL很难调试,我不确定是否有什么能让它变得简单。大多数bug都不是调试器可以轻易找到的。浏览器已报告某些错误,如大小正确的不可渲染纹理或缓冲区。其他的bug通常是数学bug、逻辑bug或数据bug。例如,没有简单的方法单步执行WebGL着色器

在任何情况下,如果您想使用spector,您需要将代码结构为友好的spector。Spector正在基于requestAnimationFrame查找帧

那么,让我们来看看最后一个例子

代码有一个
main
函数,如下所示


function main() {
  // Get A WebGL context
  /** @type {HTMLCanvasElement} */
  var canvas = document.querySelector("#canvas");
  var gl = canvas.getContext("webgl");
  if (!gl) {
    return;
  }


  // setup GLSL program
  var program = webglUtils.createProgramFromScripts(gl, ["vertex-shader-3d", "fragment-shader-3d"]);
  ...
}

main();

function main() {
  // Get A WebGL context
  /** @type {HTMLCanvasElement} */
  var canvas = document.querySelector("#canvas");
  var gl = canvas.getContext("webgl");
  if (!gl) {
    return;
  }

  const startElem = document.querySelector('button');
  startElem.addEventListener('click', start, {once: true});

  function start() {
    // run the initialization in rAF since spector only captures inside rAF events
    requestAnimationFrame(() => {
      init(gl);
    });
    // make so more frames so spector has something to look at.
    // Note: a normal webgl app would have a rAF loop: https://webglfundamentals.org/webgl/lessons/webgl-animation.html
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
  }
}

main();
我把它改成了这个。我将
main
重命名为
init
,并使其在gl上下文中传递

function init(gl) {
  // setup GLSL program
  var program = webglUtils.createProgramFromScripts(gl, ["vertex-shader-3d", "fragment-shader-3d"]);

  ...
}
然后我做了一个新的
main
,看起来像这样


function main() {
  // Get A WebGL context
  /** @type {HTMLCanvasElement} */
  var canvas = document.querySelector("#canvas");
  var gl = canvas.getContext("webgl");
  if (!gl) {
    return;
  }


  // setup GLSL program
  var program = webglUtils.createProgramFromScripts(gl, ["vertex-shader-3d", "fragment-shader-3d"]);
  ...
}

main();

function main() {
  // Get A WebGL context
  /** @type {HTMLCanvasElement} */
  var canvas = document.querySelector("#canvas");
  var gl = canvas.getContext("webgl");
  if (!gl) {
    return;
  }

  const startElem = document.querySelector('button');
  startElem.addEventListener('click', start, {once: true});

  function start() {
    // run the initialization in rAF since spector only captures inside rAF events
    requestAnimationFrame(() => {
      init(gl);
    });
    // make so more frames so spector has something to look at.
    // Note: a normal webgl app would have a rAF loop: https://webglfundamentals.org/webgl/lessons/webgl-animation.html
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
    requestAnimationFrame(() => {});
  }
}

main();
我在html中添加了一个按钮

<button type="button">start</button>
<canvas id="canvas"></canvas>

您可以做的另一件事是在每个WebGL函数之后使用助手调用
gl.getError
。这是一个你可以使用的脚本

<script src="https://greggman.github.io/webgl-helpers/webgl-gl-error-check.js"></script>

感谢您上网,帮助像我这样努力学习的人!!!我浪费了几个小时才发现VertexAttribute指针的类型是gl.BYE而不是gl.BYTE。我把那句话读了好几遍,但我的眼睛还是看不见。浏览器没有显示任何错误,这对我来说太烦人了!!!这很奇怪,你应该得到一个
无效的\u ENUM
errorNo,但是有一个警告,但没有错误,所以我找不到错误的来源。如果你使用底部提到的脚本,它将在错误发生的地方停止。你能告诉我为什么有多个requestAnimationFrame而没有回调吗。我不明白。是的,谢谢你创造了这个伟大的东西,这是一个伟大的工具和真棒。