我收到错误消息:Error: WebGL warning: drawElements: Tex image TEXTURE_2D level 0 is incurring lazy initialization.在 WebGL 上,我想知道实际上是什么意思。
无论如何,延迟初始化如何在单线程应用程序中成为问题?我理解为当你在 getter 中初始化一个变量时?
我试着寻找我的错误信息并没有真正找到任何关于它的好信息。
这是我处理纹理的代码:
const images = await Promise.all(model.maps.map(map => new Promise((resolve, reject) => {
const image = new Image();
image.src = map;
image.onload = event => {
const texture = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, texture);
gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, image.width, image.height, 0, gl.RGBA, gl.FLOAT, null);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE);
gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE);
gl.bindTexture(gl.TEXTURE_2D, null);
resolve(texture);
};
image.onerror = error => {
console.log(error);
resolve(null);
};
})));
Run Code Online (Sandbox Code Playgroud)
我的绘图功能的相关部分基本上是:
gl.bindTexture(gl.TEXTURE_2D, textures[material.textureIndex]);
gl.activeTexture(gl.TEXTURE0);
gl.drawElements(gl.TRIANGLES, material.faceCount * 3, gl.UNSIGNED_SHORT, drawnCount);
Run Code Online (Sandbox Code Playgroud)
话虽如此,如果我使用 6 参数语法:gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.FLOAT, image);那么此错误消息不再显示,我设法正确呈现。
gma*_*man 14
这不是错误。这是一个警告。
错误:WebGL警告...
它在前面说“错误”非常令人困惑,但即使它只说“警告”我已经争论了很长时间它是一个不好的警告。
警告是 WebGL 需要做一些重要的工作。
当你制作一个纹理并且你没有向它传递任何数据时,你null作为最后一个参数传递给texImage2D,这意味着在某个时候 WebGL 必须清除纹理。假设纹理是 2048x2048 RGBA/UNSIGNED_BYTE。实际上,WebGL 必须分配 16meg 的 ram (2048x2048x4),将 16meg 的 ram 清除为 0,并gl.texSubImage2D在实际使用纹理之前调用在纹理中置零。如果他们不这样做,纹理中将包含随机数据,可能是机密、密码、以前的图形内存(如照片)或其他任何数据。
因此,警告告诉您发生了一些重要的工作。
此警告的问题是停止警告的解决方法比警告本身更糟糕。解决方法是让您自己清除纹理。为此,您需要在 JavaScript 中分配 16meg,就像在new Uint8Array(2048 * 2048 * 4). 这意味着 JavaScript 正在分配 16 兆字节,它还清除了 16 兆字节。它还分配一个Uint8Array对象来跟踪该 16meg。该Uint8Array对象是一个复杂的 JavaScript 对象,可能是多个组合在一起的对象的集合,例如,ArrayBuffer还分配了一个对象。这些对象都有原型链,并且能够添加属性和方法以及 getter 和 setter。那Uint8Array和ArrayBuffer还必须进行跟踪,以便以后可以对它们进行垃圾回收,这意味着它们甚至存在开销。更糟糕的是,如果浏览器是 Chrome 的多进程,我相信 Firefox 正在努力,那么在 JavaScript 中分配的 16meg 必须复制到 GPU 进程,这意味着首先 GPU 进程也需要分配 16meg 的 ram,数据必须从运行网页的进程复制到 GPU 进程,以便它可以传递给图形驱动程序。甚至更多的工作。
因此,换句话说,让 Firefox 关闭其警告实际上会使您的代码变慢并使用更多内存,如果 Firefox 只是默默地自行清除纹理。因此,为什么我说警告不应该存在
Firefox 的开发人员有一个观点,即任何时候 WebGL 做一些重要的事情他们都想给你一个警告。鉴于治愈使您的代码更重,我不同意他们的 POV。Chrome 不会发出此警告。这也让开发人员感到困惑,因为他们认为他们做错了什么。他们没有做错任何事。
https://bugzilla.mozilla.org/show_bug.cgi?id=1478216
至于没有渲染的东西,在你发布的代码中,你没有在纹理中放置任何东西,所以纹理当然是 0,0,0,0。
| 归档时间: |
|
| 查看次数: |
2987 次 |
| 最近记录: |